All 4 squid defects confirmed: squid-0001 CWE-407 NotePairs::appendNewOnly hasPair O(S*D) 374x; squid-0002 CWE-407 removeConnectionHeaderEntries strListIsMember O(H*C) 3x; squid-0003 CWE-312 FTP+Basic auth passwords logged verbatim incl DBG_IMPORTANT; squid-0004 CWE-407 whichPeer() O(P*A) ICP peer map 83x. MOAD-0002 SquidConfig god-object documented (structural). MOAD-0003/0005 CLEAN. All 4 unit tests PASS.
1.5 KiB
squid-0002 — CWE-407 O(H*C) removeConnectionHeaderEntries() strListIsMember inner loop
Target: Squid (squid-cache/squid, depth=1, 2026-03-31)
File: src/HttpHeader.cc
Function: HttpHeader::removeConnectionHeaderEntries()
UNDF: UNDF-2026-000001162
Severity: MEDIUM
MOAD: 0001
Benchmark: 3.27x wallclock, 40x op-count at H=200 headers, C=50 Connection tokens
Defect
removeConnectionHeaderEntries() strips hop-by-hop headers listed in our
Connection: header field. It calls strListIsMember() inside our getEntry()
loop:
// Old comment in code: "think: on-average-best nesting of the two loops"
while ((e = getEntry(&pos))) {
if (strListIsMember(&strConnection, e->name, ',')) // O(C) scan per header
delAt(pos, headers_deleted);
}
strListIsMember() tokenizes our Connection string on each call, doing O(C)
work per header entry. Total: O(H * C) per response hop.
Called in removeHopByHopEntries() for every forwarded HTTP response. At H=200
headers and C=50 Connection tokens: 10,000 string comparisons per response.
Fix
Pre-build an std::unordered_set<SBuf, SBufHashCmp> from Connection tokens once
before our header loop (O(C) inserts), then probe O(1) per header entry. Total:
O(C + H) instead of O(H * C).
Test
test/SquidConnHeaderTest.java — pure Java simulation, no Squid install needed.
3.27x wallclock speedup confirmed at H=200, C=50. Correctness verified (same 3
hop-by-hop headers removed in both paths).