--- autofs-5.0.1/include/automount.h.add-missing-multi-support 2007-06-22 12:20:31.000000000 +0800 +++ autofs-5.0.1/include/automount.h 2007-06-22 12:21:27.000000000 +0800 @@ -192,6 +192,7 @@ char *cache_get_offset(const char *prefi /* Utility functions */ char **add_argv(int argc, char **argv, char *str); +char **append_argv(int argc1, char **argv1, int argc2, char **argv2); const char **copy_argv(int argc, const char **argv); int compare_argv(int argc1, const char **argv1, int argc2, const char **argv2); int free_argv(int argc, const char **argv); --- autofs-5.0.1/modules/lookup_multi.c.add-missing-multi-support 2006-09-01 13:29:50.000000000 +0800 +++ autofs-5.0.1/modules/lookup_multi.c 2007-06-22 12:21:27.000000000 +0800 @@ -45,7 +45,7 @@ int lookup_init(const char *my_mapfmt, i struct lookup_context *ctxt; char buf[MAX_ERR_BUF]; char *map, *mapfmt; - int i, j, an; + int i, an; char *estr; ctxt = malloc(sizeof(struct lookup_context)); @@ -73,7 +73,7 @@ int lookup_init(const char *my_mapfmt, i memcpy(ctxt->argl, argv, (argc + 1) * sizeof(const char *)); - for (i = j = an = 0; ctxt->argl[an]; an++) { + for (i = an = 0; ctxt->argl[an]; an++) { if (ctxt->m[i].argc == 0) { ctxt->m[i].argv = &ctxt->argl[an]; } @@ -100,9 +100,12 @@ int lookup_init(const char *my_mapfmt, i if (!(ctxt->m[i].mod = open_lookup(map, MODPREFIX, mapfmt ? mapfmt : my_mapfmt, ctxt->m[i].argc - 1, - ctxt->m[i].argv + 1))) + ctxt->m[i].argv + 1))) { error(LOGOPT_ANY, MODPREFIX "error opening module"); + free(map); goto error_out; + } + free(map); } *context = ctxt; --- autofs-5.0.1/daemon/lookup.c.add-missing-multi-support 2007-06-22 12:20:31.000000000 +0800 +++ autofs-5.0.1/daemon/lookup.c 2007-06-22 12:21:27.000000000 +0800 @@ -456,8 +456,12 @@ int lookup_nss_read_map(struct autofs_po } if (map->type) { - debug(ap->logopt, - "reading map %s %s", map->type, map->argv[0]); + if (!strncmp(map->type, "multi", 5)) + debug(ap->logopt, "reading multi map"); + else + debug(ap->logopt, + "reading map %s %s", + map->type, map->argv[0]); result = do_read_map(ap, map, age); map = map->next; continue; --- autofs-5.0.1/lib/master_tok.l.add-missing-multi-support 2007-06-22 12:20:31.000000000 +0800 +++ autofs-5.0.1/lib/master_tok.l 2007-06-22 12:21:27.000000000 +0800 @@ -29,6 +29,7 @@ static void master_echo(void); /* forwar #include <stdio.h> #include <stdlib.h> #include <string.h> +#include <ctype.h> #include "master_parse.tab.h" /* @@ -104,7 +105,9 @@ DNATTRSTR (cn|nisMapName|automountMapNam DNNAMESTR ([[:alnum:]_.\-]+) INTMAP (-hosts|-null) -MTYPE ((file|program|yp|nis|nisplus|ldap|ldaps|hesiod|userdir)(,(sun|hesiod))?) +MULTI ((multi)(,(sun|hesiod))?[\:]?{OPTWS}) +MULTISEP ([\-]{2}[[:blank:]]+) +MTYPE ((file|program|yp|nis|nisplus|ldap|ldaps|hesiod|userdir)(,(sun|hesiod))?) OPTTOUT (-t{OPTWS}|-t{OPTWS}={OPTWS}|--timeout{OPTWS}|--timeout{OPTWS}={OPTWS}) @@ -178,11 +181,18 @@ OPTTOUT (-t{OPTWS}|-t{OPTWS}={OPTWS}|-- <MAPSTR>{ {OPTWS}\\\n{OPTWS} {} + {MULTI} { + strcpy(master_lval.strtype, master_text); + return(MULTITYPE); + } + {MTYPE}/":" { strcpy(master_lval.strtype, master_text); return(MAPTYPE); } + {MULTISEP} { return(DDASH); } + ":" { return(COLON); } "-hosts" { @@ -292,6 +302,11 @@ OPTTOUT (-t{OPTWS}|-t{OPTWS}={OPTWS}|-- <OPTSTR>{ {OPTWS}\\\n{OPTWS} {} + {MULTISEP} { + BEGIN(MAPSTR); + return(DDASH); + } + {OPTTOUT} { return(OPT_TIMEOUT); } -D{OPTWS} --- autofs-5.0.1/lib/args.c.add-missing-multi-support 2006-09-01 13:29:50.000000000 +0800 +++ autofs-5.0.1/lib/args.c 2007-06-22 12:21:27.000000000 +0800 @@ -62,6 +62,45 @@ char **add_argv(int argc, char **argv, c return vector; } +char **append_argv(int argc1, char **argv1, int argc2, char **argv2) +{ + char **vector; + size_t vector_size; + int len, i, j; + + len = argc1 + argc2; + vector_size = (len + 1) * sizeof(char *); + vector = (char **) realloc(argv1, vector_size); + if (!vector) { + free_argv(argc1, (const char **) argv1); + free_argv(argc2, (const char **) argv2); + return NULL; + } + + for (i = argc1, j = 0; i <= len; i++, j++) { + if (argv2[j]) { + vector[i] = strdup(argv2[j]); + if (!vector[i]) { + error(LOGOPT_ANY, "failed to strdup arg"); + break; + } + } else + vector[i] = NULL; + } + + if (i < len) { + free_argv(len, (const char **) vector); + free_argv(argc2, (const char **) argv2); + return NULL; + } + + vector[len] = NULL; + + free_argv(argc2, (const char **) argv2); + + return vector; +} + const char **copy_argv(int argc, const char **argv) { char **vector; --- autofs-5.0.1/lib/master_parse.y.add-missing-multi-support 2007-06-22 12:20:31.000000000 +0800 +++ autofs-5.0.1/lib/master_parse.y 2007-06-22 12:21:27.000000000 +0800 @@ -24,6 +24,7 @@ #include <string.h> #include <stdlib.h> #include <stdarg.h> +#include <ctype.h> #include <sys/ioctl.h> #include "automount.h" @@ -46,6 +47,7 @@ extern void master_set_scan_buffer(const static char *master_strdup(char *); static void local_init_vars(void); static void local_free_vars(void); +static int add_multi_mapstr(void); static int master_error(const char *s); static int master_notify(const char *s); @@ -55,6 +57,8 @@ static char *type; static char *format; static long timeout; static unsigned ghost; +static char **tmp_argv; +static int tmp_argc; static char **local_argv; static int local_argc; @@ -91,7 +95,7 @@ static int master_fprintf(FILE *, char * %token COMMENT %token MAP %token OPT_TIMEOUT OPT_NOGHOST OPT_GHOST OPT_VERBOSE OPT_DEBUG -%token COLON COMMA NL +%token COLON COMMA NL DDASH %type <strtype> map %type <strtype> options %type <strtype> dn @@ -105,6 +109,7 @@ static int master_fprintf(FILE *, char * %token <strtype> NILL %token <strtype> SPACE %token <strtype> EQUAL +%token <strtype> MULTITYPE %token <strtype> MAPTYPE %token <strtype> DNSERVER %token <strtype> DNATTR @@ -128,7 +133,7 @@ file: { ; line: - | PATH map + | PATH mapspec { path = master_strdup($1); if (!path) { @@ -136,14 +141,49 @@ line: YYABORT; } } - | PATH map options + | PATH MULTITYPE maplist { + char *tmp; + + tmp = strchr($2, ':'); + if (tmp) + *tmp = '\0'; + else { + int len = strlen($2); + while (len-- && isblank($2[len])) + $2[len] = '\0'; + if (len < 4) { + master_notify($2); + local_free_vars(); + YYABORT; + } + } + path = master_strdup($1); if (!path) { + master_error("memory allocation error"); local_free_vars(); YYABORT; } - } + + if ((tmp = strchr($2, ','))) + *tmp++ = '\0'; + + type = master_strdup($2); + if (!type) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } + if (tmp) { + format = master_strdup(tmp); + if (!format) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } + } + } | PATH COLON { master_notify($1); YYABORT; } | PATH OPTION { master_notify($2); YYABORT; } | PATH NILL { master_notify($2); YYABORT; } @@ -159,25 +199,89 @@ line: | COMMENT { YYABORT; } ; -map: PATH +mapspec: map + { + local_argc = tmp_argc; + local_argv = tmp_argv; + tmp_argc = 0; + tmp_argv = NULL; + } + | map options + { + local_argc = tmp_argc; + local_argv = tmp_argv; + tmp_argc = 0; + tmp_argv = NULL; + } + ; + +maplist: map + { + if (!add_multi_mapstr()) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } + } + | map options + { + if (!add_multi_mapstr()) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } + } + | maplist DDASH map { local_argc++; - local_argv = add_argv(local_argc, local_argv, $1); + local_argv = add_argv(local_argc, local_argv, "--"); if (!local_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; } + if (!add_multi_mapstr()) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } } - | MAPNAME + | maplist DDASH map options { local_argc++; - local_argv = add_argv(local_argc, local_argv, $1); + local_argv = add_argv(local_argc, local_argv, "--"); if (!local_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; } + if (!add_multi_mapstr()) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } + } + ; + +map: PATH + { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $1); + if (!tmp_argv) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } + } + | MAPNAME + { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $1); + if (!tmp_argv) { + master_error("memory allocation error"); + local_free_vars(); + YYABORT; + } } | MAPHOSTS { @@ -202,9 +306,9 @@ map: PATH local_free_vars(); YYABORT; } - local_argc++; - local_argv = add_argv(local_argc, local_argv, $1); - if (!local_argv) { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $1); + if (!tmp_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; @@ -229,9 +333,9 @@ map: PATH YYABORT; } } - local_argc++; - local_argv = add_argv(local_argc, local_argv, $3); - if (!local_argv) { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $3); + if (!tmp_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; @@ -256,9 +360,9 @@ map: PATH YYABORT; } } - local_argc++; - local_argv = add_argv(local_argc, local_argv, $3); - if (!local_argv) { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $3); + if (!tmp_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; @@ -283,25 +387,25 @@ map: PATH YYABORT; } } - local_argc++; - local_argv = add_argv(local_argc, local_argv, $3); - if (!local_argv) { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $3); + if (!tmp_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; } /* Add back the type for lookup_ldap.c to handle ldaps */ - if (*local_argv[0]) { - tmp = malloc(strlen(type) + strlen(local_argv[0]) + 2); + if (*tmp_argv[0]) { + tmp = malloc(strlen(type) + strlen(tmp_argv[0]) + 2); if (!tmp) { local_free_vars(); YYABORT; } strcpy(tmp, type); strcat(tmp, ":"); - strcat(tmp, local_argv[0]); - free(local_argv[0]); - local_argv[0] = tmp; + strcat(tmp, tmp_argv[0]); + free(tmp_argv[0]); + tmp_argv[0] = tmp; } } ; @@ -443,9 +547,9 @@ daemon_option: OPT_TIMEOUT NUMBER { time mount_option: OPTION { - local_argc++; - local_argv = add_argv(local_argc, local_argv, $1); - if (!local_argv) { + tmp_argc++; + tmp_argv = add_argv(tmp_argc, tmp_argv, $1); + if (!tmp_argv) { master_error("memory allocation error"); local_free_vars(); YYABORT; @@ -496,6 +600,8 @@ static void local_init_vars(void) debug = 0; timeout = -1; ghost = defaults_get_browse_mode(); + tmp_argv = NULL; + tmp_argc = 0; local_argv = NULL; local_argc = 0; } @@ -511,8 +617,62 @@ static void local_free_vars(void) if (format) free(format); - if (local_argv) + if (local_argv) { free_argv(local_argc, (const char **) local_argv); + local_argv = NULL; + local_argc = 0; + } + + if (tmp_argv) { + free_argv(tmp_argc, (const char **) tmp_argv); + tmp_argv = NULL; + tmp_argc = 0; + } +} + +static int add_multi_mapstr(void) +{ + /* We need the individual map types for a multi map */ + if (!type) { + if (tmp_argc > 0 && *tmp_argv[0] == '/') + type = strdup("file"); + else + return 0; + } + + if (format) { + char *tmp = realloc(type, strlen(type) + strlen(format) + 2); + if (!tmp) + return 0; + type = tmp; + strcat(type, ","); + strcat(type, format); + free(format); + format = NULL; + } + + local_argc++; + local_argv = add_argv(local_argc, local_argv, type); + if (!local_argv) { + free(type); + type = NULL; + return 0; + } + + local_argv = append_argv(local_argc, local_argv, tmp_argc, tmp_argv); + if (!local_argv) { + free(type); + type = NULL; + return 0; + } + local_argc += tmp_argc; + + tmp_argc = 0; + tmp_argv = NULL; + free(type); + type = NULL; + + return 1; } void master_init_scan(void)