wave17: postgres-0001/asterisk-0001/haproxy-0001/nginx-0001; postfix+bevy CLEAN

postgres-0001: pg_inherits.c typeInheritsFrom() BFS visited List → HTAB O(1)
asterisk-0001: app_queue.c interface_exists() ao2_iterator walk → ao2_find O(1)
haproxy-0001: http_ana.c cookie-server scan linked-list → eb-tree index O(log S)
nginx-0001: ngx_http_link_multi_headers() O(H²) double-scan → O(H) hash pass
postfix: CLEAN (htable throughout; two marginal LOW admin-bounded candidates)
bevy: CLEAN (FixedBitSet/HashSet throughout; only hardware-bounded marginals)
This commit is contained in:
russell@unturf.com 2026-03-30 07:57:30 -04:00
parent da8b4a41d6
commit ff6292d067
10 changed files with 627 additions and 252 deletions

View file

@ -0,0 +1,87 @@
import java.util.*;
/**
* CWE-407 unit test for nginx ngx_http_core_module.c defect.
*
* nginx-0001: src/http/ngx_http_core_module.c ngx_http_link_multi_headers()
* Nested double-traversal of r->headers_in.headers to chain duplicate
* header names: outer loop at position i, inner loop scans 0..i-1.
* O(H²) where H = number of incoming request headers.
* Fix: single O(H) pass using a hash map of name → first header pointer;
* append to chain on first match, no backward scan needed.
*/
public class NginxTest {
// Simulate defect: O(H²) double-traversal
static Map<String, List<Integer>> linkMultiHeaders_quadratic(String[] headers) {
// Returns map of name -> list of positions (the "chain")
Map<String, List<Integer>> chains = new LinkedHashMap<>();
for (int i = 0; i < headers.length; i++) {
boolean linked = false;
for (int j = 0; j < i; j++) { // O(H²) total — defect
if (headers[j].equalsIgnoreCase(headers[i])) {
chains.get(headers[j].toLowerCase()).add(i);
linked = true;
break;
}
}
if (!linked) {
List<Integer> chain = new ArrayList<>();
chain.add(i);
chains.put(headers[i].toLowerCase(), chain);
}
}
return chains;
}
// Simulate fix: O(H) single pass with hash map
static Map<String, List<Integer>> linkMultiHeaders_hash(String[] headers) {
Map<String, List<Integer>> chains = new LinkedHashMap<>();
for (int i = 0; i < headers.length; i++) {
String lower = headers[i].toLowerCase();
chains.computeIfAbsent(lower, k -> new ArrayList<>()).add(i); // O(1)
}
return chains;
}
static void testNginx0001() throws Exception {
// Simulate H headers with many duplicates (worst case for O(H²))
// nginx default: ~50 unique header names, many repeated → H=300 total
int H = 300;
int UNIQUE = 20;
String[] headers = new String[H];
String[] names = new String[UNIQUE];
for (int i = 0; i < UNIQUE; i++) names[i] = "X-Header-" + i;
for (int i = 0; i < H; i++) headers[i] = names[i % UNIQUE];
// correctness
Map<String, List<Integer>> r1 = linkMultiHeaders_quadratic(headers);
Map<String, List<Integer>> r2 = linkMultiHeaders_hash(headers);
assert r1.keySet().equals(r2.keySet()) : "must produce same key set";
for (String k : r1.keySet()) {
assert r1.get(k).equals(r2.get(k)) :
"chain mismatch for " + k + ": " + r1.get(k) + " vs " + r2.get(k);
}
// performance
int REPS = 10_000;
long t0 = System.nanoTime();
for (int r = 0; r < REPS; r++) linkMultiHeaders_quadratic(headers);
long tQuad = System.nanoTime() - t0;
t0 = System.nanoTime();
for (int r = 0; r < REPS; r++) linkMultiHeaders_hash(headers);
long tHash = System.nanoTime() - t0;
double ratio = (double) tQuad / tHash;
System.out.printf("nginx-0001: quadratic=%.3fs hash=%.3fs ratio=%.1f×%n",
tQuad / 1e9, tHash / 1e9, ratio);
assert ratio > 3 : "Expected >3× speedup, got " + ratio;
System.out.println("PASS nginx-0001");
}
public static void main(String[] args) throws Exception {
testNginx0001();
System.out.println("ALL PASS");
}
}