diff options
author | Joe Orton <jorton@redhat.com> | 2021-09-17 14:57:34 +0100 |
---|---|---|
committer | Joe Orton <jorton@redhat.com> | 2021-09-17 15:05:38 +0100 |
commit | 25819517f0a4f92d89f38d43012e7ba89fa900ee (patch) | |
tree | d946887e36f540115bc8e0aa0bb20685a724f4b1 | |
parent | b13393cde9de595b206c8f6b0277515d9b5b4182 (diff) | |
download | neon-git-excess-1xx.tar.gz |
* src/ne_request.c (send_request): Limit number of interim responsesexcess-1xx
which can be read to 128.
* test/request.c (fail_excess_1xx): New test case.
-rw-r--r-- | src/ne_request.c | 15 | ||||
-rw-r--r-- | test/request.c | 8 |
2 files changed, 20 insertions, 3 deletions
diff --git a/src/ne_request.c b/src/ne_request.c index 6bed814..9e06b96 100644 --- a/src/ne_request.c +++ b/src/ne_request.c @@ -72,6 +72,8 @@ struct field { struct field *next; }; +/* Maximum number of interim responses. */ +#define MAX_INTERIM_RESPONSES (128) /* Maximum number of header fields per response: */ #define MAX_HEADER_FIELDS (100) /* Size of hash table; 43 is the smallest prime for which the common @@ -1015,6 +1017,7 @@ static int send_request(ne_request *req, const ne_buffer *request) ne_status *const status = &req->status; int sentbody = 0; /* zero until body has been sent. */ int ret, retry; /* retry non-zero whilst the request should be retried */ + unsigned count; ssize_t sret; /* Send the Request-Line and headers */ @@ -1045,9 +1048,11 @@ static int send_request(ne_request *req, const ne_buffer *request) /* Loop eating interim 1xx responses; RFC 7231ยง6.2 says clients * MUST be able to parse unsolicited interim responses. */ - while ((ret = read_status_line(req, status, retry)) == NE_OK - && status->klass == 1) { - NE_DEBUG(NE_DBG_HTTP, "Interim %d response.\n", status->code); + for (count = 0; count < MAX_INTERIM_RESPONSES + && (ret = read_status_line(req, status, retry)) == NE_OK + && status->klass == 1; count++) { + NE_DEBUG(NE_DBG_HTTP, "[req] Interim %d response %d.\n", + status->code, count); retry = 0; /* successful read() => never retry now. */ /* Discard headers with the interim response. */ if ((ret = discard_headers(req)) != NE_OK) break; @@ -1060,6 +1065,10 @@ static int send_request(ne_request *req, const ne_buffer *request) } } + if (count == MAX_INTERIM_RESPONSES) { + return aborted(req, _("Too many interim responses"), 0); + } + return ret; } diff --git a/test/request.c b/test/request.c index 6805024..e663d6d 100644 --- a/test/request.c +++ b/test/request.c @@ -2345,6 +2345,13 @@ static int safe_flags(void) return OK; } +static int fail_excess_1xx(void) +{ + struct s1xx_args args = {200, 0}; + return fail_request_with_error(0, serve_1xx, &args, 0, + "Too many interim responses"); +} + /* TODO: test that ne_set_notifier(, NULL, NULL) DTRT too. */ ne_test tests[] = { @@ -2439,5 +2446,6 @@ ne_test tests[] = { T(fail_lookup), T(fail_double_lookup), T(safe_flags), + T(fail_excess_1xx), T(NULL) }; |