Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
L
libvmod-pcre2
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
3
Issues
3
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
uplex-varnish
libvmod-pcre2
Commits
8bdce4b5
Commit
8bdce4b5
authored
Mar 20, 2017
by
Geoff Simmons
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Add the .namedref() method; currently a lot of duplication with .backref().
parent
ccff2eb0
Changes
4
Show whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
240 additions
and
0 deletions
+240
-0
README.rst
README.rst
+9
-0
namedref.vtc
src/tests/namedref.vtc
+171
-0
vmod_pcre2.c
src/vmod_pcre2.c
+57
-0
vmod_pcre2.vcc
src/vmod_pcre2.vcc
+3
-0
No files found.
README.rst
View file @
8bdce4b5
...
...
@@ -72,6 +72,15 @@ regex.backref
STRING regex.backref(INT ref, STRING fallback="**BACKREF METHOD FAILED**")
.. _func_regex.namedref:
regex.namedref
--------------
::
STRING regex.namedref(STRING name, STRING fallback="**NAMEDREF METHOD FAILED**")
.. _func_config_bool:
config_bool
...
...
src/tests/namedref.vtc
0 → 100644
View file @
8bdce4b5
# looks like -*- vcl -*-
varnishtest "namedref()"
varnish v1 -vcl {
import pcre2 from "${vmod_topbuild}/src/.libs/libvmod_pcre2.so";
backend b { .host = "${bad_ip}"; }
sub vcl_init {
new barbaz = pcre2.regex("(?<bar>bar)(?<baz>baz)");
new bazplus = pcre2.regex("(?<baz>baz)(?<dots>.+)");
}
sub vcl_recv {
return(synth(200));
}
sub vcl_synth {
# Tests task scopes for two different objects.
# Numbered backrefs also work with named groups.
if (barbaz.match("barbaz") && bazplus.match("bazquux")) {
set resp.http.bar-bar
= barbaz.namedref("bar", "err_bar");
set resp.http.bar-baz
= barbaz.namedref("baz", "err_baz");
set resp.http.baz-baz
= bazplus.namedref("baz", "err_baz");
set resp.http.baz-dots
= bazplus.namedref("dots", "err_dots");
set resp.http.bar0 = barbaz.backref(0, "error0");
set resp.http.bar1 = barbaz.backref(1, "error1");
set resp.http.bar2 = barbaz.backref(2, "error2");
set resp.http.baz0 = bazplus.backref(0, "error0");
set resp.http.baz1 = bazplus.backref(1, "error1");
set resp.http.baz2 = bazplus.backref(2, "error2");
}
else {
set resp.status = 999;
}
}
} -start
client c1 -repeat 2 {
txreq
rxresp
expect resp.status == "200"
expect resp.http.bar-bar == "bar"
expect resp.http.bar-baz == "baz"
expect resp.http.baz-baz == "baz"
expect resp.http.baz-dots == "quux"
expect resp.http.bar0 == "barbaz"
expect resp.http.bar1 == "bar"
expect resp.http.bar2 == "baz"
expect resp.http.baz0 == "bazquux"
expect resp.http.baz1 == "baz"
expect resp.http.baz2 == "quux"
} -run
# failure
varnish v1 -vcl {
import pcre2 from "${vmod_topbuild}/src/.libs/libvmod_pcre2.so";
backend b { .host = "${bad_ip}"; }
sub vcl_init {
new frobnitz = pcre2.regex("(?<frob>frob)(?<nitz>nitz)");
new barbaz = pcre2.regex("(?<bar>bar)(?<baz>baz)");
new azbc = pcre2.regex("(?<a>a|(?<z>z))(?<bc>bc)");
new foo = pcre2.regex("(?<f>f)(?<o>o)(o)",
no_auto_capture=true);
}
sub vcl_recv {
return(synth(200));
}
sub vcl_synth {
# Call to namedref() before match()
# Also tests the default fallback.
set resp.http.nomatch = barbaz.namedref("bar");
# match() and namedref() now re-use the object's task scope
if (barbaz.match("barbaz")) {
set resp.http.bar-bar
= barbaz.namedref("bar", "err_bar");
# no such name
set resp.http.bar-quux
= barbaz.namedref("quux", "err_quux");
# fallback is NULL
set resp.http.fallback
= barbaz.namedref("bar", req.http.undef);
}
# match fails
set resp.http.frob1 = frobnitz.match("barbaz");
# ... so all namedrefs fail
set resp.http.frob1-frob
= frobnitz.namedref("frob", "err_frob");
set resp.http.frob1-nitz
= frobnitz.namedref("nitz", "err_nitz");
# match succeeds, then fails again
set resp.http.frob-yes = frobnitz.match("frobnitz");
set resp.http.frob-no = frobnitz.match("barbaz");
# ... so all namedrefs fail, despite previous match
set resp.http.frob2-frob
= frobnitz.namedref("frob", "err_frob");
set resp.http.frob2-nitz
= frobnitz.namedref("nitz", "err_nitz");
# namedref "z" is unset
set resp.http.azbc = azbc.match("abc");
set resp.http.azbc-a = azbc.namedref("a", "err_a");
set resp.http.azbc-z = azbc.namedref("z", "err_z");
set resp.http.azbc-bc = azbc.namedref("bc", "err_bc");
# namedrefs succeed with no_auto_capture, as well as
# numbered backrefs that correspond to the named
# groups, and backref 0, but not the other numbered backrefs.
set resp.http.foo = foo.match("foo");
set resp.http.foo-f = foo.namedref("f", "err_f");
set resp.http.foo-o = foo.namedref("o", "err_o");
set resp.http.foo-0 = foo.backref(0, "error0");
set resp.http.foo-1 = foo.backref(1, "error1");
set resp.http.foo-2 = foo.backref(2, "error2");
set resp.http.foo-3 = foo.backref(3, "error3");
}
}
client c1 -repeat 2 {
txreq
rxresp
expect resp.status == "200"
expect resp.http.nomatch == "**NAMEDREF METHOD FAILED**"
expect resp.http.bar-bar == "bar"
expect resp.http.bar-quux == "err_quux"
expect resp.http.fallback == "**NAMEDREF METHOD FAILED**"
expect resp.http.frob1 == "false"
expect resp.http.frob1-frob == "err_frob"
expect resp.http.frob1-nitz == "err_nitz"
expect resp.http.frob-yes == "true"
expect resp.http.frob-no == "false"
expect resp.http.frob2-frob == "err_frob"
expect resp.http.frob2-nitz == "err_nitz"
expect resp.http.azbc == "true"
expect resp.http.azbc-a == "a"
expect resp.http.azbc-z == "err_z"
expect resp.http.azbc-bc == "bc"
expect resp.http.foo == "true"
expect resp.http.foo-f == "f"
expect resp.http.foo-o == "o"
expect resp.http.foo-0 == "foo"
expect resp.http.foo-1 == "f"
expect resp.http.foo-2 == "o"
expect resp.http.foo-3 == "error3"
} -run
logexpect l1 -v v1 -d 1 -g vxid -q "VCL_Error" {
expect 0 * Begin req
expect * = VCL_Error "^vmod pcre2 error: barbaz.namedref.bar. called without prior match$"
expect * = VCL_Error "^vmod pcre2 error: in barbaz.namedref.quux.: unknown substring$"
expect * = VCL_Error "^vmod pcre2 error: in barbaz.namedref..: fallback is undefined$"
expect * = VCL_Error "^vmod pcre2 error: in frobnitz.namedref.frob.: no match$"
expect * = VCL_Error "^vmod pcre2 error: in frobnitz.namedref.nitz.: no match$"
expect * = VCL_Error "^vmod pcre2 error: in frobnitz.namedref.frob.: no match$"
expect * = VCL_Error "^vmod pcre2 error: in frobnitz.namedref.nitz.: no match$"
expect * = VCL_Error "^vmod pcre2 error: in azbc.namedref.z.: requested value is not set$"
expect * = VCL_Error "^vmod pcre2 error: in foo.backref.3.: unknown substring$"
expect * = End
} -run
src/vmod_pcre2.c
View file @
8bdce4b5
...
...
@@ -572,6 +572,63 @@ vmod_regex_backref(VRT_CTX, struct vmod_pcre2_regex *regex, VCL_INT ref,
return
fallback
;
}
VCL_STRING
vmod_regex_namedref
(
VRT_CTX
,
struct
vmod_pcre2_regex
*
regex
,
VCL_STRING
name
,
VCL_STRING
fallback
)
{
struct
vmod_priv
*
match_task
;
pcre2_match_data
*
mdata
;
PCRE2_UCHAR
*
buf
;
PCRE2_SIZE
len
;
int
ret
;
char
*
msg
;
uintptr_t
snap
;
CHECK_OBJ_NOTNULL
(
ctx
,
VRT_CTX_MAGIC
);
CHECK_OBJ_NOTNULL
(
regex
,
VMOD_PCRE2_REGEX_MAGIC
);
if
(
fallback
==
NULL
)
{
VERR
(
ctx
,
"in %s.namedref(): fallback is undefined"
,
regex
->
vcl_name
);
return
"**NAMEDREF METHOD FAILED**"
;
}
if
(
name
==
NULL
)
{
VERR
(
ctx
,
"in %s.namedref(<undefined>): name is undefined"
,
regex
->
vcl_name
);
return
fallback
;
}
match_task
=
VRT_priv_task
(
ctx
,
regex
);
AN
(
match_task
);
if
(
match_task
->
priv
==
NULL
)
{
VERR
(
ctx
,
"%s.namedref(%s) called without prior match"
,
regex
->
vcl_name
,
name
);
return
fallback
;
}
WS_Assert_Allocated
(
ctx
->
ws
,
match_task
->
priv
,
0
);
mdata
=
match_task
->
priv
;
if
((
ret
=
pcre2_substring_get_byname
(
mdata
,
(
PCRE2_SPTR
)
name
,
&
buf
,
&
len
))
==
0
)
{
WS_Assert_Allocated
(
ctx
->
ws
,
buf
,
len
+
1
);
return
(
VCL_STRING
)
buf
;
}
/*
* This error is returned when the ovector was too small, cannot
* happen after using pcre2_match_data_create_from_pattern() to
* get the match data block.
*/
assert
(
ret
!=
PCRE2_ERROR_UNAVAILABLE
);
snap
=
WS_Snapshot
(
ctx
->
ws
);
if
((
msg
=
WS_Printf
(
ctx
->
ws
,
"in %s.namedref(%s)"
,
regex
->
vcl_name
,
name
))
==
NULL
)
msg
=
""
;
report_pcre2_err
(
ctx
,
ret
,
msg
,
""
);
WS_Reset
(
ctx
->
ws
,
snap
);
return
fallback
;
}
/* Functions */
VCL_BOOL
...
...
src/vmod_pcre2.vcc
View file @
8bdce4b5
...
...
@@ -41,6 +41,9 @@ $Method BOOL .match(PRIV_CALL, PRIV_TASK, STRING subject, INT len=0,
$Method STRING .backref(INT ref, STRING fallback = "**BACKREF METHOD FAILED**")
$Method STRING .namedref(STRING name,
STRING fallback = "**NAMEDREF METHOD FAILED**")
$Function BOOL config_bool(ENUM {JIT, STACKRECURSE, UNICODE})
$Function STRING config_str(ENUM {BSR, JITTARGET, NEWLINE, UNICODE_VERSION,
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment