DF-2830 / verdict.json
{ "finding_id": "DF-2830", "status": "reproduced", "reproduced": 1, "impact": "leak", "confidence": "certain", "verdict": "For zone names >= 13 chars, tmpname[len]=':' (vm_zone.c:841) overwrites the only NUL of the 14-byte stack buffer tmpname (clamp at :835 allows len==13), so ksnprintf's %s (:854) reads past the buffer, copying kernel-stack residue into the world-readable vm.zone sysctl output. Reproduced on the stock INVARIANTS guest with KLD-created 13/16-char zones: unprivileged reads showed >100 bytes of stack content per affected row; the bytes after tmpname are the previous execution's tmpbuf on the reused kernel stack, so the leak self-echoes and amplifies to ksnprintf's 127-byte cap (stable fixed point, identical md5 across 3 runs); rows also lose newlines and their stats columns get truncated. In-tree trigger: 'rfcomm_credit' (exactly 13 chars, rfcomm_session.c:162) on device-bluetooth kernels; stock GENERIC zone names are <= 9 chars, hence Medium. Fixed by clamping to 12 chars: patched kernel #1 renders clean padded rows with zero echo.", "exploit_chain": "unpriv user -> repeated sysctl vm.zone reads -> up to ~113 bytes of kernel-stack residue per affected zone row per read (CWE-125 read primitive via CWE-170 NUL clobber); no write primitive, no escalation", "evidence": "run.hexdump.log / leak_sample.txt: 'AAAAAAAAAAAAA:AAAAAAAAAAAAA:...(9+ echoes)...:ASWAPMETA:' with rows merged (no newline) from 'su -m nobody'-readable output; fix_hex.log: patched kernel prints 'AAAAAAAAAAAA: 000064, 00000000, 000000, 000000, 00000000' cleanly", "kernel_refs": ["sys/vm/vm_zone.c:816", "sys/vm/vm_zone.c:834-841", "sys/vm/vm_zone.c:854-858", "sys/netbt/rfcomm_session.c:162"], "poc_changes": "self-authored harness (no seed): KLD creates zones named AAAAAAAAAAAAA (13) and BBBBBBBBBBBBBBBB (16); 'leakmark_zone' (13 chars, DF-2829 harness) independently exhibited the same over-read", "attempts": 1, "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": 960, "guest_dirty": 0, "build_cmd": "cd /root/df2830 && make (KLD: cc -O2 -D_KERNEL ... -c df2830_harness.c; cc -Wl,... -r -o df2830.ko)", "run_cmd": "kldload /root/df2830/df2830.ko && su -m nobody -c 'sysctl vm.zone' | hexdump -C", "code_hash": "39d43bca0cb2931cd040f7a981c71f6f2277632698c141bb9ebaa681a3ad6425", "notes": "An alternate fix is widening tmpname; the applied minimal fix truncates names to 12 chars (maintainer's choice). The leak content is stack-residue-dependent: first read on a given kstack emits whatever it last held; repeats converge to self-echo. Stats-column truncation is a functional symptom of the same bug.", "recommended_fix": "Clamp len to sizeof(tmpname)-2 so the ':' fits at tmpname[12] and the NUL at tmpname[13] survives (see fix.diff)", "fix_status": "fixed", "fix_kernel_uname": "DragonFly dfbsd 6.5-DEVELOPMENT DragonFly 6.5-DEVELOPMENT #1: Tue Sep 1 20:57:06 UTC 2026 root@dfbsd:/usr/obj/usr/src/sys/X86_64_GENERIC x86_64", "fix_baseline_reproduced": 1, "fix_patched_reproduced": 0, "fix_verdict": "Applied fix.diff (with DF-2829's fix) to guest /usr/src/sys/vm/vm_zone.c, make nativekernel KERNCONF=X86_64_GENERIC, installkernel + reboot into #1. Identical PoC rerun: 'AAAAAAAAAAAA:' / 'BBBBBBBBBBBB:' rows render cleanly, no stack echo, no merged rows, intact newlines - OOB read eliminated.", "fix_evidence": "findings/poc/DF-2830/fix_validation.log and fix_hex.log (patched), run.hexdump.log + leak_sample.txt (baseline)" } |