[PATCH] um: vector: fix use-after-free in vector_mmsg_rx()

Michael Bommarito michael.bommarito at gmail.com
Mon Jun 22 05:47:22 PDT 2026


When vector_mmsg_rx() discards a packet whose overlay header fails
verify_header(), it frees the skb and continues the loop:

	if (header_check < 0) {
		dev_kfree_skb_irq(skb);
		vp->estats.rx_encaps_errors++;
		continue;
	}

The normal and short-packet paths fall through to the bottom of the
loop body, which clears the consumed slot and advances the cursors:

	(*skbuff_vector) = NULL;
	mmsg_vector++;
	skbuff_vector++;

The verify_header() < 0 path skips that via continue, so the freed skb
is left in skbuff_vector[] and the cursors do not advance. The next
iteration reads the same slot, gets the freed skb, and frees it again,
producing a refcount underflow / use-after-free in the RX path.

Discard the slot the same way the other paths do before continuing.

Only transports whose verify_header() can return negative are affected:
GRE and L2TPv3 do so on a cookie/session-id mismatch (raw/tap do not),
so any peer on such a transport can trigger it without authentication.

Fixes: 49da7e64f33e ("High Performance UML Vector Network Driver")
Cc: stable at vger.kernel.org
Assisted-by: Claude:claude-opus-4-8
Signed-off-by: Michael Bommarito <michael.bommarito at gmail.com>
---
Reproduced on a KASAN + refcount-full UML build: bring up a vec0
l2tpv3 device and send frames from the host with the right cookie but a
wrong session id. Stock kernel logs repeated "uml_l2tpv3: session
mismatch" then a refcount_t underflow / use-after-free in
dev_kfree_skb_irq_reason() <- vector_poll() <- vector_mmsg_rx(); with
this patch the mismatch is logged and the splat is gone (0 underflow, 0
use-after-free). Full dmesg and reproducer available on request.

 arch/um/drivers/vector_kern.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/arch/um/drivers/vector_kern.c b/arch/um/drivers/vector_kern.c
index 2cc90055499a5..8a70b3a625537 100644
--- a/arch/um/drivers/vector_kern.c
+++ b/arch/um/drivers/vector_kern.c
@@ -995,6 +995,9 @@ static int vector_mmsg_rx(struct vector_private *vp, int budget)
 				 */
 					dev_kfree_skb_irq(skb);
 					vp->estats.rx_encaps_errors++;
+					(*skbuff_vector) = NULL;
+					mmsg_vector++;
+					skbuff_vector++;
 					continue;
 				}
 				if (header_check > 0) {

base-commit: ef0c9f75a19532d7675384708fc8621e10850104
-- 
2.53.0




More information about the linux-um mailing list