From 15f22648cd99f392ac5cab6afeec2a0e97b85c6d Mon Sep 17 00:00:00 2001 From: Dmitry Mikhirev Date: Sat, 24 Jan 2015 14:31:23 +0300 Subject: fixed global search hang when zero-length matching found --- pcre.c | 31 +++++++++++++++++++++++++++++-- tests.mk | 6 +++++- 2 files changed, 34 insertions(+), 3 deletions(-) diff --git a/pcre.c b/pcre.c index 9da5387..3245d79 100644 --- a/pcre.c +++ b/pcre.c @@ -389,7 +389,17 @@ static char *match(const char *name, int argc, char **argv) retstr[retlen] = '\0'; /* where to start next search */ - offset = ovec[1]; + if (offset == ovec[1]) { //zero-length match + if (offset < len) { + // continue with one character shift + offset++; + } else { + // stop global search + global = 0; + } + } else { + offset = ovec[1]; + } /* set named make vars to captured substrings */ set_named_vars(re, str, ovec, ncap); @@ -513,7 +523,24 @@ static char *subst(const char *name, int argc, char **argv) rep = NULL; /* where to start next search */ - offset = ovec[1]; + if (offset == ovec[1]) { //zero-length match + if (offset < subjlen) { + // continue with one character shift + s = str_extend(retstr, retlen + 1); + if (s == NULL) { + goto end_subst; + } + retstr = s; + strncpy(retstr + retlen, str + offset, 1); + retlen++; + offset++; + } else { + // stop global search + global = 0; + } + } else { + offset = ovec[1]; + } } } while (global && (ncap != PCRE_ERROR_NOMATCH)); diff --git a/tests.mk b/tests.mk index 47031c1..ce00b89 100644 --- a/tests.mk +++ b/tests.mk @@ -2,7 +2,7 @@ ifneq ($(findstring 4.,$(MAKE_VERSION)),4.) $(error you need GNU make 4.x to run tests) endif -NUMTESTS = 30 +NUMTESTS = 32 tests := $(foreach num,$(shell seq -f%03g $(NUMTESTS)),test$(num)) load pcre.so @@ -113,6 +113,10 @@ test029 = -z "$(m ^test$,$(subj029))" -a "$(m ^test$,$(subj029),m)" = test test030 = -z "$(m test.test,$(subj029))" -a \ "$(s test.test,passed,$(subj029),s)" = passed +# test zero-length matching +test031 = "$(m x?,aaa,g)" = "" +test032 = "$(s x?,!,abcd,g)" = "!a!b!c!d!" + ### END OF TEST EXPRESSIONS ### test%: -- cgit v1.2.1