Compare commits

...

3 Commits

Author SHA1 Message Date
d917a3559d Import from CS git 2025-10-28 07:48:35 +00:00
d7b01e3ac3 Import from CS git 2025-06-04 12:51:06 +00:00
c6d920713f Import from CS git 2025-01-28 08:42:44 +00:00
4 changed files with 315 additions and 2 deletions

View File

@ -0,0 +1,179 @@
diff --git a/src/HttpRequest.cc b/src/HttpRequest.cc
index 38b9307..e0278b7 100644
--- a/src/HttpRequest.cc
+++ b/src/HttpRequest.cc
@@ -341,7 +341,7 @@ HttpRequest::swapOut(StoreEntry * e)
/* packs request-line and headers, appends <crlf> terminator */
void
-HttpRequest::pack(Packable * p) const
+HttpRequest::pack(Packable * const p, const bool maskSensitiveInfo) const
{
assert(p);
/* pack request-line */
@@ -349,8 +349,8 @@ HttpRequest::pack(Packable * p) const
SQUIDSBUFPRINT(method.image()), SQUIDSBUFPRINT(url.path()),
http_ver.major, http_ver.minor);
/* headers */
- header.packInto(p);
- /* trailer */
+ header.packInto(p, maskSensitiveInfo);
+ /* indicate the end of the header section */
p->append("\r\n", 2);
}
diff --git a/src/HttpRequest.h b/src/HttpRequest.h
index fe706ef..4329d53 100644
--- a/src/HttpRequest.h
+++ b/src/HttpRequest.h
@@ -201,7 +201,7 @@ public:
void swapOut(StoreEntry * e);
- void pack(Packable * p) const;
+ void pack(Packable * p, bool maskSensitiveInfo = false) const;
static void httpRequestPack(void *obj, Packable *p);
diff --git a/src/cf.data.pre b/src/cf.data.pre
index d55b870..7b18b0e 100644
--- a/src/cf.data.pre
+++ b/src/cf.data.pre
@@ -8319,12 +8319,18 @@ NAME: email_err_data
COMMENT: on|off
TYPE: onoff
LOC: Config.onoff.emailErrData
-DEFAULT: on
+DEFAULT: off
DOC_START
If enabled, information about the occurred error will be
included in the mailto links of the ERR pages (if %W is set)
so that the email body contains the data.
Syntax is <A HREF="mailto:%w%W">%w</A>
+
+ SECURITY WARNING:
+ Request headers and other included facts may contain
+ sensitive information about transaction history, the
+ Squid instance, and its environment which would be
+ unavailable to error recipients otherwise.
DOC_END
NAME: deny_info
diff --git a/src/client_side_reply.cc b/src/client_side_reply.cc
index fea5ecb..c7dc756 100644
--- a/src/client_side_reply.cc
+++ b/src/client_side_reply.cc
@@ -100,7 +100,7 @@ clientReplyContext::clientReplyContext(ClientHttpRequest *clientContext) :
void
clientReplyContext::setReplyToError(
err_type err, Http::StatusCode status, const HttpRequestMethod& method, char const *uri,
- Ip::Address &addr, HttpRequest * failedrequest, const char *unparsedrequest,
+ Ip::Address &addr, HttpRequest * failedrequest, const char *,
#if USE_AUTH
Auth::UserRequest::Pointer auth_user_request
#else
@@ -110,9 +110,6 @@ clientReplyContext::setReplyToError(
{
ErrorState *errstate = clientBuildError(err, status, uri, addr, failedrequest);
- if (unparsedrequest)
- errstate->request_hdrs = xstrdup(unparsedrequest);
-
#if USE_AUTH
errstate->auth_user_request = auth_user_request;
#endif
@@ -1078,10 +1075,13 @@ clientReplyContext::traceReply()
triggerInitialStoreRead();
http->storeEntry()->releaseRequest();
http->storeEntry()->buffer();
+ MemBuf *content = new MemBuf;
+ content->init();
+ http->request->pack(content, true /* hide authorization data */);
HttpReply *rep = new HttpReply;
- rep->setHeaders(Http::scOkay, NULL, "text/plain", http->request->prefixLen(), 0, squid_curtime);
+ rep->setHeaders(Http::scOkay, NULL, "message/http", content->contentSize(), 0, squid_curtime);
+ rep->body.setMb(content);
http->storeEntry()->replaceHttpReply(rep);
- http->request->swapOut(http->storeEntry());
http->storeEntry()->complete();
}
diff --git a/src/errorpage.cc b/src/errorpage.cc
index 72be100..c1f3b25 100644
--- a/src/errorpage.cc
+++ b/src/errorpage.cc
@@ -575,7 +575,6 @@ ErrorState::ErrorState(err_type t, Http::StatusCode status, HttpRequest * req) :
redirect_url(NULL),
callback(NULL),
callback_data(NULL),
- request_hdrs(NULL),
err_msg(NULL),
#if USE_OPENSSL
detail(NULL),
@@ -678,7 +677,6 @@ ErrorState::~ErrorState()
HTTPMSGUNLOCK(request);
safe_free(redirect_url);
safe_free(url);
- safe_free(request_hdrs);
wordlistDestroy(&ftp.server_msg);
safe_free(ftp.request);
safe_free(ftp.reply);
@@ -737,12 +735,10 @@ ErrorState::Dump(MemBuf * mb)
/* - HTTP stuff */
str.append("HTTP Request:\r\n", 15);
if (request) {
- str.appendf(SQUIDSBUFPH " " SQUIDSBUFPH " %s/%d.%d\n",
- SQUIDSBUFPRINT(request->method.image()),
- SQUIDSBUFPRINT(request->url.path()),
- AnyP::ProtocolType_str[request->http_ver.protocol],
- request->http_ver.major, request->http_ver.minor);
- request->header.packInto(&str);
+ MemBuf r;
+ r.init();
+ request->pack(&r, true /* hide authorization data */);
+ str.append(r.content(), r.contentSize());
}
str.append("\r\n", 2);
@@ -961,15 +957,8 @@ ErrorState::Convert(char token, bool building_deny_info_url, bool allowRecursion
p = "[no request]";
break;
}
- if (request != NULL) {
- mb.appendf(SQUIDSBUFPH " " SQUIDSBUFPH " %s/%d.%d\n",
- SQUIDSBUFPRINT(request->method.image()),
- SQUIDSBUFPRINT(request->url.path()),
- AnyP::ProtocolType_str[request->http_ver.protocol],
- request->http_ver.major, request->http_ver.minor);
+ else if (request) {
request->header.packInto(&mb, true); //hide authorization data
- } else if (request_hdrs) {
- p = request_hdrs;
} else {
p = "[no request]";
}
diff --git a/src/errorpage.h b/src/errorpage.h
index 332e507..bf61b4d 100644
--- a/src/errorpage.h
+++ b/src/errorpage.h
@@ -164,7 +164,6 @@ public:
MemBuf *listing;
} ftp;
- char *request_hdrs;
char *err_msg; /* Preformatted error message from the cache */
#if USE_OPENSSL
diff --git a/src/tests/stub_HttpRequest.cc b/src/tests/stub_HttpRequest.cc
index cd18d51..495d786 100644
--- a/src/tests/stub_HttpRequest.cc
+++ b/src/tests/stub_HttpRequest.cc
@@ -45,7 +45,7 @@ bool HttpRequest::expectingBody(const HttpRequestMethod &, int64_t &) const STUB
bool HttpRequest::bodyNibbled() const STUB_RETVAL(false)
int HttpRequest::prefixLen() const STUB_RETVAL(0)
void HttpRequest::swapOut(StoreEntry *) STUB
-void HttpRequest::pack(Packable *) const STUB
+void HttpRequest::pack(Packable *, bool) const STUB
void HttpRequest::httpRequestPack(void *, Packable *) STUB
HttpRequest * HttpRequest::FromUrl(const SBuf &, const MasterXaction::Pointer &, const HttpRequestMethod &) STUB_RETVAL(nullptr)
HttpRequest * HttpRequest::FromUrlXXX(const char *, const MasterXaction::Pointer &, const HttpRequestMethod &) STUB_RETVAL(nullptr)

View File

@ -0,0 +1,61 @@
diff --git a/src/ipcache.cc b/src/ipcache.cc
index ea32021..6012f1f 100644
--- a/src/ipcache.cc
+++ b/src/ipcache.cc
@@ -103,6 +103,7 @@ public:
} flags;
int age() const; ///< time passed since request_time or -1 if unknown
+ void updateTtl(const unsigned int rrTtl);
};
/// \ingroup IPCacheInternal
@@ -338,7 +339,6 @@ ipcacheParse(ipcache_entry *i, const rfc1035_rr * answers, int nr, const char *e
int k;
int j = 0;
int na = 0;
- int ttl = 0;
const char *name = (const char *)i->hash.key;
int cname_found = 0;
@@ -436,8 +436,8 @@ ipcacheParse(ipcache_entry *i, const rfc1035_rr * answers, int nr, const char *e
debugs(14, 3, name << " #" << j << " " << i->addrs.in_addrs[j] );
++j;
}
- if (ttl == 0 || (int) answers[k].ttl < ttl)
- ttl = answers[k].ttl;
+
+ i->updateTtl(answers[k].ttl);
}
assert(j == na);
@@ -447,17 +447,21 @@ ipcacheParse(ipcache_entry *i, const rfc1035_rr * answers, int nr, const char *e
else
i->addrs.count = 255;
- if (ttl > Config.positiveDnsTtl)
- ttl = Config.positiveDnsTtl;
-
- if (ttl < Config.negativeDnsTtl)
- ttl = Config.negativeDnsTtl;
-
- i->expires = squid_curtime + ttl;
-
i->flags.negcached = false;
}
+void
+ipcache_entry::updateTtl(const unsigned int rrTtl)
+{
+ const time_t ttl = std::min(std::max(
+ Config.negativeDnsTtl, // smallest value allowed
+ static_cast<time_t>(rrTtl)),
+ Config.positiveDnsTtl); // largest value allowed
+ const time_t rrExpires = squid_curtime + ttl;
+ if (rrExpires < expires)
+ expires = rrExpires;
+}
+
/// \ingroup IPCacheInternal
static void
ipcacheHandleReply(void *data, const rfc1035_rr * answers, int na, const char *error_message)

View File

@ -0,0 +1,48 @@
From 6c29ec591b1c777fc9a66f810f0ce5bc5076bc40 Mon Sep 17 00:00:00 2001
From: Alex Rousskov <rousskov@measurement-factory.com>
Date: Tue, 14 Nov 2023 18:40:37 +0000
Subject: [PATCH] Bug 5317: FATAL attempt to read data from memory (#1579)
FATAL: Squid has attempted to read data ... that is not present.
Recent commit 122a6e3 attempted to deliver in-memory response body bytes
to a Store-reading client that requested (at least) response headers.
That optimization relied on the old canReadFromMemory() logic, but that
logic results in false positives when the checked read offset falls into
a gap between stored headers and the first body byte of a Content-Range.
In that case, a false positive leads to a readFromMemory() call and a
FATAL mem_hdr::copy() error.
This workaround disables the above optimization without fixing
canReadFromMemory(). We believe that a readFromMemory() call that comes
right after response headers are delivered to the Store-reading client
will not suffer from the same problem because the client will supply the
read offset of the first body byte, eliminating the false positive.
---
src/store_client.cc | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/src/store_client.cc b/src/store_client.cc
index a5f2440..b09f78a 100644
--- a/src/store_client.cc
+++ b/src/store_client.cc
@@ -355,8 +355,9 @@ store_client::doCopy(StoreEntry *anEntry)
return; // failure
}
- // send any immediately available body bytes even if we also sendHttpHeaders
- if (canReadFromMemory()) {
+ // Send any immediately available body bytes unless we sendHttpHeaders.
+ // TODO: Send those body bytes when we sendHttpHeaders as well.
+ if (!sendHttpHeaders && canReadFromMemory()) {
readFromMemory();
noteNews(); // will sendHttpHeaders (if needed) as well
flags.store_copying = false;
@@ -442,6 +443,7 @@ store_client::canReadFromMemory() const
{
const auto &mem = entry->mem();
const auto memReadOffset = nextHttpReadOffset();
+ // XXX: This (lo <= offset < end) logic does not support Content-Range gaps.
return mem.inmem_lo <= memReadOffset && memReadOffset < mem.endOffset() &&
parsingBuffer.first.spaceSize();
}

View File

@ -2,7 +2,7 @@
Name: squid
Version: 4.15
Release: 10%{?dist}.3
Release: 10%{?dist}.9
Summary: The Squid proxy caching server
Epoch: 7
# See CREDITS for breakdown of non GPLv2+ code
@ -40,6 +40,10 @@ Patch208: squid-4.11-convert-ipv4.patch
Patch209: squid-4.15-ftp-filename-extraction.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=2076717
Patch210: squid-4.15-halfclosed.patch
# https://issues.redhat.com/browse/RHEL-66120
Patch211: squid-4.15-dns-obey-ttl-set-to-zero.patch
# https://issues.redhat.com/browse/RHEL-57030
Patch212: squid-4.15-fatal-read-data-from-mem.patch
# Security fixes
# https://bugzilla.redhat.com/show_bug.cgi?id=1941506
@ -74,6 +78,8 @@ Patch312: squid-4.15-CVE-2024-25111.patch
Patch313: squid-4.15-ignore-wsp-after-chunk-size.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=2260051
Patch314: squid-4.15-CVE-2024-23638.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=2404736
Patch315: squid-4.15-CVE-2025-62168.patch
Requires: bash >= 2.0
Requires(pre): shadow-utils
@ -106,7 +112,7 @@ BuildRequires: systemd-devel
%description
Squid is a high-performance proxy caching server for Web clients,
supporting FTP, gopher, and HTTP data objects. Unlike traditional
supporting FTP and HTTP data objects. Unlike traditional
caching software, Squid handles all requests in a single,
non-blocking, I/O-driven process. Squid keeps meta data and especially
hot objects cached in RAM, caches DNS lookups, supports non-blocking
@ -134,6 +140,7 @@ lookup program (dnsserver), a program for retrieving FTP data
%patch208 -p1 -b .convert-ipv4
%patch209 -p1 -b .ftp-fn-extraction
%patch210 -p1 -b .halfclosed
%patch211 -p1 -b .dns-obey-ttl-set-to-zero
# Security patches
%patch300 -p1 -b .CVE-2021-28116
@ -151,6 +158,10 @@ lookup program (dnsserver), a program for retrieving FTP data
%patch312 -p1 -b .CVE-2024-25111
%patch313 -p1 -b .ignore-wsp-chunk-sz
%patch314 -p1 -b .CVE-2024-23638
%patch315 -p1 -b .CVE-2025-62168
# patch305 follow-up
%patch212 -p1 -b .fatal-read-data-from-mem
# https://bugzilla.redhat.com/show_bug.cgi?id=1679526
# Patch in the vendor documentation and used different location for documentation
@ -367,6 +378,20 @@ fi
%changelog
* Mon Oct 20 2025 Luboš Uhliarik <luhliari@redhat.com> - 7:4.15-10.9
- Resolves: RHEL-122484 - squid: Squid vulnerable to information disclosure via
authentication credential leakage in error handling (CVE-2025-62168)
* Wed Mar 26 2025 Luboš Uhliarik <luhliari@redhat.com> - 7:4.15-10.6
- Resolves: RHEL-84420 - A squid child process causes a memory reference error
and the squid service terminates abnormally
* Fri Nov 22 2024 Luboš Uhliarik <luhliari@redhat.com> - 7:4.15-10.5
- Resolves: RHEL-66120 - squid caches DNS entries despite having TTL set to 0
* Mon Nov 18 2024 Luboš Uhliarik <luhliari@redhat.com> - 7:4.15-10.4
- Resolves: RHEL-67870 - Remove gopher mention from spec file
* Wed Nov 13 2024 Luboš Uhliarik <luhliari@redhat.com> - 7:4.15-10.3
- Resolves: RHEL-22593 - CVE-2024-23638 squid:4/squid: vulnerable to
a Denial of Service attack against Cache Manager error responses