fix CVE-2022-22719 CVE-2022-22720 CVE-2022-22721 CVE-2022-23934 sync from 22.03
This commit is contained in:
parent
54fc6ffb0c
commit
d87931197d
358
backport-001-CVE-2022-23934.patch
Normal file
358
backport-001-CVE-2022-23934.patch
Normal file
@ -0,0 +1,358 @@
|
||||
From 943f57b336f264d77e5b780c82ab73daf3d14deb Mon Sep 17 00:00:00 2001
|
||||
From: Yann Ylavic <ylavic@apache.org>
|
||||
Date: Mon, 7 Mar 2022 14:52:42 +0000
|
||||
Subject: [PATCH] mod_sed: use size_t to allow for larger buffer sizes and
|
||||
unsigned arithmetics.
|
||||
|
||||
Let's switch to apr_size_t buffers and get rid of the ints.
|
||||
|
||||
|
||||
Merge r1898690 from trunk.
|
||||
Submitted by: rpluem
|
||||
Reviewed by: rpluem, covener, ylavic
|
||||
|
||||
|
||||
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1898695 13f79535-47bb-0310-9956-ffa450edef68
|
||||
---
|
||||
modules/filters/libsed.h | 12 +++---
|
||||
modules/filters/mod_sed.c | 10 ++---
|
||||
modules/filters/sed1.c | 79 +++++++++++++++++++++++----------------
|
||||
3 files changed, 58 insertions(+), 43 deletions(-)
|
||||
|
||||
diff --git a/modules/filters/libsed.h b/modules/filters/libsed.h
|
||||
index 76cbc0ce8ad..0256b1ea831 100644
|
||||
--- a/modules/filters/libsed.h
|
||||
+++ b/modules/filters/libsed.h
|
||||
@@ -60,7 +60,7 @@ struct sed_label_s {
|
||||
};
|
||||
|
||||
typedef apr_status_t (sed_err_fn_t)(void *data, const char *error);
|
||||
-typedef apr_status_t (sed_write_fn_t)(void *ctx, char *buf, int sz);
|
||||
+typedef apr_status_t (sed_write_fn_t)(void *ctx, char *buf, apr_size_t sz);
|
||||
|
||||
typedef struct sed_commands_s sed_commands_t;
|
||||
#define NWFILES 11 /* 10 plus one for standard output */
|
||||
@@ -69,7 +69,7 @@ struct sed_commands_s {
|
||||
sed_err_fn_t *errfn;
|
||||
void *data;
|
||||
|
||||
- unsigned lsize;
|
||||
+ apr_size_t lsize;
|
||||
char *linebuf;
|
||||
char *lbend;
|
||||
const char *saveq;
|
||||
@@ -116,15 +116,15 @@ struct sed_eval_s {
|
||||
apr_int64_t lnum;
|
||||
void *fout;
|
||||
|
||||
- unsigned lsize;
|
||||
+ apr_size_t lsize;
|
||||
char *linebuf;
|
||||
char *lspend;
|
||||
|
||||
- unsigned hsize;
|
||||
+ apr_size_t hsize;
|
||||
char *holdbuf;
|
||||
char *hspend;
|
||||
|
||||
- unsigned gsize;
|
||||
+ apr_size_t gsize;
|
||||
char *genbuf;
|
||||
char *lcomend;
|
||||
|
||||
@@ -160,7 +160,7 @@ apr_status_t sed_init_eval(sed_eval_t *eval, sed_commands_t *commands,
|
||||
sed_err_fn_t *errfn, void *data,
|
||||
sed_write_fn_t *writefn, apr_pool_t *p);
|
||||
apr_status_t sed_reset_eval(sed_eval_t *eval, sed_commands_t *commands, sed_err_fn_t *errfn, void *data);
|
||||
-apr_status_t sed_eval_buffer(sed_eval_t *eval, const char *buf, int bufsz, void *fout);
|
||||
+apr_status_t sed_eval_buffer(sed_eval_t *eval, const char *buf, apr_size_t bufsz, void *fout);
|
||||
apr_status_t sed_eval_file(sed_eval_t *eval, apr_file_t *fin, void *fout);
|
||||
apr_status_t sed_finalize_eval(sed_eval_t *eval, void *f);
|
||||
void sed_destroy_eval(sed_eval_t *eval);
|
||||
diff --git a/modules/filters/mod_sed.c b/modules/filters/mod_sed.c
|
||||
index 9b408029a86..7092dd5e7f1 100644
|
||||
--- a/modules/filters/mod_sed.c
|
||||
+++ b/modules/filters/mod_sed.c
|
||||
@@ -51,7 +51,7 @@ typedef struct sed_filter_ctxt
|
||||
apr_bucket_brigade *bbinp;
|
||||
char *outbuf;
|
||||
char *curoutbuf;
|
||||
- int bufsize;
|
||||
+ apr_size_t bufsize;
|
||||
apr_pool_t *tpool;
|
||||
int numbuckets;
|
||||
} sed_filter_ctxt;
|
||||
@@ -100,7 +100,7 @@ static void alloc_outbuf(sed_filter_ctxt* ctx)
|
||||
/* append_bucket
|
||||
* Allocate a new bucket from buf and sz and append to ctx->bb
|
||||
*/
|
||||
-static apr_status_t append_bucket(sed_filter_ctxt* ctx, char* buf, int sz)
|
||||
+static apr_status_t append_bucket(sed_filter_ctxt* ctx, char* buf, apr_size_t sz)
|
||||
{
|
||||
apr_status_t status = APR_SUCCESS;
|
||||
apr_bucket *b;
|
||||
@@ -133,7 +133,7 @@ static apr_status_t append_bucket(sed_filter_ctxt* ctx, char* buf, int sz)
|
||||
*/
|
||||
static apr_status_t flush_output_buffer(sed_filter_ctxt *ctx)
|
||||
{
|
||||
- int size = ctx->curoutbuf - ctx->outbuf;
|
||||
+ apr_size_t size = ctx->curoutbuf - ctx->outbuf;
|
||||
char *out;
|
||||
apr_status_t status = APR_SUCCESS;
|
||||
if ((ctx->outbuf == NULL) || (size <=0))
|
||||
@@ -147,12 +147,12 @@ static apr_status_t flush_output_buffer(sed_filter_ctxt *ctx)
|
||||
/* This is a call back function. When libsed wants to generate the output,
|
||||
* this function will be invoked.
|
||||
*/
|
||||
-static apr_status_t sed_write_output(void *dummy, char *buf, int sz)
|
||||
+static apr_status_t sed_write_output(void *dummy, char *buf, apr_size_t sz)
|
||||
{
|
||||
/* dummy is basically filter context. Context is passed during invocation
|
||||
* of sed_eval_buffer
|
||||
*/
|
||||
- int remainbytes = 0;
|
||||
+ apr_size_t remainbytes = 0;
|
||||
apr_status_t status = APR_SUCCESS;
|
||||
sed_filter_ctxt *ctx = (sed_filter_ctxt *) dummy;
|
||||
if (ctx->outbuf == NULL) {
|
||||
diff --git a/modules/filters/sed1.c b/modules/filters/sed1.c
|
||||
index be035067885..67a8d06515e 100644
|
||||
--- a/modules/filters/sed1.c
|
||||
+++ b/modules/filters/sed1.c
|
||||
@@ -71,7 +71,7 @@ static apr_status_t dosub(sed_eval_t *eval, char *rhsbuf, int n,
|
||||
static char *place(sed_eval_t *eval, char *asp, char *al1, char *al2);
|
||||
static apr_status_t command(sed_eval_t *eval, sed_reptr_t *ipc,
|
||||
step_vars_storage *step_vars);
|
||||
-static apr_status_t wline(sed_eval_t *eval, char *buf, int sz);
|
||||
+static apr_status_t wline(sed_eval_t *eval, char *buf, apr_size_t sz);
|
||||
static apr_status_t arout(sed_eval_t *eval);
|
||||
|
||||
static void eval_errf(sed_eval_t *eval, const char *fmt, ...)
|
||||
@@ -92,11 +92,11 @@ static void eval_errf(sed_eval_t *eval, const char *fmt, ...)
|
||||
* grow_buffer
|
||||
*/
|
||||
static void grow_buffer(apr_pool_t *pool, char **buffer,
|
||||
- char **spend, unsigned int *cursize,
|
||||
- unsigned int newsize)
|
||||
+ char **spend, apr_size_t *cursize,
|
||||
+ apr_size_t newsize)
|
||||
{
|
||||
char* newbuffer = NULL;
|
||||
- int spendsize = 0;
|
||||
+ apr_size_t spendsize = 0;
|
||||
if (*cursize >= newsize)
|
||||
return;
|
||||
/* Avoid number of times realloc is called. It could cause huge memory
|
||||
@@ -124,7 +124,7 @@ static void grow_buffer(apr_pool_t *pool, char **buffer,
|
||||
/*
|
||||
* grow_line_buffer
|
||||
*/
|
||||
-static void grow_line_buffer(sed_eval_t *eval, int newsize)
|
||||
+static void grow_line_buffer(sed_eval_t *eval, apr_size_t newsize)
|
||||
{
|
||||
grow_buffer(eval->pool, &eval->linebuf, &eval->lspend,
|
||||
&eval->lsize, newsize);
|
||||
@@ -133,7 +133,7 @@ static void grow_line_buffer(sed_eval_t *eval, int newsize)
|
||||
/*
|
||||
* grow_hold_buffer
|
||||
*/
|
||||
-static void grow_hold_buffer(sed_eval_t *eval, int newsize)
|
||||
+static void grow_hold_buffer(sed_eval_t *eval, apr_size_t newsize)
|
||||
{
|
||||
grow_buffer(eval->pool, &eval->holdbuf, &eval->hspend,
|
||||
&eval->hsize, newsize);
|
||||
@@ -142,7 +142,7 @@ static void grow_hold_buffer(sed_eval_t *eval, int newsize)
|
||||
/*
|
||||
* grow_gen_buffer
|
||||
*/
|
||||
-static void grow_gen_buffer(sed_eval_t *eval, int newsize,
|
||||
+static void grow_gen_buffer(sed_eval_t *eval, apr_size_t newsize,
|
||||
char **gspend)
|
||||
{
|
||||
if (gspend == NULL) {
|
||||
@@ -156,9 +156,9 @@ static void grow_gen_buffer(sed_eval_t *eval, int newsize,
|
||||
/*
|
||||
* appendmem_to_linebuf
|
||||
*/
|
||||
-static void appendmem_to_linebuf(sed_eval_t *eval, const char* sz, int len)
|
||||
+static void appendmem_to_linebuf(sed_eval_t *eval, const char* sz, apr_size_t len)
|
||||
{
|
||||
- unsigned int reqsize = (eval->lspend - eval->linebuf) + len;
|
||||
+ apr_size_t reqsize = (eval->lspend - eval->linebuf) + len;
|
||||
if (eval->lsize < reqsize) {
|
||||
grow_line_buffer(eval, reqsize);
|
||||
}
|
||||
@@ -169,21 +169,36 @@ static void appendmem_to_linebuf(sed_eval_t *eval, const char* sz, int len)
|
||||
/*
|
||||
* append_to_linebuf
|
||||
*/
|
||||
-static void append_to_linebuf(sed_eval_t *eval, const char* sz)
|
||||
+static void append_to_linebuf(sed_eval_t *eval, const char* sz,
|
||||
+ step_vars_storage *step_vars)
|
||||
{
|
||||
- int len = strlen(sz);
|
||||
+ apr_size_t len = strlen(sz);
|
||||
+ char *old_linebuf = eval->linebuf;
|
||||
/* Copy string including null character */
|
||||
appendmem_to_linebuf(eval, sz, len + 1);
|
||||
--eval->lspend; /* lspend will now point to NULL character */
|
||||
+ /* Sync step_vars after a possible linebuf expansion */
|
||||
+ if (step_vars && old_linebuf != eval->linebuf) {
|
||||
+ if (step_vars->loc1) {
|
||||
+ step_vars->loc1 = step_vars->loc1 - old_linebuf + eval->linebuf;
|
||||
+ }
|
||||
+ if (step_vars->loc2) {
|
||||
+ step_vars->loc2 = step_vars->loc2 - old_linebuf + eval->linebuf;
|
||||
+ }
|
||||
+ if (step_vars->locs) {
|
||||
+ step_vars->locs = step_vars->locs - old_linebuf + eval->linebuf;
|
||||
+ }
|
||||
+ }
|
||||
}
|
||||
|
||||
/*
|
||||
* copy_to_linebuf
|
||||
*/
|
||||
-static void copy_to_linebuf(sed_eval_t *eval, const char* sz)
|
||||
+static void copy_to_linebuf(sed_eval_t *eval, const char* sz,
|
||||
+ step_vars_storage *step_vars)
|
||||
{
|
||||
eval->lspend = eval->linebuf;
|
||||
- append_to_linebuf(eval, sz);
|
||||
+ append_to_linebuf(eval, sz, step_vars);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -191,8 +206,8 @@ static void copy_to_linebuf(sed_eval_t *eval, const char* sz)
|
||||
*/
|
||||
static void append_to_holdbuf(sed_eval_t *eval, const char* sz)
|
||||
{
|
||||
- int len = strlen(sz);
|
||||
- unsigned int reqsize = (eval->hspend - eval->holdbuf) + len + 1;
|
||||
+ apr_size_t len = strlen(sz);
|
||||
+ apr_size_t reqsize = (eval->hspend - eval->holdbuf) + len + 1;
|
||||
if (eval->hsize <= reqsize) {
|
||||
grow_hold_buffer(eval, reqsize);
|
||||
}
|
||||
@@ -215,8 +230,8 @@ static void copy_to_holdbuf(sed_eval_t *eval, const char* sz)
|
||||
*/
|
||||
static void append_to_genbuf(sed_eval_t *eval, const char* sz, char **gspend)
|
||||
{
|
||||
- int len = strlen(sz);
|
||||
- unsigned int reqsize = (*gspend - eval->genbuf) + len + 1;
|
||||
+ apr_size_t len = strlen(sz);
|
||||
+ apr_size_t reqsize = (*gspend - eval->genbuf) + len + 1;
|
||||
if (eval->gsize < reqsize) {
|
||||
grow_gen_buffer(eval, reqsize, gspend);
|
||||
}
|
||||
@@ -230,8 +245,8 @@ static void append_to_genbuf(sed_eval_t *eval, const char* sz, char **gspend)
|
||||
*/
|
||||
static void copy_to_genbuf(sed_eval_t *eval, const char* sz)
|
||||
{
|
||||
- int len = strlen(sz);
|
||||
- unsigned int reqsize = len + 1;
|
||||
+ apr_size_t len = strlen(sz);
|
||||
+ apr_size_t reqsize = len + 1;
|
||||
if (eval->gsize < reqsize) {
|
||||
grow_gen_buffer(eval, reqsize, NULL);
|
||||
}
|
||||
@@ -353,7 +368,7 @@ apr_status_t sed_eval_file(sed_eval_t *eval, apr_file_t *fin, void *fout)
|
||||
/*
|
||||
* sed_eval_buffer
|
||||
*/
|
||||
-apr_status_t sed_eval_buffer(sed_eval_t *eval, const char *buf, int bufsz, void *fout)
|
||||
+apr_status_t sed_eval_buffer(sed_eval_t *eval, const char *buf, apr_size_t bufsz, void *fout)
|
||||
{
|
||||
apr_status_t rv;
|
||||
|
||||
@@ -383,7 +398,7 @@ apr_status_t sed_eval_buffer(sed_eval_t *eval, const char *buf, int bufsz, void
|
||||
|
||||
while (bufsz) {
|
||||
char *n;
|
||||
- int llen;
|
||||
+ apr_size_t llen;
|
||||
|
||||
n = memchr(buf, '\n', bufsz);
|
||||
if (n == NULL)
|
||||
@@ -442,7 +457,7 @@ apr_status_t sed_finalize_eval(sed_eval_t *eval, void *fout)
|
||||
* buffer is not a newline.
|
||||
*/
|
||||
/* Assure space for NULL */
|
||||
- append_to_linebuf(eval, "");
|
||||
+ append_to_linebuf(eval, "", NULL);
|
||||
}
|
||||
|
||||
*eval->lspend = '\0';
|
||||
@@ -666,7 +681,7 @@ static apr_status_t dosub(sed_eval_t *eval, char *rhsbuf, int n,
|
||||
lp = step_vars->loc2;
|
||||
step_vars->loc2 = sp - eval->genbuf + eval->linebuf;
|
||||
append_to_genbuf(eval, lp, &sp);
|
||||
- copy_to_linebuf(eval, eval->genbuf);
|
||||
+ copy_to_linebuf(eval, eval->genbuf, step_vars);
|
||||
return rv;
|
||||
}
|
||||
|
||||
@@ -676,8 +691,8 @@ static apr_status_t dosub(sed_eval_t *eval, char *rhsbuf, int n,
|
||||
static char *place(sed_eval_t *eval, char *asp, char *al1, char *al2)
|
||||
{
|
||||
char *sp = asp;
|
||||
- int n = al2 - al1;
|
||||
- unsigned int reqsize = (sp - eval->genbuf) + n + 1;
|
||||
+ apr_size_t n = al2 - al1;
|
||||
+ apr_size_t reqsize = (sp - eval->genbuf) + n + 1;
|
||||
|
||||
if (eval->gsize < reqsize) {
|
||||
grow_gen_buffer(eval, reqsize, &sp);
|
||||
@@ -735,7 +750,7 @@ static apr_status_t command(sed_eval_t *eval, sed_reptr_t *ipc,
|
||||
}
|
||||
|
||||
p1++;
|
||||
- copy_to_linebuf(eval, p1);
|
||||
+ copy_to_linebuf(eval, p1, step_vars);
|
||||
eval->jflag++;
|
||||
break;
|
||||
|
||||
@@ -745,12 +760,12 @@ static apr_status_t command(sed_eval_t *eval, sed_reptr_t *ipc,
|
||||
break;
|
||||
|
||||
case GCOM:
|
||||
- copy_to_linebuf(eval, eval->holdbuf);
|
||||
+ copy_to_linebuf(eval, eval->holdbuf, step_vars);
|
||||
break;
|
||||
|
||||
case CGCOM:
|
||||
- append_to_linebuf(eval, "\n");
|
||||
- append_to_linebuf(eval, eval->holdbuf);
|
||||
+ append_to_linebuf(eval, "\n", step_vars);
|
||||
+ append_to_linebuf(eval, eval->holdbuf, step_vars);
|
||||
break;
|
||||
|
||||
case HCOM:
|
||||
@@ -881,7 +896,7 @@ static apr_status_t command(sed_eval_t *eval, sed_reptr_t *ipc,
|
||||
if (rv != APR_SUCCESS)
|
||||
return rv;
|
||||
}
|
||||
- append_to_linebuf(eval, "\n");
|
||||
+ append_to_linebuf(eval, "\n", step_vars);
|
||||
eval->pending = ipc->next;
|
||||
break;
|
||||
|
||||
@@ -956,7 +971,7 @@ static apr_status_t command(sed_eval_t *eval, sed_reptr_t *ipc,
|
||||
|
||||
case XCOM:
|
||||
copy_to_genbuf(eval, eval->linebuf);
|
||||
- copy_to_linebuf(eval, eval->holdbuf);
|
||||
+ copy_to_linebuf(eval, eval->holdbuf, step_vars);
|
||||
copy_to_holdbuf(eval, eval->genbuf);
|
||||
break;
|
||||
|
||||
@@ -1013,7 +1028,7 @@ static apr_status_t arout(sed_eval_t *eval)
|
||||
/*
|
||||
* wline
|
||||
*/
|
||||
-static apr_status_t wline(sed_eval_t *eval, char *buf, int sz)
|
||||
+static apr_status_t wline(sed_eval_t *eval, char *buf, apr_size_t sz)
|
||||
{
|
||||
apr_status_t rv = APR_SUCCESS;
|
||||
rv = eval->writefn(eval->fout, buf, sz);
|
||||
|
||||
61
backport-002-CVE-2022-23934.patch
Normal file
61
backport-002-CVE-2022-23934.patch
Normal file
@ -0,0 +1,61 @@
|
||||
From e266bd09c313a668d7cca17a8b096d189148be49 Mon Sep 17 00:00:00 2001
|
||||
From: Ruediger Pluem <rpluem@apache.org>
|
||||
Date: Wed, 9 Mar 2022 07:41:40 +0000
|
||||
Subject: [PATCH] Merge r1898735 from trunk:
|
||||
|
||||
* Improve the logic flow
|
||||
|
||||
Reviewed by: rpluem, covener, ylavic
|
||||
|
||||
|
||||
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1898772 13f79535-47bb-0310-9956-ffa450edef68
|
||||
---
|
||||
modules/filters/mod_sed.c | 30 +++++++++++++++++++-----------
|
||||
1 file changed, 19 insertions(+), 11 deletions(-)
|
||||
|
||||
diff --git a/modules/filters/mod_sed.c b/modules/filters/mod_sed.c
|
||||
index 7092dd5e7f1..4bdb4ce33ae 100644
|
||||
--- a/modules/filters/mod_sed.c
|
||||
+++ b/modules/filters/mod_sed.c
|
||||
@@ -168,21 +168,29 @@ static apr_status_t sed_write_output(void *dummy, char *buf, apr_size_t sz)
|
||||
}
|
||||
/* buffer is now full */
|
||||
status = append_bucket(ctx, ctx->outbuf, ctx->bufsize);
|
||||
- /* old buffer is now used so allocate new buffer */
|
||||
- alloc_outbuf(ctx);
|
||||
- /* if size is bigger than the allocated buffer directly add to output
|
||||
- * brigade */
|
||||
- if ((status == APR_SUCCESS) && (sz >= ctx->bufsize)) {
|
||||
- char* newbuf = apr_pmemdup(ctx->tpool, buf, sz);
|
||||
- status = append_bucket(ctx, newbuf, sz);
|
||||
- /* pool might get clear after append_bucket */
|
||||
- if (ctx->outbuf == NULL) {
|
||||
+ if (status == APR_SUCCESS) {
|
||||
+ /* if size is bigger than the allocated buffer directly add to output
|
||||
+ * brigade */
|
||||
+ if (sz >= ctx->bufsize) {
|
||||
+ char* newbuf = apr_pmemdup(ctx->tpool, buf, sz);
|
||||
+ status = append_bucket(ctx, newbuf, sz);
|
||||
+ if (status == APR_SUCCESS) {
|
||||
+ /* old buffer is now used so allocate new buffer */
|
||||
+ alloc_outbuf(ctx);
|
||||
+ }
|
||||
+ else {
|
||||
+ clear_ctxpool(ctx);
|
||||
+ }
|
||||
+ }
|
||||
+ else {
|
||||
+ /* old buffer is now used so allocate new buffer */
|
||||
alloc_outbuf(ctx);
|
||||
+ memcpy(ctx->curoutbuf, buf, sz);
|
||||
+ ctx->curoutbuf += sz;
|
||||
}
|
||||
}
|
||||
else {
|
||||
- memcpy(ctx->curoutbuf, buf, sz);
|
||||
- ctx->curoutbuf += sz;
|
||||
+ clear_ctxpool(ctx);
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
||||
93
backport-CVE-2022-22719.patch
Normal file
93
backport-CVE-2022-22719.patch
Normal file
@ -0,0 +1,93 @@
|
||||
From 1b96582269d9ec7c82ee0fea1f67934e4b8176ad Mon Sep 17 00:00:00 2001
|
||||
From: Yann Ylavic <ylavic@apache.org>
|
||||
Date: Mon, 7 Mar 2022 14:51:19 +0000
|
||||
Subject: [PATCH] mod_lua: Error out if lua_read_body() or lua_write_body()
|
||||
fail.
|
||||
|
||||
Otherwise r:requestbody() or r:parsebody() failures might go unnoticed for
|
||||
the user.
|
||||
|
||||
|
||||
Merge r1898689 from trunk.
|
||||
Submitted by: rpluem
|
||||
Reviewed by: rpluem, covener, ylavic
|
||||
|
||||
|
||||
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1898694 13f79535-47bb-0310-9956-ffa450edef68
|
||||
---
|
||||
modules/lua/lua_request.c | 33 ++++++++++++++++++++-------------
|
||||
1 file changed, 20 insertions(+), 13 deletions(-)
|
||||
|
||||
diff --git a/modules/lua/lua_request.c b/modules/lua/lua_request.c
|
||||
index 493b2bb431c..1eab7b6a47b 100644
|
||||
--- a/modules/lua/lua_request.c
|
||||
+++ b/modules/lua/lua_request.c
|
||||
@@ -235,14 +235,16 @@ static int lua_read_body(request_rec *r, const char **rbuf, apr_off_t *size,
|
||||
{
|
||||
int rc = OK;
|
||||
|
||||
+ *rbuf = NULL;
|
||||
+ *size = 0;
|
||||
+
|
||||
if ((rc = ap_setup_client_block(r, REQUEST_CHUNKED_ERROR))) {
|
||||
return (rc);
|
||||
}
|
||||
if (ap_should_client_block(r)) {
|
||||
|
||||
/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
|
||||
- char argsbuffer[HUGE_STRING_LEN];
|
||||
- apr_off_t rsize, len_read, rpos = 0;
|
||||
+ apr_off_t len_read, rpos = 0;
|
||||
apr_off_t length = r->remaining;
|
||||
/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
|
||||
|
||||
@@ -250,18 +252,18 @@ static int lua_read_body(request_rec *r, const char **rbuf, apr_off_t *size,
|
||||
return APR_EINCOMPLETE; /* Only room for incomplete data chunk :( */
|
||||
}
|
||||
*rbuf = (const char *) apr_pcalloc(r->pool, (apr_size_t) (length + 1));
|
||||
- *size = length;
|
||||
- while ((len_read = ap_get_client_block(r, argsbuffer, sizeof(argsbuffer))) > 0) {
|
||||
- if ((rpos + len_read) > length) {
|
||||
- rsize = length - rpos;
|
||||
- }
|
||||
- else {
|
||||
- rsize = len_read;
|
||||
- }
|
||||
-
|
||||
- memcpy((char *) *rbuf + rpos, argsbuffer, (size_t) rsize);
|
||||
- rpos += rsize;
|
||||
+ while ((rpos < length)
|
||||
+ && (len_read = ap_get_client_block(r, (char *) *rbuf + rpos,
|
||||
+ length - rpos)) > 0) {
|
||||
+ rpos += len_read;
|
||||
+ }
|
||||
+ if (len_read < 0) {
|
||||
+ return APR_EINCOMPLETE;
|
||||
}
|
||||
+ *size = rpos;
|
||||
+ }
|
||||
+ else {
|
||||
+ rc = DONE;
|
||||
}
|
||||
|
||||
return (rc);
|
||||
@@ -278,6 +280,8 @@ static apr_status_t lua_write_body(request_rec *r, apr_file_t *file, apr_off_t *
|
||||
{
|
||||
apr_status_t rc = OK;
|
||||
|
||||
+ *size = 0;
|
||||
+
|
||||
if ((rc = ap_setup_client_block(r, REQUEST_CHUNKED_ERROR)))
|
||||
return rc;
|
||||
if (ap_should_client_block(r)) {
|
||||
@@ -303,6 +307,9 @@ static apr_status_t lua_write_body(request_rec *r, apr_file_t *file, apr_off_t *
|
||||
rpos += rsize;
|
||||
}
|
||||
}
|
||||
+ else {
|
||||
+ rc = DONE;
|
||||
+ }
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
187
backport-CVE-2022-22720.patch
Normal file
187
backport-CVE-2022-22720.patch
Normal file
@ -0,0 +1,187 @@
|
||||
From 19aa2d83b379719420f3a178413325156d7a62f3 Mon Sep 17 00:00:00 2001
|
||||
From: Yann Ylavic <ylavic@apache.org>
|
||||
Date: Mon, 7 Mar 2022 14:46:08 +0000
|
||||
Subject: [PATCH] core: Simpler connection close logic if discarding the
|
||||
request body fails.
|
||||
|
||||
If ap_discard_request_body() sets AP_CONN_CLOSE by itself it simplifies and
|
||||
allows to consolidate end_output_stream() and error_output_stream().
|
||||
|
||||
|
||||
Merge r1898683 from trunk.
|
||||
Submitted by: ylavic, rpluem
|
||||
Reviewed by: ylavic, rpluem, covener
|
||||
|
||||
|
||||
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1898692 13f79535-47bb-0310-9956-ffa450edef68
|
||||
---
|
||||
changes-entries/discard_body.diff | 2 +
|
||||
modules/http/http_filters.c | 69 ++++++++++++++++---------------
|
||||
server/protocol.c | 14 +++++--
|
||||
3 files changed, 48 insertions(+), 37 deletions(-)
|
||||
create mode 100644 changes-entries/discard_body.diff
|
||||
|
||||
diff --git a/changes-entries/discard_body.diff b/changes-entries/discard_body.diff
|
||||
new file mode 100644
|
||||
index 00000000000..6b467ac5ee3
|
||||
--- /dev/null
|
||||
+++ b/changes-entries/discard_body.diff
|
||||
@@ -0,0 +1,2 @@
|
||||
+ *) core: Simpler connection close logic if discarding the request body fails.
|
||||
+ [Yann Ylavic, Ruediger Pluem]
|
||||
\ No newline at end of file
|
||||
diff --git a/modules/http/http_filters.c b/modules/http/http_filters.c
|
||||
index d9b36212155..43e8c6dd5d5 100644
|
||||
--- a/modules/http/http_filters.c
|
||||
+++ b/modules/http/http_filters.c
|
||||
@@ -1598,9 +1598,9 @@ AP_DECLARE(int) ap_map_http_request_error(apr_status_t rv, int status)
|
||||
*/
|
||||
AP_DECLARE(int) ap_discard_request_body(request_rec *r)
|
||||
{
|
||||
+ int rc = OK;
|
||||
+ conn_rec *c = r->connection;
|
||||
apr_bucket_brigade *bb;
|
||||
- int seen_eos;
|
||||
- apr_status_t rv;
|
||||
|
||||
/* Sometimes we'll get in a state where the input handling has
|
||||
* detected an error where we want to drop the connection, so if
|
||||
@@ -1609,54 +1609,57 @@ AP_DECLARE(int) ap_discard_request_body(request_rec *r)
|
||||
*
|
||||
* This function is also a no-op on a subrequest.
|
||||
*/
|
||||
- if (r->main || r->connection->keepalive == AP_CONN_CLOSE ||
|
||||
- ap_status_drops_connection(r->status)) {
|
||||
+ if (r->main || c->keepalive == AP_CONN_CLOSE) {
|
||||
+ return OK;
|
||||
+ }
|
||||
+ if (ap_status_drops_connection(r->status)) {
|
||||
+ c->keepalive = AP_CONN_CLOSE;
|
||||
return OK;
|
||||
}
|
||||
|
||||
bb = apr_brigade_create(r->pool, r->connection->bucket_alloc);
|
||||
- seen_eos = 0;
|
||||
- do {
|
||||
- apr_bucket *bucket;
|
||||
+ for (;;) {
|
||||
+ apr_status_t rv;
|
||||
|
||||
rv = ap_get_brigade(r->input_filters, bb, AP_MODE_READBYTES,
|
||||
APR_BLOCK_READ, HUGE_STRING_LEN);
|
||||
-
|
||||
if (rv != APR_SUCCESS) {
|
||||
- apr_brigade_destroy(bb);
|
||||
- return ap_map_http_request_error(rv, HTTP_BAD_REQUEST);
|
||||
+ rc = ap_map_http_request_error(rv, HTTP_BAD_REQUEST);
|
||||
+ goto cleanup;
|
||||
}
|
||||
|
||||
- for (bucket = APR_BRIGADE_FIRST(bb);
|
||||
- bucket != APR_BRIGADE_SENTINEL(bb);
|
||||
- bucket = APR_BUCKET_NEXT(bucket))
|
||||
- {
|
||||
- const char *data;
|
||||
- apr_size_t len;
|
||||
+ while (!APR_BRIGADE_EMPTY(bb)) {
|
||||
+ apr_bucket *b = APR_BRIGADE_FIRST(bb);
|
||||
|
||||
- if (APR_BUCKET_IS_EOS(bucket)) {
|
||||
- seen_eos = 1;
|
||||
- break;
|
||||
- }
|
||||
-
|
||||
- /* These are metadata buckets. */
|
||||
- if (bucket->length == 0) {
|
||||
- continue;
|
||||
+ if (APR_BUCKET_IS_EOS(b)) {
|
||||
+ goto cleanup;
|
||||
}
|
||||
|
||||
- /* We MUST read because in case we have an unknown-length
|
||||
- * bucket or one that morphs, we want to exhaust it.
|
||||
+ /* There is no need to read empty or metadata buckets or
|
||||
+ * buckets of known length, but we MUST read buckets of
|
||||
+ * unknown length in order to exhaust them.
|
||||
*/
|
||||
- rv = apr_bucket_read(bucket, &data, &len, APR_BLOCK_READ);
|
||||
- if (rv != APR_SUCCESS) {
|
||||
- apr_brigade_destroy(bb);
|
||||
- return HTTP_BAD_REQUEST;
|
||||
+ if (b->length == (apr_size_t)-1) {
|
||||
+ apr_size_t len;
|
||||
+ const char *data;
|
||||
+
|
||||
+ rv = apr_bucket_read(b, &data, &len, APR_BLOCK_READ);
|
||||
+ if (rv != APR_SUCCESS) {
|
||||
+ rc = HTTP_BAD_REQUEST;
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
}
|
||||
+
|
||||
+ apr_bucket_delete(b);
|
||||
}
|
||||
- apr_brigade_cleanup(bb);
|
||||
- } while (!seen_eos);
|
||||
+ }
|
||||
|
||||
- return OK;
|
||||
+cleanup:
|
||||
+ apr_brigade_cleanup(bb);
|
||||
+ if (rc != OK) {
|
||||
+ c->keepalive = AP_CONN_CLOSE;
|
||||
+ }
|
||||
+ return rc;
|
||||
}
|
||||
|
||||
/* Here we deal with getting the request message body from the client.
|
||||
diff --git a/server/protocol.c b/server/protocol.c
|
||||
index 2214f72b5a4..298f61e1fb8 100644
|
||||
--- a/server/protocol.c
|
||||
+++ b/server/protocol.c
|
||||
@@ -1687,23 +1687,29 @@ AP_DECLARE(void) ap_set_sub_req_protocol(request_rec *rnew,
|
||||
rnew->main = (request_rec *) r;
|
||||
}
|
||||
|
||||
-static void end_output_stream(request_rec *r)
|
||||
+static void end_output_stream(request_rec *r, int status)
|
||||
{
|
||||
conn_rec *c = r->connection;
|
||||
apr_bucket_brigade *bb;
|
||||
apr_bucket *b;
|
||||
|
||||
bb = apr_brigade_create(r->pool, c->bucket_alloc);
|
||||
+ if (status != OK) {
|
||||
+ b = ap_bucket_error_create(status, NULL, r->pool, c->bucket_alloc);
|
||||
+ APR_BRIGADE_INSERT_TAIL(bb, b);
|
||||
+ }
|
||||
b = apr_bucket_eos_create(c->bucket_alloc);
|
||||
APR_BRIGADE_INSERT_TAIL(bb, b);
|
||||
+
|
||||
ap_pass_brigade(r->output_filters, bb);
|
||||
+ apr_brigade_cleanup(bb);
|
||||
}
|
||||
|
||||
AP_DECLARE(void) ap_finalize_sub_req_protocol(request_rec *sub)
|
||||
{
|
||||
/* tell the filter chain there is no more content coming */
|
||||
if (!sub->eos_sent) {
|
||||
- end_output_stream(sub);
|
||||
+ end_output_stream(sub, OK);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1714,11 +1720,11 @@ AP_DECLARE(void) ap_finalize_sub_req_protocol(request_rec *sub)
|
||||
*/
|
||||
AP_DECLARE(void) ap_finalize_request_protocol(request_rec *r)
|
||||
{
|
||||
- (void) ap_discard_request_body(r);
|
||||
+ int status = ap_discard_request_body(r);
|
||||
|
||||
/* tell the filter chain there is no more content coming */
|
||||
if (!r->eos_sent) {
|
||||
- end_output_stream(r);
|
||||
+ end_output_stream(r, status);
|
||||
}
|
||||
}
|
||||
|
||||
113
backport-CVE-2022-22721.patch
Normal file
113
backport-CVE-2022-22721.patch
Normal file
@ -0,0 +1,113 @@
|
||||
From 5a72f0fe6f2f8ce35c45242e99a421dc19251ab5 Mon Sep 17 00:00:00 2001
|
||||
From: Yann Ylavic <ylavic@apache.org>
|
||||
Date: Mon, 7 Mar 2022 14:48:54 +0000
|
||||
Subject: [PATCH] core: Make sure and check that LimitXMLRequestBody fits in
|
||||
system memory.
|
||||
|
||||
LimitXMLRequestBody can not exceed the size needed to ap_escape_html2() the
|
||||
body without failing to allocate memory, so enforce this at load time based
|
||||
on APR_SIZE_MAX, and make sure that ap_escape_html2() is within the bounds.
|
||||
|
||||
Document the limits for LimitXMLRequestBody in our docs.
|
||||
|
||||
|
||||
Merge r1898686 from trunk.
|
||||
Submitted by: ylavic, rpluem
|
||||
Reviewed by: ylavic, covener, rpluem
|
||||
|
||||
|
||||
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1898693 13f79535-47bb-0310-9956-ffa450edef68
|
||||
---
|
||||
changes-entries/AP_MAX_LIMIT_XML_BODY.diff | 2 ++
|
||||
server/core.c | 9 +++++++++
|
||||
server/util.c | 8 ++++++--
|
||||
server/util_xml.c | 2 +-
|
||||
4 files changed, 27 insertions(+), 6 deletions(-)
|
||||
create mode 100644 changes-entries/AP_MAX_LIMIT_XML_BODY.diff
|
||||
|
||||
diff --git a/changes-entries/AP_MAX_LIMIT_XML_BODY.diff b/changes-entries/AP_MAX_LIMIT_XML_BODY.diff
|
||||
new file mode 100644
|
||||
index 00000000000..07fef3c624c
|
||||
--- /dev/null
|
||||
+++ b/changes-entries/AP_MAX_LIMIT_XML_BODY.diff
|
||||
@@ -0,0 +1,2 @@
|
||||
+ *) core: Make sure and check that LimitXMLRequestBody fits in system memory.
|
||||
+ [Ruediger Pluem, Yann Ylavic]
|
||||
\ No newline at end of file
|
||||
diff --git a/server/core.c b/server/core.c
|
||||
index 798212b4808..090e3976421 100644
|
||||
--- a/server/core.c
|
||||
+++ b/server/core.c
|
||||
@@ -72,6 +72,8 @@
|
||||
/* LimitXMLRequestBody handling */
|
||||
#define AP_LIMIT_UNSET ((long) -1)
|
||||
#define AP_DEFAULT_LIMIT_XML_BODY ((apr_size_t)1000000)
|
||||
+/* Hard limit for ap_escape_html2() */
|
||||
+#define AP_MAX_LIMIT_XML_BODY ((apr_size_t)(APR_SIZE_MAX / 6 - 1))
|
||||
|
||||
#define AP_MIN_SENDFILE_BYTES (256)
|
||||
|
||||
@@ -3761,6 +3763,11 @@ static const char *set_limit_xml_req_body(cmd_parms *cmd, void *conf_,
|
||||
if (conf->limit_xml_body < 0)
|
||||
return "LimitXMLRequestBody requires a non-negative integer.";
|
||||
|
||||
+ /* zero is AP_MAX_LIMIT_XML_BODY (implicitly) */
|
||||
+ if ((apr_size_t)conf->limit_xml_body > AP_MAX_LIMIT_XML_BODY)
|
||||
+ return apr_psprintf(cmd->pool, "LimitXMLRequestBody must not exceed "
|
||||
+ "%" APR_SIZE_T_FMT, AP_MAX_LIMIT_XML_BODY);
|
||||
+
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -3849,6 +3856,8 @@ AP_DECLARE(apr_size_t) ap_get_limit_xml_body(const request_rec *r)
|
||||
conf = ap_get_core_module_config(r->per_dir_config);
|
||||
if (conf->limit_xml_body == AP_LIMIT_UNSET)
|
||||
return AP_DEFAULT_LIMIT_XML_BODY;
|
||||
+ if (conf->limit_xml_body == 0)
|
||||
+ return AP_MAX_LIMIT_XML_BODY;
|
||||
|
||||
return (apr_size_t)conf->limit_xml_body;
|
||||
}
|
||||
diff --git a/server/util.c b/server/util.c
|
||||
index 6cfe0035c49..604be1a1ce3 100644
|
||||
--- a/server/util.c
|
||||
+++ b/server/util.c
|
||||
@@ -2142,11 +2142,14 @@ AP_DECLARE(char *) ap_escape_urlencoded(apr_pool_t *p, const char *buffer)
|
||||
|
||||
AP_DECLARE(char *) ap_escape_html2(apr_pool_t *p, const char *s, int toasc)
|
||||
{
|
||||
- int i, j;
|
||||
+ apr_size_t i, j;
|
||||
char *x;
|
||||
|
||||
/* first, count the number of extra characters */
|
||||
- for (i = 0, j = 0; s[i] != '\0'; i++)
|
||||
+ for (i = 0, j = 0; s[i] != '\0'; i++) {
|
||||
+ if (i + j > APR_SIZE_MAX - 6) {
|
||||
+ abort();
|
||||
+ }
|
||||
if (s[i] == '<' || s[i] == '>')
|
||||
j += 3;
|
||||
else if (s[i] == '&')
|
||||
@@ -2155,6 +2158,7 @@ AP_DECLARE(char *) ap_escape_html2(apr_pool_t *p, const char *s, int toasc)
|
||||
j += 5;
|
||||
else if (toasc && !apr_isascii(s[i]))
|
||||
j += 5;
|
||||
+ }
|
||||
|
||||
if (j == 0)
|
||||
return apr_pstrmemdup(p, s, i);
|
||||
diff --git a/server/util_xml.c b/server/util_xml.c
|
||||
index 4845194656e..22806fa8a40 100644
|
||||
--- a/server/util_xml.c
|
||||
+++ b/server/util_xml.c
|
||||
@@ -85,7 +85,7 @@ AP_DECLARE(int) ap_xml_parse_input(request_rec * r, apr_xml_doc **pdoc)
|
||||
}
|
||||
|
||||
total_read += len;
|
||||
- if (limit_xml_body && total_read > limit_xml_body) {
|
||||
+ if (total_read > limit_xml_body) {
|
||||
ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(00539)
|
||||
"XML request body is larger than the configured "
|
||||
"limit of %lu", (unsigned long)limit_xml_body);
|
||||
|
||||
17
httpd.spec
17
httpd.spec
@ -8,7 +8,7 @@
|
||||
Name: httpd
|
||||
Summary: Apache HTTP Server
|
||||
Version: 2.4.51
|
||||
Release: 1
|
||||
Release: 2
|
||||
License: ASL 2.0
|
||||
URL: https://httpd.apache.org/
|
||||
Source0: https://archive.apache.org/dist/httpd/httpd-%{version}.tar.bz2
|
||||
@ -68,8 +68,13 @@ Patch14: backport-layout_add_openEuler.patch
|
||||
Patch15: backport-httpd-2.4.43-gettid.patch
|
||||
Patch16: backport-httpd-2.4.43-r1861793+.patch
|
||||
Patch17: backport-httpd-2.4.48-r1828172+.patch
|
||||
Patch18: backport-httpd-2.4.46-htcacheclean-dont-break.patch
|
||||
Patch19: backport-CVE-2021-44790.patch
|
||||
Patch18: backport-httpd-2.4.46-htcacheclean-dont-break.patch
|
||||
Patch19: backport-CVE-2022-22719.patch
|
||||
Patch20: backport-CVE-2022-22720.patch
|
||||
Patch21: backport-CVE-2022-22721.patch
|
||||
Patch22: backport-001-CVE-2022-23934.patch
|
||||
Patch23: backport-002-CVE-2022-23934.patch
|
||||
Patch24: backport-CVE-2021-44790.patch
|
||||
|
||||
BuildRequires: gcc autoconf pkgconfig findutils xmlto perl-interpreter perl-generators systemd-devel
|
||||
BuildRequires: zlib-devel libselinux-devel lua-devel brotli-devel
|
||||
@ -502,6 +507,12 @@ exit $rv
|
||||
%{_rpmconfigdir}/macros.d/macros.httpd
|
||||
|
||||
%changelog
|
||||
* Mon Mar 28 2022 yanglu <yanglu72@h-partners.com> - 2.4.51-2
|
||||
- Type:cves
|
||||
- ID:NA
|
||||
- SUG:restart
|
||||
- DESC:fix CVE-2022-22719 CVE-2022-22720 CVE-2022-22721 CVE-2022-23934
|
||||
|
||||
* Sat Mar 26 2022 yanglu <yanglu72@h-partners.com> - 2.4.51-1
|
||||
- Type:requirement
|
||||
- ID:NA
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user