# DF-2570 — ng_device_rcvdata kmalloc/mtod/kfree(M_DEVBUF) heap corruption

## Claim (severity: High)

`sys/netgraph/ng_device.c` `ng_device_rcvdata` (lines 334-380) allocates a
buffer via `kmalloc(..., M_DEVBUF, ...)` (line 363), immediately reassigns the
local pointer to `mtod(m, char *)` (line 369) — leaking the kmalloc and now
pointing into the mbuf zone — then `kfree(buffer, M_DEVBUF)` (line 377) frees
`m->m_data` through the **wrong zone (M_DEVBUF)**. Result: (1) memory leak of
the kmalloc'd buffer per received mbuf; (2) M_DEVBUF slab freelist corruption
plus a double-freeable mbuf when the mbuf is later freed through its own zone.

## Verdict: NOT REPRODUCED — orphaned dead code (false positive on live axes)

The defect is **genuinely present in the cited source text** but the file is
**orphaned dead code**, identical in status to sibling findings DF-2571 and
DF-2572 (same file):

- **Not built:** `sys/netgraph/ng_device.c` has no entry in `sys/conf/files`
  (the only `ng_device` entry, at `conf/files:1699`, is `netgraph7/ng_device.c`
  — a different file). Not in `sys/config/X86_64_GENERIC`.
- **Not in the running kernel:** `nm /boot/kernel/kernel.debug | grep -c ng_device` = 0.
- **Not loadable:** no `ng_device.ko` on disk; the orphaned source **fails to
  compile** against modern kernel headers (removed `cdevsw`/`d_*_t`/`make_dev`
  API) — 52 error lines, see `module_build_failure.txt`.
- **Maintained version has NO analogous bug:** `sys/netgraph7/ng_device.c`
  `ng_device_rcvdata` (259-287) enqueues the mbuf whole via `_IF_ENQUEUE`; there
  is no `kmalloc(...M_DEVBUF)`, no `buffer = mtod`, no `kfree(...M_DEVBUF)`
  anywhere in the function.
- **Root-only even if live:** the netgraph graph feeding `rcvdata` and the
  `/dev/ngdN` device (mode 0600) both require root.

See `VERDICT.md` for the full trace and `module_build_failure.txt` for the
compile proof.

## How to reproduce (the reachability check, not a live trigger)

```sh
./build.sh     # builds the documentation-only trigger
./run.sh       # reports the dead-code status (nm count, conf/files, /dev/ngd*)
```

The trigger documents the in-kernel path it *would* take if the module were
live (send mbuf data to an ng_device node's hook). It cannot exercise live code
on the default kernel.

## Files

- `trigger.c` — documentation trigger (path it would take + dead-code status).
- `build.sh` / `run.sh` — build/run the documentation trigger.
- `build.log` / `run.log` — captured output.
- `env.txt` — guest environment + live reachability evidence.
- `module_build_failure.txt` — proof the orphaned source cannot compile.
- `fix.diff` — defense-in-depth fix (remove kmalloc/buffer/kfree dance, copy
  straight from mtod(m)). Applies cleanly; cannot be built into a live kernel.
- `VERDICT.md` — full narrative.
- `manifest.json` — artifact catalog.
