xf86Config.c revision 311f2276
1/*
2 * Loosely based on code bearing the following copyright:
3 *
4 *   Copyright 1990,91 by Thomas Roell, Dinkelscherben, Germany.
5 */
6
7/*
8 * Copyright 1992-2003 by The XFree86 Project, Inc.
9 * Copyright 1997 by Metro Link, Inc.
10 *
11 * Permission is hereby granted, free of charge, to any person obtaining a
12 * copy of this software and associated documentation files (the "Software"),
13 * to deal in the Software without restriction, including without limitation
14 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
15 * and/or sell copies of the Software, and to permit persons to whom the
16 * Software is furnished to do so, subject to the following conditions:
17 *
18 * The above copyright notice and this permission notice shall be included in
19 * all copies or substantial portions of the Software.
20 *
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
22 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
23 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
24 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
25 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
26 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
27 * OTHER DEALINGS IN THE SOFTWARE.
28 *
29 * Except as contained in this notice, the name of the copyright holder(s)
30 * and author(s) shall not be used in advertising or otherwise to promote
31 * the sale, use or other dealings in this Software without prior written
32 * authorization from the copyright holder(s) and author(s).
33 */
34
35/*
36 *
37 * Authors:
38 *	Dirk Hohndel <hohndel@XFree86.Org>
39 *	David Dawes <dawes@XFree86.Org>
40 *      Marc La France <tsi@XFree86.Org>
41 *      Egbert Eich <eich@XFree86.Org>
42 *      ... and others
43 */
44
45#ifdef HAVE_XORG_CONFIG_H
46#include <xorg-config.h>
47#endif
48
49#ifdef XF86DRI
50#include <sys/types.h>
51#include <grp.h>
52#endif
53
54#include "xf86.h"
55#include "xf86Parser.h"
56#include "xf86tokens.h"
57#include "xf86Config.h"
58#include "xf86Priv.h"
59#include "xf86_OSlib.h"
60#include "configProcs.h"
61#include "globals.h"
62#include "extension.h"
63#include "xf86pciBus.h"
64
65#include "xf86Xinput.h"
66
67#include "xkbsrv.h"
68
69#include "picture.h"
70
71/*
72 * These paths define the way the config file search is done.  The escape
73 * sequences are documented in parser/scan.c.
74 */
75#ifndef ROOT_CONFIGPATH
76#define ROOT_CONFIGPATH	"%A," "%R," \
77			"/etc/X11/%R," "%P/etc/X11/%R," \
78			"%E," "%F," \
79			"/etc/X11/%F," "%P/etc/X11/%F," \
80			"/etc/X11/%X," "/etc/%X," \
81			"%P/etc/X11/%X.%H," \
82			"%P/etc/X11/%X," \
83			"%P/lib/X11/%X.%H," \
84			"%P/lib/X11/%X"
85#endif
86#ifndef USER_CONFIGPATH
87#define USER_CONFIGPATH	"/etc/X11/%S," "%P/etc/X11/%S," \
88			"/etc/X11/%G," "%P/etc/X11/%G," \
89			"/etc/X11/%X," "/etc/%X," \
90			"%P/etc/X11/%X.%H," \
91			"%P/etc/X11/%X," \
92			"%P/lib/X11/%X.%H," \
93			"%P/lib/X11/%X"
94#endif
95#ifndef ROOT_CONFIGDIRPATH
96#define ROOT_CONFIGDIRPATH	"%A," "%R," \
97				"/etc/X11/%R," "%C/X11/%R," \
98				"/etc/X11/%X," "%C/X11/%X"
99#endif
100#ifndef USER_CONFIGDIRPATH
101#define USER_CONFIGDIRPATH	"/etc/X11/%R," "%C/X11/%R," \
102				"/etc/X11/%X," "%C/X11/%X"
103#endif
104#ifndef SYS_CONFIGDIRPATH
105#define SYS_CONFIGDIRPATH	"/usr/share/X11/%X," "%D/X11/%X"
106#endif
107#ifndef PROJECTROOT
108#define PROJECTROOT	"/usr/X11R6"
109#endif
110
111static ModuleDefault ModuleDefaults[] = {
112    {.name = "extmod",   .toLoad = TRUE,    .load_opt=NULL},
113#ifdef DBE
114    {.name = "dbe",      .toLoad = TRUE,    .load_opt=NULL},
115#endif
116#ifdef GLXEXT
117    {.name = "glx",      .toLoad = TRUE,    .load_opt=NULL},
118#endif
119#ifdef XRECORD
120    {.name = "record",   .toLoad = TRUE,    .load_opt=NULL},
121#endif
122#ifdef XF86DRI
123    {.name = "dri",      .toLoad = TRUE,    .load_opt=NULL},
124#endif
125#ifdef DRI2
126    {.name = "dri2",     .toLoad = TRUE,    .load_opt=NULL},
127#endif
128    {.name = NULL,       .toLoad = FALSE,   .load_opt=NULL}
129};
130
131
132/* Forward declarations */
133static Bool configScreen(confScreenPtr screenp, XF86ConfScreenPtr conf_screen,
134			 int scrnum, MessageType from);
135static Bool configMonitor(MonPtr monitorp, XF86ConfMonitorPtr conf_monitor);
136static Bool configDevice(GDevPtr devicep, XF86ConfDevicePtr conf_device,
137			 Bool active);
138static Bool configInput(InputInfoPtr pInfo, XF86ConfInputPtr conf_input,
139			MessageType from);
140static Bool configDisplay(DispPtr displayp, XF86ConfDisplayPtr conf_display);
141static Bool addDefaultModes(MonPtr monitorp);
142#ifdef XF86DRI
143static void configDRI(XF86ConfDRIPtr drip);
144#endif
145static void configExtensions(XF86ConfExtensionsPtr conf_ext);
146
147/*
148 * xf86GetPathElem --
149 *	Extract a single element from the font path string starting at
150 *	pnt.  The font path element will be returned, and pnt will be
151 *	updated to point to the start of the next element, or set to
152 *	NULL if there are no more.
153 */
154static char *
155xf86GetPathElem(char **pnt)
156{
157  char *p1;
158
159  p1 = *pnt;
160  *pnt = index(*pnt, ',');
161  if (*pnt != NULL) {
162    **pnt = '\0';
163    *pnt += 1;
164  }
165  return p1;
166}
167
168/*
169 * xf86ValidateFontPath --
170 *	Validates the user-specified font path.  Each element that
171 *	begins with a '/' is checked to make sure the directory exists.
172 *	If the directory exists, the existence of a file named 'fonts.dir'
173 *	is checked.  If either check fails, an error is printed and the
174 *	element is removed from the font path.
175 */
176
177#define DIR_FILE "/fonts.dir"
178static char *
179xf86ValidateFontPath(char *path)
180{
181  char *tmp_path, *out_pnt, *path_elem, *next, *p1, *dir_elem;
182  struct stat stat_buf;
183  int flag;
184  int dirlen;
185
186  tmp_path = calloc(1,strlen(path)+1);
187  out_pnt = tmp_path;
188  path_elem = NULL;
189  next = path;
190  while (next != NULL) {
191    path_elem = xf86GetPathElem(&next);
192    if (*path_elem == '/') {
193      dir_elem = xnfcalloc(1, strlen(path_elem) + 1);
194      if ((p1 = strchr(path_elem, ':')) != 0)
195	dirlen = p1 - path_elem;
196      else
197	dirlen = strlen(path_elem);
198      strncpy(dir_elem, path_elem, dirlen);
199      dir_elem[dirlen] = '\0';
200      flag = stat(dir_elem, &stat_buf);
201      if (flag == 0)
202	if (!S_ISDIR(stat_buf.st_mode))
203	  flag = -1;
204      if (flag != 0) {
205        xf86Msg(X_WARNING, "The directory \"%s\" does not exist.\n", dir_elem);
206	xf86ErrorF("\tEntry deleted from font path.\n");
207	free(dir_elem);
208	continue;
209      }
210      else {
211	XNFasprintf(&p1, "%s%s", dir_elem, DIR_FILE);
212	flag = stat(p1, &stat_buf);
213	if (flag == 0)
214	  if (!S_ISREG(stat_buf.st_mode))
215	    flag = -1;
216	free(p1);
217	if (flag != 0) {
218	  xf86Msg(X_WARNING,
219		  "`fonts.dir' not found (or not valid) in \"%s\".\n",
220		  dir_elem);
221	  xf86ErrorF("\tEntry deleted from font path.\n");
222	  xf86ErrorF("\t(Run 'mkfontdir' on \"%s\").\n", dir_elem);
223	  free(dir_elem);
224	  continue;
225	}
226      }
227      free(dir_elem);
228    }
229
230    /*
231     * Either an OK directory, or a font server name.  So add it to
232     * the path.
233     */
234    if (out_pnt != tmp_path)
235      *out_pnt++ = ',';
236    strcat(out_pnt, path_elem);
237    out_pnt += strlen(path_elem);
238  }
239  return tmp_path;
240}
241
242
243/*
244 * use the datastructure that the parser provides and pick out the parts
245 * that we need at this point
246 */
247char **
248xf86ModulelistFromConfig(pointer **optlist)
249{
250    int count = 0, i = 0;
251    char **modulearray;
252    char *ignore[] = { "GLcore", "speedo", "bitmap", "drm",
253		       "freetype", "type1",
254		       NULL };
255    pointer *optarray;
256    XF86LoadPtr modp;
257    Bool found;
258
259    /*
260     * make sure the config file has been parsed and that we have a
261     * ModulePath set; if no ModulePath was given, use the default
262     * ModulePath
263     */
264    if (xf86configptr == NULL) {
265        xf86Msg(X_ERROR, "Cannot access global config data structure\n");
266        return NULL;
267    }
268
269    if (xf86configptr->conf_modules) {
270        /* Walk the disable list and let people know what we've parsed to
271         * not be loaded
272         */
273        modp = xf86configptr->conf_modules->mod_disable_lst;
274        while (modp) {
275            xf86Msg(X_WARNING, "\"%s\" will not be loaded unless you've specified it to be loaded elsewhere.\n", modp->load_name);
276	        modp = (XF86LoadPtr) modp->list.next;
277        }
278        /*
279         * Walk the default settings table. For each module listed to be
280         * loaded, make sure it's in the mod_load_lst. If it's not, make
281         * sure it's not in the mod_no_load_lst. If it's not disabled,
282         * append it to mod_load_lst
283         */
284         for (i=0 ; ModuleDefaults[i].name != NULL ; i++) {
285            if (ModuleDefaults[i].toLoad == FALSE) {
286                xf86Msg(X_WARNING, "\"%s\" is not to be loaded by default. Skipping.\n", ModuleDefaults[i].name);
287                continue;
288            }
289            found = FALSE;
290            modp = xf86configptr->conf_modules->mod_load_lst;
291            while (modp) {
292                if (strcmp(modp->load_name, ModuleDefaults[i].name) == 0) {
293                    xf86Msg(X_INFO, "\"%s\" will be loaded. This was enabled by default and also specified in the config file.\n", ModuleDefaults[i].name);
294                    found = TRUE;
295                    break;
296                }
297	        modp = (XF86LoadPtr) modp->list.next;
298            }
299            if (found == FALSE) {
300                modp = xf86configptr->conf_modules->mod_disable_lst;
301                while (modp) {
302                    if (strcmp(modp->load_name, ModuleDefaults[i].name) == 0) {
303                        xf86Msg(X_INFO, "\"%s\" will be loaded even though the default is to disable it.\n", ModuleDefaults[i].name);
304                        found = TRUE;
305                        break;
306                    }
307	                modp = (XF86LoadPtr) modp->list.next;
308                }
309            }
310            if (found == FALSE) {
311		XF86LoadPtr ptr = (XF86LoadPtr)xf86configptr->conf_modules;
312                xf86addNewLoadDirective(ptr, ModuleDefaults[i].name, XF86_LOAD_MODULE, ModuleDefaults[i].load_opt);
313                xf86Msg(X_INFO, "\"%s\" will be loaded by default.\n", ModuleDefaults[i].name);
314            }
315         }
316    } else {
317	xf86configptr->conf_modules = xnfcalloc(1, sizeof(XF86ConfModuleRec));
318	for (i=0 ; ModuleDefaults[i].name != NULL ; i++) {
319	    if (ModuleDefaults[i].toLoad == TRUE) {
320		XF86LoadPtr ptr = (XF86LoadPtr)xf86configptr->conf_modules;
321		xf86addNewLoadDirective(ptr, ModuleDefaults[i].name, XF86_LOAD_MODULE, ModuleDefaults[i].load_opt);
322	    }
323	}
324    }
325
326	    /*
327	     * Walk the list of modules in the "Module" section to determine how
328	     * many we have.
329	    */
330	    modp = xf86configptr->conf_modules->mod_load_lst;
331	    while (modp) {
332                for (i = 0; ignore[i]; i++) {
333                    if (strcmp(modp->load_name, ignore[i]) == 0)
334                        modp->ignore = 1;
335                }
336                if (!modp->ignore)
337	            count++;
338	        modp = (XF86LoadPtr) modp->list.next;
339	    }
340
341    /*
342     * allocate the memory and walk the list again to fill in the pointers
343     */
344    modulearray = xnfalloc((count + 1) * sizeof(char*));
345    optarray = xnfalloc((count + 1) * sizeof(pointer));
346    count = 0;
347    if (xf86configptr->conf_modules) {
348	    modp = xf86configptr->conf_modules->mod_load_lst;
349	    while (modp) {
350            if (!modp->ignore) {
351	            modulearray[count] = modp->load_name;
352	            optarray[count] = modp->load_opt;
353	            count++;
354            }
355	        modp = (XF86LoadPtr) modp->list.next;
356	    }
357    }
358    modulearray[count] = NULL;
359    optarray[count] = NULL;
360    if (optlist)
361	    *optlist = optarray;
362    else
363	    free(optarray);
364    return modulearray;
365}
366
367
368char **
369xf86DriverlistFromConfig(void)
370{
371    int count = 0;
372    int j;
373    char **modulearray;
374    screenLayoutPtr slp;
375
376    /*
377     * make sure the config file has been parsed and that we have a
378     * ModulePath set; if no ModulePath was given, use the default
379     * ModulePath
380     */
381    if (xf86configptr == NULL) {
382        xf86Msg(X_ERROR, "Cannot access global config data structure\n");
383        return NULL;
384    }
385
386    /*
387     * Walk the list of driver lines in active "Device" sections to
388     * determine now many implicitly loaded modules there are.
389     *
390     */
391    if (xf86ConfigLayout.screens) {
392        slp = xf86ConfigLayout.screens;
393        while ((slp++)->screen) {
394	    count++;
395        }
396    }
397
398    /*
399     * Handle the set of inactive "Device" sections.
400     */
401    j = 0;
402    while (xf86ConfigLayout.inactives[j++].identifier)
403	count++;
404
405    if (count == 0)
406	return NULL;
407
408    /*
409     * allocate the memory and walk the list again to fill in the pointers
410     */
411    modulearray = xnfalloc((count + 1) * sizeof(char*));
412    count = 0;
413    slp = xf86ConfigLayout.screens;
414    while (slp->screen) {
415	modulearray[count] = slp->screen->device->driver;
416	count++;
417	slp++;
418    }
419
420    j = 0;
421
422    while (xf86ConfigLayout.inactives[j].identifier)
423	modulearray[count++] = xf86ConfigLayout.inactives[j++].driver;
424
425    modulearray[count] = NULL;
426
427    /* Remove duplicates */
428    for (count = 0; modulearray[count] != NULL; count++) {
429	int i;
430
431	for (i = 0; i < count; i++)
432	    if (xf86NameCmp(modulearray[i], modulearray[count]) == 0) {
433		modulearray[count] = "";
434		break;
435	    }
436    }
437    return modulearray;
438}
439
440char **
441xf86InputDriverlistFromConfig(void)
442{
443    int count = 0;
444    char **modulearray;
445    InputInfoPtr *idp;
446
447    /*
448     * make sure the config file has been parsed and that we have a
449     * ModulePath set; if no ModulePath was given, use the default
450     * ModulePath
451     */
452    if (xf86configptr == NULL) {
453        xf86Msg(X_ERROR, "Cannot access global config data structure\n");
454        return NULL;
455    }
456
457    /*
458     * Walk the list of driver lines in active "InputDevice" sections to
459     * determine now many implicitly loaded modules there are.
460     */
461    if (xf86ConfigLayout.inputs) {
462        idp = xf86ConfigLayout.inputs;
463        while (*idp) {
464	    count++;
465	    idp++;
466        }
467    }
468
469    if (count == 0)
470	return NULL;
471
472    /*
473     * allocate the memory and walk the list again to fill in the pointers
474     */
475    modulearray = xnfalloc((count + 1) * sizeof(char*));
476    count = 0;
477    idp = xf86ConfigLayout.inputs;
478    while (idp && *idp) {
479        modulearray[count] = (*idp)->driver;
480	count++;
481	idp++;
482    }
483    modulearray[count] = NULL;
484
485    /* Remove duplicates */
486    for (count = 0; modulearray[count] != NULL; count++) {
487	int i;
488
489	for (i = 0; i < count; i++)
490	    if (xf86NameCmp(modulearray[i], modulearray[count]) == 0) {
491		modulearray[count] = "";
492		break;
493	    }
494    }
495    return modulearray;
496}
497
498static void
499fixup_video_driver_list(char **drivers)
500{
501    static const char *fallback[4] = { "vesa", "fbdev", "wsfb", NULL };
502    char **end, **drv;
503    char *x;
504    int i;
505
506    /* walk to the end of the list */
507    for (end = drivers; *end && **end; end++) ;
508    end--;
509
510    /*
511     * for each of the fallback drivers, if we find it in the list,
512     * swap it with the last available non-fallback driver.
513     */
514    for (i = 0; fallback[i]; i++) {
515        for (drv = drivers; drv != end; drv++) {
516            if (strstr(*drv, fallback[i])) {
517                x = *drv; *drv = *end; *end = x;
518                end--;
519                break;
520            }
521        }
522    }
523}
524
525static char **
526GenerateDriverlist(char * dirname)
527{
528    char **ret;
529    const char *subdirs[] = { dirname, NULL };
530    static const char *patlist[] = {"(.*)_drv\\.so$", "(.*)_drv\\.o$", NULL};
531    ret = LoaderListDirs(subdirs, patlist);
532
533    /* fix up the probe order for video drivers */
534    if (strstr(dirname, "drivers") && ret != NULL)
535        fixup_video_driver_list(ret);
536
537    return ret;
538}
539
540char **
541xf86DriverlistFromCompile(void)
542{
543    static char **driverlist = NULL;
544
545    if (!driverlist)
546        driverlist = GenerateDriverlist("drivers");
547
548    return driverlist;
549}
550
551/*
552 * xf86ConfigError --
553 *      Print a READABLE ErrorMessage!!!  All information that is
554 *      available is printed.
555 */
556static void
557xf86ConfigError(char *msg, ...)
558{
559    va_list ap;
560
561    ErrorF("\nConfig Error:\n");
562    va_start(ap, msg);
563    VErrorF(msg, ap);
564    va_end(ap);
565    ErrorF("\n");
566    return;
567}
568
569static void
570configFiles(XF86ConfFilesPtr fileconf)
571{
572    MessageType	 pathFrom;
573    Bool	 must_copy;
574    int		 size, countDirs;
575    char	*temp_path, *log_buf, *start, *end;
576
577    /* FontPath */
578    must_copy = TRUE;
579
580    temp_path = defaultFontPath ? defaultFontPath : "";
581    if (xf86fpFlag)
582	pathFrom = X_CMDLINE;
583    else if (fileconf && fileconf->file_fontpath) {
584	pathFrom = X_CONFIG;
585	if (xf86Info.useDefaultFontPath) {
586	    if (asprintf(&defaultFontPath, "%s%s%s", fileconf->file_fontpath,
587			 *temp_path ? "," : "", temp_path) == -1)
588		defaultFontPath = NULL;
589	    else
590		must_copy = FALSE;
591	}
592	else
593	    defaultFontPath = fileconf->file_fontpath;
594    }
595    else
596	pathFrom = X_DEFAULT;
597    temp_path = defaultFontPath ? defaultFontPath : "";
598
599    /* xf86ValidateFontPath modifies its argument, but returns a copy of it. */
600    temp_path = must_copy ? xnfstrdup(defaultFontPath) : defaultFontPath;
601    defaultFontPath = xf86ValidateFontPath(temp_path);
602    free(temp_path);
603
604    /* make fontpath more readable in the logfiles */
605    countDirs = 1;
606    temp_path = defaultFontPath;
607    while ((temp_path = index(temp_path, ',')) != NULL) {
608	countDirs++;
609	temp_path++;
610    }
611
612    log_buf = xnfalloc(strlen(defaultFontPath) + (2 * countDirs) + 1);
613    temp_path = log_buf;
614    start = defaultFontPath;
615    while((end = index(start, ',')) != NULL) {
616      size = (end - start) + 1;
617      *(temp_path++) = '\t';
618      strncpy(temp_path, start, size);
619      temp_path += size;
620      *(temp_path++) = '\n';
621      start += size;
622    }
623    /* copy last entry */
624    *(temp_path++) = '\t';
625    strcpy(temp_path, start);
626    xf86Msg(pathFrom, "FontPath set to:\n%s\n", log_buf);
627    free(log_buf);
628
629  /* ModulePath */
630
631  if (fileconf) {
632    if (xf86ModPathFrom != X_CMDLINE && fileconf->file_modulepath) {
633      xf86ModulePath = fileconf->file_modulepath;
634      xf86ModPathFrom = X_CONFIG;
635    }
636  }
637
638  xf86Msg(xf86ModPathFrom, "ModulePath set to \"%s\"\n", xf86ModulePath);
639
640  if (!xf86xkbdirFlag && fileconf && fileconf->file_xkbdir) {
641    XkbBaseDirectory = fileconf->file_xkbdir;
642    xf86Msg(X_CONFIG, "XKB base directory set to \"%s\"\n",
643	    XkbBaseDirectory);
644  }
645#if 0
646  /* LogFile */
647  /*
648   * XXX The problem with this is that the log file is already open.
649   * One option might be to copy the exiting contents to the new location.
650   * and re-open it.  The down side is that the default location would
651   * already have been overwritten.  Another option would be to start with
652   * unique temporary location, then copy it once the correct name is known.
653   * A problem with this is what happens if the server exits before that
654   * happens.
655   */
656  if (xf86LogFileFrom == X_DEFAULT && fileconf->file_logfile) {
657    xf86LogFile = fileconf->file_logfile;
658    xf86LogFileFrom = X_CONFIG;
659  }
660#endif
661
662  return;
663}
664
665typedef enum {
666    FLAG_NOTRAPSIGNALS,
667    FLAG_DONTVTSWITCH,
668    FLAG_DONTZAP,
669    FLAG_DONTZOOM,
670    FLAG_DISABLEVIDMODE,
671    FLAG_ALLOWNONLOCAL,
672    FLAG_ALLOWMOUSEOPENFAIL,
673    FLAG_VTSYSREQ,
674    FLAG_SAVER_BLANKTIME,
675    FLAG_DPMS_STANDBYTIME,
676    FLAG_DPMS_SUSPENDTIME,
677    FLAG_DPMS_OFFTIME,
678    FLAG_PIXMAP,
679    FLAG_PC98,
680    FLAG_NOPM,
681    FLAG_XINERAMA,
682    FLAG_LOG,
683    FLAG_RENDER_COLORMAP_MODE,
684    FLAG_RANDR,
685    FLAG_AIGLX,
686    FLAG_IGNORE_ABI,
687    FLAG_ALLOW_EMPTY_INPUT,
688    FLAG_USE_DEFAULT_FONT_PATH,
689    FLAG_AUTO_ADD_DEVICES,
690    FLAG_AUTO_ENABLE_DEVICES,
691    FLAG_GLX_VISUALS,
692    FLAG_DRI2,
693    FLAG_USE_SIGIO
694} FlagValues;
695
696/**
697 * NOTE: the last value for each entry is NOT the default. It is set to TRUE
698 * if the parser found the option in the config file.
699 */
700static OptionInfoRec FlagOptions[] = {
701  { FLAG_NOTRAPSIGNALS,		"NoTrapSignals",		OPTV_BOOLEAN,
702	{0}, FALSE },
703  { FLAG_DONTVTSWITCH,		"DontVTSwitch",			OPTV_BOOLEAN,
704	{0}, FALSE },
705  { FLAG_DONTZAP,		"DontZap",			OPTV_BOOLEAN,
706	{0}, FALSE },
707  { FLAG_DONTZOOM,		"DontZoom",			OPTV_BOOLEAN,
708	{0}, FALSE },
709  { FLAG_DISABLEVIDMODE,	"DisableVidModeExtension",	OPTV_BOOLEAN,
710	{0}, FALSE },
711  { FLAG_ALLOWNONLOCAL,		"AllowNonLocalXvidtune",	OPTV_BOOLEAN,
712	{0}, FALSE },
713  { FLAG_ALLOWMOUSEOPENFAIL,	"AllowMouseOpenFail",		OPTV_BOOLEAN,
714	{0}, FALSE },
715  { FLAG_VTSYSREQ,		"VTSysReq",			OPTV_BOOLEAN,
716	{0}, FALSE },
717  { FLAG_SAVER_BLANKTIME,	"BlankTime"		,	OPTV_INTEGER,
718	{0}, FALSE },
719  { FLAG_DPMS_STANDBYTIME,	"StandbyTime",			OPTV_INTEGER,
720	{0}, FALSE },
721  { FLAG_DPMS_SUSPENDTIME,	"SuspendTime",			OPTV_INTEGER,
722	{0}, FALSE },
723  { FLAG_DPMS_OFFTIME,		"OffTime",			OPTV_INTEGER,
724	{0}, FALSE },
725  { FLAG_PIXMAP,		"Pixmap",			OPTV_INTEGER,
726	{0}, FALSE },
727  { FLAG_PC98,			"PC98",				OPTV_BOOLEAN,
728	{0}, FALSE },
729  { FLAG_NOPM,			"NoPM",				OPTV_BOOLEAN,
730	{0}, FALSE },
731  { FLAG_XINERAMA,		"Xinerama",			OPTV_BOOLEAN,
732	{0}, FALSE },
733  { FLAG_LOG,			"Log",				OPTV_STRING,
734	{0}, FALSE },
735  { FLAG_RENDER_COLORMAP_MODE,	"RenderColormapMode",		OPTV_STRING,
736        {0}, FALSE },
737  { FLAG_RANDR,			"RandR",			OPTV_BOOLEAN,
738	{0}, FALSE },
739  { FLAG_AIGLX,			"AIGLX",			OPTV_BOOLEAN,
740	{0}, FALSE },
741  { FLAG_IGNORE_ABI,		"IgnoreABI",			OPTV_BOOLEAN,
742	{0}, FALSE },
743  { FLAG_USE_DEFAULT_FONT_PATH,  "UseDefaultFontPath",		OPTV_BOOLEAN,
744	{0}, FALSE },
745  { FLAG_AUTO_ADD_DEVICES,       "AutoAddDevices",		OPTV_BOOLEAN,
746        {0}, FALSE },
747  { FLAG_AUTO_ENABLE_DEVICES,    "AutoEnableDevices",		OPTV_BOOLEAN,
748        {0}, FALSE },
749  { FLAG_GLX_VISUALS,		"GlxVisuals",			OPTV_STRING,
750        {0}, FALSE },
751  { FLAG_DRI2,			"DRI2",				OPTV_BOOLEAN,
752	{0}, FALSE },
753  { FLAG_USE_SIGIO,		"UseSIGIO",			OPTV_BOOLEAN,
754	{0}, FALSE },
755  { -1,				NULL,				OPTV_NONE,
756	{0}, FALSE },
757};
758
759#ifdef SUPPORT_PC98
760static Bool
761detectPC98(void)
762{
763    unsigned char buf[2];
764
765    if (xf86ReadBIOS(0xf8000, 0xe80, buf, 2) != 2)
766	return FALSE;
767    if ((buf[0] == 0x98) && (buf[1] == 0x21))
768	return TRUE;
769    else
770	return FALSE;
771}
772#endif
773
774static Bool
775configServerFlags(XF86ConfFlagsPtr flagsconf, XF86OptionPtr layoutopts)
776{
777    XF86OptionPtr optp, tmp;
778    int i;
779    Pix24Flags pix24 = Pix24DontCare;
780    Bool value;
781    MessageType from;
782    const char *s;
783    XkbRMLVOSet set;
784    /* Default options. */
785    set.rules = "base";
786    set.model = "pc105";
787    set.layout = "us";
788    set.variant = NULL;
789    set.options = NULL;
790
791    /*
792     * Merge the ServerLayout and ServerFlags options.  The former have
793     * precedence over the latter.
794     */
795    optp = NULL;
796    if (flagsconf && flagsconf->flg_option_lst)
797	optp = xf86optionListDup(flagsconf->flg_option_lst);
798    if (layoutopts) {
799	tmp = xf86optionListDup(layoutopts);
800	if (optp)
801	    optp = xf86optionListMerge(optp, tmp);
802	else
803	    optp = tmp;
804    }
805
806    xf86ProcessOptions(-1, optp, FlagOptions);
807
808    xf86GetOptValBool(FlagOptions, FLAG_NOTRAPSIGNALS, &xf86Info.notrapSignals);
809    xf86GetOptValBool(FlagOptions, FLAG_DONTVTSWITCH, &xf86Info.dontVTSwitch);
810    xf86GetOptValBool(FlagOptions, FLAG_DONTZAP, &xf86Info.dontZap);
811    xf86GetOptValBool(FlagOptions, FLAG_DONTZOOM, &xf86Info.dontZoom);
812
813    xf86GetOptValBool(FlagOptions, FLAG_IGNORE_ABI, &xf86Info.ignoreABI);
814    if (xf86Info.ignoreABI) {
815	    xf86Msg(X_CONFIG, "Ignoring ABI Version\n");
816    }
817
818    if (xf86SIGIOSupported()) {
819	xf86Info.useSIGIO = xf86ReturnOptValBool(FlagOptions, FLAG_USE_SIGIO, USE_SIGIO_BY_DEFAULT);
820	if (xf86IsOptionSet(FlagOptions, FLAG_USE_SIGIO)) {
821	    from = X_CONFIG;
822	} else {
823	    from = X_DEFAULT;
824	}
825	if (!xf86Info.useSIGIO) {
826	    xf86Msg(from, "Disabling SIGIO handlers for input devices\n");
827	} else if (from == X_CONFIG) {
828	    xf86Msg(from, "Enabling SIGIO handlers for input devices\n");
829	}
830    } else {
831	xf86Info.useSIGIO = FALSE;
832    }
833
834    if (xf86IsOptionSet(FlagOptions, FLAG_AUTO_ADD_DEVICES)) {
835        xf86GetOptValBool(FlagOptions, FLAG_AUTO_ADD_DEVICES,
836                          &xf86Info.autoAddDevices);
837        from = X_CONFIG;
838    }
839    else {
840        from = X_DEFAULT;
841    }
842    xf86Msg(from, "%sutomatically adding devices\n",
843            xf86Info.autoAddDevices ? "A" : "Not a");
844
845    if (xf86IsOptionSet(FlagOptions, FLAG_AUTO_ENABLE_DEVICES)) {
846        xf86GetOptValBool(FlagOptions, FLAG_AUTO_ENABLE_DEVICES,
847                          &xf86Info.autoEnableDevices);
848        from = X_CONFIG;
849    }
850    else {
851        from = X_DEFAULT;
852    }
853    xf86Msg(from, "%sutomatically enabling devices\n",
854            xf86Info.autoEnableDevices ? "A" : "Not a");
855
856    /*
857     * Set things up based on the config file information.  Some of these
858     * settings may be overridden later when the command line options are
859     * checked.
860     */
861#ifdef XF86VIDMODE
862    if (xf86GetOptValBool(FlagOptions, FLAG_DISABLEVIDMODE, &value))
863	xf86Info.vidModeEnabled = !value;
864    if (xf86GetOptValBool(FlagOptions, FLAG_ALLOWNONLOCAL, &value))
865	xf86Info.vidModeAllowNonLocal = value;
866#endif
867
868    if (xf86GetOptValBool(FlagOptions, FLAG_ALLOWMOUSEOPENFAIL, &value))
869	xf86Info.allowMouseOpenFail = value;
870
871    if (xf86GetOptValBool(FlagOptions, FLAG_VTSYSREQ, &value)) {
872#ifdef USE_VT_SYSREQ
873	xf86Info.vtSysreq = value;
874	xf86Msg(X_CONFIG, "VTSysReq %s\n", value ? "enabled" : "disabled");
875#else
876	if (value)
877	    xf86Msg(X_WARNING, "VTSysReq is not supported on this OS\n");
878#endif
879    }
880
881    xf86Info.pmFlag = TRUE;
882    if (xf86GetOptValBool(FlagOptions, FLAG_NOPM, &value))
883	xf86Info.pmFlag = !value;
884    {
885	if ((s = xf86GetOptValString(FlagOptions, FLAG_LOG))) {
886	    if (!xf86NameCmp(s,"flush")) {
887		xf86Msg(X_CONFIG, "Flushing logfile enabled\n");
888		xf86Info.log = LogFlush;
889		LogSetParameter(XLOG_FLUSH, TRUE);
890	    } else if (!xf86NameCmp(s,"sync")) {
891		xf86Msg(X_CONFIG, "Syncing logfile enabled\n");
892		xf86Info.log = LogSync;
893		LogSetParameter(XLOG_FLUSH, TRUE);
894		LogSetParameter(XLOG_SYNC, TRUE);
895	    } else {
896		xf86Msg(X_WARNING,"Unknown Log option\n");
897	    }
898        }
899    }
900
901    {
902	if ((s = xf86GetOptValString(FlagOptions, FLAG_RENDER_COLORMAP_MODE))){
903	    int policy = PictureParseCmapPolicy (s);
904	    if (policy == PictureCmapPolicyInvalid)
905		xf86Msg(X_WARNING, "Unknown colormap policy \"%s\"\n", s);
906	    else
907	    {
908		xf86Msg(X_CONFIG, "Render colormap policy set to %s\n", s);
909		PictureCmapPolicy = policy;
910	    }
911	}
912    }
913
914#ifdef RANDR
915    xf86Info.disableRandR = FALSE;
916    xf86Info.randRFrom = X_DEFAULT;
917    if (xf86GetOptValBool(FlagOptions, FLAG_RANDR, &value)) {
918	xf86Info.disableRandR = !value;
919	xf86Info.randRFrom = X_CONFIG;
920    }
921#endif
922
923    xf86Info.aiglx = TRUE;
924    xf86Info.aiglxFrom = X_DEFAULT;
925    if (xf86GetOptValBool(FlagOptions, FLAG_AIGLX, &value)) {
926	xf86Info.aiglx = value;
927	xf86Info.aiglxFrom = X_CONFIG;
928    }
929
930#ifdef GLXEXT
931    xf86Info.glxVisuals = XF86_GlxVisualsTypical;
932    xf86Info.glxVisualsFrom = X_DEFAULT;
933    if ((s = xf86GetOptValString(FlagOptions, FLAG_GLX_VISUALS))) {
934	if (!xf86NameCmp(s, "minimal")) {
935	    xf86Info.glxVisuals = XF86_GlxVisualsMinimal;
936	} else if (!xf86NameCmp(s, "typical")) {
937	    xf86Info.glxVisuals = XF86_GlxVisualsTypical;
938	} else if (!xf86NameCmp(s, "all")) {
939	    xf86Info.glxVisuals = XF86_GlxVisualsAll;
940	} else {
941	    xf86Msg(X_WARNING,"Unknown GlxVisuals option\n");
942	}
943    }
944
945    if (xf86GetOptValBool(FlagOptions, FLAG_AIGLX, &value)) {
946	xf86Info.aiglx = value;
947	xf86Info.aiglxFrom = X_CONFIG;
948    }
949#endif
950
951    /* if we're not hotplugging, force some input devices to exist */
952    xf86Info.forceInputDevices = !(xf86Info.autoAddDevices && xf86Info.autoEnableDevices);
953
954    /* when forcing input devices, we use kbd. otherwise evdev, so use the
955     * evdev rules set. */
956#if defined(linux)
957    if (!xf86Info.forceInputDevices)
958        set.rules = "evdev";
959#endif
960    XkbSetRulesDflts(&set);
961
962    xf86Info.useDefaultFontPath = TRUE;
963    xf86Info.useDefaultFontPathFrom = X_DEFAULT;
964    if (xf86GetOptValBool(FlagOptions, FLAG_USE_DEFAULT_FONT_PATH, &value)) {
965	xf86Info.useDefaultFontPath = value;
966	xf86Info.useDefaultFontPathFrom = X_CONFIG;
967    }
968
969/* Make sure that timers don't overflow CARD32's after multiplying */
970#define MAX_TIME_IN_MIN (0x7fffffff / MILLI_PER_MIN)
971
972    i = -1;
973    xf86GetOptValInteger(FlagOptions, FLAG_SAVER_BLANKTIME, &i);
974    if ((i >= 0) && (i < MAX_TIME_IN_MIN))
975	ScreenSaverTime = defaultScreenSaverTime = i * MILLI_PER_MIN;
976    else if (i != -1)
977	xf86ConfigError("BlankTime value %d outside legal range of 0 - %d minutes",
978			i, MAX_TIME_IN_MIN);
979
980#ifdef DPMSExtension
981    i = -1;
982    xf86GetOptValInteger(FlagOptions, FLAG_DPMS_STANDBYTIME, &i);
983    if ((i >= 0) && (i < MAX_TIME_IN_MIN))
984	DPMSStandbyTime = i * MILLI_PER_MIN;
985    else if (i != -1)
986	xf86ConfigError("StandbyTime value %d outside legal range of 0 - %d minutes",
987			i, MAX_TIME_IN_MIN);
988    i = -1;
989    xf86GetOptValInteger(FlagOptions, FLAG_DPMS_SUSPENDTIME, &i);
990    if ((i >= 0) && (i < MAX_TIME_IN_MIN))
991	DPMSSuspendTime = i * MILLI_PER_MIN;
992    else if (i != -1)
993	xf86ConfigError("SuspendTime value %d outside legal range of 0 - %d minutes",
994			i, MAX_TIME_IN_MIN);
995    i = -1;
996    xf86GetOptValInteger(FlagOptions, FLAG_DPMS_OFFTIME, &i);
997    if ((i >= 0) && (i < MAX_TIME_IN_MIN))
998	DPMSOffTime = i * MILLI_PER_MIN;
999    else if (i != -1)
1000	xf86ConfigError("OffTime value %d outside legal range of 0 - %d minutes",
1001			i, MAX_TIME_IN_MIN);
1002#endif
1003
1004    i = -1;
1005    xf86GetOptValInteger(FlagOptions, FLAG_PIXMAP, &i);
1006    switch (i) {
1007    case 24:
1008	pix24 = Pix24Use24;
1009	break;
1010    case 32:
1011	pix24 = Pix24Use32;
1012	break;
1013    case -1:
1014	break;
1015    default:
1016	xf86ConfigError("Pixmap option's value (%d) must be 24 or 32\n", i);
1017	return FALSE;
1018    }
1019    if (xf86Pix24 != Pix24DontCare) {
1020	xf86Info.pixmap24 = xf86Pix24;
1021	xf86Info.pix24From = X_CMDLINE;
1022    } else if (pix24 != Pix24DontCare) {
1023	xf86Info.pixmap24 = pix24;
1024	xf86Info.pix24From = X_CONFIG;
1025    } else {
1026	xf86Info.pixmap24 = Pix24DontCare;
1027	xf86Info.pix24From = X_DEFAULT;
1028    }
1029#ifdef SUPPORT_PC98
1030    if (xf86GetOptValBool(FlagOptions, FLAG_PC98, &value)) {
1031	xf86Info.pc98 = value;
1032	if (value) {
1033	    xf86Msg(X_CONFIG, "Japanese PC98 architecture\n");
1034	}
1035    } else
1036	if (detectPC98()) {
1037	    xf86Info.pc98 = TRUE;
1038	    xf86Msg(X_PROBED, "Japanese PC98 architecture\n");
1039	}
1040#endif
1041
1042#ifdef PANORAMIX
1043    from = X_DEFAULT;
1044    if (!noPanoramiXExtension)
1045      from = X_CMDLINE;
1046    else if (xf86GetOptValBool(FlagOptions, FLAG_XINERAMA, &value)) {
1047      noPanoramiXExtension = !value;
1048      from = X_CONFIG;
1049    }
1050    if (!noPanoramiXExtension)
1051      xf86Msg(from, "Xinerama: enabled\n");
1052#endif
1053
1054#ifdef DRI2
1055    xf86Info.dri2 = FALSE;
1056    xf86Info.dri2From = X_DEFAULT;
1057    if (xf86GetOptValBool(FlagOptions, FLAG_DRI2, &value)) {
1058	xf86Info.dri2 = value;
1059	xf86Info.dri2From = X_CONFIG;
1060    }
1061#endif
1062
1063    return TRUE;
1064}
1065
1066Bool xf86DRI2Enabled(void)
1067{
1068    return xf86Info.dri2;
1069}
1070
1071/*
1072 * Locate the core input devices.  These can be specified/located in
1073 * the following ways, in order of priority:
1074 *
1075 *  1. The InputDevices named by the -pointer and -keyboard command line
1076 *     options.
1077 *  2. The "CorePointer" and "CoreKeyboard" InputDevices referred to by
1078 *     the active ServerLayout.
1079 *  3. The first InputDevices marked as "CorePointer" and "CoreKeyboard".
1080 *  4. The first InputDevices that use 'keyboard' or 'kbd' and a valid mouse
1081 *     driver (mouse, synaptics, evdev, vmmouse, void)
1082 *  5. Default devices with an empty (default) configuration.  These defaults
1083 *     will reference the 'mouse' and 'keyboard' drivers.
1084 */
1085
1086static Bool
1087checkCoreInputDevices(serverLayoutPtr servlayoutp, Bool implicitLayout)
1088{
1089    InputInfoPtr corePointer = NULL, coreKeyboard = NULL;
1090    Bool foundPointer = FALSE, foundKeyboard = FALSE;
1091    const char *pointerMsg = NULL, *keyboardMsg = NULL;
1092    InputInfoPtr *devs, /* iterator */
1093            indp;
1094    InputInfoRec Pointer = {}, Keyboard = {};
1095    XF86ConfInputPtr confInput;
1096    XF86ConfInputRec defPtr, defKbd;
1097    int count = 0;
1098    MessageType from = X_DEFAULT;
1099    int found = 0;
1100    const char *mousedrivers[] = { "mouse", "synaptics", "evdev", "vmmouse",
1101				   "void", NULL };
1102
1103    /*
1104     * First check if a core pointer or core keyboard have been specified
1105     * in the active ServerLayout.  If more than one is specified for either,
1106     * remove the core attribute from the later ones.
1107     */
1108    for (devs = servlayoutp->inputs; devs && *devs; devs++) {
1109        indp = *devs;
1110	if (indp->options &&
1111	    xf86CheckBoolOption(indp->options, "CorePointer", FALSE)) {
1112	    if (!corePointer) {
1113		corePointer = indp;
1114	    } else {
1115		    xf86ReplaceBoolOption(indp->options, "CorePointer", FALSE);
1116		xf86Msg(X_WARNING, "Duplicate core pointer devices.  "
1117			"Removing core pointer attribute from \"%s\"\n",
1118			indp->name);
1119	    }
1120	}
1121	if (indp->options &&
1122	    xf86CheckBoolOption(indp->options, "CoreKeyboard", FALSE)) {
1123	    if (!coreKeyboard) {
1124		coreKeyboard = indp;
1125	    } else {
1126		    xf86ReplaceBoolOption(indp->options, "CoreKeyboard", FALSE);
1127		xf86Msg(X_WARNING, "Duplicate core keyboard devices.  "
1128			"Removing core keyboard attribute from \"%s\"\n",
1129			indp->name);
1130	    }
1131	}
1132	count++;
1133    }
1134
1135    confInput = NULL;
1136
1137    /* 1. Check for the -pointer command line option. */
1138    if (xf86PointerName) {
1139	confInput = xf86findInput(xf86PointerName,
1140				  xf86configptr->conf_input_lst);
1141	if (!confInput) {
1142	    xf86Msg(X_ERROR, "No InputDevice section called \"%s\"\n",
1143		    xf86PointerName);
1144	    return FALSE;
1145	}
1146	from = X_CMDLINE;
1147	/*
1148	 * If one was already specified in the ServerLayout, it needs to be
1149	 * removed.
1150	 */
1151	if (corePointer) {
1152	    for (devs = servlayoutp->inputs; devs && *devs; devs++)
1153		if (*devs == corePointer)
1154                {
1155                    free(*devs);
1156                    *devs = (InputInfoPtr)0x1; /* ensure we dont skip next loop*/
1157		    break;
1158                }
1159	    for (; devs && *devs; devs++)
1160		devs[0] = devs[1];
1161	    count--;
1162	}
1163	corePointer = NULL;
1164	foundPointer = TRUE;
1165    }
1166
1167    /* 2. ServerLayout-specified core pointer. */
1168    if (corePointer) {
1169	foundPointer = TRUE;
1170	from = X_CONFIG;
1171    }
1172
1173    /* 3. First core pointer device. */
1174    if (!foundPointer && (xf86Info.forceInputDevices || implicitLayout)) {
1175	XF86ConfInputPtr p;
1176
1177	for (p = xf86configptr->conf_input_lst; p; p = p->list.next) {
1178	    if (p->inp_option_lst &&
1179		xf86CheckBoolOption(p->inp_option_lst, "CorePointer", FALSE)) {
1180		confInput = p;
1181		foundPointer = TRUE;
1182		from = X_DEFAULT;
1183		pointerMsg = "first core pointer device";
1184		break;
1185	    }
1186	}
1187    }
1188
1189    /* 4. First pointer with an allowed mouse driver. */
1190    if (!foundPointer && xf86Info.forceInputDevices) {
1191	const char **driver = mousedrivers;
1192	confInput = xf86findInput(CONF_IMPLICIT_POINTER,
1193				  xf86configptr->conf_input_lst);
1194	while (*driver && !confInput) {
1195	    confInput = xf86findInputByDriver(*driver,
1196					      xf86configptr->conf_input_lst);
1197	    driver++;
1198	}
1199	if (confInput) {
1200	    foundPointer = TRUE;
1201	    from = X_DEFAULT;
1202	    pointerMsg = "first mouse device";
1203	}
1204    }
1205
1206    /* 5. Built-in default. */
1207    if (!foundPointer && xf86Info.forceInputDevices) {
1208	memset(&defPtr, 0, sizeof(defPtr));
1209	defPtr.inp_identifier = strdup("<default pointer>");
1210	defPtr.inp_driver = strdup("mouse");
1211	confInput = &defPtr;
1212	foundPointer = TRUE;
1213	from = X_DEFAULT;
1214	pointerMsg = "default mouse configuration";
1215    }
1216
1217    /* Add the core pointer device to the layout, and set it to Core. */
1218    if (foundPointer && confInput) {
1219	foundPointer = configInput(&Pointer, confInput, from);
1220        if (foundPointer) {
1221	    count++;
1222	    devs = xnfrealloc(servlayoutp->inputs,
1223			      (count + 1) * sizeof(InputInfoPtr));
1224            devs[count - 1] = xnfalloc(sizeof(InputInfoRec));
1225	    *devs[count - 1] = Pointer;
1226	    devs[count - 1]->options =
1227				xf86addNewOption(devs[count -1]->options,
1228				    xnfstrdup("CorePointer"), NULL);
1229	    devs[count] = NULL;
1230	    servlayoutp->inputs = devs;
1231	}
1232    }
1233
1234    if (!foundPointer && xf86Info.forceInputDevices) {
1235	/* This shouldn't happen. */
1236	xf86Msg(X_ERROR, "Cannot locate a core pointer device.\n");
1237	return FALSE;
1238    }
1239
1240    /*
1241     * always synthesize a 'mouse' section configured to send core
1242     * events, unless a 'void' section is found, in which case the user
1243     * probably wants to run footless.
1244     *
1245     * If you're using an evdev keyboard and expect a default mouse
1246     * section ... deal.
1247     */
1248    for (devs = servlayoutp->inputs; devs && *devs; devs++) {
1249	const char **driver = mousedrivers;
1250	while(*driver) {
1251	    if (!strcmp((*devs)->driver, *driver)) {
1252		found = 1;
1253		break;
1254	    }
1255	    driver++;
1256	}
1257    }
1258    if (!found && xf86Info.forceInputDevices) {
1259	xf86Msg(X_INFO, "No default mouse found, adding one\n");
1260	memset(&defPtr, 0, sizeof(defPtr));
1261	defPtr.inp_identifier = strdup("<default pointer>");
1262	defPtr.inp_driver = strdup("mouse");
1263	confInput = &defPtr;
1264	foundPointer = configInput(&Pointer, confInput, from);
1265        if (foundPointer) {
1266	    count++;
1267	    devs = xnfrealloc(servlayoutp->inputs,
1268			      (count + 1) * sizeof(InputInfoPtr));
1269            devs[count - 1] = xnfalloc(sizeof(InputInfoRec));
1270	    *devs[count - 1] = Pointer;
1271	    devs[count - 1]->options =
1272				xf86addNewOption(NULL, xnfstrdup("AlwaysCore"), NULL);
1273	    devs[count] = NULL;
1274	    servlayoutp->inputs = devs;
1275	}
1276    }
1277
1278    confInput = NULL;
1279
1280    /* 1. Check for the -keyboard command line option. */
1281    if (xf86KeyboardName) {
1282	confInput = xf86findInput(xf86KeyboardName,
1283				  xf86configptr->conf_input_lst);
1284	if (!confInput) {
1285	    xf86Msg(X_ERROR, "No InputDevice section called \"%s\"\n",
1286		    xf86KeyboardName);
1287	    return FALSE;
1288	}
1289	from = X_CMDLINE;
1290	/*
1291	 * If one was already specified in the ServerLayout, it needs to be
1292	 * removed.
1293	 */
1294	if (coreKeyboard) {
1295	    for (devs = servlayoutp->inputs; devs && *devs; devs++)
1296		if (*devs == coreKeyboard)
1297                {
1298                    free(*devs);
1299                    *devs = (InputInfoPtr)0x1; /* ensure we dont skip next loop */
1300		    break;
1301                }
1302	    for (; devs && *devs; devs++)
1303		devs[0] = devs[1];
1304	    count--;
1305	}
1306	coreKeyboard = NULL;
1307	foundKeyboard = TRUE;
1308    }
1309
1310    /* 2. ServerLayout-specified core keyboard. */
1311    if (coreKeyboard) {
1312	foundKeyboard = TRUE;
1313	from = X_CONFIG;
1314    }
1315
1316    /* 3. First core keyboard device. */
1317    if (!foundKeyboard && (xf86Info.forceInputDevices || implicitLayout)) {
1318	XF86ConfInputPtr p;
1319
1320	for (p = xf86configptr->conf_input_lst; p; p = p->list.next) {
1321	    if (p->inp_option_lst &&
1322		xf86CheckBoolOption(p->inp_option_lst, "CoreKeyboard", FALSE)) {
1323		confInput = p;
1324		foundKeyboard = TRUE;
1325		from = X_DEFAULT;
1326		keyboardMsg = "first core keyboard device";
1327		break;
1328	    }
1329	}
1330    }
1331
1332    /* 4. First keyboard with 'keyboard' or 'kbd' as the driver. */
1333    if (!foundKeyboard && xf86Info.forceInputDevices) {
1334	confInput = xf86findInput(CONF_IMPLICIT_KEYBOARD,
1335				  xf86configptr->conf_input_lst);
1336	if (!confInput) {
1337	    confInput = xf86findInputByDriver("kbd",
1338					      xf86configptr->conf_input_lst);
1339	}
1340	if (confInput) {
1341	    foundKeyboard = TRUE;
1342	    from = X_DEFAULT;
1343	    keyboardMsg = "first keyboard device";
1344	}
1345    }
1346
1347    /* 5. Built-in default. */
1348    if (!foundKeyboard && xf86Info.forceInputDevices) {
1349	memset(&defKbd, 0, sizeof(defKbd));
1350	defKbd.inp_identifier = strdup("<default keyboard>");
1351	defKbd.inp_driver = strdup("kbd");
1352	confInput = &defKbd;
1353	foundKeyboard = TRUE;
1354	keyboardMsg = "default keyboard configuration";
1355	from = X_DEFAULT;
1356    }
1357
1358    /* Add the core keyboard device to the layout, and set it to Core. */
1359    if (foundKeyboard && confInput) {
1360	foundKeyboard = configInput(&Keyboard, confInput, from);
1361        if (foundKeyboard) {
1362	    count++;
1363	    devs = xnfrealloc(servlayoutp->inputs,
1364			      (count + 1) * sizeof(InputInfoPtr));
1365            devs[count - 1] = xnfalloc(sizeof(InputInfoRec));
1366	    *devs[count - 1] = Keyboard;
1367	    devs[count - 1]->options =
1368				xf86addNewOption(devs[count - 1]->options,
1369				    xnfstrdup("CoreKeyboard"), NULL);
1370	    devs[count] = NULL;
1371	    servlayoutp->inputs = devs;
1372	}
1373    }
1374
1375    if (!foundKeyboard && xf86Info.forceInputDevices) {
1376	/* This shouldn't happen. */
1377	xf86Msg(X_ERROR, "Cannot locate a core keyboard device.\n");
1378	return FALSE;
1379    }
1380
1381    if (pointerMsg) {
1382	if (implicitLayout)
1383	    xf86Msg(X_DEFAULT, "No Layout section. Using the %s.\n",
1384	            pointerMsg);
1385	else
1386	    xf86Msg(X_DEFAULT, "The core pointer device wasn't specified "
1387	            "explicitly in the layout.\n"
1388	            "\tUsing the %s.\n", pointerMsg);
1389    }
1390
1391    if (keyboardMsg) {
1392	if (implicitLayout)
1393	    xf86Msg(X_DEFAULT, "No Layout section. Using the %s.\n",
1394	            keyboardMsg);
1395	else
1396	    xf86Msg(X_DEFAULT, "The core keyboard device wasn't specified "
1397	            "explicitly in the layout.\n"
1398	            "\tUsing the %s.\n", keyboardMsg);
1399    }
1400
1401    if (!xf86Info.forceInputDevices && !(foundPointer && foundKeyboard)) {
1402#if defined(CONFIG_HAL) || defined(CONFIG_UDEV)
1403	const char *config_backend;
1404#if defined(CONFIG_HAL)
1405	config_backend = "HAL";
1406#else
1407	config_backend = "udev";
1408#endif
1409	xf86Msg(X_INFO, "The server relies on %s to provide the list of "
1410	                "input devices.\n\tIf no devices become available, "
1411	                "reconfigure %s or disable AutoAddDevices.\n",
1412			config_backend, config_backend);
1413#else
1414	xf86Msg(X_WARNING, "Hotplugging requested but the server was "
1415			   "compiled without a config backend. "
1416			   "No input devices were configured, the server "
1417			   "will start without any input devices.\n");
1418#endif
1419    }
1420
1421    return TRUE;
1422}
1423
1424typedef enum {
1425    LAYOUT_ISOLATEDEVICE,
1426    LAYOUT_SINGLECARD
1427} LayoutValues;
1428
1429static OptionInfoRec LayoutOptions[] = {
1430  { LAYOUT_ISOLATEDEVICE,      "IsolateDevice",        OPTV_STRING,
1431       {0}, FALSE },
1432  { LAYOUT_SINGLECARD,         "SingleCard",           OPTV_BOOLEAN,
1433       {0}, FALSE },
1434  { -1,                                NULL,                   OPTV_NONE,
1435       {0}, FALSE },
1436};
1437
1438static Bool
1439configInputDevices(XF86ConfLayoutPtr layout, serverLayoutPtr servlayoutp)
1440{
1441    XF86ConfInputrefPtr irp;
1442    InputInfoPtr *indp;
1443    int count = 0;
1444
1445    /*
1446     * Count the number of input devices.
1447     */
1448    irp = layout->lay_input_lst;
1449    while (irp) {
1450	count++;
1451	irp = (XF86ConfInputrefPtr)irp->list.next;
1452    }
1453    DebugF("Found %d input devices in the layout section %s\n",
1454	    count, layout->lay_identifier);
1455    indp = xnfcalloc((count + 1), sizeof(InputInfoPtr));
1456    indp[count] = NULL;
1457    irp = layout->lay_input_lst;
1458    count = 0;
1459    while (irp) {
1460	indp[count] = xf86AllocateInput();
1461	if (!configInput(indp[count], irp->iref_inputdev, X_CONFIG)) {
1462	    do {
1463		free(indp[count]);
1464	    } while(count--);
1465	    free(indp);
1466	    return FALSE;
1467	}
1468	indp[count]->options = xf86OptionListMerge(indp[count]->options,
1469						   irp->iref_option_lst);
1470	count++;
1471	irp = (XF86ConfInputrefPtr)irp->list.next;
1472    }
1473    servlayoutp->inputs = indp;
1474
1475    return TRUE;
1476}
1477
1478
1479/*
1480 * figure out which layout is active, which screens are used in that layout,
1481 * which drivers and monitors are used in these screens
1482 */
1483static Bool
1484configLayout(serverLayoutPtr servlayoutp, XF86ConfLayoutPtr conf_layout,
1485	     char *default_layout)
1486{
1487    XF86ConfAdjacencyPtr adjp;
1488    XF86ConfInactivePtr idp;
1489    int saved_count, count = 0;
1490    int scrnum;
1491    XF86ConfLayoutPtr l;
1492    MessageType from;
1493    screenLayoutPtr slp;
1494    GDevPtr gdp;
1495    int i = 0, j;
1496
1497    if (!servlayoutp)
1498	return FALSE;
1499
1500    /*
1501     * which layout section is the active one?
1502     *
1503     * If there is a -layout command line option, use that one, otherwise
1504     * pick the first one.
1505     */
1506    from = X_DEFAULT;
1507    if (xf86LayoutName != NULL)
1508	from = X_CMDLINE;
1509    else if (default_layout) {
1510	xf86LayoutName = default_layout;
1511	from = X_CONFIG;
1512    }
1513    if (xf86LayoutName != NULL) {
1514	if ((l = xf86findLayout(xf86LayoutName, conf_layout)) == NULL) {
1515	    xf86Msg(X_ERROR, "No ServerLayout section called \"%s\"\n",
1516		    xf86LayoutName);
1517	    return FALSE;
1518	}
1519	conf_layout = l;
1520    }
1521    xf86Msg(from, "ServerLayout \"%s\"\n", conf_layout->lay_identifier);
1522    adjp = conf_layout->lay_adjacency_lst;
1523
1524    /*
1525     * we know that each screen is referenced exactly once on the left side
1526     * of a layout statement in the Layout section. So to allocate the right
1527     * size for the array we do a quick walk of the list to figure out how
1528     * many sections we have
1529     */
1530    while (adjp) {
1531        count++;
1532        adjp = (XF86ConfAdjacencyPtr)adjp->list.next;
1533    }
1534
1535    DebugF("Found %d screens in the layout section %s",
1536           count, conf_layout->lay_identifier);
1537    if (!count) /* alloc enough storage even if no screen is specified */
1538        count = 1;
1539
1540    slp = xnfcalloc(1, (count + 1) * sizeof(screenLayoutRec));
1541    slp[count].screen = NULL;
1542    /*
1543     * now that we have storage, loop over the list again and fill in our
1544     * data structure; at this point we do not fill in the adjacency
1545     * information as it is not clear if we need it at all
1546     */
1547    adjp = conf_layout->lay_adjacency_lst;
1548    count = 0;
1549    while (adjp) {
1550        slp[count].screen = xnfcalloc(1, sizeof(confScreenRec));
1551	if (adjp->adj_scrnum < 0)
1552	    scrnum = count;
1553	else
1554	    scrnum = adjp->adj_scrnum;
1555	if (!configScreen(slp[count].screen, adjp->adj_screen, scrnum,
1556			  X_CONFIG)) {
1557	    do {
1558		free(slp[count].screen);
1559	    } while(count--);
1560	    free(slp);
1561	    return FALSE;
1562	}
1563	slp[count].x = adjp->adj_x;
1564	slp[count].y = adjp->adj_y;
1565	slp[count].refname = adjp->adj_refscreen;
1566	switch (adjp->adj_where) {
1567	case CONF_ADJ_OBSOLETE:
1568	    slp[count].where = PosObsolete;
1569	    slp[count].topname = adjp->adj_top_str;
1570	    slp[count].bottomname = adjp->adj_bottom_str;
1571	    slp[count].leftname = adjp->adj_left_str;
1572	    slp[count].rightname = adjp->adj_right_str;
1573	    break;
1574	case CONF_ADJ_ABSOLUTE:
1575	    slp[count].where = PosAbsolute;
1576	    break;
1577	case CONF_ADJ_RIGHTOF:
1578	    slp[count].where = PosRightOf;
1579	    break;
1580	case CONF_ADJ_LEFTOF:
1581	    slp[count].where = PosLeftOf;
1582	    break;
1583	case CONF_ADJ_ABOVE:
1584	    slp[count].where = PosAbove;
1585	    break;
1586	case CONF_ADJ_BELOW:
1587	    slp[count].where = PosBelow;
1588	    break;
1589	case CONF_ADJ_RELATIVE:
1590	    slp[count].where = PosRelative;
1591	    break;
1592	}
1593        count++;
1594        adjp = (XF86ConfAdjacencyPtr)adjp->list.next;
1595    }
1596
1597    /* No screen was specified in the layout. take the first one from the
1598     * config file, or - if it is NULL - configScreen autogenerates one for
1599     * us */
1600    if (!count)
1601    {
1602        slp[0].screen = xnfcalloc(1, sizeof(confScreenRec));
1603	if (!configScreen(slp[0].screen, xf86configptr->conf_screen_lst,
1604                          0, X_CONFIG)) {
1605	    free(slp[0].screen);
1606	    free(slp);
1607	    return FALSE;
1608	}
1609    }
1610
1611    /* XXX Need to tie down the upper left screen. */
1612
1613    /* Fill in the refscreen and top/bottom/left/right values */
1614    for (i = 0; i < count; i++) {
1615	for (j = 0; j < count; j++) {
1616	    if (slp[i].refname &&
1617		strcmp(slp[i].refname, slp[j].screen->id) == 0) {
1618		slp[i].refscreen = slp[j].screen;
1619	    }
1620	    if (slp[i].topname &&
1621		strcmp(slp[i].topname, slp[j].screen->id) == 0) {
1622		slp[i].top = slp[j].screen;
1623	    }
1624	    if (slp[i].bottomname &&
1625		strcmp(slp[i].bottomname, slp[j].screen->id) == 0) {
1626		slp[i].bottom = slp[j].screen;
1627	    }
1628	    if (slp[i].leftname &&
1629		strcmp(slp[i].leftname, slp[j].screen->id) == 0) {
1630		slp[i].left = slp[j].screen;
1631	    }
1632	    if (slp[i].rightname &&
1633		strcmp(slp[i].rightname, slp[j].screen->id) == 0) {
1634		slp[i].right = slp[j].screen;
1635	    }
1636	}
1637	if (slp[i].where != PosObsolete
1638	    && slp[i].where != PosAbsolute
1639	    && !slp[i].refscreen) {
1640	    xf86Msg(X_ERROR,"Screen %s doesn't exist: deleting placement\n",
1641		     slp[i].refname);
1642	    slp[i].where = PosAbsolute;
1643	    slp[i].x = 0;
1644	    slp[i].y = 0;
1645	}
1646    }
1647
1648    if (!count)
1649	saved_count = 1;
1650    else
1651	saved_count = count;
1652    /*
1653     * Count the number of inactive devices.
1654     */
1655    count = 0;
1656    idp = conf_layout->lay_inactive_lst;
1657    while (idp) {
1658        count++;
1659        idp = (XF86ConfInactivePtr)idp->list.next;
1660    }
1661    DebugF("Found %d inactive devices in the layout section %s\n",
1662           count, conf_layout->lay_identifier);
1663    gdp = xnfalloc((count + 1) * sizeof(GDevRec));
1664    gdp[count].identifier = NULL;
1665    idp = conf_layout->lay_inactive_lst;
1666    count = 0;
1667    while (idp) {
1668	if (!configDevice(&gdp[count], idp->inactive_device, FALSE))
1669	    goto bail;
1670        count++;
1671        idp = (XF86ConfInactivePtr)idp->list.next;
1672    }
1673
1674    if (!configInputDevices(conf_layout, servlayoutp))
1675	goto bail;
1676
1677    servlayoutp->id = conf_layout->lay_identifier;
1678    servlayoutp->screens = slp;
1679    servlayoutp->inactives = gdp;
1680    servlayoutp->options = conf_layout->lay_option_lst;
1681    from = X_DEFAULT;
1682
1683    return TRUE;
1684
1685bail:
1686    do {
1687	free(slp[saved_count].screen);
1688    } while(saved_count--);
1689    free(slp);
1690    free(gdp);
1691    return FALSE;
1692}
1693
1694/*
1695 * No layout section, so find the first Screen section and set that up as
1696 * the only active screen.
1697 */
1698static Bool
1699configImpliedLayout(serverLayoutPtr servlayoutp, XF86ConfScreenPtr conf_screen,
1700                    XF86ConfigPtr xf86configptr)
1701{
1702    MessageType from;
1703    XF86ConfScreenPtr s;
1704    screenLayoutPtr slp;
1705    InputInfoPtr *indp;
1706    XF86ConfLayoutRec layout;
1707
1708    if (!servlayoutp)
1709	return FALSE;
1710
1711    /*
1712     * which screen section is the active one?
1713     *
1714     * If there is a -screen option, use that one, otherwise use the first
1715     * one.
1716     */
1717
1718    from = X_CONFIG;
1719    if (xf86ScreenName != NULL) {
1720	if ((s = xf86findScreen(xf86ScreenName, conf_screen)) == NULL) {
1721	    xf86Msg(X_ERROR, "No Screen section called \"%s\"\n",
1722		    xf86ScreenName);
1723	    return FALSE;
1724	}
1725	conf_screen = s;
1726	from = X_CMDLINE;
1727    }
1728
1729    /* We have exactly one screen */
1730
1731    slp = xnfcalloc(1, 2 * sizeof(screenLayoutRec));
1732    slp[0].screen = xnfcalloc(1, sizeof(confScreenRec));
1733    slp[1].screen = NULL;
1734    if (!configScreen(slp[0].screen, conf_screen, 0, from)) {
1735	free(slp);
1736	return FALSE;
1737    }
1738    servlayoutp->id = "(implicit)";
1739    servlayoutp->screens = slp;
1740    servlayoutp->inactives = xnfcalloc(1, sizeof(GDevRec));
1741    servlayoutp->options = NULL;
1742
1743    memset(&layout, 0, sizeof(layout));
1744    layout.lay_identifier = servlayoutp->id;
1745    if (xf86layoutAddInputDevices(xf86configptr, &layout) > 0) {
1746	if (!configInputDevices(&layout, servlayoutp))
1747	    return FALSE;
1748	from = X_DEFAULT;
1749    } else {
1750	/* Set up an empty input device list, then look for some core devices. */
1751	indp = xnfalloc(sizeof(InputInfoPtr));
1752	*indp = NULL;
1753	servlayoutp->inputs = indp;
1754    }
1755
1756    return TRUE;
1757}
1758
1759static Bool
1760configXvAdaptor(confXvAdaptorPtr adaptor, XF86ConfVideoAdaptorPtr conf_adaptor)
1761{
1762    int count = 0;
1763    XF86ConfVideoPortPtr conf_port;
1764
1765    xf86Msg(X_CONFIG, "|   |-->VideoAdaptor \"%s\"\n",
1766	    conf_adaptor->va_identifier);
1767    adaptor->identifier = conf_adaptor->va_identifier;
1768    adaptor->options = conf_adaptor->va_option_lst;
1769    if (conf_adaptor->va_busid || conf_adaptor->va_driver) {
1770	xf86Msg(X_CONFIG, "|   | Unsupported device type, skipping entry\n");
1771	return FALSE;
1772    }
1773
1774    /*
1775     * figure out how many videoport subsections there are and fill them in
1776     */
1777    conf_port = conf_adaptor->va_port_lst;
1778    while(conf_port) {
1779        count++;
1780        conf_port = (XF86ConfVideoPortPtr)conf_port->list.next;
1781    }
1782    adaptor->ports = xnfalloc((count) * sizeof(confXvPortRec));
1783    adaptor->numports = count;
1784    count = 0;
1785    conf_port = conf_adaptor->va_port_lst;
1786    while(conf_port) {
1787	adaptor->ports[count].identifier = conf_port->vp_identifier;
1788	adaptor->ports[count].options = conf_port->vp_option_lst;
1789        count++;
1790        conf_port = (XF86ConfVideoPortPtr)conf_port->list.next;
1791    }
1792
1793    return TRUE;
1794}
1795
1796static Bool
1797configScreen(confScreenPtr screenp, XF86ConfScreenPtr conf_screen, int scrnum,
1798	     MessageType from)
1799{
1800    int count = 0;
1801    XF86ConfDisplayPtr dispptr;
1802    XF86ConfAdaptorLinkPtr conf_adaptor;
1803    Bool defaultMonitor = FALSE;
1804    XF86ConfScreenRec local_conf_screen;
1805
1806    if (!conf_screen) {
1807        memset(&local_conf_screen, 0, sizeof(local_conf_screen));
1808        conf_screen = &local_conf_screen;
1809        conf_screen->scrn_identifier = "Default Screen Section";
1810        xf86Msg(X_DEFAULT, "No screen section available. Using defaults.\n");
1811    }
1812
1813    xf86Msg(from, "|-->Screen \"%s\" (%d)\n", conf_screen->scrn_identifier,
1814	    scrnum);
1815    /*
1816     * now we fill in the elements of the screen
1817     */
1818    screenp->id         = conf_screen->scrn_identifier;
1819    screenp->screennum  = scrnum;
1820    screenp->defaultdepth = conf_screen->scrn_defaultdepth;
1821    screenp->defaultbpp = conf_screen->scrn_defaultbpp;
1822    screenp->defaultfbbpp = conf_screen->scrn_defaultfbbpp;
1823    screenp->monitor    = xnfcalloc(1, sizeof(MonRec));
1824    /* If no monitor is specified, create a default one. */
1825    if (!conf_screen->scrn_monitor) {
1826	XF86ConfMonitorRec defMon;
1827
1828	memset(&defMon, 0, sizeof(defMon));
1829	defMon.mon_identifier = "<default monitor>";
1830	if (!configMonitor(screenp->monitor, &defMon))
1831	    return FALSE;
1832	defaultMonitor = TRUE;
1833    } else {
1834	if (!configMonitor(screenp->monitor,conf_screen->scrn_monitor))
1835	    return FALSE;
1836    }
1837    /* Configure the device. If there isn't one configured, attach to the
1838     * first inactive one that we can configure. If there's none that work,
1839     * set it to NULL so that the section can be autoconfigured later */
1840    screenp->device     = xnfcalloc(1, sizeof(GDevRec));
1841    if ((!conf_screen->scrn_device) && (xf86configptr->conf_device_lst)) {
1842        conf_screen->scrn_device = xf86configptr->conf_device_lst;
1843	xf86Msg(X_DEFAULT, "No device specified for screen \"%s\".\n"
1844		"\tUsing the first device section listed.\n", screenp->id);
1845    }
1846    if (configDevice(screenp->device,conf_screen->scrn_device, TRUE)) {
1847        screenp->device->myScreenSection = screenp;
1848    } else {
1849        screenp->device = NULL;
1850    }
1851    screenp->options = conf_screen->scrn_option_lst;
1852
1853    /*
1854     * figure out how many display subsections there are and fill them in
1855     */
1856    dispptr = conf_screen->scrn_display_lst;
1857    while(dispptr) {
1858        count++;
1859        dispptr = (XF86ConfDisplayPtr)dispptr->list.next;
1860    }
1861    screenp->displays   = xnfalloc((count) * sizeof(DispRec));
1862    screenp->numdisplays = count;
1863
1864    /* Fill in the default Virtual size, if any */
1865    if (conf_screen->scrn_virtualX && conf_screen->scrn_virtualY) {
1866	for (count = 0, dispptr = conf_screen->scrn_display_lst;
1867	     dispptr;
1868	     dispptr = (XF86ConfDisplayPtr)dispptr->list.next, count++) {
1869	    screenp->displays[count].virtualX = conf_screen->scrn_virtualX;
1870	    screenp->displays[count].virtualY = conf_screen->scrn_virtualY;
1871	}
1872    }
1873
1874    /* Now do the per-Display Virtual sizes */
1875    count = 0;
1876    dispptr = conf_screen->scrn_display_lst;
1877    while(dispptr) {
1878        configDisplay(&(screenp->displays[count]),dispptr);
1879        count++;
1880        dispptr = (XF86ConfDisplayPtr)dispptr->list.next;
1881    }
1882
1883    /*
1884     * figure out how many videoadaptor references there are and fill them in
1885     */
1886    conf_adaptor = conf_screen->scrn_adaptor_lst;
1887    while(conf_adaptor) {
1888        count++;
1889        conf_adaptor = (XF86ConfAdaptorLinkPtr)conf_adaptor->list.next;
1890    }
1891    screenp->xvadaptors = xnfalloc((count) * sizeof(confXvAdaptorRec));
1892    screenp->numxvadaptors = 0;
1893    conf_adaptor = conf_screen->scrn_adaptor_lst;
1894    while(conf_adaptor) {
1895        if (configXvAdaptor(&(screenp->xvadaptors[screenp->numxvadaptors]),
1896			    conf_adaptor->al_adaptor))
1897    	    screenp->numxvadaptors++;
1898        conf_adaptor = (XF86ConfAdaptorLinkPtr)conf_adaptor->list.next;
1899    }
1900
1901    if (defaultMonitor) {
1902	xf86Msg(X_DEFAULT, "No monitor specified for screen \"%s\".\n"
1903		"\tUsing a default monitor configuration.\n", screenp->id);
1904    }
1905    return TRUE;
1906}
1907
1908typedef enum {
1909    MON_REDUCEDBLANKING,
1910    MON_MAX_PIX_CLOCK,
1911} MonitorValues;
1912
1913static OptionInfoRec MonitorOptions[] = {
1914  { MON_REDUCEDBLANKING,      "ReducedBlanking",        OPTV_BOOLEAN,
1915       {0}, FALSE },
1916  { MON_MAX_PIX_CLOCK,	      "MaxPixClock",		OPTV_FREQ,
1917       {0}, FALSE },
1918  { -1,                                NULL,                   OPTV_NONE,
1919       {0}, FALSE },
1920};
1921
1922static Bool
1923configMonitor(MonPtr monitorp, XF86ConfMonitorPtr conf_monitor)
1924{
1925    int count;
1926    DisplayModePtr mode,last = NULL;
1927    XF86ConfModeLinePtr cmodep;
1928    XF86ConfModesPtr modes;
1929    XF86ConfModesLinkPtr modeslnk = conf_monitor->mon_modes_sect_lst;
1930    Gamma zeros = {0.0, 0.0, 0.0};
1931    float badgamma = 0.0;
1932    double maxPixClock;
1933
1934    xf86Msg(X_CONFIG, "|   |-->Monitor \"%s\"\n",
1935	    conf_monitor->mon_identifier);
1936    monitorp->id = conf_monitor->mon_identifier;
1937    monitorp->vendor = conf_monitor->mon_vendor;
1938    monitorp->model = conf_monitor->mon_modelname;
1939    monitorp->Modes = NULL;
1940    monitorp->Last = NULL;
1941    monitorp->gamma = zeros;
1942    monitorp->widthmm = conf_monitor->mon_width;
1943    monitorp->heightmm = conf_monitor->mon_height;
1944    monitorp->reducedblanking = FALSE;
1945    monitorp->maxPixClock = 0;
1946    monitorp->options = conf_monitor->mon_option_lst;
1947
1948    /*
1949     * fill in the monitor structure
1950     */
1951    for( count = 0 ;
1952	 count < conf_monitor->mon_n_hsync && count < MAX_HSYNC;
1953	 count++) {
1954        monitorp->hsync[count].hi = conf_monitor->mon_hsync[count].hi;
1955        monitorp->hsync[count].lo = conf_monitor->mon_hsync[count].lo;
1956    }
1957    monitorp->nHsync = count;
1958    for( count = 0 ;
1959	 count < conf_monitor->mon_n_vrefresh && count < MAX_VREFRESH;
1960	 count++) {
1961        monitorp->vrefresh[count].hi = conf_monitor->mon_vrefresh[count].hi;
1962        monitorp->vrefresh[count].lo = conf_monitor->mon_vrefresh[count].lo;
1963    }
1964    monitorp->nVrefresh = count;
1965
1966    /*
1967     * first we collect the mode lines from the UseModes directive
1968     */
1969    while(modeslnk)
1970    {
1971        modes = xf86findModes (modeslnk->ml_modes_str,
1972			       xf86configptr->conf_modes_lst);
1973	modeslnk->ml_modes = modes;
1974
1975
1976	/* now add the modes found in the modes
1977	   section to the list of modes for this
1978	   monitor unless it has been added before
1979	   because we are reusing the same section
1980	   for another screen */
1981	if (xf86itemNotSublist(
1982			       (GenericListPtr)conf_monitor->mon_modeline_lst,
1983			       (GenericListPtr)modes->mon_modeline_lst)) {
1984	    conf_monitor->mon_modeline_lst = (XF86ConfModeLinePtr)
1985	        xf86addListItem(
1986				(GenericListPtr)conf_monitor->mon_modeline_lst,
1987				(GenericListPtr)modes->mon_modeline_lst);
1988	}
1989	modeslnk = modeslnk->list.next;
1990    }
1991
1992    /*
1993     * we need to hook in the mode lines now
1994     * here both data structures use lists, only our internal one
1995     * is double linked
1996     */
1997    cmodep = conf_monitor->mon_modeline_lst;
1998    while( cmodep ) {
1999        mode = xnfcalloc(1, sizeof(DisplayModeRec));
2000	mode->type       = 0;
2001        mode->Clock      = cmodep->ml_clock;
2002        mode->HDisplay   = cmodep->ml_hdisplay;
2003        mode->HSyncStart = cmodep->ml_hsyncstart;
2004        mode->HSyncEnd   = cmodep->ml_hsyncend;
2005        mode->HTotal     = cmodep->ml_htotal;
2006        mode->VDisplay   = cmodep->ml_vdisplay;
2007        mode->VSyncStart = cmodep->ml_vsyncstart;
2008        mode->VSyncEnd   = cmodep->ml_vsyncend;
2009        mode->VTotal     = cmodep->ml_vtotal;
2010        mode->Flags      = cmodep->ml_flags;
2011        mode->HSkew      = cmodep->ml_hskew;
2012        mode->VScan      = cmodep->ml_vscan;
2013        mode->name       = xnfstrdup(cmodep->ml_identifier);
2014        if( last ) {
2015            mode->prev = last;
2016            last->next = mode;
2017        }
2018        else {
2019            /*
2020             * this is the first mode
2021             */
2022            monitorp->Modes = mode;
2023            mode->prev = NULL;
2024        }
2025        last = mode;
2026        cmodep = (XF86ConfModeLinePtr)cmodep->list.next;
2027    }
2028    if(last){
2029      last->next = NULL;
2030    }
2031    monitorp->Last = last;
2032
2033    /* add the (VESA) default modes */
2034    if (! addDefaultModes(monitorp) )
2035	return FALSE;
2036
2037    if (conf_monitor->mon_gamma_red > GAMMA_ZERO)
2038	monitorp->gamma.red = conf_monitor->mon_gamma_red;
2039    if (conf_monitor->mon_gamma_green > GAMMA_ZERO)
2040	monitorp->gamma.green = conf_monitor->mon_gamma_green;
2041    if (conf_monitor->mon_gamma_blue > GAMMA_ZERO)
2042	monitorp->gamma.blue = conf_monitor->mon_gamma_blue;
2043
2044    /* Check that the gamma values are within range */
2045    if (monitorp->gamma.red > GAMMA_ZERO &&
2046	(monitorp->gamma.red < GAMMA_MIN ||
2047	 monitorp->gamma.red > GAMMA_MAX)) {
2048	badgamma = monitorp->gamma.red;
2049    } else if (monitorp->gamma.green > GAMMA_ZERO &&
2050	(monitorp->gamma.green < GAMMA_MIN ||
2051	 monitorp->gamma.green > GAMMA_MAX)) {
2052	badgamma = monitorp->gamma.green;
2053    } else if (monitorp->gamma.blue > GAMMA_ZERO &&
2054	(monitorp->gamma.blue < GAMMA_MIN ||
2055	 monitorp->gamma.blue > GAMMA_MAX)) {
2056	badgamma = monitorp->gamma.blue;
2057    }
2058    if (badgamma > GAMMA_ZERO) {
2059	xf86ConfigError("Gamma value %.f is out of range (%.2f - %.1f)\n",
2060			badgamma, GAMMA_MIN, GAMMA_MAX);
2061	    return FALSE;
2062    }
2063
2064    xf86ProcessOptions(-1, monitorp->options, MonitorOptions);
2065    xf86GetOptValBool(MonitorOptions, MON_REDUCEDBLANKING,
2066                      &monitorp->reducedblanking);
2067    if (xf86GetOptValFreq(MonitorOptions, MON_MAX_PIX_CLOCK, OPTUNITS_KHZ,
2068			  &maxPixClock) == TRUE) {
2069	monitorp->maxPixClock = (int) maxPixClock;
2070    }
2071
2072    return TRUE;
2073}
2074
2075static int
2076lookupVisual(const char *visname)
2077{
2078    int i;
2079
2080    if (!visname || !*visname)
2081	return -1;
2082
2083    for (i = 0; i <= DirectColor; i++) {
2084	if (!xf86nameCompare(visname, xf86VisualNames[i]))
2085	    break;
2086    }
2087
2088    if (i <= DirectColor)
2089	return i;
2090
2091    return -1;
2092}
2093
2094
2095static Bool
2096configDisplay(DispPtr displayp, XF86ConfDisplayPtr conf_display)
2097{
2098    int count = 0;
2099    XF86ModePtr modep;
2100
2101    displayp->frameX0           = conf_display->disp_frameX0;
2102    displayp->frameY0           = conf_display->disp_frameY0;
2103    displayp->virtualX          = conf_display->disp_virtualX;
2104    displayp->virtualY          = conf_display->disp_virtualY;
2105    displayp->depth             = conf_display->disp_depth;
2106    displayp->fbbpp             = conf_display->disp_bpp;
2107    displayp->weight.red        = conf_display->disp_weight.red;
2108    displayp->weight.green      = conf_display->disp_weight.green;
2109    displayp->weight.blue       = conf_display->disp_weight.blue;
2110    displayp->blackColour.red   = conf_display->disp_black.red;
2111    displayp->blackColour.green = conf_display->disp_black.green;
2112    displayp->blackColour.blue  = conf_display->disp_black.blue;
2113    displayp->whiteColour.red   = conf_display->disp_white.red;
2114    displayp->whiteColour.green = conf_display->disp_white.green;
2115    displayp->whiteColour.blue  = conf_display->disp_white.blue;
2116    displayp->options           = conf_display->disp_option_lst;
2117    if (conf_display->disp_visual) {
2118	displayp->defaultVisual = lookupVisual(conf_display->disp_visual);
2119	if (displayp->defaultVisual == -1) {
2120	    xf86ConfigError("Invalid visual name: \"%s\"",
2121			    conf_display->disp_visual);
2122	    return FALSE;
2123	}
2124    } else {
2125	displayp->defaultVisual = -1;
2126    }
2127
2128    /*
2129     * now hook in the modes
2130     */
2131    modep = conf_display->disp_mode_lst;
2132    while(modep) {
2133        count++;
2134        modep = (XF86ModePtr)modep->list.next;
2135    }
2136    displayp->modes = xnfalloc((count+1) * sizeof(char*));
2137    modep = conf_display->disp_mode_lst;
2138    count = 0;
2139    while(modep) {
2140        displayp->modes[count] = modep->mode_name;
2141        count++;
2142        modep = (XF86ModePtr)modep->list.next;
2143    }
2144    displayp->modes[count] = NULL;
2145
2146    return TRUE;
2147}
2148
2149static Bool
2150configDevice(GDevPtr devicep, XF86ConfDevicePtr conf_device, Bool active)
2151{
2152    int i;
2153
2154    if (!conf_device) {
2155        return FALSE;
2156    }
2157
2158    if (active)
2159	xf86Msg(X_CONFIG, "|   |-->Device \"%s\"\n",
2160		conf_device->dev_identifier);
2161    else
2162	xf86Msg(X_CONFIG, "|-->Inactive Device \"%s\"\n",
2163		conf_device->dev_identifier);
2164
2165    devicep->identifier = conf_device->dev_identifier;
2166    devicep->vendor = conf_device->dev_vendor;
2167    devicep->board = conf_device->dev_board;
2168    devicep->chipset = conf_device->dev_chipset;
2169    devicep->ramdac = conf_device->dev_ramdac;
2170    devicep->driver = conf_device->dev_driver;
2171    devicep->active = active;
2172    devicep->videoRam = conf_device->dev_videoram;
2173    devicep->BiosBase = conf_device->dev_bios_base;
2174    devicep->MemBase = conf_device->dev_mem_base;
2175    devicep->IOBase = conf_device->dev_io_base;
2176    devicep->clockchip = conf_device->dev_clockchip;
2177    devicep->busID = conf_device->dev_busid;
2178    devicep->textClockFreq = conf_device->dev_textclockfreq;
2179    devicep->chipID = conf_device->dev_chipid;
2180    devicep->chipRev = conf_device->dev_chiprev;
2181    devicep->options = conf_device->dev_option_lst;
2182    devicep->irq = conf_device->dev_irq;
2183    devicep->screen = conf_device->dev_screen;
2184
2185    for (i = 0; i < MAXDACSPEEDS; i++) {
2186	if (i < CONF_MAXDACSPEEDS)
2187            devicep->dacSpeeds[i] = conf_device->dev_dacSpeeds[i];
2188	else
2189	    devicep->dacSpeeds[i] = 0;
2190    }
2191    devicep->numclocks = conf_device->dev_clocks;
2192    if (devicep->numclocks > MAXCLOCKS)
2193	devicep->numclocks = MAXCLOCKS;
2194    for (i = 0; i < devicep->numclocks; i++) {
2195	devicep->clock[i] = conf_device->dev_clock[i];
2196    }
2197    devicep->claimed = FALSE;
2198
2199    return TRUE;
2200}
2201
2202#ifdef XF86DRI
2203static void
2204configDRI(XF86ConfDRIPtr drip)
2205{
2206    struct group       *grp;
2207
2208    xf86ConfigDRI.group      = -1;
2209    xf86ConfigDRI.mode       = 0;
2210
2211    if (drip) {
2212	if (drip->dri_group_name) {
2213	    if ((grp = getgrnam(drip->dri_group_name)))
2214		xf86ConfigDRI.group = grp->gr_gid;
2215	} else {
2216	    if (drip->dri_group >= 0)
2217		xf86ConfigDRI.group = drip->dri_group;
2218	}
2219	xf86ConfigDRI.mode = drip->dri_mode;
2220    }
2221}
2222#endif
2223
2224static void
2225configExtensions(XF86ConfExtensionsPtr conf_ext)
2226{
2227    XF86OptionPtr o;
2228
2229    if (conf_ext && conf_ext->ext_option_lst) {
2230	for (o = conf_ext->ext_option_lst; o; o = xf86NextOption(o)) {
2231	    char *name   = xf86OptionName(o);
2232	    char *val    = xf86OptionValue(o);
2233	    char *n;
2234	    Bool  enable = TRUE;
2235
2236	    /* Handle "No<ExtensionName>" */
2237	    n = xf86NormalizeName(name);
2238	    if (strncmp(n, "no", 2) == 0) {
2239		name += 2;
2240		enable = FALSE;
2241	    }
2242
2243	    if (!val ||
2244		xf86NameCmp(val, "enable") == 0 ||
2245		xf86NameCmp(val, "enabled") == 0 ||
2246		xf86NameCmp(val, "on") == 0 ||
2247		xf86NameCmp(val, "1") == 0 ||
2248		xf86NameCmp(val, "yes") == 0 ||
2249		xf86NameCmp(val, "true") == 0) {
2250		/* NOTHING NEEDED -- enabling is handled below */
2251	    } else if (xf86NameCmp(val, "disable") == 0 ||
2252                       xf86NameCmp(val, "disabled") == 0 ||
2253		       xf86NameCmp(val, "off") == 0 ||
2254		       xf86NameCmp(val, "0") == 0 ||
2255		       xf86NameCmp(val, "no") == 0 ||
2256		       xf86NameCmp(val, "false") == 0) {
2257		enable = !enable;
2258	    } else {
2259		xf86Msg(X_WARNING, "Ignoring unrecognized value \"%s\"\n", val);
2260		free(n);
2261		continue;
2262	    }
2263
2264	    if (EnableDisableExtension(name, enable)) {
2265		xf86Msg(X_CONFIG, "Extension \"%s\" is %s\n",
2266			name, enable ? "enabled" : "disabled");
2267	    } else {
2268		xf86Msg(X_WARNING, "Ignoring unrecognized extension \"%s\"\n",
2269                        name);
2270	    }
2271	    free(n);
2272	}
2273    }
2274}
2275
2276static Bool
2277configInput(InputInfoPtr inputp, XF86ConfInputPtr conf_input, MessageType from)
2278{
2279    xf86Msg(from, "|-->Input Device \"%s\"\n", conf_input->inp_identifier);
2280    inputp->name = conf_input->inp_identifier;
2281    inputp->driver = conf_input->inp_driver;
2282    inputp->options = conf_input->inp_option_lst;
2283    inputp->attrs = NULL;
2284
2285    return TRUE;
2286}
2287
2288static Bool
2289modeIsPresent(DisplayModePtr mode, MonPtr monitorp)
2290{
2291    DisplayModePtr knownmodes = monitorp->Modes;
2292
2293    /* all I can think of is a linear search... */
2294    while(knownmodes != NULL)
2295    {
2296	if(!strcmp(mode->name, knownmodes->name) &&
2297	   !(knownmodes->type & M_T_DEFAULT))
2298	    return TRUE;
2299	knownmodes = knownmodes->next;
2300    }
2301    return FALSE;
2302}
2303
2304static Bool
2305addDefaultModes(MonPtr monitorp)
2306{
2307    DisplayModePtr mode;
2308    DisplayModePtr last = monitorp->Last;
2309    int i = 0;
2310
2311    for (i = 0; i < xf86NumDefaultModes; i++)
2312    {
2313	mode = xf86DuplicateMode(&xf86DefaultModes[i]);
2314	if (!modeIsPresent(mode, monitorp))
2315	{
2316	    monitorp->Modes = xf86ModesAdd(monitorp->Modes, mode);
2317	    last = mode;
2318	} else {
2319	    free(mode);
2320	}
2321    }
2322    monitorp->Last = last;
2323
2324    return TRUE;
2325}
2326
2327static void
2328checkInput(serverLayoutPtr layout, Bool implicit_layout) {
2329    checkCoreInputDevices(layout, implicit_layout);
2330
2331    /* Unless we're forcing input devices, disable mouse/kbd devices in the
2332     * config. Otherwise the same physical device is added multiple times,
2333     * leading to duplicate events.
2334     */
2335    if (!xf86Info.forceInputDevices && layout->inputs)
2336    {
2337        InputInfoPtr *dev = layout->inputs;
2338        BOOL warned = FALSE;
2339
2340        while(*dev)
2341        {
2342            if (strcmp((*dev)->driver, "kbd") == 0 ||
2343                strcmp((*dev)->driver, "mouse") == 0 ||
2344                strcmp((*dev)->driver, "vmmouse") == 0)
2345            {
2346                InputInfoPtr *current;
2347                if (!warned)
2348                {
2349                    xf86Msg(X_WARNING, "Hotplugging is on, devices using "
2350                            "drivers 'kbd', 'mouse' or 'vmmouse' will be disabled.\n");
2351                    warned = TRUE;
2352                }
2353
2354                xf86Msg(X_WARNING, "Disabling %s\n", (*dev)->name);
2355
2356                current = dev;
2357                free(*dev);
2358
2359                do {
2360                    *current = *(current + 1);
2361                    current++;
2362                } while(*current);
2363            } else
2364                dev++;
2365        }
2366    }
2367}
2368
2369/*
2370 * load the config file and fill the global data structure
2371 */
2372ConfigStatus
2373xf86HandleConfigFile(Bool autoconfig)
2374{
2375    const char *filename, *dirname, *sysdirname;
2376    char *filesearch, *dirsearch;
2377    MessageType filefrom = X_DEFAULT;
2378    MessageType dirfrom = X_DEFAULT;
2379    char *scanptr;
2380    Bool singlecard = 0;
2381    Bool implicit_layout = FALSE;
2382
2383    if (!autoconfig) {
2384	if (getuid() == 0) {
2385	    filesearch = ROOT_CONFIGPATH;
2386	    dirsearch = ROOT_CONFIGDIRPATH;
2387	} else {
2388	    filesearch = USER_CONFIGPATH;
2389	    dirsearch = USER_CONFIGDIRPATH;
2390	}
2391
2392	if (xf86ConfigFile)
2393	    filefrom = X_CMDLINE;
2394	if (xf86ConfigDir)
2395	    dirfrom = X_CMDLINE;
2396
2397	xf86initConfigFiles();
2398	sysdirname = xf86openConfigDirFiles(SYS_CONFIGDIRPATH, NULL,
2399					    PROJECTROOT);
2400	dirname = xf86openConfigDirFiles(dirsearch, xf86ConfigDir, PROJECTROOT);
2401	filename = xf86openConfigFile(filesearch, xf86ConfigFile, PROJECTROOT);
2402	if (filename) {
2403	    xf86MsgVerb(filefrom, 0, "Using config file: \"%s\"\n", filename);
2404	    xf86ConfigFile = xnfstrdup(filename);
2405	} else {
2406	    if (xf86ConfigFile)
2407		xf86Msg(X_ERROR, "Unable to locate/open config file: \"%s\"\n",
2408			xf86ConfigFile);
2409	}
2410	if (dirname) {
2411	    xf86MsgVerb(dirfrom, 0, "Using config directory: \"%s\"\n",
2412			dirname);
2413	    xf86ConfigDir = xnfstrdup(dirname);
2414	} else {
2415	    if (xf86ConfigDir)
2416		xf86Msg(X_ERROR,
2417			"Unable to locate/open config directory: \"%s\"\n",
2418			xf86ConfigDir);
2419	}
2420	if (sysdirname)
2421	    xf86MsgVerb(X_DEFAULT, 0, "Using system config directory \"%s\"\n",
2422			sysdirname);
2423	if (!filename && !dirname && !sysdirname)
2424	    return CONFIG_NOFILE;
2425    }
2426
2427    if ((xf86configptr = xf86readConfigFile ()) == NULL) {
2428	xf86Msg(X_ERROR, "Problem parsing the config file\n");
2429	return CONFIG_PARSE_ERROR;
2430    }
2431    xf86closeConfigFile ();
2432
2433    /* Initialise a few things. */
2434
2435    /*
2436     * now we convert part of the information contained in the parser
2437     * structures into our own structures.
2438     * The important part here is to figure out which Screen Sections
2439     * in the XF86Config file are active so that we can piece together
2440     * the modes that we need later down the road.
2441     * And while we are at it, we'll decode the rest of the stuff as well
2442     */
2443
2444    /* First check if a layout section is present, and if it is valid. */
2445
2446    if (xf86configptr->conf_layout_lst == NULL || xf86ScreenName != NULL) {
2447	if (xf86ScreenName == NULL) {
2448	    xf86Msg(X_DEFAULT,
2449		    "No Layout section.  Using the first Screen section.\n");
2450	}
2451	if (!configImpliedLayout(&xf86ConfigLayout,
2452				 xf86configptr->conf_screen_lst,
2453				 xf86configptr)) {
2454            xf86Msg(X_ERROR, "Unable to determine the screen layout\n");
2455	    return CONFIG_PARSE_ERROR;
2456	}
2457	implicit_layout = TRUE;
2458    } else {
2459	if (xf86configptr->conf_flags != NULL) {
2460	  char *dfltlayout = NULL;
2461 	  pointer optlist = xf86configptr->conf_flags->flg_option_lst;
2462
2463	  if (optlist && xf86FindOption(optlist, "defaultserverlayout"))
2464	    dfltlayout = xf86SetStrOption(optlist, "defaultserverlayout", NULL);
2465	  if (!configLayout(&xf86ConfigLayout, xf86configptr->conf_layout_lst,
2466			  dfltlayout)) {
2467	    xf86Msg(X_ERROR, "Unable to determine the screen layout\n");
2468	    return CONFIG_PARSE_ERROR;
2469	  }
2470	} else {
2471	  if (!configLayout(&xf86ConfigLayout, xf86configptr->conf_layout_lst,
2472			  NULL)) {
2473	    xf86Msg(X_ERROR, "Unable to determine the screen layout\n");
2474	    return CONFIG_PARSE_ERROR;
2475	  }
2476	}
2477    }
2478
2479    xf86ProcessOptions(-1, xf86ConfigLayout.options, LayoutOptions);
2480
2481    if ((scanptr = xf86GetOptValString(LayoutOptions, LAYOUT_ISOLATEDEVICE))) {
2482       ; /* IsolateDevice specified; overrides SingleCard */
2483    } else {
2484       xf86GetOptValBool(LayoutOptions, LAYOUT_SINGLECARD, &singlecard);
2485       if (singlecard)
2486           scanptr = xf86ConfigLayout.screens->screen->device->busID;
2487    }
2488    if (scanptr) {
2489       if (strncmp(scanptr, "PCI:", 4) != 0) {
2490           xf86Msg(X_WARNING, "Bus types other than PCI not yet isolable.\n"
2491                              "\tIgnoring IsolateDevice option.\n");
2492       } else
2493           xf86PciIsolateDevice(scanptr);
2494    }
2495
2496    /* Now process everything else */
2497    if (!configServerFlags(xf86configptr->conf_flags,xf86ConfigLayout.options)){
2498             ErrorF ("Problem when converting the config data structures\n");
2499             return CONFIG_PARSE_ERROR;
2500    }
2501
2502    configFiles(xf86configptr->conf_files);
2503    configExtensions(xf86configptr->conf_extensions);
2504#ifdef XF86DRI
2505    configDRI(xf86configptr->conf_dri);
2506#endif
2507
2508    checkInput(&xf86ConfigLayout, implicit_layout);
2509
2510    /*
2511     * Handle some command line options that can override some of the
2512     * ServerFlags settings.
2513     */
2514#ifdef XF86VIDMODE
2515    if (xf86VidModeDisabled)
2516	xf86Info.vidModeEnabled = FALSE;
2517    if (xf86VidModeAllowNonLocal)
2518	xf86Info.vidModeAllowNonLocal = TRUE;
2519#endif
2520
2521    if (xf86AllowMouseOpenFail)
2522	xf86Info.allowMouseOpenFail = TRUE;
2523
2524    return CONFIG_OK;
2525}
2526
2527Bool
2528xf86PathIsSafe(const char *path)
2529{
2530    return (xf86pathIsSafe(path) != 0);
2531}
2532