make: revert part of previous commit
That code was not ready yet.
This commit is contained in:
parent
62b202434d
commit
b37a044ff1
@ -1,4 +1,4 @@
|
|||||||
/* $NetBSD: var.c,v 1.814 2021/02/14 17:24:47 rillig Exp $ */
|
/* $NetBSD: var.c,v 1.815 2021/02/14 17:27:25 rillig Exp $ */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 1988, 1989, 1990, 1993
|
* Copyright (c) 1988, 1989, 1990, 1993
|
||||||
@ -139,7 +139,7 @@
|
|||||||
#include "metachar.h"
|
#include "metachar.h"
|
||||||
|
|
||||||
/* "@(#)var.c 8.3 (Berkeley) 3/19/94" */
|
/* "@(#)var.c 8.3 (Berkeley) 3/19/94" */
|
||||||
MAKE_RCSID("$NetBSD: var.c,v 1.814 2021/02/14 17:24:47 rillig Exp $");
|
MAKE_RCSID("$NetBSD: var.c,v 1.815 2021/02/14 17:27:25 rillig Exp $");
|
||||||
|
|
||||||
typedef enum VarFlags {
|
typedef enum VarFlags {
|
||||||
VAR_NONE = 0,
|
VAR_NONE = 0,
|
||||||
@ -2087,30 +2087,25 @@ typedef struct ApplyModifiersState {
|
|||||||
VarExprStatus exprStatus;
|
VarExprStatus exprStatus;
|
||||||
} ApplyModifiersState;
|
} ApplyModifiersState;
|
||||||
|
|
||||||
/*
|
typedef ApplyModifiersState Expr;
|
||||||
* A variable expression such as $@ or ${VAR:Mpattern:Q}.
|
|
||||||
*/
|
|
||||||
typedef struct Expr {
|
|
||||||
ApplyModifiersState *st; /* only during ApplyModifiers */
|
|
||||||
} Expr;
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
Expr_Define(Expr *expr)
|
Expr_Define(Expr *expr)
|
||||||
{
|
{
|
||||||
if (expr->st->exprStatus == VES_UNDEF)
|
if (expr->exprStatus == VES_UNDEF)
|
||||||
expr->st->exprStatus = VES_DEF;
|
expr->exprStatus = VES_DEF;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
Expr_SetValueOwn(Expr *expr, char *value)
|
Expr_SetValueOwn(Expr *expr, char *value)
|
||||||
{
|
{
|
||||||
expr->st->newValue = FStr_InitOwn(value);
|
expr->newValue = FStr_InitOwn(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
Expr_SetValueRefer(Expr *expr, const char *value)
|
Expr_SetValueRefer(Expr *expr, const char *value)
|
||||||
{
|
{
|
||||||
expr->st->newValue = FStr_InitRefer(value);
|
expr->newValue = FStr_InitRefer(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
typedef enum ApplyModifierResult {
|
typedef enum ApplyModifierResult {
|
||||||
@ -2145,7 +2140,7 @@ ParseModifierPartSubst(
|
|||||||
const char **pp,
|
const char **pp,
|
||||||
char delim,
|
char delim,
|
||||||
VarEvalFlags eflags,
|
VarEvalFlags eflags,
|
||||||
Expr *expr,
|
ApplyModifiersState *st,
|
||||||
char **out_part,
|
char **out_part,
|
||||||
/* Optionally stores the length of the returned string, just to save
|
/* Optionally stores the length of the returned string, just to save
|
||||||
* another strlen call. */
|
* another strlen call. */
|
||||||
@ -2158,7 +2153,6 @@ ParseModifierPartSubst(
|
|||||||
struct ModifyWord_SubstArgs *subst
|
struct ModifyWord_SubstArgs *subst
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
Buffer buf;
|
Buffer buf;
|
||||||
const char *p;
|
const char *p;
|
||||||
|
|
||||||
@ -2287,11 +2281,11 @@ ParseModifierPart(
|
|||||||
/* Flags for evaluating nested variables; if VARE_WANTRES is not set,
|
/* Flags for evaluating nested variables; if VARE_WANTRES is not set,
|
||||||
* the text is only parsed. */
|
* the text is only parsed. */
|
||||||
VarEvalFlags eflags,
|
VarEvalFlags eflags,
|
||||||
Expr *expr,
|
ApplyModifiersState *st,
|
||||||
char **out_part
|
char **out_part
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
return ParseModifierPartSubst(pp, delim, eflags, expr, out_part,
|
return ParseModifierPartSubst(pp, delim, eflags, st, out_part,
|
||||||
NULL, NULL, NULL);
|
NULL, NULL, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2375,9 +2369,8 @@ TryParseChar(const char **pp, int base, char *out_ch)
|
|||||||
|
|
||||||
/* :@var@...${var}...@ */
|
/* :@var@...${var}...@ */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Loop(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Loop(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
struct ModifyWord_LoopArgs args;
|
struct ModifyWord_LoopArgs args;
|
||||||
char prev_sep;
|
char prev_sep;
|
||||||
VarParseResult res;
|
VarParseResult res;
|
||||||
@ -2385,7 +2378,7 @@ ApplyModifier_Loop(const char **pp, const char *val, Expr *expr)
|
|||||||
args.scope = st->scope;
|
args.scope = st->scope;
|
||||||
|
|
||||||
(*pp)++; /* Skip the first '@' */
|
(*pp)++; /* Skip the first '@' */
|
||||||
res = ParseModifierPart(pp, '@', VARE_NONE, expr, &args.tvar);
|
res = ParseModifierPart(pp, '@', VARE_NONE, st, &args.tvar);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
if (opts.strict && strchr(args.tvar, '$') != NULL) {
|
if (opts.strict && strchr(args.tvar, '$') != NULL) {
|
||||||
@ -2396,14 +2389,14 @@ ApplyModifier_Loop(const char **pp, const char *val, Expr *expr)
|
|||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
}
|
}
|
||||||
|
|
||||||
res = ParseModifierPart(pp, '@', VARE_NONE, expr, &args.str);
|
res = ParseModifierPart(pp, '@', VARE_NONE, st, &args.str);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
args.eflags = st->eflags & ~(unsigned)VARE_KEEP_DOLLAR;
|
args.eflags = st->eflags & ~(unsigned)VARE_KEEP_DOLLAR;
|
||||||
prev_sep = st->sep;
|
prev_sep = st->sep;
|
||||||
st->sep = ' '; /* XXX: should be st->sep for consistency */
|
st->sep = ' '; /* XXX: should be st->sep for consistency */
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, ModifyWord_Loop, &args, st->oneBigWord, st->sep));
|
ModifyWords(val, ModifyWord_Loop, &args, st->oneBigWord, st->sep));
|
||||||
st->sep = prev_sep;
|
st->sep = prev_sep;
|
||||||
/* XXX: Consider restoring the previous variable instead of deleting. */
|
/* XXX: Consider restoring the previous variable instead of deleting. */
|
||||||
@ -2419,9 +2412,8 @@ ApplyModifier_Loop(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
/* :Ddefined or :Uundefined */
|
/* :Ddefined or :Uundefined */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Defined(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Defined(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
Buffer buf;
|
Buffer buf;
|
||||||
const char *p;
|
const char *p;
|
||||||
|
|
||||||
@ -2466,12 +2458,12 @@ ApplyModifier_Defined(const char **pp, const char *val, Expr *expr)
|
|||||||
}
|
}
|
||||||
*pp = p;
|
*pp = p;
|
||||||
|
|
||||||
Expr_Define(expr);
|
Expr_Define(st);
|
||||||
|
|
||||||
if (eflags & VARE_WANTRES) {
|
if (eflags & VARE_WANTRES) {
|
||||||
Expr_SetValueOwn(expr, Buf_DoneData(&buf));
|
Expr_SetValueOwn(st, Buf_DoneData(&buf));
|
||||||
} else {
|
} else {
|
||||||
Expr_SetValueRefer(expr, val);
|
Expr_SetValueRefer(st, val);
|
||||||
Buf_Done(&buf);
|
Buf_Done(&buf);
|
||||||
}
|
}
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
@ -2479,10 +2471,10 @@ ApplyModifier_Defined(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
/* :L */
|
/* :L */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Literal(const char **pp, Expr *expr)
|
ApplyModifier_Literal(const char **pp, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
Expr_Define(expr);
|
Expr_Define(st);
|
||||||
Expr_SetValueOwn(expr, bmake_strdup(expr->st->var->name.str));
|
Expr_SetValueOwn(st, bmake_strdup(st->var->name.str));
|
||||||
(*pp)++;
|
(*pp)++;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
@ -2508,12 +2500,12 @@ TryParseTime(const char **pp, time_t *out_time)
|
|||||||
|
|
||||||
/* :gmtime */
|
/* :gmtime */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Gmtime(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Gmtime(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
time_t utc;
|
time_t utc;
|
||||||
|
|
||||||
const char *mod = *pp;
|
const char *mod = *pp;
|
||||||
if (!ModMatchEq(mod, "gmtime", expr->st->endc))
|
if (!ModMatchEq(mod, "gmtime", st->endc))
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
|
|
||||||
if (mod[6] == '=') {
|
if (mod[6] == '=') {
|
||||||
@ -2528,19 +2520,19 @@ ApplyModifier_Gmtime(const char **pp, const char *val, Expr *expr)
|
|||||||
utc = 0;
|
utc = 0;
|
||||||
*pp = mod + 6;
|
*pp = mod + 6;
|
||||||
}
|
}
|
||||||
Expr_SetValueOwn(expr, VarStrftime(val, TRUE, utc));
|
Expr_SetValueOwn(st, VarStrftime(val, TRUE, utc));
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* :localtime */
|
/* :localtime */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Localtime(const char **pp, const char *val,
|
ApplyModifier_Localtime(const char **pp, const char *val,
|
||||||
Expr *expr)
|
ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
time_t utc;
|
time_t utc;
|
||||||
|
|
||||||
const char *mod = *pp;
|
const char *mod = *pp;
|
||||||
if (!ModMatchEq(mod, "localtime", expr->st->endc))
|
if (!ModMatchEq(mod, "localtime", st->endc))
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
|
|
||||||
if (mod[9] == '=') {
|
if (mod[9] == '=') {
|
||||||
@ -2555,31 +2547,30 @@ ApplyModifier_Localtime(const char **pp, const char *val,
|
|||||||
utc = 0;
|
utc = 0;
|
||||||
*pp = mod + 9;
|
*pp = mod + 9;
|
||||||
}
|
}
|
||||||
Expr_SetValueOwn(expr, VarStrftime(val, FALSE, utc));
|
Expr_SetValueOwn(st, VarStrftime(val, FALSE, utc));
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* :hash */
|
/* :hash */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Hash(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Hash(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
if (!ModMatch(*pp, "hash", expr->st->endc))
|
if (!ModMatch(*pp, "hash", st->endc))
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
|
|
||||||
Expr_SetValueOwn(expr, VarHash(val));
|
Expr_SetValueOwn(st, VarHash(val));
|
||||||
*pp += 4;
|
*pp += 4;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* :P */
|
/* :P */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Path(const char **pp, Expr *expr)
|
ApplyModifier_Path(const char **pp, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
GNode *gn;
|
GNode *gn;
|
||||||
char *path;
|
char *path;
|
||||||
|
|
||||||
Expr_Define(expr);
|
Expr_Define(st);
|
||||||
|
|
||||||
gn = Targ_FindNode(st->var->name.str);
|
gn = Targ_FindNode(st->var->name.str);
|
||||||
if (gn == NULL || gn->type & OP_NOPATH) {
|
if (gn == NULL || gn->type & OP_NOPATH) {
|
||||||
@ -2592,7 +2583,7 @@ ApplyModifier_Path(const char **pp, Expr *expr)
|
|||||||
}
|
}
|
||||||
if (path == NULL)
|
if (path == NULL)
|
||||||
path = bmake_strdup(st->var->name.str);
|
path = bmake_strdup(st->var->name.str);
|
||||||
Expr_SetValueOwn(expr, path);
|
Expr_SetValueOwn(st, path);
|
||||||
|
|
||||||
(*pp)++;
|
(*pp)++;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
@ -2600,28 +2591,27 @@ ApplyModifier_Path(const char **pp, Expr *expr)
|
|||||||
|
|
||||||
/* :!cmd! */
|
/* :!cmd! */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_ShellCommand(const char **pp, Expr *expr)
|
ApplyModifier_ShellCommand(const char **pp, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char *cmd;
|
char *cmd;
|
||||||
const char *errfmt;
|
const char *errfmt;
|
||||||
VarParseResult res;
|
VarParseResult res;
|
||||||
|
|
||||||
(*pp)++;
|
(*pp)++;
|
||||||
res = ParseModifierPart(pp, '!', st->eflags, expr, &cmd);
|
res = ParseModifierPart(pp, '!', st->eflags, st, &cmd);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
errfmt = NULL;
|
errfmt = NULL;
|
||||||
if (st->eflags & VARE_WANTRES)
|
if (st->eflags & VARE_WANTRES)
|
||||||
Expr_SetValueOwn(expr, Cmd_Exec(cmd, &errfmt));
|
Expr_SetValueOwn(st, Cmd_Exec(cmd, &errfmt));
|
||||||
else
|
else
|
||||||
Expr_SetValueRefer(expr, "");
|
Expr_SetValueRefer(st, "");
|
||||||
if (errfmt != NULL)
|
if (errfmt != NULL)
|
||||||
Error(errfmt, cmd); /* XXX: why still return AMR_OK? */
|
Error(errfmt, cmd); /* XXX: why still return AMR_OK? */
|
||||||
free(cmd);
|
free(cmd);
|
||||||
|
|
||||||
Expr_Define(expr);
|
Expr_Define(st);
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2630,9 +2620,8 @@ ApplyModifier_ShellCommand(const char **pp, Expr *expr)
|
|||||||
* The :range=7 modifier generates an integer sequence from 1 to 7.
|
* The :range=7 modifier generates an integer sequence from 1 to 7.
|
||||||
*/
|
*/
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Range(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Range(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
size_t n;
|
size_t n;
|
||||||
Buffer buf;
|
Buffer buf;
|
||||||
size_t i;
|
size_t i;
|
||||||
@ -2670,15 +2659,14 @@ ApplyModifier_Range(const char **pp, const char *val, Expr *expr)
|
|||||||
Buf_AddInt(&buf, 1 + (int)i);
|
Buf_AddInt(&buf, 1 + (int)i);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr_SetValueOwn(expr, Buf_DoneData(&buf));
|
Expr_SetValueOwn(st, Buf_DoneData(&buf));
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* :Mpattern or :Npattern */
|
/* :Mpattern or :Npattern */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Match(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Match(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *mod = *pp;
|
const char *mod = *pp;
|
||||||
Boolean copy = FALSE; /* pattern should be, or has been, copied */
|
Boolean copy = FALSE; /* pattern should be, or has been, copied */
|
||||||
Boolean needSubst = FALSE;
|
Boolean needSubst = FALSE;
|
||||||
@ -2748,7 +2736,7 @@ ApplyModifier_Match(const char **pp, const char *val, Expr *expr)
|
|||||||
st->var->name.str, val, pattern);
|
st->var->name.str, val, pattern);
|
||||||
|
|
||||||
callback = mod[0] == 'M' ? ModifyWord_Match : ModifyWord_NoMatch;
|
callback = mod[0] == 'M' ? ModifyWord_Match : ModifyWord_NoMatch;
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, callback, pattern, st->oneBigWord, st->sep));
|
ModifyWords(val, callback, pattern, st->oneBigWord, st->sep));
|
||||||
free(pattern);
|
free(pattern);
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
@ -2756,9 +2744,8 @@ ApplyModifier_Match(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
/* :S,from,to, */
|
/* :S,from,to, */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Subst(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Subst(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
struct ModifyWord_SubstArgs args;
|
struct ModifyWord_SubstArgs args;
|
||||||
char *lhs, *rhs;
|
char *lhs, *rhs;
|
||||||
Boolean oneBigWord;
|
Boolean oneBigWord;
|
||||||
@ -2785,13 +2772,13 @@ ApplyModifier_Subst(const char **pp, const char *val, Expr *expr)
|
|||||||
(*pp)++;
|
(*pp)++;
|
||||||
}
|
}
|
||||||
|
|
||||||
res = ParseModifierPartSubst(pp, delim, st->eflags, expr, &lhs,
|
res = ParseModifierPartSubst(pp, delim, st->eflags, st, &lhs,
|
||||||
&args.lhsLen, &args.pflags, NULL);
|
&args.lhsLen, &args.pflags, NULL);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
args.lhs = lhs;
|
args.lhs = lhs;
|
||||||
|
|
||||||
res = ParseModifierPartSubst(pp, delim, st->eflags, expr, &rhs,
|
res = ParseModifierPartSubst(pp, delim, st->eflags, st, &rhs,
|
||||||
&args.rhsLen, NULL, &args);
|
&args.rhsLen, NULL, &args);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
@ -2809,7 +2796,7 @@ ApplyModifier_Subst(const char **pp, const char *val, Expr *expr)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, ModifyWord_Subst, &args, oneBigWord, st->sep));
|
ModifyWords(val, ModifyWord_Subst, &args, oneBigWord, st->sep));
|
||||||
|
|
||||||
free(lhs);
|
free(lhs);
|
||||||
@ -2821,9 +2808,8 @@ ApplyModifier_Subst(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
/* :C,from,to, */
|
/* :C,from,to, */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Regex(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Regex(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char *re;
|
char *re;
|
||||||
struct ModifyWord_SubstRegexArgs args;
|
struct ModifyWord_SubstRegexArgs args;
|
||||||
Boolean oneBigWord;
|
Boolean oneBigWord;
|
||||||
@ -2839,11 +2825,11 @@ ApplyModifier_Regex(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
*pp += 2;
|
*pp += 2;
|
||||||
|
|
||||||
res = ParseModifierPart(pp, delim, st->eflags, expr, &re);
|
res = ParseModifierPart(pp, delim, st->eflags, st, &re);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
res = ParseModifierPart(pp, delim, st->eflags, expr, &args.replace);
|
res = ParseModifierPart(pp, delim, st->eflags, st, &args.replace);
|
||||||
if (args.replace == NULL) {
|
if (args.replace == NULL) {
|
||||||
free(re);
|
free(re);
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
@ -2874,7 +2860,7 @@ ApplyModifier_Regex(const char **pp, const char *val, Expr *expr)
|
|||||||
args.nsub = args.re.re_nsub + 1;
|
args.nsub = args.re.re_nsub + 1;
|
||||||
if (args.nsub > 10)
|
if (args.nsub > 10)
|
||||||
args.nsub = 10;
|
args.nsub = 10;
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, ModifyWord_SubstRegex, &args,
|
ModifyWords(val, ModifyWord_SubstRegex, &args,
|
||||||
oneBigWord, st->sep));
|
oneBigWord, st->sep));
|
||||||
regfree(&args.re);
|
regfree(&args.re);
|
||||||
@ -2886,10 +2872,10 @@ ApplyModifier_Regex(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
/* :Q, :q */
|
/* :Q, :q */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Quote(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Quote(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
if ((*pp)[1] == expr->st->endc || (*pp)[1] == ':') {
|
if ((*pp)[1] == st->endc || (*pp)[1] == ':') {
|
||||||
Expr_SetValueOwn(expr, VarQuote(val, **pp == 'q'));
|
Expr_SetValueOwn(st, VarQuote(val, **pp == 'q'));
|
||||||
(*pp)++;
|
(*pp)++;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
} else
|
} else
|
||||||
@ -2905,9 +2891,8 @@ ModifyWord_Copy(const char *word, SepBuf *buf, void *data MAKE_ATTR_UNUSED)
|
|||||||
|
|
||||||
/* :ts<separator> */
|
/* :ts<separator> */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_ToSep(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_ToSep(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *sep = *pp + 2;
|
const char *sep = *pp + 2;
|
||||||
|
|
||||||
/* ":ts<any><endc>" or ":ts<any>:" */
|
/* ":ts<any><endc>" or ":ts<any>:" */
|
||||||
@ -2971,7 +2956,7 @@ ApplyModifier_ToSep(const char **pp, const char *val, Expr *expr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
ok:
|
ok:
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, ModifyWord_Copy, NULL, st->oneBigWord, st->sep));
|
ModifyWords(val, ModifyWord_Copy, NULL, st->oneBigWord, st->sep));
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
@ -3006,9 +2991,8 @@ str_tolower(const char *str)
|
|||||||
|
|
||||||
/* :tA, :tu, :tl, :ts<separator>, etc. */
|
/* :tA, :tu, :tl, :ts<separator>, etc. */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_To(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_To(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *mod = *pp;
|
const char *mod = *pp;
|
||||||
assert(mod[0] == 't');
|
assert(mod[0] == 't');
|
||||||
|
|
||||||
@ -3018,7 +3002,7 @@ ApplyModifier_To(const char **pp, const char *val, Expr *expr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (mod[1] == 's')
|
if (mod[1] == 's')
|
||||||
return ApplyModifier_ToSep(pp, val, expr);
|
return ApplyModifier_ToSep(pp, val, st);
|
||||||
|
|
||||||
if (mod[2] != st->endc && mod[2] != ':') { /* :t<unrecognized> */
|
if (mod[2] != st->endc && mod[2] != ':') { /* :t<unrecognized> */
|
||||||
*pp = mod + 1;
|
*pp = mod + 1;
|
||||||
@ -3026,7 +3010,7 @@ ApplyModifier_To(const char **pp, const char *val, Expr *expr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (mod[1] == 'A') { /* :tA */
|
if (mod[1] == 'A') { /* :tA */
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, ModifyWord_Realpath, NULL,
|
ModifyWords(val, ModifyWord_Realpath, NULL,
|
||||||
st->oneBigWord, st->sep));
|
st->oneBigWord, st->sep));
|
||||||
*pp = mod + 2;
|
*pp = mod + 2;
|
||||||
@ -3034,20 +3018,20 @@ ApplyModifier_To(const char **pp, const char *val, Expr *expr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (mod[1] == 'u') { /* :tu */
|
if (mod[1] == 'u') { /* :tu */
|
||||||
Expr_SetValueOwn(expr, str_toupper(val));
|
Expr_SetValueOwn(st, str_toupper(val));
|
||||||
*pp = mod + 2;
|
*pp = mod + 2;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mod[1] == 'l') { /* :tl */
|
if (mod[1] == 'l') { /* :tl */
|
||||||
Expr_SetValueOwn(expr, str_tolower(val));
|
Expr_SetValueOwn(st, str_tolower(val));
|
||||||
*pp = mod + 2;
|
*pp = mod + 2;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mod[1] == 'W' || mod[1] == 'w') { /* :tW, :tw */
|
if (mod[1] == 'W' || mod[1] == 'w') { /* :tW, :tw */
|
||||||
st->oneBigWord = mod[1] == 'W';
|
st->oneBigWord = mod[1] == 'W';
|
||||||
Expr_SetValueRefer(expr, val);
|
Expr_SetValueRefer(st, val);
|
||||||
*pp = mod + 2;
|
*pp = mod + 2;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
@ -3059,16 +3043,15 @@ ApplyModifier_To(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
/* :[#], :[1], :[-1..1], etc. */
|
/* :[#], :[1], :[-1..1], etc. */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Words(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Words(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char *estr;
|
char *estr;
|
||||||
int first, last;
|
int first, last;
|
||||||
VarParseResult res;
|
VarParseResult res;
|
||||||
const char *p;
|
const char *p;
|
||||||
|
|
||||||
(*pp)++; /* skip the '[' */
|
(*pp)++; /* skip the '[' */
|
||||||
res = ParseModifierPart(pp, ']', st->eflags, expr, &estr);
|
res = ParseModifierPart(pp, ']', st->eflags, st, &estr);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
@ -3080,7 +3063,7 @@ ApplyModifier_Words(const char **pp, const char *val, Expr *expr)
|
|||||||
|
|
||||||
if (estr[0] == '#' && estr[1] == '\0') { /* Found ":[#]" */
|
if (estr[0] == '#' && estr[1] == '\0') { /* Found ":[#]" */
|
||||||
if (st->oneBigWord) {
|
if (st->oneBigWord) {
|
||||||
Expr_SetValueRefer(expr, "1");
|
Expr_SetValueRefer(st, "1");
|
||||||
} else {
|
} else {
|
||||||
Buffer buf;
|
Buffer buf;
|
||||||
|
|
||||||
@ -3091,20 +3074,20 @@ ApplyModifier_Words(const char **pp, const char *val, Expr *expr)
|
|||||||
/* 3 digits + '\0' is usually enough */
|
/* 3 digits + '\0' is usually enough */
|
||||||
Buf_InitSize(&buf, 4);
|
Buf_InitSize(&buf, 4);
|
||||||
Buf_AddInt(&buf, (int)ac);
|
Buf_AddInt(&buf, (int)ac);
|
||||||
Expr_SetValueOwn(expr, Buf_DoneData(&buf));
|
Expr_SetValueOwn(st, Buf_DoneData(&buf));
|
||||||
}
|
}
|
||||||
goto ok;
|
goto ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (estr[0] == '*' && estr[1] == '\0') { /* Found ":[*]" */
|
if (estr[0] == '*' && estr[1] == '\0') { /* Found ":[*]" */
|
||||||
st->oneBigWord = TRUE;
|
st->oneBigWord = TRUE;
|
||||||
Expr_SetValueRefer(expr, val);
|
Expr_SetValueRefer(st, val);
|
||||||
goto ok;
|
goto ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (estr[0] == '@' && estr[1] == '\0') { /* Found ":[@]" */
|
if (estr[0] == '@' && estr[1] == '\0') { /* Found ":[@]" */
|
||||||
st->oneBigWord = FALSE;
|
st->oneBigWord = FALSE;
|
||||||
Expr_SetValueRefer(expr, val);
|
Expr_SetValueRefer(st, val);
|
||||||
goto ok;
|
goto ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3133,7 +3116,7 @@ ApplyModifier_Words(const char **pp, const char *val, Expr *expr)
|
|||||||
if (first == 0 && last == 0) {
|
if (first == 0 && last == 0) {
|
||||||
/* ":[0]" or perhaps ":[0..0]" */
|
/* ":[0]" or perhaps ":[0..0]" */
|
||||||
st->oneBigWord = TRUE;
|
st->oneBigWord = TRUE;
|
||||||
Expr_SetValueRefer(expr, val);
|
Expr_SetValueRefer(st, val);
|
||||||
goto ok;
|
goto ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3142,7 +3125,7 @@ ApplyModifier_Words(const char **pp, const char *val, Expr *expr)
|
|||||||
goto bad_modifier;
|
goto bad_modifier;
|
||||||
|
|
||||||
/* Normal case: select the words described by first and last. */
|
/* Normal case: select the words described by first and last. */
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
VarSelectWords(st->sep, st->oneBigWord, val, first, last));
|
VarSelectWords(st->sep, st->oneBigWord, val, first, last));
|
||||||
|
|
||||||
ok:
|
ok:
|
||||||
@ -3181,9 +3164,8 @@ ShuffleStrings(char **strs, size_t n)
|
|||||||
|
|
||||||
/* :O (order ascending) or :Or (order descending) or :Ox (shuffle) */
|
/* :O (order ascending) or :Or (order descending) or :Ox (shuffle) */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Order(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Order(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *mod = (*pp)++; /* skip past the 'O' in any case */
|
const char *mod = (*pp)++; /* skip past the 'O' in any case */
|
||||||
|
|
||||||
Words words = Str_Words(val, FALSE);
|
Words words = Str_Words(val, FALSE);
|
||||||
@ -3207,15 +3189,14 @@ ApplyModifier_Order(const char **pp, const char *val, Expr *expr)
|
|||||||
return AMR_BAD;
|
return AMR_BAD;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr_SetValueOwn(expr, Words_JoinFree(words));
|
Expr_SetValueOwn(st, Words_JoinFree(words));
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* :? then : else */
|
/* :? then : else */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_IfElse(const char **pp, Expr *expr)
|
ApplyModifier_IfElse(const char **pp, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char *then_expr, *else_expr;
|
char *then_expr, *else_expr;
|
||||||
VarParseResult res;
|
VarParseResult res;
|
||||||
|
|
||||||
@ -3233,11 +3214,11 @@ ApplyModifier_IfElse(const char **pp, Expr *expr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
(*pp)++; /* skip past the '?' */
|
(*pp)++; /* skip past the '?' */
|
||||||
res = ParseModifierPart(pp, ':', then_eflags, expr, &then_expr);
|
res = ParseModifierPart(pp, ':', then_eflags, st, &then_expr);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
res = ParseModifierPart(pp, st->endc, else_eflags, expr, &else_expr);
|
res = ParseModifierPart(pp, st->endc, else_eflags, st, &else_expr);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
@ -3250,13 +3231,13 @@ ApplyModifier_IfElse(const char **pp, Expr *expr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (value) {
|
if (value) {
|
||||||
Expr_SetValueOwn(expr, then_expr);
|
Expr_SetValueOwn(st, then_expr);
|
||||||
free(else_expr);
|
free(else_expr);
|
||||||
} else {
|
} else {
|
||||||
Expr_SetValueOwn(expr, else_expr);
|
Expr_SetValueOwn(st, else_expr);
|
||||||
free(then_expr);
|
free(then_expr);
|
||||||
}
|
}
|
||||||
Expr_Define(expr);
|
Expr_Define(st);
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3283,9 +3264,8 @@ ApplyModifier_IfElse(const char **pp, Expr *expr)
|
|||||||
* variable.
|
* variable.
|
||||||
*/
|
*/
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Assign(const char **pp, Expr *expr)
|
ApplyModifier_Assign(const char **pp, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
GNode *scope;
|
GNode *scope;
|
||||||
char *val;
|
char *val;
|
||||||
VarParseResult res;
|
VarParseResult res;
|
||||||
@ -3325,7 +3305,7 @@ ok:
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
res = ParseModifierPart(pp, st->endc, st->eflags, expr, &val);
|
res = ParseModifierPart(pp, st->endc, st->eflags, st, &val);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
@ -3358,7 +3338,7 @@ ok:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
free(val);
|
free(val);
|
||||||
Expr_SetValueRefer(expr, "");
|
Expr_SetValueRefer(st, "");
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3368,9 +3348,8 @@ ok:
|
|||||||
*/
|
*/
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Remember(const char **pp, const char *val,
|
ApplyModifier_Remember(const char **pp, const char *val,
|
||||||
Expr *expr)
|
ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *mod = *pp;
|
const char *mod = *pp;
|
||||||
if (!ModMatchEq(mod, "_", st->endc))
|
if (!ModMatchEq(mod, "_", st->endc))
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
@ -3385,7 +3364,7 @@ ApplyModifier_Remember(const char **pp, const char *val,
|
|||||||
Var_Set(st->scope, "_", val);
|
Var_Set(st->scope, "_", val);
|
||||||
*pp = mod + 1;
|
*pp = mod + 1;
|
||||||
}
|
}
|
||||||
Expr_SetValueRefer(expr, val);
|
Expr_SetValueRefer(st, val);
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3395,25 +3374,23 @@ ApplyModifier_Remember(const char **pp, const char *val,
|
|||||||
*/
|
*/
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_WordFunc(const char **pp, const char *val,
|
ApplyModifier_WordFunc(const char **pp, const char *val,
|
||||||
Expr *expr, ModifyWordsCallback modifyWord)
|
ApplyModifiersState *st, ModifyWordsCallback modifyWord)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char delim = (*pp)[1];
|
char delim = (*pp)[1];
|
||||||
if (delim != st->endc && delim != ':')
|
if (delim != st->endc && delim != ':')
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
|
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, modifyWord, NULL, st->oneBigWord, st->sep));
|
ModifyWords(val, modifyWord, NULL, st->oneBigWord, st->sep));
|
||||||
(*pp)++;
|
(*pp)++;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_Unique(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_Unique(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
if ((*pp)[1] == st->endc || (*pp)[1] == ':') {
|
if ((*pp)[1] == st->endc || (*pp)[1] == ':') {
|
||||||
Expr_SetValueOwn(expr, VarUniq(val));
|
Expr_SetValueOwn(st, VarUniq(val));
|
||||||
(*pp)++;
|
(*pp)++;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
} else
|
} else
|
||||||
@ -3423,9 +3400,8 @@ ApplyModifier_Unique(const char **pp, const char *val, Expr *expr)
|
|||||||
#ifdef SYSVVARSUB
|
#ifdef SYSVVARSUB
|
||||||
/* :from=to */
|
/* :from=to */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_SysV(const char **pp, const char *val, Expr *expr)
|
ApplyModifier_SysV(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char *lhs, *rhs;
|
char *lhs, *rhs;
|
||||||
VarParseResult res;
|
VarParseResult res;
|
||||||
|
|
||||||
@ -3452,22 +3428,22 @@ ApplyModifier_SysV(const char **pp, const char *val, Expr *expr)
|
|||||||
if (*p != st->endc || !eqFound)
|
if (*p != st->endc || !eqFound)
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
|
|
||||||
res = ParseModifierPart(pp, '=', st->eflags, expr, &lhs);
|
res = ParseModifierPart(pp, '=', st->eflags, st, &lhs);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
/* The SysV modifier lasts until the end of the variable expression. */
|
/* The SysV modifier lasts until the end of the variable expression. */
|
||||||
res = ParseModifierPart(pp, st->endc, st->eflags, expr, &rhs);
|
res = ParseModifierPart(pp, st->endc, st->eflags, st, &rhs);
|
||||||
if (res != VPR_OK)
|
if (res != VPR_OK)
|
||||||
return AMR_CLEANUP;
|
return AMR_CLEANUP;
|
||||||
|
|
||||||
(*pp)--; /* Go back to the st->endc. */
|
(*pp)--; /* Go back to the st->endc. */
|
||||||
|
|
||||||
if (lhs[0] == '\0' && val[0] == '\0') {
|
if (lhs[0] == '\0' && val[0] == '\0') {
|
||||||
Expr_SetValueRefer(expr, val); /* special case */
|
Expr_SetValueRefer(st, val); /* special case */
|
||||||
} else {
|
} else {
|
||||||
struct ModifyWord_SYSVSubstArgs args = { st->scope, lhs, rhs };
|
struct ModifyWord_SYSVSubstArgs args = { st->scope, lhs, rhs };
|
||||||
Expr_SetValueOwn(expr,
|
Expr_SetValueOwn(st,
|
||||||
ModifyWords(val, ModifyWord_SYSVSubst, &args,
|
ModifyWords(val, ModifyWord_SYSVSubst, &args,
|
||||||
st->oneBigWord, st->sep));
|
st->oneBigWord, st->sep));
|
||||||
}
|
}
|
||||||
@ -3481,18 +3457,17 @@ ApplyModifier_SysV(const char **pp, const char *val, Expr *expr)
|
|||||||
/* :sh */
|
/* :sh */
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier_SunShell(const char **pp, const char *val,
|
ApplyModifier_SunShell(const char **pp, const char *val,
|
||||||
Expr *expr)
|
ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *p = *pp;
|
const char *p = *pp;
|
||||||
if (p[1] == 'h' && (p[2] == st->endc || p[2] == ':')) {
|
if (p[1] == 'h' && (p[2] == st->endc || p[2] == ':')) {
|
||||||
if (st->eflags & VARE_WANTRES) {
|
if (st->eflags & VARE_WANTRES) {
|
||||||
const char *errfmt;
|
const char *errfmt;
|
||||||
Expr_SetValueOwn(expr, Cmd_Exec(val, &errfmt));
|
Expr_SetValueOwn(st, Cmd_Exec(val, &errfmt));
|
||||||
if (errfmt != NULL)
|
if (errfmt != NULL)
|
||||||
Error(errfmt, val);
|
Error(errfmt, val);
|
||||||
} else
|
} else
|
||||||
Expr_SetValueRefer(expr, "");
|
Expr_SetValueRefer(st, "");
|
||||||
*pp = p + 2;
|
*pp = p + 2;
|
||||||
return AMR_OK;
|
return AMR_OK;
|
||||||
} else
|
} else
|
||||||
@ -3501,10 +3476,9 @@ ApplyModifier_SunShell(const char **pp, const char *val,
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
static void
|
static void
|
||||||
LogBeforeApply(const Expr *expr, const char *mod, char endc,
|
LogBeforeApply(const ApplyModifiersState *st, const char *mod, char endc,
|
||||||
const char *val)
|
const char *val)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char eflags_str[VarEvalFlags_ToStringSize];
|
char eflags_str[VarEvalFlags_ToStringSize];
|
||||||
char vflags_str[VarFlags_ToStringSize];
|
char vflags_str[VarFlags_ToStringSize];
|
||||||
Boolean is_single_char = mod[0] != '\0' &&
|
Boolean is_single_char = mod[0] != '\0' &&
|
||||||
@ -3520,9 +3494,8 @@ LogBeforeApply(const Expr *expr, const char *mod, char endc,
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
LogAfterApply(Expr *expr, const char *p, const char *mod)
|
LogAfterApply(ApplyModifiersState *st, const char *p, const char *mod)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
char eflags_str[VarEvalFlags_ToStringSize];
|
char eflags_str[VarEvalFlags_ToStringSize];
|
||||||
char vflags_str[VarFlags_ToStringSize];
|
char vflags_str[VarFlags_ToStringSize];
|
||||||
const char *quot = st->newValue.str == var_Error ? "" : "\"";
|
const char *quot = st->newValue.str == var_Error ? "" : "\"";
|
||||||
@ -3537,72 +3510,72 @@ LogAfterApply(Expr *expr, const char *p, const char *mod)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplyModifier(const char **pp, const char *val, Expr *expr)
|
ApplyModifier(const char **pp, const char *val, ApplyModifiersState *st)
|
||||||
{
|
{
|
||||||
switch (**pp) {
|
switch (**pp) {
|
||||||
case ':':
|
case ':':
|
||||||
return ApplyModifier_Assign(pp, expr);
|
return ApplyModifier_Assign(pp, st);
|
||||||
case '@':
|
case '@':
|
||||||
return ApplyModifier_Loop(pp, val, expr);
|
return ApplyModifier_Loop(pp, val, st);
|
||||||
case '_':
|
case '_':
|
||||||
return ApplyModifier_Remember(pp, val, expr);
|
return ApplyModifier_Remember(pp, val, st);
|
||||||
case 'D':
|
case 'D':
|
||||||
case 'U':
|
case 'U':
|
||||||
return ApplyModifier_Defined(pp, val, expr);
|
return ApplyModifier_Defined(pp, val, st);
|
||||||
case 'L':
|
case 'L':
|
||||||
return ApplyModifier_Literal(pp, expr);
|
return ApplyModifier_Literal(pp, st);
|
||||||
case 'P':
|
case 'P':
|
||||||
return ApplyModifier_Path(pp, expr);
|
return ApplyModifier_Path(pp, st);
|
||||||
case '!':
|
case '!':
|
||||||
return ApplyModifier_ShellCommand(pp, expr);
|
return ApplyModifier_ShellCommand(pp, st);
|
||||||
case '[':
|
case '[':
|
||||||
return ApplyModifier_Words(pp, val, expr);
|
return ApplyModifier_Words(pp, val, st);
|
||||||
case 'g':
|
case 'g':
|
||||||
return ApplyModifier_Gmtime(pp, val, expr);
|
return ApplyModifier_Gmtime(pp, val, st);
|
||||||
case 'h':
|
case 'h':
|
||||||
return ApplyModifier_Hash(pp, val, expr);
|
return ApplyModifier_Hash(pp, val, st);
|
||||||
case 'l':
|
case 'l':
|
||||||
return ApplyModifier_Localtime(pp, val, expr);
|
return ApplyModifier_Localtime(pp, val, st);
|
||||||
case 't':
|
case 't':
|
||||||
return ApplyModifier_To(pp, val, expr);
|
return ApplyModifier_To(pp, val, st);
|
||||||
case 'N':
|
case 'N':
|
||||||
case 'M':
|
case 'M':
|
||||||
return ApplyModifier_Match(pp, val, expr);
|
return ApplyModifier_Match(pp, val, st);
|
||||||
case 'S':
|
case 'S':
|
||||||
return ApplyModifier_Subst(pp, val, expr);
|
return ApplyModifier_Subst(pp, val, st);
|
||||||
case '?':
|
case '?':
|
||||||
return ApplyModifier_IfElse(pp, expr);
|
return ApplyModifier_IfElse(pp, st);
|
||||||
#ifndef NO_REGEX
|
#ifndef NO_REGEX
|
||||||
case 'C':
|
case 'C':
|
||||||
return ApplyModifier_Regex(pp, val, expr);
|
return ApplyModifier_Regex(pp, val, st);
|
||||||
#endif
|
#endif
|
||||||
case 'q':
|
case 'q':
|
||||||
case 'Q':
|
case 'Q':
|
||||||
return ApplyModifier_Quote(pp, val, expr);
|
return ApplyModifier_Quote(pp, val, st);
|
||||||
case 'T':
|
case 'T':
|
||||||
return ApplyModifier_WordFunc(pp, val, expr, ModifyWord_Tail);
|
return ApplyModifier_WordFunc(pp, val, st, ModifyWord_Tail);
|
||||||
case 'H':
|
case 'H':
|
||||||
return ApplyModifier_WordFunc(pp, val, expr, ModifyWord_Head);
|
return ApplyModifier_WordFunc(pp, val, st, ModifyWord_Head);
|
||||||
case 'E':
|
case 'E':
|
||||||
return ApplyModifier_WordFunc(pp, val, expr, ModifyWord_Suffix);
|
return ApplyModifier_WordFunc(pp, val, st, ModifyWord_Suffix);
|
||||||
case 'R':
|
case 'R':
|
||||||
return ApplyModifier_WordFunc(pp, val, expr, ModifyWord_Root);
|
return ApplyModifier_WordFunc(pp, val, st, ModifyWord_Root);
|
||||||
case 'r':
|
case 'r':
|
||||||
return ApplyModifier_Range(pp, val, expr);
|
return ApplyModifier_Range(pp, val, st);
|
||||||
case 'O':
|
case 'O':
|
||||||
return ApplyModifier_Order(pp, val, expr);
|
return ApplyModifier_Order(pp, val, st);
|
||||||
case 'u':
|
case 'u':
|
||||||
return ApplyModifier_Unique(pp, val, expr);
|
return ApplyModifier_Unique(pp, val, st);
|
||||||
#ifdef SUNSHCMD
|
#ifdef SUNSHCMD
|
||||||
case 's':
|
case 's':
|
||||||
return ApplyModifier_SunShell(pp, val, expr);
|
return ApplyModifier_SunShell(pp, val, st);
|
||||||
#endif
|
#endif
|
||||||
default:
|
default:
|
||||||
return AMR_UNKNOWN;
|
return AMR_UNKNOWN;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static FStr ApplyModifiers(Expr *, const char **, FStr, char, char, Var *,
|
static FStr ApplyModifiers(const char **, FStr, char, char, Var *,
|
||||||
VarExprStatus *, GNode *, VarEvalFlags);
|
VarExprStatus *, GNode *, VarEvalFlags);
|
||||||
|
|
||||||
typedef enum ApplyModifiersIndirectResult {
|
typedef enum ApplyModifiersIndirectResult {
|
||||||
@ -3631,10 +3604,9 @@ typedef enum ApplyModifiersIndirectResult {
|
|||||||
* modifier, and it is neither a SysV modifier but a parse error.
|
* modifier, and it is neither a SysV modifier but a parse error.
|
||||||
*/
|
*/
|
||||||
static ApplyModifiersIndirectResult
|
static ApplyModifiersIndirectResult
|
||||||
ApplyModifiersIndirect(Expr *expr, const char **pp,
|
ApplyModifiersIndirect(ApplyModifiersState *st, const char **pp,
|
||||||
FStr *inout_value)
|
FStr *inout_value)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
const char *p = *pp;
|
const char *p = *pp;
|
||||||
FStr mods;
|
FStr mods;
|
||||||
|
|
||||||
@ -3651,7 +3623,7 @@ ApplyModifiersIndirect(Expr *expr, const char **pp,
|
|||||||
|
|
||||||
if (mods.str[0] != '\0') {
|
if (mods.str[0] != '\0') {
|
||||||
const char *modsp = mods.str;
|
const char *modsp = mods.str;
|
||||||
FStr newValue = ApplyModifiers(expr, &modsp, *inout_value, '\0', '\0',
|
FStr newValue = ApplyModifiers(&modsp, *inout_value, '\0', '\0',
|
||||||
st->var, &st->exprStatus, st->scope, st->eflags);
|
st->var, &st->exprStatus, st->scope, st->eflags);
|
||||||
*inout_value = newValue;
|
*inout_value = newValue;
|
||||||
if (newValue.str == var_Error || *modsp != '\0') {
|
if (newValue.str == var_Error || *modsp != '\0') {
|
||||||
@ -3677,23 +3649,22 @@ ApplyModifiersIndirect(Expr *expr, const char **pp,
|
|||||||
}
|
}
|
||||||
|
|
||||||
static ApplyModifierResult
|
static ApplyModifierResult
|
||||||
ApplySingleModifier(Expr *expr, const char *mod, char endc,
|
ApplySingleModifier(ApplyModifiersState *st, const char *mod, char endc,
|
||||||
const char **pp, FStr *inout_value)
|
const char **pp, FStr *inout_value)
|
||||||
{
|
{
|
||||||
ApplyModifiersState *st = expr->st;
|
|
||||||
ApplyModifierResult res;
|
ApplyModifierResult res;
|
||||||
const char *p = *pp;
|
const char *p = *pp;
|
||||||
const char *const val = inout_value->str;
|
const char *const val = inout_value->str;
|
||||||
|
|
||||||
if (DEBUG(VAR))
|
if (DEBUG(VAR))
|
||||||
LogBeforeApply(expr, mod, endc, val);
|
LogBeforeApply(st, mod, endc, val);
|
||||||
|
|
||||||
res = ApplyModifier(&p, val, expr);
|
res = ApplyModifier(&p, val, st);
|
||||||
|
|
||||||
#ifdef SYSVVARSUB
|
#ifdef SYSVVARSUB
|
||||||
if (res == AMR_UNKNOWN) {
|
if (res == AMR_UNKNOWN) {
|
||||||
assert(p == mod);
|
assert(p == mod);
|
||||||
res = ApplyModifier_SysV(&p, val, expr);
|
res = ApplyModifier_SysV(&p, val, st);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -3707,7 +3678,7 @@ ApplySingleModifier(Expr *expr, const char *mod, char endc,
|
|||||||
*/
|
*/
|
||||||
for (p++; *p != ':' && *p != st->endc && *p != '\0'; p++)
|
for (p++; *p != ':' && *p != st->endc && *p != '\0'; p++)
|
||||||
continue;
|
continue;
|
||||||
Expr_SetValueRefer(expr, var_Error);
|
Expr_SetValueRefer(st, var_Error);
|
||||||
}
|
}
|
||||||
if (res == AMR_CLEANUP || res == AMR_BAD) {
|
if (res == AMR_CLEANUP || res == AMR_BAD) {
|
||||||
*pp = p;
|
*pp = p;
|
||||||
@ -3715,7 +3686,7 @@ ApplySingleModifier(Expr *expr, const char *mod, char endc,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (DEBUG(VAR))
|
if (DEBUG(VAR))
|
||||||
LogAfterApply(expr, p, mod);
|
LogAfterApply(st, p, mod);
|
||||||
|
|
||||||
if (st->newValue.str != val) {
|
if (st->newValue.str != val) {
|
||||||
FStr_Done(inout_value);
|
FStr_Done(inout_value);
|
||||||
@ -3744,7 +3715,6 @@ ApplySingleModifier(Expr *expr, const char *mod, char endc,
|
|||||||
/* Apply any modifiers (such as :Mpattern or :@var@loop@ or :Q or ::=value). */
|
/* Apply any modifiers (such as :Mpattern or :@var@loop@ or :Q or ::=value). */
|
||||||
static FStr
|
static FStr
|
||||||
ApplyModifiers(
|
ApplyModifiers(
|
||||||
Expr *expr,
|
|
||||||
const char **pp, /* the parsing position, updated upon return */
|
const char **pp, /* the parsing position, updated upon return */
|
||||||
FStr value, /* the current value of the expression */
|
FStr value, /* the current value of the expression */
|
||||||
char startc, /* '(' or '{', or '\0' for indirect modifiers */
|
char startc, /* '(' or '{', or '\0' for indirect modifiers */
|
||||||
@ -3769,15 +3739,12 @@ ApplyModifiers(
|
|||||||
};
|
};
|
||||||
const char *p;
|
const char *p;
|
||||||
const char *mod;
|
const char *mod;
|
||||||
ApplyModifiersState *prevst;
|
|
||||||
|
|
||||||
assert(startc == '(' || startc == '{' || startc == '\0');
|
assert(startc == '(' || startc == '{' || startc == '\0');
|
||||||
assert(endc == ')' || endc == '}' || endc == '\0');
|
assert(endc == ')' || endc == '}' || endc == '\0');
|
||||||
assert(value.str != NULL);
|
assert(value.str != NULL);
|
||||||
|
|
||||||
p = *pp;
|
p = *pp;
|
||||||
prevst = expr->st;
|
|
||||||
expr->st = &st;
|
|
||||||
|
|
||||||
if (*p == '\0' && endc != '\0') {
|
if (*p == '\0' && endc != '\0') {
|
||||||
Error(
|
Error(
|
||||||
@ -3791,7 +3758,7 @@ ApplyModifiers(
|
|||||||
|
|
||||||
if (*p == '$') {
|
if (*p == '$') {
|
||||||
ApplyModifiersIndirectResult amir;
|
ApplyModifiersIndirectResult amir;
|
||||||
amir = ApplyModifiersIndirect(expr, &p, &value);
|
amir = ApplyModifiersIndirect(&st, &p, &value);
|
||||||
if (amir == AMIR_CONTINUE)
|
if (amir == AMIR_CONTINUE)
|
||||||
continue;
|
continue;
|
||||||
if (amir == AMIR_OUT)
|
if (amir == AMIR_OUT)
|
||||||
@ -3802,7 +3769,7 @@ ApplyModifiers(
|
|||||||
st.newValue = FStr_InitRefer(var_Error);
|
st.newValue = FStr_InitRefer(var_Error);
|
||||||
mod = p;
|
mod = p;
|
||||||
|
|
||||||
res = ApplySingleModifier(expr, mod, endc, &p, &value);
|
res = ApplySingleModifier(&st, mod, endc, &p, &value);
|
||||||
if (res == AMR_CLEANUP)
|
if (res == AMR_CLEANUP)
|
||||||
goto cleanup;
|
goto cleanup;
|
||||||
if (res == AMR_BAD)
|
if (res == AMR_BAD)
|
||||||
@ -3812,7 +3779,6 @@ ApplyModifiers(
|
|||||||
*pp = p;
|
*pp = p;
|
||||||
assert(value.str != NULL); /* Use var_Error or varUndefined instead. */
|
assert(value.str != NULL); /* Use var_Error or varUndefined instead. */
|
||||||
*exprStatus = st.exprStatus;
|
*exprStatus = st.exprStatus;
|
||||||
expr->st = prevst;
|
|
||||||
return value;
|
return value;
|
||||||
|
|
||||||
bad_modifier:
|
bad_modifier:
|
||||||
@ -3824,7 +3790,6 @@ cleanup:
|
|||||||
*pp = p;
|
*pp = p;
|
||||||
FStr_Done(&value);
|
FStr_Done(&value);
|
||||||
*exprStatus = st.exprStatus;
|
*exprStatus = st.exprStatus;
|
||||||
expr->st = prevst;
|
|
||||||
return FStr_InitRefer(var_Error);
|
return FStr_InitRefer(var_Error);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -4261,7 +4226,6 @@ Var_Parse(const char **pp, GNode *scope, VarEvalFlags eflags, FStr *out_val)
|
|||||||
FStr value;
|
FStr value;
|
||||||
char eflags_str[VarEvalFlags_ToStringSize];
|
char eflags_str[VarEvalFlags_ToStringSize];
|
||||||
VarExprStatus exprStatus = VES_NONE;
|
VarExprStatus exprStatus = VES_NONE;
|
||||||
Expr expr = { NULL };
|
|
||||||
|
|
||||||
DEBUG2(VAR, "Var_Parse: %s with %s\n", start,
|
DEBUG2(VAR, "Var_Parse: %s with %s\n", start,
|
||||||
VarEvalFlags_ToString(eflags_str, eflags));
|
VarEvalFlags_ToString(eflags_str, eflags));
|
||||||
@ -4326,14 +4290,14 @@ Var_Parse(const char **pp, GNode *scope, VarEvalFlags eflags, FStr *out_val)
|
|||||||
if (haveModifier || extramodifiers != NULL) {
|
if (haveModifier || extramodifiers != NULL) {
|
||||||
if (extramodifiers != NULL) {
|
if (extramodifiers != NULL) {
|
||||||
const char *em = extramodifiers;
|
const char *em = extramodifiers;
|
||||||
value = ApplyModifiers(&expr, &em, value, '\0', '\0',
|
value = ApplyModifiers(&em, value, '\0', '\0',
|
||||||
v, &exprStatus, scope, eflags);
|
v, &exprStatus, scope, eflags);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (haveModifier) {
|
if (haveModifier) {
|
||||||
p++; /* Skip initial colon. */
|
p++; /* Skip initial colon. */
|
||||||
|
|
||||||
value = ApplyModifiers(&expr, &p, value, startc, endc,
|
value = ApplyModifiers(&p, value, startc, endc,
|
||||||
v, &exprStatus, scope, eflags);
|
v, &exprStatus, scope, eflags);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user