⬢ DragonFlyBSD Kernel Audit
DF-2830 / verdict.json
← back to finding ↓ download raw
{
  "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 ksnprintfs %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 executions tmpbuf on the reused kernel stack, so the leak self-echoes and amplifies to ksnprintfs 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 (maintainers 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-2829s 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)"
}