DF-2429 / verdict.json
{ "finding_id": "DF-2429", "status": "reproduced", "verdict": "REPRODUCED: production btaction XPT_CALC_GEOMETRY handler panics the kernel (Fatal trap 18 integer divide fault at btaction+0x4ff, the bt.c:1157 size_mb division) when xpt_action delivers block_size=2MiB (device-fed READ CAPACITY value that passes the CAM-layer block_size==0/volume_size==0 filter at cam_xpt.c:3063-3071). Honest correction: the block_size==0 variant cited first in the finding never reaches bt.c -- the CAM filter completes it with CAM_REQ_CMP (demonstrated live); only the >1MiB variant (inner quotient 0) panics. Local DoS/panic from hostile SCSI target data on real bt(4) hardware.", "reproduced": true, "impact": "panic", "confidence": "certain", "exploit_chain": "lying SCSI target reports secsize>1MiB in READ CAPACITY -> da(4) dasetgeom -> xpt_action(XPT_CALC_GEOMETRY) (filter passes, both fields nonzero) -> production btaction bt.c:1157 computes (1024*1024)/2097152==0 then volume_size/0 -> #DE -> kernel panic", "evidence": "panic.txt (Fatal trap 18, Stopped at btaction+0x4ff: divq %rsi,%eax; disassembly context in VERDICT.md); run.log (variant 1 block_size=0 survives with heads=0 status=0x1 proving the CAM filter; variant 2 panics)", "kernel_refs": [ "sys/dev/disk/buslogic/bt.c:1157", "sys/bus/cam/cam_xpt.c:3063", "sys/bus/cam/scsi/scsi_da.c:1831", "sys/bus/cam/scsi/scsi_da.c:2302" ], "poc_changes": "original finding cited block_size==0 as the trigger; the CAM layer filters that case (proven live), so the PoC uses block_size=2097152 (>1MiB) which zeroes the inner quotient -- same division, same line, actually reachable", "attempts": 2, "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": 95, "guest_dirty": 0, "build_cmd": "./push_rig.sh (make KERNBUILDDIR=/usr/obj/usr/src/sys/X86_64_GENERIC; cc dfbt_ctl.c)", "run_cmd": "sh run.sh (dfbt_ctl calcgeom 0 4194304; dfbt_ctl calcgeom 2097152 4194304)", "code_hash": "745f8b43787e6bb6a37f62b8ac9fc1a99d7aab498a1faa6d34c8caeba4ba8651", "notes": "bt(4) is compiled into X86_64_GENERIC (config line 102); no BusLogic HBA exists on the QEMU guest, so the rig fabricates the post-attach softc and dispatches the REAL production handlers resolved from /boot/kernel/kernel (no KASLR, prologues byte-verified). Guest reset clean after the panic run.", "recommended_fix": "Reject block_size==0 or >1MiB with CAM_REQ_INVALID before the division (fix.diff, object-compile validated under -Werror with kernel headers)", "fix_status": "not_tested", "fix_baseline_reproduced": true, "fix_patched_reproduced": false, "fix_verdict": "object-compile validation only (panic class, not memory corruption; kernel A/B not mandated): patched bt.c+btreg.h compile clean with the X86_64_GENERIC kernel flags", "fix_evidence": "fix.diff; guest build log line FIXED-COMPILES-CLEAN with bt.fixed.o produced (cc -Werror, kernel headers)" } |