mirror of
git://projects.qi-hardware.com/eda-tools.git
synced 2024-11-23 02:30:36 +02:00
b2/: meta-variable $ for "previously matched variable"
We need this for iterative processing of FN.
This commit is contained in:
parent
2946b830f1
commit
3d2eca34ff
5
b2/SUBST
5
b2/SUBST
@ -1,5 +1,7 @@
|
||||
FN=DNP { ignore }
|
||||
|
||||
FN=X(*) { $=$1 }
|
||||
|
||||
REF=R[0-9]* {
|
||||
T=R
|
||||
VAL=(#R) { R=$1 }
|
||||
@ -23,8 +25,9 @@ variable:
|
||||
$foo, ...
|
||||
with curly braces:
|
||||
${foo}, ...
|
||||
input variable:
|
||||
input variable (in pattern):
|
||||
$$
|
||||
the input variable ($) can also be used as LHS for matches and assignments
|
||||
|
||||
Caveat:
|
||||
|
||||
|
@ -94,6 +94,7 @@ int main(int argc, char **argv)
|
||||
void (*process)(const char *name) = parse_hierarchy;
|
||||
int i;
|
||||
|
||||
dollar = unique("$");
|
||||
for (i = 1; i != argc; i++) {
|
||||
if (*argv[i] == '-') {
|
||||
if (!strcmp(argv[i], "-c"))
|
||||
|
@ -17,6 +17,8 @@
|
||||
#include "subst.h"
|
||||
|
||||
|
||||
extern const char *dollar; /* "$" */
|
||||
|
||||
extern struct action hierarchy;
|
||||
extern struct subst *substitutions;
|
||||
|
||||
|
16
b2/lang.y
16
b2/lang.y
@ -25,6 +25,8 @@
|
||||
#include "y.tab.h"
|
||||
|
||||
|
||||
const char *dollar;
|
||||
|
||||
struct action hierarchy;
|
||||
struct subst *substitutions = NULL;
|
||||
|
||||
@ -110,6 +112,7 @@ static const struct field *top_field(void)
|
||||
%type <stock> stock
|
||||
%type <prov> providers provider
|
||||
%type <subst> substitutions block opt_block
|
||||
%type <s> word_or_dollar
|
||||
|
||||
%%
|
||||
|
||||
@ -589,7 +592,7 @@ block:
|
||||
{
|
||||
$$ = NULL;
|
||||
}
|
||||
| WORD relop PATTERN opt_block block
|
||||
| word_or_dollar relop PATTERN opt_block block
|
||||
{
|
||||
if ($4) {
|
||||
if ($2 != rel_eq)
|
||||
@ -622,6 +625,17 @@ block:
|
||||
}
|
||||
;
|
||||
|
||||
word_or_dollar:
|
||||
'$'
|
||||
{
|
||||
$$ = dollar;
|
||||
}
|
||||
| WORD
|
||||
{
|
||||
$$ = $1;
|
||||
}
|
||||
;
|
||||
|
||||
opt_block:
|
||||
{
|
||||
$$ = NULL;
|
||||
|
@ -66,6 +66,8 @@ struct value {
|
||||
* When using "struct param" to store (string) variables not associated to a
|
||||
* field, then u.name contains the variable name, "op" contains the relational
|
||||
* operator (default rel_eq), and value.u.s contains the variable's value.
|
||||
*
|
||||
* If the variable is "$", then u.name is set to NULL.
|
||||
*/
|
||||
|
||||
struct param {
|
||||
|
39
b2/subex.c
39
b2/subex.c
@ -20,6 +20,7 @@
|
||||
|
||||
#include "util.h"
|
||||
#include "vstring.h"
|
||||
#include "lang.h"
|
||||
#include "relop.h"
|
||||
#include "subst.h"
|
||||
#include "subex.h"
|
||||
@ -163,46 +164,53 @@ static int do_match_1(const char *var, const regex_t *re,
|
||||
}
|
||||
|
||||
|
||||
static int do_match(const char *var, const regex_t *re,
|
||||
static int do_match(const char **var, const regex_t *re,
|
||||
const struct param *in, const struct param *out,
|
||||
const char **val, regmatch_t *match)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (var != fn)
|
||||
return do_match_1(var, re, in, out, val, match);
|
||||
if (*var != fn)
|
||||
return do_match_1(*var, re, in, out, val, match);
|
||||
for (i = 0; i != FIELDS; i++)
|
||||
if (!do_match_1(f[i], re, in, out, val, match))
|
||||
if (!do_match_1(f[i], re, in, out, val, match)) {
|
||||
*var = f[i];
|
||||
return 0;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
static const struct subst *recurse_sub(const struct subst *sub,
|
||||
const struct param *in, const char *s, const regmatch_t *match,
|
||||
const char *units, struct param **out)
|
||||
const struct param *in, const char *matched_var, const char *matched_val,
|
||||
const regmatch_t *match, const char *units, struct param **out)
|
||||
{
|
||||
const struct subst *jump;
|
||||
regmatch_t m_tmp[10];
|
||||
const char *val;
|
||||
const char *var, *val;
|
||||
char *tmp;
|
||||
|
||||
while (sub) {
|
||||
switch (sub->type) {
|
||||
case st_match:
|
||||
if (do_match(sub->u.match.src, &sub->u.match.re,
|
||||
var = sub->u.match.src;
|
||||
if (var == dollar)
|
||||
var = matched_var;
|
||||
if (do_match(&var, &sub->u.match.re,
|
||||
in, *out, &val, m_tmp))
|
||||
break;
|
||||
jump = recurse_sub(sub->u.match.block, in, val, m_tmp,
|
||||
sub->u.match.units, out);
|
||||
jump = recurse_sub(sub->u.match.block, in,
|
||||
var, val, m_tmp, sub->u.match.units, out);
|
||||
if (jump && jump != sub)
|
||||
return jump;
|
||||
break;
|
||||
case st_assign:
|
||||
tmp = compose(sub->u.assign.pat, in, *out, s, match,
|
||||
units);
|
||||
do_assign(sub->u.assign.dst, out, sub->u.assign.op,
|
||||
tmp);
|
||||
tmp = compose(sub->u.assign.pat, in, *out, matched_val,
|
||||
match, units);
|
||||
var = sub->u.assign.dst;
|
||||
if (var == dollar)
|
||||
var = matched_var;
|
||||
do_assign(var, out, sub->u.assign.op, tmp);
|
||||
break;
|
||||
case st_end:
|
||||
return &jump_end;
|
||||
@ -237,5 +245,6 @@ int substitute(const struct subst *sub, const struct param *in,
|
||||
}
|
||||
}
|
||||
*out = NULL;
|
||||
return recurse_sub(sub, in, NULL, NULL, NULL, out) != &jump_ignore;
|
||||
return recurse_sub(sub, in, NULL, NULL, NULL, NULL, out)
|
||||
!= &jump_ignore;
|
||||
}
|
||||
|
@ -356,10 +356,14 @@ static void recurse_fin(struct subst *sub, const struct parent *parent)
|
||||
sub->prev = prev;
|
||||
switch (sub->type) {
|
||||
case st_match:
|
||||
if (!parent && sub->u.match.src == dollar)
|
||||
yyerror("$ without match");
|
||||
next.sub = sub;
|
||||
recurse_fin(sub->u.match.block, &next);
|
||||
break;
|
||||
case st_assign:
|
||||
if (!parent && sub->u.assign.dst == dollar)
|
||||
yyerror("$ without match");
|
||||
check_chunks(sub->u.assign.pat, parent, prev);
|
||||
break;
|
||||
case st_end:
|
||||
|
Loading…
Reference in New Issue
Block a user