darwin.c revision c8548ba8
1/************************************************************** 2 * 3 * Xquartz initialization code 4 * 5 * Copyright (c) 2007-2012 Apple Inc. 6 * Copyright (c) 2001-2004 Torrey T. Lyons. All Rights Reserved. 7 * 8 * Permission is hereby granted, free of charge, to any person obtaining a 9 * copy of this software and associated documentation files (the "Software"), 10 * to deal in the Software without restriction, including without limitation 11 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 12 * and/or sell copies of the Software, and to permit persons to whom the 13 * Software is furnished to do so, subject to the following conditions: 14 * 15 * The above copyright notice and this permission notice shall be included in 16 * all copies or substantial portions of the Software. 17 * 18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 21 * THE ABOVE LISTED COPYRIGHT HOLDER(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR 22 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 23 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 24 * DEALINGS IN THE SOFTWARE. 25 * 26 * Except as contained in this notice, the name(s) of the above copyright 27 * holders shall not be used in advertising or otherwise to promote the sale, 28 * use or other dealings in this Software without prior written authorization. 29 */ 30 31#ifdef HAVE_DIX_CONFIG_H 32#include <dix-config.h> 33#endif 34 35#include <X11/X.h> 36#include <X11/Xproto.h> 37#include "os.h" 38#include "servermd.h" 39#include "inputstr.h" 40#include "scrnintstr.h" 41#include "mipointer.h" // mi software cursor 42#include "micmap.h" // mi colormap code 43#include "fb.h" // fb framebuffer code 44#include "site.h" 45#include "globals.h" 46#include "dix.h" 47#include "xkbsrv.h" 48 49#include <X11/extensions/XI.h> 50#include <X11/extensions/XIproto.h> 51#include "exevents.h" 52#include "extinit.h" 53#include "glx_extinit.h" 54#include "xserver-properties.h" 55 56#include <sys/types.h> 57#include <sys/time.h> 58#include <sys/stat.h> 59#include <sys/syslimits.h> 60#include <stdio.h> 61#include <fcntl.h> 62#include <unistd.h> 63#include <stdarg.h> 64 65#define HAS_UTSNAME 1 66#include <sys/utsname.h> 67 68#define NO_CFPLUGIN 69#include <IOKit/hidsystem/IOHIDLib.h> 70 71#ifdef MITSHM 72#include "shmint.h" 73#endif 74 75#include "darwin.h" 76#include "darwinEvents.h" 77#include "quartzKeyboard.h" 78#include "quartz.h" 79 80#include "X11Application.h" 81 82aslclient aslc; 83 84void 85xq_asl_log(int level, const char *subsystem, const char *file, 86 const char *function, int line, const char *fmt, 87 ...) 88{ 89 va_list args; 90 aslmsg msg = asl_new(ASL_TYPE_MSG); 91 92 if (msg) { 93 char *_line; 94 95 asl_set(msg, "File", file); 96 asl_set(msg, "Function", function); 97 asprintf(&_line, "%d", line); 98 if (_line) { 99 asl_set(msg, "Line", _line); 100 free(_line); 101 } 102 if (subsystem) 103 asl_set(msg, "Subsystem", subsystem); 104 } 105 106 va_start(args, fmt); 107 asl_vlog(aslc, msg, level, fmt, args); 108 va_end(args); 109 110 if (msg) 111 asl_free(msg); 112} 113 114/* 115 * X server shared global variables 116 */ 117int darwinScreensFound = 0; 118DevPrivateKeyRec darwinScreenKeyRec; 119io_connect_t darwinParamConnect = 0; 120int darwinEventReadFD = -1; 121int darwinEventWriteFD = -1; 122// int darwinMouseAccelChange = 1; 123int darwinFakeButtons = 0; 124 125// location of X11's (0,0) point in global screen coordinates 126int darwinMainScreenX = 0; 127int darwinMainScreenY = 0; 128 129// parameters read from the command line or user preferences 130int darwinDesiredDepth = -1; 131int darwinSyncKeymap = FALSE; 132 133// modifier masks for faking mouse buttons - ANY of these bits trigger it (not all) 134#ifdef NX_DEVICELCMDKEYMASK 135int darwinFakeMouse2Mask = NX_DEVICELALTKEYMASK | NX_DEVICERALTKEYMASK; 136int darwinFakeMouse3Mask = NX_DEVICELCMDKEYMASK | NX_DEVICERCMDKEYMASK; 137#else 138int darwinFakeMouse2Mask = NX_ALTERNATEMASK; 139int darwinFakeMouse3Mask = NX_COMMANDMASK; 140#endif 141 142// Modifier mask for overriding event delivery to appkit (might be useful to set this to rcommand for input menu 143unsigned int darwinAppKitModMask = 0; // Any of these bits 144 145// Modifier mask for items in the Window menu (0 and -1 cause shortcuts to be disabled) 146unsigned int windowItemModMask = NX_COMMANDMASK; 147 148// devices 149DeviceIntPtr darwinKeyboard = NULL; 150DeviceIntPtr darwinPointer = NULL; 151DeviceIntPtr darwinTabletStylus = NULL; 152DeviceIntPtr darwinTabletCursor = NULL; 153DeviceIntPtr darwinTabletEraser = NULL; 154 155// Common pixmap formats 156static PixmapFormatRec formats[] = { 157 { 1, 1, BITMAP_SCANLINE_PAD }, 158 { 4, 8, BITMAP_SCANLINE_PAD }, 159 { 8, 8, BITMAP_SCANLINE_PAD }, 160 { 15, 16, BITMAP_SCANLINE_PAD }, 161 { 16, 16, BITMAP_SCANLINE_PAD }, 162 { 24, 32, BITMAP_SCANLINE_PAD }, 163 { 32, 32, BITMAP_SCANLINE_PAD } 164}; 165 166void 167DarwinPrintBanner(void) 168{ 169 ErrorF("Xquartz starting:\n"); 170 ErrorF("X.Org X Server %s\n", XSERVER_VERSION); 171 ErrorF("Build Date: %s\n", BUILD_DATE); 172} 173 174/* 175 * DarwinSaveScreen 176 * X screensaver support. Not implemented. 177 */ 178static Bool 179DarwinSaveScreen(ScreenPtr pScreen, int on) 180{ 181 // FIXME 182 if (on == SCREEN_SAVER_FORCER) {} 183 else if (on == SCREEN_SAVER_ON) {} 184 else {} 185 return TRUE; 186} 187 188/* 189 * DarwinScreenInit 190 * This is a callback from dix during AddScreen() from InitOutput(). 191 * Initialize the screen and communicate information about it back to dix. 192 */ 193static Bool 194DarwinScreenInit(ScreenPtr pScreen, int argc, char **argv) 195{ 196 int dpi; 197 static int foundIndex = 0; 198 Bool ret; 199 DarwinFramebufferPtr dfb; 200 201 if (!dixRegisterPrivateKey(&darwinScreenKeyRec, PRIVATE_SCREEN, 0)) 202 return FALSE; 203 204 // reset index of found screens for each server generation 205 if (pScreen->myNum == 0) { 206 foundIndex = 0; 207 208 // reset the visual list 209 miClearVisualTypes(); 210 } 211 212 // allocate space for private per screen storage 213 dfb = malloc(sizeof(DarwinFramebufferRec)); 214 215 // SCREEN_PRIV(pScreen) = dfb; 216 dixSetPrivate(&pScreen->devPrivates, darwinScreenKey, dfb); 217 218 // setup hardware/mode specific details 219 ret = QuartzAddScreen(foundIndex, pScreen); 220 foundIndex++; 221 if (!ret) 222 return FALSE; 223 224 // setup a single visual appropriate for our pixel type 225 if (!miSetVisualTypesAndMasks(dfb->depth, dfb->visuals, dfb->bitsPerRGB, 226 dfb->preferredCVC, dfb->redMask, 227 dfb->greenMask, dfb->blueMask)) { 228 return FALSE; 229 } 230 231 // TODO: Make PseudoColor visuals not suck in TrueColor mode 232 // if(dfb->depth > 8) 233 // miSetVisualTypesAndMasks(8, PseudoColorMask, 8, PseudoColor, 0, 0, 0); 234 // 235 // TODO: Re-add support for 15bit 236 // if (dfb->depth > 15) 237 // miSetVisualTypesAndMasks(15, TrueColorMask, 5, TrueColor, 238 // RM_ARGB(0, 5, 5, 5), GM_ARGB(0, 5, 5, 239 // 5), 240 // BM_ARGB(0, 5, 5, 5)); 241 if (dfb->depth > 24) 242 miSetVisualTypesAndMasks(24, TrueColorMask, 8, TrueColor, 243 RM_ARGB(0, 8, 8, 8), GM_ARGB(0, 8, 8, 244 8), 245 BM_ARGB(0, 8, 8, 8)); 246 247 miSetPixmapDepths(); 248 249 // machine independent screen init 250 // setup _Screen structure in pScreen 251 if (monitorResolution) 252 dpi = monitorResolution; 253 else 254 dpi = 96; 255 256 // initialize fb 257 if (!fbScreenInit(pScreen, 258 dfb->framebuffer, // pointer to screen bitmap 259 dfb->width, dfb->height, // screen size in pixels 260 dpi, dpi, // dots per inch 261 dfb->pitch / (dfb->bitsPerPixel / 8), // pixel width of framebuffer 262 dfb->bitsPerPixel)) { // bits per pixel for screen 263 return FALSE; 264 } 265 266 if (!fbPictureInit(pScreen, 0, 0)) { 267 return FALSE; 268 } 269 270#ifdef MITSHM 271 ShmRegisterFbFuncs(pScreen); 272#endif 273 274 // this must be initialized (why doesn't X have a default?) 275 pScreen->SaveScreen = DarwinSaveScreen; 276 277 // finish mode dependent screen setup including cursor support 278 if (!QuartzSetupScreen(pScreen->myNum, pScreen)) { 279 return FALSE; 280 } 281 282 // create and install the default colormap and 283 // set pScreen->blackPixel / pScreen->white 284 if (!miCreateDefColormap(pScreen)) { 285 return FALSE; 286 } 287 288 pScreen->x = dfb->x; 289 pScreen->y = dfb->y; 290 291 /* ErrorF("Screen %d added: %dx%d @ (%d,%d)\n", 292 index, dfb->width, dfb->height, dfb->x, dfb->y); */ 293 294 return TRUE; 295} 296 297/* 298 ============================================================================= 299 300 mouse and keyboard callbacks 301 302 ============================================================================= 303 */ 304 305static void 306DarwinInputHandlerNotify(int fd __unused, int ready __unused, void *data __unused) 307{ 308} 309 310/* 311 * DarwinMouseProc: Handle the initialization, etc. of a mouse 312 */ 313static int 314DarwinMouseProc(DeviceIntPtr pPointer, int what) 315{ 316#define NBUTTONS 3 317#define NAXES 6 318 // 3 buttons: left, middle, right 319 CARD8 map[NBUTTONS + 1] = { 0, 1, 2, 3}; 320 Atom btn_labels[NBUTTONS] = { 0 }; 321 Atom axes_labels[NAXES] = { 0 }; 322 323 switch (what) { 324 case DEVICE_INIT: 325 pPointer->public.on = FALSE; 326 327 btn_labels[0] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_LEFT); 328 btn_labels[1] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_MIDDLE); 329 btn_labels[2] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_RIGHT); 330 331 axes_labels[0] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_X); 332 axes_labels[1] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_Y); 333 axes_labels[2] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_X); 334 axes_labels[3] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_Y); 335 axes_labels[4] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_WHEEL); 336 axes_labels[5] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_HWHEEL); 337 338 // Set button map. 339 InitPointerDeviceStruct((DevicePtr)pPointer, map, NBUTTONS, 340 btn_labels, 341 (PtrCtrlProcPtr)NoopDDA, 342 GetMotionHistorySize(), NAXES, 343 axes_labels); 344 InitValuatorAxisStruct(pPointer, 0, axes_labels[0], 345 NO_AXIS_LIMITS, NO_AXIS_LIMITS, 346 0, 0, 0, Absolute); 347 InitValuatorAxisStruct(pPointer, 1, axes_labels[1], 348 NO_AXIS_LIMITS, NO_AXIS_LIMITS, 349 0, 0, 0, Absolute); 350 InitValuatorAxisStruct(pPointer, 2, axes_labels[2], 351 NO_AXIS_LIMITS, NO_AXIS_LIMITS, 352 1, 0, 1, Relative); 353 InitValuatorAxisStruct(pPointer, 3, axes_labels[3], 354 NO_AXIS_LIMITS, NO_AXIS_LIMITS, 355 1, 0, 1, Relative); 356 InitValuatorAxisStruct(pPointer, 4, axes_labels[4], 357 NO_AXIS_LIMITS, NO_AXIS_LIMITS, 358 1, 0, 1, Relative); 359 InitValuatorAxisStruct(pPointer, 5, axes_labels[5], 360 NO_AXIS_LIMITS, NO_AXIS_LIMITS, 361 1, 0, 1, Relative); 362 363 SetScrollValuator(pPointer, 4, SCROLL_TYPE_VERTICAL, -1.0, SCROLL_FLAG_PREFERRED); 364 SetScrollValuator(pPointer, 5, SCROLL_TYPE_HORIZONTAL, -1.0, SCROLL_FLAG_NONE); 365 break; 366 367 case DEVICE_ON: 368 pPointer->public.on = TRUE; 369 SetNotifyFd(darwinEventReadFD, DarwinInputHandlerNotify, X_NOTIFY_READ, NULL); 370 return Success; 371 372 case DEVICE_CLOSE: 373 case DEVICE_OFF: 374 pPointer->public.on = FALSE; 375 RemoveNotifyFd(darwinEventReadFD); 376 return Success; 377 } 378 379 return Success; 380#undef NBUTTONS 381#undef NAXES 382} 383 384static int 385DarwinTabletProc(DeviceIntPtr pPointer, int what) 386{ 387#define NBUTTONS 3 388#define NAXES 5 389 CARD8 map[NBUTTONS + 1] = { 0, 1, 2, 3 }; 390 Atom btn_labels[NBUTTONS] = { 0 }; 391 Atom axes_labels[NAXES] = { 0 }; 392 393 switch (what) { 394 case DEVICE_INIT: 395 pPointer->public.on = FALSE; 396 397 btn_labels[0] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_LEFT); 398 btn_labels[1] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_MIDDLE); 399 btn_labels[2] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_RIGHT); 400 401 axes_labels[0] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_X); 402 axes_labels[1] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_Y); 403 axes_labels[2] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_PRESSURE); 404 axes_labels[3] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_TILT_X); 405 axes_labels[4] = XIGetKnownProperty(AXIS_LABEL_PROP_ABS_TILT_Y); 406 407 // Set button map. 408 InitPointerDeviceStruct((DevicePtr)pPointer, map, NBUTTONS, 409 btn_labels, 410 (PtrCtrlProcPtr)NoopDDA, 411 GetMotionHistorySize(), NAXES, 412 axes_labels); 413 InitProximityClassDeviceStruct(pPointer); 414 415 InitValuatorAxisStruct(pPointer, 0, axes_labels[0], 416 0, XQUARTZ_VALUATOR_LIMIT, 417 1, 0, 1, Absolute); 418 InitValuatorAxisStruct(pPointer, 1, axes_labels[1], 419 0, XQUARTZ_VALUATOR_LIMIT, 420 1, 0, 1, Absolute); 421 InitValuatorAxisStruct(pPointer, 2, axes_labels[2], 422 0, XQUARTZ_VALUATOR_LIMIT, 423 1, 0, 1, Absolute); 424 InitValuatorAxisStruct(pPointer, 3, axes_labels[3], 425 -XQUARTZ_VALUATOR_LIMIT, 426 XQUARTZ_VALUATOR_LIMIT, 427 1, 0, 1, Absolute); 428 InitValuatorAxisStruct(pPointer, 4, axes_labels[4], 429 -XQUARTZ_VALUATOR_LIMIT, 430 XQUARTZ_VALUATOR_LIMIT, 431 1, 0, 1, Absolute); 432 433 // pPointer->use = IsXExtensionDevice; 434 break; 435 436 case DEVICE_ON: 437 pPointer->public.on = TRUE; 438 SetNotifyFd(darwinEventReadFD, DarwinInputHandlerNotify, X_NOTIFY_READ, NULL); 439 return Success; 440 441 case DEVICE_CLOSE: 442 case DEVICE_OFF: 443 pPointer->public.on = FALSE; 444 RemoveNotifyFd(darwinEventReadFD); 445 return Success; 446 } 447 return Success; 448#undef NBUTTONS 449#undef NAXES 450} 451 452/* 453 * DarwinKeybdProc 454 * Callback from X 455 */ 456static int 457DarwinKeybdProc(DeviceIntPtr pDev, int onoff) 458{ 459 switch (onoff) { 460 case DEVICE_INIT: 461 DarwinKeyboardInit(pDev); 462 break; 463 464 case DEVICE_ON: 465 pDev->public.on = TRUE; 466 SetNotifyFd(darwinEventReadFD, DarwinInputHandlerNotify, X_NOTIFY_READ, NULL); 467 break; 468 469 case DEVICE_OFF: 470 pDev->public.on = FALSE; 471 RemoveNotifyFd(darwinEventReadFD); 472 break; 473 474 case DEVICE_CLOSE: 475 break; 476 } 477 478 return Success; 479} 480 481/* 482 =========================================================================== 483 484 Utility routines 485 486 =========================================================================== 487 */ 488 489/* 490 * DarwinParseModifierList 491 * Parse a list of modifier names and return a corresponding modifier mask 492 */ 493int 494DarwinParseModifierList(const char *constmodifiers, int separatelr) 495{ 496 int result = 0; 497 498 if (constmodifiers) { 499 char *modifiers = strdup(constmodifiers); 500 char *modifier; 501 int nxkey; 502 char *p = modifiers; 503 504 while (p) { 505 modifier = strsep(&p, " ,+&|/"); // allow lots of separators 506 nxkey = DarwinModifierStringToNXMask(modifier, separatelr); 507 if (nxkey) 508 result |= nxkey; 509 else 510 ErrorF("fakebuttons: Unknown modifier \"%s\"\n", modifier); 511 } 512 free(modifiers); 513 } 514 return result; 515} 516 517/* 518 =========================================================================== 519 520 Functions needed to link against device independent X 521 522 =========================================================================== 523 */ 524 525/* 526 * InitInput 527 * Register the keyboard and mouse devices 528 */ 529void 530InitInput(int argc, char **argv) 531{ 532 XkbRMLVOSet rmlvo = { 533 .rules = "base", .model = "empty", .layout = "empty", 534 .variant = NULL, .options = NULL 535 }; 536 537 /* We need to really have rules... or something... */ 538 XkbSetRulesDflts(&rmlvo); 539 540 assert(Success == AllocDevicePair(serverClient, "xquartz virtual", 541 &darwinPointer, &darwinKeyboard, 542 DarwinMouseProc, DarwinKeybdProc, FALSE)); 543 544 /* here's the snippet from the current gdk sources: 545 if (!strcmp (tmp_name, "pointer")) 546 gdkdev->info.source = GDK_SOURCE_MOUSE; 547 else if (!strcmp (tmp_name, "wacom") || 548 !strcmp (tmp_name, "pen")) 549 gdkdev->info.source = GDK_SOURCE_PEN; 550 else if (!strcmp (tmp_name, "eraser")) 551 gdkdev->info.source = GDK_SOURCE_ERASER; 552 else if (!strcmp (tmp_name, "cursor")) 553 gdkdev->info.source = GDK_SOURCE_CURSOR; 554 else 555 gdkdev->info.source = GDK_SOURCE_PEN; 556 */ 557 558 darwinTabletStylus = AddInputDevice(serverClient, DarwinTabletProc, TRUE); 559 assert(darwinTabletStylus); 560 darwinTabletStylus->name = strdup("pen"); 561 562 darwinTabletCursor = AddInputDevice(serverClient, DarwinTabletProc, TRUE); 563 assert(darwinTabletCursor); 564 darwinTabletCursor->name = strdup("cursor"); 565 566 darwinTabletEraser = AddInputDevice(serverClient, DarwinTabletProc, TRUE); 567 assert(darwinTabletEraser); 568 darwinTabletEraser->name = strdup("eraser"); 569 570 DarwinEQInit(); 571 572 QuartzInitInput(argc, argv); 573} 574 575void 576CloseInput(void) 577{ 578 DarwinEQFini(); 579} 580 581/* 582 * DarwinAdjustScreenOrigins 583 * Shift all screens so the X11 (0, 0) coordinate is at the top 584 * left of the global screen coordinates. 585 * 586 * Screens can be arranged so the top left isn't on any screen, so 587 * instead use the top left of the leftmost screen as (0,0). This 588 * may mean some screen space is in -y, but it's better that (0,0) 589 * be onscreen, or else default xterms disappear. It's better that 590 * -y be used than -x, because when popup menus are forced 591 * "onscreen" by dumb window managers like twm, they'll shift the 592 * menus down instead of left, which still looks funny but is an 593 * easier target to hit. 594 */ 595void 596DarwinAdjustScreenOrigins(ScreenInfo *pScreenInfo) 597{ 598 int i, left, top; 599 600 left = pScreenInfo->screens[0]->x; 601 top = pScreenInfo->screens[0]->y; 602 603 /* Find leftmost screen. If there's a tie, take the topmost of the two. */ 604 for (i = 1; i < pScreenInfo->numScreens; i++) { 605 if (pScreenInfo->screens[i]->x < left || 606 (pScreenInfo->screens[i]->x == left && 607 pScreenInfo->screens[i]->y < top)) { 608 left = pScreenInfo->screens[i]->x; 609 top = pScreenInfo->screens[i]->y; 610 } 611 } 612 613 darwinMainScreenX = left; 614 darwinMainScreenY = top; 615 616 DEBUG_LOG("top = %d, left=%d\n", top, left); 617 618 /* Shift all screens so that there is a screen whose top left 619 * is at X11 (0,0) and at global screen coordinate 620 * (darwinMainScreenX, darwinMainScreenY). 621 */ 622 623 if (darwinMainScreenX != 0 || darwinMainScreenY != 0) { 624 for (i = 0; i < pScreenInfo->numScreens; i++) { 625 pScreenInfo->screens[i]->x -= darwinMainScreenX; 626 pScreenInfo->screens[i]->y -= darwinMainScreenY; 627 DEBUG_LOG("Screen %d placed at X11 coordinate (%d,%d).\n", 628 i, pScreenInfo->screens[i]->x, 629 pScreenInfo->screens[i]->y); 630 } 631 } 632 633 /* Update screenInfo.x/y */ 634 update_desktop_dimensions(); 635} 636 637/* 638 * InitOutput 639 * Initialize screenInfo for all actually accessible framebuffers. 640 * 641 * The display mode dependent code gets called three times. The mode 642 * specific InitOutput routines are expected to discover the number 643 * of potentially useful screens and cache routes to them internally. 644 * Inside DarwinScreenInit are two other mode specific calls. 645 * A mode specific AddScreen routine is called for each screen to 646 * actually initialize the screen with the ScreenPtr structure. 647 * After other screen setup has been done, a mode specific 648 * SetupScreen function can be called to finalize screen setup. 649 */ 650void 651InitOutput(ScreenInfo *pScreenInfo, int argc, char **argv) 652{ 653 int i; 654 655 pScreenInfo->imageByteOrder = IMAGE_BYTE_ORDER; 656 pScreenInfo->bitmapScanlineUnit = BITMAP_SCANLINE_UNIT; 657 pScreenInfo->bitmapScanlinePad = BITMAP_SCANLINE_PAD; 658 pScreenInfo->bitmapBitOrder = BITMAP_BIT_ORDER; 659 660 // List how we want common pixmap formats to be padded 661 pScreenInfo->numPixmapFormats = ARRAY_SIZE(formats); 662 for (i = 0; i < ARRAY_SIZE(formats); i++) 663 pScreenInfo->formats[i] = formats[i]; 664 665 // Discover screens and do mode specific initialization 666 QuartzInitOutput(argc, argv); 667 668 // Add screens 669 for (i = 0; i < darwinScreensFound; i++) { 670 AddScreen(DarwinScreenInit, argc, argv); 671 } 672 673 xorgGlxCreateVendor(); 674 675 DarwinAdjustScreenOrigins(pScreenInfo); 676} 677 678/* 679 * OsVendorFatalError 680 */ 681void 682OsVendorFatalError(const char *f, va_list args) 683{ 684} 685 686/* 687 * OsVendorInit 688 * Initialization of Darwin OS support. 689 */ 690void 691OsVendorInit(void) 692{ 693 if (serverGeneration == 1) { 694 char *lf; 695 char *home = getenv("HOME"); 696 assert(home); 697 assert(0 < asprintf(&lf, "%s/Library/Logs/X11", home)); 698 699 /* Ignore errors. If EEXIST, we don't care. If anything else, 700 * LogInit will handle it for us. 701 */ 702 (void)mkdir(lf, S_IRWXU | S_IRWXG | S_IRWXO); 703 free(lf); 704 705 assert(0 < 706 asprintf(&lf, "%s/Library/Logs/X11/%s.log", home, 707 bundle_id_prefix)); 708 LogInit(lf, ".old"); 709 free(lf); 710 711 DarwinPrintBanner(); 712 } 713} 714 715/* 716 * ddxProcessArgument 717 * Process device-dependent command line args. Returns 0 if argument is 718 * not device dependent, otherwise Count of number of elements of argv 719 * that are part of a device dependent commandline option. 720 */ 721int 722ddxProcessArgument(int argc, char *argv[], int i) 723{ 724 // if ( !strcmp( argv[i], "-fullscreen" ) ) { 725 // ErrorF( "Running full screen in parallel with Mac OS X Quartz window server.\n" ); 726 // return 1; 727 // } 728 729 // if ( !strcmp( argv[i], "-rootless" ) ) { 730 // ErrorF( "Running rootless inside Mac OS X window server.\n" ); 731 // return 1; 732 // } 733 734 // This command line arg is passed when launched from the Aqua GUI. 735 if (!strncmp(argv[i], "-psn_", 5)) { 736 return 1; 737 } 738 739 if (!strcmp(argv[i], "-fakebuttons")) { 740 darwinFakeButtons = TRUE; 741 ErrorF("Faking a three button mouse\n"); 742 return 1; 743 } 744 745 if (!strcmp(argv[i], "-nofakebuttons")) { 746 darwinFakeButtons = FALSE; 747 ErrorF("Not faking a three button mouse\n"); 748 return 1; 749 } 750 751 if (!strcmp(argv[i], "-fakemouse2")) { 752 if (i == argc - 1) { 753 FatalError("-fakemouse2 must be followed by a modifier list\n"); 754 } 755 if (!strcasecmp(argv[i + 1], "none") || !strcmp(argv[i + 1], "")) 756 darwinFakeMouse2Mask = 0; 757 else 758 darwinFakeMouse2Mask = DarwinParseModifierList(argv[i + 1], 1); 759 ErrorF("Modifier mask to fake mouse button 2 = 0x%x\n", 760 darwinFakeMouse2Mask); 761 return 2; 762 } 763 764 if (!strcmp(argv[i], "-fakemouse3")) { 765 if (i == argc - 1) { 766 FatalError("-fakemouse3 must be followed by a modifier list\n"); 767 } 768 if (!strcasecmp(argv[i + 1], "none") || !strcmp(argv[i + 1], "")) 769 darwinFakeMouse3Mask = 0; 770 else 771 darwinFakeMouse3Mask = DarwinParseModifierList(argv[i + 1], 1); 772 ErrorF("Modifier mask to fake mouse button 3 = 0x%x\n", 773 darwinFakeMouse3Mask); 774 return 2; 775 } 776 777 if (!strcmp(argv[i], "+synckeymap")) { 778 darwinSyncKeymap = TRUE; 779 return 1; 780 } 781 782 if (!strcmp(argv[i], "-synckeymap")) { 783 darwinSyncKeymap = FALSE; 784 return 1; 785 } 786 787 if (!strcmp(argv[i], "-depth")) { 788 if (i == argc - 1) { 789 FatalError("-depth must be followed by a number\n"); 790 } 791 darwinDesiredDepth = atoi(argv[i + 1]); 792 if (darwinDesiredDepth != -1 && 793 darwinDesiredDepth != 8 && 794 darwinDesiredDepth != 15 && 795 darwinDesiredDepth != 24) { 796 FatalError("Unsupported pixel depth. Use 8, 15, or 24 bits\n"); 797 } 798 799 ErrorF("Attempting to use pixel depth of %i\n", darwinDesiredDepth); 800 return 2; 801 } 802 803 if (!strcmp(argv[i], "-showconfig") || !strcmp(argv[i], "-version")) { 804 DarwinPrintBanner(); 805 exit(0); 806 } 807 808 return 0; 809} 810 811/* 812 * ddxUseMsg -- 813 * Print out correct use of device dependent commandline options. 814 * Maybe the user now knows what really to do ... 815 */ 816void 817ddxUseMsg(void) 818{ 819 ErrorF("\n"); 820 ErrorF("\n"); 821 ErrorF("Device Dependent Usage:\n"); 822 ErrorF("\n"); 823 ErrorF("-depth <8,15,24> : use this bit depth.\n"); 824 ErrorF( 825 "-fakebuttons : fake a three button mouse with Command and Option keys.\n"); 826 ErrorF("-nofakebuttons : don't fake a three button mouse.\n"); 827 ErrorF( 828 "-fakemouse2 <modifiers> : fake middle mouse button with modifier keys.\n"); 829 ErrorF( 830 "-fakemouse3 <modifiers> : fake right mouse button with modifier keys.\n"); 831 ErrorF( 832 " ex: -fakemouse2 \"option,shift\" = option-shift-click is middle button.\n"); 833 ErrorF("-version : show the server version.\n"); 834 ErrorF("\n"); 835} 836 837/* 838 * ddxGiveUp -- 839 * Device dependent cleanup. Called by dix before normal server death. 840 */ 841void 842ddxGiveUp(enum ExitCode error) 843{ 844 LogClose(error); 845} 846 847/* 848 * AbortDDX -- 849 * DDX - specific abort routine. Called by AbortServer(). The attempt is 850 * made to restore all original setting of the displays. Also all devices 851 * are closed. 852 */ 853_X_NORETURN 854void 855AbortDDX(enum ExitCode error) 856{ 857 ErrorF(" AbortDDX\n"); 858 OsAbort(); 859} 860 861#if INPUTTHREAD 862/** This function is called in Xserver/os/inputthread.c when starting 863 the input thread. */ 864void 865ddxInputThreadInit(void) 866{ 867} 868#endif 869