diff options
author | Brian Pane <brianp@apache.org> | 2002-03-21 04:17:11 +0000 |
---|---|---|
committer | Brian Pane <brianp@apache.org> | 2002-03-21 04:17:11 +0000 |
commit | 987b84f020898f819e63672673db04f0d76da4ab (patch) | |
tree | 9e6e8722da7a403e2f197b2bda0c0ceb75d21be1 /srclib | |
parent | 5ffc63f688d7a6e59b245d6cff031c258834b027 (diff) | |
download | httpd-987b84f020898f819e63672673db04f0d76da4ab.tar.gz |
Performance optimization: use a temp buffer on the stack instead
of a malloc'ed buffer in regexec() in cases where the required
buffer size is small.
This will help us avoid a malloc/free pair when executing mod_rewrite
rules that use $1/$2/etc to reference sequences in the matched pattern.
Note: I've also submitted this change as a patch for PCRE, but because
the next PCRE release isn't planned until later this year I'm
committing it to the httpd-2.0 copy of PCRE in the meantime.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@94069 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'srclib')
-rw-r--r-- | srclib/pcre/pcreposix.c | 26 |
1 files changed, 22 insertions, 4 deletions
diff --git a/srclib/pcre/pcreposix.c b/srclib/pcre/pcreposix.c index 9b2efe2098..29f2e01740 100644 --- a/srclib/pcre/pcreposix.c +++ b/srclib/pcre/pcreposix.c @@ -224,13 +224,23 @@ substring, so we have to get and release working store instead of just using the POSIX structures as was done in earlier releases when PCRE needed only 2 ints. */ +#define SMALL_NMATCH 5 int regexec(regex_t *preg, const char *string, size_t nmatch, regmatch_t pmatch[], int eflags) { int rc; int options = 0; +/* NOTE: The code related to the "SMALL_NMATCH" optimization + * currently is unique to the httpd-2.0 copy of PCRE 3.9. I've + * submitted the patch to the PCRE maintainer for inclusion in + * the next PCRE release, slated for late 2002. At that time, + * we can merge the new PCRE version into the httpd-2.0/srclib + * tree. --brianp 3/20/2002 + */ +int small_ovector[SMALL_NMATCH * 3]; int *ovector = NULL; +int allocated_ovector = 0; if ((eflags & REG_NOTBOL) != 0) options |= PCRE_NOTBOL; if ((eflags & REG_NOTEOL) != 0) options |= PCRE_NOTEOL; @@ -244,8 +254,16 @@ preg->re_erroffset = (size_t)(-1); /* Only has meaning after compile */ if (nmatch > 0) { - ovector = (int *)malloc(sizeof(int) * nmatch * 3); - if (ovector == NULL) return REG_ESPACE; + if (nmatch <= SMALL_NMATCH) + { + ovector = &(small_ovector[0]); + } + else + { + ovector = (int *)malloc(sizeof(int) * nmatch * 3); + if (ovector == NULL) return REG_ESPACE; + allocated_ovector = 1; + } } rc = pcre_exec(preg->re_pcre, NULL, string, (int)strlen(string), 0, options, @@ -261,14 +279,14 @@ if (rc >= 0) pmatch[i].rm_so = ovector[i*2]; pmatch[i].rm_eo = ovector[i*2+1]; } - if (ovector != NULL) free(ovector); + if (allocated_ovector) free(ovector); for (; i < nmatch; i++) pmatch[i].rm_so = pmatch[i].rm_eo = -1; return 0; } else { - if (ovector != NULL) free(ovector); + if (allocated_ovector) free(ovector); switch(rc) { case PCRE_ERROR_NOMATCH: return REG_NOMATCH; |