xf86Init.c revision 6747b715
1/*
2 * Loosely based on code bearing the following copyright:
3 *
4 *   Copyright 1990,91 by Thomas Roell, Dinkelscherben, Germany.
5 */
6/*
7 * Copyright (c) 1992-2003 by The XFree86 Project, Inc.
8 *
9 * Permission is hereby granted, free of charge, to any person obtaining a
10 * copy of this software and associated documentation files (the "Software"),
11 * to deal in the Software without restriction, including without limitation
12 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
13 * and/or sell copies of the Software, and to permit persons to whom the
14 * Software is furnished to do so, subject to the following conditions:
15 *
16 * The above copyright notice and this permission notice shall be included in
17 * all copies or substantial portions of the Software.
18 *
19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
22 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
23 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
24 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
25 * OTHER DEALINGS IN THE SOFTWARE.
26 *
27 * Except as contained in this notice, the name of the copyright holder(s)
28 * and author(s) shall not be used in advertising or otherwise to promote
29 * the sale, use or other dealings in this Software without prior written
30 * authorization from the copyright holder(s) and author(s).
31 */
32
33#ifdef HAVE_XORG_CONFIG_H
34#include <xorg-config.h>
35#endif
36
37#include <stdlib.h>
38#include <errno.h>
39
40#undef HAS_UTSNAME
41#if !defined(WIN32)
42#define HAS_UTSNAME 1
43#include <sys/utsname.h>
44#endif
45
46#include <X11/X.h>
47#include <X11/Xmd.h>
48#include <X11/Xproto.h>
49#include <X11/Xatom.h>
50#include "input.h"
51#include "servermd.h"
52#include "windowstr.h"
53#include "scrnintstr.h"
54#include "site.h"
55#include "mi.h"
56
57#include "compiler.h"
58
59#include "loaderProcs.h"
60#ifdef XFreeXDGA
61#include "dgaproc.h"
62#endif
63
64#define XF86_OS_PRIVS
65#include "xf86.h"
66#include "xf86Priv.h"
67#include "xf86Config.h"
68#include "xf86_OSlib.h"
69#include "xf86cmap.h"
70#include "xorgVersion.h"
71#include "xf86Build.h"
72#include "mipointer.h"
73#include <X11/extensions/XI.h>
74#include <X11/extensions/XIproto.h>
75#include "xf86DDC.h"
76#include "xf86Xinput.h"
77#include "xf86InPriv.h"
78#include "picturestr.h"
79
80#include "xf86Bus.h"
81#include "xf86VGAarbiter.h"
82#include "globals.h"
83
84#ifdef DPMSExtension
85#include <X11/extensions/dpmsconst.h>
86#include "dpmsproc.h"
87#endif
88#include <hotplug.h>
89
90
91#ifdef XF86PM
92void (*xf86OSPMClose)(void) = NULL;
93#endif
94static Bool xorgHWOpenConsole = FALSE;
95
96/* Common pixmap formats */
97
98static PixmapFormatRec formats[MAXFORMATS] = {
99	{ 1,	1,	BITMAP_SCANLINE_PAD },
100	{ 4,	8,	BITMAP_SCANLINE_PAD },
101	{ 8,	8,	BITMAP_SCANLINE_PAD },
102	{ 15,	16,	BITMAP_SCANLINE_PAD },
103	{ 16,	16,	BITMAP_SCANLINE_PAD },
104	{ 24,	32,	BITMAP_SCANLINE_PAD },
105	{ 32,	32,	BITMAP_SCANLINE_PAD },
106};
107static int numFormats = 7;
108static Bool formatsDone = FALSE;
109
110#ifndef OSNAME
111#define OSNAME " unknown"
112#endif
113#ifndef OSVENDOR
114#define OSVENDOR ""
115#endif
116#ifndef PRE_RELEASE
117#define PRE_RELEASE XORG_VERSION_SNAP
118#endif
119
120static void
121xf86PrintBanner(void)
122{
123#if PRE_RELEASE
124  xf86ErrorFVerb(0, "\n"
125    "This is a pre-release version of the X server from " XVENDORNAME ".\n"
126    "It is not supported in any way.\n"
127    "Bugs may be filed in the bugzilla at http://bugs.freedesktop.org/.\n"
128    "Select the \"xorg\" product for bugs you find in this release.\n"
129    "Before reporting bugs in pre-release versions please check the\n"
130    "latest version in the X.Org Foundation git repository.\n"
131    "See http://wiki.x.org/wiki/GitPage for git access instructions.\n");
132#endif
133  xf86ErrorFVerb(0, "\nX.Org X Server %d.%d.%d",
134	 XORG_VERSION_MAJOR,
135	 XORG_VERSION_MINOR,
136	 XORG_VERSION_PATCH);
137#if XORG_VERSION_SNAP > 0
138  xf86ErrorFVerb(0, ".%d", XORG_VERSION_SNAP);
139#endif
140
141#if XORG_VERSION_SNAP >= 900
142  /* When the minor number is 99, that signifies that the we are making
143   * a release candidate for a major version.  (X.0.0)
144   * When the patch number is 99, that signifies that the we are making
145   * a release candidate for a minor version.  (X.Y.0)
146   * When the patch number is < 99, then we are making a release
147   * candidate for the next point release.  (X.Y.Z)
148   */
149#if XORG_VERSION_MINOR >= 99
150  xf86ErrorFVerb(0, " (%d.0.0 RC %d)", XORG_VERSION_MAJOR+1,
151                 XORG_VERSION_SNAP - 900);
152#elif XORG_VERSION_PATCH == 99
153  xf86ErrorFVerb(0, " (%d.%d.0 RC %d)", XORG_VERSION_MAJOR,
154                 XORG_VERSION_MINOR + 1, XORG_VERSION_SNAP - 900);
155#else
156  xf86ErrorFVerb(0, " (%d.%d.%d RC %d)", XORG_VERSION_MAJOR,
157                 XORG_VERSION_MINOR, XORG_VERSION_PATCH + 1,
158                 XORG_VERSION_SNAP - 900);
159#endif
160#endif
161
162#ifdef XORG_CUSTOM_VERSION
163  xf86ErrorFVerb(0, " (%s)", XORG_CUSTOM_VERSION);
164#endif
165#ifndef XORG_DATE
166# define XORG_DATE "Unknown"
167#endif
168  xf86ErrorFVerb(0, "\nRelease Date: %s\n", XORG_DATE);
169  xf86ErrorFVerb(0, "X Protocol Version %d, Revision %d\n",
170         X_PROTOCOL, X_PROTOCOL_REVISION);
171  xf86ErrorFVerb(0, "Build Operating System: %s %s\n", OSNAME, OSVENDOR);
172#ifdef HAS_UTSNAME
173  {
174    struct utsname name;
175
176    /* Linux & BSD state that 0 is success, SysV (including Solaris, HP-UX,
177       and Irix) and Single Unix Spec 3 just say that non-negative is success.
178       All agree that failure is represented by a negative number.
179     */
180    if (uname(&name) >= 0) {
181      xf86ErrorFVerb(0, "Current Operating System: %s %s %s %s %s\n",
182	name.sysname, name.nodename, name.release, name.version, name.machine);
183#ifdef linux
184      do {
185	  char buf[80];
186	  int fd = open("/proc/cmdline", O_RDONLY);
187	  if (fd != -1) {
188	    xf86ErrorFVerb(0, "Kernel command line: ");
189	    memset(buf, 0, 80);
190	    while (read(fd, buf, 80) > 0) {
191		xf86ErrorFVerb(0, "%.80s", buf);
192		memset(buf, 0, 80);
193	    }
194	    close(fd);
195	  }
196      } while (0);
197#endif
198    }
199  }
200#endif
201#if defined(BUILD_DATE) && (BUILD_DATE > 19000000)
202  {
203    struct tm t;
204    char buf[100];
205
206    memset(&t, 0, sizeof(t));
207    memset(buf, 0, sizeof(buf));
208    t.tm_mday = BUILD_DATE % 100;
209    t.tm_mon = (BUILD_DATE / 100) % 100 - 1;
210    t.tm_year = BUILD_DATE / 10000 - 1900;
211#if defined(BUILD_TIME)
212    t.tm_sec = BUILD_TIME % 100;
213    t.tm_min = (BUILD_TIME / 100) % 100;
214    t.tm_hour = (BUILD_TIME / 10000) % 100;
215    if (strftime(buf, sizeof(buf), "%d %B %Y  %I:%M:%S%p", &t))
216       xf86ErrorFVerb(0, "Build Date: %s\n", buf);
217#else
218    if (strftime(buf, sizeof(buf), "%d %B %Y", &t))
219       xf86ErrorFVerb(0, "Build Date: %s\n", buf);
220#endif
221  }
222#endif
223#if defined(BUILDERSTRING)
224  xf86ErrorFVerb(0, "%s \n", BUILDERSTRING);
225#endif
226  xf86ErrorFVerb(0, "Current version of pixman: %s\n",
227                 pixman_version_string());
228  xf86ErrorFVerb(0, "\tBefore reporting problems, check "
229                 ""__VENDORDWEBSUPPORT__"\n"
230                 "\tto make sure that you have the latest version.\n");
231}
232
233static void
234xf86PrintMarkers(void)
235{
236  LogPrintMarkers();
237}
238
239static Bool
240xf86CreateRootWindow(WindowPtr pWin)
241{
242  int ret = TRUE;
243  int err = Success;
244  ScreenPtr pScreen = pWin->drawable.pScreen;
245  RootWinPropPtr pProp;
246  CreateWindowProcPtr CreateWindow = (CreateWindowProcPtr)
247      dixLookupPrivate(&pScreen->devPrivates, xf86CreateRootWindowKey);
248
249  DebugF("xf86CreateRootWindow(%p)\n", pWin);
250
251  if ( pScreen->CreateWindow != xf86CreateRootWindow ) {
252    /* Can't find hook we are hung on */
253	xf86DrvMsg(pScreen->myNum, X_WARNING /* X_ERROR */,
254		  "xf86CreateRootWindow %p called when not in pScreen->CreateWindow %p n",
255		   (void *)xf86CreateRootWindow,
256		   (void *)pScreen->CreateWindow );
257  }
258
259  /* Unhook this function ... */
260  pScreen->CreateWindow = CreateWindow;
261  dixSetPrivate(&pScreen->devPrivates, xf86CreateRootWindowKey, NULL);
262
263  /* ... and call the previous CreateWindow fuction, if any */
264  if (NULL!=pScreen->CreateWindow) {
265    ret = (*pScreen->CreateWindow)(pWin);
266  }
267
268  /* Now do our stuff */
269  if (xf86RegisteredPropertiesTable != NULL) {
270    if (pWin->parent == NULL && xf86RegisteredPropertiesTable != NULL) {
271      for (pProp = xf86RegisteredPropertiesTable[pScreen->myNum];
272	   pProp != NULL && err==Success;
273	   pProp = pProp->next )
274	{
275	  Atom prop;
276
277	  prop = MakeAtom(pProp->name, strlen(pProp->name), TRUE);
278	  err = dixChangeWindowProperty(serverClient, pWin,
279					prop, pProp->type,
280					pProp->format, PropModeReplace,
281					pProp->size, pProp->data,
282					FALSE);
283	}
284
285      /* Look at err */
286      ret &= (err==Success);
287
288    } else {
289      xf86Msg(X_ERROR, "xf86CreateRootWindow unexpectedly called with "
290	      "non-root window %p (parent %p)\n",
291	      (void *)pWin, (void *)pWin->parent);
292      ret = FALSE;
293    }
294  }
295
296  DebugF("xf86CreateRootWindow() returns %d\n", ret);
297  return ret;
298}
299
300
301static void
302InstallSignalHandlers(void)
303{
304    /*
305     * Install signal handler for unexpected signals
306     */
307    xf86Info.caughtSignal=FALSE;
308    if (!xf86Info.notrapSignals) {
309	OsRegisterSigWrapper(xf86SigWrapper);
310    } else {
311	signal(SIGSEGV, SIG_DFL);
312	signal(SIGILL, SIG_DFL);
313#ifdef SIGEMT
314	signal(SIGEMT, SIG_DFL);
315#endif
316	signal(SIGFPE, SIG_DFL);
317#ifdef SIGBUS
318	signal(SIGBUS, SIG_DFL);
319#endif
320#ifdef SIGSYS
321	signal(SIGSYS, SIG_DFL);
322#endif
323#ifdef SIGXCPU
324	signal(SIGXCPU, SIG_DFL);
325#endif
326#ifdef SIGXFSZ
327	signal(SIGXFSZ, SIG_DFL);
328#endif
329    }
330}
331
332/*
333 * InitOutput --
334 *	Initialize screenInfo for all actually accessible framebuffers.
335 *      That includes vt-manager setup, querying all possible devices and
336 *      collecting the pixmap formats.
337 */
338void
339InitOutput(ScreenInfo *pScreenInfo, int argc, char **argv)
340{
341  int                    i, j, k, scr_index;
342  char                   **modulelist;
343  pointer                *optionlist;
344  Pix24Flags		 screenpix24, pix24;
345  MessageType		 pix24From = X_DEFAULT;
346  Bool			 pix24Fail = FALSE;
347  Bool			 autoconfig = FALSE;
348  GDevPtr		 configured_device;
349
350  xf86Initialising = TRUE;
351
352  if (serverGeneration == 1) {
353    if ((xf86ServerName = strrchr(argv[0], '/')) != 0)
354      xf86ServerName++;
355    else
356      xf86ServerName = argv[0];
357
358	xf86PrintBanner();
359	xf86PrintMarkers();
360	if (xf86LogFile)  {
361	    time_t t;
362	    const char *ct;
363	    t = time(NULL);
364	    ct = ctime(&t);
365	    xf86MsgVerb(xf86LogFileFrom, 0, "Log file: \"%s\", Time: %s",
366			xf86LogFile, ct);
367	}
368
369    /* Read and parse the config file */
370    if (!xf86DoConfigure && !xf86DoShowOptions) {
371      switch (xf86HandleConfigFile(FALSE)) {
372      case CONFIG_OK:
373	break;
374      case CONFIG_PARSE_ERROR:
375	xf86Msg(X_ERROR, "Error parsing the config file\n");
376	return;
377      case CONFIG_NOFILE:
378	autoconfig = TRUE;
379	break;
380      }
381    }
382
383    InstallSignalHandlers();
384
385    /* Initialise the loader */
386    LoaderInit();
387
388    /* Tell the loader the default module search path */
389    LoaderSetPath(xf86ModulePath);
390
391    if (xf86Info.ignoreABI) {
392        LoaderSetOptions(LDR_OPT_ABI_MISMATCH_NONFATAL);
393    }
394
395    if (xf86DoShowOptions)
396        DoShowOptions();
397
398    /* Do a general bus probe.  This will be a PCI probe for x86 platforms */
399    xf86BusProbe();
400
401    if (xf86DoConfigure)
402	DoConfigure();
403
404    if (autoconfig) {
405	if (!xf86AutoConfig()) {
406	    xf86Msg(X_ERROR, "Auto configuration failed\n");
407	    return;
408	}
409    }
410
411#ifdef XF86PM
412    xf86OSPMClose = xf86OSPMOpen();
413#endif
414
415    /* Load all modules specified explicitly in the config file */
416    if ((modulelist = xf86ModulelistFromConfig(&optionlist))) {
417      xf86LoadModules(modulelist, optionlist);
418      free(modulelist);
419      free(optionlist);
420    }
421
422    /* Load all driver modules specified in the config file */
423    /* If there aren't any specified in the config file, autoconfig them */
424    /* FIXME: Does not handle multiple active screen sections, but I'm not
425     * sure if we really want to handle that case*/
426    configured_device = xf86ConfigLayout.screens->screen->device;
427    if ((!configured_device) || (!configured_device->driver)) {
428        if (!autoConfigDevice(configured_device)) {
429            xf86Msg(X_ERROR, "Automatic driver configuration failed\n");
430            return ;
431        }
432    }
433    if ((modulelist = xf86DriverlistFromConfig())) {
434      xf86LoadModules(modulelist, NULL);
435      free(modulelist);
436    }
437
438    /* Load all input driver modules specified in the config file. */
439    if ((modulelist = xf86InputDriverlistFromConfig())) {
440      xf86LoadModules(modulelist, NULL);
441      free(modulelist);
442    }
443
444    /*
445     * It is expected that xf86AddDriver()/xf86AddInputDriver will be
446     * called for each driver as it is loaded.  Those functions save the
447     * module pointers for drivers.
448     * XXX Nothing keeps track of them for other modules.
449     */
450    /* XXX What do we do if not all of these could be loaded? */
451
452    /*
453     * At this point, xf86DriverList[] is all filled in with entries for
454     * each of the drivers to try and xf86NumDrivers has the number of
455     * drivers.  If there are none, return now.
456     */
457
458    if (xf86NumDrivers == 0) {
459      xf86Msg(X_ERROR, "No drivers available.\n");
460      return;
461    }
462
463    /*
464     * Call each of the Identify functions and call the driverFunc to check
465     * if HW access is required.  The Identify functions print out some
466     * identifying information, and anything else that might be
467     * needed at this early stage.
468     */
469
470    for (i = 0; i < xf86NumDrivers; i++) {
471	if (xf86DriverList[i]->Identify != NULL)
472	    xf86DriverList[i]->Identify(0);
473
474	if (!xorgHWAccess || !xorgHWOpenConsole) {
475	    xorgHWFlags flags;
476	    if(!xf86DriverList[i]->driverFunc
477		|| !xf86DriverList[i]->driverFunc(NULL,
478						  GET_REQUIRED_HW_INTERFACES,
479						  &flags))
480		flags = HW_IO;
481
482	    if(NEED_IO_ENABLED(flags))
483		xorgHWAccess = TRUE;
484	    if(!(flags & HW_SKIP_CONSOLE))
485		xorgHWOpenConsole = TRUE;
486	}
487    }
488
489    if (xorgHWOpenConsole)
490	xf86OpenConsole();
491    else
492	xf86Info.dontVTSwitch = TRUE;
493
494    if (xf86BusConfig() == FALSE)
495        return;
496
497    xf86PostProbe();
498
499    /*
500     * Sort the drivers to match the requested ording.  Using a slow
501     * bubble sort.
502     */
503    for (j = 0; j < xf86NumScreens - 1; j++) {
504	for (i = 0; i < xf86NumScreens - j - 1; i++) {
505	    if (xf86Screens[i + 1]->confScreen->screennum <
506		xf86Screens[i]->confScreen->screennum) {
507		ScrnInfoPtr tmpScrn = xf86Screens[i + 1];
508		xf86Screens[i + 1] = xf86Screens[i];
509		xf86Screens[i] = tmpScrn;
510	    }
511	}
512    }
513    /* Fix up the indexes */
514    for (i = 0; i < xf86NumScreens; i++) {
515	xf86Screens[i]->scrnIndex = i;
516    }
517
518    /*
519     * Call the driver's PreInit()'s to complete initialisation for the first
520     * generation.
521     */
522
523    for (i = 0; i < xf86NumScreens; i++) {
524	xf86VGAarbiterScrnInit(xf86Screens[i]);
525	xf86VGAarbiterLock(xf86Screens[i]);
526	if (xf86Screens[i]->PreInit &&
527	    xf86Screens[i]->PreInit(xf86Screens[i], 0))
528	    xf86Screens[i]->configured = TRUE;
529	xf86VGAarbiterUnlock(xf86Screens[i]);
530    }
531    for (i = 0; i < xf86NumScreens; i++)
532	if (!xf86Screens[i]->configured)
533	    xf86DeleteScreen(i--, 0);
534
535    /*
536     * If no screens left, return now.
537     */
538
539    if (xf86NumScreens == 0) {
540      xf86Msg(X_ERROR,
541	      "Screen(s) found, but none have a usable configuration.\n");
542      return;
543    }
544
545    for (i = 0; i < xf86NumScreens; i++) {
546      if (xf86Screens[i]->name == NULL) {
547	xf86Screens[i]->name = xnfalloc(strlen("screen") + 10 + 1);
548	sprintf(xf86Screens[i]->name, "screen%d", i);
549	xf86MsgVerb(X_WARNING, 0,
550		    "Screen driver %d has no name set, using `%s'.\n",
551		    i, xf86Screens[i]->name);
552      }
553    }
554
555    /* Remove (unload) drivers that are not required */
556    for (i = 0; i < xf86NumDrivers; i++)
557	if (xf86DriverList[i] && xf86DriverList[i]->refCount <= 0)
558	    xf86DeleteDriver(i);
559
560    /*
561     * At this stage we know how many screens there are.
562     */
563
564    for (i = 0; i < xf86NumScreens; i++)
565      xf86InitViewport(xf86Screens[i]);
566
567    /*
568     * Collect all pixmap formats and check for conflicts at the display
569     * level.  Should we die here?  Or just delete the offending screens?
570     */
571    screenpix24 = Pix24DontCare;
572    for (i = 0; i < xf86NumScreens; i++) {
573	if (xf86Screens[i]->imageByteOrder !=
574	    xf86Screens[0]->imageByteOrder)
575	    FatalError("Inconsistent display bitmapBitOrder.  Exiting\n");
576	if (xf86Screens[i]->bitmapScanlinePad !=
577	    xf86Screens[0]->bitmapScanlinePad)
578	    FatalError("Inconsistent display bitmapScanlinePad.  Exiting\n");
579	if (xf86Screens[i]->bitmapScanlineUnit !=
580	    xf86Screens[0]->bitmapScanlineUnit)
581	    FatalError("Inconsistent display bitmapScanlineUnit.  Exiting\n");
582	if (xf86Screens[i]->bitmapBitOrder !=
583	    xf86Screens[0]->bitmapBitOrder)
584	    FatalError("Inconsistent display bitmapBitOrder.  Exiting\n");
585
586	/* Determine the depth 24 pixmap format the screens would like */
587	if (xf86Screens[i]->pixmap24 != Pix24DontCare) {
588	    if (screenpix24 == Pix24DontCare)
589		screenpix24 = xf86Screens[i]->pixmap24;
590	    else if (screenpix24 != xf86Screens[i]->pixmap24)
591		FatalError("Inconsistent depth 24 pixmap format.  Exiting\n");
592	}
593    }
594    /* check if screenpix24 is consistent with the config/cmdline */
595    if (xf86Info.pixmap24 != Pix24DontCare) {
596	pix24 = xf86Info.pixmap24;
597	pix24From = xf86Info.pix24From;
598	if (screenpix24 != Pix24DontCare && screenpix24 != xf86Info.pixmap24)
599	    pix24Fail = TRUE;
600    } else if (screenpix24 != Pix24DontCare) {
601	pix24 = screenpix24;
602	pix24From = X_PROBED;
603    } else
604	pix24 = Pix24Use32;
605
606    if (pix24Fail)
607	FatalError("Screen(s) can't use the required depth 24 pixmap format"
608		   " (%d).  Exiting\n", PIX24TOBPP(pix24));
609
610    /* Initialise the depth 24 format */
611    for (j = 0; j < numFormats && formats[j].depth != 24; j++)
612	;
613    formats[j].bitsPerPixel = PIX24TOBPP(pix24);
614
615    /* Collect additional formats */
616    for (i = 0; i < xf86NumScreens; i++) {
617	for (j = 0; j < xf86Screens[i]->numFormats; j++) {
618	    for (k = 0; ; k++) {
619		if (k >= numFormats) {
620		    if (k >= MAXFORMATS)
621			FatalError("Too many pixmap formats!  Exiting\n");
622		    formats[k] = xf86Screens[i]->formats[j];
623		    numFormats++;
624		    break;
625		}
626		if (formats[k].depth == xf86Screens[i]->formats[j].depth) {
627		    if ((formats[k].bitsPerPixel ==
628			 xf86Screens[i]->formats[j].bitsPerPixel) &&
629		        (formats[k].scanlinePad ==
630			 xf86Screens[i]->formats[j].scanlinePad))
631			break;
632		    FatalError("Inconsistent pixmap format for depth %d."
633			       "  Exiting\n", formats[k].depth);
634		}
635	    }
636	}
637    }
638    formatsDone = TRUE;
639
640    if (xf86Info.vtno >= 0 ) {
641#define VT_ATOM_NAME         "XFree86_VT"
642      Atom VTAtom=-1;
643      CARD32  *VT = NULL;
644      int  ret;
645
646      /* This memory needs to stay available until the screen has been
647	 initialized, and we can create the property for real.
648      */
649      if ( (VT = malloc(sizeof(CARD32)))==NULL ) {
650	FatalError("Unable to make VT property - out of memory. Exiting...\n");
651      }
652      *VT = xf86Info.vtno;
653
654      VTAtom = MakeAtom(VT_ATOM_NAME, sizeof(VT_ATOM_NAME) - 1, TRUE);
655
656      for (i = 0, ret = Success; i < xf86NumScreens && ret == Success; i++) {
657	ret = xf86RegisterRootWindowProperty(xf86Screens[i]->scrnIndex,
658					     VTAtom, XA_INTEGER, 32,
659					     1, VT );
660	if (ret != Success)
661	  xf86DrvMsg(xf86Screens[i]->scrnIndex, X_WARNING,
662		     "Failed to register VT property\n");
663      }
664    }
665
666    /* If a screen uses depth 24, show what the pixmap format is */
667    for (i = 0; i < xf86NumScreens; i++) {
668	if (xf86Screens[i]->depth == 24) {
669	    xf86Msg(pix24From, "Depth 24 pixmap format is %d bpp\n",
670		    PIX24TOBPP(pix24));
671	    break;
672	}
673    }
674  } else {
675    /*
676     * serverGeneration != 1; some OSs have to do things here, too.
677     */
678    if (xorgHWOpenConsole)
679	xf86OpenConsole();
680
681#ifdef XF86PM
682    /*
683      should we reopen it here? We need to deal with an already opened
684      device. We could leave this to the OS layer. For now we simply
685      close it here
686    */
687    if (xf86OSPMClose)
688        xf86OSPMClose();
689    if ((xf86OSPMClose = xf86OSPMOpen()) != NULL)
690	xf86MsgVerb(X_INFO, 3, "APM registered successfully\n");
691#endif
692
693    /* Make sure full I/O access is enabled */
694    if (xorgHWAccess)
695	xf86EnableIO();
696  }
697
698  /*
699   * Use the previously collected parts to setup pScreenInfo
700   */
701
702  pScreenInfo->imageByteOrder = xf86Screens[0]->imageByteOrder;
703  pScreenInfo->bitmapScanlinePad = xf86Screens[0]->bitmapScanlinePad;
704  pScreenInfo->bitmapScanlineUnit = xf86Screens[0]->bitmapScanlineUnit;
705  pScreenInfo->bitmapBitOrder = xf86Screens[0]->bitmapBitOrder;
706  pScreenInfo->numPixmapFormats = numFormats;
707  for (i = 0; i < numFormats; i++)
708    pScreenInfo->formats[i] = formats[i];
709
710  /* Make sure the server's VT is active */
711
712  if (serverGeneration != 1) {
713    xf86Resetting = TRUE;
714    /* All screens are in the same state, so just check the first */
715    if (!xf86Screens[0]->vtSema) {
716#ifdef HAS_USL_VTS
717      ioctl(xf86Info.consoleFd, VT_RELDISP, VT_ACKACQ);
718#endif
719      xf86AccessEnter();
720      xf86EnterServerState(SETUP);
721    }
722  }
723#ifdef SCO325
724  else {
725    /*
726     * Under SCO we must ack that we got the console at startup,
727     * I think this is the safest way to assure it.
728     */
729    static int once = 1;
730    if (once) {
731      once = 0;
732      if (ioctl(xf86Info.consoleFd, VT_RELDISP, VT_ACKACQ) < 0)
733        xf86Msg(X_WARNING, "VT_ACKACQ failed");
734    }
735  }
736#endif /* SCO325 */
737
738  for (i = 0; i < xf86NumScreens; i++)
739      if (!xf86ColormapAllocatePrivates(xf86Screens[i]))
740	  FatalError("Cannot register DDX private keys");
741
742  if (!dixRegisterPrivateKey(&xf86ScreenKeyRec, PRIVATE_SCREEN, 0) ||
743      !dixRegisterPrivateKey(&xf86CreateRootWindowKeyRec, PRIVATE_SCREEN, 0) ||
744      !dixRegisterPrivateKey(&xf86PixmapKeyRec, PRIVATE_PIXMAP, 0))
745      FatalError("Cannot register DDX private keys");
746
747  for (i = 0; i < xf86NumScreens; i++) {
748	xf86VGAarbiterLock(xf86Screens[i]);
749	/*
750	 * Almost everything uses these defaults, and many of those that
751	 * don't, will wrap them.
752	 */
753	xf86Screens[i]->EnableDisableFBAccess = xf86EnableDisableFBAccess;
754#ifdef XFreeXDGA
755	xf86Screens[i]->SetDGAMode = xf86SetDGAMode;
756#endif
757	xf86Screens[i]->DPMSSet = NULL;
758	xf86Screens[i]->LoadPalette = NULL;
759	xf86Screens[i]->SetOverscan = NULL;
760	xf86Screens[i]->DriverFunc = NULL;
761	xf86Screens[i]->pScreen = NULL;
762	scr_index = AddScreen(xf86Screens[i]->ScreenInit, argc, argv);
763	xf86VGAarbiterUnlock(xf86Screens[i]);
764      if (scr_index == i) {
765	/*
766	 * Hook in our ScrnInfoRec, and initialise some other pScreen
767	 * fields.
768	 */
769	dixSetPrivate(&screenInfo.screens[scr_index]->devPrivates,
770		      xf86ScreenKey, xf86Screens[i]);
771	xf86Screens[i]->pScreen = screenInfo.screens[scr_index];
772	/* The driver should set this, but make sure it is set anyway */
773	xf86Screens[i]->vtSema = TRUE;
774      } else {
775	/* This shouldn't normally happen */
776	FatalError("AddScreen/ScreenInit failed for driver %d\n", i);
777      }
778
779      DebugF("InitOutput - xf86Screens[%d]->pScreen = %p\n",
780	     i, xf86Screens[i]->pScreen );
781      DebugF("xf86Screens[%d]->pScreen->CreateWindow = %p\n",
782	     i, xf86Screens[i]->pScreen->CreateWindow );
783
784      dixSetPrivate(&screenInfo.screens[scr_index]->devPrivates,
785		    xf86CreateRootWindowKey,
786		    xf86Screens[i]->pScreen->CreateWindow);
787      xf86Screens[i]->pScreen->CreateWindow = xf86CreateRootWindow;
788
789    if (PictureGetSubpixelOrder (xf86Screens[i]->pScreen) == SubPixelUnknown)
790    {
791	xf86MonPtr DDC = (xf86MonPtr)(xf86Screens[i]->monitor->DDC);
792	PictureSetSubpixelOrder (xf86Screens[i]->pScreen,
793				 DDC ?
794				 (DDC->features.input_type ?
795				  SubPixelHorizontalRGB : SubPixelNone) :
796				 SubPixelUnknown);
797    }
798#ifdef RANDR
799    if (!xf86Info.disableRandR)
800	xf86RandRInit (screenInfo.screens[scr_index]);
801    xf86Msg(xf86Info.randRFrom, "RandR %s\n",
802	    xf86Info.disableRandR ? "disabled" : "enabled");
803#endif
804  }
805
806  xf86PostScreenInit();
807
808  xf86InitOrigins();
809
810  xf86Resetting = FALSE;
811  xf86Initialising = FALSE;
812
813  RegisterBlockAndWakeupHandlers((BlockHandlerProcPtr)NoopDDA, xf86Wakeup,
814				 NULL);
815}
816
817/*
818 * InitInput --
819 *      Initialize all supported input devices.
820 */
821
822void
823InitInput(int argc, char **argv)
824{
825    IDevPtr* pDev;
826    DeviceIntPtr dev;
827
828    xf86Info.vtRequestsPending = FALSE;
829
830    mieqInit();
831
832    GetEventList(&xf86Events);
833
834    /* Call the PreInit function for each input device instance. */
835    for (pDev = xf86ConfigLayout.inputs; pDev && *pDev; pDev++) {
836        /* Replace obsolete keyboard driver with kbd */
837        if (!xf86NameCmp((*pDev)->driver, "keyboard")) {
838            strcpy((*pDev)->driver, "kbd");
839        }
840
841        /* If one fails, the others will too */
842        if (xf86NewInputDevice(*pDev, &dev, TRUE) == BadAlloc)
843            break;
844    }
845
846    config_init();
847}
848
849void
850CloseInput (void)
851{
852    config_fini();
853}
854
855/*
856 * OsVendorInit --
857 *      OS/Vendor-specific initialisations.  Called from OsInit(), which
858 *      is called by dix before establishing the well known sockets.
859 */
860
861void
862OsVendorInit(void)
863{
864  static Bool beenHere = FALSE;
865
866#ifdef SIGCHLD
867  signal(SIGCHLD, SIG_DFL);	/* Need to wait for child processes */
868#endif
869
870  if (!beenHere) {
871    umask(022);
872    xf86LogInit();
873  }
874
875        /* Set stderr to non-blocking. */
876#ifndef O_NONBLOCK
877#if defined(FNDELAY)
878#define O_NONBLOCK FNDELAY
879#elif defined(O_NDELAY)
880#define O_NONBLOCK O_NDELAY
881#endif
882
883#ifdef O_NONBLOCK
884  if (!beenHere) {
885    if (geteuid() == 0 && getuid() != geteuid())
886    {
887      int status;
888
889      status = fcntl(fileno(stderr), F_GETFL, 0);
890      if (status != -1) {
891	fcntl(fileno(stderr), F_SETFL, status | O_NONBLOCK);
892      }
893    }
894  }
895#endif
896#endif
897
898  beenHere = TRUE;
899}
900
901/*
902 * ddxGiveUp --
903 *      Device dependent cleanup. Called by by dix before normal server death.
904 *      For SYSV386 we must switch the terminal back to normal mode. No error-
905 *      checking here, since there should be restored as much as possible.
906 */
907
908void
909ddxGiveUp(void)
910{
911    int i;
912
913    xf86VGAarbiterFini();
914
915#ifdef XF86PM
916    if (xf86OSPMClose)
917	xf86OSPMClose();
918    xf86OSPMClose = NULL;
919#endif
920
921    for (i = 0; i < xf86NumScreens; i++) {
922	/*
923	 * zero all access functions to
924	 * trap calls when switched away.
925	 */
926	xf86Screens[i]->vtSema = FALSE;
927    }
928
929#ifdef XFreeXDGA
930    DGAShutdown();
931#endif
932
933    if (xorgHWOpenConsole)
934	xf86CloseConsole();
935
936    xf86CloseLog();
937
938    /* If an unexpected signal was caught, dump a core for debugging */
939    if (xf86Info.caughtSignal)
940	OsAbort();
941}
942
943
944
945/*
946 * AbortDDX --
947 *      DDX - specific abort routine.  Called by AbortServer(). The attempt is
948 *      made to restore all original setting of the displays. Also all devices
949 *      are closed.
950 */
951
952void
953AbortDDX(void)
954{
955  int i;
956
957  /*
958   * try to restore the original video state
959   */
960#ifdef DPMSExtension /* Turn screens back on */
961  if (DPMSPowerLevel != DPMSModeOn)
962      DPMSSet(serverClient, DPMSModeOn);
963#endif
964  if (xf86Screens) {
965      if (xf86Screens[0]->vtSema)
966	  xf86EnterServerState(SETUP);
967      for (i = 0; i < xf86NumScreens; i++)
968	  if (xf86Screens[i]->vtSema) {
969	      /*
970	       * if we are aborting before ScreenInit() has finished
971	       * we might not have been wrapped yet. Therefore enable
972	       * screen explicitely.
973	       */
974	      xf86VGAarbiterLock(xf86Screens[i]);
975	      (xf86Screens[i]->LeaveVT)(i, 0);
976	      xf86VGAarbiterUnlock(xf86Screens[i]);
977	  }
978  }
979
980  xf86AccessLeave();
981
982  /*
983   * This is needed for an abnormal server exit, since the normal exit stuff
984   * MUST also be performed (i.e. the vt must be left in a defined state)
985   */
986  ddxGiveUp();
987}
988
989void
990OsVendorFatalError(void)
991{
992#ifdef VENDORSUPPORT
993    ErrorF("\nPlease refer to your Operating System Vendor support pages\n"
994	   "at %s for support on this crash.\n",VENDORSUPPORT);
995#else
996    ErrorF("\nPlease consult the "XVENDORNAME" support \n"
997	   "\t at "__VENDORDWEBSUPPORT__"\n for help. \n");
998#endif
999    if (xf86LogFile && xf86LogFileWasOpened)
1000	ErrorF("Please also check the log file at \"%s\" for additional "
1001              "information.\n", xf86LogFile);
1002    ErrorF("\n");
1003}
1004
1005int
1006xf86SetVerbosity(int verb)
1007{
1008    int save = xf86Verbose;
1009
1010    xf86Verbose = verb;
1011    LogSetParameter(XLOG_VERBOSITY, verb);
1012    return save;
1013}
1014
1015int
1016xf86SetLogVerbosity(int verb)
1017{
1018    int save = xf86LogVerbose;
1019
1020    xf86LogVerbose = verb;
1021    LogSetParameter(XLOG_FILE_VERBOSITY, verb);
1022    return save;
1023}
1024
1025static void
1026xf86PrintDefaultModulePath(void)
1027{
1028  ErrorF("%s\n", DEFAULT_MODULE_PATH);
1029}
1030
1031static void
1032xf86PrintDefaultLibraryPath(void)
1033{
1034  ErrorF("%s\n", DEFAULT_LIBRARY_PATH);
1035}
1036
1037/*
1038 * ddxProcessArgument --
1039 *	Process device-dependent command line args. Returns 0 if argument is
1040 *      not device dependent, otherwise Count of number of elements of argv
1041 *      that are part of a device dependent commandline option.
1042 *
1043 */
1044
1045/* ARGSUSED */
1046int
1047ddxProcessArgument(int argc, char **argv, int i)
1048{
1049  /*
1050   * Note: can't use xalloc/xfree here because OsInit() hasn't been called
1051   * yet.  Use malloc/free instead.
1052   */
1053
1054#define CHECK_FOR_REQUIRED_ARGUMENT() \
1055    if (((i + 1) >= argc) || (!argv[i + 1])) { 				\
1056      ErrorF("Required argument to %s not specified\n", argv[i]); 	\
1057      UseMsg(); 							\
1058      FatalError("Required argument to %s not specified\n", argv[i]);	\
1059    }
1060
1061  /* First the options that are only allowed for root */
1062  if (!strcmp(argv[i], "-modulepath") || !strcmp(argv[i], "-logfile")) {
1063    if ( (geteuid() == 0) && (getuid() != 0) ) {
1064      FatalError("The '%s' option can only be used by root.\n", argv[i]);
1065    }
1066    else if (!strcmp(argv[i], "-modulepath"))
1067    {
1068      char *mp;
1069      CHECK_FOR_REQUIRED_ARGUMENT();
1070      mp = malloc(strlen(argv[i + 1]) + 1);
1071      if (!mp)
1072	FatalError("Can't allocate memory for ModulePath\n");
1073      strcpy(mp, argv[i + 1]);
1074      xf86ModulePath = mp;
1075      xf86ModPathFrom = X_CMDLINE;
1076      return 2;
1077    }
1078    else if (!strcmp(argv[i], "-logfile"))
1079    {
1080      char *lf;
1081      CHECK_FOR_REQUIRED_ARGUMENT();
1082      lf = malloc(strlen(argv[i + 1]) + 1);
1083      if (!lf)
1084	FatalError("Can't allocate memory for LogFile\n");
1085      strcpy(lf, argv[i + 1]);
1086      xf86LogFile = lf;
1087      xf86LogFileFrom = X_CMDLINE;
1088      return 2;
1089    }
1090  }
1091  if (!strcmp(argv[i], "-config") || !strcmp(argv[i], "-xf86config"))
1092  {
1093    CHECK_FOR_REQUIRED_ARGUMENT();
1094    if (getuid() != 0 && !xf86PathIsSafe(argv[i + 1])) {
1095      FatalError("\nInvalid argument for %s\n"
1096	  "\tFor non-root users, the file specified with %s must be\n"
1097	  "\ta relative path and must not contain any \"..\" elements.\n"
1098	  "\tUsing default "__XCONFIGFILE__" search path.\n\n",
1099	  argv[i], argv[i]);
1100    }
1101    xf86ConfigFile = argv[i + 1];
1102    return 2;
1103  }
1104  if (!strcmp(argv[i], "-configdir"))
1105  {
1106    CHECK_FOR_REQUIRED_ARGUMENT();
1107    if (getuid() != 0 && !xf86PathIsSafe(argv[i + 1])) {
1108      FatalError("\nInvalid argument for %s\n"
1109	  "\tFor non-root users, the file specified with %s must be\n"
1110	  "\ta relative path and must not contain any \"..\" elements.\n"
1111	  "\tUsing default "__XCONFIGDIR__" search path.\n\n",
1112	  argv[i], argv[i]);
1113    }
1114    xf86ConfigDir = argv[i + 1];
1115    return 2;
1116  }
1117  if (!strcmp(argv[i],"-flipPixels"))
1118  {
1119    xf86FlipPixels = TRUE;
1120    return 1;
1121  }
1122#ifdef XF86VIDMODE
1123  if (!strcmp(argv[i],"-disableVidMode"))
1124  {
1125    xf86VidModeDisabled = TRUE;
1126    return 1;
1127  }
1128  if (!strcmp(argv[i],"-allowNonLocalXvidtune"))
1129  {
1130    xf86VidModeAllowNonLocal = TRUE;
1131    return 1;
1132  }
1133#endif
1134  if (!strcmp(argv[i],"-allowMouseOpenFail"))
1135  {
1136    xf86AllowMouseOpenFail = TRUE;
1137    return 1;
1138  }
1139  if (!strcmp(argv[i],"-ignoreABI"))
1140  {
1141    LoaderSetOptions(LDR_OPT_ABI_MISMATCH_NONFATAL);
1142    return 1;
1143  }
1144  if (!strcmp(argv[i],"-verbose"))
1145  {
1146    if (++i < argc && argv[i])
1147    {
1148      char *end;
1149      long val;
1150      val = strtol(argv[i], &end, 0);
1151      if (*end == '\0')
1152      {
1153	xf86SetVerbosity(val);
1154	return 2;
1155      }
1156    }
1157    xf86SetVerbosity(++xf86Verbose);
1158    return 1;
1159  }
1160  if (!strcmp(argv[i],"-logverbose"))
1161  {
1162    if (++i < argc && argv[i])
1163    {
1164      char *end;
1165      long val;
1166      val = strtol(argv[i], &end, 0);
1167      if (*end == '\0')
1168      {
1169	xf86SetLogVerbosity(val);
1170	return 2;
1171      }
1172    }
1173    xf86SetLogVerbosity(++xf86LogVerbose);
1174    return 1;
1175  }
1176  if (!strcmp(argv[i],"-quiet"))
1177  {
1178    xf86SetVerbosity(-1);
1179    return 1;
1180  }
1181  if (!strcmp(argv[i],"-showconfig") || !strcmp(argv[i],"-version"))
1182  {
1183    xf86PrintBanner();
1184    exit(0);
1185  }
1186  if (!strcmp(argv[i],"-showDefaultModulePath"))
1187  {
1188    xf86PrintDefaultModulePath();
1189    exit(0);
1190  }
1191  if (!strcmp(argv[i],"-showDefaultLibPath"))
1192  {
1193    xf86PrintDefaultLibraryPath();
1194    exit(0);
1195  }
1196  /* Notice the -fp flag, but allow it to pass to the dix layer */
1197  if (!strcmp(argv[i], "-fp"))
1198  {
1199    xf86fpFlag = TRUE;
1200    return 0;
1201  }
1202  /* Notice the -bs flag, but allow it to pass to the dix layer */
1203  if (!strcmp(argv[i], "-bs"))
1204  {
1205    xf86bsDisableFlag = TRUE;
1206    return 0;
1207  }
1208  /* Notice the +bs flag, but allow it to pass to the dix layer */
1209  if (!strcmp(argv[i], "+bs"))
1210  {
1211    xf86bsEnableFlag = TRUE;
1212    return 0;
1213  }
1214  /* Notice the -s flag, but allow it to pass to the dix layer */
1215  if (!strcmp(argv[i], "-s"))
1216  {
1217    xf86sFlag = TRUE;
1218    return 0;
1219  }
1220  if (!strcmp(argv[i], "-pixmap24"))
1221  {
1222    xf86Pix24 = Pix24Use24;
1223    return 1;
1224  }
1225  if (!strcmp(argv[i], "-pixmap32"))
1226  {
1227    xf86Pix24 = Pix24Use32;
1228    return 1;
1229  }
1230  if (!strcmp(argv[i], "-fbbpp"))
1231  {
1232    int bpp;
1233    CHECK_FOR_REQUIRED_ARGUMENT();
1234    if (sscanf(argv[++i], "%d", &bpp) == 1)
1235    {
1236      xf86FbBpp = bpp;
1237      return 2;
1238    }
1239    else
1240    {
1241      ErrorF("Invalid fbbpp\n");
1242      return 0;
1243    }
1244  }
1245  if (!strcmp(argv[i], "-depth"))
1246  {
1247    int depth;
1248    CHECK_FOR_REQUIRED_ARGUMENT();
1249    if (sscanf(argv[++i], "%d", &depth) == 1)
1250    {
1251      xf86Depth = depth;
1252      return 2;
1253    }
1254    else
1255    {
1256      ErrorF("Invalid depth\n");
1257      return 0;
1258    }
1259  }
1260  if (!strcmp(argv[i], "-weight"))
1261  {
1262    int red, green, blue;
1263    CHECK_FOR_REQUIRED_ARGUMENT();
1264    if (sscanf(argv[++i], "%1d%1d%1d", &red, &green, &blue) == 3)
1265    {
1266      xf86Weight.red = red;
1267      xf86Weight.green = green;
1268      xf86Weight.blue = blue;
1269      return 2;
1270    }
1271    else
1272    {
1273      ErrorF("Invalid weighting\n");
1274      return 0;
1275    }
1276  }
1277  if (!strcmp(argv[i], "-gamma")  || !strcmp(argv[i], "-rgamma") ||
1278      !strcmp(argv[i], "-ggamma") || !strcmp(argv[i], "-bgamma"))
1279  {
1280    double gamma;
1281    CHECK_FOR_REQUIRED_ARGUMENT();
1282    if (sscanf(argv[++i], "%lf", &gamma) == 1) {
1283       if (gamma < GAMMA_MIN || gamma > GAMMA_MAX) {
1284	  ErrorF("gamma out of range, only  %.2f <= gamma_value <= %.1f"
1285		 " is valid\n", GAMMA_MIN, GAMMA_MAX);
1286	  return 0;
1287       }
1288       if (!strcmp(argv[i-1], "-gamma"))
1289	  xf86Gamma.red = xf86Gamma.green = xf86Gamma.blue = gamma;
1290       else if (!strcmp(argv[i-1], "-rgamma")) xf86Gamma.red = gamma;
1291       else if (!strcmp(argv[i-1], "-ggamma")) xf86Gamma.green = gamma;
1292       else if (!strcmp(argv[i-1], "-bgamma")) xf86Gamma.blue = gamma;
1293       return 2;
1294    }
1295  }
1296  if (!strcmp(argv[i], "-layout"))
1297  {
1298    CHECK_FOR_REQUIRED_ARGUMENT();
1299    xf86LayoutName = argv[++i];
1300    return 2;
1301  }
1302  if (!strcmp(argv[i], "-screen"))
1303  {
1304    CHECK_FOR_REQUIRED_ARGUMENT();
1305    xf86ScreenName = argv[++i];
1306    return 2;
1307  }
1308  if (!strcmp(argv[i], "-pointer"))
1309  {
1310    CHECK_FOR_REQUIRED_ARGUMENT();
1311    xf86PointerName = argv[++i];
1312    return 2;
1313  }
1314  if (!strcmp(argv[i], "-keyboard"))
1315  {
1316    CHECK_FOR_REQUIRED_ARGUMENT();
1317    xf86KeyboardName = argv[++i];
1318    return 2;
1319  }
1320  if (!strcmp(argv[i], "-nosilk"))
1321  {
1322    xf86silkenMouseDisableFlag = TRUE;
1323    return 1;
1324  }
1325#ifdef HAVE_ACPI
1326  if (!strcmp(argv[i], "-noacpi"))
1327  {
1328    xf86acpiDisableFlag = TRUE;
1329    return 1;
1330  }
1331#endif
1332  if (!strcmp(argv[i], "-configure"))
1333  {
1334    if (getuid() != 0 && geteuid() == 0) {
1335	ErrorF("The '-configure' option can only be used by root.\n");
1336	exit(1);
1337    }
1338    xf86DoConfigure = TRUE;
1339    xf86AllowMouseOpenFail = TRUE;
1340    return 1;
1341  }
1342  if (!strcmp(argv[i], "-showopts"))
1343  {
1344    if (getuid() != 0 && geteuid() == 0) {
1345    ErrorF("The '-showopts' option can only be used by root.\n");
1346    exit(1);
1347    }
1348    xf86DoShowOptions = TRUE;
1349    return 1;
1350  }
1351  if (!strcmp(argv[i], "-isolateDevice"))
1352  {
1353    CHECK_FOR_REQUIRED_ARGUMENT();
1354    if (strncmp(argv[++i], "PCI:", 4)) {
1355       FatalError("Bus types other than PCI not yet isolable\n");
1356    }
1357    xf86PciIsolateDevice(argv[i]);
1358    return 2;
1359  }
1360  /* Notice cmdline xkbdir, but pass to dix as well */
1361  if (!strcmp(argv[i], "-xkbdir"))
1362  {
1363    xf86xkbdirFlag = TRUE;
1364    return 0;
1365  }
1366
1367  /* OS-specific processing */
1368  return xf86ProcessArgument(argc, argv, i);
1369}
1370
1371/*
1372 * ddxUseMsg --
1373 *	Print out correct use of device dependent commandline options.
1374 *      Maybe the user now knows what really to do ...
1375 */
1376
1377void
1378ddxUseMsg(void)
1379{
1380  ErrorF("\n");
1381  ErrorF("\n");
1382  ErrorF("Device Dependent Usage\n");
1383  if (getuid() == 0 || geteuid() != 0)
1384  {
1385    ErrorF("-modulepath paths      specify the module search path\n");
1386    ErrorF("-logfile file          specify a log file name\n");
1387    ErrorF("-configure             probe for devices and write an "__XCONFIGFILE__"\n");
1388    ErrorF("-showopts              print available options for all installed drivers\n");
1389  }
1390  ErrorF("-config file           specify a configuration file, relative to the\n");
1391  ErrorF("                       "__XCONFIGFILE__" search path, only root can use absolute\n");
1392  ErrorF("-configdir dir         specify a configuration directory, relative to the\n");
1393  ErrorF("                       "__XCONFIGDIR__" search path, only root can use absolute\n");
1394  ErrorF("-verbose [n]           verbose startup messages\n");
1395  ErrorF("-logverbose [n]        verbose log messages\n");
1396  ErrorF("-quiet                 minimal startup messages\n");
1397  ErrorF("-pixmap24              use 24bpp pixmaps for depth 24\n");
1398  ErrorF("-pixmap32              use 32bpp pixmaps for depth 24\n");
1399  ErrorF("-fbbpp n               set bpp for the framebuffer. Default: 8\n");
1400  ErrorF("-depth n               set colour depth. Default: 8\n");
1401  ErrorF("-gamma f               set gamma value (0.1 < f < 10.0) Default: 1.0\n");
1402  ErrorF("-rgamma f              set gamma value for red phase\n");
1403  ErrorF("-ggamma f              set gamma value for green phase\n");
1404  ErrorF("-bgamma f              set gamma value for blue phase\n");
1405  ErrorF("-weight nnn            set RGB weighting at 16 bpp.  Default: 565\n");
1406  ErrorF("-layout name           specify the ServerLayout section name\n");
1407  ErrorF("-screen name           specify the Screen section name\n");
1408  ErrorF("-keyboard name         specify the core keyboard InputDevice name\n");
1409  ErrorF("-pointer name          specify the core pointer InputDevice name\n");
1410  ErrorF("-nosilk                disable Silken Mouse\n");
1411  ErrorF("-flipPixels            swap default black/white Pixel values\n");
1412#ifdef XF86VIDMODE
1413  ErrorF("-disableVidMode        disable mode adjustments with xvidtune\n");
1414  ErrorF("-allowNonLocalXvidtune allow xvidtune to be run as a non-local client\n");
1415#endif
1416  ErrorF("-allowMouseOpenFail    start server even if the mouse can't be initialized\n");
1417  ErrorF("-ignoreABI             make module ABI mismatches non-fatal\n");
1418  ErrorF("-isolateDevice bus_id  restrict device resets to bus_id (PCI only)\n");
1419  ErrorF("-version               show the server version\n");
1420  ErrorF("-showDefaultModulePath show the server default module path\n");
1421  ErrorF("-showDefaultLibPath    show the server default library path\n");
1422  /* OS-specific usage */
1423  xf86UseMsg();
1424  ErrorF("\n");
1425}
1426
1427
1428/*
1429 * xf86LoadModules iterates over a list that is being passed in.
1430 */
1431Bool
1432xf86LoadModules(char **list, pointer *optlist)
1433{
1434    int errmaj, errmin;
1435    pointer opt;
1436    int i;
1437    char *name;
1438    Bool failed = FALSE;
1439
1440    if (!list)
1441	return TRUE;
1442
1443    for (i = 0; list[i] != NULL; i++) {
1444
1445	/* Normalise the module name */
1446	name = xf86NormalizeName(list[i]);
1447
1448	/* Skip empty names */
1449	if (name == NULL || *name == '\0')
1450	    continue;
1451
1452	/* Replace obsolete keyboard driver with kbd */
1453	if (!xf86NameCmp(name, "keyboard")) {
1454	    strcpy(name, "kbd");
1455	}
1456
1457	if (optlist)
1458	    opt = optlist[i];
1459	else
1460	    opt = NULL;
1461
1462        if (!LoadModule(name, NULL, NULL, NULL, opt, NULL, &errmaj, &errmin)) {
1463	    LoaderErrorMsg(NULL, name, errmaj, errmin);
1464	    failed = TRUE;
1465	}
1466	free(name);
1467    }
1468    return !failed;
1469}
1470
1471/* Pixmap format stuff */
1472
1473PixmapFormatPtr
1474xf86GetPixFormat(ScrnInfoPtr pScrn, int depth)
1475{
1476    int i;
1477    static PixmapFormatRec format;	/* XXX not reentrant */
1478
1479    /*
1480     * When the formats[] list initialisation isn't complete, check the
1481     * depth 24 pixmap config/cmdline options and screen-specified formats.
1482     */
1483
1484    if (!formatsDone) {
1485	if (depth == 24) {
1486	    Pix24Flags pix24 = Pix24DontCare;
1487
1488	    format.depth = 24;
1489	    format.scanlinePad = BITMAP_SCANLINE_PAD;
1490	    if (xf86Info.pixmap24 != Pix24DontCare)
1491		pix24 = xf86Info.pixmap24;
1492	    else if (pScrn->pixmap24 != Pix24DontCare)
1493		pix24 = pScrn->pixmap24;
1494	    if (pix24 == Pix24Use24)
1495		format.bitsPerPixel = 24;
1496	    else
1497		format.bitsPerPixel = 32;
1498	    return &format;
1499	}
1500    }
1501
1502    for (i = 0; i < numFormats; i++)
1503	if (formats[i].depth == depth)
1504	   break;
1505    if (i != numFormats)
1506	return &formats[i];
1507    else if (!formatsDone) {
1508	/* Check for screen-specified formats */
1509	for (i = 0; i < pScrn->numFormats; i++)
1510	    if (pScrn->formats[i].depth == depth)
1511		break;
1512	if (i != pScrn->numFormats)
1513	    return &pScrn->formats[i];
1514    }
1515    return NULL;
1516}
1517
1518int
1519xf86GetBppFromDepth(ScrnInfoPtr pScrn, int depth)
1520{
1521    PixmapFormatPtr format;
1522
1523
1524    format = xf86GetPixFormat(pScrn, depth);
1525    if (format)
1526	return format->bitsPerPixel;
1527    else
1528	return 0;
1529}
1530