Sat Jul 4 10:35:30 2020 UTC ()
make(1): remove unnecessary forward declarations, fix indentation


(rillig)
diff -r1.248 -r1.249 src/usr.bin/make/var.c

cvs diff -r1.248 -r1.249 src/usr.bin/make/var.c (expand / switch to unified diff)

--- src/usr.bin/make/var.c 2020/07/04 10:19:39 1.248
+++ src/usr.bin/make/var.c 2020/07/04 10:35:30 1.249
@@ -1,14 +1,14 @@ @@ -1,14 +1,14 @@
1/* $NetBSD: var.c,v 1.248 2020/07/04 10:19:39 rillig Exp $ */ 1/* $NetBSD: var.c,v 1.249 2020/07/04 10:35:30 rillig Exp $ */
2 2
3/* 3/*
4 * Copyright (c) 1988, 1989, 1990, 1993 4 * Copyright (c) 1988, 1989, 1990, 1993
5 * The Regents of the University of California. All rights reserved. 5 * The Regents of the University of California. All rights reserved.
6 * 6 *
7 * This code is derived from software contributed to Berkeley by 7 * This code is derived from software contributed to Berkeley by
8 * Adam de Boor. 8 * Adam de Boor.
9 * 9 *
10 * Redistribution and use in source and binary forms, with or without 10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions 11 * modification, are permitted provided that the following conditions
12 * are met: 12 * are met:
13 * 1. Redistributions of source code must retain the above copyright 13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer. 14 * notice, this list of conditions and the following disclaimer.
@@ -59,34 +59,34 @@ @@ -59,34 +59,34 @@
59 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 59 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
60 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 60 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
61 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 61 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
62 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 62 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
63 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 63 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
64 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 64 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
65 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 65 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
66 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 66 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
67 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 67 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
68 * SUCH DAMAGE. 68 * SUCH DAMAGE.
69 */ 69 */
70 70
71#ifndef MAKE_NATIVE 71#ifndef MAKE_NATIVE
72static char rcsid[] = "$NetBSD: var.c,v 1.248 2020/07/04 10:19:39 rillig Exp $"; 72static char rcsid[] = "$NetBSD: var.c,v 1.249 2020/07/04 10:35:30 rillig Exp $";
73#else 73#else
74#include <sys/cdefs.h> 74#include <sys/cdefs.h>
75#ifndef lint 75#ifndef lint
76#if 0 76#if 0
77static char sccsid[] = "@(#)var.c 8.3 (Berkeley) 3/19/94"; 77static char sccsid[] = "@(#)var.c 8.3 (Berkeley) 3/19/94";
78#else 78#else
79__RCSID("$NetBSD: var.c,v 1.248 2020/07/04 10:19:39 rillig Exp $"); 79__RCSID("$NetBSD: var.c,v 1.249 2020/07/04 10:35:30 rillig Exp $");
80#endif 80#endif
81#endif /* not lint */ 81#endif /* not lint */
82#endif 82#endif
83 83
84/*- 84/*-
85 * var.c -- 85 * var.c --
86 * Variable-handling functions 86 * Variable-handling functions
87 * 87 *
88 * Interface: 88 * Interface:
89 * Var_Set Set the value of a variable in the given 89 * Var_Set Set the value of a variable in the given
90 * context. The variable is created if it doesn't 90 * context. The variable is created if it doesn't
91 * yet exist. The value and variable name need not 91 * yet exist. The value and variable name need not
92 * be preserved. 92 * be preserved.
@@ -142,34 +142,34 @@ __RCSID("$NetBSD: var.c,v 1.248 2020/07/ @@ -142,34 +142,34 @@ __RCSID("$NetBSD: var.c,v 1.248 2020/07/
142 142
143extern int makelevel; 143extern int makelevel;
144/* 144/*
145 * This lets us tell if we have replaced the original environ 145 * This lets us tell if we have replaced the original environ
146 * (which we cannot free). 146 * (which we cannot free).
147 */ 147 */
148char **savedEnv = NULL; 148char **savedEnv = NULL;
149 149
150/* 150/*
151 * This is a harmless return value for Var_Parse that can be used by Var_Subst 151 * This is a harmless return value for Var_Parse that can be used by Var_Subst
152 * to determine if there was an error in parsing -- easier than returning 152 * to determine if there was an error in parsing -- easier than returning
153 * a flag, as things outside this module don't give a hoot. 153 * a flag, as things outside this module don't give a hoot.
154 */ 154 */
155char var_Error[] = ""; 155char var_Error[] = "";
156 156
157/* 157/*
158 * Similar to var_Error, but returned when the 'VARF_UNDEFERR' flag for 158 * Similar to var_Error, but returned when the 'VARF_UNDEFERR' flag for
159 * Var_Parse is not set. Why not just use a constant? Well, gcc likes 159 * Var_Parse is not set. Why not just use a constant? Well, gcc likes
160 * to condense identical string instances... 160 * to condense identical string instances...
161 */ 161 */
162static char varNoError[] = ""; 162static char varNoError[] = "";
163 163
164/* 164/*
165 * Traditionally we consume $$ during := like any other expansion. 165 * Traditionally we consume $$ during := like any other expansion.
166 * Other make's do not. 166 * Other make's do not.
167 * This knob allows controlling the behavior. 167 * This knob allows controlling the behavior.
168 * FALSE for old behavior. 168 * FALSE for old behavior.
169 * TRUE for new compatible. 169 * TRUE for new compatible.
170 */ 170 */
171#define SAVE_DOLLARS ".MAKE.SAVE_DOLLARS" 171#define SAVE_DOLLARS ".MAKE.SAVE_DOLLARS"
172static Boolean save_dollars = TRUE; 172static Boolean save_dollars = TRUE;
173 173
174/* 174/*
175 * Internally, variables are contained in four different contexts. 175 * Internally, variables are contained in four different contexts.
@@ -289,39 +289,26 @@ typedef struct { @@ -289,39 +289,26 @@ typedef struct {
289 int nsub; 289 int nsub;
290 regmatch_t *matches; 290 regmatch_t *matches;
291 char *replace; 291 char *replace;
292 int flags; 292 int flags;
293} VarREPattern; 293} VarREPattern;
294#endif 294#endif
295 295
296/* struct passed to VarSelectWords() for ":[start..end]" */ 296/* struct passed to VarSelectWords() for ":[start..end]" */
297typedef struct { 297typedef struct {
298 int start; /* first word to select */ 298 int start; /* first word to select */
299 int end; /* last word to select */ 299 int end; /* last word to select */
300} VarSelectWords_t; 300} VarSelectWords_t;
301 301
302static char *VarGetPattern(GNode *, Var_Parse_State *, 
303 VarPattern_Flags, const char **, int, 
304 VarPattern_Flags *, int *, VarPattern *); 
305static char *VarQuote(char *, Boolean); 
306static char *VarHash(char *); 
307static char *VarModify(GNode *, Var_Parse_State *, 
308 const char *, 
309 Boolean (*)(GNode *, Var_Parse_State *, char *, Boolean, Buffer *, void *), 
310 void *); 
311static char *VarOrder(const char *, const char); 
312static char *VarUniq(const char *); 
313static int VarWordCompare(const void *, const void *); 
314 
315#define BROPEN '{' 302#define BROPEN '{'
316#define BRCLOSE '}' 303#define BRCLOSE '}'
317#define PROPEN '(' 304#define PROPEN '('
318#define PRCLOSE ')' 305#define PRCLOSE ')'
319 306
320/*- 307/*-
321 *----------------------------------------------------------------------- 308 *-----------------------------------------------------------------------
322 * VarFind -- 309 * VarFind --
323 * Find the given variable in the given context and any other contexts 310 * Find the given variable in the given context and any other contexts
324 * indicated. 311 * indicated.
325 * 312 *
326 * Input: 313 * Input:
327 * name name to find 314 * name name to find
@@ -864,27 +851,27 @@ Var_UnExport(char *str) @@ -864,27 +851,27 @@ Var_UnExport(char *str)
864 free(as); 851 free(as);
865 free(av); 852 free(av);
866 if (vlist != str) { 853 if (vlist != str) {
867 Var_Delete(MAKE_EXPORTED, VAR_GLOBAL); 854 Var_Delete(MAKE_EXPORTED, VAR_GLOBAL);
868 free(vlist); 855 free(vlist);
869 } 856 }
870 } 857 }
871} 858}
872 859
873static void 860static void
874Var_Set_with_flags(const char *name, const char *val, GNode *ctxt, 861Var_Set_with_flags(const char *name, const char *val, GNode *ctxt,
875 VarSet_Flags flags) 862 VarSet_Flags flags)
876{ 863{
877 Var *v; 864 Var *v;
878 char *expanded_name = NULL; 865 char *expanded_name = NULL;
879 866
880 /* 867 /*
881 * We only look for a variable in the given context since anything set 868 * We only look for a variable in the given context since anything set
882 * here will override anything in a lower context, so there's not much 869 * here will override anything in a lower context, so there's not much
883 * point in searching them all just to save a bit of memory... 870 * point in searching them all just to save a bit of memory...
884 */ 871 */
885 if (strchr(name, '$') != NULL) { 872 if (strchr(name, '$') != NULL) {
886 expanded_name = Var_Subst(NULL, name, ctxt, VARF_WANTRES); 873 expanded_name = Var_Subst(NULL, name, ctxt, VARF_WANTRES);
887 if (expanded_name[0] == 0) { 874 if (expanded_name[0] == 0) {
888 if (DEBUG(VAR)) { 875 if (DEBUG(VAR)) {
889 fprintf(debug_file, "Var_Set(\"%s\", \"%s\", ...) " 876 fprintf(debug_file, "Var_Set(\"%s\", \"%s\", ...) "
890 "name expands to empty string - ignored\n", 877 "name expands to empty string - ignored\n",
@@ -1017,28 +1004,28 @@ Var_Set(const char *name, const char *va @@ -1017,28 +1004,28 @@ Var_Set(const char *name, const char *va
1017 * 1004 *
1018 * Notes: 1005 * Notes:
1019 * Only if the variable is being sought in the global context is the 1006 * Only if the variable is being sought in the global context is the
1020 * environment searched. 1007 * environment searched.
1021 * XXX: Knows its calling circumstances in that if called with ctxt 1008 * XXX: Knows its calling circumstances in that if called with ctxt
1022 * an actual target, it will only search that context since only 1009 * an actual target, it will only search that context since only
1023 * a local variable could be being appended to. This is actually 1010 * a local variable could be being appended to. This is actually
1024 * a big win and must be tolerated. 1011 * a big win and must be tolerated.
1025 *----------------------------------------------------------------------- 1012 *-----------------------------------------------------------------------
1026 */ 1013 */
1027void 1014void
1028Var_Append(const char *name, const char *val, GNode *ctxt) 1015Var_Append(const char *name, const char *val, GNode *ctxt)
1029{ 1016{
1030 Var *v; 1017 Var *v;
1031 Hash_Entry *h; 1018 Hash_Entry *h;
1032 char *expanded_name = NULL; 1019 char *expanded_name = NULL;
1033 1020
1034 if (strchr(name, '$') != NULL) { 1021 if (strchr(name, '$') != NULL) {
1035 expanded_name = Var_Subst(NULL, name, ctxt, VARF_WANTRES); 1022 expanded_name = Var_Subst(NULL, name, ctxt, VARF_WANTRES);
1036 if (expanded_name[0] == 0) { 1023 if (expanded_name[0] == 0) {
1037 if (DEBUG(VAR)) { 1024 if (DEBUG(VAR)) {
1038 fprintf(debug_file, "Var_Append(\"%s\", \"%s\", ...) " 1025 fprintf(debug_file, "Var_Append(\"%s\", \"%s\", ...) "
1039 "name expands to empty string - ignored\n", 1026 "name expands to empty string - ignored\n",
1040 name, val); 1027 name, val);
1041 } 1028 }
1042 free(expanded_name); 1029 free(expanded_name);
1043 return; 1030 return;
1044 } 1031 }
@@ -1320,27 +1307,27 @@ VarSubstitute(GNode *ctx MAKE_ATTR_UNUSE @@ -1320,27 +1307,27 @@ VarSubstitute(GNode *ctx MAKE_ATTR_UNUSE
1320 addSpace = TRUE; 1307 addSpace = TRUE;
1321 Buf_AddBytes(buf, pattern->rightLen, pattern->rhs); 1308 Buf_AddBytes(buf, pattern->rightLen, pattern->rhs);
1322 } 1309 }
1323 pattern->flags |= VAR_SUB_MATCHED; 1310 pattern->flags |= VAR_SUB_MATCHED;
1324 } else if (pattern->flags & VAR_MATCH_END) { 1311 } else if (pattern->flags & VAR_MATCH_END) {
1325 /* 1312 /*
1326 * Doesn't match to end -- copy word wholesale 1313 * Doesn't match to end -- copy word wholesale
1327 */ 1314 */
1328 goto nosub; 1315 goto nosub;
1329 } else { 1316 } else {
1330 /* 1317 /*
1331 * Matches at start but need to copy in trailing characters 1318 * Matches at start but need to copy in trailing characters
1332 */ 1319 */
1333 if ((pattern->rightLen + wordLen - pattern->leftLen) != 0){ 1320 if ((pattern->rightLen + wordLen - pattern->leftLen) != 0) {
1334 if (addSpace && vpstate->varSpace) { 1321 if (addSpace && vpstate->varSpace) {
1335 Buf_AddByte(buf, vpstate->varSpace); 1322 Buf_AddByte(buf, vpstate->varSpace);
1336 } 1323 }
1337 addSpace = TRUE; 1324 addSpace = TRUE;
1338 } 1325 }
1339 Buf_AddBytes(buf, pattern->rightLen, pattern->rhs); 1326 Buf_AddBytes(buf, pattern->rightLen, pattern->rhs);
1340 Buf_AddBytes(buf, wordLen - pattern->leftLen, 1327 Buf_AddBytes(buf, wordLen - pattern->leftLen,
1341 (word + pattern->leftLen)); 1328 (word + pattern->leftLen));
1342 pattern->flags |= VAR_SUB_MATCHED; 1329 pattern->flags |= VAR_SUB_MATCHED;
1343 } 1330 }
1344 } else if (pattern->flags & VAR_MATCH_START) { 1331 } else if (pattern->flags & VAR_MATCH_START) {
1345 /* 1332 /*
1346 * Had to match at start of word and didn't -- copy whole word. 1333 * Had to match at start of word and didn't -- copy whole word.
@@ -1387,27 +1374,27 @@ VarSubstitute(GNode *ctx MAKE_ATTR_UNUSE @@ -1387,27 +1374,27 @@ VarSubstitute(GNode *ctx MAKE_ATTR_UNUSE
1387 * accordingly through the loop) is copied straight into the 1374 * accordingly through the loop) is copied straight into the
1388 * buffer. 1375 * buffer.
1389 * addSpace is set FALSE as soon as a space is added to the 1376 * addSpace is set FALSE as soon as a space is added to the
1390 * buffer. 1377 * buffer.
1391 */ 1378 */
1392 Boolean done; 1379 Boolean done;
1393 int origSize; 1380 int origSize;
1394 1381
1395 done = FALSE; 1382 done = FALSE;
1396 origSize = Buf_Size(buf); 1383 origSize = Buf_Size(buf);
1397 while (!done) { 1384 while (!done) {
1398 cp = Str_FindSubstring(word, pattern->lhs); 1385 cp = Str_FindSubstring(word, pattern->lhs);
1399 if (cp != NULL) { 1386 if (cp != NULL) {
1400 if (addSpace && (((cp - word) + pattern->rightLen) != 0)){ 1387 if (addSpace && (((cp - word) + pattern->rightLen) != 0)) {
1401 Buf_AddByte(buf, vpstate->varSpace); 1388 Buf_AddByte(buf, vpstate->varSpace);
1402 addSpace = FALSE; 1389 addSpace = FALSE;
1403 } 1390 }
1404 Buf_AddBytes(buf, cp-word, word); 1391 Buf_AddBytes(buf, cp-word, word);
1405 Buf_AddBytes(buf, pattern->rightLen, pattern->rhs); 1392 Buf_AddBytes(buf, pattern->rightLen, pattern->rhs);
1406 wordLen -= (cp - word) + pattern->leftLen; 1393 wordLen -= (cp - word) + pattern->leftLen;
1407 word = cp + pattern->leftLen; 1394 word = cp + pattern->leftLen;
1408 if (wordLen == 0) { 1395 if (wordLen == 0) {
1409 done = TRUE; 1396 done = TRUE;
1410 } 1397 }
1411 if ((pattern->flags & VAR_SUB_GLOBAL) == 0) { 1398 if ((pattern->flags & VAR_SUB_GLOBAL) == 0) {
1412 done = TRUE; 1399 done = TRUE;
1413 } 1400 }
@@ -1585,34 +1572,34 @@ VarRESubstitute(GNode *ctx MAKE_ATTR_UNU @@ -1585,34 +1572,34 @@ VarRESubstitute(GNode *ctx MAKE_ATTR_UNU
1585 * ODE make. We set the temp variable named in pattern.lhs to word and 1572 * ODE make. We set the temp variable named in pattern.lhs to word and
1586 * expand pattern.rhs. */ 1573 * expand pattern.rhs. */
1587static Boolean 1574static Boolean
1588VarLoopExpand(GNode *ctx MAKE_ATTR_UNUSED, 1575VarLoopExpand(GNode *ctx MAKE_ATTR_UNUSED,
1589 Var_Parse_State *vpstate MAKE_ATTR_UNUSED, 1576 Var_Parse_State *vpstate MAKE_ATTR_UNUSED,
1590 char *word, Boolean addSpace, Buffer *buf, 1577 char *word, Boolean addSpace, Buffer *buf,
1591 void *data) 1578 void *data)
1592{ 1579{
1593 VarLoop_t *loop = data; 1580 VarLoop_t *loop = data;
1594 char *s; 1581 char *s;
1595 int slen; 1582 int slen;
1596 1583
1597 if (*word) { 1584 if (*word) {
1598 Var_Set_with_flags(loop->tvar, word, loop->ctxt, VAR_NO_EXPORT); 1585 Var_Set_with_flags(loop->tvar, word, loop->ctxt, VAR_NO_EXPORT);
1599 s = Var_Subst(NULL, loop->str, loop->ctxt, loop->flags); 1586 s = Var_Subst(NULL, loop->str, loop->ctxt, loop->flags);
1600 if (s != NULL && *s != '\0') { 1587 if (s != NULL && *s != '\0') {
1601 if (addSpace && *s != '\n') 1588 if (addSpace && *s != '\n')
1602 Buf_AddByte(buf, ' '); 1589 Buf_AddByte(buf, ' ');
1603 Buf_AddBytes(buf, (slen = strlen(s)), s); 1590 Buf_AddBytes(buf, (slen = strlen(s)), s);
1604 addSpace = (slen > 0 && s[slen - 1] != '\n'); 1591 addSpace = (slen > 0 && s[slen - 1] != '\n');
1605 } 1592 }
1606 free(s); 1593 free(s);
1607 } 1594 }
1608 return addSpace; 1595 return addSpace;
1609} 1596}
1610 1597
1611 1598
1612/*- 1599/*-
1613 *----------------------------------------------------------------------- 1600 *-----------------------------------------------------------------------
1614 * VarSelectWords -- 1601 * VarSelectWords --
1615 * Implements the :[start..end] modifier. 1602 * Implements the :[start..end] modifier.
1616 * This is a special case of VarModify since we want to be able 1603 * This is a special case of VarModify since we want to be able
1617 * to scan the list backwards if start > end. 1604 * to scan the list backwards if start > end.
1618 * 1605 *
@@ -2008,28 +1995,28 @@ VarGetPattern(GNode *ctxt, Var_Parse_Sta @@ -2008,28 +1995,28 @@ VarGetPattern(GNode *ctxt, Var_Parse_Sta
2008 */ 1995 */
2009 *vflags |= VAR_MATCH_END; 1996 *vflags |= VAR_MATCH_END;
2010 } else { 1997 } else {
2011 if (vflags == NULL || (*vflags & VAR_NOSUBST) == 0) { 1998 if (vflags == NULL || (*vflags & VAR_NOSUBST) == 0) {
2012 char *cp2; 1999 char *cp2;
2013 int len; 2000 int len;
2014 void *freeIt; 2001 void *freeIt;
2015 2002
2016 /* 2003 /*
2017 * If unescaped dollar sign not before the 2004 * If unescaped dollar sign not before the
2018 * delimiter, assume it's a variable 2005 * delimiter, assume it's a variable
2019 * substitution and recurse. 2006 * substitution and recurse.
2020 */ 2007 */
2021 cp2 = Var_Parse(cp, ctxt, errnum | 2008 cp2 = Var_Parse(cp, ctxt, errnum | (flags & VARF_WANTRES),
2022 (flags & VARF_WANTRES), &len, &freeIt); 2009 &len, &freeIt);
2023 Buf_AddBytes(&buf, strlen(cp2), cp2); 2010 Buf_AddBytes(&buf, strlen(cp2), cp2);
2024 free(freeIt); 2011 free(freeIt);
2025 cp += len - 1; 2012 cp += len - 1;
2026 } else { 2013 } else {
2027 const char *cp2 = &cp[1]; 2014 const char *cp2 = &cp[1];
2028 2015
2029 if (*cp2 == PROPEN || *cp2 == BROPEN) { 2016 if (*cp2 == PROPEN || *cp2 == BROPEN) {
2030 /* 2017 /*
2031 * Find the end of this variable reference 2018 * Find the end of this variable reference
2032 * and suck it in without further ado. 2019 * and suck it in without further ado.
2033 * It will be interpreted later. 2020 * It will be interpreted later.
2034 */ 2021 */
2035 int have = *cp2; 2022 int have = *cp2;
@@ -2174,29 +2161,29 @@ VarHash(char *str) @@ -2174,29 +2161,29 @@ VarHash(char *str)
2174 h = h * 5 + 0x52dce729U; 2161 h = h * 5 + 0x52dce729U;
2175 h ^= k; 2162 h ^= k;
2176 } 2163 }
2177 h ^= len2; 2164 h ^= len2;
2178 h *= 0x85ebca6b; 2165 h *= 0x85ebca6b;
2179 h ^= h >> 13; 2166 h ^= h >> 13;
2180 h *= 0xc2b2ae35; 2167 h *= 0xc2b2ae35;
2181 h ^= h >> 16; 2168 h ^= h >> 16;
2182 2169
2183 Buf_Init(&buf, 0); 2170 Buf_Init(&buf, 0);
2184 for (len = 0; len < 8; ++len) { 2171 for (len = 0; len < 8; ++len) {
2185 Buf_AddByte(&buf, hexdigits[h & 15]); 2172 Buf_AddByte(&buf, hexdigits[h & 15]);
2186 h >>= 4; 2173 h >>= 4;
2187 } 2174 }
2188 2175
2189 return Buf_Destroy(&buf, FALSE); 2176 return Buf_Destroy(&buf, FALSE);
2190} 2177}
2191 2178
2192static char * 2179static char *
2193VarStrftime(const char *fmt, int zulu, time_t utc) 2180VarStrftime(const char *fmt, int zulu, time_t utc)
2194{ 2181{
2195 char buf[BUFSIZ]; 2182 char buf[BUFSIZ];
2196 2183
2197 if (!utc) 2184 if (!utc)
2198 time(&utc); 2185 time(&utc);
2199 if (!*fmt) 2186 if (!*fmt)
2200 fmt = "%c"; 2187 fmt = "%c";
2201 strftime(buf, sizeof(buf), fmt, zulu ? gmtime(&utc) : localtime(&utc)); 2188 strftime(buf, sizeof(buf), fmt, zulu ? gmtime(&utc) : localtime(&utc));
2202 2189
@@ -3124,27 +3111,27 @@ ApplyModifier_Assign(ApplyModifiersState @@ -3124,27 +3111,27 @@ ApplyModifier_Assign(ApplyModifiersState
3124static Boolean 3111static Boolean
3125ApplyModifier_Remember(ApplyModifiersState *st) 3112ApplyModifier_Remember(ApplyModifiersState *st)
3126{ 3113{
3127 st->cp = st->tstr + 1; /* make sure it is set */ 3114 st->cp = st->tstr + 1; /* make sure it is set */
3128 if (!STRMOD_MATCHX(st->tstr, "_", 1)) 3115 if (!STRMOD_MATCHX(st->tstr, "_", 1))
3129 return FALSE; 3116 return FALSE;
3130 3117
3131 if (st->tstr[1] == '=') { 3118 if (st->tstr[1] == '=') {
3132 char *np; 3119 char *np;
3133 int n; 3120 int n;
3134 3121
3135 st->cp++; 3122 st->cp++;
3136 n = strcspn(st->cp, ":)}"); 3123 n = strcspn(st->cp, ":)}");
3137 np = bmake_strndup(st->cp, n+1); 3124 np = bmake_strndup(st->cp, n + 1);
3138 np[n] = '\0'; 3125 np[n] = '\0';
3139 st->cp = st->tstr + 2 + n; 3126 st->cp = st->tstr + 2 + n;
3140 Var_Set(np, st->nstr, st->ctxt); 3127 Var_Set(np, st->nstr, st->ctxt);
3141 free(np); 3128 free(np);
3142 } else { 3129 } else {
3143 Var_Set("_", st->nstr, st->ctxt); 3130 Var_Set("_", st->nstr, st->ctxt);
3144 } 3131 }
3145 st->newStr = st->nstr; 3132 st->newStr = st->nstr;
3146 st->termc = *st->cp; 3133 st->termc = *st->cp;
3147 return TRUE; 3134 return TRUE;
3148} 3135}
3149 3136
3150#ifdef SYSVVARSUB 3137#ifdef SYSVVARSUB
@@ -3696,28 +3683,27 @@ Var_Parse(const char *str, GNode *ctxt,  @@ -3696,28 +3683,27 @@ Var_Parse(const char *str, GNode *ctxt,
3696 tstr = &str[1]; 3683 tstr = &str[1];
3697 endc = str[1]; 3684 endc = str[1];
3698 } 3685 }
3699 } else { 3686 } else {
3700 Buffer buf; /* Holds the variable name */ 3687 Buffer buf; /* Holds the variable name */
3701 int depth = 1; 3688 int depth = 1;
3702 3689
3703 endc = startc == PROPEN ? PRCLOSE : BRCLOSE; 3690 endc = startc == PROPEN ? PRCLOSE : BRCLOSE;
3704 Buf_Init(&buf, 0); 3691 Buf_Init(&buf, 0);
3705 3692
3706 /* 3693 /*
3707 * Skip to the end character or a colon, whichever comes first. 3694 * Skip to the end character or a colon, whichever comes first.
3708 */ 3695 */
3709 for (tstr = str + 2; *tstr != '\0'; tstr++) 3696 for (tstr = str + 2; *tstr != '\0'; tstr++) {
3710 { 
3711 /* Track depth so we can spot parse errors. */ 3697 /* Track depth so we can spot parse errors. */
3712 if (*tstr == startc) 3698 if (*tstr == startc)
3713 depth++; 3699 depth++;
3714 if (*tstr == endc) { 3700 if (*tstr == endc) {
3715 if (--depth == 0) 3701 if (--depth == 0)
3716 break; 3702 break;
3717 } 3703 }
3718 if (depth == 1 && *tstr == ':') 3704 if (depth == 1 && *tstr == ':')
3719 break; 3705 break;
3720 /* A variable inside a variable, expand. */ 3706 /* A variable inside a variable, expand. */
3721 if (*tstr == '$') { 3707 if (*tstr == '$') {
3722 int rlen; 3708 int rlen;
3723 void *freeIt; 3709 void *freeIt;
@@ -3884,27 +3870,27 @@ Var_Parse(const char *str, GNode *ctxt,  @@ -3884,27 +3870,27 @@ Var_Parse(const char *str, GNode *ctxt,
3884 tstr++; 3870 tstr++;
3885 3871
3886 nstr = ApplyModifiers(nstr, tstr, startc, endc, 3872 nstr = ApplyModifiers(nstr, tstr, startc, endc,
3887 v, ctxt, flags, &used, freePtr); 3873 v, ctxt, flags, &used, freePtr);
3888 tstr += used; 3874 tstr += used;
3889 free(extraFree); 3875 free(extraFree);
3890 } else { 3876 } else {
3891 *freePtr = extraFree; 3877 *freePtr = extraFree;
3892 } 3878 }
3893 } 3879 }
3894 *lengthPtr = tstr - start + (*tstr ? 1 : 0); 3880 *lengthPtr = tstr - start + (*tstr ? 1 : 0);
3895 3881
3896 if (v->flags & VAR_FROM_ENV) { 3882 if (v->flags & VAR_FROM_ENV) {
3897 Boolean destroy = FALSE; 3883 Boolean destroy = FALSE;
3898 3884
3899 if (nstr != Buf_GetAll(&v->val, NULL)) { 3885 if (nstr != Buf_GetAll(&v->val, NULL)) {
3900 destroy = TRUE; 3886 destroy = TRUE;
3901 } else { 3887 } else {
3902 /* 3888 /*
3903 * Returning the value unmodified, so tell the caller to free 3889 * Returning the value unmodified, so tell the caller to free
3904 * the thing. 3890 * the thing.
3905 */ 3891 */
3906 *freePtr = nstr; 3892 *freePtr = nstr;
3907 } 3893 }
3908 VarFreeEnv(v, destroy); 3894 VarFreeEnv(v, destroy);
3909 } else if (v->flags & VAR_JUNK) { 3895 } else if (v->flags & VAR_JUNK) {
3910 /* 3896 /*
@@ -3979,27 +3965,27 @@ Var_Subst(const char *var, const char *s @@ -3979,27 +3965,27 @@ Var_Subst(const char *var, const char *s
3979 * In such a case, we skip over the escape character and store the 3965 * In such a case, we skip over the escape character and store the
3980 * dollar sign into the buffer directly. 3966 * dollar sign into the buffer directly.
3981 */ 3967 */
3982 if (save_dollars && (flags & VARF_ASSIGN)) 3968 if (save_dollars && (flags & VARF_ASSIGN))
3983 Buf_AddByte(&buf, *str); 3969 Buf_AddByte(&buf, *str);
3984 str++; 3970 str++;
3985 Buf_AddByte(&buf, *str); 3971 Buf_AddByte(&buf, *str);
3986 str++; 3972 str++;
3987 } else if (*str != '$') { 3973 } else if (*str != '$') {
3988 /* 3974 /*
3989 * Skip as many characters as possible -- either to the end of 3975 * Skip as many characters as possible -- either to the end of
3990 * the string or to the next dollar sign (variable invocation). 3976 * the string or to the next dollar sign (variable invocation).
3991 */ 3977 */
3992 const char *cp; 3978 const char *cp;
3993 3979
3994 for (cp = str++; *str != '$' && *str != '\0'; str++) 3980 for (cp = str++; *str != '$' && *str != '\0'; str++)
3995 continue; 3981 continue;
3996 Buf_AddBytes(&buf, str - cp, cp); 3982 Buf_AddBytes(&buf, str - cp, cp);
3997 } else { 3983 } else {
3998 if (var != NULL) { 3984 if (var != NULL) {
3999 int expand; 3985 int expand;
4000 for (;;) { 3986 for (;;) {
4001 if (str[1] == '\0') { 3987 if (str[1] == '\0') {
4002 /* A trailing $ is kind of a special case */ 3988 /* A trailing $ is kind of a special case */
4003 Buf_AddByte(&buf, str[0]); 3989 Buf_AddByte(&buf, str[0]);
4004 str++; 3990 str++;
4005 expand = FALSE; 3991 expand = FALSE;
@@ -4026,27 +4012,27 @@ Var_Subst(const char *var, const char *s @@ -4026,27 +4012,27 @@ Var_Subst(const char *var, const char *s
4026 */ 4012 */
4027 if (*p == '$') { 4013 if (*p == '$') {
4028 Buf_AddBytes(&buf, p - str, str); 4014 Buf_AddBytes(&buf, p - str, str);
4029 str = p; 4015 str = p;
4030 continue; 4016 continue;
4031 } 4017 }
4032 4018
4033 if (strncmp(var, str + 2, p - str - 2) != 0 || 4019 if (strncmp(var, str + 2, p - str - 2) != 0 ||
4034 var[p - str - 2] != '\0') { 4020 var[p - str - 2] != '\0') {
4035 /* 4021 /*
4036 * Not the variable we want to expand, scan 4022 * Not the variable we want to expand, scan
4037 * until the next variable 4023 * until the next variable
4038 */ 4024 */
4039 for (;*p != '$' && *p != '\0'; p++) 4025 for (; *p != '$' && *p != '\0'; p++)
4040 continue; 4026 continue;
4041 Buf_AddBytes(&buf, p - str, str); 4027 Buf_AddBytes(&buf, p - str, str);
4042 str = p; 4028 str = p;
4043 expand = FALSE; 4029 expand = FALSE;
4044 } else 4030 } else
4045 expand = TRUE; 4031 expand = TRUE;
4046 break; 4032 break;
4047 } 4033 }
4048 } 4034 }
4049 if (!expand) 4035 if (!expand)
4050 continue; 4036 continue;
4051 } 4037 }
4052 4038