# DF-4309 — adw_free() never destroys the per-ACB buffer DMA maps (attach/detach asymmetry)

**File:** `sys/dev/disk/advansys/adwcam.c` — severity Info (resource leak /
cleanup asymmetry), bucket base:dev, confidence certain (source).

## Root cause

`adwallocacbs()` creates one buffer DMA map per ACB:

```c
error = bus_dmamap_create(adw->buffer_dmat, /*flags*/0,
			  &next_acb->dmamap);        /* adwcam.c:205-206 */
```

`adw_free()` (adwcam.c:843-886) unwinds init levels 9→1: it frees the sg
maps (case 9), unloads/frees the acb array (cases 8/7) and destroys
`buffer_dmat` itself (case 2, adwcam.c:878) — but **never destroys the
`next_acb->dmamap` maps** (up to `ADW_DEF_MAX_HOST_QNG` = 253 of them,
adwlib.h:54). Every `adw_free()` — driver detach / kldunload / failed
attach — leaks all per-ACB bus_dma map structures and destroys their tag
while the maps are still live.

Impact: kernel resource leak only (repeatable by privileged module
load/unload); no direct memory-safety consequence. Filed as Info hardening
found by the pass-2 attach-error-path lens.

## Reproduction

Hardware-gated (needs Advansys HBA for adw_init to reach adwallocacbs).
Guest has none (`pciconf -l | grep 10cd` → empty). Status `untested`.

## Fix

`fix.diff` — destroy the per-ACB maps in `adw_free()` case 9 (before the
buffer tag is torn down in case 2). `patch -p1` apply-verified.

## 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.
