3 * Scanner for the configuration file
5 * Copyright (c) 2000-2005, PostgreSQL Global Development Group
7 * $PostgreSQL: pgsql/src/backend/utils/misc/guc-file.l,v 1.31 2005/07/08 18:41:40 tgl Exp $
17 #include "miscadmin.h"
18 #include "storage/fd.h"
19 #include "utils/guc.h"
21 /* Avoid exit() on fatal scanner errors (a bit ugly -- see yy_fatal_error) */
23 #define fprintf(file, fmt, msg) ereport(ERROR, (errmsg_internal("%s", msg)))
25 static unsigned ConfigFileLineno;
33 GUC_UNQUOTED_STRING = 6,
39 /* prototype, so compiler is happy with our high warnings setting */
41 static char *GUC_scanstr(char *);
45 %option never-interactive
55 INTEGER {SIGN}?({DIGIT}+|0x{HEXDIGIT}+)
57 EXPONENT [Ee]{SIGN}?{DIGIT}+
58 REAL {SIGN}?{DIGIT}*"."{DIGIT}*{EXPONENT}?
60 LETTER [A-Za-z_\200-\377]
61 LETTER_OR_DIGIT [A-Za-z_0-9\200-\377]
63 ID {LETTER}{LETTER_OR_DIGIT}*
64 QUALIFIED_ID {ID}"."{ID}
66 UNQUOTED_STRING {LETTER}({LETTER_OR_DIGIT}|[-._:/])*
67 STRING \'([^'\n]|\\.)*\'
71 \n ConfigFileLineno++; return GUC_EOL;
72 [ \t\r]+ /* eat whitespace */
73 #.* /* eat comment (.* matches anything until newline) */
76 {QUALIFIED_ID} return GUC_QUALIFIED_ID;
77 {STRING} return GUC_STRING;
78 {UNQUOTED_STRING} return GUC_UNQUOTED_STRING;
79 {INTEGER} return GUC_INTEGER;
80 {REAL} return GUC_REAL;
88 struct name_value_pair
92 struct name_value_pair *next;
97 * Free a list of name/value pairs, including the names and the values
100 free_name_value_list(struct name_value_pair * list)
102 struct name_value_pair *item;
107 struct name_value_pair *save;
119 * Official function to read and process the configuration file. The
120 * parameter indicates in what context the file is being read --- either
121 * postmaster startup (including standalone-backend startup) or SIGHUP.
122 * All options mentioned in the configuration file are set to new values.
123 * If an error occurs, no values will be changed.
126 ProcessConfigFile(GucContext context)
129 int token, parse_state;
130 char *opt_name, *opt_value;
131 struct name_value_pair *item, *head, *tail;
134 Assert(context == PGC_POSTMASTER || context == PGC_SIGHUP);
136 if (context == PGC_SIGHUP)
139 * To avoid cluttering the log, only the postmaster bleats loudly
140 * about problems with the config file.
142 elevel = IsUnderPostmaster ? DEBUG2 : LOG;
147 fp = AllocateFile(ConfigFileName, "r");
151 (errcode_for_file_access(),
152 errmsg("could not open configuration file \"%s\": %m",
163 opt_name = opt_value = NULL;
164 ConfigFileLineno = 1;
166 while ((token = yylex()))
170 case 0: /* no previous input */
171 if (token == GUC_EOL) /* empty line */
173 if (token != GUC_ID && token != GUC_QUALIFIED_ID)
175 opt_name = pstrdup(yytext);
179 case 1: /* found name */
180 /* ignore equals sign */
181 if (token == GUC_EQUALS)
184 if (token != GUC_ID && token != GUC_STRING &&
185 token != GUC_INTEGER &&
187 token != GUC_UNQUOTED_STRING)
189 opt_value = pstrdup(yytext);
190 if (token == GUC_STRING)
192 /* remove the beginning and ending quote/apostrophe */
193 /* first: shift the whole thing down one character */
194 memmove(opt_value, opt_value+1, strlen(opt_value)-1);
195 /* second: null out the 2 characters we shifted */
196 opt_value[strlen(opt_value)-2] = '\0';
197 /* do the escape thing. pfree()'s the pstrdup above */
198 opt_value = GUC_scanstr(opt_value);
203 case 2: /* now we'd like an end of line */
204 if (token != GUC_EOL)
207 if (strcmp(opt_name, "custom_variable_classes") == 0)
210 * This variable must be processed first as it controls
211 * the validity of other variables; so apply immediately.
213 if (!set_config_option(opt_name, opt_value, context,
214 PGC_S_FILE, false, true))
227 item = palloc(sizeof *item);
228 item->name = opt_name;
229 item->value = opt_value;
246 * Check if all options are valid
248 for(item = head; item; item=item->next)
250 if (!set_config_option(item->name, item->value, context,
251 PGC_S_FILE, false, false))
255 /* If we got here all the options parsed okay, so apply them. */
256 for(item = head; item; item=item->next)
258 set_config_option(item->name, item->value, context,
259 PGC_S_FILE, false, true);
263 free_name_value_list(head);
268 free_name_value_list(head);
269 if (token == GUC_EOL)
271 (errcode(ERRCODE_SYNTAX_ERROR),
272 errmsg("syntax error in file \"%s\" line %u, near end of line",
273 ConfigFileName, ConfigFileLineno - 1)));
276 (errcode(ERRCODE_SYNTAX_ERROR),
277 errmsg("syntax error in file \"%s\" line %u, near token \"%s\"",
278 ConfigFileName, ConfigFileLineno, yytext)));
286 * if the string passed in has escaped codes, map the escape codes to actual
289 * the string returned is palloc'd and should eventually be pfree'd by the
290 * caller; also we assume we should pfree the input string.
302 if (s == NULL || s[0] == '\0')
310 newStr = palloc(len + 1); /* string cannot get longer */
312 for (i = 0, j = 0; i < len; i++)
347 s[i + k] >= '0' && s[i + k] <= '7' && k < 3;
349 octVal = (octVal << 3) + (s[i + k] - '0');
351 newStr[j] = ((char) octVal);