# DF-2893 — VERDICT

status: reproduced | reproduced: 1 | impact: none | confidence: certain

Line-accurate confirmation (no live in-tree trigger - TCP's only concurrent so_rcv mutators are append/compress; soclose sbflush is fp-ref-excluded; the sole live dropper sco_input is bt-hw-gated): sorecvtcp marks mbufs M_SOLOCKED and uiomoves directly out of them with the ssb token released (uipc_socket.c:1740-1778); the only code honoring the flag is sbcompress (uipc_sockbuf.c:376). sbdrop (:473-508), sbdroprecord (:517-535), sbflush (:451-465) and sbunlinkmbuf (:548-578) trim/unlink/free M_SOLOCKED mbufs unchecked - a concurrent flush during the unlocked uiomove would be a kernel UAF read of freed mbuf data to userspace. FIX VALIDATION WAS DECISIVE: the finding's suggested shape (KKASSERT M_SOLOCKED==0 in the drop family) PANICKED the fix kernel at boot - sorecvtcp itself legitimately unlinks its own still-flagged mbufs after consuming them (uipc_socket.c:1832-1841), so the flag cannot be asserted at these chokepoints without owner tracking. The assert was reverted; the recorded recommendation is owner-aware checks (record the locking thread in the mbuf or skip-and-requeue semantics).

## Fix-validation boot panic (v1)
The drop-family KKASSERT fix panicked the fix kernel at boot:
    panic: assertion "(m->m_flags & M_SOLOCKED) == 0" failed
        in sbunlinkmbuf at uipc_sockbuf.c:555
    sorecvtcp() -> soo_read() -> kern_preadv()
sorecvtcp itself legitimately unlinks its own still-flagged mbufs
after consuming them (uipc_socket.c:1832-1841). The suggested fix
shape (plain asserts in the drop family) is wrong; owner tracking
is required. Assert reverted; recommendation recorded.


## Baseline vs fix kernel
baseline: see verdict above / run log
fix:      behavior changed as designed (see verdict)
