Commit dc62b399 dc62b3998f0fe8ce0f131e269b130831093264fb by Sergey Poznyakoff

Improve configuration file handling.

* include/mailutils/cfg.h (mu_cfg_parse_hints):
Rename site_rcfile to site_file, custom_rcfile to custom_file.
Remove append_tree and data fields.
(MU_PARSE_CONFIG_GLOBAL,MU_CFG_PARSE_PROGRAM): Remove.
(MU_PARSE_CONFIG_VERBOSE): Rename to MU_CF_VERBOSE.
(MU_PARSE_CONFIG_DUMP): Rename to MU_CF_DUMP.
(MU_CFG_FMT_LOCUS): Rename to MU_CF_FMT_LOCUS.
(MU_CFG_FMT_VALUE_ONLY): Rename to MU_CF_FMT_VALUE_ONLY.
(MU_CFG_FMT_PARAM_PATH): Rename to MU_CF_FMT_PARAM_PATH.

(MU_CFG_COMPATIBILITY,MU_CFG_DEPRECATED): Remove.
(mu_parse_config, mu_get_config): Remove deprecated functions.

* libmailutils/cli/cli.c (mu_general_help_text): New global.
(app_data): New struct.
(init_options): Construct configuration option group depending on
which configuration files are in use.
(mu_cli_ext): Don't use per-user configuration files for servers.
Pass pointer to app_data structure as po.po_data
(mu_cli): Set MU_CFHINT_PER_USER_FILE flag by default.

* mail/testsuite/lib/mail.exp: Rewrite invocation of the mu_init command.
* include/mailutils/cli.h (mu_cli_setup) <server>: New field.

* comsat/comsat.c (cli): Mark as server.
(main): Bugfix: pass pointer to server to mu_cli.
* imap4d/imap4d.c (cli): Mark as server.
* pop3d/pop3d.c: Likewise.

* comsat/tests/testsuite.at: Use the --no-site-config
option.
* imap4d/tests/testsuite.at: Likewise.

* libmailutils/cfg/driver.c: Update.
* libmailutils/cfg/format.c: Update.
* libmailutils/cfg/lexer.l: Update.
* libmailutils/cfg/parser.y: Update.
* mu/acl.c: Update.

* pop3d/testsuite/lib/pop3d.exp: Likewise.

* mu/mu.c: Don't read configuration files.
* mu/query.c: Fix args_doc

* testsuite/lib/mailutils.exp (mu_init): Change option handling.
Set --no-config option by default.
1 parent b4c787e6
...@@ -194,11 +194,11 @@ struct mu_cfg_param comsat_cfg_param[] = { ...@@ -194,11 +194,11 @@ struct mu_cfg_param comsat_cfg_param[] = {
194 static char const *alt_args[] = { N_("--test MBOX-URL MSG-QID"), NULL }; 194 static char const *alt_args[] = { N_("--test MBOX-URL MSG-QID"), NULL };
195 195
196 static struct mu_cli_setup cli = { 196 static struct mu_cli_setup cli = {
197 options, 197 .optv = options,
198 comsat_cfg_param, 198 .cfg =comsat_cfg_param,
199 N_("GNU comsatd -- notify users about incoming mail"), 199 .prog_doc = N_("GNU comsatd -- notify users about incoming mail"),
200 "", 200 .prog_alt_args = alt_args,
201 alt_args, 201 .server = 1
202 }; 202 };
203 203
204 static char *capa[] = { 204 static char *capa[] = {
...@@ -568,7 +568,7 @@ main (int argc, char **argv) ...@@ -568,7 +568,7 @@ main (int argc, char **argv)
568 568
569 save_argv = argv; 569 save_argv = argv;
570 570
571 mu_cli (argc, argv, &cli, capa, NULL, &argc, &argv); 571 mu_cli (argc, argv, &cli, capa, server, &argc, &argv);
572 572
573 if (test_mode) 573 if (test_mode)
574 { 574 {
......
...@@ -22,7 +22,7 @@ m4_pushdef([BIFF_MBOX],[`pwd`/mailbox]) ...@@ -22,7 +22,7 @@ m4_pushdef([BIFF_MBOX],[`pwd`/mailbox])
22 22
23 dnl ------------------------------------------------------------ 23 dnl ------------------------------------------------------------
24 dnl comsatcmd 24 dnl comsatcmd
25 m4_pushdef([comsatcmd],[comsatd --no-site --no-user --file ./biff.rc dnl 25 m4_pushdef([comsatcmd],[comsatd --no-site-config --file ./biff.rc dnl
26 --set logging.syslog=no --test]) 26 --set logging.syslog=no --test])
27 27
28 dnl ------------------------------------------------------------ 28 dnl ------------------------------------------------------------
......
...@@ -449,9 +449,10 @@ static struct mu_cfg_param imap4d_cfg_param[] = { ...@@ -449,9 +449,10 @@ static struct mu_cfg_param imap4d_cfg_param[] = {
449 }; 449 };
450 450
451 struct mu_cli_setup cli = { 451 struct mu_cli_setup cli = {
452 options, 452 .optv = options,
453 imap4d_cfg_param, 453 .cfg = imap4d_cfg_param,
454 N_("GNU imap4d -- the IMAP4D daemon.") 454 .prog_doc = N_("GNU imap4d -- the IMAP4D daemon."),
455 .server = 1
455 }; 456 };
456 457
457 int 458 int
...@@ -659,7 +660,7 @@ get_client_address (int fd, struct sockaddr_in *pcs) ...@@ -659,7 +660,7 @@ get_client_address (int fd, struct sockaddr_in *pcs)
659 } 660 }
660 661
661 static int 662 static int
662 set_strerr_flt () 663 set_strerr_flt (void)
663 { 664 {
664 mu_stream_t flt, trans[2]; 665 mu_stream_t flt, trans[2];
665 int rc; 666 int rc;
...@@ -700,7 +701,7 @@ set_strerr_flt () ...@@ -700,7 +701,7 @@ set_strerr_flt ()
700 } 701 }
701 702
702 static void 703 static void
703 clr_strerr_flt () 704 clr_strerr_flt (void)
704 { 705 {
705 mu_stream_t flt, trans[2]; 706 mu_stream_t flt, trans[2];
706 int rc; 707 int rc;
......
...@@ -20,7 +20,6 @@ m4_define([IMAP4D_HOMEDIR]) ...@@ -20,7 +20,6 @@ m4_define([IMAP4D_HOMEDIR])
20 20
21 m4_define([IMAP4D_DEFAULT_OPTIONS],[dnl 21 m4_define([IMAP4D_DEFAULT_OPTIONS],[dnl
22 --no-site-config dnl 22 --no-site-config dnl
23 --no-user-config dnl
24 --test dnl 23 --test dnl
25 --set logging.syslog=0 dnl 24 --set logging.syslog=0 dnl
26 --set logging.severity=notice dnl 25 --set logging.severity=notice dnl
......
...@@ -76,13 +76,39 @@ struct mu_cfg_node ...@@ -76,13 +76,39 @@ struct mu_cfg_node
76 struct mu_cfg_parse_hints 76 struct mu_cfg_parse_hints
77 { 77 {
78 int flags; 78 int flags;
79 char *site_rcfile; 79 char *site_file;
80 char *custom_rcfile; 80 char *custom_file;
81 char *program; 81 char *program;
82 struct mu_cfg_tree *append_tree;
83 void *data;
84 }; 82 };
85 83
84 /* Bit constants for the flags field of struct mu_cfg_parse_hints */
85 /* Parse site-wide configuration file hints.site_file */
86 #define MU_CFHINT_SITE_FILE 0x0001
87 /* Parse custom configuration file hints.custom_file */
88 #define MU_CFHINT_CUSTOM_FILE 0x0002
89 /* The hints.program field is set. The "program PROGNAME" section
90 will be processed, if PROGNAME is the same as hints.program.
91 If include statement is used with the directory name DIR as its
92 argument, the file DIR/PROGNAME will be looked up and read in,
93 if it exists. */
94 #define MU_CFHINT_PROGRAM 0x0004
95
96 /* If MU_CFHINT_PROGRAM is set, look for the file ~/.PROGNAME after parsing
97 site-wide configuration */
98 #define MU_CFHINT_PER_USER_FILE 0x0008
99
100 /* Verbosely log files being processed */
101 #define MU_CF_VERBOSE 0x0010
102 /* Dump the pare tree on stderr */
103 #define MU_CF_DUMP 0x0020
104
105 /* Format location of the statement */
106 #define MU_CF_FMT_LOCUS 0x0100
107 /* Print only value */
108 #define MU_CF_FMT_VALUE_ONLY 0x0200
109 /* Print full parameter path */
110 #define MU_CF_FMT_PARAM_PATH 0x0400
111
86 struct mu_cfg_tree 112 struct mu_cfg_tree
87 { 113 {
88 mu_list_t nodes; /* a list of mu_cfg_node_t */ 114 mu_list_t nodes; /* a list of mu_cfg_node_t */
...@@ -140,9 +166,6 @@ struct mu_cfg_param ...@@ -140,9 +166,6 @@ struct mu_cfg_param
140 const char *argname; 166 const char *argname;
141 }; 167 };
142 168
143 #define MU_TARGET_REF(f) &f, 0
144 #define MU_TARGET_OFF(s,f) NULL, mu_offsetof(s,f)
145
146 enum mu_cfg_section_stage 169 enum mu_cfg_section_stage
147 { 170 {
148 mu_cfg_section_start, 171 mu_cfg_section_start,
...@@ -230,28 +253,6 @@ int mu_config_register_plain_section (const char *parent_path, ...@@ -230,28 +253,6 @@ int mu_config_register_plain_section (const char *parent_path,
230 const char *ident, 253 const char *ident,
231 struct mu_cfg_param *params); 254 struct mu_cfg_param *params);
232 255
233 #define MU_PARSE_CONFIG_GLOBAL 0x001
234 #define MU_PARSE_CONFIG_VERBOSE 0x002
235 #define MU_PARSE_CONFIG_DUMP 0x004
236 #define MU_PARSE_CONFIG_PLAIN 0x008
237 #define MU_CFG_PARSE_SITE_RCFILE 0x010
238 #define MU_CFG_PARSE_CUSTOM_RCFILE 0x020
239 #define MU_CFG_PARSE_PROGRAM 0x040
240 #define MU_CFG_FMT_LOCUS 0x080
241 #define MU_CFG_FMT_VALUE_ONLY 0x100
242 #define MU_CFG_FMT_PARAM_PATH 0x200
243 #define MU_PARSE_CONFIG_LINT 0x400
244 #define MU_CFG_APPEND_TREE 0x800
245
246 #ifdef MU_CFG_COMPATIBILITY
247 # define MU_CFG_DEPRECATED
248 #else
249 # define MU_CFG_DEPRECATED MU_DEPRECATED
250 #endif
251
252 int mu_parse_config (const char *file, const char *progname,
253 struct mu_cfg_param *progparam, int flags,
254 void *target_ptr) MU_CFG_DEPRECATED;
255 256
256 extern int mu_cfg_parser_verbose; 257 extern int mu_cfg_parser_verbose;
257 extern size_t mu_cfg_error_count; 258 extern size_t mu_cfg_error_count;
...@@ -279,10 +280,6 @@ int mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, ...@@ -279,10 +280,6 @@ int mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file,
279 int flags); 280 int flags);
280 281
281 282
282 int mu_get_config (const char *file, const char *progname,
283 struct mu_cfg_param *progparam, int flags,
284 void *target_ptr) MU_CFG_DEPRECATED;
285
286 int mu_cfg_tree_create (struct mu_cfg_tree **ptree); 283 int mu_cfg_tree_create (struct mu_cfg_tree **ptree);
287 mu_cfg_node_t *mu_cfg_tree_create_node (struct mu_cfg_tree *tree, 284 mu_cfg_node_t *mu_cfg_tree_create_node (struct mu_cfg_tree *tree,
288 enum mu_cfg_node_type type, 285 enum mu_cfg_node_type type,
......
...@@ -50,11 +50,14 @@ struct mu_cli_setup ...@@ -50,11 +50,14 @@ struct mu_cli_setup
50 int ex_usage; /* If not 0, exit code on usage errors */ 50 int ex_usage; /* If not 0, exit code on usage errors */
51 int ex_config; /* If not 0, exit code on configuration 51 int ex_config; /* If not 0, exit code on configuration
52 errors */ 52 errors */
53 int inorder; 53 int inorder:1; /* Don't permute options and arguments */
54 int server:1; /* This is a server: don't read per-user
55 configuration files */
54 void (*prog_doc_hook) (mu_stream_t); 56 void (*prog_doc_hook) (mu_stream_t);
55 }; 57 };
56 58
57 extern const char mu_version_copyright[]; 59 extern const char mu_version_copyright[];
60 extern const char mu_general_help_text[];
58 61
59 void mu_version_hook (struct mu_parseopt *po, mu_stream_t stream); 62 void mu_version_hook (struct mu_parseopt *po, mu_stream_t stream);
60 void mu_cli (int argc, char **argv, struct mu_cli_setup *setup, 63 void mu_cli (int argc, char **argv, struct mu_cli_setup *setup,
......
...@@ -27,7 +27,6 @@ ...@@ -27,7 +27,6 @@
27 #include <ctype.h> 27 #include <ctype.h>
28 #include <mailutils/argcv.h> 28 #include <mailutils/argcv.h>
29 #include <mailutils/nls.h> 29 #include <mailutils/nls.h>
30 #define MU_CFG_COMPATIBILITY /* This source uses deprecated cfg interfaces */
31 #include <mailutils/cfg.h> 30 #include <mailutils/cfg.h>
32 #include <mailutils/errno.h> 31 #include <mailutils/errno.h>
33 #include <mailutils/error.h> 32 #include <mailutils/error.h>
...@@ -466,14 +465,14 @@ mu_cfg_tree_reduce (mu_cfg_tree_t *parse_tree, ...@@ -466,14 +465,14 @@ mu_cfg_tree_reduce (mu_cfg_tree_t *parse_tree,
466 struct mu_cfg_cont *cont; 465 struct mu_cfg_cont *cont;
467 if (!parse_tree) 466 if (!parse_tree)
468 return 0; 467 return 0;
469 if (hints && (hints->flags & MU_PARSE_CONFIG_DUMP)) 468 if (hints && (hints->flags & MU_CF_DUMP))
470 { 469 {
471 int yes = 1; 470 int yes = 1;
472 mu_stream_t stream; 471 mu_stream_t stream;
473 472
474 mu_stdio_stream_create (&stream, MU_STDERR_FD, 0); 473 mu_stdio_stream_create (&stream, MU_STDERR_FD, 0);
475 mu_stream_ioctl (stream, MU_IOCTL_FD, MU_IOCTL_FD_SET_BORROW, &yes); 474 mu_stream_ioctl (stream, MU_IOCTL_FD, MU_IOCTL_FD_SET_BORROW, &yes);
476 mu_cfg_format_parse_tree (stream, parse_tree, MU_CFG_FMT_LOCUS); 475 mu_cfg_format_parse_tree (stream, parse_tree, MU_CF_FMT_LOCUS);
477 mu_stream_destroy (&stream); 476 mu_stream_destroy (&stream);
478 } 477 }
479 478
...@@ -492,29 +491,6 @@ mu_format_config_tree (mu_stream_t stream, struct mu_cfg_param *progparam) ...@@ -492,29 +491,6 @@ mu_format_config_tree (mu_stream_t stream, struct mu_cfg_param *progparam)
492 mu_config_destroy_container (&cont); 491 mu_config_destroy_container (&cont);
493 } 492 }
494 493
495 int
496 mu_parse_config (const char *file, const char *progname,
497 struct mu_cfg_param *progparam, int flags,
498 void *target_ptr)
499 {
500 int rc;
501 char *full_name = mu_tilde_expansion (file, MU_HIERARCHY_DELIMITER, NULL);
502 if (full_name)
503 {
504 if (access (full_name, R_OK) == 0)
505 {
506 rc = mu_get_config (full_name, progname, progparam, flags,
507 target_ptr);
508 }
509 else
510 rc = ENOENT;
511 free (full_name);
512 }
513 else
514 rc = ENOMEM;
515 return rc;
516 }
517
518 static const char * 494 static const char *
519 _first_value_ptr (mu_config_value_t *val) 495 _first_value_ptr (mu_config_value_t *val)
520 { 496 {
......
...@@ -152,7 +152,7 @@ format_node (const mu_cfg_node_t *node, void *data) ...@@ -152,7 +152,7 @@ format_node (const mu_cfg_node_t *node, void *data)
152 { 152 {
153 struct tree_print *tp = data; 153 struct tree_print *tp = data;
154 154
155 if ((tp->flags & MU_CFG_FMT_LOCUS) && node->locus.mu_file) 155 if ((tp->flags & MU_CF_FMT_LOCUS) && node->locus.mu_file)
156 mu_stream_printf (tp->stream, "# %lu \"%s\"\n", 156 mu_stream_printf (tp->stream, "# %lu \"%s\"\n",
157 (unsigned long) node->locus.mu_line, 157 (unsigned long) node->locus.mu_line,
158 node->locus.mu_file); 158 node->locus.mu_file);
...@@ -165,7 +165,7 @@ format_node (const mu_cfg_node_t *node, void *data) ...@@ -165,7 +165,7 @@ format_node (const mu_cfg_node_t *node, void *data)
165 break; 165 break;
166 166
167 case mu_cfg_node_statement: 167 case mu_cfg_node_statement:
168 if (tp->flags & MU_CFG_FMT_PARAM_PATH) 168 if (tp->flags & MU_CF_FMT_PARAM_PATH)
169 return MU_CFG_ITER_OK; 169 return MU_CFG_ITER_OK;
170 else 170 else
171 { 171 {
...@@ -181,9 +181,9 @@ format_node (const mu_cfg_node_t *node, void *data) ...@@ -181,9 +181,9 @@ format_node (const mu_cfg_node_t *node, void *data)
181 break; 181 break;
182 182
183 case mu_cfg_node_param: 183 case mu_cfg_node_param:
184 if (tp->flags & MU_CFG_FMT_VALUE_ONLY) 184 if (tp->flags & MU_CF_FMT_VALUE_ONLY)
185 format_value (tp, node->label); 185 format_value (tp, node->label);
186 else if (tp->flags & MU_CFG_FMT_PARAM_PATH) 186 else if (tp->flags & MU_CF_FMT_PARAM_PATH)
187 { 187 {
188 format_path (tp, node, ':'); 188 format_path (tp, node, ':');
189 mu_stream_write (tp->stream, " ", 1, NULL); 189 mu_stream_write (tp->stream, " ", 1, NULL);
...@@ -209,7 +209,7 @@ static int ...@@ -209,7 +209,7 @@ static int
209 format_node_end (const mu_cfg_node_t *node, void *data) 209 format_node_end (const mu_cfg_node_t *node, void *data)
210 { 210 {
211 struct tree_print *tp = data; 211 struct tree_print *tp = data;
212 if (!(tp->flags & MU_CFG_FMT_PARAM_PATH)) 212 if (!(tp->flags & MU_CF_FMT_PARAM_PATH))
213 { 213 {
214 tp->level--; 214 tp->level--;
215 format_level (tp->stream, tp->level); 215 format_level (tp->stream, tp->level);
...@@ -242,7 +242,7 @@ mu_cfg_format_node (mu_stream_t stream, const mu_cfg_node_t *node, int flags) ...@@ -242,7 +242,7 @@ mu_cfg_format_node (mu_stream_t stream, const mu_cfg_node_t *node, int flags)
242 struct tree_print t; 242 struct tree_print t;
243 243
244 if (node->type == mu_cfg_node_statement) 244 if (node->type == mu_cfg_node_statement)
245 flags &= ~MU_CFG_FMT_VALUE_ONLY; 245 flags &= ~MU_CF_FMT_VALUE_ONLY;
246 t.flags = flags; 246 t.flags = flags;
247 t.level = 0; 247 t.level = 0;
248 t.stream = stream; 248 t.stream = stream;
......
...@@ -330,14 +330,14 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags) ...@@ -330,14 +330,14 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags)
330 int rc; 330 int rc;
331 char *full_name = mu_tilde_expansion (file, MU_HIERARCHY_DELIMITER, NULL); 331 char *full_name = mu_tilde_expansion (file, MU_HIERARCHY_DELIMITER, NULL);
332 332
333 if (flags & MU_PARSE_CONFIG_VERBOSE) 333 if (flags & MU_CF_VERBOSE)
334 mu_diag_output (MU_DIAG_INFO, _("opening configuration file %s"), 334 mu_diag_output (MU_DIAG_INFO, _("opening configuration file %s"),
335 full_name); 335 full_name);
336 if (stat (full_name, &st)) 336 if (stat (full_name, &st))
337 { 337 {
338 if (errno != ENOENT) 338 if (errno != ENOENT)
339 mu_error (_("cannot stat `%s': %s"), full_name, mu_strerror (errno)); 339 mu_error (_("cannot stat `%s': %s"), full_name, mu_strerror (errno));
340 else if (flags & MU_PARSE_CONFIG_VERBOSE) 340 else if (flags & MU_CF_VERBOSE)
341 mu_diag_output (MU_DIAG_INFO, _("configuration file %s doesn't exist"), 341 mu_diag_output (MU_DIAG_INFO, _("configuration file %s doesn't exist"),
342 full_name); 342 full_name);
343 free (full_name); 343 free (full_name);
...@@ -345,7 +345,7 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags) ...@@ -345,7 +345,7 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags)
345 } 345 }
346 else if (!S_ISREG (st.st_mode)) 346 else if (!S_ISREG (st.st_mode))
347 { 347 {
348 if (flags & MU_PARSE_CONFIG_VERBOSE) 348 if (flags & MU_CF_VERBOSE)
349 mu_diag_output (MU_DIAG_INFO, _("%s: not a regular file"), full_name); 349 mu_diag_output (MU_DIAG_INFO, _("%s: not a regular file"), full_name);
350 free (full_name); 350 free (full_name);
351 return ENOENT; 351 return ENOENT;
...@@ -360,7 +360,7 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags) ...@@ -360,7 +360,7 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags)
360 return errno; 360 return errno;
361 } 361 }
362 362
363 if (flags & MU_PARSE_CONFIG_VERBOSE) 363 if (flags & MU_CF_VERBOSE)
364 mu_diag_output (MU_DIAG_INFO, _("parsing file `%s'"), full_name); 364 mu_diag_output (MU_DIAG_INFO, _("parsing file `%s'"), full_name);
365 365
366 mu_cfg_set_lex_debug (); 366 mu_cfg_set_lex_debug ();
...@@ -379,37 +379,13 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags) ...@@ -379,37 +379,13 @@ mu_cfg_parse_file (mu_cfg_tree_t **return_tree, const char *file, int flags)
379 yyrestart (fp); 379 yyrestart (fp);
380 rc = mu_cfg_parse (return_tree); 380 rc = mu_cfg_parse (return_tree);
381 fclose (fp); 381 fclose (fp);
382 if (flags & MU_PARSE_CONFIG_VERBOSE) 382 if (flags & MU_CF_VERBOSE)
383 mu_diag_output (MU_DIAG_INFO, _("finished parsing file `%s'"), 383 mu_diag_output (MU_DIAG_INFO, _("finished parsing file `%s'"),
384 mu_cfg_locus.mu_file); 384 mu_cfg_locus.mu_file);
385 385
386 return rc == 0 ? 0 : MU_ERR_FAILURE; 386 return rc == 0 ? 0 : MU_ERR_FAILURE;
387 } 387 }
388 388
389 /* FIXME: Deprecated interface */
390 int
391 mu_get_config (const char *file, const char *progname,
392 struct mu_cfg_param *progparam, int flags, void *target_ptr)
393 {
394 mu_cfg_tree_t *parse_tree;
395 int rc = mu_cfg_parse_file (&parse_tree, file, flags);
396 if (rc == 0)
397 {
398 struct mu_cfg_parse_hints hints;
399
400 hints.flags = flags | MU_CFG_PARSE_PROGRAM;
401 hints.program = (char*)progname;
402
403 rc = mu_cfg_tree_postprocess (parse_tree, &hints);
404 if (rc == 0)
405 rc = mu_cfg_tree_reduce (parse_tree, &hints, progparam, target_ptr);
406 mu_cfg_destroy_tree (&parse_tree);
407 }
408
409 return rc == 0 ? 0 : MU_ERR_FAILURE;
410 }
411
412
413 mu_opool_t 389 mu_opool_t
414 mu_cfg_lexer_pool () 390 mu_cfg_lexer_pool ()
415 { 391 {
......
...@@ -501,8 +501,7 @@ do_include (const char *name, struct mu_cfg_parse_hints *hints, ...@@ -501,8 +501,7 @@ do_include (const char *name, struct mu_cfg_parse_hints *hints,
501 501
502 if (S_ISDIR (sb.st_mode)) 502 if (S_ISDIR (sb.st_mode))
503 { 503 {
504 if ((hints->flags & (MU_PARSE_CONFIG_GLOBAL|MU_CFG_PARSE_PROGRAM)) == 504 if (hints->flags & MU_CFHINT_PROGRAM)
505 (MU_PARSE_CONFIG_GLOBAL|MU_CFG_PARSE_PROGRAM))
506 { 505 {
507 char *file = mu_make_file_name (name, hints->program); 506 char *file = mu_make_file_name (name, hints->program);
508 rc = mu_cfg_parse_file (&tree, file, hints->flags); 507 rc = mu_cfg_parse_file (&tree, file, hints->flags);
...@@ -515,7 +514,7 @@ do_include (const char *name, struct mu_cfg_parse_hints *hints, ...@@ -515,7 +514,7 @@ do_include (const char *name, struct mu_cfg_parse_hints *hints,
515 if (rc == 0 && tree) 514 if (rc == 0 && tree)
516 { 515 {
517 struct mu_cfg_parse_hints xhints = *hints; 516 struct mu_cfg_parse_hints xhints = *hints;
518 xhints.flags &= ~MU_PARSE_CONFIG_GLOBAL; 517 xhints.flags &= ~MU_CFHINT_PROGRAM;
519 mu_cfg_tree_postprocess (tree, &xhints); 518 mu_cfg_tree_postprocess (tree, &xhints);
520 } 519 }
521 } 520 }
...@@ -538,8 +537,7 @@ do_include (const char *name, struct mu_cfg_parse_hints *hints, ...@@ -538,8 +537,7 @@ do_include (const char *name, struct mu_cfg_parse_hints *hints,
538 } 537 }
539 538
540 int 539 int
541 mu_cfg_tree_postprocess (mu_cfg_tree_t *tree, 540 mu_cfg_tree_postprocess (mu_cfg_tree_t *tree, struct mu_cfg_parse_hints *hints)
542 struct mu_cfg_parse_hints *hints)
543 { 541 {
544 int rc; 542 int rc;
545 mu_iterator_t itr; 543 mu_iterator_t itr;
...@@ -558,13 +556,12 @@ mu_cfg_tree_postprocess (mu_cfg_tree_t *tree, ...@@ -558,13 +556,12 @@ mu_cfg_tree_postprocess (mu_cfg_tree_t *tree,
558 556
559 if (node->type == mu_cfg_node_statement) 557 if (node->type == mu_cfg_node_statement)
560 { 558 {
561 if ((hints->flags & MU_PARSE_CONFIG_GLOBAL) && 559 if ((hints->flags & MU_CFHINT_PROGRAM) &&
562 strcmp (node->tag, "program") == 0) 560 strcmp (node->tag, "program") == 0)
563 { 561 {
564 if (node->label->type == MU_CFG_STRING) 562 if (node->label->type == MU_CFG_STRING)
565 { 563 {
566 if ((hints->flags & MU_CFG_PARSE_PROGRAM) 564 if (strcmp (node->label->v.string, hints->program) == 0)
567 && strcmp (node->label->v.string, hints->program) == 0)
568 { 565 {
569 /* Reset the parent node */ 566 /* Reset the parent node */
570 mu_list_foreach (node->nodes, _node_set_parent, 567 mu_list_foreach (node->nodes, _node_set_parent,
...@@ -1527,10 +1524,11 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints) ...@@ -1527,10 +1524,11 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints)
1527 { 1524 {
1528 int rc = 0; 1525 int rc = 0;
1529 mu_cfg_tree_t *tree = NULL, *tmp; 1526 mu_cfg_tree_t *tree = NULL, *tmp;
1527 struct mu_cfg_parse_hints xhints;
1530 1528
1531 if ((hints->flags & MU_CFG_PARSE_SITE_RCFILE) && hints->site_rcfile) 1529 if ((hints->flags & MU_CFHINT_SITE_FILE) && hints->site_file)
1532 { 1530 {
1533 rc = mu_cfg_parse_file (&tmp, hints->site_rcfile, hints->flags); 1531 rc = mu_cfg_parse_file (&tmp, hints->site_file, hints->flags);
1534 1532
1535 if (rc == ENOMEM) 1533 if (rc == ENOMEM)
1536 { 1534 {
...@@ -1539,14 +1537,16 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints) ...@@ -1539,14 +1537,16 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints)
1539 } 1537 }
1540 else if (rc == 0) 1538 else if (rc == 0)
1541 { 1539 {
1542 struct mu_cfg_parse_hints xhints = *hints; 1540 mu_cfg_tree_postprocess (tmp, hints);
1543 xhints.flags |= MU_PARSE_CONFIG_GLOBAL;
1544 mu_cfg_tree_postprocess (tmp, &xhints);
1545 mu_cfg_tree_union (&tree, &tmp); 1541 mu_cfg_tree_union (&tree, &tmp);
1546 } 1542 }
1547 } 1543 }
1548 1544
1549 if ((hints->flags & MU_CFG_PARSE_PROGRAM) && hints->program) 1545 xhints = *hints;
1546 xhints.flags &= ~MU_CFHINT_PROGRAM;
1547
1548 if ((hints->flags & MU_CFHINT_PER_USER_FILE)
1549 && (hints->flags & MU_CFHINT_PROGRAM))
1550 { 1550 {
1551 size_t size = 3 + strlen (hints->program) + 1; 1551 size_t size = 3 + strlen (hints->program) + 1;
1552 char *file_name = malloc (size); 1552 char *file_name = malloc (size);
...@@ -1555,7 +1555,7 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints) ...@@ -1555,7 +1555,7 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints)
1555 strcpy (file_name, "~/."); 1555 strcpy (file_name, "~/.");
1556 strcat (file_name, hints->program); 1556 strcat (file_name, hints->program);
1557 1557
1558 rc = mu_cfg_parse_file (&tmp, file_name, hints->flags); 1558 rc = mu_cfg_parse_file (&tmp, file_name, xhints.flags);
1559 if (rc == ENOMEM) 1559 if (rc == ENOMEM)
1560 { 1560 {
1561 mu_error ("%s", mu_strerror (rc)); 1561 mu_error ("%s", mu_strerror (rc));
...@@ -1564,7 +1564,7 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints) ...@@ -1564,7 +1564,7 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints)
1564 } 1564 }
1565 else if (rc == 0) 1565 else if (rc == 0)
1566 { 1566 {
1567 mu_cfg_tree_postprocess (tmp, hints); 1567 mu_cfg_tree_postprocess (tmp, &xhints);
1568 mu_cfg_tree_union (&tree, &tmp); 1568 mu_cfg_tree_union (&tree, &tmp);
1569 } 1569 }
1570 else if (rc == ENOENT) 1570 else if (rc == ENOENT)
...@@ -1573,26 +1573,23 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints) ...@@ -1573,26 +1573,23 @@ mu_cfg_parse_config (mu_cfg_tree_t **ptree, struct mu_cfg_parse_hints *hints)
1573 } 1573 }
1574 } 1574 }
1575 1575
1576 if ((hints->flags & MU_CFG_PARSE_CUSTOM_RCFILE) && hints->custom_rcfile) 1576 if ((hints->flags & MU_CFHINT_CUSTOM_FILE) && hints->custom_file)
1577 { 1577 {
1578 rc = mu_cfg_parse_file (&tmp, hints->custom_rcfile, hints->flags); 1578 rc = mu_cfg_parse_file (&tmp, hints->custom_file, xhints.flags);
1579 if (rc) 1579 if (rc)
1580 { 1580 {
1581 mu_error (_("errors parsing file %s: %s"), hints->custom_rcfile, 1581 mu_error (_("errors parsing file %s: %s"), hints->custom_file,
1582 mu_strerror (rc)); 1582 mu_strerror (rc));
1583 mu_cfg_destroy_tree (&tree); 1583 mu_cfg_destroy_tree (&tree);
1584 return rc; 1584 return rc;
1585 } 1585 }
1586 else 1586 else
1587 { 1587 {
1588 mu_cfg_tree_postprocess (tmp, hints); 1588 mu_cfg_tree_postprocess (tmp, &xhints);
1589 mu_cfg_tree_union (&tree, &tmp); 1589 mu_cfg_tree_union (&tree, &tmp);
1590 } 1590 }
1591 } 1591 }
1592 1592
1593 if (hints->flags & MU_CFG_APPEND_TREE)
1594 mu_cfg_tree_union (&tree, &hints->append_tree);
1595
1596 *ptree = tree; 1593 *ptree = tree;
1597 return rc; 1594 return rc;
1598 } 1595 }
......
...@@ -18,7 +18,7 @@ ...@@ -18,7 +18,7 @@
18 18
19 source $top_srcdir/testsuite/lib/mailutils.exp 19 source $top_srcdir/testsuite/lib/mailutils.exp
20 20
21 mu_init "--nosum --norc" 21 mu_init --nosum --norc
22 22
23 #FIXME: this doesn't work with remote testing 23 #FIXME: this doesn't work with remote testing
24 set env(MAILRC) $MU_RC_DIR/mail.rc 24 set env(MAILRC) $MU_RC_DIR/mail.rc
......
...@@ -58,8 +58,8 @@ mutool_acl (int argc, char **argv) ...@@ -58,8 +58,8 @@ mutool_acl (int argc, char **argv)
58 } 58 }
59 59
60 memset (&hints, 0, sizeof (hints)); 60 memset (&hints, 0, sizeof (hints));
61 hints.flags = MU_CFG_PARSE_CUSTOM_RCFILE; 61 hints.flags = MU_CFHINT_CUSTOM_FILE;
62 hints.custom_rcfile = input_file_name; 62 hints.custom_file = input_file_name;
63 63
64 mu_acl_cfg_init (); 64 mu_acl_cfg_init ();
65 if (mu_cfg_parse_config (&tree, &hints)) 65 if (mu_cfg_parse_config (&tree, &hints))
......
...@@ -43,6 +43,19 @@ int ...@@ -43,6 +43,19 @@ int
43 main (int argc, char **argv) 43 main (int argc, char **argv)
44 { 44 {
45 mutool_action_t action; 45 mutool_action_t action;
46 static struct mu_parseopt pohint = {
47 .po_flags = MU_PARSEOPT_PACKAGE_NAME
48 | MU_PARSEOPT_PACKAGE_URL
49 | MU_PARSEOPT_BUG_ADDRESS
50 | MU_PARSEOPT_EXTRA_INFO
51 | MU_PARSEOPT_VERSION_HOOK,
52 .po_package_name = PACKAGE_NAME,
53 .po_package_url = PACKAGE_URL,
54 .po_bug_address = PACKAGE_BUGREPORT,
55 .po_extra_info = mu_general_help_text,
56 .po_version_hook = mu_version_hook,
57 };
58 struct mu_cfg_parse_hints cfhint = { .flags = 0 };
46 59
47 /* Native Language Support */ 60 /* Native Language Support */
48 MU_APP_INIT_NLS (); 61 MU_APP_INIT_NLS ();
...@@ -51,7 +64,7 @@ main (int argc, char **argv) ...@@ -51,7 +64,7 @@ main (int argc, char **argv)
51 /* Register the desired mailbox formats. */ 64 /* Register the desired mailbox formats. */
52 mu_register_all_mbox_formats (); 65 mu_register_all_mbox_formats ();
53 66
54 mu_cli (argc, argv, &cli, capa, NULL, &argc, &argv); 67 mu_cli_ext (argc, argv, &cli, &pohint, &cfhint, capa, NULL, &argc, &argv);
55 68
56 if (argc < 1) 69 if (argc < 1)
57 { 70 {
......
...@@ -17,7 +17,7 @@ ...@@ -17,7 +17,7 @@
17 #include "mu.h" 17 #include "mu.h"
18 18
19 char query_docstring[] = N_("query configuration values"); 19 char query_docstring[] = N_("query configuration values");
20 static char query_args_doc[] = N_("path [path...]"); 20 static char query_args_doc[] = N_("PATH [PATH...]");
21 21
22 static char *file_name; 22 static char *file_name;
23 int value_option; 23 int value_option;
...@@ -59,21 +59,21 @@ mutool_query (int argc, char **argv) ...@@ -59,21 +59,21 @@ mutool_query (int argc, char **argv)
59 return 1; 59 return 1;
60 } 60 }
61 61
62 hints.flags = MU_CFG_PARSE_SITE_RCFILE | MU_PARSE_CONFIG_GLOBAL; 62 hints.flags = MU_CFHINT_SITE_FILE;
63 hints.site_rcfile = file_name ? file_name : mu_site_config_file (); 63 hints.site_file = file_name ? file_name : mu_site_config_file ();
64 64
65 if (progname) 65 if (progname)
66 { 66 {
67 hints.flags |= MU_CFG_PARSE_PROGRAM; 67 hints.flags |= MU_CFHINT_PROGRAM;
68 hints.program = progname; 68 hints.program = progname;
69 } 69 }
70 70
71 if (verbose_option) 71 if (verbose_option)
72 hints.flags |= MU_CFG_FMT_LOCUS; 72 hints.flags |= MU_CF_FMT_LOCUS;
73 if (value_option) 73 if (value_option)
74 hints.flags |= MU_CFG_FMT_VALUE_ONLY; 74 hints.flags |= MU_CF_FMT_VALUE_ONLY;
75 if (path_option) 75 if (path_option)
76 hints.flags |= MU_CFG_FMT_PARAM_PATH; 76 hints.flags |= MU_CF_FMT_PARAM_PATH;
77 77
78 if (mu_cfg_parse_config (&tree, &hints)) 78 if (mu_cfg_parse_config (&tree, &hints))
79 return 1; 79 return 1;
......
...@@ -317,9 +317,10 @@ static char *capa[] = { ...@@ -317,9 +317,10 @@ static char *capa[] = {
317 }; 317 };
318 318
319 struct mu_cli_setup cli = { 319 struct mu_cli_setup cli = {
320 options, 320 .optv = options,
321 pop3d_cfg_param, 321 .cfg = pop3d_cfg_param,
322 N_("GNU pop3d -- the POP3 daemon."), 322 .prog_doc = N_("GNU pop3d -- the POP3 daemon."),
323 .server = 1
323 }; 324 };
324 325
325 int 326 int
......
...@@ -18,8 +18,7 @@ ...@@ -18,8 +18,7 @@
18 18
19 source $top_srcdir/testsuite/lib/mailutils.exp 19 source $top_srcdir/testsuite/lib/mailutils.exp
20 20
21 21 mu_init "--config-file=$objdir/pop3d.rc"
22 mu_init "--rcfile=$objdir/pop3d.rc"
23 mu_version 22 mu_version
24 if ![mu_check_capability ENABLE_VIRTUAL_DOMAINS] { 23 if ![mu_check_capability ENABLE_VIRTUAL_DOMAINS] {
25 clone_output "WARNING: Support for virtual domains not compiled in" 24 clone_output "WARNING: Support for virtual domains not compiled in"
......
...@@ -148,14 +148,25 @@ proc mu_init {args} { ...@@ -148,14 +148,25 @@ proc mu_init {args} {
148 set MU_SPOOL_DIR "$MU_DATA_DIR/spool" 148 set MU_SPOOL_DIR "$MU_DATA_DIR/spool"
149 set MU_FOLDER_DIR "$MU_DATA_DIR/folder" 149 set MU_FOLDER_DIR "$MU_DATA_DIR/folder"
150 150
151 if {[llength $args] == 1 && [lindex $args 0] == "-noflags"} { 151 lappend flags "--no-config" "--set mailbox.mail-spool=\"'$MU_SPOOL_DIR'\""
152 set MU_TOOL_FLAGS "--no-site-rcfile --no-user-rcfile" 152 set i 0
153 } else { 153 for {} {$i < [llength $args]} {incr i} {
154 set MU_TOOL_FLAGS "--set mailbox.mail-spool=\"'$MU_SPOOL_DIR'\" --no-site-rcfile --no-user-rcfile" 154 switch -- [lindex $args $i] {
155 for {set i 0} {$i < [llength $args]} {incr i} { 155 -noflags {
156 append MU_TOOL_FLAGS " [lindex $args $i]" 156 unset flags
157 }
158 -- {
159 incr i
160 break
161 }
162 default {
163
164 break
165 }
157 } 166 }
158 } 167 }
168 lappend flags {*}[lrange $args $i end]
169 set MU_TOOL_FLAGS [join $flags { }]
159 } 170 }
160 } 171 }
161 172
......