Added ~/.<progname>rc to be last config file.
Fixed segv for NULL capa and added header file blurb.
Showing
2 changed files
with
75 additions
and
27 deletions
... | @@ -362,7 +362,7 @@ mu_daemon_argp_parser (int key, char *arg, struct argp_state *state) | ... | @@ -362,7 +362,7 @@ mu_daemon_argp_parser (int key, char *arg, struct argp_state *state) |
362 | #endif | 362 | #endif |
363 | 363 | ||
364 | #ifndef MU_USER_CONFIG_FILE | 364 | #ifndef MU_USER_CONFIG_FILE |
365 | # define MU_USER_CONFIG_FILE ".mailutils" | 365 | # define MU_USER_CONFIG_FILE "~/.mailutils" |
366 | #endif | 366 | #endif |
367 | 367 | ||
368 | static int | 368 | static int |
... | @@ -375,6 +375,12 @@ member (const char *array[], const char *text, size_t len) | ... | @@ -375,6 +375,12 @@ member (const char *array[], const char *text, size_t len) |
375 | return 0; | 375 | return 0; |
376 | } | 376 | } |
377 | 377 | ||
378 | /* | ||
379 | Appends applicable options found in file NAME to argv. If progname | ||
380 | is NULL, all the options found are assumed to apply. Otherwise they | ||
381 | apply only if the line starts with ":something", and something is | ||
382 | found in the CAPA array, or the line starts with PROGNAME. | ||
383 | */ | ||
378 | void | 384 | void |
379 | read_rc (const char *progname, const char *name, const char *capa[], | 385 | read_rc (const char *progname, const char *name, const char *capa[], |
380 | int *argc, char ***argv) | 386 | int *argc, char ***argv) |
... | @@ -385,10 +391,20 @@ read_rc (const char *progname, const char *name, const char *capa[], | ... | @@ -385,10 +391,20 @@ read_rc (const char *progname, const char *name, const char *capa[], |
385 | size_t n = 0; | 391 | size_t n = 0; |
386 | int x_argc = *argc; | 392 | int x_argc = *argc; |
387 | char **x_argv = *argv; | 393 | char **x_argv = *argv; |
394 | char* rcfile = mu_tilde_expansion (name, "/", NULL); | ||
388 | 395 | ||
389 | fp = fopen (name, "r"); | 396 | if (!rcfile) |
397 | { | ||
398 | fprintf (stderr, "%s: not enough memory\n", progname); | ||
399 | exit (1); | ||
400 | } | ||
401 | |||
402 | fp = fopen (rcfile, "r"); | ||
390 | if (!fp) | 403 | if (!fp) |
404 | { | ||
405 | free(rcfile); | ||
391 | return; | 406 | return; |
407 | } | ||
392 | 408 | ||
393 | while (getline (&buf, &n, fp) > 0) | 409 | while (getline (&buf, &n, fp) > 0) |
394 | { | 410 | { |
... | @@ -435,12 +451,19 @@ read_rc (const char *progname, const char *name, const char *capa[], | ... | @@ -435,12 +451,19 @@ read_rc (const char *progname, const char *name, const char *capa[], |
435 | } | 451 | } |
436 | 452 | ||
437 | len = 0; | 453 | len = 0; |
454 | if(progname) | ||
455 | { | ||
438 | for (p = kwp; *p && !isspace (*p); p++) | 456 | for (p = kwp; *p && !isspace (*p); p++) |
439 | len++; | 457 | len++; |
440 | 458 | } | |
441 | if ((kwp[0] == ':' | 459 | else |
442 | && member (capa, kwp+1, len-1)) | 460 | p = kwp; /* Use the whole line. */ |
443 | || strncmp (progname, kwp, len) == 0) | 461 | |
462 | if ( | ||
463 | progname == NULL | ||
464 | || (kwp[0] == ':' && member (capa, kwp+1, len-1)) | ||
465 | || strncmp (progname, kwp, len) == 0 | ||
466 | ) | ||
444 | { | 467 | { |
445 | int i, n_argc = 0; | 468 | int i, n_argc = 0; |
446 | char **n_argv; | 469 | char **n_argv; |
... | @@ -471,6 +494,7 @@ read_rc (const char *progname, const char *name, const char *capa[], | ... | @@ -471,6 +494,7 @@ read_rc (const char *progname, const char *name, const char *capa[], |
471 | } | 494 | } |
472 | } | 495 | } |
473 | fclose (fp); | 496 | fclose (fp); |
497 | free(rcfile); | ||
474 | 498 | ||
475 | *argc = x_argc; | 499 | *argc = x_argc; |
476 | *argv = x_argv; | 500 | *argv = x_argv; |
... | @@ -485,8 +509,7 @@ mu_create_argcv (const char *capa[], | ... | @@ -485,8 +509,7 @@ mu_create_argcv (const char *capa[], |
485 | int x_argc; | 509 | int x_argc; |
486 | char **x_argv; | 510 | char **x_argv; |
487 | int i; | 511 | int i; |
488 | struct passwd *pw; | 512 | |
489 | |||
490 | progname = strrchr (argv[0], '/'); | 513 | progname = strrchr (argv[0], '/'); |
491 | if (progname) | 514 | if (progname) |
492 | progname++; | 515 | progname++; |
... | @@ -505,28 +528,30 @@ mu_create_argcv (const char *capa[], | ... | @@ -505,28 +528,30 @@ mu_create_argcv (const char *capa[], |
505 | x_argv[x_argc] = argv[x_argc]; | 528 | x_argv[x_argc] = argv[x_argc]; |
506 | x_argc++; | 529 | x_argc++; |
507 | 530 | ||
531 | /* Add global config file. */ | ||
508 | read_rc (progname, MU_CONFIG_FILE, capa, &x_argc, &x_argv); | 532 | read_rc (progname, MU_CONFIG_FILE, capa, &x_argc, &x_argv); |
509 | pw = getpwuid (getuid ()); | ||
510 | if (pw) | ||
511 | { | ||
512 | struct stat sb; | ||
513 | 533 | ||
514 | if (stat (pw->pw_dir, &sb) == 0 && S_ISDIR (sb.st_mode)) | 534 | /* Add per-user config file. */ |
515 | { | 535 | read_rc (progname, MU_USER_CONFIG_FILE, capa, &x_argc, &x_argv); |
516 | /* note: sizeof return value counts terminating zero */ | 536 | |
517 | char *name = xmalloc (strlen (pw->pw_dir) + 1 | 537 | /* Add per-program (and per-user) config file. */ |
518 | + sizeof (MU_USER_CONFIG_FILE)); | 538 | { |
519 | sprintf (name, "%s/%s", pw->pw_dir, MU_USER_CONFIG_FILE); | 539 | char* progrc = malloc (strlen (progname) + 3 /* ~/ */ + 3 /* rc */ + 1); |
520 | read_rc (progname, name, capa, &x_argc, &x_argv); | 540 | if (!progrc) |
521 | free (name); | 541 | { |
522 | } | 542 | fprintf (stderr, "%s: not enough memory\n", progname); |
523 | } | 543 | exit (1); |
544 | } | ||
545 | sprintf (progrc, "~/.%src", progname); | ||
546 | read_rc (NULL, progrc, capa, &x_argc, &x_argv); | ||
547 | free (progrc); | ||
548 | } | ||
524 | 549 | ||
525 | /* Finally, add the command line options */ | 550 | /* Finally, add the command line options */ |
526 | x_argv = realloc (x_argv, (x_argc + argc) * sizeof (x_argv[0])); | 551 | x_argv = realloc (x_argv, (x_argc + argc) * sizeof (x_argv[0])); |
527 | for (i = 1; i < argc; i++) | 552 | for (i = 1; i < argc; i++) |
528 | x_argv[x_argc++] = argv[i]; | 553 | x_argv[x_argc++] = argv[i]; |
529 | 554 | ||
530 | x_argv[x_argc] = NULL; | 555 | x_argv[x_argc] = NULL; |
531 | 556 | ||
532 | *p_argc = x_argc; | 557 | *p_argc = x_argc; |
... | @@ -562,9 +587,9 @@ mu_build_argp (const struct argp *template, const char *capa[]) | ... | @@ -562,9 +587,9 @@ mu_build_argp (const struct argp *template, const char *capa[]) |
562 | struct argp *argp; | 587 | struct argp *argp; |
563 | 588 | ||
564 | /* Count the capabilities */ | 589 | /* Count the capabilities */ |
565 | for (n = 0; capa[n]; n++) | 590 | for (n = 0; capa && capa[n]; n++) |
566 | ; | 591 | ; |
567 | if (template->children) | 592 | if (template && template->children) |
568 | for (; template->children[n].argp; n++) | 593 | for (; template->children[n].argp; n++) |
569 | ; | 594 | ; |
570 | 595 | ||
... | @@ -576,11 +601,11 @@ mu_build_argp (const struct argp *template, const char *capa[]) | ... | @@ -576,11 +601,11 @@ mu_build_argp (const struct argp *template, const char *capa[]) |
576 | } | 601 | } |
577 | 602 | ||
578 | n = 0; | 603 | n = 0; |
579 | if (template->children) | 604 | if (template && template->children) |
580 | for (; template->children[n].argp; n++) | 605 | for (; template->children[n].argp; n++) |
581 | ap[n] = template->children[n]; | 606 | ap[n] = template->children[n]; |
582 | 607 | ||
583 | for (; capa[n]; n++) | 608 | for (; capa && capa[n]; n++) |
584 | { | 609 | { |
585 | struct argp_child *tmp = find_argp_child (capa[n]); | 610 | struct argp_child *tmp = find_argp_child (capa[n]); |
586 | if (!tmp) | 611 | if (!tmp) |
... | @@ -621,3 +646,4 @@ mu_argp_parse(const struct argp *argp, | ... | @@ -621,3 +646,4 @@ mu_argp_parse(const struct argp *argp, |
621 | free ((void*) argp); | 646 | free ((void*) argp); |
622 | return ret; | 647 | return ret; |
623 | } | 648 | } |
649 | ... | ... |
1 | /* GNU mailutils - a suite of utilities for electronic mail | ||
2 | Copyright (C) 1999, 2000, 2001 Free Software Foundation, Inc. | ||
3 | |||
4 | This program is free software; you can redistribute it and/or modify | ||
5 | it under the terms of the GNU General Public License as published by | ||
6 | the Free Software Foundation; either version 2, or (at your option) | ||
7 | any later version. | ||
8 | |||
9 | This program is distributed in the hope that it will be useful, | ||
10 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | GNU General Public License for more details. | ||
13 | |||
14 | You should have received a copy of the GNU General Public License | ||
15 | along with this program; if not, write to the Free Software | ||
16 | Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ | ||
17 | |||
18 | #ifndef MU_ARGP_H | ||
19 | #define MU_ARGP_H 1 | ||
20 | |||
1 | #include <mailutils/mailbox.h> | 21 | #include <mailutils/mailbox.h> |
2 | #include <argp.h> | 22 | #include <argp.h> |
3 | 23 | ||
... | @@ -27,3 +47,5 @@ extern error_t mu_argp_parse __P((const struct argp *argp, | ... | @@ -27,3 +47,5 @@ extern error_t mu_argp_parse __P((const struct argp *argp, |
27 | int *arg_index, | 47 | int *arg_index, |
28 | void *input)); | 48 | void *input)); |
29 | 49 | ||
50 | #endif | ||
51 | ... | ... |
-
Please register or sign in to post a comment