Commit ae19f8dd authored by Poul-Henning Kamp's avatar Poul-Henning Kamp

Turn backends into self evaluating symbols



git-svn-id: http://www.varnish-cache.org/svn/trunk/varnish-cache@5482 d4fa192b-c00b-0410-8231-f00ffab90ce4
parent d438ad82
......@@ -675,6 +675,22 @@ vcc_ParseBackendHost(struct vcc *tl, int serial, char **nm)
}
}
/*--------------------------------------------------------------------
* Tell rest of compiler about a backend
*/
static void
vcc_DefBackend(struct vcc *tl, const struct token *nm)
{
struct symbol *sym;
sym = VCC_GetSymbolTok(tl, nm, SYM_BACKEND);
AN(sym);
sym->fmt = BACKEND;
sym->eval = vcc_Expr_Backend;
sym->ndef++;
}
/*--------------------------------------------------------------------
* Parse a plain backend aka a simple director
*/
......@@ -687,7 +703,7 @@ vcc_ParseSimpleDirector(struct vcc *tl)
h = TlAlloc(tl, sizeof *h);
h->name = tl->t_dir;
vcc_AddDef(tl, tl->t_dir, SYM_BACKEND);
vcc_DefBackend(tl, tl->t_dir);
sprintf(vgcname, "_%.*s", PF(h->name));
h->vgcname = TlAlloc(tl, strlen(vgcname) + 1);
strcpy(h->vgcname, vgcname);
......@@ -735,7 +751,7 @@ vcc_ParseDirector(struct vcc *tl)
tl->t_policy = t_first;
vcc_ParseSimpleDirector(tl);
} else {
vcc_AddDef(tl, tl->t_dir, SYM_BACKEND);
vcc_DefBackend(tl, tl->t_dir);
ExpectErr(tl, ID); /* ID: policy */
tl->t_policy = tl->t;
vcc_NextToken(tl);
......
......@@ -78,7 +78,7 @@ enum symkind {
#undef VCC_SYMB
};
typedef void sym_expr_t(struct vcc *tl, struct expr **e,
typedef void sym_expr_t(struct vcc *tl, struct expr * const *e,
const struct symbol *sym);
struct symbol {
......@@ -241,6 +241,7 @@ void vcc_Expr(struct vcc *tl, enum var_type typ);
void vcc_Expr_Call(struct vcc *tl, const struct symbol *sym);
sym_expr_t vcc_Expr_Var;
sym_expr_t vcc_Expr_Func;
sym_expr_t vcc_Expr_Backend;
/* vcc_dir_dns.c */
parsedirector_f vcc_ParseDnsDirector;
......
......@@ -417,7 +417,22 @@ vcc_arg_type(const char **p)
*/
void
vcc_Expr_Var(struct vcc *tl, struct expr **e, const struct symbol *sym)
vcc_Expr_Backend(struct vcc *tl, struct expr * const *e, const struct symbol *sym)
{
assert(sym->kind == SYM_BACKEND);
vcc_ExpectCid(tl);
vcc_AddRef(tl, tl->t, SYM_BACKEND);
vsb_printf((*e)->vsb, "VGCDIR(_%.*s)", PF(tl->t));
(*e)->fmt = BACKEND;
vcc_NextToken(tl);
}
/*--------------------------------------------------------------------
*/
void
vcc_Expr_Var(struct vcc *tl, struct expr * const *e, const struct symbol *sym)
{
const struct var *vp;
......@@ -429,18 +444,16 @@ vcc_Expr_Var(struct vcc *tl, struct expr **e, const struct symbol *sym)
vsb_printf((*e)->vsb, "%s", vp->rname);
(*e)->fmt = vp->fmt;
vcc_NextToken(tl);
vsb_finish((*e)->vsb);
AZ(vsb_overflowed((*e)->vsb));
}
/*--------------------------------------------------------------------
*/
void
vcc_Expr_Func(struct vcc *tl, struct expr **e, const struct symbol *sym)
vcc_Expr_Func(struct vcc *tl, struct expr * const *e, const struct symbol *sym)
{
const char *p, *q, *r;
struct expr *e1;
struct expr *e1, *e2;
enum var_type fmt;
char buf[32];
......@@ -450,10 +463,11 @@ vcc_Expr_Func(struct vcc *tl, struct expr **e, const struct symbol *sym)
SkipToken(tl, ID);
SkipToken(tl, '(');
p = sym->args;
(*e)->fmt = vcc_arg_type(&p);
vsb_printf((*e)->vsb, "%s(sp, \v+", sym->cfunc);
vsb_finish((*e)->vsb);
AZ(vsb_overflowed((*e)->vsb));
e2 = vcc_new_expr();
e2->fmt = vcc_arg_type(&p);
vsb_printf(e2->vsb, "%s(sp, \v+", sym->cfunc);
vsb_finish(e2->vsb);
AZ(vsb_overflowed(e2->vsb));
q = "\v1\n\v2";
while (*p != '\0') {
e1 = NULL;
......@@ -496,11 +510,13 @@ vcc_Expr_Func(struct vcc *tl, struct expr **e, const struct symbol *sym)
if (*p != '\0')
SkipToken(tl, ',');
}
*e = vcc_expr_edit((*e)->fmt, q, *e, e1);
e2 = vcc_expr_edit(e2->fmt, q, e2, e1);
q = "\v1,\n\v2";
}
SkipToken(tl, ')');
*e = vcc_expr_edit((*e)->fmt, "\v1\n)\v-", *e, NULL);
e2 = vcc_expr_edit(e2->fmt, "\v1\n)\v-", e2, NULL);
(*e)->fmt = e2->fmt;
vsb_cat((*e)->vsb, vsb_data(e2->vsb));
}
/*--------------------------------------------------------------------
......@@ -516,7 +532,6 @@ vcc_expr4(struct vcc *tl, struct expr **e, enum var_type fmt)
{
struct expr *e1, *e2;
const struct symbol *sym;
const struct var *vp;
double d;
*e = NULL;
......@@ -553,14 +568,6 @@ vcc_expr4(struct vcc *tl, struct expr **e, enum var_type fmt)
e1->fmt = BOOL;
break;
}
if (fmt == BACKEND) {
vcc_ExpectCid(tl);
vcc_AddRef(tl, tl->t, SYM_BACKEND);
vsb_printf(e1->vsb, "VGCDIR(_%.*s)", PF(tl->t));
e1->fmt = BACKEND;
vcc_NextToken(tl);
break;
}
/*
* XXX: what if var and func/proc had same name ?
* XXX: look for SYM_VAR first for consistency ?
......@@ -578,8 +585,7 @@ vcc_expr4(struct vcc *tl, struct expr **e, enum var_type fmt)
if (sym->eval != NULL) {
sym->eval(tl, &e1, sym);
ERRCHK(tl);
*e = e1;
return;
break;
}
switch(sym->kind) {
......@@ -1049,6 +1055,8 @@ vcc_Expr_Call(struct vcc *tl, const struct symbol *sym)
t1 = tl->t;
e = vcc_new_expr();
vcc_Expr_Func(tl, &e, sym);
vsb_finish(e->vsb);
AZ(vsb_overflowed(e->vsb));
if (!tl->err) {
vcc_expr_fmt(tl->fb, tl->indent, e);
vsb_cat(tl->fb, ";\n");
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment