From: Amos Jeffries Date: Thu, 8 Sep 2016 08:06:43 +0000 (+1200) Subject: HTTP: do not allow Proxy-Connection to override Connection header X-Git-Tag: SQUID_4_0_14~5 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=1c4feb505b75772519fe47f907ad42117020696d;p=thirdparty%2Fsquid.git HTTP: do not allow Proxy-Connection to override Connection header Proxy-Connection header is never actually valid, it is relevant in HTTP/1.0 messages only when Connection header is missing and not relevant at all in HTTP/1.1 messages. This fixes part of the behaviour, making Squid use Connection header for persistence (keep-alive vs close) checking if one is present instead of letting Proxy-Connection override it. TODO: Proxy-Connection still needs to be ignored completely when the message version is HTTP/1.1. --- diff --git a/src/HttpHeaderTools.cc b/src/HttpHeaderTools.cc index 7015f1b9b8..e5dd451bbc 100644 --- a/src/HttpHeaderTools.cc +++ b/src/HttpHeaderTools.cc @@ -82,32 +82,26 @@ httpHeaderAddContRange(HttpHeader * hdr, HttpHdrRangeSpec spec, int64_t ent_len) } /** - * return true if a given directive is found in at least one of - * the "connection" header-fields note: if Http::HdrType::PROXY_CONNECTION is - * present we ignore Http::HdrType::CONNECTION. + * \return true if a given directive is found in the Connection header field-value. + * + * \note if no Connection header exists we may check the Proxy-Connection header */ -int +bool httpHeaderHasConnDir(const HttpHeader * hdr, const char *directive) { String list; - int res; + /* what type of header do we have? */ + if (hdr->getList(Http::HdrType::CONNECTION, &list)) + return strListIsMember(&list, directive, ',') != 0; #if USE_HTTP_VIOLATIONS - if (hdr->has(Http::HdrType::PROXY_CONNECTION)) - list = hdr->getList(Http::HdrType::PROXY_CONNECTION); - else + if (hdr->getList(Http::HdrType::PROXY_CONNECTION, &list)) + return strListIsMember(&list, directive, ',') != 0; #endif - if (hdr->has(Http::HdrType::CONNECTION)) - list = hdr->getList(Http::HdrType::CONNECTION); - else - return 0; - - res = strListIsMember(&list, directive, ','); - - list.clean(); - return res; + // else, no connection header for it to exist in + return false; } /** handy to printf prefixes of potentially very long buffers */ diff --git a/src/HttpHeaderTools.h b/src/HttpHeaderTools.h index 24e5bc88c1..bb919f6b99 100644 --- a/src/HttpHeaderTools.h +++ b/src/HttpHeaderTools.h @@ -125,7 +125,7 @@ public: /// \return true if and only if no problems were found. bool httpHeaderParseOffset(const char *start, int64_t *offPtr, char **endPtr = nullptr); -int httpHeaderHasConnDir(const HttpHeader * hdr, const char *directive); +bool httpHeaderHasConnDir(const HttpHeader * hdr, const char *directive); int httpHeaderParseInt(const char *start, int *val); void httpHeaderPutStrf(HttpHeader * hdr, Http::HdrType id, const char *fmt,...) PRINTF_FORMAT_ARG3;