diff options
-rw-r--r-- | usr.bin/make/hash_tables.c | 49 | ||||
-rw-r--r-- | usr.bin/make/main.c | 5 | ||||
-rw-r--r-- | usr.bin/make/parse.c | 6 | ||||
-rw-r--r-- | usr.bin/make/var.c | 146 | ||||
-rw-r--r-- | usr.bin/make/var.h | 7 |
5 files changed, 119 insertions, 94 deletions
diff --git a/usr.bin/make/hash_tables.c b/usr.bin/make/hash_tables.c index 5c5e16a..5436326 100644 --- a/usr.bin/make/hash_tables.c +++ b/usr.bin/make/hash_tables.c @@ -1,7 +1,7 @@ /* * DO NOT EDIT * $FreeBSD$ - * auto-generated from FreeBSD: src/usr.bin/make/parse.c,v 1.99 2005/04/29 14:37:44 harti Exp + * auto-generated from FreeBSD: src/usr.bin/make/parse.c,v 1.100 2005/04/29 15:15:28 harti Exp * DO NOT EDIT */ #include <sys/types.h> @@ -66,8 +66,8 @@ directive_hash(const u_char *key, size_t len) } /* * d=2 - * n=69 - * m=33 + * n=72 + * m=34 * c=2.09 * maxlen=1 * minklen=4 @@ -75,34 +75,35 @@ directive_hash(const u_char *key, size_t len) * minchar=46 * maxchar=95 * loop=0 - * numiter=8 + * numiter=4 * seed= */ static const signed char keyword_g[] = { - -1, 17, 16, 0, -1, -1, -1, -1, 25, 18, - 2, -1, -1, 27, 28, 1, 0, 15, 16, -1, - -1, 14, 19, 1, -1, 13, -1, 0, 1, -1, - 11, 15, 0, 8, 14, 18, 31, -1, -1, 22, - -1, 27, -1, 0, -1, 9, -1, -1, -1, 21, - 3, 25, 0, 0, 0, -1, -1, 6, 0, 19, - -1, -1, -1, 23, -1, 17, -1, 0, 0, + 8, 15, -1, 25, 22, 20, -1, 33, 16, -1, + 21, 31, 0, 0, 0, 29, 30, 8, -1, 0, + -1, 21, -1, 0, -1, -1, -1, -1, -1, 4, + -1, -1, 25, 28, -1, 27, 11, 23, 0, 0, + 24, -1, -1, 0, 3, 0, -1, 24, 0, 0, + -1, 28, 12, -1, 20, 13, -1, 5, -1, 1, + 0, 0, -1, 0, 10, 19, 13, 9, -1, 2, + -1, -1, }; static const u_char keyword_T0[] = { - 8, 30, 55, 61, 14, 13, 48, 1, 18, 12, - 0, 52, 1, 40, 44, 52, 33, 58, 29, 29, - 3, 30, 26, 42, 1, 49, 10, 26, 5, 45, - 65, 13, 6, 22, 45, 61, 7, 25, 62, 65, - 8, 34, 48, 50, 5, 63, 33, 38, 52, 33, + 32, 10, 54, 61, 2, 35, 62, 50, 52, 53, + 70, 7, 62, 18, 24, 30, 31, 66, 10, 61, + 52, 71, 56, 56, 28, 6, 33, 67, 12, 41, + 39, 45, 51, 21, 34, 53, 56, 40, 47, 52, + 21, 61, 60, 12, 7, 28, 42, 38, 38, 52, }; static const u_char keyword_T1[] = { - 44, 18, 49, 61, 56, 13, 1, 54, 1, 47, - 46, 17, 22, 36, 25, 66, 14, 36, 58, 51, - 60, 22, 61, 19, 43, 37, 5, 18, 50, 58, - 32, 65, 47, 12, 28, 34, 65, 29, 59, 67, - 48, 36, 15, 41, 44, 11, 39, 29, 18, 68, + 0, 39, 65, 48, 13, 62, 46, 42, 5, 50, + 69, 69, 69, 43, 2, 46, 12, 6, 11, 9, + 24, 10, 25, 64, 68, 13, 57, 55, 17, 33, + 1, 18, 0, 67, 10, 14, 57, 56, 0, 6, + 50, 13, 3, 47, 56, 22, 37, 13, 28, 48, }; @@ -122,8 +123,8 @@ keyword_hash(const u_char *key, size_t len) f1 += keyword_T1[-46 + *kp]; } - f0 %= 69; - f1 %= 69; + f0 %= 72; + f1 %= 72; - return (keyword_g[f0] + keyword_g[f1]) % 33; + return (keyword_g[f0] + keyword_g[f1]) % 34; } diff --git a/usr.bin/make/main.c b/usr.bin/make/main.c index 8bb8897..2b8fd8a 100644 --- a/usr.bin/make/main.c +++ b/usr.bin/make/main.c @@ -101,6 +101,8 @@ __FBSDID("$FreeBSD$"); #define MAKEFLAGS ".MAKEFLAGS" +extern char **environ; /* XXX what header declares this variable? */ + /* Targets to be made */ Lst create = Lst_Initializer(create); @@ -695,7 +697,7 @@ main(int argc, char **argv) */ Dir_Init(); /* Initialize directory structures so -I flags * can be processed correctly */ - Var_Init(); /* As well as the lists of variables for + Var_Init(environ); /* As well as the lists of variables for * parsing arguments */ str_init(); @@ -781,6 +783,7 @@ main(int argc, char **argv) Dir_InitDot(); /* Initialize the "." directory */ if (objdir != curdir) Path_AddDir(&dirSearchPath, curdir); + Var_Set(".ST_EXPORTVAR", "YES", VAR_GLOBAL); Var_Set(".CURDIR", curdir, VAR_GLOBAL); Var_Set(".OBJDIR", objdir, VAR_GLOBAL); diff --git a/usr.bin/make/parse.c b/usr.bin/make/parse.c index 56f9e24..fb48a77 100644 --- a/usr.bin/make/parse.c +++ b/usr.bin/make/parse.c @@ -153,13 +153,13 @@ typedef enum { Begin, /* .BEGIN */ Default, /* .DEFAULT */ End, /* .END */ + ExportVar, /* .EXPORTVAR */ Ignore, /* .IGNORE */ Includes, /* .INCLUDES */ Interrupt, /* .INTERRUPT */ Libs, /* .LIBS */ MFlags, /* .MFLAGS or .MAKEFLAGS */ Main, /* .MAIN and we don't have anyth. user-spec. to make */ - NoExport, /* .NOEXPORT */ Not, /* Not special */ NotParallel, /* .NOTPARALELL */ Null, /* .NULL */ @@ -204,6 +204,7 @@ static const struct keyword { { ".DEFAULT", Default, 0 }, { ".END", End, 0 }, { ".EXEC", Attribute, OP_EXEC }, + { ".EXPORTVAR", ExportVar, 0 }, { ".IGNORE", Ignore, OP_IGNORE }, { ".INCLUDES", Includes, 0 }, { ".INTERRUPT", Interrupt, 0 }, @@ -1170,6 +1171,9 @@ ParseDoDependency(char *line) } Lst_Destroy(&paths, NOFREE); + } else if (specType == ExportVar) { + Var_SetEnv(line, VAR_GLOBAL); + } else { /* list of sources in order */ Lst curSrcs = Lst_Initializer(curSrc); diff --git a/usr.bin/make/var.c b/usr.bin/make/var.c index 892e1da..6be737c 100644 --- a/usr.bin/make/var.c +++ b/usr.bin/make/var.c @@ -141,6 +141,7 @@ static char varNoError[] = ""; * The four contexts are searched in the reverse order from which they are * listed. */ +GNode *VAR_ENV; /* variables from the environment */ GNode *VAR_GLOBAL; /* variables from the makefile */ GNode *VAR_CMD; /* variables defined on the command-line */ @@ -283,19 +284,14 @@ static Var * VarFindEnv(const char name[], GNode *ctxt) { Var *var; - char *env; name = VarLocal(name); - /* First look for the variable in the given context. */ if ((var = VarLookup(&ctxt->context, name)) != NULL) return (var); - /* Look for the variable in the environment. */ - if ((env = getenv(name)) != NULL) { - /* craft this variable from the environment value */ - return (VarCreate(name, env, VAR_FROM_ENV)); - } + if ((var = VarLookup(&VAR_ENV->context, name)) != NULL) + return (var); return (NULL); } @@ -325,7 +321,6 @@ VarFindAny(const char name[], GNode *ctxt) Boolean localCheckEnvFirst; LstNode *ln; Var *var; - char *env; name = VarLocal(name); @@ -361,11 +356,8 @@ VarFindAny(const char name[], GNode *ctxt) return (var); } - /* look in the environment */ - if ((env = getenv(name)) != NULL) { - /* craft this variable from the environment value */ - return (VarCreate(name, env, VAR_FROM_ENV)); - } + if ((var = VarLookup(&VAR_ENV->context, name)) != NULL) + return (var); /* deferred check for the environment (in case of -e/-E) */ if ((ctxt != VAR_GLOBAL) && (checkEnvFirst || localCheckEnvFirst)) { @@ -376,10 +368,8 @@ VarFindAny(const char name[], GNode *ctxt) return (NULL); } -/*- - *----------------------------------------------------------------------- - * VarAdd -- - * Add a new variable of name name and value val to the given context. +/** + * Add a new variable of name name and value val to the given context. * * Results: * None @@ -388,7 +378,6 @@ VarFindAny(const char name[], GNode *ctxt) * The new variable is placed at the front of the given context * The name and val arguments are duplicated so they may * safely be freed. - *----------------------------------------------------------------------- */ static void VarAdd(const char *name, const char *val, GNode *ctxt) @@ -462,22 +451,68 @@ Var_Set(const char *name, const char *val, GNode *ctxt) v = VarFindOnly(n, ctxt); if (v == NULL) { VarAdd(n, val, ctxt); + if (ctxt == VAR_CMD) { + /* + * Any variables given on the command line + * are automatically exported to the + * environment (as per POSIX standard) + */ + setenv(n, val, 1); + } } else { Buf_Clear(v->val); Buf_Append(v->val, val); - DEBUGF(VAR, ("%s:%s = %s\n", ctxt->name, n, val)); - } - /* - * Any variables given on the command line are automatically exported - * to the environment (as per POSIX standard) - */ - if (ctxt == VAR_CMD) { - setenv(n, val, 1); + if (ctxt == VAR_CMD || (v->flags & VAR_TO_ENV)) { + /* + * Any variables given on the command line + * are automatically exported to the + * environment (as per POSIX standard) + */ + setenv(n, val, 1); + } + } + + DEBUGF(VAR, ("%s:%s = %s\n", ctxt->name, n, val)); free(n); } +/* + * Var_SetEnv -- + * Set the VAR_TO_ENV flag on a variable + */ +void +Var_SetEnv(const char *name, GNode *ctxt) +{ + Var *v; + + v = VarFindOnly(name, VAR_CMD); + if (v != NULL) { + /* + * Do not allow .EXPORT: to be set on variables + * from the comand line or MAKEFLAGS. + */ + Error( + "Warning: Did not set .EXPORTVAR: on %s because it " + "is from the comand line or MAKEFLAGS", name); + return; + } + + v = VarFindAny(name, ctxt); + if (v == NULL) { + Lst_AtFront(&VAR_ENV->context, + VarCreate(name, NULL, VAR_TO_ENV)); + setenv(name, "", 1); + Error("Warning: .EXPORTVAR: set on undefined variable %s", name); + } else { + if ((v->flags & VAR_TO_ENV) == 0) { + v->flags |= VAR_TO_ENV; + setenv(v->name, Buf_Data(v->val), 1); + } + } +} + /*- *----------------------------------------------------------------------- * Var_Append -- @@ -514,21 +549,6 @@ Var_Append(const char *name, const char *val, GNode *ctxt) } if (v == NULL) { VarAdd(n, val, ctxt); - - } else if (v->flags & VAR_FROM_ENV) { - Buf_AddByte(v->val, (Byte)' '); - Buf_Append(v->val, val); - DEBUGF(VAR, ("%s:%s = %s\n", ctxt->name, n, Buf_Data(v->val))); - /* - * If the original variable came from the - * environment, we have to install it in the global - * context (we could place it in the environment, but - * then we should provide a way to export other - * variables...) - */ - v->flags &= ~VAR_FROM_ENV; - Lst_AtFront(&ctxt->context, v); - } else { Buf_AddByte(v->val, (Byte)' '); Buf_Append(v->val, val); @@ -561,10 +581,6 @@ Var_Exists(const char *name, GNode *ctxt) if (v == NULL) { free(n); return (FALSE); - } else if (v->flags & VAR_FROM_ENV) { - VarDestroy(v, TRUE); - free(n); - return (TRUE); } else { free(n); return (TRUE); @@ -595,10 +611,6 @@ Var_Value(const char *name, GNode *ctxt, char **frp) if (v == NULL) { p = NULL; *frp = NULL; - } else if (v->flags & VAR_FROM_ENV) { - p = Buf_Data(v->val); - *frp = p; - VarDestroy(v, FALSE); } else { p = Buf_Data(v->val); *frp = NULL; @@ -1320,10 +1332,6 @@ ParseRestModifier(VarParser *vp, char startc, Buffer *buf, Boolean *freeResult) v = VarFindAny(vname, vp->ctxt); if (v != NULL) { value = ParseModifier(vp, startc, v, freeResult); - - if (v->flags & VAR_FROM_ENV) { - VarDestroy(v, TRUE); - } return (value); } @@ -1430,11 +1438,6 @@ ParseRestEnd(VarParser *vp, Buffer *buf, Boolean *freeResult) v = VarFindAny(vname, vp->ctxt); if (v != NULL) { value = VarExpand(v, vp); - - if (v->flags & VAR_FROM_ENV) { - VarDestroy(v, TRUE); - } - *freeResult = TRUE; return (value); } @@ -1600,11 +1603,6 @@ VarParseShort(VarParser *vp, Boolean *freeResult) v = VarFindAny(vname, vp->ctxt); if (v != NULL) { value = VarExpand(v, vp); - - if (v->flags & VAR_FROM_ENV) { - VarDestroy(v, TRUE); - } - *freeResult = TRUE; return (value); } @@ -1950,11 +1948,29 @@ Var_GetHead(char *file) *----------------------------------------------------------------------- */ void -Var_Init(void) +Var_Init(char **env) { + char **ptr; - VAR_GLOBAL = Targ_NewGN("Global"); VAR_CMD = Targ_NewGN("Command"); + VAR_ENV = Targ_NewGN("Environment"); + VAR_GLOBAL = Targ_NewGN("Global"); + + /* + * Copy user environment variables into ENV context. + */ + for (ptr = env; *ptr != NULL; ++ptr) { + char *tmp = estrdup(*ptr); + const char *name = tmp; + char *sep = strchr(name, '='); + const char *value = sep + 1; + + if (sep != NULL) { + *sep = '\0'; + VarAdd(name, value, VAR_ENV); + } + free(tmp); + } } /*- diff --git a/usr.bin/make/var.h b/usr.bin/make/var.h index 3128b2b..f5fb9c6 100644 --- a/usr.bin/make/var.h +++ b/usr.bin/make/var.h @@ -57,12 +57,12 @@ typedef struct Var { #define VAR_IN_USE 1 /* Variable's value currently being used. * Used to avoid recursion */ -#define VAR_FROM_ENV 2 /* Variable comes from the environment */ - #define VAR_JUNK 4 /* Variable is a junk variable that * should be destroyed when done with * it. Used by Var_Parse for undefined, * modified variables */ + +#define VAR_TO_ENV 8 /* Place variable in environment */ } Var; /* Var*Pattern flags */ @@ -95,10 +95,11 @@ void Var_Dump(const struct GNode *); Boolean Var_Exists(const char *, struct GNode *); char *Var_GetHead(char *); char *Var_GetTail(char *); -void Var_Init(void); +void Var_Init(char **); char *Var_Parse(const char *, struct GNode *, Boolean, size_t *, Boolean *); char *Var_Quote(const char *); void Var_Set(const char *, const char *, struct GNode *); +void Var_SetEnv(const char *, struct GNode *); struct Buffer *Var_Subst(const char *, const char *, struct GNode *, Boolean); char *Var_Value(const char *, struct GNode *, char **); |