my_softc my_ldata_ptr (2056-byte DMA descriptor block) is never freed: leaked on every detach and every failed attach
Summary
my_attach kmallocs 2056 bytes; my_detach releases only irq and res - 'kfree' appears ZERO times in the whole driver. Every detach leaks the block, and the attach-fail label routes through my_detach, so the no-PHY ENXIO path and bus_setup_intr failure leak it too. Root can loop kldload/kldunload for unbounded kernel-heap exhaustion (2KB/cycle). kfree fix.
Discussion (0)
PoC verification
Evidence pack
findings/poc/DF-4257 Β· 6 files| File | Type | Description | Size | |
|---|---|---|---|---|
| trigger.sh | β | 544 B | view raw | |
| env.txt | β | 1007 B | view raw | |
| VERDICT.md | β | 1.9 KB | β raw | |
| fix.diff | β | 397 B | view raw | |
| manifest.json | β | 719 B | view raw | |
| verdict.json | β | 2.0 KB | view raw |
DF-4257 VERDICT β my(4) leaks my_ldata_ptr on detach and on failed attach
Status: inconclusive on the audit guest (hardware-gated). Leak certain at source level.
Reproduction attempt
pciconf -l | grep 1516 on the audit guest: no Myson device (env.txt);
my_probe (if_my.c:754-771) never returns 0, so my_attach never runs and
neither the allocation nor the leak can occur. A purely software trigger
does not exist: the allocation is tied to PCI device attachment.
Analysis
grep -n "my_ldata_ptr" sys/dev/netif/my/if_my.c yields exactly three
uses: the kmalloc (870), the alias assignment (872, 882), and the pointer
arithmetic β there is no kfree(sc->my_ldata_ptr, M_DEVBUF) anywhere in
the driver. my_detach (971-992) releases my_irq (987) and my_res
(989) only.
Two leak paths:
- Normal lifecycle: attach succeeds β later
my_detach(kldunload or device removal) frees everything except the 2,056-byte descriptor block. Repeatable by root without bound. - Failed attach: every
goto failafter line 870 (no PHY found at 936-939;bus_setup_intrfailure at 955-961) dispatches tomy_detach(dev)(966-968) which β becausedevice_is_attached()is false β releases only the resources, leaking the block.
This is a distinct allocation from the mbuf leak in DF-1479 (which covers
my_encap failure inside my_start): DF-4257 is the softc-owned DMA
descriptor array.
Severity Low: kernel memory leak, 2 KB per event, root-driven unload or hardware-provoked attach failure. CWE-401. Fix is a one-line kfree in my_detach (fix.diff).
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
not_testableone-line kfree added in my_detach (fix.diff); hardware-gated, not validated on this guest
findings/poc/DF-4257/fix.diff
Confirmed kernel references
Detail
Evidence (decisive lines)
VERDICT.md (all my_ldata_ptr uses enumerated β no kfree exists); env.txt (no Myson PCI device on guest)
PoC changes
trigger.sh documents the kldload/kldunload loop + vmstat -m observation for affected hardware
Verified recommended fix
kfree(sc->my_ldata_ptr, M_DEVBUF) in my_detach before releasing resources
Verdict
my_attach allocates sc->my_ldata_ptr = kmalloc(sizeof(struct my_list_data)+8, M_DEVBUF, M_WAITOK) (sys/dev/netif/my/if_my.c:870-871) and my_detach (971-992) never kfree()s it β it releases only my_irq and my_res. Every detach leaks 2056 bytes, and every failed attach (no PHY found at 936-939, bus_setup_intr failure at 955-961 β both routed to my_detach via the fail label at 966-968) leaks it too; there is no kfree of my_ldata_ptr anywhere in the driver. Root can loop kldload/kldunload for unbounded kernel heap exhaustion. Distinct allocation from the DF-1479 mbuf leak. Not executable on the audit guest: pciconf shows no 1516 device (env.txt) so my_probe never matches and my_attach never runs.
No comments yet.