⬢ DragonFlyBSD Kernel Audit
DF-3479 / verdict.json
← back to finding ↓ download raw
{
  "finding_id": "DF-3479",
  "status": "reproduced",
  "reproduced": 1,
  "impact": "panic",
  "confidence": "certain",
  "verdict": "Reproduced with the btsbx.ko fake-lower-layer harness: delivering an L2CA ConnectInd for a locally listened PSM reaches ng_btsocket_l2cap_process_l2ca_con_ind -> sonewconn -> ng_btsocket_l2cap_attach, which links the pcb without taking the implied pcb reference (soreference) that sonewconns KKASSERT (uipc_socket2.c:404) requires \u2014 kernel panic on INVARIANTS builds (panic.txt). On non-INVARIANTS kernels the child socket refcount runs one low; the pcb stays in ng_btsocket_l2cap_sockets after the socket is freed (pcb->so dangling) \u2014 latent UAF on accepted-socket close. Fix (soreference(so) after linking the pcb) validated: with the patched module the same harness completed the whole inbound handshake to OPEN, accept() returned the child, and 16M+ packets were transferred. Remote-peer triggerable on any BT system (peer connects to a listened PSM); locally triggerable via the graph.",
  "exploit_chain": "remote peer (or local graph): connect to listened PSM -> sonewconn -> attach without pcb ref -> INVARIANTS: panic; production: socket freed with pcb alive in the sockets list -> pcb->so UAF on later lookups (analysis; not runtime-demonstrated)",
  "evidence": [
    "panic.txt (sonewconn_faddr KKASSERT trace via ng_btsocket_l2cap_input)",
    "README.md",
    "fix.diff + harness completion on patched module (DF-3480 pack logs)"
  ],
  "kernel_refs": [
    "sys/netgraph7/bluetooth/socket/ng_btsocket_l2cap.c:1961",
    "sys/netgraph7/bluetooth/socket/ng_btsocket_l2cap.c:593",
    "sys/kern/uipc_socket2.c:404",
    "sys/netinet/in_pcb.c:295"
  ],
  "poc_changes": "harness-written (no seed); trigger is a single netgraph control message",
  "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": 30,
  "guest_dirty": 0,
  "build_cmd": "cd /usr/src/sys/netgraph7/bluetooth/socket && make   (after applying fix.diff for the patched run)",
  "run_cmd": "kldload btsbx.ko; sysctl -w debug.btsbx_cmd=1; sysctl -w debug.btsbx_cmd=2   (listener bound to psm 0x1234 via ./df3478_drive)",
  "code_hash": "n/a (trigger is a netgraph message; harness sources in ../DF-3480)",
  "notes": "The raw-l2cap / rfcomm / hci-raw attach paths in sibling files may share the omission \u2014 flagged for their own audits. Requires DF-3478s fix first (listen() must work to create the listener).",
  "recommended_fix": "soreference(so) in ng_btsocket_l2cap_attach() after linking the pcb (mirror in_pcballoc)",
  "fix_status": "fixed",
  "fix_kernel_uname": "DragonFly dfbsd 6.5-DEVELOPMENT #0 (ng_btsocket.ko rebuilt with fix.diff)",
  "fix_baseline_reproduced": 1,
  "fix_patched_reproduced": 0,
  "fix_verdict": "Baseline: KKASSERT panic at con_ind. Patched: no panic; harness completed inbound handshake, accept() returned child socket, 16M+ packets transferred. Fix validated.",
  "fix_evidence": "DF-3480 run.log excerpts (handshake states + t+ counters) captured on the patched module"
}