ACK/Cmnt: [SRU][J][PATCH 0/1] CVE-2026-43500
Cengiz Can
cengiz.can at canonical.com
Thu May 21 17:55:25 UTC 2026
On 5/21/26 20:17, John Cabaj wrote:
> On 5/21/26 11:52 AM, Cengiz Can wrote:
>> https://ubuntu.com/security/CVE-2026-43500
>>
>> [ Impact ]
>>
>> The DATA-packet handler in net/rxrpc/input.c calls skb_unshare() to
>> copy the skb to a linear one before in-place decryption, but
>> skb_unshare() only copies when skb_cloned() is true. An skb that
>> is not cloned but carries externally-owned paged fragments (pages
>> deposited by splice() into a UDP socket bound to rxrpc) falls
>> through to the in-place decryption path. The AEAD/skcipher SGL is
>> built directly over the externally-owned pages via skb_to_sgvec(),
>> and the decrypt writes plaintext into the original page cache.
>>
>> An unprivileged local user can use this primitive to corrupt the
>> page cache of a read-only file owned by root (e.g. /etc/passwd),
>> yielding a local privilege escalation. The bug is empirically
>> reproducible on the released GA jammy kernel image (5.15.0-101 and
>> later) via the public V4bel exp.c with the --force-rxrpc flag, run
>> as uid=1000 with no namespaces and no AppArmor evasion.
>>
>> The rxrpc module auto-loads on socket(AF_RXRPC) from an
>> unprivileged user, so AppArmor's unprivileged_userns profile does
>> not mitigate this code path.
>>
>>
>> [ Fix ]
>>
>> This submission targets jammy 5.15.
>>
>> Upstream commit aa54b1d27fe0c2b78e664a34fd0fdf7cd1960d71 ("rxrpc:
>> Also unshare DATA/RESPONSE packets when paged frags are present",
>> v7.1-rc3) widens the gate to also catch shared paged fragments
>> before in-place decrypt.
>>
>> The jammy backport differs from upstream along two axes:
>>
>> 1. Target file. Upstream patches rxrpc_input_call_event() in
>> net/rxrpc/call_event.c and rxrpc_verify_response() in
>> net/rxrpc/conn_event.c. Both functions were added by the
>> v7.1-rc1 unshare-move refactors 1f2740150f90 ("rxrpc: Fix
>> potential UAF after skb_unshare() failure") and 24481a7f5733
>> ("rxrpc: Fix conn-level packet handling to unshare RESPONSE
>> packets"). Neither refactor is present in jammy 5.15. The
>> backport instead applies the fix to the older unconditional
>> skb_unshare() call site in net/rxrpc/input.c.
>>
>> 2. Gate predicate. Upstream uses
>> skb_cloned() || skb_has_frag_list() || skb_has_shared_frag().
>> SKBFL_SHARED_FRAG is set in __ip_append_data by the companion
>> DirtyFrag-ESP fix f4c50a4034e6 ("xfrm: esp: avoid in-place
>> decrypt on shared skb frags"), which is not yet backported to
>> jammy. Without that flag-setter, splice() into a UDP socket on
>> jammy goes through udp_sendpage / ip_append_page and never
>> sets the flag, so skb_has_shared_frag() returns false on the
>> very skbs the gate needs to catch. The backport substitutes
>> skb_is_nonlinear() for the two flag-based checks. It is a
>> strict superset that catches the same skbs the upstream gate
>> targets and is correct independent of the DirtyFrag-ESP
>> backport status.
>
> Does this check require re-evaluation once DirtyFrag-ESP backport hits? It seems that was backported to 5.15 in https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/commit/?h=linux-5.15.y&id=ab8b995323e5237041472d07e5055f5f7dcdf15b
>
Hi John,
Thanks for the pointer. Really useful to cross-check.
Quick clarification: the commit you linked, ab8b995323e5 on linux-5.15.y, is the stable
backport of f4c50a4034e6 "xfrm: esp: avoid in-place decrypt on shared skb frags". That's
CVE-2026-43284 (the ESP half of Dirty Frag), not CVE-2026-43500 (the rxrpc half).
For 43500 specifically (aa54b1d27fe0 upstream), I searched and found:
- linux-5.15.y stable: no backport yet. The v7.1-rc1 prerequisite refactors
(1f2740150f90, 55b2984c96c3, 24481a7f5733) are also not in 5.15.y.
- linux-5.10.y, linux-5.4.y: also nothing.
- linux-6.6.y stable: full 4-commit chain. The three v7.1-rc1 refactors backported
first, then aa54b1d27fe0 applied verbatim.
- linux-6.12.y, linux-6.18.y, linux-7.0.y stable: have the fix.
Since 5.15.y stable hasn't taken either the refactors or the fix, I went with a
tree-specific adjusted backport: 1 commit, 7 lines in net/rxrpc/input.c, applying the
same logical gate to the pre-refactor skb_unshare() call site.
PoC-verified against the V4bel --force-rxrpc exploit on a built kernel. The patched
VM blocks the exploit (sha256 of /etc/passwd unchanged after the run; without the
patch it gets mutated).
If you'd prefer me to mirror the 6.6.y approach instead, backporting the three
prerequisite refactors and then applying the fix verbatim, happy to redo it that way.
These files will be modified if we do the 6.6.y approach:
net/rxrpc/input.c
net/rxrpc/io_thread.c,
net/rxrpc/input.c
net/rxrpc/call_event.c,
net/rxrpc/conn_event.c
net/rxrpc/ar-internal.h
The single-commit version was the lower-risk option, but I'm not married to it if you'd
rather see the multi-commit pattern that matches what stable did for the 6.6.y backport.
Cengiz
> Otherwise
>
> Acked-by; John Cabaj <john.cabaj at canonical.com>
>
>
>>
>>
>> [ Test Plan ]
>>
>> Booted linux-image-5.15.0-180-generic with this backport applied.
>> Ran the public V4bel ./exp --force-rxrpc as an unprivileged user
>> inside a uvt-kvm jammy VM. Pre-test sha256 of /etc/passwd captured;
>> post-test sha256 reread without dropping caches; getent passwd
>> root reread to confirm via NSS.
>>
>> pre sha256(/etc/passwd) = e1dbccbd4c798210ea8902dca26879820d7f43e8b34142a9c5984db04cb3b8e1
>> post sha256(/etc/passwd) = e1dbccbd4c798210ea8902dca26879820d7f43e8b34142a9c5984db04cb3b8e1
>> getent passwd root pre = root:x:0:0:root:/root:/bin/bash
>> getent passwd root post = root:x:0:0:root:/root:/bin/bash
>> exp.c outcome = "dirtyfrag: failed (rc=4)"
>> exp.c self-check = "post-trigger sanity check failed -- char layout off"
>>
>> The exploit aborted because the page-cache write primitive did not
>> land. The same exploit on the unpatched 5.15.0-101 image produces
>> a mutated /etc/passwd with an empty root password field (verified
>> in prior testing).
>>
>>
>> [ Where Problems Could Occur ]
>>
>> This change affects only the rxrpc protocol with rxkad encryption
>> enabled. rxrpc is used almost exclusively by AFS (Andrew File
>> System) clients; non-AFS workloads do not touch this code path.
>>
>> For AFS workloads, the change may cause the kernel to allocate a
>> copy of an incoming packet more often than before in cases where
>> the packet arrives with paged fragments. In practice these
>> fragments only appear when the packet comes from a non-NIC source
>> (splice loopback, certain virtual devices). Ordinary AFS over
>> Ethernet receives linear skbs and is unaffected.
>>
>> If a regression were to occur it would most likely manifest as
>> slightly higher CPU and memory use on AFS clients under heavy
>> load, not as a functional failure. No data path is changed; the
>> fix only adds a copy decision before processing.
>>
>>
>> [ Other Info ]
>>
>> Colloquially known as the rxrpc half of "Dirty Frag" (the ESP half
>> is CVE-2026-43284).
>>
>
>
More information about the kernel-team
mailing list