⬢ DragonFlyBSD Kernel Audit
DF-2319 / verdict.json
← back to finding ↓ download raw
{
  "finding_id": "DF-2319",
  "status": "reproduced",
  "verdict": "REPRODUCED at the verbatim-rig level on the DragonFly guest; kernel entry is hardware-gated (no PCMCIA bridge in QEMU -- proven in env.txt). The production parser was machine-extracted BYTE-IDENTICAL from the guests own /usr/src/sys/bus/pccard/pccard_cis.c (extract.sh; sha256 gate: acdd2484...; manifest in pack) and driven through the real entry pccard_read_cis(). Two deterministic NULL dereferences, both pinned by disassembly to the exact claimed statements inside pccard_parse_cis_tuple: (A) CFTABLE_ENTRY as the FIRST tuple of the primary chain: state is bzerod (pccard_cis.c:81) so default_cfe stays NULL until CISTPL_CONFIG (:867); the CFTABLE case (:871) has NO guard and evaluates num != state->default_cfe->number (:907) -> SIGSEGV si_addr=0x0 at pccard_parse_cis_tuple+0x437, instruction cmp %ecx,(%rax) with rax=state->default_cfe=NULL (disasm_proof.txt) -- in kernel context a read at NULL == deterministic panic at card insertion. (B) after the LONGLINK_MFC reset at CISTPL_END (:635-649) sets state->pf=NULL (:648), a CFTABLE_ENTRY in the next MFC chain reaches STAILQ_INSERT_TAIL(&state->pf->cfe_head,...) (:916) with pf==NULL -> SIGSEGV si_addr=0x30 == offsetof(pccard_function,cfe_head)=40 + offsetof(stqh_last)=8 (rig prints the offsets; second instruction in disasm_proof.txt). Fix validated two ways: single-fix rig A/B (both scenarios clean, nothing else changes) and a combined-five-fix kernel built with -Werror, installed, booted (kernel #1, sha256 in env.txt); the rig re-extracted from the RUNNING kernels patched source parses both crashing cards without any fault (postboot_run.log).",
  "reproduced": true,
  "impact": "panic",
  "confidence": "certain",
  "exploit_chain": "evil PC Card/CardBus insert -> pccard_attach_card (socket event, pccard.c:195) -> pccard_read_cis -> pccard_scan_cis -> pccard_parse_cis_tuple(CISTPL_CFTABLE_ENTRY) -> NULL deref (:907 read at NULL / :916 access at NULL+0x30) -> kernel-mode page fault on the socket thread -> panic (local/physical DoS). No privilege boundary is crossed: the faults are at fixed NULL-page offsets only; there is no attacker-controlled mapping of the NULL page from the card-attach path.",
  "evidence": "run.log (both scenarios: SIGSEGV si_addr=0x0 and si_addr=0x30, child_exit=91); disasm_proof.txt (cmp %ecx,(%rax) with rax=0 == :907; pf==NULL stqh_last load at +0x30 == :916); fixed_run.log (f2319: both return normally, card->error=1); matrix.log (only f2319 flips these scenarios); postboot_run.log (running fixed kernels source: no fault)",
  "kernel_refs": [
    "sys/bus/pccard/pccard_cis.c:81",
    "sys/bus/pccard/pccard_cis.c:635",
    "sys/bus/pccard/pccard_cis.c:641",
    "sys/bus/pccard/pccard_cis.c:644",
    "sys/bus/pccard/pccard_cis.c:648",
    "sys/bus/pccard/pccard_cis.c:867",
    "sys/bus/pccard/pccard_cis.c:871",
    "sys/bus/pccard/pccard_cis.c:907",
    "sys/bus/pccard/pccard_cis.c:916",
    "sys/bus/pccard/pccard.c:195"
  ],
  "poc_changes": "Pack created fresh (no seeded rig). Authored the verbatim rig (extract.sh + rig_shims.h + rig_main.c) and the two crash scenarios; 2 build iterations on the guest (DragonFly mcontext field name), then deterministic reproduction across two independent boots (identical faulting RIPs 0x402027/0x4025e9).",
  "attempts": 4,
  "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": 1500,
  "guest_dirty": 0,
  "build_cmd": "sh extract.sh . && cc -O2 -Wall -o rig rig_main.c",
  "run_cmd": "./rig nullderef_a && ./rig nullderef_b   (A/B: sh run_matrix.sh)",
  "code_hash": "908c166959ac485b7dadf00c66e9ec963ba421de027b157ddc056f2ed3837319",
  "notes": "Verbatim-rig standard (orchestrator-approved method for this hardware-gated parser; DF-1040/1041 precedent): the compiled parser text is the guests own /usr/src production code, sha256-gated at extraction (extract_manifest.txt). Kernel entry unreachable on this guest: no PCMCIA bridge, no /dev/pccard*, no pccardc (env.txt) -- impact statements are the in-kernel consequences of the demonstrated production-code behavior. Deterministic across two independent boots (identical matrix). Guest left up and clean on the with-src snapshot; pristine pccard_cis.c sha256 acdd2484... re-verified after reset. Incidental: poweroff of the freshly-installed test kernel #1 required a QEMU kill on both takes (no panic trace in the serial console; stock kernel shuts down cleanly) -- VM artifact, not a parser finding.",
  "recommended_fix": "Guard the CFTABLE_ENTRY case: require state->default_cfe and state->pf non-NULL (error++ + break otherwise).",
  "fix_status": "fixed",
  "fix_baseline_reproduced": 1,
  "fix_patched_reproduced": 0,
  "fix_verdict": "VALIDATED. (1) Single-fix rig A/B: guard at the top of the CFTABLE_ENTRY case -> both crash scenarios return normally (card->error=1), applied_fix.diff shows only the guard hunk, all 9 other scenarios unchanged incl. benign/checksum_ok. (2) Combined five-fix kernel: -Werror build rc=0, installkernel rc=0, booted kernel #1 (sha256 c73653c6...), markers present in the running source, rig re-extracted from it: no fault. In-kernel behavioral test impossible (no PCMCIA bridge) -- DF-1040/1041 precedent.",
  "fix_evidence": "fix.diff; fixed_run.log; matrix.log (single-fix A/B); kernel_apply.log + kernel_build.tail.log + env.txt + postboot_extract_manifest.txt + postboot_run.log (combined-fix kernel build/boot/running-source rerun)"
}