Imported Debian patch 2:1.11.4-0ubuntu8
[ubuntu-omap:xserver.git] / hw / xfree86 / common / xf86Init.c
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
92 void (*xf86OSPMClose)(void) = NULL;
93 #endif
94 static Bool xorgHWOpenConsole = FALSE;
95
96 /* Common pixmap formats */
97
98 static 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 };
107 static int numFormats = 7;
108 static 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
120 static void
121 xf86PrintBanner(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
233 static void
234 xf86PrintMarkers(void)
235 {
236   LogPrintMarkers();
237 }
238
239 static Bool
240 xf86CreateRootWindow(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
301 static void
302 InstallSignalHandlers(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         signal(SIGBUS, SIG_DFL);
318         signal(SIGSYS, SIG_DFL);
319         signal(SIGXCPU, SIG_DFL);
320         signal(SIGXFSZ, SIG_DFL);
321     }
322 }
323
324 /*
325  * InitOutput --
326  *      Initialize screenInfo for all actually accessible framebuffers.
327  *      That includes vt-manager setup, querying all possible devices and
328  *      collecting the pixmap formats.
329  */
330 void
331 InitOutput(ScreenInfo *pScreenInfo, int argc, char **argv)
332 {
333   int                    i, j, k, scr_index, was_blocked = 0;
334   char                   **modulelist;
335   pointer                *optionlist;
336   Pix24Flags             screenpix24, pix24;
337   MessageType            pix24From = X_DEFAULT;
338   Bool                   pix24Fail = FALSE;
339   Bool                   autoconfig = FALSE;
340   GDevPtr                configured_device;
341
342   xf86Initialising = TRUE;
343
344   if (serverGeneration == 1) {
345     if ((xf86ServerName = strrchr(argv[0], '/')) != 0)
346       xf86ServerName++;
347     else
348       xf86ServerName = argv[0];
349
350         xf86PrintBanner();
351         xf86PrintMarkers();
352         if (xf86LogFile)  {
353             time_t t;
354             const char *ct;
355             t = time(NULL);
356             ct = ctime(&t);
357             xf86MsgVerb(xf86LogFileFrom, 0, "Log file: \"%s\", Time: %s",
358                         xf86LogFile, ct);
359         }
360
361     /* Read and parse the config file */
362     if (!xf86DoConfigure && !xf86DoShowOptions) {
363       switch (xf86HandleConfigFile(FALSE)) {
364       case CONFIG_OK:
365         break;
366       case CONFIG_PARSE_ERROR:
367         xf86Msg(X_ERROR, "Error parsing the config file\n");
368         return;
369       case CONFIG_NOFILE:
370         autoconfig = TRUE;
371         break;
372       }
373     }
374
375     InstallSignalHandlers();
376
377     /* Initialise the loader */
378     LoaderInit();
379
380     /* Tell the loader the default module search path */
381     LoaderSetPath(xf86ModulePath);
382
383     if (xf86Info.ignoreABI) {
384         LoaderSetOptions(LDR_OPT_ABI_MISMATCH_NONFATAL);
385     }
386
387     if (xf86DoShowOptions)
388         DoShowOptions();
389
390     /* Do a general bus probe.  This will be a PCI probe for x86 platforms */
391     xf86BusProbe();
392
393     if (xf86DoConfigure)
394         DoConfigure();
395
396     if (autoconfig) {
397         if (!xf86AutoConfig()) {
398             xf86Msg(X_ERROR, "Auto configuration failed\n");
399             return;
400         }
401     }
402
403 #ifdef XF86PM
404     xf86OSPMClose = xf86OSPMOpen();
405 #endif
406
407     /* Load all modules specified explicitly in the config file */
408     if ((modulelist = xf86ModulelistFromConfig(&optionlist))) {
409       xf86LoadModules(modulelist, optionlist);
410       free(modulelist);
411       free(optionlist);
412     }
413
414     /* Load all driver modules specified in the config file */
415     /* If there aren't any specified in the config file, autoconfig them */
416     /* FIXME: Does not handle multiple active screen sections, but I'm not
417      * sure if we really want to handle that case*/
418     configured_device = xf86ConfigLayout.screens->screen->device;
419     if ((!configured_device) || (!configured_device->driver)) {
420         if (!autoConfigDevice(configured_device)) {
421             xf86Msg(X_ERROR, "Automatic driver configuration failed\n");
422             return ;
423         }
424     }
425     if ((modulelist = xf86DriverlistFromConfig())) {
426       xf86LoadModules(modulelist, NULL);
427       free(modulelist);
428     }
429
430     /* Load all input driver modules specified in the config file. */
431     if ((modulelist = xf86InputDriverlistFromConfig())) {
432       xf86LoadModules(modulelist, NULL);
433       free(modulelist);
434     }
435
436     /*
437      * It is expected that xf86AddDriver()/xf86AddInputDriver will be
438      * called for each driver as it is loaded.  Those functions save the
439      * module pointers for drivers.
440      * XXX Nothing keeps track of them for other modules.
441      */
442     /* XXX What do we do if not all of these could be loaded? */
443
444     /*
445      * At this point, xf86DriverList[] is all filled in with entries for
446      * each of the drivers to try and xf86NumDrivers has the number of
447      * drivers.  If there are none, return now.
448      */
449
450     if (xf86NumDrivers == 0) {
451       xf86Msg(X_ERROR, "No drivers available.\n");
452       return;
453     }
454
455     /*
456      * Call each of the Identify functions and call the driverFunc to check
457      * if HW access is required.  The Identify functions print out some
458      * identifying information, and anything else that might be
459      * needed at this early stage.
460      */
461
462     for (i = 0; i < xf86NumDrivers; i++) {
463         if (xf86DriverList[i]->Identify != NULL)
464             xf86DriverList[i]->Identify(0);
465
466         if (!xorgHWAccess || !xorgHWOpenConsole) {
467             xorgHWFlags flags;
468             if(!xf86DriverList[i]->driverFunc
469                 || !xf86DriverList[i]->driverFunc(NULL,
470                                                   GET_REQUIRED_HW_INTERFACES,
471                                                   &flags))
472                 flags = HW_IO;
473
474             if(NEED_IO_ENABLED(flags))
475                 xorgHWAccess = TRUE;
476             if(!(flags & HW_SKIP_CONSOLE))
477                 xorgHWOpenConsole = TRUE;
478         }
479     }
480
481     if (xorgHWOpenConsole)
482         xf86OpenConsole();
483     else
484         xf86Info.dontVTSwitch = TRUE;
485
486     if (xf86BusConfig() == FALSE)
487         return;
488
489     xf86PostProbe();
490
491     /*
492      * Sort the drivers to match the requested ording.  Using a slow
493      * bubble sort.
494      */
495     for (j = 0; j < xf86NumScreens - 1; j++) {
496         for (i = 0; i < xf86NumScreens - j - 1; i++) {
497             if (xf86Screens[i + 1]->confScreen->screennum <
498                 xf86Screens[i]->confScreen->screennum) {
499                 ScrnInfoPtr tmpScrn = xf86Screens[i + 1];
500                 xf86Screens[i + 1] = xf86Screens[i];
501                 xf86Screens[i] = tmpScrn;
502             }
503         }
504     }
505     /* Fix up the indexes */
506     for (i = 0; i < xf86NumScreens; i++) {
507         xf86Screens[i]->scrnIndex = i;
508     }
509
510     /*
511      * Call the driver's PreInit()'s to complete initialisation for the first
512      * generation.
513      */
514
515     for (i = 0; i < xf86NumScreens; i++) {
516         xf86VGAarbiterScrnInit(xf86Screens[i]);
517         xf86VGAarbiterLock(xf86Screens[i]);
518         if (xf86Screens[i]->PreInit &&
519             xf86Screens[i]->PreInit(xf86Screens[i], 0))
520             xf86Screens[i]->configured = TRUE;
521         xf86VGAarbiterUnlock(xf86Screens[i]);
522     }
523     for (i = 0; i < xf86NumScreens; i++)
524         if (!xf86Screens[i]->configured)
525             xf86DeleteScreen(i--, 0);
526
527     /*
528      * If no screens left, return now.
529      */
530
531     if (xf86NumScreens == 0) {
532       xf86Msg(X_ERROR,
533               "Screen(s) found, but none have a usable configuration.\n");
534       return;
535     }
536
537     for (i = 0; i < xf86NumScreens; i++) {
538       if (xf86Screens[i]->name == NULL) {
539         XNFasprintf(&xf86Screens[i]->name, "screen%d", i);
540         xf86MsgVerb(X_WARNING, 0,
541                     "Screen driver %d has no name set, using `%s'.\n",
542                     i, xf86Screens[i]->name);
543       }
544     }
545
546     /* Remove (unload) drivers that are not required */
547     for (i = 0; i < xf86NumDrivers; i++)
548         if (xf86DriverList[i] && xf86DriverList[i]->refCount <= 0)
549             xf86DeleteDriver(i);
550
551     /*
552      * At this stage we know how many screens there are.
553      */
554
555     for (i = 0; i < xf86NumScreens; i++)
556       xf86InitViewport(xf86Screens[i]);
557
558     /*
559      * Collect all pixmap formats and check for conflicts at the display
560      * level.  Should we die here?  Or just delete the offending screens?
561      */
562     screenpix24 = Pix24DontCare;
563     for (i = 0; i < xf86NumScreens; i++) {
564         if (xf86Screens[i]->imageByteOrder !=
565             xf86Screens[0]->imageByteOrder)
566             FatalError("Inconsistent display bitmapBitOrder.  Exiting\n");
567         if (xf86Screens[i]->bitmapScanlinePad !=
568             xf86Screens[0]->bitmapScanlinePad)
569             FatalError("Inconsistent display bitmapScanlinePad.  Exiting\n");
570         if (xf86Screens[i]->bitmapScanlineUnit !=
571             xf86Screens[0]->bitmapScanlineUnit)
572             FatalError("Inconsistent display bitmapScanlineUnit.  Exiting\n");
573         if (xf86Screens[i]->bitmapBitOrder !=
574             xf86Screens[0]->bitmapBitOrder)
575             FatalError("Inconsistent display bitmapBitOrder.  Exiting\n");
576
577         /* Determine the depth 24 pixmap format the screens would like */
578         if (xf86Screens[i]->pixmap24 != Pix24DontCare) {
579             if (screenpix24 == Pix24DontCare)
580                 screenpix24 = xf86Screens[i]->pixmap24;
581             else if (screenpix24 != xf86Screens[i]->pixmap24)
582                 FatalError("Inconsistent depth 24 pixmap format.  Exiting\n");
583         }
584     }
585     /* check if screenpix24 is consistent with the config/cmdline */
586     if (xf86Info.pixmap24 != Pix24DontCare) {
587         pix24 = xf86Info.pixmap24;
588         pix24From = xf86Info.pix24From;
589         if (screenpix24 != Pix24DontCare && screenpix24 != xf86Info.pixmap24)
590             pix24Fail = TRUE;
591     } else if (screenpix24 != Pix24DontCare) {
592         pix24 = screenpix24;
593         pix24From = X_PROBED;
594     } else
595         pix24 = Pix24Use32;
596
597     if (pix24Fail)
598         FatalError("Screen(s) can't use the required depth 24 pixmap format"
599                    " (%d).  Exiting\n", PIX24TOBPP(pix24));
600
601     /* Initialise the depth 24 format */
602     for (j = 0; j < numFormats && formats[j].depth != 24; j++)
603         ;
604     formats[j].bitsPerPixel = PIX24TOBPP(pix24);
605
606     /* Collect additional formats */
607     for (i = 0; i < xf86NumScreens; i++) {
608         for (j = 0; j < xf86Screens[i]->numFormats; j++) {
609             for (k = 0; ; k++) {
610                 if (k >= numFormats) {
611                     if (k >= MAXFORMATS)
612                         FatalError("Too many pixmap formats!  Exiting\n");
613                     formats[k] = xf86Screens[i]->formats[j];
614                     numFormats++;
615                     break;
616                 }
617                 if (formats[k].depth == xf86Screens[i]->formats[j].depth) {
618                     if ((formats[k].bitsPerPixel ==
619                          xf86Screens[i]->formats[j].bitsPerPixel) &&
620                         (formats[k].scanlinePad ==
621                          xf86Screens[i]->formats[j].scanlinePad))
622                         break;
623                     FatalError("Inconsistent pixmap format for depth %d."
624                                "  Exiting\n", formats[k].depth);
625                 }
626             }
627         }
628     }
629     formatsDone = TRUE;
630
631     if (xf86Info.vtno >= 0 ) {
632 #define VT_ATOM_NAME         "XFree86_VT"
633       Atom VTAtom=-1;
634       CARD32  *VT = NULL;
635       int  ret;
636
637       /* This memory needs to stay available until the screen has been
638          initialized, and we can create the property for real.
639       */
640       if ( (VT = malloc(sizeof(CARD32)))==NULL ) {
641         FatalError("Unable to make VT property - out of memory. Exiting...\n");
642       }
643       *VT = xf86Info.vtno;
644
645       VTAtom = MakeAtom(VT_ATOM_NAME, sizeof(VT_ATOM_NAME) - 1, TRUE);
646
647       for (i = 0, ret = Success; i < xf86NumScreens && ret == Success; i++) {
648         ret = xf86RegisterRootWindowProperty(xf86Screens[i]->scrnIndex,
649                                              VTAtom, XA_INTEGER, 32,
650                                              1, VT );
651         if (ret != Success)
652           xf86DrvMsg(xf86Screens[i]->scrnIndex, X_WARNING,
653                      "Failed to register VT property\n");
654       }
655     }
656
657     /* If a screen uses depth 24, show what the pixmap format is */
658     for (i = 0; i < xf86NumScreens; i++) {
659         if (xf86Screens[i]->depth == 24) {
660             xf86Msg(pix24From, "Depth 24 pixmap format is %d bpp\n",
661                     PIX24TOBPP(pix24));
662             break;
663         }
664     }
665   } else {
666     /*
667      * serverGeneration != 1; some OSs have to do things here, too.
668      */
669     if (xorgHWOpenConsole)
670         xf86OpenConsole();
671
672 #ifdef XF86PM
673     /*
674       should we reopen it here? We need to deal with an already opened
675       device. We could leave this to the OS layer. For now we simply
676       close it here
677     */
678     if (xf86OSPMClose)
679         xf86OSPMClose();
680     if ((xf86OSPMClose = xf86OSPMOpen()) != NULL)
681         xf86MsgVerb(X_INFO, 3, "APM registered successfully\n");
682 #endif
683
684     /* Make sure full I/O access is enabled */
685     if (xorgHWAccess)
686         xf86EnableIO();
687   }
688
689   /*
690    * Use the previously collected parts to setup pScreenInfo
691    */
692
693   pScreenInfo->imageByteOrder = xf86Screens[0]->imageByteOrder;
694   pScreenInfo->bitmapScanlinePad = xf86Screens[0]->bitmapScanlinePad;
695   pScreenInfo->bitmapScanlineUnit = xf86Screens[0]->bitmapScanlineUnit;
696   pScreenInfo->bitmapBitOrder = xf86Screens[0]->bitmapBitOrder;
697   pScreenInfo->numPixmapFormats = numFormats;
698   for (i = 0; i < numFormats; i++)
699     pScreenInfo->formats[i] = formats[i];
700
701   /* Make sure the server's VT is active */
702
703   if (serverGeneration != 1) {
704     xf86Resetting = TRUE;
705     /* All screens are in the same state, so just check the first */
706     if (!xf86Screens[0]->vtSema) {
707 #ifdef HAS_USL_VTS
708       ioctl(xf86Info.consoleFd, VT_RELDISP, VT_ACKACQ);
709 #endif
710       xf86AccessEnter();
711       was_blocked = xf86BlockSIGIO();
712     }
713   }
714
715   for (i = 0; i < xf86NumScreens; i++)
716       if (!xf86ColormapAllocatePrivates(xf86Screens[i]))
717           FatalError("Cannot register DDX private keys");
718
719   if (!dixRegisterPrivateKey(&xf86ScreenKeyRec, PRIVATE_SCREEN, 0) ||
720       !dixRegisterPrivateKey(&xf86CreateRootWindowKeyRec, PRIVATE_SCREEN, 0))
721       FatalError("Cannot register DDX private keys");
722
723   for (i = 0; i < xf86NumScreens; i++) {
724         xf86VGAarbiterLock(xf86Screens[i]);
725         /*
726          * Almost everything uses these defaults, and many of those that
727          * don't, will wrap them.
728          */
729         xf86Screens[i]->EnableDisableFBAccess = xf86EnableDisableFBAccess;
730 #ifdef XFreeXDGA
731         xf86Screens[i]->SetDGAMode = xf86SetDGAMode;
732 #endif
733         xf86Screens[i]->DPMSSet = NULL;
734         xf86Screens[i]->LoadPalette = NULL;
735         xf86Screens[i]->SetOverscan = NULL;
736         xf86Screens[i]->DriverFunc = NULL;
737         xf86Screens[i]->pScreen = NULL;
738         scr_index = AddScreen(xf86Screens[i]->ScreenInit, argc, argv);
739         xf86VGAarbiterUnlock(xf86Screens[i]);
740       if (scr_index == i) {
741         /*
742          * Hook in our ScrnInfoRec, and initialise some other pScreen
743          * fields.
744          */
745         dixSetPrivate(&screenInfo.screens[scr_index]->devPrivates,
746                       xf86ScreenKey, xf86Screens[i]);
747         xf86Screens[i]->pScreen = screenInfo.screens[scr_index];
748         /* The driver should set this, but make sure it is set anyway */
749         xf86Screens[i]->vtSema = TRUE;
750       } else {
751         /* This shouldn't normally happen */
752         FatalError("AddScreen/ScreenInit failed for driver %d\n", i);
753       }
754
755       DebugF("InitOutput - xf86Screens[%d]->pScreen = %p\n",
756              i, xf86Screens[i]->pScreen );
757       DebugF("xf86Screens[%d]->pScreen->CreateWindow = %p\n",
758              i, xf86Screens[i]->pScreen->CreateWindow );
759
760       dixSetPrivate(&screenInfo.screens[scr_index]->devPrivates,
761                     xf86CreateRootWindowKey,
762                     xf86Screens[i]->pScreen->CreateWindow);
763       xf86Screens[i]->pScreen->CreateWindow = xf86CreateRootWindow;
764
765     if (PictureGetSubpixelOrder (xf86Screens[i]->pScreen) == SubPixelUnknown)
766     {
767         xf86MonPtr DDC = (xf86MonPtr)(xf86Screens[i]->monitor->DDC);
768         PictureSetSubpixelOrder (xf86Screens[i]->pScreen,
769                                  DDC ?
770                                  (DDC->features.input_type ?
771                                   SubPixelHorizontalRGB : SubPixelNone) :
772                                  SubPixelUnknown);
773     }
774 #ifdef RANDR
775     if (!xf86Info.disableRandR)
776         xf86RandRInit (screenInfo.screens[scr_index]);
777     xf86Msg(xf86Info.randRFrom, "RandR %s\n",
778             xf86Info.disableRandR ? "disabled" : "enabled");
779 #endif
780   }
781
782   xf86VGAarbiterWrapFunctions();
783   xf86UnblockSIGIO(was_blocked);
784
785   xf86InitOrigins();
786
787   xf86Resetting = FALSE;
788   xf86Initialising = FALSE;
789
790   RegisterBlockAndWakeupHandlers((BlockHandlerProcPtr)NoopDDA, xf86Wakeup,
791                                  NULL);
792 }
793
794 static InputInfoPtr
795 duplicateDevice(InputInfoPtr pInfo)
796 {
797     InputInfoPtr dup = calloc(1, sizeof(InputInfoRec));
798     if (dup) {
799         dup->name = strdup(pInfo->name);
800         dup->driver = strdup(pInfo->driver);
801         dup->options = xf86OptionListDuplicate(pInfo->options);
802         /* type_name is a const string */
803         dup->type_name = pInfo->type_name;
804         dup->fd = -1;
805     }
806     return dup;
807 }
808
809 /**
810  * Initialize all supported input devices present and referenced in the
811  * xorg.conf.
812  */
813 void
814 InitInput(int argc, char **argv)
815 {
816     InputInfoPtr* pInfo;
817     DeviceIntPtr dev;
818
819     xf86Info.vtRequestsPending = FALSE;
820
821     mieqInit();
822
823     /* Initialize all configured input devices */
824     for (pInfo = xf86ConfigLayout.inputs; pInfo && *pInfo; pInfo++) {
825         InputInfoPtr dup;
826         /* Replace obsolete keyboard driver with kbd */
827         if (!xf86NameCmp((*pInfo)->driver, "keyboard")) {
828             strcpy((*pInfo)->driver, "kbd");
829         }
830
831         /* Data passed into xf86NewInputDevice will be freed on shutdown.
832          * Duplicate from xf86ConfigLayout.inputs, otherwise we don't have any
833          * xorg.conf input devices in the second generation
834          */
835         dup = duplicateDevice(*pInfo);
836
837         /* If one fails, the others will too */
838         if (xf86NewInputDevice(dup, &dev, TRUE) == BadAlloc)
839             break;
840     }
841
842     config_init();
843 }
844
845 void
846 CloseInput (void)
847 {
848     config_fini();
849     mieqFini();
850 }
851
852 /*
853  * OsVendorInit --
854  *      OS/Vendor-specific initialisations.  Called from OsInit(), which
855  *      is called by dix before establishing the well known sockets.
856  */
857
858 void
859 OsVendorInit(void)
860 {
861   static Bool beenHere = FALSE;
862
863   signal(SIGCHLD, SIG_DFL);     /* Need to wait for child processes */
864
865   if (!beenHere) {
866     umask(022);
867     xf86LogInit();
868   }
869
870         /* Set stderr to non-blocking. */
871 #ifndef O_NONBLOCK
872 #if defined(FNDELAY)
873 #define O_NONBLOCK FNDELAY
874 #elif defined(O_NDELAY)
875 #define O_NONBLOCK O_NDELAY
876 #endif
877
878 #ifdef O_NONBLOCK
879   if (!beenHere) {
880     if (geteuid() == 0 && getuid() != geteuid())
881     {
882       int status;
883
884       status = fcntl(fileno(stderr), F_GETFL, 0);
885       if (status != -1) {
886         fcntl(fileno(stderr), F_SETFL, status | O_NONBLOCK);
887       }
888     }
889   }
890 #endif
891 #endif
892
893   beenHere = TRUE;
894 }
895
896 /*
897  * ddxGiveUp --
898  *      Device dependent cleanup. Called by by dix before normal server death.
899  *      For SYSV386 we must switch the terminal back to normal mode. No error-
900  *      checking here, since there should be restored as much as possible.
901  */
902
903 void
904 ddxGiveUp(enum ExitCode error)
905 {
906     int i;
907
908     xf86VGAarbiterFini();
909
910 #ifdef XF86PM
911     if (xf86OSPMClose)
912         xf86OSPMClose();
913     xf86OSPMClose = NULL;
914 #endif
915
916     for (i = 0; i < xf86NumScreens; i++) {
917         /*
918          * zero all access functions to
919          * trap calls when switched away.
920          */
921         xf86Screens[i]->vtSema = FALSE;
922     }
923
924 #ifdef XFreeXDGA
925     DGAShutdown();
926 #endif
927
928     if (xorgHWOpenConsole)
929         xf86CloseConsole();
930
931     xf86CloseLog(error);
932
933     /* If an unexpected signal was caught, dump a core for debugging */
934     if (xf86Info.caughtSignal)
935         OsAbort();
936 }
937
938
939
940 /*
941  * AbortDDX --
942  *      DDX - specific abort routine.  Called by AbortServer(). The attempt is
943  *      made to restore all original setting of the displays. Also all devices
944  *      are closed.
945  */
946
947 void
948 AbortDDX(enum ExitCode error)
949 {
950   int i;
951
952   xf86BlockSIGIO();
953
954   /*
955    * try to restore the original video state
956    */
957 #ifdef DPMSExtension /* Turn screens back on */
958   if (DPMSPowerLevel != DPMSModeOn)
959       DPMSSet(serverClient, DPMSModeOn);
960 #endif
961   if (xf86Screens) {
962       for (i = 0; i < xf86NumScreens; i++)
963           if (xf86Screens[i]->vtSema) {
964               /*
965                * if we are aborting before ScreenInit() has finished
966                * we might not have been wrapped yet. Therefore enable
967                * screen explicitely.
968                */
969               xf86VGAarbiterLock(xf86Screens[i]);
970               (xf86Screens[i]->LeaveVT)(i, 0);
971               xf86VGAarbiterUnlock(xf86Screens[i]);
972           }
973   }
974
975   xf86AccessLeave();
976
977   /*
978    * This is needed for an abnormal server exit, since the normal exit stuff
979    * MUST also be performed (i.e. the vt must be left in a defined state)
980    */
981   ddxGiveUp(error);
982 }
983
984 void
985 OsVendorFatalError(void)
986 {
987 #ifdef VENDORSUPPORT
988     ErrorF("\nPlease refer to your Operating System Vendor support pages\n"
989            "at %s for support on this crash.\n",VENDORSUPPORT);
990 #else
991     ErrorF("\nPlease consult the "XVENDORNAME" support \n"
992            "\t at "__VENDORDWEBSUPPORT__"\n for help. \n");
993 #endif
994     if (xf86LogFile && xf86LogFileWasOpened)
995         ErrorF("Please also check the log file at \"%s\" for additional "
996               "information.\n", xf86LogFile);
997     ErrorF("\n");
998 }
999
1000 int
1001 xf86SetVerbosity(int verb)
1002 {
1003     int save = xf86Verbose;
1004
1005     xf86Verbose = verb;
1006     LogSetParameter(XLOG_VERBOSITY, verb);
1007     return save;
1008 }
1009
1010 int
1011 xf86SetLogVerbosity(int verb)
1012 {
1013     int save = xf86LogVerbose;
1014
1015     xf86LogVerbose = verb;
1016     LogSetParameter(XLOG_FILE_VERBOSITY, verb);
1017     return save;
1018 }
1019
1020 static void
1021 xf86PrintDefaultModulePath(void)
1022 {
1023   ErrorF("%s\n", DEFAULT_MODULE_PATH);
1024 }
1025
1026 static void
1027 xf86PrintDefaultLibraryPath(void)
1028 {
1029   ErrorF("%s\n", DEFAULT_LIBRARY_PATH);
1030 }
1031
1032 /*
1033  * ddxProcessArgument --
1034  *      Process device-dependent command line args. Returns 0 if argument is
1035  *      not device dependent, otherwise Count of number of elements of argv
1036  *      that are part of a device dependent commandline option.
1037  *
1038  */
1039
1040 /* ARGSUSED */
1041 int
1042 ddxProcessArgument(int argc, char **argv, int i)
1043 {
1044 #define CHECK_FOR_REQUIRED_ARGUMENT() \
1045     if (((i + 1) >= argc) || (!argv[i + 1])) {                          \
1046       ErrorF("Required argument to %s not specified\n", argv[i]);       \
1047       UseMsg();                                                         \
1048       FatalError("Required argument to %s not specified\n", argv[i]);   \
1049     }
1050
1051   /* First the options that are only allowed for root */
1052   if (!strcmp(argv[i], "-modulepath") || !strcmp(argv[i], "-logfile")) {
1053     if ( (geteuid() == 0) && (getuid() != 0) ) {
1054       FatalError("The '%s' option can only be used by root.\n", argv[i]);
1055     }
1056     else if (!strcmp(argv[i], "-modulepath"))
1057     {
1058       char *mp;
1059       CHECK_FOR_REQUIRED_ARGUMENT();
1060       mp = strdup(argv[i + 1]);
1061       if (!mp)
1062         FatalError("Can't allocate memory for ModulePath\n");
1063       xf86ModulePath = mp;
1064       xf86ModPathFrom = X_CMDLINE;
1065       return 2;
1066     }
1067     else if (!strcmp(argv[i], "-logfile"))
1068     {
1069       char *lf;
1070       CHECK_FOR_REQUIRED_ARGUMENT();
1071       lf = strdup(argv[i + 1]);
1072       if (!lf)
1073         FatalError("Can't allocate memory for LogFile\n");
1074       xf86LogFile = lf;
1075       xf86LogFileFrom = X_CMDLINE;
1076       return 2;
1077     }
1078   }
1079   if (!strcmp(argv[i], "-config") || !strcmp(argv[i], "-xf86config"))
1080   {
1081     CHECK_FOR_REQUIRED_ARGUMENT();
1082     if (getuid() != 0 && !xf86PathIsSafe(argv[i + 1])) {
1083       FatalError("\nInvalid argument for %s\n"
1084           "\tFor non-root users, the file specified with %s must be\n"
1085           "\ta relative path and must not contain any \"..\" elements.\n"
1086           "\tUsing default "__XCONFIGFILE__" search path.\n\n",
1087           argv[i], argv[i]);
1088     }
1089     xf86ConfigFile = argv[i + 1];
1090     return 2;
1091   }
1092   if (!strcmp(argv[i], "-configdir"))
1093   {
1094     CHECK_FOR_REQUIRED_ARGUMENT();
1095     if (getuid() != 0 && !xf86PathIsSafe(argv[i + 1])) {
1096       FatalError("\nInvalid argument for %s\n"
1097           "\tFor non-root users, the file specified with %s must be\n"
1098           "\ta relative path and must not contain any \"..\" elements.\n"
1099           "\tUsing default "__XCONFIGDIR__" search path.\n\n",
1100           argv[i], argv[i]);
1101     }
1102     xf86ConfigDir = argv[i + 1];
1103     return 2;
1104   }
1105   if (!strcmp(argv[i],"-flipPixels"))
1106   {
1107     xf86FlipPixels = TRUE;
1108     return 1;
1109   }
1110 #ifdef XF86VIDMODE
1111   if (!strcmp(argv[i],"-disableVidMode"))
1112   {
1113     xf86VidModeDisabled = TRUE;
1114     return 1;
1115   }
1116   if (!strcmp(argv[i],"-allowNonLocalXvidtune"))
1117   {
1118     xf86VidModeAllowNonLocal = TRUE;
1119     return 1;
1120   }
1121 #endif
1122   if (!strcmp(argv[i],"-allowMouseOpenFail"))
1123   {
1124     xf86AllowMouseOpenFail = TRUE;
1125     return 1;
1126   }
1127   if (!strcmp(argv[i],"-ignoreABI"))
1128   {
1129     LoaderSetOptions(LDR_OPT_ABI_MISMATCH_NONFATAL);
1130     return 1;
1131   }
1132   if (!strcmp(argv[i],"-verbose"))
1133   {
1134     if (++i < argc && argv[i])
1135     {
1136       char *end;
1137       long val;
1138       val = strtol(argv[i], &end, 0);
1139       if (*end == '\0')
1140       {
1141         xf86SetVerbosity(val);
1142         return 2;
1143       }
1144     }
1145     xf86SetVerbosity(++xf86Verbose);
1146     return 1;
1147   }
1148   if (!strcmp(argv[i],"-logverbose"))
1149   {
1150     if (++i < argc && argv[i])
1151     {
1152       char *end;
1153       long val;
1154       val = strtol(argv[i], &end, 0);
1155       if (*end == '\0')
1156       {
1157         xf86SetLogVerbosity(val);
1158         return 2;
1159       }
1160     }
1161     xf86SetLogVerbosity(++xf86LogVerbose);
1162     return 1;
1163   }
1164   if (!strcmp(argv[i],"-quiet"))
1165   {
1166     xf86SetVerbosity(-1);
1167     return 1;
1168   }
1169   if (!strcmp(argv[i],"-showconfig") || !strcmp(argv[i],"-version"))
1170   {
1171     xf86PrintBanner();
1172     exit(0);
1173   }
1174   if (!strcmp(argv[i],"-showDefaultModulePath"))
1175   {
1176     xf86PrintDefaultModulePath();
1177     exit(0);
1178   }
1179   if (!strcmp(argv[i],"-showDefaultLibPath"))
1180   {
1181     xf86PrintDefaultLibraryPath();
1182     exit(0);
1183   }
1184   /* Notice the -fp flag, but allow it to pass to the dix layer */
1185   if (!strcmp(argv[i], "-fp"))
1186   {
1187     xf86fpFlag = TRUE;
1188     return 0;
1189   }
1190   /* Notice the -bs flag, but allow it to pass to the dix layer */
1191   if (!strcmp(argv[i], "-bs"))
1192   {
1193     xf86bsDisableFlag = TRUE;
1194     return 0;
1195   }
1196   /* Notice the +bs flag, but allow it to pass to the dix layer */
1197   if (!strcmp(argv[i], "+bs"))
1198   {
1199     xf86bsEnableFlag = TRUE;
1200     return 0;
1201   }
1202   /* Notice the -s flag, but allow it to pass to the dix layer */
1203   if (!strcmp(argv[i], "-s"))
1204   {
1205     xf86sFlag = TRUE;
1206     return 0;
1207   }
1208   if (!strcmp(argv[i], "-pixmap24"))
1209   {
1210     xf86Pix24 = Pix24Use24;
1211     return 1;
1212   }
1213   if (!strcmp(argv[i], "-pixmap32"))
1214   {
1215     xf86Pix24 = Pix24Use32;
1216     return 1;
1217   }
1218   if (!strcmp(argv[i], "-fbbpp"))
1219   {
1220     int bpp;
1221     CHECK_FOR_REQUIRED_ARGUMENT();
1222     if (sscanf(argv[++i], "%d", &bpp) == 1)
1223     {
1224       xf86FbBpp = bpp;
1225       return 2;
1226     }
1227     else
1228     {
1229       ErrorF("Invalid fbbpp\n");
1230       return 0;
1231     }
1232   }
1233   if (!strcmp(argv[i], "-depth"))
1234   {
1235     int depth;
1236     CHECK_FOR_REQUIRED_ARGUMENT();
1237     if (sscanf(argv[++i], "%d", &depth) == 1)
1238     {
1239       xf86Depth = depth;
1240       return 2;
1241     }
1242     else
1243     {
1244       ErrorF("Invalid depth\n");
1245       return 0;
1246     }
1247   }
1248   if (!strcmp(argv[i], "-weight"))
1249   {
1250     int red, green, blue;
1251     CHECK_FOR_REQUIRED_ARGUMENT();
1252     if (sscanf(argv[++i], "%1d%1d%1d", &red, &green, &blue) == 3)
1253     {
1254       xf86Weight.red = red;
1255       xf86Weight.green = green;
1256       xf86Weight.blue = blue;
1257       return 2;
1258     }
1259     else
1260     {
1261       ErrorF("Invalid weighting\n");
1262       return 0;
1263     }
1264   }
1265   if (!strcmp(argv[i], "-gamma")  || !strcmp(argv[i], "-rgamma") ||
1266       !strcmp(argv[i], "-ggamma") || !strcmp(argv[i], "-bgamma"))
1267   {
1268     double gamma;
1269     CHECK_FOR_REQUIRED_ARGUMENT();
1270     if (sscanf(argv[++i], "%lf", &gamma) == 1) {
1271        if (gamma < GAMMA_MIN || gamma > GAMMA_MAX) {
1272           ErrorF("gamma out of range, only  %.2f <= gamma_value <= %.1f"
1273                  " is valid\n", GAMMA_MIN, GAMMA_MAX);
1274           return 0;
1275        }
1276        if (!strcmp(argv[i-1], "-gamma"))
1277           xf86Gamma.red = xf86Gamma.green = xf86Gamma.blue = gamma;
1278        else if (!strcmp(argv[i-1], "-rgamma")) xf86Gamma.red = gamma;
1279        else if (!strcmp(argv[i-1], "-ggamma")) xf86Gamma.green = gamma;
1280        else if (!strcmp(argv[i-1], "-bgamma")) xf86Gamma.blue = gamma;
1281        return 2;
1282     }
1283   }
1284   if (!strcmp(argv[i], "-layout"))
1285   {
1286     CHECK_FOR_REQUIRED_ARGUMENT();
1287     xf86LayoutName = argv[++i];
1288     return 2;
1289   }
1290   if (!strcmp(argv[i], "-screen"))
1291   {
1292     CHECK_FOR_REQUIRED_ARGUMENT();
1293     xf86ScreenName = argv[++i];
1294     return 2;
1295   }
1296   if (!strcmp(argv[i], "-pointer"))
1297   {
1298     CHECK_FOR_REQUIRED_ARGUMENT();
1299     xf86PointerName = argv[++i];
1300     return 2;
1301   }
1302   if (!strcmp(argv[i], "-keyboard"))
1303   {
1304     CHECK_FOR_REQUIRED_ARGUMENT();
1305     xf86KeyboardName = argv[++i];
1306     return 2;
1307   }
1308   if (!strcmp(argv[i], "-nosilk"))
1309   {
1310     xf86silkenMouseDisableFlag = TRUE;
1311     return 1;
1312   }
1313 #ifdef HAVE_ACPI
1314   if (!strcmp(argv[i], "-noacpi"))
1315   {
1316     xf86acpiDisableFlag = TRUE;
1317     return 1;
1318   }
1319 #endif
1320   if (!strcmp(argv[i], "-configure"))
1321   {
1322     if (getuid() != 0 && geteuid() == 0) {
1323         ErrorF("The '-configure' option can only be used by root.\n");
1324         exit(1);
1325     }
1326     xf86DoConfigure = TRUE;
1327     xf86AllowMouseOpenFail = TRUE;
1328     return 1;
1329   }
1330   if (!strcmp(argv[i], "-showopts"))
1331   {
1332     if (getuid() != 0 && geteuid() == 0) {
1333     ErrorF("The '-showopts' option can only be used by root.\n");
1334     exit(1);
1335     }
1336     xf86DoShowOptions = TRUE;
1337     return 1;
1338   }
1339   if (!strcmp(argv[i], "-isolateDevice"))
1340   {
1341     CHECK_FOR_REQUIRED_ARGUMENT();
1342     if (strncmp(argv[++i], "PCI:", 4)) {
1343        FatalError("Bus types other than PCI not yet isolable\n");
1344     }
1345     xf86PciIsolateDevice(argv[i]);
1346     return 2;
1347   }
1348   /* Notice cmdline xkbdir, but pass to dix as well */
1349   if (!strcmp(argv[i], "-xkbdir"))
1350   {
1351     xf86xkbdirFlag = TRUE;
1352     return 0;
1353   }
1354
1355   /* OS-specific processing */
1356   return xf86ProcessArgument(argc, argv, i);
1357 }
1358
1359 /*
1360  * ddxUseMsg --
1361  *      Print out correct use of device dependent commandline options.
1362  *      Maybe the user now knows what really to do ...
1363  */
1364
1365 void
1366 ddxUseMsg(void)
1367 {
1368   ErrorF("\n");
1369   ErrorF("\n");
1370   ErrorF("Device Dependent Usage\n");
1371   if (getuid() == 0 || geteuid() != 0)
1372   {
1373     ErrorF("-modulepath paths      specify the module search path\n");
1374     ErrorF("-logfile file          specify a log file name\n");
1375     ErrorF("-configure             probe for devices and write an "__XCONFIGFILE__"\n");
1376     ErrorF("-showopts              print available options for all installed drivers\n");
1377   }
1378   ErrorF("-config file           specify a configuration file, relative to the\n");
1379   ErrorF("                       "__XCONFIGFILE__" search path, only root can use absolute\n");
1380   ErrorF("-configdir dir         specify a configuration directory, relative to the\n");
1381   ErrorF("                       "__XCONFIGDIR__" search path, only root can use absolute\n");
1382   ErrorF("-verbose [n]           verbose startup messages\n");
1383   ErrorF("-logverbose [n]        verbose log messages\n");
1384   ErrorF("-quiet                 minimal startup messages\n");
1385   ErrorF("-pixmap24              use 24bpp pixmaps for depth 24\n");
1386   ErrorF("-pixmap32              use 32bpp pixmaps for depth 24\n");
1387   ErrorF("-fbbpp n               set bpp for the framebuffer. Default: 8\n");
1388   ErrorF("-depth n               set colour depth. Default: 8\n");
1389   ErrorF("-gamma f               set gamma value (0.1 < f < 10.0) Default: 1.0\n");
1390   ErrorF("-rgamma f              set gamma value for red phase\n");
1391   ErrorF("-ggamma f              set gamma value for green phase\n");
1392   ErrorF("-bgamma f              set gamma value for blue phase\n");
1393   ErrorF("-weight nnn            set RGB weighting at 16 bpp.  Default: 565\n");
1394   ErrorF("-layout name           specify the ServerLayout section name\n");
1395   ErrorF("-screen name           specify the Screen section name\n");
1396   ErrorF("-keyboard name         specify the core keyboard InputDevice name\n");
1397   ErrorF("-pointer name          specify the core pointer InputDevice name\n");
1398   ErrorF("-nosilk                disable Silken Mouse\n");
1399   ErrorF("-flipPixels            swap default black/white Pixel values\n");
1400 #ifdef XF86VIDMODE
1401   ErrorF("-disableVidMode        disable mode adjustments with xvidtune\n");
1402   ErrorF("-allowNonLocalXvidtune allow xvidtune to be run as a non-local client\n");
1403 #endif
1404   ErrorF("-allowMouseOpenFail    start server even if the mouse can't be initialized\n");
1405   ErrorF("-ignoreABI             make module ABI mismatches non-fatal\n");
1406   ErrorF("-isolateDevice bus_id  restrict device resets to bus_id (PCI only)\n");
1407   ErrorF("-version               show the server version\n");
1408   ErrorF("-showDefaultModulePath show the server default module path\n");
1409   ErrorF("-showDefaultLibPath    show the server default library path\n");
1410   /* OS-specific usage */
1411   xf86UseMsg();
1412   ErrorF("\n");
1413 }
1414
1415
1416 /*
1417  * xf86LoadModules iterates over a list that is being passed in.
1418  */
1419 Bool
1420 xf86LoadModules(char **list, pointer *optlist)
1421 {
1422     int errmaj, errmin;
1423     pointer opt;
1424     int i;
1425     char *name;
1426     Bool failed = FALSE;
1427
1428     if (!list)
1429         return TRUE;
1430
1431     for (i = 0; list[i] != NULL; i++) {
1432
1433         /* Normalise the module name */
1434         name = xf86NormalizeName(list[i]);
1435
1436         /* Skip empty names */
1437         if (name == NULL || *name == '\0') {
1438             free(name);
1439             continue;
1440         }
1441
1442         /* Replace obsolete keyboard driver with kbd */
1443         if (!xf86NameCmp(name, "keyboard")) {
1444             strcpy(name, "kbd");
1445         }
1446
1447         if (optlist)
1448             opt = optlist[i];
1449         else
1450             opt = NULL;
1451
1452         if (!LoadModule(name, NULL, NULL, NULL, opt, NULL, &errmaj, &errmin)) {
1453             LoaderErrorMsg(NULL, name, errmaj, errmin);
1454             failed = TRUE;
1455         }
1456         free(name);
1457     }
1458     return !failed;
1459 }
1460
1461 /* Pixmap format stuff */
1462
1463 PixmapFormatPtr
1464 xf86GetPixFormat(ScrnInfoPtr pScrn, int depth)
1465 {
1466     int i;
1467     static PixmapFormatRec format;      /* XXX not reentrant */
1468
1469     /*
1470      * When the formats[] list initialisation isn't complete, check the
1471      * depth 24 pixmap config/cmdline options and screen-specified formats.
1472      */
1473
1474     if (!formatsDone) {
1475         if (depth == 24) {
1476             Pix24Flags pix24 = Pix24DontCare;
1477
1478             format.depth = 24;
1479             format.scanlinePad = BITMAP_SCANLINE_PAD;
1480             if (xf86Info.pixmap24 != Pix24DontCare)
1481                 pix24 = xf86Info.pixmap24;
1482             else if (pScrn->pixmap24 != Pix24DontCare)
1483                 pix24 = pScrn->pixmap24;
1484             if (pix24 == Pix24Use24)
1485                 format.bitsPerPixel = 24;
1486             else
1487                 format.bitsPerPixel = 32;
1488             return &format;
1489         }
1490     }
1491
1492     for (i = 0; i < numFormats; i++)
1493         if (formats[i].depth == depth)
1494            break;
1495     if (i != numFormats)
1496         return &formats[i];
1497     else if (!formatsDone) {
1498         /* Check for screen-specified formats */
1499         for (i = 0; i < pScrn->numFormats; i++)
1500             if (pScrn->formats[i].depth == depth)
1501                 break;
1502         if (i != pScrn->numFormats)
1503             return &pScrn->formats[i];
1504     }
1505     return NULL;
1506 }
1507
1508 int
1509 xf86GetBppFromDepth(ScrnInfoPtr pScrn, int depth)
1510 {
1511     PixmapFormatPtr format;
1512
1513
1514     format = xf86GetPixFormat(pScrn, depth);
1515     if (format)
1516         return format->bitsPerPixel;
1517     else
1518         return 0;
1519 }