⬢ DragonFlyBSD Kernel Audit
DF-4690 / verdict.json
← back to finding ↓ download raw
{
  "finding_id": "DF-4690",
  "status": "reproduced",
  "reproduced": 1,
  "impact": "none",
  "confidence": "certain",
  "verdict": "REPRODUCED at decoder level on the DragonFly guest (verbatim-extracted decode_tuple_bar, cardbus_cis.c:293-385, driven with crafted CIS bytes + emulated PCI probe; the accepted DF-1811 used the same source-only standard since the guest has no CardBus bridge). Beyond DF-1811 (which covers only masked-probe-zero ffs(0)): (mode 1) when the BAR probe reads back 0xffffffff -- exactly the case :362 excludes -- the attacker-controlled 32-bit CIS size field survives, is assigned to the INT `len` (:308) and passed UNCHECKED as the resource count to resource_list_add (:377): 0xFFFFFFF0 -> count = -16; (mode 2) a BAR probing 0x80000000 gives `1 << (ffs(pci_bar)-1)` = 1 << 31 (:368), signed-overflow UB manifesting as INT_MIN -> count = -2147483648. A negative count in a child resource-list entry is nonsense for every later rman allocation of that entry. Hardware-gated (physical CardBus card); realistic ceiling is the cards driver failing to attach / resource misbehavior, not privilege escalation.",
  "exploit_chain": "malicious CardBus card (physical insertion) -> cardbus_do_cis -> decode_tuple_bar/decode_tuple_funce -> negative resource count / stale-byte MAC ivar; no uid0 path",
  "evidence": "run.log: m1: ... probe=0xffffffff -> resource_list_add count = -16 ... NEGATIVE COUNT and m2: ... probe=0x80000000 -> count = -2147483648 ... NEGATIVE; fix_run.log: PATCHED modes 1/2/3 ... count = 1111638594 (0x42424242) (sentinel intact = resource_list_add never reached).",
  "kernel_refs": [
    "sys/dev/pccard/cardbus/cardbus_cis.c:308",
    "sys/dev/pccard/cardbus/cardbus_cis.c:360",
    "sys/dev/pccard/cardbus/cardbus_cis.c:362",
    "sys/dev/pccard/cardbus/cardbus_cis.c:368",
    "sys/dev/pccard/cardbus/cardbus_cis.c:377"
  ],
  "poc_changes": "verbatim extraction of the two decoder bodies (anchors, cardbus_cis.c:258-290/293-385) against minimal newbus/pci stubs (pci_read/write_config probe emulation, resource_list_add capture); added errno.h include after first build failed on EINVAL",
  "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": 30,
  "guest_dirty": 0,
  "build_cmd": "cd /root/cb4690 && sh build.sh",
  "run_cmd": "cd /root/cb4690 && sh run.sh",
  "code_hash": "b662d9d7a366c595e7eb6d018c7f15ec865f1c17fea6bdac58ce1715e454be3e",
  "notes": "hardware-gated (no CardBus bridge on guest); decoder-level verification per the accepted DF-1811 source-only reproduced standard",
  "recommended_fix": "After the probe block, reject non-positive sizes (len <= 0 -> EINVAL) and the masked pci_bar == 0 case (the DF-1811 half) before resource_list_add.",
  "fix_status": "fixed",
  "fix_baseline_reproduced": 1,
  "fix_patched_reproduced": 0,
  "fix_verdict": "Harness-level: baseline m1/m2/m3 deliver negative counts into resource_list_add; with fix4690.diff all three return EINVAL and the captured count keeps its sentinel 0x42424242 (never called).",
  "fix_evidence": "run.log: m1: ... probe=0xffffffff -> resource_list_add count = -16 ... NEGATIVE COUNT and m2: ... probe=0x80000000 -> count = -2147483648 ... NEGATIVE; fix_run.log: PATCHED modes 1/2/3 ... count = 1111638594 (0x42424242) (sentinel intact = resource_list_add never reached)."
}