1706f2543Smrg/************************************************************************** 2706f2543Smrg 3706f2543SmrgCopyright (c) 2002-2007 Apple Inc. All Rights Reserved. 4706f2543SmrgCopyright (c) 2003 Torrey T. Lyons. All Rights Reserved. 5706f2543Smrg 6706f2543SmrgPermission is hereby granted, free of charge, to any person obtaining a 7706f2543Smrgcopy of this software and associated documentation files (the 8706f2543Smrg"Software"), to deal in the Software without restriction, including 9706f2543Smrgwithout limitation the rights to use, copy, modify, merge, publish, 10706f2543Smrgdistribute, sub license, and/or sell copies of the Software, and to 11706f2543Smrgpermit persons to whom the Software is furnished to do so, subject to 12706f2543Smrgthe following conditions: 13706f2543Smrg 14706f2543SmrgThe above copyright notice and this permission notice (including the 15706f2543Smrgnext paragraph) shall be included in all copies or substantial portions 16706f2543Smrgof the Software. 17706f2543Smrg 18706f2543SmrgTHE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 19706f2543SmrgOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 20706f2543SmrgMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. 21706f2543SmrgIN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR 22706f2543SmrgANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 23706f2543SmrgTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 24706f2543SmrgSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25706f2543Smrg 26706f2543Smrg**************************************************************************/ 27706f2543Smrg 28706f2543Smrg#include "sanitizedCarbon.h" 29706f2543Smrg 30706f2543Smrg#ifdef HAVE_DIX_CONFIG_H 31706f2543Smrg#include <dix-config.h> 32706f2543Smrg#endif 33706f2543Smrg 34706f2543Smrg#include "quartzCommon.h" 35706f2543Smrg 36706f2543Smrg#include "misc.h" 37706f2543Smrg#include "dixstruct.h" 38706f2543Smrg#include "globals.h" 39706f2543Smrg#include "extnsionst.h" 40706f2543Smrg#include "colormapst.h" 41706f2543Smrg#include "cursorstr.h" 42706f2543Smrg#include "scrnintstr.h" 43706f2543Smrg#include "windowstr.h" 44706f2543Smrg#include "servermd.h" 45706f2543Smrg#include "swaprep.h" 46706f2543Smrg#include "propertyst.h" 47706f2543Smrg#include <X11/Xatom.h> 48706f2543Smrg#include "darwin.h" 49706f2543Smrg#define _APPLEWM_SERVER_ 50706f2543Smrg#include <X11/extensions/applewmproto.h> 51706f2543Smrg#include "applewmExt.h" 52706f2543Smrg#include "X11Application.h" 53706f2543Smrg#include "protocol-versions.h" 54706f2543Smrg 55706f2543Smrg#define DEFINE_ATOM_HELPER(func,atom_name) \ 56706f2543Smrgstatic Atom func (void) { \ 57706f2543Smrg static int generation; \ 58706f2543Smrg static Atom atom; \ 59706f2543Smrg if (generation != serverGeneration) { \ 60706f2543Smrg generation = serverGeneration; \ 61706f2543Smrg atom = MakeAtom (atom_name, strlen (atom_name), TRUE); \ 62706f2543Smrg } \ 63706f2543Smrg return atom; \ 64706f2543Smrg} 65706f2543Smrg 66706f2543SmrgDEFINE_ATOM_HELPER(xa_native_screen_origin, "_NATIVE_SCREEN_ORIGIN") 67706f2543SmrgDEFINE_ATOM_HELPER (xa_apple_no_order_in, "_APPLE_NO_ORDER_IN") 68706f2543Smrg 69706f2543Smrgstatic AppleWMProcsPtr appleWMProcs; 70706f2543Smrg 71706f2543Smrgstatic int WMErrorBase; 72706f2543Smrg 73706f2543Smrg 74706f2543Smrgstatic unsigned char WMReqCode = 0; 75706f2543Smrgstatic int WMEventBase = 0; 76706f2543Smrg 77706f2543Smrgstatic RESTYPE ClientType, EventType; /* resource types for event masks */ 78706f2543Smrgstatic XID eventResource; 79706f2543Smrg 80706f2543Smrg/* Currently selected events */ 81706f2543Smrgstatic unsigned int eventMask = 0; 82706f2543Smrg 83706f2543Smrgstatic int WMFreeClient (pointer data, XID id); 84706f2543Smrgstatic int WMFreeEvents (pointer data, XID id); 85706f2543Smrgstatic void SNotifyEvent(xAppleWMNotifyEvent *from, xAppleWMNotifyEvent *to); 86706f2543Smrg 87706f2543Smrgtypedef struct _WMEvent *WMEventPtr; 88706f2543Smrgtypedef struct _WMEvent { 89706f2543Smrg WMEventPtr next; 90706f2543Smrg ClientPtr client; 91706f2543Smrg XID clientResource; 92706f2543Smrg unsigned int mask; 93706f2543Smrg} WMEventRec; 94706f2543Smrg 95706f2543Smrgstatic inline BoxRec 96706f2543Smrgmake_box (int x, int y, int w, int h) 97706f2543Smrg{ 98706f2543Smrg BoxRec r; 99706f2543Smrg r.x1 = x; 100706f2543Smrg r.y1 = y; 101706f2543Smrg r.x2 = x + w; 102706f2543Smrg r.y2 = y + h; 103706f2543Smrg return r; 104706f2543Smrg} 105706f2543Smrg 106706f2543Smrg/* Updates the _NATIVE_SCREEN_ORIGIN property on the given root window. */ 107706f2543Smrgvoid 108706f2543SmrgAppleWMSetScreenOrigin( 109706f2543Smrg WindowPtr pWin 110706f2543Smrg) 111706f2543Smrg{ 112706f2543Smrg int32_t data[2]; 113706f2543Smrg 114706f2543Smrg data[0] = pWin->drawable.pScreen->x + darwinMainScreenX; 115706f2543Smrg data[1] = pWin->drawable.pScreen->y + darwinMainScreenY; 116706f2543Smrg 117706f2543Smrg dixChangeWindowProperty(serverClient, pWin, xa_native_screen_origin(), 118706f2543Smrg XA_INTEGER, 32, PropModeReplace, 2, data, TRUE); 119706f2543Smrg} 120706f2543Smrg 121706f2543Smrg/* Window managers can set the _APPLE_NO_ORDER_IN property on windows 122706f2543Smrg that are being genie-restored from the Dock. We want them to 123706f2543Smrg be mapped but remain ordered-out until the animation 124706f2543Smrg completes (when the Dock will order them in). */ 125706f2543SmrgBool 126706f2543SmrgAppleWMDoReorderWindow( 127706f2543Smrg WindowPtr pWin 128706f2543Smrg) 129706f2543Smrg{ 130706f2543Smrg Atom atom; 131706f2543Smrg PropertyPtr prop; 132706f2543Smrg int rc; 133706f2543Smrg 134706f2543Smrg atom = xa_apple_no_order_in(); 135706f2543Smrg rc = dixLookupProperty(&prop, pWin, atom, serverClient, DixReadAccess); 136706f2543Smrg 137706f2543Smrg if(Success == rc && prop->type == atom) 138706f2543Smrg return 0; 139706f2543Smrg 140706f2543Smrg return 1; 141706f2543Smrg} 142706f2543Smrg 143706f2543Smrg 144706f2543Smrgstatic int 145706f2543SmrgProcAppleWMQueryVersion( 146706f2543Smrg register ClientPtr client 147706f2543Smrg) 148706f2543Smrg{ 149706f2543Smrg xAppleWMQueryVersionReply rep; 150706f2543Smrg register int n; 151706f2543Smrg 152706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMQueryVersionReq); 153706f2543Smrg rep.type = X_Reply; 154706f2543Smrg rep.length = 0; 155706f2543Smrg rep.sequenceNumber = client->sequence; 156706f2543Smrg rep.majorVersion = SERVER_APPLEWM_MAJOR_VERSION; 157706f2543Smrg rep.minorVersion = SERVER_APPLEWM_MINOR_VERSION; 158706f2543Smrg rep.patchVersion = SERVER_APPLEWM_PATCH_VERSION; 159706f2543Smrg if (client->swapped) { 160706f2543Smrg swaps(&rep.sequenceNumber, n); 161706f2543Smrg swapl(&rep.length, n); 162706f2543Smrg } 163706f2543Smrg WriteToClient(client, sizeof(xAppleWMQueryVersionReply), (char *)&rep); 164706f2543Smrg return Success; 165706f2543Smrg} 166706f2543Smrg 167706f2543Smrg 168706f2543Smrg/* events */ 169706f2543Smrg 170706f2543Smrgstatic inline void 171706f2543SmrgupdateEventMask (WMEventPtr *pHead) 172706f2543Smrg{ 173706f2543Smrg WMEventPtr pCur; 174706f2543Smrg 175706f2543Smrg eventMask = 0; 176706f2543Smrg for (pCur = *pHead; pCur != NULL; pCur = pCur->next) 177706f2543Smrg eventMask |= pCur->mask; 178706f2543Smrg} 179706f2543Smrg 180706f2543Smrg/*ARGSUSED*/ 181706f2543Smrgstatic int 182706f2543SmrgWMFreeClient (pointer data, XID id) { 183706f2543Smrg WMEventPtr pEvent; 184706f2543Smrg WMEventPtr *pHead, pCur, pPrev; 185706f2543Smrg int i; 186706f2543Smrg 187706f2543Smrg pEvent = (WMEventPtr) data; 188706f2543Smrg i = dixLookupResourceByType((pointer *)&pHead, eventResource, EventType, serverClient, DixReadAccess | DixWriteAccess | DixDestroyAccess); 189706f2543Smrg if (i == Success && pHead) { 190706f2543Smrg pPrev = 0; 191706f2543Smrg for (pCur = *pHead; pCur && pCur != pEvent; pCur=pCur->next) 192706f2543Smrg pPrev = pCur; 193706f2543Smrg if (pCur) { 194706f2543Smrg if (pPrev) 195706f2543Smrg pPrev->next = pEvent->next; 196706f2543Smrg else 197706f2543Smrg *pHead = pEvent->next; 198706f2543Smrg } 199706f2543Smrg updateEventMask (pHead); 200706f2543Smrg } 201706f2543Smrg free((pointer) pEvent); 202706f2543Smrg return 1; 203706f2543Smrg} 204706f2543Smrg 205706f2543Smrg/*ARGSUSED*/ 206706f2543Smrgstatic int 207706f2543SmrgWMFreeEvents (pointer data, XID id) { 208706f2543Smrg WMEventPtr *pHead, pCur, pNext; 209706f2543Smrg 210706f2543Smrg pHead = (WMEventPtr *) data; 211706f2543Smrg for (pCur = *pHead; pCur; pCur = pNext) { 212706f2543Smrg pNext = pCur->next; 213706f2543Smrg FreeResource (pCur->clientResource, ClientType); 214706f2543Smrg free((pointer) pCur); 215706f2543Smrg } 216706f2543Smrg free((pointer) pHead); 217706f2543Smrg eventMask = 0; 218706f2543Smrg return 1; 219706f2543Smrg} 220706f2543Smrg 221706f2543Smrgstatic int 222706f2543SmrgProcAppleWMSelectInput (register ClientPtr client) 223706f2543Smrg{ 224706f2543Smrg REQUEST(xAppleWMSelectInputReq); 225706f2543Smrg WMEventPtr pEvent, pNewEvent, *pHead; 226706f2543Smrg XID clientResource; 227706f2543Smrg int i; 228706f2543Smrg 229706f2543Smrg REQUEST_SIZE_MATCH (xAppleWMSelectInputReq); 230706f2543Smrg i = dixLookupResourceByType((pointer *)&pHead, eventResource, EventType, client, DixWriteAccess); 231706f2543Smrg if (stuff->mask != 0) { 232706f2543Smrg if (i == Success && pHead) { 233706f2543Smrg /* check for existing entry. */ 234706f2543Smrg for (pEvent = *pHead; pEvent; pEvent = pEvent->next) 235706f2543Smrg { 236706f2543Smrg if (pEvent->client == client) 237706f2543Smrg { 238706f2543Smrg pEvent->mask = stuff->mask; 239706f2543Smrg updateEventMask (pHead); 240706f2543Smrg return Success; 241706f2543Smrg } 242706f2543Smrg } 243706f2543Smrg } 244706f2543Smrg 245706f2543Smrg /* build the entry */ 246706f2543Smrg pNewEvent = (WMEventPtr) malloc(sizeof (WMEventRec)); 247706f2543Smrg if (!pNewEvent) 248706f2543Smrg return BadAlloc; 249706f2543Smrg pNewEvent->next = 0; 250706f2543Smrg pNewEvent->client = client; 251706f2543Smrg pNewEvent->mask = stuff->mask; 252706f2543Smrg /* 253706f2543Smrg * add a resource that will be deleted when 254706f2543Smrg * the client goes away 255706f2543Smrg */ 256706f2543Smrg clientResource = FakeClientID (client->index); 257706f2543Smrg pNewEvent->clientResource = clientResource; 258706f2543Smrg if (!AddResource (clientResource, ClientType, (pointer)pNewEvent)) 259706f2543Smrg return BadAlloc; 260706f2543Smrg /* 261706f2543Smrg * create a resource to contain a pointer to the list 262706f2543Smrg * of clients selecting input. This must be indirect as 263706f2543Smrg * the list may be arbitrarily rearranged which cannot be 264706f2543Smrg * done through the resource database. 265706f2543Smrg */ 266706f2543Smrg if (i != Success || !pHead) 267706f2543Smrg { 268706f2543Smrg pHead = (WMEventPtr *) malloc(sizeof (WMEventPtr)); 269706f2543Smrg if (!pHead || 270706f2543Smrg !AddResource (eventResource, EventType, (pointer)pHead)) 271706f2543Smrg { 272706f2543Smrg FreeResource (clientResource, RT_NONE); 273706f2543Smrg return BadAlloc; 274706f2543Smrg } 275706f2543Smrg *pHead = 0; 276706f2543Smrg } 277706f2543Smrg pNewEvent->next = *pHead; 278706f2543Smrg *pHead = pNewEvent; 279706f2543Smrg updateEventMask (pHead); 280706f2543Smrg } else if (stuff->mask == 0) { 281706f2543Smrg /* delete the interest */ 282706f2543Smrg if (i == Success && pHead) { 283706f2543Smrg pNewEvent = 0; 284706f2543Smrg for (pEvent = *pHead; pEvent; pEvent = pEvent->next) { 285706f2543Smrg if (pEvent->client == client) 286706f2543Smrg break; 287706f2543Smrg pNewEvent = pEvent; 288706f2543Smrg } 289706f2543Smrg if (pEvent) { 290706f2543Smrg FreeResource (pEvent->clientResource, ClientType); 291706f2543Smrg if (pNewEvent) 292706f2543Smrg pNewEvent->next = pEvent->next; 293706f2543Smrg else 294706f2543Smrg *pHead = pEvent->next; 295706f2543Smrg free(pEvent); 296706f2543Smrg updateEventMask (pHead); 297706f2543Smrg } 298706f2543Smrg } 299706f2543Smrg } else { 300706f2543Smrg client->errorValue = stuff->mask; 301706f2543Smrg return BadValue; 302706f2543Smrg } 303706f2543Smrg return Success; 304706f2543Smrg} 305706f2543Smrg 306706f2543Smrg/* 307706f2543Smrg * deliver the event 308706f2543Smrg */ 309706f2543Smrg 310706f2543Smrgvoid 311706f2543SmrgAppleWMSendEvent (int type, unsigned int mask, int which, int arg) { 312706f2543Smrg WMEventPtr *pHead, pEvent; 313706f2543Smrg xAppleWMNotifyEvent se; 314706f2543Smrg int i; 315706f2543Smrg 316706f2543Smrg i = dixLookupResourceByType((pointer *)&pHead, eventResource, EventType, serverClient, DixReadAccess); 317706f2543Smrg if (i != Success || !pHead) 318706f2543Smrg return; 319706f2543Smrg for (pEvent = *pHead; pEvent; pEvent = pEvent->next) { 320706f2543Smrg if ((pEvent->mask & mask) == 0) 321706f2543Smrg continue; 322706f2543Smrg se.type = type + WMEventBase; 323706f2543Smrg se.kind = which; 324706f2543Smrg se.arg = arg; 325706f2543Smrg se.time = currentTime.milliseconds; 326706f2543Smrg WriteEventsToClient (pEvent->client, 1, (xEvent *) &se); 327706f2543Smrg } 328706f2543Smrg} 329706f2543Smrg 330706f2543Smrg/* Safe to call from any thread. */ 331706f2543Smrgunsigned int 332706f2543SmrgAppleWMSelectedEvents (void) 333706f2543Smrg{ 334706f2543Smrg return eventMask; 335706f2543Smrg} 336706f2543Smrg 337706f2543Smrg 338706f2543Smrg/* general utility functions */ 339706f2543Smrg 340706f2543Smrgstatic int 341706f2543SmrgProcAppleWMDisableUpdate( 342706f2543Smrg register ClientPtr client 343706f2543Smrg) 344706f2543Smrg{ 345706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMDisableUpdateReq); 346706f2543Smrg 347706f2543Smrg appleWMProcs->DisableUpdate(); 348706f2543Smrg 349706f2543Smrg return Success; 350706f2543Smrg} 351706f2543Smrg 352706f2543Smrgstatic int 353706f2543SmrgProcAppleWMReenableUpdate( 354706f2543Smrg register ClientPtr client 355706f2543Smrg) 356706f2543Smrg{ 357706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMReenableUpdateReq); 358706f2543Smrg 359706f2543Smrg appleWMProcs->EnableUpdate(); 360706f2543Smrg 361706f2543Smrg return Success; 362706f2543Smrg} 363706f2543Smrg 364706f2543Smrg 365706f2543Smrg/* window functions */ 366706f2543Smrg 367706f2543Smrgstatic int 368706f2543SmrgProcAppleWMSetWindowMenu( 369706f2543Smrg register ClientPtr client 370706f2543Smrg) 371706f2543Smrg{ 372706f2543Smrg const char *bytes, **items; 373706f2543Smrg char *shortcuts; 374706f2543Smrg int max_len, nitems, i, j; 375706f2543Smrg REQUEST(xAppleWMSetWindowMenuReq); 376706f2543Smrg 377706f2543Smrg REQUEST_AT_LEAST_SIZE(xAppleWMSetWindowMenuReq); 378706f2543Smrg 379706f2543Smrg nitems = stuff->nitems; 380706f2543Smrg items = malloc(sizeof (char *) * nitems); 381706f2543Smrg shortcuts = malloc(sizeof (char) * nitems); 382706f2543Smrg 383706f2543Smrg max_len = (stuff->length << 2) - sizeof(xAppleWMSetWindowMenuReq); 384706f2543Smrg bytes = (char *) &stuff[1]; 385706f2543Smrg 386706f2543Smrg for (i = j = 0; i < max_len && j < nitems;) 387706f2543Smrg { 388706f2543Smrg shortcuts[j] = bytes[i++]; 389706f2543Smrg items[j++] = bytes + i; 390706f2543Smrg 391706f2543Smrg while (i < max_len) 392706f2543Smrg { 393706f2543Smrg if (bytes[i++] == 0) 394706f2543Smrg break; 395706f2543Smrg } 396706f2543Smrg } 397706f2543Smrg X11ApplicationSetWindowMenu (nitems, items, shortcuts); 398706f2543Smrg free(items); 399706f2543Smrg free(shortcuts); 400706f2543Smrg 401706f2543Smrg return Success; 402706f2543Smrg} 403706f2543Smrg 404706f2543Smrgstatic int 405706f2543SmrgProcAppleWMSetWindowMenuCheck( 406706f2543Smrg register ClientPtr client 407706f2543Smrg) 408706f2543Smrg{ 409706f2543Smrg REQUEST(xAppleWMSetWindowMenuCheckReq); 410706f2543Smrg 411706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMSetWindowMenuCheckReq); 412706f2543Smrg X11ApplicationSetWindowMenuCheck(stuff->index); 413706f2543Smrg return Success; 414706f2543Smrg} 415706f2543Smrg 416706f2543Smrgstatic int 417706f2543SmrgProcAppleWMSetFrontProcess( 418706f2543Smrg register ClientPtr client 419706f2543Smrg) 420706f2543Smrg{ 421706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMSetFrontProcessReq); 422706f2543Smrg 423706f2543Smrg X11ApplicationSetFrontProcess(); 424706f2543Smrg return Success; 425706f2543Smrg} 426706f2543Smrg 427706f2543Smrgstatic int 428706f2543SmrgProcAppleWMSetWindowLevel(register ClientPtr client) 429706f2543Smrg{ 430706f2543Smrg REQUEST(xAppleWMSetWindowLevelReq); 431706f2543Smrg WindowPtr pWin; 432706f2543Smrg int err; 433706f2543Smrg 434706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMSetWindowLevelReq); 435706f2543Smrg 436706f2543Smrg if (Success != dixLookupWindow(&pWin, stuff->window, client, 437706f2543Smrg DixReadAccess)) 438706f2543Smrg return BadValue; 439706f2543Smrg 440706f2543Smrg if (stuff->level < 0 || stuff->level >= AppleWMNumWindowLevels) { 441706f2543Smrg return BadValue; 442706f2543Smrg } 443706f2543Smrg 444706f2543Smrg err = appleWMProcs->SetWindowLevel(pWin, stuff->level); 445706f2543Smrg if (err != Success) { 446706f2543Smrg return err; 447706f2543Smrg } 448706f2543Smrg 449706f2543Smrg return Success; 450706f2543Smrg} 451706f2543Smrg 452706f2543Smrgstatic int 453706f2543SmrgProcAppleWMSendPSN(register ClientPtr client) 454706f2543Smrg{ 455706f2543Smrg REQUEST(xAppleWMSendPSNReq); 456706f2543Smrg int err; 457706f2543Smrg 458706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMSendPSNReq); 459706f2543Smrg 460706f2543Smrg if(!appleWMProcs->SendPSN) 461706f2543Smrg return BadRequest; 462706f2543Smrg 463706f2543Smrg err = appleWMProcs->SendPSN(stuff->psn_hi, stuff->psn_lo); 464706f2543Smrg if (err != Success) { 465706f2543Smrg return err; 466706f2543Smrg } 467706f2543Smrg 468706f2543Smrg return Success; 469706f2543Smrg} 470706f2543Smrg 471706f2543Smrgstatic int 472706f2543SmrgProcAppleWMAttachTransient(register ClientPtr client) 473706f2543Smrg{ 474706f2543Smrg WindowPtr pWinChild, pWinParent; 475706f2543Smrg REQUEST(xAppleWMAttachTransientReq); 476706f2543Smrg int err; 477706f2543Smrg 478706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMAttachTransientReq); 479706f2543Smrg 480706f2543Smrg if(!appleWMProcs->AttachTransient) 481706f2543Smrg return BadRequest; 482706f2543Smrg 483706f2543Smrg if (Success != dixLookupWindow(&pWinChild, stuff->child, client, DixReadAccess)) 484706f2543Smrg return BadValue; 485706f2543Smrg 486706f2543Smrg if(stuff->parent) { 487706f2543Smrg if(Success != dixLookupWindow(&pWinParent, stuff->parent, client, DixReadAccess)) 488706f2543Smrg return BadValue; 489706f2543Smrg } else { 490706f2543Smrg pWinParent = NULL; 491706f2543Smrg } 492706f2543Smrg 493706f2543Smrg err = appleWMProcs->AttachTransient(pWinChild, pWinParent); 494706f2543Smrg if (err != Success) { 495706f2543Smrg return err; 496706f2543Smrg } 497706f2543Smrg 498706f2543Smrg return Success; 499706f2543Smrg} 500706f2543Smrg 501706f2543Smrgstatic int 502706f2543SmrgProcAppleWMSetCanQuit( 503706f2543Smrg register ClientPtr client 504706f2543Smrg) 505706f2543Smrg{ 506706f2543Smrg REQUEST(xAppleWMSetCanQuitReq); 507706f2543Smrg 508706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMSetCanQuitReq); 509706f2543Smrg 510706f2543Smrg X11ApplicationSetCanQuit(stuff->state); 511706f2543Smrg return Success; 512706f2543Smrg} 513706f2543Smrg 514706f2543Smrg 515706f2543Smrg/* frame functions */ 516706f2543Smrg 517706f2543Smrgstatic int 518706f2543SmrgProcAppleWMFrameGetRect( 519706f2543Smrg register ClientPtr client 520706f2543Smrg) 521706f2543Smrg{ 522706f2543Smrg xAppleWMFrameGetRectReply rep; 523706f2543Smrg BoxRec ir, or, rr; 524706f2543Smrg REQUEST(xAppleWMFrameGetRectReq); 525706f2543Smrg 526706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMFrameGetRectReq); 527706f2543Smrg rep.type = X_Reply; 528706f2543Smrg rep.length = 0; 529706f2543Smrg rep.sequenceNumber = client->sequence; 530706f2543Smrg 531706f2543Smrg ir = make_box (stuff->ix, stuff->iy, stuff->iw, stuff->ih); 532706f2543Smrg or = make_box (stuff->ox, stuff->oy, stuff->ow, stuff->oh); 533706f2543Smrg 534706f2543Smrg if (appleWMProcs->FrameGetRect(stuff->frame_rect, 535706f2543Smrg stuff->frame_class, 536706f2543Smrg &or, &ir, &rr) != Success) 537706f2543Smrg { 538706f2543Smrg return BadValue; 539706f2543Smrg } 540706f2543Smrg 541706f2543Smrg rep.x = rr.x1; 542706f2543Smrg rep.y = rr.y1; 543706f2543Smrg rep.w = rr.x2 - rr.x1; 544706f2543Smrg rep.h = rr.y2 - rr.y1; 545706f2543Smrg 546706f2543Smrg WriteToClient(client, sizeof(xAppleWMFrameGetRectReply), (char *)&rep); 547706f2543Smrg return Success; 548706f2543Smrg} 549706f2543Smrg 550706f2543Smrgstatic int 551706f2543SmrgProcAppleWMFrameHitTest( 552706f2543Smrg register ClientPtr client 553706f2543Smrg) 554706f2543Smrg{ 555706f2543Smrg xAppleWMFrameHitTestReply rep; 556706f2543Smrg BoxRec ir, or; 557706f2543Smrg int ret; 558706f2543Smrg REQUEST(xAppleWMFrameHitTestReq); 559706f2543Smrg 560706f2543Smrg REQUEST_SIZE_MATCH(xAppleWMFrameHitTestReq); 561706f2543Smrg rep.type = X_Reply; 562706f2543Smrg rep.length = 0; 563706f2543Smrg rep.sequenceNumber = client->sequence; 564706f2543Smrg 565706f2543Smrg ir = make_box (stuff->ix, stuff->iy, stuff->iw, stuff->ih); 566706f2543Smrg or = make_box (stuff->ox, stuff->oy, stuff->ow, stuff->oh); 567706f2543Smrg 568706f2543Smrg if (appleWMProcs->FrameHitTest(stuff->frame_class, stuff->px, 569706f2543Smrg stuff->py, &or, &ir, &ret) != Success) 570706f2543Smrg { 571706f2543Smrg return BadValue; 572706f2543Smrg } 573706f2543Smrg 574706f2543Smrg rep.ret = ret; 575706f2543Smrg 576706f2543Smrg WriteToClient(client, sizeof(xAppleWMFrameHitTestReply), (char *)&rep); 577706f2543Smrg return Success; 578706f2543Smrg} 579706f2543Smrg 580706f2543Smrgstatic int 581706f2543SmrgProcAppleWMFrameDraw( 582706f2543Smrg register ClientPtr client 583706f2543Smrg) 584706f2543Smrg{ 585706f2543Smrg BoxRec ir, or; 586706f2543Smrg unsigned int title_length, title_max; 587706f2543Smrg unsigned char *title_bytes; 588706f2543Smrg REQUEST(xAppleWMFrameDrawReq); 589706f2543Smrg WindowPtr pWin; 590706f2543Smrg 591706f2543Smrg REQUEST_AT_LEAST_SIZE(xAppleWMFrameDrawReq); 592706f2543Smrg 593706f2543Smrg if (Success != dixLookupWindow(&pWin, stuff->window, client, 594706f2543Smrg DixReadAccess)) 595706f2543Smrg return BadValue; 596706f2543Smrg 597706f2543Smrg ir = make_box (stuff->ix, stuff->iy, stuff->iw, stuff->ih); 598706f2543Smrg or = make_box (stuff->ox, stuff->oy, stuff->ow, stuff->oh); 599706f2543Smrg 600706f2543Smrg title_length = stuff->title_length; 601706f2543Smrg title_max = (stuff->length << 2) - sizeof(xAppleWMFrameDrawReq); 602706f2543Smrg 603706f2543Smrg if (title_max < title_length) 604706f2543Smrg return BadValue; 605706f2543Smrg 606706f2543Smrg title_bytes = (unsigned char *) &stuff[1]; 607706f2543Smrg 608706f2543Smrg errno = appleWMProcs->FrameDraw(pWin, stuff->frame_class, 609706f2543Smrg stuff->frame_attr, &or, &ir, 610706f2543Smrg title_length, title_bytes); 611706f2543Smrg if (errno != Success) { 612706f2543Smrg return errno; 613706f2543Smrg } 614706f2543Smrg 615706f2543Smrg return Success; 616706f2543Smrg} 617706f2543Smrg 618706f2543Smrg 619706f2543Smrg/* dispatch */ 620706f2543Smrg 621706f2543Smrgstatic int 622706f2543SmrgProcAppleWMDispatch ( 623706f2543Smrg register ClientPtr client 624706f2543Smrg) 625706f2543Smrg{ 626706f2543Smrg REQUEST(xReq); 627706f2543Smrg 628706f2543Smrg switch (stuff->data) 629706f2543Smrg { 630706f2543Smrg case X_AppleWMQueryVersion: 631706f2543Smrg return ProcAppleWMQueryVersion(client); 632706f2543Smrg } 633706f2543Smrg 634706f2543Smrg if (!LocalClient(client)) 635706f2543Smrg return WMErrorBase + AppleWMClientNotLocal; 636706f2543Smrg 637706f2543Smrg switch (stuff->data) 638706f2543Smrg { 639706f2543Smrg case X_AppleWMSelectInput: 640706f2543Smrg return ProcAppleWMSelectInput(client); 641706f2543Smrg case X_AppleWMDisableUpdate: 642706f2543Smrg return ProcAppleWMDisableUpdate(client); 643706f2543Smrg case X_AppleWMReenableUpdate: 644706f2543Smrg return ProcAppleWMReenableUpdate(client); 645706f2543Smrg case X_AppleWMSetWindowMenu: 646706f2543Smrg return ProcAppleWMSetWindowMenu(client); 647706f2543Smrg case X_AppleWMSetWindowMenuCheck: 648706f2543Smrg return ProcAppleWMSetWindowMenuCheck(client); 649706f2543Smrg case X_AppleWMSetFrontProcess: 650706f2543Smrg return ProcAppleWMSetFrontProcess(client); 651706f2543Smrg case X_AppleWMSetWindowLevel: 652706f2543Smrg return ProcAppleWMSetWindowLevel(client); 653706f2543Smrg case X_AppleWMSetCanQuit: 654706f2543Smrg return ProcAppleWMSetCanQuit(client); 655706f2543Smrg case X_AppleWMFrameGetRect: 656706f2543Smrg return ProcAppleWMFrameGetRect(client); 657706f2543Smrg case X_AppleWMFrameHitTest: 658706f2543Smrg return ProcAppleWMFrameHitTest(client); 659706f2543Smrg case X_AppleWMFrameDraw: 660706f2543Smrg return ProcAppleWMFrameDraw(client); 661706f2543Smrg case X_AppleWMSendPSN: 662706f2543Smrg return ProcAppleWMSendPSN(client); 663706f2543Smrg case X_AppleWMAttachTransient: 664706f2543Smrg return ProcAppleWMAttachTransient(client); 665706f2543Smrg default: 666706f2543Smrg return BadRequest; 667706f2543Smrg } 668706f2543Smrg} 669706f2543Smrg 670706f2543Smrgstatic void 671706f2543SmrgSNotifyEvent(xAppleWMNotifyEvent *from, xAppleWMNotifyEvent *to) { 672706f2543Smrg to->type = from->type; 673706f2543Smrg to->kind = from->kind; 674706f2543Smrg cpswaps (from->sequenceNumber, to->sequenceNumber); 675706f2543Smrg cpswapl (from->time, to->time); 676706f2543Smrg cpswapl (from->arg, to->arg); 677706f2543Smrg} 678706f2543Smrg 679706f2543Smrgstatic int 680706f2543SmrgSProcAppleWMQueryVersion( 681706f2543Smrg register ClientPtr client 682706f2543Smrg) 683706f2543Smrg{ 684706f2543Smrg register int n; 685706f2543Smrg REQUEST(xAppleWMQueryVersionReq); 686706f2543Smrg swaps(&stuff->length, n); 687706f2543Smrg return ProcAppleWMQueryVersion(client); 688706f2543Smrg} 689706f2543Smrg 690706f2543Smrgstatic int 691706f2543SmrgSProcAppleWMDispatch ( 692706f2543Smrg register ClientPtr client 693706f2543Smrg) 694706f2543Smrg{ 695706f2543Smrg REQUEST(xReq); 696706f2543Smrg 697706f2543Smrg /* It is bound to be non-local when there is byte swapping */ 698706f2543Smrg if (!LocalClient(client)) 699706f2543Smrg return WMErrorBase + AppleWMClientNotLocal; 700706f2543Smrg 701706f2543Smrg /* only local clients are allowed WM access */ 702706f2543Smrg switch (stuff->data) 703706f2543Smrg { 704706f2543Smrg case X_AppleWMQueryVersion: 705706f2543Smrg return SProcAppleWMQueryVersion(client); 706706f2543Smrg default: 707706f2543Smrg return BadRequest; 708706f2543Smrg } 709706f2543Smrg} 710706f2543Smrg 711706f2543Smrgvoid 712706f2543SmrgAppleWMExtensionInit( 713706f2543Smrg AppleWMProcsPtr procsPtr) 714706f2543Smrg{ 715706f2543Smrg ExtensionEntry* extEntry; 716706f2543Smrg 717706f2543Smrg ClientType = CreateNewResourceType(WMFreeClient, "WMClient"); 718706f2543Smrg EventType = CreateNewResourceType(WMFreeEvents, "WMEvent"); 719706f2543Smrg eventResource = FakeClientID(0); 720706f2543Smrg 721706f2543Smrg if (ClientType && EventType && 722706f2543Smrg (extEntry = AddExtension(APPLEWMNAME, 723706f2543Smrg AppleWMNumberEvents, 724706f2543Smrg AppleWMNumberErrors, 725706f2543Smrg ProcAppleWMDispatch, 726706f2543Smrg SProcAppleWMDispatch, 727706f2543Smrg NULL, 728706f2543Smrg StandardMinorOpcode))) 729706f2543Smrg { 730706f2543Smrg size_t i; 731706f2543Smrg WMReqCode = (unsigned char)extEntry->base; 732706f2543Smrg WMErrorBase = extEntry->errorBase; 733706f2543Smrg WMEventBase = extEntry->eventBase; 734706f2543Smrg for (i=0; i < AppleWMNumberEvents; i++) 735706f2543Smrg EventSwapVector[WMEventBase + i] = (EventSwapPtr) SNotifyEvent; 736706f2543Smrg appleWMProcs = procsPtr; 737706f2543Smrg } 738706f2543Smrg} 739