DF-2838 / verdict.json
{ "finding_id": "DF-2838", "status": "reproduced", "reproduced": 1, "impact": "leak", "confidence": "certain", "verdict": "sotoxsocket (uipc_socket2.c:827-848) and ssbtoxsockbuf (188-198) never initialize structure padding (2 tail bytes per struct xsockbuf, 4 tail bytes of struct xsocket on amd64). tcp_pcblist_sysctl (tcp_subr.c ~1265) exports a never-zeroed stack struct xtcpcb to any unprivileged reader of net.inet.tcp.pcblist, shipping 8 stale kernel-stack bytes per TCP pcb record. Demonstrated unprivileged 3 runs: so_rcv pad = 0xffff in every record of every run; xsocket tail pad = fffff801 (upper half of a kernel-range pointer, 0xfffff801xxxxxxxx) in runs 1-2, 0 by chance in run 3 - uninitialized memory with kernel-pointer pattern across >=2/3 runs. Patched kernel (bzero in both exporters) zeroes all pads (fix_validation.log). Limited-magnitude kernel info leak, KASLR-relevant on hardened deployments.", "exploit_chain": "", "evidence": [ "run.log/run.2.log: 'rec#0 pads: rcv=ffff snd=0000 tail=fffff801' (every record)", "run.3.log: 'tail=00000000' - value varies with stack history, proving uninitialized memory", "fix_validation.log: all pads zero on the patched kernel" ], "kernel_refs": [ "sys/kern/uipc_socket2.c:188-198", "sys/kern/uipc_socket2.c:827-848", "sys/netinet/tcp_subr.c:1265-1292" ], "poc_changes": "Seed written fresh. Fixed twice during bring-up: (1) include stdint.h/-include for uint32_t with _KERNEL_STRUCTURES against kernel headers, (2) corrected pad offset math (first version sampled content bytes at offsetof(so_snd)-46; correct is offsetof(so_rcv)+46 - first run's all-zero result was offset error, not absence of leak).", "attempts": 3, "guest_uname": "DragonFly dfbsd 6.5-DEVELOPMENT DragonFly 6.5-DEVELOPMENT #0: Thu Jul 2 06:02:54 UTC 2026 root@dfbsd:/usr/obj/usr/src/sys/X86_64_GENERIC x86_64", "runtime_sec": 180, "guest_dirty": 1, "build_cmd": "cc -O -D_KERNEL_STRUCTURES -include /usr/include/stdint.h -I/usr/src/sys -I/usr/src/sys/sys -o pcbleak pcbleak.c", "run_cmd": "/tmp/pcbleak (as unprivileged user)", "code_hash": "abbfb964d6ba19cc249076c30c989667fb0c841152163303de4f352739d94bc6", "notes": "in_pcb.c:2467 pre-zeroes its xi buffer (inpcb/udp pcblists clean); unix-domain variant already filed as DF-2558. Guest has no KASLR, but the leaked fffff801 half is exactly the KASLR-decisive pointer half on deployments that do.", "recommended_fix": "bzero the exported struct at the top of sotoxsocket() and ssbtoxsockbuf() (see fix.diff); validated in-guest.", "fix_status": "fixed", "fix_kernel_uname": "DragonFly dfbsd 6.5-DEVELOPMENT #1: Wed Sep 2 04:31:48 UTC 2026 root@dfbsd:/usr/obj/usr/src/sys/X86_64_GENERIC x86_64 (one-fix nativekernel: DF-2836 + DF-2838 edits in uipc_socket2.c)", "fix_baseline_reproduced": 1, "fix_patched_reproduced": 0, "fix_verdict": "Applied bzero() to both exporters in the guest /usr/src copy, rebuilt with make nativekernel KERNCONF=X86_64_GENERIC, rebooted, re-ran the identical PoC: baseline nonzero pads (rcv=ffff, tail=fffff801) -> all pads zero in all records on the patched kernel (fix_validation.log). Leak gone; fix validated.", "fix_evidence": [ "findings/poc/DF-2838/fix.diff", "findings/poc/DF-2838/fix_validation.log" ] } |