From: Stefan Eissing Date: Wed, 23 Nov 2016 16:14:06 +0000 (+0000) Subject: mod_proxy_http2: not forwarding any 1xx responses on frontend HTTP/1.x connections... X-Git-Tag: 2.5.0-alpha~980 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=b1f6b6edd27364bc49ad6a41b9dab88968f5cc22;p=apache mod_proxy_http2: not forwarding any 1xx responses on frontend HTTP/1.x connections. Unless its 100 and the client is expecting that. git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1770998 13f79535-47bb-0310-9956-ffa450edef68 --- diff --git a/docs/log-message-tags/next-number b/docs/log-message-tags/next-number index 98233cb68e..39c4610775 100644 --- a/docs/log-message-tags/next-number +++ b/docs/log-message-tags/next-number @@ -1 +1 @@ -3486 +3488 diff --git a/modules/http2/h2_proxy_session.c b/modules/http2/h2_proxy_session.c index b1929f70b0..25d1eb3d18 100644 --- a/modules/http2/h2_proxy_session.c +++ b/modules/http2/h2_proxy_session.c @@ -160,10 +160,17 @@ static int on_frame_recv(nghttp2_session *ngh2, const nghttp2_frame *frame, } r = stream->r; if (r->status >= 100 && r->status < 200) { - ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, - "h2_proxy_session(%s): got interim HEADERS, status=%d", - session->id, r->status); + /* By default, we will forward all interim responses when + * we are sitting on a HTTP/2 connection to the client */ + int forward = session->h2_front; switch(r->status) { + case 100: + if (stream->waiting_on_100) { + stream->waiting_on_100 = 0; + r->status_line = ap_get_status_line(r->status); + forward = 1; + } + break; case 103: /* workaround until we get this into http protocol base * parts. without this, unknown codes are converted to @@ -174,9 +181,14 @@ static int on_frame_recv(nghttp2_session *ngh2, const nghttp2_frame *frame, r->status_line = ap_get_status_line(r->status); break; } - ap_send_interim_response(r, 1); + ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, APLOGNO(03487) + "h2_proxy_session(%s): got interim HEADERS, " + "status=%d, will forward=%d", + session->id, r->status, forward); + if (forward) { + ap_send_interim_response(r, 1); + } } - stream->waiting_on_100 = 0; stream_resume(stream); break; case NGHTTP2_PING: @@ -582,6 +594,7 @@ static int on_invalid_header_cb(nghttp2_session *ngh2, h2_proxy_session *h2_proxy_session_setup(const char *id, proxy_conn_rec *p_conn, proxy_server_conf *conf, + int h2_front, unsigned char window_bits_connection, unsigned char window_bits_stream, h2_proxy_request_done *done) @@ -602,6 +615,7 @@ h2_proxy_session *h2_proxy_session_setup(const char *id, proxy_conn_rec *p_conn, session->conf = conf; session->pool = p_conn->scpool; session->state = H2_PROXYS_ST_INIT; + session->h2_front = h2_front; session->window_bits_stream = window_bits_stream; session->window_bits_connection = window_bits_connection; session->streams = h2_proxy_ihash_create(pool, offsetof(h2_proxy_stream, id)); diff --git a/modules/http2/h2_proxy_session.h b/modules/http2/h2_proxy_session.h index 709fe4b0b7..c9820563f5 100644 --- a/modules/http2/h2_proxy_session.h +++ b/modules/http2/h2_proxy_session.h @@ -64,6 +64,7 @@ struct h2_proxy_session { unsigned int aborted : 1; unsigned int check_ping : 1; + unsigned int h2_front : 1; /* if front-end connection is HTTP/2 */ h2_proxy_request_done *done; void *user_data; @@ -86,6 +87,7 @@ struct h2_proxy_session { h2_proxy_session *h2_proxy_session_setup(const char *id, proxy_conn_rec *p_conn, proxy_server_conf *conf, + int h2_front, unsigned char window_bits_connection, unsigned char window_bits_stream, h2_proxy_request_done *done); diff --git a/modules/http2/mod_proxy_http2.c b/modules/http2/mod_proxy_http2.c index 503dd7dddf..f9a3b31cc7 100644 --- a/modules/http2/mod_proxy_http2.c +++ b/modules/http2/mod_proxy_http2.c @@ -335,14 +335,17 @@ static apr_status_t next_request(h2_proxy_ctx *ctx, int before_leave) static apr_status_t proxy_engine_run(h2_proxy_ctx *ctx) { apr_status_t status = OK; + int h2_front; /* Step Four: Send the Request in a new HTTP/2 stream and * loop until we got the response or encounter errors. */ ap_log_cerror(APLOG_MARK, APLOG_TRACE1, 0, ctx->owner, "eng(%s): setup session", ctx->engine_id); - ctx->session = h2_proxy_session_setup(ctx->engine_id, ctx->p_conn, ctx->conf, - 30, h2_proxy_log2((int)ctx->req_buffer_size), + h2_front = is_h2? is_h2(ctx->owner) : 0; + ctx->session = h2_proxy_session_setup(ctx->engine_id, ctx->p_conn, ctx->conf, + h2_front, 30, + h2_proxy_log2((int)ctx->req_buffer_size), request_done); if (!ctx->session) { ap_log_cerror(APLOG_MARK, APLOG_DEBUG, 0, ctx->owner,