2 * Copyright (c) 1997-2004 Erez Zadok
3 * Copyright (c) 1990 Jan-Simon Pendry
4 * Copyright (c) 1990 Imperial College of Science, Technology & Medicine
5 * Copyright (c) 1990 The Regents of the University of California.
8 * This code is derived from software contributed to Berkeley by
9 * Jan-Simon Pendry at Imperial College, London.
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright
17 * notice, this list of conditions and the following disclaimer in the
18 * documentation and/or other materials provided with the distribution.
19 * 3. All advertising materials mentioning features or use of this software
20 * must display the following acknowledgment:
21 * This product includes software developed by the University of
22 * California, Berkeley and its contributors.
23 * 4. Neither the name of the University nor the names of its contributors
24 * may be used to endorse or promote products derived from this software
25 * without specific prior written permission.
27 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
28 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
29 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
30 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
31 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
32 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
33 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
34 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
35 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
36 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
41 * $Id: conf.c,v 1.7.2.8 2004/01/21 04:04:58 ib42 Exp $
46 * Functions to handle the configuration file.
51 #endif /* HAVE_CONFIG_H */
59 /* Turn on to show some info about maps being configured */
60 /* #define DEBUG_CONF */
65 typedef int (*OptFuncPtr)(const char *);
76 * FORWARD DECLARATIONS:
78 static int gopt_arch(const char *val);
79 static int gopt_auto_dir(const char *val);
80 static int gopt_browsable_dirs(const char *val);
81 static int gopt_cache_duration(const char *val);
82 static int gopt_cluster(const char *val);
83 static int gopt_debug_options(const char *val);
84 static int gopt_dismount_interval(const char *val);
85 static int gopt_full_os(const char *val);
86 static int gopt_fully_qualified_hosts(const char *val);
87 static int gopt_hesiod_base(const char *val);
88 static int gopt_karch(const char *val);
89 static int gopt_ldap_base(const char *val);
90 static int gopt_ldap_cache_maxmem(const char *val);
91 static int gopt_ldap_cache_seconds(const char *val);
92 static int gopt_ldap_hostports(const char *val);
93 static int gopt_local_domain(const char *val);
94 static int gopt_log_file(const char *val);
95 static int gopt_log_options(const char *val);
96 static int gopt_map_options(const char *val);
97 static int gopt_map_type(const char *val);
98 static int gopt_mount_type(const char *val);
99 static int gopt_pid_file(const char *val);
100 static int gopt_portmap_program(const char *val);
101 static int gopt_nfs_allow_insecure_port(const char *val);
102 static int gopt_nfs_proto(const char *val);
103 static int gopt_nfs_retransmit_counter(const char *val);
104 static int gopt_nfs_retry_interval(const char *val);
105 static int gopt_nfs_vers(const char *val);
106 static int gopt_nis_domain(const char *val);
107 static int gopt_normalize_hostnames(const char *val);
108 static int gopt_os(const char *val);
109 static int gopt_osver(const char *val);
110 static int gopt_plock(const char *val);
111 static int gopt_print_pid(const char *val);
112 static int gopt_print_version(const char *val);
113 static int gopt_restart_mounts(const char *val);
114 static int gopt_search_path(const char *val);
115 static int gopt_selectors_in_defaults(const char *val);
116 static int gopt_show_statfs_entries(const char *val);
117 static int gopt_unmount_on_exit(const char *val);
118 static int gopt_vendor(const char *val);
119 static int process_global_option(const char *key, const char *val);
120 static int process_regular_map(cf_map_t *cfm);
121 static int process_regular_option(const char *section, const char *key, const char *val, cf_map_t *cfm);
122 static int ropt_browsable_dirs(const char *val, cf_map_t *cfm);
123 static int ropt_map_name(const char *val, cf_map_t *cfm);
124 static int ropt_map_options(const char *val, cf_map_t *cfm);
125 static int ropt_map_type(const char *val, cf_map_t *cfm);
126 static int ropt_mount_type(const char *val, cf_map_t *cfm);
127 static int ropt_search_path(const char *val, cf_map_t *cfm);
128 static int ropt_tag(const char *val, cf_map_t *cfm);
129 static void reset_cf_map(cf_map_t *cfm);
135 static cf_map_t cur_map;
136 static struct _func_map glob_functable[] = {
138 {"auto_dir", gopt_auto_dir},
139 {"browsable_dirs", gopt_browsable_dirs},
140 {"cache_duration", gopt_cache_duration},
141 {"cluster", gopt_cluster},
142 {"debug_options", gopt_debug_options},
143 {"dismount_interval", gopt_dismount_interval},
144 {"fully_qualified_hosts", gopt_fully_qualified_hosts},
145 {"full_os", gopt_full_os},
146 {"hesiod_base", gopt_hesiod_base},
147 {"karch", gopt_karch},
148 {"ldap_base", gopt_ldap_base},
149 {"ldap_cache_maxmem", gopt_ldap_cache_maxmem},
150 {"ldap_cache_seconds", gopt_ldap_cache_seconds},
151 {"ldap_hostports", gopt_ldap_hostports},
152 {"local_domain", gopt_local_domain},
153 {"log_file", gopt_log_file},
154 {"log_options", gopt_log_options},
155 {"map_options", gopt_map_options},
156 {"map_type", gopt_map_type},
157 {"mount_type", gopt_mount_type},
158 {"pid_file", gopt_pid_file},
159 {"portmap_program", gopt_portmap_program},
160 {"nfs_allow_insecure_port", gopt_nfs_allow_insecure_port},
161 {"nfs_proto", gopt_nfs_proto},
162 {"nfs_retransmit_counter", gopt_nfs_retransmit_counter},
163 {"nfs_retry_interval", gopt_nfs_retry_interval},
164 {"nfs_vers", gopt_nfs_vers},
165 {"nis_domain", gopt_nis_domain},
166 {"normalize_hostnames", gopt_normalize_hostnames},
168 {"osver", gopt_osver},
169 {"plock", gopt_plock},
170 {"print_pid", gopt_print_pid},
171 {"print_version", gopt_print_version},
172 {"restart_mounts", gopt_restart_mounts},
173 {"search_path", gopt_search_path},
174 {"selectors_on_default", gopt_selectors_in_defaults},
175 {"selectors_in_defaults", gopt_selectors_in_defaults},
176 {"show_statfs_entries", gopt_show_statfs_entries},
177 {"unmount_on_exit", gopt_unmount_on_exit},
178 {"vendor", gopt_vendor},
187 reset_cf_map(cf_map_t *cfm)
198 XFREE(cfm->cfm_name);
199 cfm->cfm_name = NULL;
208 * reset/initialize a regular map's flags and other variables from the
209 * global ones, so that they are applied to all maps. Of course, each map
210 * can then override the flags individually.
213 * (1): Will only work for maps that appear after [global].
214 * (2): Also be careful not to free() a global option.
215 * (3): I'm doing direct char* pointer comparison, and not strcmp(). This
219 /* initialize map_type from [global] */
220 if (cfm->cfm_type && cfm->cfm_type != gopt.map_type)
221 XFREE(cfm->cfm_type);
222 cfm->cfm_type = gopt.map_type;
224 /* initialize map_opts from [global] */
225 if (cfm->cfm_opts && cfm->cfm_opts != gopt.map_options)
226 XFREE(cfm->cfm_opts);
227 cfm->cfm_opts = gopt.map_options;
229 /* initialize search_path from [global] */
230 if (cfm->cfm_search_path && cfm->cfm_search_path != gopt.search_path)
231 XFREE(cfm->cfm_search_path);
232 cfm->cfm_search_path = gopt.search_path;
235 * Initialize flags that are common both to [global] and a local map.
237 cfm->cfm_flags = gopt.flags & (CFM_BROWSABLE_DIRS |
238 CFM_BROWSABLE_DIRS_FULL |
239 CFM_MOUNT_TYPE_AUTOFS |
240 CFM_SELECTORS_IN_DEFAULTS);
245 * Process configuration file options.
246 * Return 0 if OK, 1 otherwise.
249 set_conf_kv(const char *section, const char *key, const char *val)
254 fprintf(stderr,"set_conf_kv: section=%s, key=%s, val=%s\n",
256 #endif /* DEBUG_CONF */
259 * If global section, process them one at a time.
261 if (STREQ(section, "global")) {
263 * Check if a regular map was configured before "global",
264 * and process it as needed.
266 if (cur_map.cfm_dir) {
267 fprintf(stderr,"processing regular map \"%s\" before global one.\n",
269 ret = process_regular_map(&cur_map); /* will reset map */
274 /* process the global option first */
275 ret = process_global_option(key, val);
277 /* reset default options for regular maps from just updated globals */
279 reset_cf_map(&cur_map);
281 /* return status from the processing of the global option */
286 * otherwise save options and process a single map all at once.
289 /* check if we found a new map, so process one already collected */
290 if (cur_map.cfm_dir && !STREQ(cur_map.cfm_dir, section)) {
291 ret = process_regular_map(&cur_map); /* will reset map */
296 /* now process a single entry of a regular map */
297 return process_regular_option(section, key, val, &cur_map);
302 * Process global section of configuration file options.
303 * Return 0 upon success, 1 otherwise.
306 process_global_option(const char *key, const char *val)
308 struct _func_map *gfp;
310 /* ensure that val is valid */
311 if (!val || val[0] == '\0')
315 * search for global function.
317 for (gfp = glob_functable; gfp->name; gfp++)
318 if (FSTREQ(gfp->name, key))
319 return (gfp->func)(val);
321 fprintf(stderr, "conf: unknown global key: \"%s\"\n", key);
322 return 1; /* failed to match any command */
327 gopt_arch(const char *val)
329 gopt.arch = strdup((char *)val);
335 gopt_auto_dir(const char *val)
337 gopt.auto_dir = strdup((char *)val);
343 gopt_browsable_dirs(const char *val)
345 if (STREQ(val, "full")) {
346 gopt.flags |= CFM_BROWSABLE_DIRS_FULL;
348 } else if (STREQ(val, "yes")) {
349 gopt.flags |= CFM_BROWSABLE_DIRS;
351 } else if (STREQ(val, "no")) {
352 gopt.flags &= ~CFM_BROWSABLE_DIRS;
356 fprintf(stderr, "conf: unknown value to browsable_dirs \"%s\"\n", val);
357 return 1; /* unknown value */
362 gopt_cache_duration(const char *val)
364 gopt.am_timeo = atoi(val);
365 if (gopt.am_timeo <= 0)
366 gopt.am_timeo = AM_TTL;
372 gopt_cluster(const char *val)
374 gopt.cluster = strdup((char *)val);
380 gopt_debug_options(const char *val)
383 usage += debug_option(strdup((char *)val));
385 #else /* not DEBUG */
386 fprintf(stderr, "%s: not compiled with DEBUG option -- sorry.\n",
389 #endif /* not DEBUG */
394 gopt_dismount_interval(const char *val)
396 gopt.am_timeo_w = atoi(val);
397 if (gopt.am_timeo_w <= 0)
398 gopt.am_timeo_w = AM_TTL_W;
404 gopt_full_os(const char *val)
406 gopt.op_sys_full = strdup((char *)val);
412 gopt_fully_qualified_hosts(const char *val)
414 if (STREQ(val, "yes")) {
415 gopt.flags |= CFM_FULLY_QUALIFIED_HOSTS;
417 } else if (STREQ(val, "no")) {
418 gopt.flags &= ~CFM_FULLY_QUALIFIED_HOSTS;
422 fprintf(stderr, "conf: unknown value to fully_qualified_hosts \"%s\"\n", val);
423 return 1; /* unknown value */
428 gopt_hesiod_base(const char *val)
430 #ifdef HAVE_MAP_HESIOD
431 gopt.hesiod_base = strdup((char *)val);
433 #else /* not HAVE_MAP_HESIOD */
434 fprintf(stderr, "conf: hesiod_base option ignored. No Hesiod support available.\n");
436 #endif /* not HAVE_MAP_HESIOD */
441 gopt_karch(const char *val)
443 gopt.karch = strdup((char *)val);
449 gopt_pid_file(const char *val)
451 gopt.pid_file = strdup((char *)val);
457 gopt_local_domain(const char *val)
459 gopt.sub_domain = strdup((char *)val);
465 gopt_ldap_base(const char *val)
468 gopt.ldap_base = strdup((char *)val);
470 #else /* not HAVE_MAP_LDAP */
471 fprintf(stderr, "conf: ldap_base option ignored. No LDAP support available.\n");
473 #endif /* not HAVE_MAP_LDAP */
478 gopt_ldap_cache_seconds(const char *val)
483 gopt.ldap_cache_seconds = strtol((char *)val, &end, 10);
485 fprintf(stderr, "conf: bad LDAP cache (seconds) option: %s\n",val);
489 #else /* not HAVE_MAP_LDAP */
490 fprintf(stderr, "conf: ldap_cache_seconds option ignored. No LDAP support available.\n");
492 #endif /* not HAVE_MAP_LDAP */
497 gopt_ldap_cache_maxmem(const char *val)
502 gopt.ldap_cache_maxmem = strtol((char *)val, &end, 10);
504 fprintf(stderr, "conf: bad LDAP cache (maxmem) option: %s\n",val);
508 #else /* not HAVE_MAP_LDAP */
509 fprintf(stderr, "conf: ldap_cache_maxmem option ignored. No LDAP support available.\n");
511 #endif /* not HAVE_MAP_LDAP */
516 gopt_ldap_hostports(const char *val)
519 gopt.ldap_hostports = strdup((char *)val);
521 #else /* not HAVE_MAP_LDAP */
522 fprintf(stderr, "conf: ldap_hostports option ignored. No LDAP support available.\n");
524 #endif /* not HAVE_MAP_LDAP */
530 gopt_log_file(const char *val)
532 gopt.logfile = strdup((char *)val);
538 gopt_log_options(const char *val)
540 usage += switch_option(strdup((char *)val));
546 gopt_map_options(const char *val)
548 gopt.map_options = strdup((char *)val);
554 gopt_map_type(const char *val)
556 /* check if map type exist */
557 if (!mapc_type_exists(val)) {
558 fprintf(stderr, "conf: no such map type \"%s\"\n", val);
561 gopt.map_type = strdup((char *)val);
567 gopt_mount_type(const char *val)
569 if (STREQ(val, "autofs")) {
570 fprintf(stderr, "conf: no autofs support available, turning it off\n");
571 gopt.flags &= ~CFM_MOUNT_TYPE_AUTOFS;
573 } else if (STREQ(val, "nfs")) {
574 gopt.flags &= ~CFM_MOUNT_TYPE_AUTOFS;
578 fprintf(stderr, "conf: unknown value to mount_type \"%s\"\n", val);
579 return 1; /* unknown value */
584 gopt_portmap_program(const char *val)
586 gopt.portmap_program = atoi(val);
588 * allow alternate program numbers to be no more than 10 offset from
589 * official amd program number (300019).
591 if (gopt.portmap_program < AMQ_PROGRAM ||
592 gopt.portmap_program > AMQ_PROGRAM + 10) {
593 gopt.portmap_program = AMQ_PROGRAM;
594 set_amd_program_number(gopt.portmap_program);
595 fprintf(stderr, "conf: illegal amd program number \"%s\"\n", val);
599 set_amd_program_number(gopt.portmap_program);
600 return 0; /* all is OK */
605 gopt_nfs_allow_insecure_port(const char *val)
607 if (STREQ(val, "yes")) {
608 gopt.flags |= CFM_NFS_INSECURE_PORT;
610 } else if (STREQ(val, "no")) {
611 gopt.flags &= ~CFM_NFS_INSECURE_PORT;
615 fprintf(stderr, "conf: unknown value to nfs_allow_insecure_port \"%s\"\n", val);
616 return 1; /* unknown value */
621 gopt_nfs_proto(const char *val)
623 if (STREQ(val, "udp") || STREQ(val, "tcp")) {
624 gopt.nfs_proto = strdup((char *)val);
627 fprintf(stderr, "conf: illegal nfs_proto \"%s\"\n", val);
633 gopt_nfs_retransmit_counter(const char *val)
635 gopt.amfs_auto_retrans = atoi(val);
641 gopt_nfs_retry_interval(const char *val)
643 gopt.amfs_auto_timeo = atoi(val);
649 gopt_nfs_vers(const char *val)
653 if (i == 2 || i == 3) {
657 fprintf(stderr, "conf: illegal nfs_vers \"%s\"\n", val);
663 gopt_nis_domain(const char *val)
666 gopt.nis_domain = strdup((char *)val);
668 #else /* not HAVE_MAP_NIS */
669 fprintf(stderr, "conf: nis_domain option ignored. No NIS support available.\n");
671 #endif /* not HAVE_MAP_NIS */
676 gopt_normalize_hostnames(const char *val)
678 if (STREQ(val, "yes")) {
679 gopt.flags |= CFM_NORMALIZE_HOSTNAMES;
681 } else if (STREQ(val, "no")) {
682 gopt.flags &= ~CFM_NORMALIZE_HOSTNAMES;
686 fprintf(stderr, "conf: unknown value to normalize_hostnames \"%s\"\n", val);
687 return 1; /* unknown value */
692 gopt_os(const char *val)
694 gopt.op_sys = strdup((char *)val);
700 gopt_osver(const char *val)
702 gopt.op_sys_ver = strdup((char *)val);
708 gopt_plock(const char *val)
710 if (STREQ(val, "yes")) {
711 gopt.flags |= CFM_PROCESS_LOCK;
713 } else if (STREQ(val, "no")) {
714 gopt.flags &= ~CFM_PROCESS_LOCK;
718 fprintf(stderr, "conf: unknown value to plock \"%s\"\n", val);
719 return 1; /* unknown value */
724 gopt_print_pid(const char *val)
726 if (STREQ(val, "yes")) {
727 gopt.flags |= CFM_PRINT_PID;
729 } else if (STREQ(val, "no")) {
730 gopt.flags &= ~CFM_PRINT_PID;
734 fprintf(stderr, "conf: unknown value to print_pid \"%s\"\n", val);
735 return 1; /* unknown value */
740 gopt_print_version(const char *val)
742 if (STREQ(val, "yes")) {
743 fputs(get_version_string(), stderr);
745 } else if (STREQ(val, "no")) {
749 fprintf(stderr, "conf: unknown value to print_version \"%s\"\n", val);
750 return 1; /* unknown value */
755 gopt_restart_mounts(const char *val)
757 if (STREQ(val, "yes")) {
758 gopt.flags |= CFM_RESTART_EXISTING_MOUNTS;
760 } else if (STREQ(val, "no")) {
761 gopt.flags &= ~CFM_RESTART_EXISTING_MOUNTS;
765 fprintf(stderr, "conf: unknown value to restart_mounts \"%s\"\n", val);
766 return 1; /* unknown value */
771 gopt_search_path(const char *val)
773 gopt.search_path = strdup((char *)val);
779 gopt_selectors_in_defaults(const char *val)
781 if (STREQ(val, "yes")) {
782 gopt.flags |= CFM_SELECTORS_IN_DEFAULTS;
784 } else if (STREQ(val, "no")) {
785 gopt.flags &= ~CFM_SELECTORS_IN_DEFAULTS;
789 fprintf(stderr, "conf: unknown value to enable_default_selectors \"%s\"\n", val);
790 return 1; /* unknown value */
795 gopt_show_statfs_entries(const char *val)
797 if (STREQ(val, "yes")) {
798 gopt.flags |= CFM_SHOW_STATFS_ENTRIES;
800 } else if (STREQ(val, "no")) {
801 gopt.flags &= ~CFM_SHOW_STATFS_ENTRIES;
805 fprintf(stderr, "conf: unknown value to show_statfs_entries \"%s\"\n", val);
806 return 1; /* unknown value */
811 gopt_unmount_on_exit(const char *val)
813 if (STREQ(val, "yes")) {
814 gopt.flags |= CFM_UNMOUNT_ON_EXIT;
816 } else if (STREQ(val, "no")) {
817 gopt.flags &= ~CFM_UNMOUNT_ON_EXIT;
821 fprintf(stderr, "conf: unknown value to unmount_on_exit \"%s\"\n", val);
822 return 1; /* unknown value */
827 gopt_vendor(const char *val)
829 gopt.op_sys_vendor = strdup((char *)val);
835 * Collect one entry for a regular map
838 process_regular_option(const char *section, const char *key, const char *val, cf_map_t *cfm)
840 /* ensure that val is valid */
841 if (!section || section[0] == '\0' ||
842 !key || key[0] == '\0' ||
843 !val || val[0] == '\0' ||
845 fprintf(stderr, "conf: process_regular_option: null entries\n");
849 /* check if initializing a new map */
851 cfm->cfm_dir = strdup((char *)section);
853 /* check for each possible field */
854 if (STREQ(key, "browsable_dirs"))
855 return ropt_browsable_dirs(val, cfm);
857 if (STREQ(key, "map_name"))
858 return ropt_map_name(val, cfm);
860 if (STREQ(key, "map_options"))
861 return ropt_map_options(val, cfm);
863 if (STREQ(key, "map_type"))
864 return ropt_map_type(val, cfm);
866 if (STREQ(key, "mount_type"))
867 return ropt_mount_type(val, cfm);
869 if (STREQ(key, "search_path"))
870 return ropt_search_path(val, cfm);
872 if (STREQ(key, "tag"))
873 return ropt_tag(val, cfm);
875 fprintf(stderr, "conf: unknown regular key \"%s\" for section \"%s\"\n",
877 return 1; /* failed to match any command */
882 ropt_browsable_dirs(const char *val, cf_map_t *cfm)
884 if (STREQ(val, "full")) {
885 cfm->cfm_flags |= CFM_BROWSABLE_DIRS_FULL;
887 } else if (STREQ(val, "yes")) {
888 cfm->cfm_flags |= CFM_BROWSABLE_DIRS;
890 } else if (STREQ(val, "no")) {
891 cfm->cfm_flags &= ~CFM_BROWSABLE_DIRS;
895 fprintf(stderr, "conf: unknown value to browsable_dirs \"%s\"\n", val);
896 return 1; /* unknown value */
901 ropt_map_name(const char *val, cf_map_t *cfm)
903 cfm->cfm_name = strdup((char *)val);
909 ropt_map_options(const char *val, cf_map_t *cfm)
911 cfm->cfm_opts = strdup((char *)val);
917 ropt_map_type(const char *val, cf_map_t *cfm)
919 /* check if map type exist */
920 if (!mapc_type_exists(val)) {
921 fprintf(stderr, "conf: no such map type \"%s\"\n", val);
924 cfm->cfm_type = strdup((char *)val);
930 ropt_mount_type(const char *val, cf_map_t *cfm)
932 if (STREQ(val, "autofs")) {
933 fprintf(stderr, "conf: no autofs support available, turning it off\n");
934 cfm->cfm_flags &= ~CFM_MOUNT_TYPE_AUTOFS;
936 } else if (STREQ(val, "nfs")) {
937 cfm->cfm_flags &= ~CFM_MOUNT_TYPE_AUTOFS;
941 fprintf(stderr, "conf: unknown value to mount_type \"%s\"\n", val);
942 return 1; /* unknown value */
947 ropt_search_path(const char *val, cf_map_t *cfm)
949 cfm->cfm_search_path = strdup((char *)val);
955 ropt_tag(const char *val, cf_map_t *cfm)
957 cfm->cfm_tag = strdup((char *)val);
963 * Process one collected map.
966 process_regular_map(cf_map_t *cfm)
969 if (!cfm->cfm_name) {
970 fprintf(stderr, "conf: map_name must be defined for map \"%s\"\n", cfm->cfm_dir);
974 * If map has no tag defined, process the map.
975 * If no conf_tag was set in amd -T, process all untagged entries.
976 * If a tag is defined, then process it only if it matches the map tag.
979 (conf_tag && STREQ(cfm->cfm_tag, conf_tag))) {
981 fprintf(stderr, "processing map %s (flags=0x%x)...\n",
982 cfm->cfm_dir, cfm->cfm_flags);
983 #endif /* DEBUG_CONF */
984 root_newmap(cfm->cfm_dir,
985 cfm->cfm_opts ? cfm->cfm_opts : "",
989 fprintf(stderr, "skipping map %s...\n", cfm->cfm_dir);
998 * Process last map in conf file (if any)
1001 process_last_regular_map(void)
1004 * If the amd.conf file only has a [global] section (pretty useless
1005 * IMHO), do not try to process a map that does not exist.
1007 if (!cur_map.cfm_dir)
1009 return process_regular_map(&cur_map);