22 #include "pedigree/native/ipc/Ipc.h" 28 #include <arpa/inet.h> 30 #include <netinet/in.h> 34 #include <sys/select.h> 40 #include <bsd/string.h> 50 #define UNIX_PATH_MAX (sizeof sockaddr_un::sun_path) 52 #define PEDIGREE_WINMAN_ENDPOINT "pedigree-winman" 55 static bool defaultEventHandler(
56 WidgetMessages message,
size_t dataSize,
const void *dataBuffer)
66 : m_bConstructed(false), m_pFramebuffer(0), m_Handle(0),
67 m_EventCallback(defaultEventHandler), m_Socket(-1), m_SharedFramebuffer(0)
91 const char *endpoint,
const char *title, widgetCallback_t cb,
104 struct sockaddr_un meaddr;
105 memset(&meaddr, 0,
sizeof(meaddr));
106 meaddr.sun_family = AF_UNIX;
107 snprintf(meaddr.sun_path, UNIX_PATH_MAX, CLIENT_SOCKET_BASE, endpoint);
109 struct sockaddr_un saddr;
110 memset(&saddr, 0,
sizeof(saddr));
111 saddr.sun_family = AF_UNIX;
112 strncpy(saddr.sun_path, WINMAN_SOCKET_PATH, UNIX_PATH_MAX);
115 m_Socket = socket(AF_UNIX, SOCK_DGRAM, 0);
120 if (bind(m_Socket, (
struct sockaddr *) &meaddr,
sizeof(meaddr)) != 0)
122 syslog(LOG_ALERT,
"widget bind failed: %s", strerror(errno));
127 if (connect(m_Socket, (
struct sockaddr *) &saddr,
sizeof(saddr)) != 0)
129 syslog(LOG_ALERT,
"widget connection failed: %s", strerror(errno));
136 uint64_t pid = getpid();
137 uintptr_t widgetPointer =
reinterpret_cast<uintptr_t
>(
this);
141 (((widgetPointer >> 32) | (widgetPointer & 0xFFFFFFFF)) & 0xFFFFFFFF);
143 m_Handle = (pid << 32) | (widgetPointer);
148 char *messageData =
new char[totalSize];
149 memset(messageData, 0, totalSize);
160 strlcpy(pCreate->
endpoint, endpoint, 256);
161 strlcpy(pCreate->
title, title, 256);
162 pCreate->
minWidth = dimensions.getW();
163 pCreate->minHeight = dimensions.getH();
164 pCreate->
rigid =
true;
169 send(m_Socket, messageData, totalSize, 0);
170 delete[] messageData;
172 s_KnownWidgets.insert(std::make_pair(m_Handle,
this));
177 m_EventCallback = cb;
195 size_t titleLength = newTitle.length();
196 if (titleLength > 511)
201 char *messageData =
new char[totalSize];
202 memset(messageData, 0, totalSize);
214 newTitle.copy(pMessage->newTitle,
sizeof pMessage->newTitle);
217 bool result = send(m_Socket, messageData, totalSize, 0) == totalSize;
220 delete[] messageData;
233 char *messageData =
new char[totalSize];
234 memset(messageData, 0, totalSize);
245 pMessage->x = rt.getX();
246 pMessage->y = rt.getY();
247 pMessage->width = rt.getW();
248 pMessage->height = rt.getH();
252 bRet = send(m_Socket, messageData, totalSize, 0) == totalSize;
253 delete[] messageData;
264 handlePendingMessages();
278 char *messageData =
new char[totalSize];
279 memset(messageData, 0, totalSize);
290 pMessage->bVisible = vis;
293 bool result = send(m_Socket, messageData, totalSize, 0) == totalSize;
296 delete[] messageData;
309 char *messageData =
new char[totalSize];
310 memset(messageData, 0, totalSize);
322 send(m_Socket, messageData, totalSize, 0);
325 delete[] messageData;
332 delete m_pFramebuffer;
333 delete m_SharedFramebuffer;
335 m_SharedFramebuffer = 0;
341 bool bContinue =
true;
353 char *buffer =
new char[4096];
355 for (std::map<uint64_t, Widget *>::iterator it = s_KnownWidgets.begin();
356 it != s_KnownWidgets.end(); ++it)
358 Widget *pWidget = it->second;
359 max_fd = std::max(max_fd, pWidget->
getSocket());
364 tv.tv_sec = tv.tv_usec = 0;
367 int nready = select(max_fd + 1, &fds, 0, 0, bAsync ? &tv : 0);
370 for (
int i = 0; i <= max_fd; ++i)
372 if (FD_ISSET(i, &fds))
374 recv(i, buffer, 4096, 0);
393 bool bContinue =
true;
396 size_t messagesToCheck = s_PendingMessages.size();
397 for (; messagesToCheck > 0; --messagesToCheck)
399 char *buffer = s_PendingMessages.front();
400 s_PendingMessages.pop();
406 handleMessage(buffer);
411 s_PendingMessages.push(buffer);
420 char *buffer =
new char[4096];
422 for (std::map<uint64_t, Widget *>::iterator it = s_KnownWidgets.begin();
423 it != s_KnownWidgets.end(); ++it)
425 Widget *pWidget = it->second;
426 max_fd = std::max(max_fd, pWidget->
getSocket());
431 tv.tv_sec = tv.tv_usec = 0;
433 int nready = select(max_fd + 1, &fds, 0, 0, 0);
436 bool gotMessage =
false;
437 for (
int i = 0; i <= max_fd; ++i)
439 if (FD_ISSET(i, &fds))
441 recv(i, buffer, 4096, 0);
464 handleMessage(buffer);
471 s_PendingMessages.push(buffer);
482 std::map<uint64_t, Widget *>::iterator it;
483 if ((it = s_KnownWidgets.find(pMessage->
widgetHandle)) ==
484 s_KnownWidgets.end())
487 LOG_ALERT,
"no widget known for handle %lx",
492 Widget *pWidget = it->second;
501 case LibUiProtocol::Reposition:
518 cb(::Reposition,
sizeof(pReposition->
rt), &pReposition->
rt);
521 case LibUiProtocol::KeyEvent:
528 cb(::KeyUp,
sizeof(pKeyEvent->key), &pKeyEvent->key);
531 case LibUiProtocol::RawKeyEvent:
538 WidgetMessages msg = ::RawKeyUp;
539 if (pKeyEvent->state == LibUiProtocol::Down)
542 cb(msg,
sizeof(pKeyEvent->scancode), &pKeyEvent->scancode);
545 case LibUiProtocol::Focus:
548 case LibUiProtocol::NoFocus:
551 case LibUiProtocol::RequestRedraw:
554 case LibUiProtocol::Destroy:
555 cb(::Terminate, 0, 0);
558 syslog(LOG_INFO,
"** unknown event %d", pMessage->
messageCode);
564 bool bHandled = !s_PendingMessages.empty();
565 while (!s_PendingMessages.empty())
567 char *buffer = s_PendingMessages.front();
568 s_PendingMessages.pop();
PedigreeGraphics::Rect rt
New rect.
bool rigid
A 'rigid' window cannot be resized by the window manager.
char endpoint[256]
IPC endpoint for this widget.
void * shmem_handle
New handle for the shared memory space.
char title[256]
Initial title for this widget.
Abstracts a buffer shared between multiple processes.
handle_t widgetHandle
Handle for the widget being referred to. Zero if no widget.
size_t messageSize
Size of the data in the message (after this header).
size_t shmem_size
Size of the framebuffer.
size_t minWidth
Minimum width and height for the window.
MessageIdentifiers messageCode
Code of the message being sent.
bool isResponse
Whether this message is a response from the window manager or not.