⬢ DragonFlyBSD Kernel Audit
DF-5322 / verdict.json
← back to finding ↓ download raw
{
  "finding_id": "DF-5322",
  "status": "reproduced",
  "reproduced": true,
  "impact": "leak",
  "confidence": "certain",
  "verdict": "Reproduced and measured on the QEMU guest with the production firewire.c compiled into a KLD harness: every split-transaction timeout leaks exactly one 16-byte struct tlabel because firewire_xfer_timeout() (firewire.c:348) unlinks the tlabel without kfree and the only free site, fw_tl_free() (firewire.c:900), requires list membership. 5000 timeouts -> M_FW inuse delta 5000 objects / 80000 bytes (baseline); 0/0 with fix.diff applied to /usr/src and the module rebuilt. Unbounded attacker-paced kernel memory exhaustion (DoS); no disclosure or corruption from this defect alone.",
  "exploit_chain": "open /dev/fwN.M (operator group) -> FW_ASYREQ to a non-answering node (or kernel fwmem traffic on a busy bus) -> each 200 ms split timeout leaks one M_FW tlabel -> unbounded slow kernel memory exhaustion.",
  "evidence": "run.log (baseline: M_FW inuse delta = 5000 objects, memuse delta = 80000 bytes ... LEAK REPRODUCED), fix_run.log (delta = 0 objects, memuse delta = 0 bytes), VERDICT.md",
  "kernel_refs": [
    "sys/bus/firewire/firewire.c:320",
    "sys/bus/firewire/firewire.c:348",
    "sys/bus/firewire/firewire.c:890",
    "sys/bus/firewire/firewire.c:900",
    "sys/bus/firewire/firewire.c:994",
    "sys/bus/firewire/firewirereg.h:214"
  ],
  "poc_changes": "Harness is the DF-5321 module (df5322.c byte-identical to df5321.c; KMOD renamed df5322, sysctl names unchanged df5321_*); mode 0 measures the renamed M_FW malloc type in-kernel (ks_use[cpu].inuse/memuse summed) around the production timeout+free sequence with prewarmed zones.",
  "attempts": 2,
  "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": 12,
  "guest_dirty": 0,
  "build_cmd": "sh build.sh  (cd /root/df5322 && make; compiles production /sys/bus/firewire/firewire.c into df5322.ko)",
  "run_cmd": "sh run.sh  (sysctl kern.df5321_mode=0 kern.df5321_iters=5000; sysctl kern.df5321_fire=1)",
  "code_hash": "858fff8bd4cba49ad2c2a3d25388b80ca2b18eee26b30dc02c1ef27f16d7122d",
  "notes": "Baseline leak was first captured from the identical module artifact (df5321.ko, same source hash) during the DF-5321 run series, then re-confirmed from the DF-5322-named module after a fresh vm.sh reset with-src; fixed run on the patched source. Independent corroboration: DF-5321s baseline panics show the watchdog dereferencing tlabels freed by other paths (their lifetime is untracked after the timeout unlink).",
  "recommended_fix": "kfree(tl, M_FW) after STAILQ_REMOVE_HEAD in firewire_xfer_timeout() (carried inside the DF-5321 fix.diff serialization rework).",
  "fix_status": "fixed",
  "fix_baseline_reproduced": true,
  "fix_patched_reproduced": false,
  "fix_verdict": "Baseline: 5000 objects / 80000 bytes leaked over 5000 timeouts via the production path. Patched (fix.diff on /usr/src, module rebuilt, identical trigger): delta 0 objects / 0 bytes.",
  "fix_evidence": "fix_run.log, fix_build.log, fix.diff"
}