XFree86 server 4.x Design (DRAFT) : Config file ``Option'' entries
Previous: Keeping Track of Bus Resources
Next: Modules, Drivers, Include Files and Interface Issues

## 10. Config file ``Option'' entries

Option entries are permitted in most sections and subsections of the config file. There are two forms of option entries:

Option "option-name"

  A boolean option.

Option "option-name" "option-value"

  An option with an arbitrary value.

The option entries are handled by the parser, and a list of the parsed options is included with each of the appropriate data structures that the drivers have access to. The data structures used to hold the option information are opaque to the driver, and a driver must not access the option data directly. Instead, the common layer provides a set of functions that may be used to access, check and manipulate the option data.

First, the low level option handling functions. In most cases drivers would not need to use these directly.

> `pointer xf86FindOption(pointer options, const char *name)`

> > Takes a list of options and an option name, and returns a handle for the first option entry in the list matching the name. Returns `NULL` if no match is found.

> `char *xf86FindOptionValue(pointer options, const char *name)`

> > Takes a list of options and an option name, and returns the value associated with the first option entry in the list matching the name. If the matching option has no value, an empty string (`""`) is returned. Returns `NULL` if no match is found.

> `void xf86MarkOptionUsed(pointer option)`

> > Takes a handle for an option, and marks that option as used.

> `void xf86MarkOptionUsedByName(pointer options, const char *name)`

> > Takes a list of options and an option name and marks the first option entry in the list matching the name as used.

Next, the higher level functions that most drivers would use.

> `void xf86CollectOptions(ScrnInfoPtr pScrn, pointer extraOpts)`

> > Collect the options from each of the config file sections used by the screen (`pScrn`) and return the merged list as `pScrn->options`. This function requires that `pScrn->confScreen`, `pScrn->display`, `pScrn->monitor`, `pScrn->numEntities`, and `pScrn->entityList` are initialised. `extraOpts` may optionally be set to an additional list of options to be combined with the others. The order of precedence for options is `extraOpts`, display, confScreen, monitor, device.

> `void xf86ProcessOptions(int scrnIndex, pointer options,
> OptionInfoPtr optinfo)`

> > Processes a list of options according to the information in the array of `OptionInfoRecs` (`optinfo`). The resulting information is stored in the `value` fields of the appropriate `optinfo` entries. The `found` fields are set to `TRUE` when an option with a value of the correct type if found, and `FALSE` otherwise. The `type` field is used to determine the expected value type for each option. Each option in the list of options for which there is a name match (but not necessarily a value type match) is marked as used. Warning messages are printed when option values don't match the types specified in the optinfo data.

> > NOTE: If this function is called before a driver's screen number is known (e.g., from the `ChipProbe()` function) a `scrnIndex` value of `-1` should be used.

> > NOTE 2: Given that this function stores into the `OptionInfoRecs` pointed to by `optinfo`, the caller should ensure the `OptionInfoRecs` are (re-)initialised before the call, especially if the caller expects to use the predefined option values as defaults.

> > The `OptionInfoRec` is defined as follows:

> >           typedef struct {
> >               double freq;
> >               int units;
> >           } OptFrequency;

> >           typedef union {
> >               unsigned long       num;
> >               char *              str;
> >               double              realnum;
> >               Bool                bool;
> >               OptFrequency        freq;
> >           } ValueUnion;

> >           typedef enum {
> >               OPTV_NONE = 0,
> >               OPTV_INTEGER,
> >               OPTV_STRING,  /* a non-empty string */
> >               OPTV_ANYSTR,  /* Any string, including an empty one */
> >               OPTV_REAL,
> >               OPTV_BOOLEAN,
> >               OPTV_FREQ
> >           } OptionValueType;

> >           typedef enum {
> >               OPTUNITS_HZ = 1,
> >               OPTUNITS_KHZ,
> >               OPTUNITS_MHZ
> >           } OptFreqUnits;

> >           typedef struct {
> >               int                 token;
> >               const char*         name;
> >               OptionValueType     type;
> >               ValueUnion          value;
> >               Bool                found;
> >           } OptionInfoRec, *OptionInfoPtr;

> > `OPTV_FREQ` can be used for options values that are frequencies. These values are a floating point number with an optional unit name appended. The unit name can be one of "Hz", "kHz", "k", "MHz", "M". The multiplier associated with the unit is stored in `freq.units`, and the scaled frequency is stored in `freq.freq`. When no unit is specified, `freq.units` is set to `0`, and `freq.freq` is unscaled.

> > Typical usage is to setup an array of `OptionInfoRecs` with all fields initialised. The `value` and `found` fields get set by `xf86ProcessOptions()`. For cases where the value parsing is more complex, the driver should specify `OPTV_STRING`, and parse the string itself. An example of using this option handling is included in the Sample Driver section.

> `void xf86ShowUnusedOptions(int scrnIndex, pointer options)`

> > Prints out warning messages for each option in the list of options that isn't marked as used. This is intended to show options that the driver hasn't recognised. It would normally be called near the end of the `ChipScreenInit()` function, but only when `serverGeneration == 1`.

> `OptionInfoPtr xf86TokenToOptinfo(const OptionInfoRec *table,
> int token)`

> > Returns a pointer to the `OptionInfoRec` in `table` with a token field matching `token`. Returns `NULL` if no match is found.

> `Bool xf86IsOptionSet(const OptionInfoRec *table, int token)`

> > Returns the `found` field of the `OptionInfoRec` in `table` with a `token` field matching `token`. This can be used for options of all types. Note that for options of type `OPTV_BOOLEAN`, it isn't sufficient to check this to determine the value of the option. Returns `FALSE` if no match is found.

> `char *xf86GetOptValString(const OptionInfoRec *table, int token)`

> > Returns the `value.str` field of the `OptionInfoRec` in `table` with a token field matching `token`. Returns `NULL` if no match is found.

> `Bool xf86GetOptValInteger(const OptionInfoRec *table, int token,
> int *value)`

> > Returns via `*value` the `value.num` field of the `OptionInfoRec` in `table` with a `token` field matching `token`. `*value` is only changed when a match is found so it can be safely initialised with a default prior to calling this function. The function return value is as for `xf86IsOptionSet()`.

> `Bool xf86GetOptValULong(const OptionInfoRec *table, int token,
> unsigned long *value)`

> > Like `xf86GetOptValInteger()`, except the value is treated as an `unsigned long`.

> `Bool xf86GetOptValReal(const OptionInfoRec *table, int token,
> double *value)`

> > Like `xf86GetOptValInteger()`, except that `value.realnum` is used.

> `Bool xf86GetOptValFreq(const OptionInfoRec *table, int token,
> OptFreqUnits expectedUnits, double *value)`

> > Like `xf86GetOptValInteger()`, except that the `value.freq` data is returned. The frequency value is scaled to the units indicated by `expectedUnits`. The scaling is exact when the units were specified explicitly in the option's value. Otherwise, the `expectedUnits` field is used as a hint when doing the scaling. In this case, values larger than `1000` are assumed to have be specified in the next smallest units. For example, if the Option value is "10000" and expectedUnits is `OPTUNITS_MHZ`, the value returned is `10`.

> `Bool xf86GetOptValBool(const OptionInfoRec *table, int token, Bool *value)`

> > This function is used to check boolean options (`OPTV_BOOLEAN`). If the function return value is `FALSE`, it means the option wasn't set. Otherwise `*value` is set to the boolean value indicated by the option's value. No option `value` is interpreted as `TRUE`. Option values meaning `TRUE` are "1", "yes", "on", "true", and option values meaning `FALSE` are "0", "no", "off", "false". Option names both with the "no" prefix in their names, and with that prefix removed are also checked and handled in the obvious way. `*value` is not changed when the option isn't present. It should normally be set to a default value before calling this function.

> `Bool xf86ReturnOptValBool(const OptionInfoRec *table, int token, Bool def)`

> > This function is used to check boolean options (`OPTV_BOOLEAN`). If the option is set, its value is returned. If the options is not set, the default value specified by `def` is returned. The option interpretation is the same as for `xf86GetOptValBool()`.

> `int xf86NameCmp(const char *s1, const char *s2)`

> > This function should be used when comparing strings from the config file with expected values. It works like `strcmp()`, but is not case sensitive and space, tab, and ``_`' characters are ignored in the comparison. The use of this function isn't restricted to parsing option values. It may be used anywhere where this functionality required.

XFree86 server 4.x Design (DRAFT) : Config file ``Option'' entries
Previous: Keeping Track of Bus Resources
Next: Modules, Drivers, Include Files and Interface Issues