From 0724f8982a8cdbaf65d603f40c0d327eb880b408 Mon Sep 17 00:00:00 2001 From: Andy Green Date: Fri, 1 Dec 2017 11:07:00 +0800 Subject: [PATCH] h2: fix multiple cookie header handling Firefox 57 at least still sends multiple cookie: headers over h2. Correctly aggregate them with a ';' delimiter. --- lib/http2/hpack.c | 22 +++++++++++++++++++++- lib/server/cgi.c | 8 +++++--- 2 files changed, 26 insertions(+), 4 deletions(-) diff --git a/lib/http2/hpack.c b/lib/http2/hpack.c index 6533bcbc..f9cbe29c 100644 --- a/lib/http2/hpack.c +++ b/lib/http2/hpack.c @@ -247,7 +247,27 @@ static int lws_frag_start(struct lws *wsi, int hdr_token_idx) ah->hdr_token_idx = hdr_token_idx; - ah->frag_index[hdr_token_idx] = ah->nfrag; + /* + * Okay, but we could be, eg, the second or subsequent cookie: header + */ + + if (ah->frag_index[hdr_token_idx]) { + int n; + + /* find the last fragment for this header... */ + n = ah->frag_index[hdr_token_idx]; + while (ah->frags[n].nfrag) + n = ah->frags[n].nfrag; + /* and point it to continue in our continuation fragment */ + ah->frags[n].nfrag = ah->nfrag; + + /* cookie continuations need a separator token of ';' */ + if (hdr_token_idx == WSI_TOKEN_HTTP_COOKIE) { + ah->data[ah->pos++] = ';'; + ah->frags[ah->nfrag].len++; + } + } else + ah->frag_index[hdr_token_idx] = ah->nfrag; return 0; } diff --git a/lib/server/cgi.c b/lib/server/cgi.c index cff6bb72..106d98c0 100644 --- a/lib/server/cgi.c +++ b/lib/server/cgi.c @@ -299,9 +299,11 @@ lws_cgi(struct lws *wsi, const char * const *exec_array, int script_uri_path_len if (script_uri_path_len >= 0 && lws_hdr_total_length(wsi, WSI_TOKEN_HTTP_COOKIE)) { env_array[n++] = p; - p += lws_snprintf(p, end - p, "HTTP_COOKIE=%s", - lws_hdr_simple_ptr(wsi, WSI_TOKEN_HTTP_COOKIE)); - p++; + p += lws_snprintf(p, end - p, "HTTP_COOKIE="); + m = lws_hdr_copy(wsi, p, end - p, WSI_TOKEN_HTTP_COOKIE); + if (m > 0) + p += lws_hdr_total_length(wsi, WSI_TOKEN_HTTP_COOKIE); + *p++ = '\0'; } if (script_uri_path_len >= 0 && lws_hdr_total_length(wsi, WSI_TOKEN_HTTP_USER_AGENT)) {