Commit a22465ba authored by Geoff Simmons's avatar Geoff Simmons

fix a bug in backref -- correctly return the fallback when a backref

number "in the middle" does not capture any string, e.g. when
"(a|(z))(bc)" matches "abc", with no capture for backref 2
parent 7563cb57
...@@ -12,6 +12,7 @@ varnish v1 -vcl+backend { ...@@ -12,6 +12,7 @@ varnish v1 -vcl+backend {
sub vcl_init { sub vcl_init {
new frobnitz = re.regex("(frob)(nitz)"); new frobnitz = re.regex("(frob)(nitz)");
new barbaz = re.regex("(bar)(baz)"); new barbaz = re.regex("(bar)(baz)");
new azbc = re.regex("(a|(z))(bc)");
} }
sub vcl_deliver { sub vcl_deliver {
...@@ -60,6 +61,14 @@ varnish v1 -vcl+backend { ...@@ -60,6 +61,14 @@ varnish v1 -vcl+backend {
set resp.http.barf8 = barbaz.backref(8, "fallback8"); set resp.http.barf8 = barbaz.backref(8, "fallback8");
set resp.http.barf9 = barbaz.backref(9, "fallback9"); set resp.http.barf9 = barbaz.backref(9, "fallback9");
set resp.http.barf10 = barbaz.backref(10, "fallback10"); set resp.http.barf10 = barbaz.backref(10, "fallback10");
if (azbc.match("abc")) {
set resp.http.abc1 = azbc.backref(1, "error1");
set resp.http.abc2 = azbc.backref(2, "none");
set resp.http.abc3 = azbc.backref(3, "error3");
} else {
set resp.http.abc = "fail";
}
} }
} -start } -start
...@@ -97,6 +106,10 @@ client c1 { ...@@ -97,6 +106,10 @@ client c1 {
expect resp.http.barf8 == "fallback8" expect resp.http.barf8 == "fallback8"
expect resp.http.barf9 == "fallback9" expect resp.http.barf9 == "fallback9"
expect resp.http.barf10 == "fallback10" expect resp.http.barf10 == "fallback10"
expect resp.http.abc == <undef>
expect resp.http.abc1 == "a"
expect resp.http.abc2 == "none"
expect resp.http.abc3 == "bc"
} -run } -run
logexpect l1 -v v1 -d 1 -g vxid -q "VCL_Error" { logexpect l1 -v v1 -d 1 -g vxid -q "VCL_Error" {
......
...@@ -70,7 +70,6 @@ typedef struct ov_s { ...@@ -70,7 +70,6 @@ typedef struct ov_s {
#define OV_MAGIC 0x844bfa39 #define OV_MAGIC 0x844bfa39
const char *subject; const char *subject;
int ovector[MAX_OV_USED]; int ovector[MAX_OV_USED];
int count;
} ov_t; } ov_t;
static char c; static char c;
...@@ -210,7 +209,7 @@ match(const struct vrt_ctx *ctx, struct vmod_re_regex *re, vre_t *vre, ...@@ -210,7 +209,7 @@ match(const struct vrt_ctx *ctx, struct vmod_re_regex *re, vre_t *vre,
return 0; return 0;
} }
ov->magic = OV_MAGIC; ov->magic = OV_MAGIC;
ov->count = s; memset(ov->ovector, -1, sizeof(ov->ovector));
cp = s * 2 * sizeof(*nov); cp = s * 2 * sizeof(*nov);
assert(cp <= sizeof(nov)); assert(cp <= sizeof(nov));
memcpy(ov->ovector, nov, cp); memcpy(ov->ovector, nov, cp);
...@@ -277,17 +276,16 @@ vmod_regex_backref(const struct vrt_ctx *ctx, struct vmod_re_regex *re, ...@@ -277,17 +276,16 @@ vmod_regex_backref(const struct vrt_ctx *ctx, struct vmod_re_regex *re,
CAST_OBJ(ov, p, OV_MAGIC); CAST_OBJ(ov, p, OV_MAGIC);
assert((char *)ov >= ctx->ws->s && (char *)ov < ctx->ws->e); assert((char *)ov >= ctx->ws->s && (char *)ov < ctx->ws->e);
assert(ov->subject >= ctx->ws->s && ov->subject < ctx->ws->e); assert(ov->subject >= ctx->ws->s && ov->subject < ctx->ws->e);
assert(ov->count > 0 && ov->count <= MAX_MATCHES);
if (refnum >= ov->count) refnum <<= 1;
assert(refnum + 1 < MAX_OV_USED);
if (ov->ovector[refnum] == -1)
return fallback; return fallback;
l = WS_Reserve(ctx->ws, 0); l = WS_Reserve(ctx->ws, 0);
substr = ctx->ws->f; substr = ctx->ws->f;
/* cf. pcre_copy_substring */ /* cf. pcre_copy_substring */
refnum <<= 1;
assert(refnum + 1 < MAX_OV_USED);
len = ov->ovector[refnum+1] - ov->ovector[refnum]; len = ov->ovector[refnum+1] - ov->ovector[refnum];
if (len + 1 > l) { if (len + 1 > l) {
VSLb(ctx->vsl, SLT_VCL_Error, VSLb(ctx->vsl, SLT_VCL_Error,
......
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