From 2b80ff2374fce1610d366654d2afd570381ab4c0 Mon Sep 17 00:00:00 2001 From: ringabout <43030857+ringabout@users.noreply.github.com> Date: Thu, 15 Sep 2022 13:54:53 +0800 Subject: [PATCH] fixes #19104; peg Incorrect captures [backport:1.6] (#20352) * fixes #19104; peg Incorrect captures [backport:1.6] * add tests Co-authored-by: khchen --- lib/pure/pegs.nim | 5 ++++- tests/stdlib/tpegs.nim | 4 ++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/lib/pure/pegs.nim b/lib/pure/pegs.nim index 6319be551c..a957008255 100644 --- a/lib/pure/pegs.nim +++ b/lib/pure/pegs.nim @@ -838,10 +838,13 @@ template matchOrParse(mopProc: untyped) = var idx = c.ml # reserve a slot for the subpattern result = mopProc(s, p.sons[0], start, c) if result >= 0: - inc(c.ml) if idx < MaxSubpatterns: + if idx != c.ml: + for i in countdown(c.ml, idx): + c.matches[i+1] = c.matches[i] c.matches[idx] = (start, start+result-1) #else: silently ignore the capture + inc(c.ml) leave(pkCapture, s, p, start, result) of pkBackRef: enter(pkBackRef, s, p, start) diff --git a/tests/stdlib/tpegs.nim b/tests/stdlib/tpegs.nim index c3d8942cff..550f7ac4fd 100644 --- a/tests/stdlib/tpegs.nim +++ b/tests/stdlib/tpegs.nim @@ -158,6 +158,10 @@ block: privateAccess(NonTerminal) privateAccess(Captures) + if "test" =~ peg"s <- {{\ident}}": # bug #19104 + doAssert matches[0] == "test" + doAssert matches[1] == "test", $matches[1] + doAssert escapePeg("abc''def'") == r"'abc'\x27\x27'def'\x27" doAssert match("(a b c)", peg"'(' @ ')'") doAssert match("W_HI_Le", peg"\y 'while'")