summaryrefslogtreecommitdiffstats
path: root/server/util.c
diff options
context:
space:
mode:
authorStefan Fritsch <sf@apache.org>2011-10-26 00:29:13 +0200
committerStefan Fritsch <sf@apache.org>2011-10-26 00:29:13 +0200
commit04ca93ecfff9e24a8d491eaaefb3e466f234c17b (patch)
tree6b5dc1754217a004190dcb2b119e92fb30c24452 /server/util.c
parentRemove spurious parsing of the cipher parameter. (diff)
downloadapache2-04ca93ecfff9e24a8d491eaaefb3e466f234c17b.tar.xz
apache2-04ca93ecfff9e24a8d491eaaefb3e466f234c17b.zip
Limit ap_pregsub() to 64K, add ap_pregsub_ex() for longer strings and with
better error reporting. Modify ap_varbuf_regsub() to be similar to ap_pregsub_ex(). git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1188950 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'server/util.c')
-rw-r--r--server/util.c68
1 files changed, 48 insertions, 20 deletions
diff --git a/server/util.c b/server/util.c
index cdeec894bf..0f772e6305 100644
--- a/server/util.c
+++ b/server/util.c
@@ -370,32 +370,35 @@ AP_DECLARE(const char *) ap_stripprefix(const char *bigstring,
* AT&T V8 regexp package.
*/
-static char *regsub_core(apr_pool_t *p, struct ap_varbuf *vb,
- const char *input, const char *source,
- size_t nmatch, ap_regmatch_t pmatch[])
+static apr_status_t regsub_core(apr_pool_t *p, char **result,
+ struct ap_varbuf *vb, const char *input,
+ const char *source, size_t nmatch,
+ ap_regmatch_t pmatch[], apr_size_t maxlen)
{
const char *src = input;
- char *dest, *dst;
+ char *dst;
char c;
size_t no;
- int len;
+ apr_size_t len = 0;
+ AP_DEBUG_ASSERT((result && p && !vb) || (vb && !p && !result));
if (!source)
- return NULL;
+ return APR_EINVAL;
if (!nmatch || nmatch>AP_MAX_REG_MATCH) {
+ len = strlen(src);
+ if (maxlen > 0 && len > maxlen)
+ return APR_ENOMEM;
if (!vb) {
- return apr_pstrdup(p, src);
+ *result = apr_pstrmemdup(p, src, len);
+ return APR_SUCCESS;
}
else {
- ap_varbuf_strcat(vb, src);
- return NULL;
+ ap_varbuf_strmemcat(vb, src, len);
+ return APR_SUCCESS;
}
}
/* First pass, find the size */
-
- len = 0;
-
while ((c = *src++) != '\0') {
if (c == '$' && apr_isdigit(*src))
no = *src++ - '0';
@@ -413,14 +416,17 @@ static char *regsub_core(apr_pool_t *p, struct ap_varbuf *vb,
}
+ if (len > maxlen && maxlen > 0)
+ return APR_ENOMEM;
+
if (!vb) {
- dest = dst = apr_pcalloc(p, len + 1);
+ *result = dst = apr_pcalloc(p, len + 1);
}
else {
if (vb->buf && vb->strlen == AP_VARBUF_UNKNOWN)
vb->strlen = strlen(vb->buf);
ap_varbuf_grow(vb, vb->strlen + len);
- dest = dst = vb->buf + vb->strlen;
+ dst = vb->buf + vb->strlen;
vb->strlen += len;
}
@@ -450,14 +456,34 @@ static char *regsub_core(apr_pool_t *p, struct ap_varbuf *vb,
}
*dst = '\0';
- return dest;
+ return APR_SUCCESS;
}
+#ifndef AP_PREGSUB_MAXLEN
+#define AP_PREGSUB_MAXLEN 65536
+#endif
AP_DECLARE(char *) ap_pregsub(apr_pool_t *p, const char *input,
const char *source, size_t nmatch,
ap_regmatch_t pmatch[])
{
- return regsub_core(p, NULL, input, source, nmatch, pmatch);
+ char *result;
+ apr_status_t rc = regsub_core(p, &result, NULL, input, source, nmatch,
+ pmatch, AP_PREGSUB_MAXLEN);
+ if (rc != APR_SUCCESS)
+ result = NULL;
+ return result;
+}
+
+AP_DECLARE(apr_status_t) ap_pregsub_ex(apr_pool_t *p, char **result,
+ const char *input, const char *source,
+ size_t nmatch, ap_regmatch_t pmatch[],
+ apr_size_t maxlen)
+{
+ apr_status_t rc = regsub_core(p, result, NULL, input, source, nmatch,
+ pmatch, maxlen);
+ if (rc != APR_SUCCESS)
+ *result = NULL;
+ return rc;
}
/*
@@ -2647,11 +2673,13 @@ AP_DECLARE(char *) ap_varbuf_pdup(apr_pool_t *p, struct ap_varbuf *buf,
return "";
}
-AP_DECLARE(void) ap_varbuf_regsub(struct ap_varbuf *vb, const char *input,
- const char *source, size_t nmatch,
- ap_regmatch_t pmatch[])
+AP_DECLARE(apr_status_t) ap_varbuf_regsub(struct ap_varbuf *vb,
+ const char *input,
+ const char *source, size_t nmatch,
+ ap_regmatch_t pmatch[],
+ apr_size_t maxlen)
{
- regsub_core(NULL, vb, input, source, nmatch, pmatch);
+ return regsub_core(NULL, NULL, vb, input, source, nmatch, pmatch, maxlen);
}
static const char * const oom_message = "[crit] Memory allocation failed, "