⬢ DragonFlyBSD Kernel Audit
DF-4795 / verdict.json
← back to finding ↓ download raw
{
  "finding_id": "DF-4795",
  "status": "untested",
  "reproduced": 0,
  "impact": "none demonstrated at runtime (no SR-IOV VF hardware on guest); source-proven disclosure class: up to 50 of 60 payload bytes of the E1000_VF_SET_MULTICAST mailbox message are uninitialized guest kernel stack, copied verbatim by e1000_write_mbx_vf (e1000_mbx.c:476-477) into E1000_VMBMEM registers read by the host PF driver \u2014 guest-kernel-stack residue crosses the guest->host boundary on every multicast update with <30 groups (the common case)",
  "confidence": "certain",
  "verdict": "not runnable on the audit guest by hardware absence (virtio-only, env.txt); the byte-level write/forward pattern is certain from source: msgbuf[16] declared uninitialized at e1000_vf.c:403, only msgbuf[0] (:426-427) and count*2 bytes at offset 4 (:429-434) are written, yet e1000_write_msg_read_ack (:436 -> :385) forwards all E1000_VFMAILBOX_SIZE=16 words and e1000_write_mbx_vf copies all size words into VMBMEM (e1000_mbx.c:476-477) which the PF reads. FreeBSD current initializes the array (= {}), confirming upstream treats this as a bug. Path is live for igb VF devices (if_igb.c:108/123 -> e1000_api.c:510 -> igb_set_multi if_igb.c:1304); unprivileged users trigger it by joining multicast groups. Deterministic demo on guest (run.log): count=5 -> 50/60 bytes uninitialized. fix.diff hunk 1 (= { 0 }); compile-validated BASE_CC_RC=0/FIXED_CC_RC=0 (build.log), git apply --check clean.",
  "exploit_chain": "",
  "evidence": "run.log (count=5 line: uninit stack bytes sent to PF: 50 of 60); VERDICT.md (write-pattern proof path:line, reachability chain, upstream divergence); build.log (guest compile validation + source sha256 match); env.txt (no e1000 hardware on guest); fix.diff (git-apply-clean, hunk 1 = this finding)",
  "kernel_refs": [
    "sys/dev/netif/ig_hal/e1000_vf.c:403",
    "sys/dev/netif/ig_hal/e1000_vf.c:422",
    "sys/dev/netif/ig_hal/e1000_vf.c:429",
    "sys/dev/netif/ig_hal/e1000_vf.c:436",
    "sys/dev/netif/ig_hal/e1000_mbx.c:476",
    "sys/dev/netif/ig_hal/e1000_mbx.c:477"
  ],
  "poc_changes": "no seeded PoC; authored mcmsg_demo.c (deterministic byte-initialization model of the exact write/forward pattern) + combined fix.diff",
  "attempts": 0,
  "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": 0,
  "guest_dirty": 0,
  "build_cmd": "cc -Wall -O2 -o mcmsg_demo mcmsg_demo.c (guest, RC=0); cc -fsyntax-only -D_KERNEL -I/usr/obj/usr/src/sys/X86_64_GENERIC -I/usr/src/sys -I/usr/src/sys/dev/netif/ig_hal {base,fixed}.c (RC=0/RC=0)",
  "run_cmd": "./mcmsg_demo",
  "code_hash": "7c25206611722c7c067c8308d7a139be0f53af5b24ed4e5ef4134dea5ad90791",
  "notes": "Pass-2 e1000_vf.c, kernleak bucket. Shares function and combined fix.diff with DF-4794 (hunk 2 = overflow flag). The dead uninit read msgbuf[0]|= at :422 folded here. Other VFTA/RLPML/PROMISC/RESET/RAR messages in this file fully initialize their buffers (msgbuf[2] words 0+1 written; rar_set memsets 12; reset sends 1 word) \u2014 only update_mc_addr_list_vf leaks.",
  "recommended_fix": "Zero-initialize the message buffer: u32 msgbuf[E1000_VFMAILBOX_SIZE] = { 0 }; (fix.diff hunk 1)",
  "fix_status": "not_testable",
  "fix_baseline_reproduced": 0,
  "fix_patched_reproduced": 0,
  "fix_verdict": "compile-validated only: fix.diff git apply --check clean; both hunks applied on guest copy; cc -fsyntax-only BASE_CC_RC=0 / FIXED_CC_RC=0 with only the pre-existing systm.h:216 warning (build.log); runtime fix-validation impossible on this virtio-only guest (no igb/VF device)",
  "fix_evidence": "fix.diff; build.log; env.txt"
}