summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2013-07-18 21:22:58 -0400
committerTom Lane <tgl@sss.pgh.pa.us>2013-07-18 21:22:58 -0400
commit1a8a3f64cedeb943062b9b2ae3412e9d66545ef1 (patch)
tree476c0a29875527c87a82fe4289f8900701e363fa
parent5174bc2240c7e873912b4061285df2d475ce6639 (diff)
Fix regex match failures for backrefs combined with non-greedy quantifiers.
An ancient logic error in cfindloop() could cause the regex engine to fail to find matches that begin later than the start of the string. This function is only used when the regex pattern contains a back reference, and so far as we can tell the error is only reachable if the pattern is non-greedy (i.e. its first quantifier uses the ? modifier). Furthermore, the actual match must begin after some potential match that satisfies the DFA but then fails the back-reference's match test. Reported and fixed by Jeevan Chalke, with cosmetic adjustments by me.
-rw-r--r--src/backend/regex/regexec.c20
1 files changed, 11 insertions, 9 deletions
diff --git a/src/backend/regex/regexec.c b/src/backend/regex/regexec.c
index 8b462756e36..16cdd897571 100644
--- a/src/backend/regex/regexec.c
+++ b/src/backend/regex/regexec.c
@@ -464,19 +464,21 @@ cfindloop(struct vars * v,
*coldp = cold;
return er;
}
- if ((shorter) ? end == estop : end == begin)
- {
- /* no point in trying again */
- *coldp = cold;
- return REG_NOMATCH;
- }
- /* go around and try again */
+ /* try next shorter/longer match with same begin point */
if (shorter)
+ {
+ if (end == estop)
+ break; /* NOTE BREAK OUT */
estart = end + 1;
+ }
else
+ {
+ if (end == begin)
+ break; /* NOTE BREAK OUT */
estop = end - 1;
- }
- }
+ }
+ } /* end loop over endpoint positions */
+ } /* end loop over beginning positions */
} while (close < v->stop);
*coldp = cold;