Mon Dec 21 00:30:13 2020 UTC ()
make(1): save a few memory allocations in variable expressions


(rillig)
diff -r1.758 -r1.759 src/usr.bin/make/var.c

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

--- src/usr.bin/make/var.c 2020/12/21 00:20:58 1.758
+++ src/usr.bin/make/var.c 2020/12/21 00:30:13 1.759
@@ -1,14 +1,14 @@ @@ -1,14 +1,14 @@
1/* $NetBSD: var.c,v 1.758 2020/12/21 00:20:58 rillig Exp $ */ 1/* $NetBSD: var.c,v 1.759 2020/12/21 00:30:13 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.
@@ -121,27 +121,27 @@ @@ -121,27 +121,27 @@
121#include <regex.h> 121#include <regex.h>
122#endif 122#endif
123#include <errno.h> 123#include <errno.h>
124#include <inttypes.h> 124#include <inttypes.h>
125#include <limits.h> 125#include <limits.h>
126#include <time.h> 126#include <time.h>
127 127
128#include "make.h" 128#include "make.h"
129#include "dir.h" 129#include "dir.h"
130#include "job.h" 130#include "job.h"
131#include "metachar.h" 131#include "metachar.h"
132 132
133/* "@(#)var.c 8.3 (Berkeley) 3/19/94" */ 133/* "@(#)var.c 8.3 (Berkeley) 3/19/94" */
134MAKE_RCSID("$NetBSD: var.c,v 1.758 2020/12/21 00:20:58 rillig Exp $"); 134MAKE_RCSID("$NetBSD: var.c,v 1.759 2020/12/21 00:30:13 rillig Exp $");
135 135
136typedef enum VarFlags { 136typedef enum VarFlags {
137 VAR_NONE = 0, 137 VAR_NONE = 0,
138 138
139 /* 139 /*
140 * The variable's value is currently being used by Var_Parse or 140 * The variable's value is currently being used by Var_Parse or
141 * Var_Subst. This marker is used to avoid endless recursion. 141 * Var_Subst. This marker is used to avoid endless recursion.
142 */ 142 */
143 VAR_IN_USE = 0x01, 143 VAR_IN_USE = 0x01,
144 144
145 /* 145 /*
146 * The variable comes from the environment. 146 * The variable comes from the environment.
147 * These variables are not registered in any GNode, therefore they 147 * These variables are not registered in any GNode, therefore they
@@ -2422,27 +2422,27 @@ ApplyModifier_ShellCommand(const char ** @@ -2422,27 +2422,27 @@ ApplyModifier_ShellCommand(const char **
2422 const char *errfmt; 2422 const char *errfmt;
2423 VarParseResult res; 2423 VarParseResult res;
2424 2424
2425 (*pp)++; 2425 (*pp)++;
2426 res = ParseModifierPart(pp, '!', st->eflags, st, 2426 res = ParseModifierPart(pp, '!', st->eflags, st,
2427 &cmd, NULL, NULL, NULL); 2427 &cmd, NULL, NULL, NULL);
2428 if (res != VPR_OK) 2428 if (res != VPR_OK)
2429 return AMR_CLEANUP; 2429 return AMR_CLEANUP;
2430 2430
2431 errfmt = NULL; 2431 errfmt = NULL;
2432 if (st->eflags & VARE_WANTRES) 2432 if (st->eflags & VARE_WANTRES)
2433 st->newVal = FStr_InitOwn(Cmd_Exec(cmd, &errfmt)); 2433 st->newVal = FStr_InitOwn(Cmd_Exec(cmd, &errfmt));
2434 else 2434 else
2435 st->newVal = FStr_InitOwn(bmake_strdup("")); 2435 st->newVal = FStr_InitRefer("");
2436 if (errfmt != NULL) 2436 if (errfmt != NULL)
2437 Error(errfmt, cmd); /* XXX: why still return AMR_OK? */ 2437 Error(errfmt, cmd); /* XXX: why still return AMR_OK? */
2438 free(cmd); 2438 free(cmd);
2439 2439
2440 ApplyModifiersState_Define(st); 2440 ApplyModifiersState_Define(st);
2441 return AMR_OK; 2441 return AMR_OK;
2442} 2442}
2443 2443
2444/* The :range modifier generates an integer sequence as long as the words. 2444/* The :range modifier generates an integer sequence as long as the words.
2445 * The :range=7 modifier generates an integer sequence from 1 to 7. */ 2445 * The :range=7 modifier generates an integer sequence from 1 to 7. */
2446static ApplyModifierResult 2446static ApplyModifierResult
2447ApplyModifier_Range(const char **pp, const char *val, ApplyModifiersState *st) 2447ApplyModifier_Range(const char **pp, const char *val, ApplyModifiersState *st)
2448{ 2448{
@@ -2889,27 +2889,27 @@ ApplyModifier_Words(const char **pp, con @@ -2889,27 +2889,27 @@ ApplyModifier_Words(const char **pp, con
2889 &estr, NULL, NULL, NULL); 2889 &estr, NULL, NULL, NULL);
2890 if (res != VPR_OK) 2890 if (res != VPR_OK)
2891 return AMR_CLEANUP; 2891 return AMR_CLEANUP;
2892 2892
2893 /* now *pp points just after the closing ']' */ 2893 /* now *pp points just after the closing ']' */
2894 if (**pp != ':' && **pp != st->endc) 2894 if (**pp != ':' && **pp != st->endc)
2895 goto bad_modifier; /* Found junk after ']' */ 2895 goto bad_modifier; /* Found junk after ']' */
2896 2896
2897 if (estr[0] == '\0') 2897 if (estr[0] == '\0')
2898 goto bad_modifier; /* empty square brackets in ":[]". */ 2898 goto bad_modifier; /* empty square brackets in ":[]". */
2899 2899
2900 if (estr[0] == '#' && estr[1] == '\0') { /* Found ":[#]" */ 2900 if (estr[0] == '#' && estr[1] == '\0') { /* Found ":[#]" */
2901 if (st->oneBigWord) { 2901 if (st->oneBigWord) {
2902 st->newVal = FStr_InitOwn(bmake_strdup("1")); 2902 st->newVal = FStr_InitRefer("1");
2903 } else { 2903 } else {
2904 Buffer buf; 2904 Buffer buf;
2905 2905
2906 Words words = Str_Words(val, FALSE); 2906 Words words = Str_Words(val, FALSE);
2907 size_t ac = words.len; 2907 size_t ac = words.len;
2908 Words_Free(words); 2908 Words_Free(words);
2909 2909
2910 /* 3 digits + '\0' is usually enough */ 2910 /* 3 digits + '\0' is usually enough */
2911 Buf_InitSize(&buf, 4); 2911 Buf_InitSize(&buf, 4);
2912 Buf_AddInt(&buf, (int)ac); 2912 Buf_AddInt(&buf, (int)ac);
2913 st->newVal = FStr_InitOwn(Buf_Destroy(&buf, FALSE)); 2913 st->newVal = FStr_InitOwn(Buf_Destroy(&buf, FALSE));
2914 } 2914 }
2915 goto ok; 2915 goto ok;
@@ -3167,27 +3167,27 @@ ok: @@ -3167,27 +3167,27 @@ ok:
3167 free(cmd_output); 3167 free(cmd_output);
3168 break; 3168 break;
3169 } 3169 }
3170 case '?': 3170 case '?':
3171 if (!(st->exprFlags & VEF_UNDEF)) 3171 if (!(st->exprFlags & VEF_UNDEF))
3172 break; 3172 break;
3173 /* FALLTHROUGH */ 3173 /* FALLTHROUGH */
3174 default: 3174 default:
3175 Var_Set(st->var->name.str, val, ctxt); 3175 Var_Set(st->var->name.str, val, ctxt);
3176 break; 3176 break;
3177 } 3177 }
3178 } 3178 }
3179 free(val); 3179 free(val);
3180 st->newVal = FStr_InitOwn(bmake_strdup("")); 3180 st->newVal = FStr_InitRefer("");
3181 return AMR_OK; 3181 return AMR_OK;
3182} 3182}
3183 3183
3184/* :_=... 3184/* :_=...
3185 * remember current value */ 3185 * remember current value */
3186static ApplyModifierResult 3186static ApplyModifierResult
3187ApplyModifier_Remember(const char **pp, const char *val, 3187ApplyModifier_Remember(const char **pp, const char *val,
3188 ApplyModifiersState *st) 3188 ApplyModifiersState *st)
3189{ 3189{
3190 const char *mod = *pp; 3190 const char *mod = *pp;
3191 if (!ModMatchEq(mod, "_", st->endc)) 3191 if (!ModMatchEq(mod, "_", st->endc))
3192 return AMR_UNKNOWN; 3192 return AMR_UNKNOWN;
3193 3193
@@ -3293,27 +3293,27 @@ ApplyModifier_SysV(const char **pp, cons @@ -3293,27 +3293,27 @@ ApplyModifier_SysV(const char **pp, cons
3293/* :sh */ 3293/* :sh */
3294static ApplyModifierResult 3294static ApplyModifierResult
3295ApplyModifier_SunShell(const char **pp, const char *val, 3295ApplyModifier_SunShell(const char **pp, const char *val,
3296 ApplyModifiersState *st) 3296 ApplyModifiersState *st)
3297{ 3297{
3298 const char *p = *pp; 3298 const char *p = *pp;
3299 if (p[1] == 'h' && (p[2] == st->endc || p[2] == ':')) { 3299 if (p[1] == 'h' && (p[2] == st->endc || p[2] == ':')) {
3300 if (st->eflags & VARE_WANTRES) { 3300 if (st->eflags & VARE_WANTRES) {
3301 const char *errfmt; 3301 const char *errfmt;
3302 st->newVal = FStr_InitOwn(Cmd_Exec(val, &errfmt)); 3302 st->newVal = FStr_InitOwn(Cmd_Exec(val, &errfmt));
3303 if (errfmt != NULL) 3303 if (errfmt != NULL)
3304 Error(errfmt, val); 3304 Error(errfmt, val);
3305 } else 3305 } else
3306 st->newVal = FStr_InitOwn(bmake_strdup("")); 3306 st->newVal = FStr_InitRefer("");
3307 *pp = p + 2; 3307 *pp = p + 2;
3308 return AMR_OK; 3308 return AMR_OK;
3309 } else 3309 } else
3310 return AMR_UNKNOWN; 3310 return AMR_UNKNOWN;
3311} 3311}
3312#endif 3312#endif
3313 3313
3314static void 3314static void
3315LogBeforeApply(const ApplyModifiersState *st, const char *mod, char endc, 3315LogBeforeApply(const ApplyModifiersState *st, const char *mod, char endc,
3316 const char *val) 3316 const char *val)
3317{ 3317{
3318 char eflags_str[VarEvalFlags_ToStringSize]; 3318 char eflags_str[VarEvalFlags_ToStringSize];
3319 char vflags_str[VarFlags_ToStringSize]; 3319 char vflags_str[VarFlags_ToStringSize];