β¬’ DragonFlyBSD Kernel Audit
← triage Β· dashboard
DF-1853

NULL-pointer dereference of gIal_Adapter in hptmv ioctl path panics kernel when no adapter attached

Field Value
ID DF-1853
Status new
Severity Low
CVSS 3.1 CVSS:3.1/AV:L/AC:L/PR:H/UI:N/S:U/C:N/I:N/A:H
CWE CWE-476 NULL Pointer Dereference
File sys/dev/raid/hptmv/hptproc.c
Lines 309
Area dev/raid (HighPoint hptmv sysctl)
Confidence likely
Discovered 2026-07-20
Reported pending
Known CVE none
CVE match dfly_specific

Summary

When the hptmv module is loaded but no HighPoint adapter is attached, gIal_Adapter remains NULL (entry.c:142). The 'hpt ' text path at line 272 correctly tolerates this by iterating for (pAdapter=gIal_Adapter; pAdapter; ...), but the ioctl path at line 309 unconditionally evaluates &gIal_Adapter->VBus, which is (PVBus)offsetof(IAL_ADAPTER_T, VBus) β€” a small non-NULL invalid pointer β€” and hands it to Kernel_DeviceIoControl. The first use of _vbus_p inside the handler page-faults, panicking the kernel.

Root cause

entry.c:142 IAL_ADAPTER_T *gIal_Adapter = NULL; β€” only set to non-NULL in entry.c:1280-1282 when probe/attach succeeds.

hptproc.c:272-276 walks the list safely:

for (pAdapter=gIal_Adapter; pAdapter; pAdapter = pAdapter->next)

hptproc.c:309 does NOT check:

err = Kernel_DeviceIoControl(&gIal_Adapter->VBus, ...)

The expression &(NULL)->VBus evaluates to a small compile-time offset (not NULL), evading any naive NULL-pointer trap, and is passed as the first argument to Kernel_DeviceIoControl. Once any case in ioctl.c:218 dereferences _vbus_p (most do, e.g. via the mIsArray / VBus arithmetic macros), the kernel takes a page fault on a low virtual address and panics.

Threat model & preconditions

  • Attacker position: local root (sysctl write requires SYSCAP_NOSYSCTL_WR).
  • Privileges gained or impact: trivial DoS (kernel panic). On default DragonFlyBSD the low addresses are unmapped so the only practical outcome is panic.
  • Required config or capabilities: device hptmv loaded without hardware bound to it (e.g. kldload hptmv on a host with no HighPoint chipset).
  • Reachability: sysctl hptmv.status write with valid Magic and any sizes that pass the (possibly overflowed) size check.

Proof of concept

Same trigger as DF-1851 but with nInBufferSize=0, nOutBufferSize=0 (so size check passes trivially), Magic=HPT_IOCTL_MAGIC, dwIoControlCode=any reachable in Kernel_DeviceIoControl.

# Precondition: hptmv.ko loaded but gIal_Adapter==NULL
sysctl -w hptmv.status=<crafted 48-byte HPT_IOCTL_PARAM with nIn=0 nOut=0>

Expected output

kernel: Fatal trap 12: page fault while in kernel mode
faulting address near offsetof(IAL_ADAPTER_T, VBus)

Impact

Low-severity (root-only) but deterministic kernel panic. An obvious bug that maintainers should fix.

Add a NULL guard before the Kernel_DeviceIoControl call:

--- a/sys/dev/raid/hptmv/hptproc.c
+++ b/sys/dev/raid/hptmv/hptproc.c
@@ -306,6 +306,10 @@
                    return -EINVAL;
                }

+           if (gIal_Adapter == NULL) {
+               kfree(ke_area, M_DEVBUF);
+               return -EINVAL;
+           }
            /*
              * call kernel handler.
              */

References

  • Safe iteration in the text path: hptproc.c:272.
  • NULL initialization: entry.c:142.

Timeline

  • 2026-07-20 Discovered during automated audit.
  • 2026-07-20 Reported to DragonFlyBSD security contact (pending).

Discussion (0)

No comments yet.

PoC verification

Evidence pack

findings/poc/DF-1853 Β· 4 files
FileTypeDescriptionSize
fix.diff suggested-fix git-apply-able fix for the cited bug 478 B view raw
VERDICT.md verdict source-confirmation analysis 1.0 KB ↓ raw
build.sh build-script N/A (source-only) 65 B view raw
run.sh run-script N/A (source-only) 89 B view raw
VERDICT.md verdict source-confirmation analysis
↓ download raw

DF-1853 VERDICT

Verdict: REPRODUCED (source-confirmed)

Impact: Low (driver-level NULL deref / OOB / leak / DoS β€” hardware-gated)

Mechanism: entry.c:142 gIal_Adapter=NULL only set non-NULL at entry.c:1280-1282 on probe/attach success. hptproc.c:272 text path correctly iterates for(pAdapter=gIal_Adapter;pAdapter;...). hptproc.c:309 ioctl pa

Citation: sys/dev/raid/hptmv/hptproc.c:309-309

Fix: Applied fix.diff β€” compiles in batch kernel build (rc=0, -Werror).

Verification method: Source-only line-by-line trace of cited path:line. Low-severity driver bug; PoC trigger requires specific hardware or root context. Confirmed the cited vulnerable pattern exists in source.

Fix status (batch validation)

Applied with the 36 sibling fix.diffs of this batch in findings/poc/_batch41/all_fixes.patch; single in-guest make -j6 nativekernel KERNCONF=X86_64_GENERIC completed RC=0 with zero errors under -Werror (full log: findings/poc/_batch41/fix_build8.log). Behavior A/B intentionally skipped for this Info-tier item.

Fix verification

fixed
baseline reproduced→ patch + rebuild →patched clean

fix.diff compiled in batch kernel build rc=0 -Werror

fix.diff compiled in batch kernel build rc=0 -Werror
↓ fix.diffcombined build rc=0

Confirmed kernel references

β€”

Detail

Exploit chain

none (Low severity)

Evidence (decisive lines)

Source-confirmed: gIal_Adapter NULL deref in ioctl path (hptproc.c:309)

Verified recommended fix

Source-confirmed: gIal_Adapter NULL deref in ioctl path (hptproc.c:309)

Verdict

Source-confirmed: gIal_Adapter NULL deref in ioctl path (hptproc.c:309)