⬢ DragonFlyBSD Kernel Audit
DF-3459 / verdict.json
← back to finding ↓ download raw
{
  "finding_id": "DF-3459",
  "status": "reproduced",
  "reproduced": 1,
  "impact": "panic",
  "confidence": "certain",
  "verdict": "REPRODUCED (code-level harness; module latent on this guest). rssadapt_rate (ieee80211_rssadapt.c:253-255) exhausts its pick loop with rix=-1 whenever no threshold is STRICTLY below rssi<<8 \u2014 deterministically for any fresh node because node_getrssi (ieee80211_node.c:1146-1155) returns 0 while ni_avgrssi is IEEE80211_RSSI_DUMMY_MARKER and all M_ZEROd thresholds are 0 (0<0 false for every row), and after threshold convergence under signal decay. rix=-1 then (a) reads rs_rates[-1] at :258 (in-struct, returns the rs_nrates byte into ni_txrate), (b) is stored into ra_rix and returned to callers \u2014 if_iwm.c:3540/3574 feeds it to iwm_setrates whose KASSERT(rix>=0&&rix<nrates) (if_iwm.c:4366) panics INVARIANTS kernels, and (c) on the next failed TX completion rssadapt_lower_rate (:279 u_int rix; :283 rix=ra->ra_rix) turns -1 into 0xffffffff so (*thrs)[rix] at :284/:285 reads AND writes at chunk+0x1fffffffe (~+8GiB) \u2014 a wild 2-byte read+write: page-fault panic on unmapped KVA, genuine wild heap corruption where the direct map covers chunk+8GiB. Negative-side residual of DF-0730 (its fix resized the array but left rix<0 untouched). Latent: wlan_rssadapt is optional, not in GENERIC, no in-tree driver selects it, guest has no radio \u2014 same blocker class as DF-0730/DF-0731.",
  "exploit_chain": "Hypothetical wired-up deployment only (module unselectable in-tree): remote peer associates (fresh node, RSSI unsampled -> 0) -> attacker forces TX failure (deauth/RTS flood) -> rssadapt_lower_rate wild 2-byte write at ra+0x1fffffffe with value interpolate(last_thr, rssi<<8). Fixed-offset, bounded-value corruption; realistic ceiling is DoS panic (offset usually unmapped). No chain developed on the guest: hard blocker (module cannot be loaded/selected \u2014 no radio, no ratectl selector).",
  "evidence": [
    "findings/poc/DF-3459/run.log \u2014 buggy run: rix=-1, rs_rates[-1] read confirmed, iwm KASSERT condition VIOLATED, wild access at chunk+0x200000032 (~+8GiB) caught by SIGSEGV trapper",
    "findings/poc/DF-3459/run.fixed.log \u2014 fix.diff logic active: rix=0, no KASSERT violation, no fault, canaries intact",
    "findings/poc/DF-3459/fix_module_build.log \u2014 patched wlan_rssadapt.ko builds clean, full kernel -Werror CFLAGS, rc=0",
    "findings/poc/DF-3459/df3459_harness.c \u2014 exact struct layout (DF-0730 resize applied) + exact kernel code paths"
  ],
  "kernel_refs": [
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:253",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:258",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:259",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:279",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:283",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:284",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:285",
    "sys/netproto/802_11/wlan/ieee80211_rssadapt.c:202",
    "sys/netproto/802_11/wlan/ieee80211_node.c:1146",
    "sys/dev/netif/iwm/if_iwm.c:3540",
    "sys/dev/netif/iwm/if_iwm.c:4366",
    "sys/netproto/802_11/ieee80211_ratectl.h:91"
  ],
  "poc_changes": "Harness is self-authored (no seed). Two iterations were needed: (1) canary region initially misaligned the struct (zone+1) causing an unrelated SSE fault \u2014 moved to a 32-byte-aligned slot; (2) the wild access is performed in a forked child with a SIGSEGV trapper (_exit(42)) so the fault the kernel cannot catch is reported instead of silently killing the harness; buggy/fixed modes selected by build.sh arg, following the DF-0730 pack conventions.",
  "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": 240,
  "guest_dirty": 0,
  "build_cmd": "sh build.sh          (buggy)   /   sh build.sh fixed   (fixed)   [on guest: cc -Wall -O2 -o df3459_harness df3459_harness.c]",
  "run_cmd": "./run.sh   (runs the already-built df3459_harness)",
  "code_hash": "b0eb08adcc4fa50d30b6ab77d8aadd7a6a21c9b773c46f9cfb1aa4007c381e19",
  "notes": "Latent module \u2014 identical reachability profile as DF-0730/DF-0731 (wlan_rssadapt optional, sys/conf/files:1655; default ratectl AMRR ieee80211_ratectl.c:121-122; guest has no radio). Would be High if a driver wired RSSADAPT (remote wild write). rs_rates[-1] read is contained (returns rs_nrates byte) \u2014 the security-relevant primitive is the u_int-indexed +8GiB access. raise_rate (:299 signed int rix) has the same -1 reachability but only a contained 2-byte-before-row access at :304. Guest /usr/src restored to pristine after module fix-build (sha256 verified).",
  "recommended_fix": "Clamp rix to 0 when the threshold pick loop exhausts, refuse to adapt when ra_rix < 0 in rssadapt_lower_rate (u_int hazard), and bail out of rssadapt_node_init on empty ratesets \u2014 see findings/poc/DF-3459/fix.diff.",
  "fix_status": "fixed",
  "fix_kernel_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",
  "fix_baseline_reproduced": 1,
  "fix_patched_reproduced": 0,
  "fix_verdict": "fix.diff applies cleanly (git apply --check on the guests /usr/src); the patched wlan_rssadapt module rebuilds with full kernel -Werror CFLAGS (rc=0, fix_module_build.log); harness fixed-mode shows rix=0, no iwm KASSERT violation, and no wild access (run.fixed.log). Module cannot be exercised at runtime on this guest (no radio), so validation is compile + harness-level, matching the DF-0730 precedent.",
  "fix_evidence": [
    "findings/poc/DF-3459/fix.diff",
    "findings/poc/DF-3459/fix_module_build.log",
    "findings/poc/DF-3459/run.fixed.log"
  ]
}