Compare commits

...

12 Commits

Author SHA1 Message Date
V4bel aab16fcada update 2026-05-11 02:29:16 +09:00
V4bel cb2bc342d1 update 2026-05-11 02:19:41 +09:00
V4bel 5bb21af6dd update 2026-05-11 02:17:43 +09:00
V4bel 8beafb186f template 2026-05-10 05:57:35 +09:00
V4bel 882707286f typo 2026-05-10 04:27:55 +09:00
V4bel 07995be9d9 template 2026-05-08 18:21:57 +09:00
V4bel f3dd525bf6 CVE 2026-05-08 18:19:19 +09:00
V4bel 4bc7ffe2fb template 2026-05-08 18:12:55 +09:00
V4bel 7f0f3a1390 CVE 2026-05-08 18:10:42 +09:00
V4bel 979a5d992d Merge pull request #20 from Nriver/master
Update README: clarify page cache cleanup after exploit
2026-05-08 16:24:45 +09:00
Nate River beeb925e30 Enhance mitigation instructions in README
Updated mitigation instructions to include clearing the page cache after removing vulnerable modules.
2026-05-08 13:49:44 +08:00
Nate River f2796739b2 Update README: clarify page cache cleanup after exploit 2026-05-08 11:58:36 +08:00
2 changed files with 42 additions and 23 deletions
+22 -8
View File
@@ -8,13 +8,17 @@
![tux](assets/demo.gif)
This document describes the Dirty Frag vulnerability class, first discovered and reported by [Hyunwoo Kim (@v4bel)](https://x.com/v4bel), which can obtain root privileges on major Linux distributions by chaining the `xfrm-ESP Page-Cache Write` vulnerability and the `RxRPC Page-Cache Write` vulnerability.
This document describes the Dirty Frag vulnerability class, first discovered and reported by [Hyunwoo Kim (@v4bel)](https://x.com/v4bel), which can obtain root privileges on major Linux distributions by chaining the `xfrm-ESP Page-Cache Write (CVE-2026-43284)` vulnerability and the `RxRPC Page-Cache Write (CVE-2026-43500)` vulnerability.
Dirty Frag is a case that extends the bug class to which [Dirty Pipe](https://dirtypipe.cm4all.com/) and [Copy Fail](https://copy.fail/) belong. Because it is a deterministic logic bug that does not depend on a timing window, no race condition is required, the kernel does not panic when the exploit fails, and the success rate is very high.
For detailed technical information and the timeline, [see here](assets/write-up.md).
Because the embargo has currently been broken, no patch or CVE exists. After consultation with the maintainers on linux-distros@vs.openwall.org and at their request, this Dirty Frag document is being published. For the disclosure timeline, refer to the technical details.
- `xfrm-ESP Page-Cache Write (CVE-2026-43284)` was patched in mainline [f4c50a4034e6](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=f4c50a4034e62ab75f1d5cdd191dd5f9c77fdff4).
- `RxRPC Page-Cache Write (CVE-2026-43500)` was patched in mainline [aa54b1d27fe0](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=aa54b1d27fe0c2b78e664a34fd0fdf7cd1960d71).
> [!NOTE]
> At the time this document was first made public (2026-05-07), the embargo had been broken due to external factors, so no patch or CVE existed yet. After consultation with the maintainers on linux-distros@vs.openwall.org at that time, the Dirty Frag document was published at their request. For the disclosure timeline, refer to the technical details.
# Exploiting
@@ -26,9 +30,20 @@ git clone https://github.com/V4bel/dirtyfrag.git && cd dirtyfrag && gcc -O0 -Wal
This PoC is provided as accurate information following consultation with linux-distros. Do not use it on systems that you are not authorized to test.
## Cleanup
⚠️ **Important:** After running this exploit, the page cache is contaminated. To clear the polluted page cache and ensure system stability, either run:
```bash
echo 3 > /proc/sys/vm/drop_caches
```
or reboot the system.
# Affected Versions
The xfrm-ESP Page-Cache Write vulnerability is in scope from cac2661c53f3 (2017-01-17) up to upstream, and the RxRPC Page-Cache Write vulnerability is in scope from 2dc334f1a63a (2023-06) up to upstream.
- **CVE-2026-43284**: xfrm-ESP Page-Cache Write vulnerability is in scope from [cac2661c53f3 (2017-01-17)](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=cac2661c53f3) up to [f4c50a4034e6 (2026-05-05)](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=f4c50a4034e62ab75f1d5cdd191dd5f9c77fdff4).
- **CVE-2026-43500**: RxRPC Page-Cache Write vulnerability is in scope from [2dc334f1a63a (2023-06-08)](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=2dc334f1a63a) up to [aa54b1d27fe0 (2026-05-10)](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=aa54b1d27fe0c2b78e664a34fd0fdf7cd1960d71).
In other words, the effective lifetime of the vulnerabilities is about 9 years.
@@ -44,10 +59,9 @@ This Dirty Frag has been tested on the following distribution versions.
# Mitigation
1. Because the responsible disclosure schedule and the embargo have been broken, no patch exists for any distribution. Use the following command to remove the modules in which the vulnerabilities occur.
```
sh -c "printf 'install esp4 /bin/false\ninstall esp6 /bin/false\ninstall rxrpc /bin/false\n' > /etc/modprobe.d/dirtyfrag.conf; rmmod esp4 esp6 rxrpc 2>/dev/null; true"
1. Use the following command to remove the modules in which the vulnerabilities occur and clear the page cache.
```bash
sh -c "printf 'install esp4 /bin/false\ninstall esp6 /bin/false\ninstall rxrpc /bin/false\n' > /etc/modprobe.d/dirtyfrag.conf; rmmod esp4 esp6 rxrpc 2>/dev/null; echo 3 > /proc/sys/vm/drop_caches; true"
```
2. Once each distribution backports a patch, update accordingly.
@@ -72,4 +86,4 @@ Copy Fail was the motivation for starting this research. In particular, xfrm-ESP
## So, how do I fix my Linux?
Refer to the Mitigation and [Disclosure Timeline sections](assets/write-up.md). Due to external factors, the embargo has been broken, so no patch exists for any distribution.
Refer to the Mitigation section above.
+20 -15
View File
@@ -30,7 +30,7 @@ Dirty Frag is a vulnerability where the same pattern is reproduced on top of the
Note that Dirty Frag can be triggered regardless of whether the `algif_aead` module is available. In other words, even on systems where the publicly known Copy Fail mitigation (algif_aead blacklist) is applied, your Linux is still vulnerable to Dirty Frag.
# xfrm-ESP Page-Cache Write
# CVE-2026-43284: xfrm-ESP Page-Cache Write
## Root Cause
@@ -178,7 +178,7 @@ By cycling i over 0..47, the 192-byte ELF is fully assembled on top of the page
## Patch
The [patch](https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git/commit/?id=f4c50a4034e62ab75f1d5cdd191dd5f9c77fdff4) sets the `SKBFL_SHARED_FRAG` flag on page frags that came in via `splice` in the IPv4/IPv6 datagram append paths, and in the skip_cow branch of ESP input (`esp_input` / `esp6_input`) it checks this flag so that an skb with externally pinned pages is always routed to the `skb_cow_data` path. As a result, attacker-pinned page cache pages can no longer enter the dst SGL of the in-place AEAD, and page cache modification is blocked.
The [patch](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=f4c50a4034e62ab75f1d5cdd191dd5f9c77fdff4) sets the `SKBFL_SHARED_FRAG` flag on page frags that came in via `splice` in the IPv4/IPv6 datagram append paths, and in the skip_cow branch of ESP input (`esp_input` / `esp6_input`) it checks this flag so that an skb with externally pinned pages is always routed to the `skb_cow_data` path. As a result, attacker-pinned page cache pages can no longer enter the dst SGL of the in-place AEAD, and page cache modification is blocked.
```diff
diff --git a/net/ipv4/esp4.c b/net/ipv4/esp4.c
@@ -249,8 +249,10 @@ My v1 patch took the approach of calling `skb_cow_data()` directly in the input
- 2026-05-07: Submitted detailed information about the vulnerability and the exploit to the linux-distros mailing list. The embargo was set to 5 days, with an agreement that if a third party publishes the exploit on the internet during the embargo period, the Dirty Frag exploit would be published publicly.
- 2026-05-07: Detailed information and the exploit for this vulnerability were published publicly by an unrelated third party, breaking the embargo.
- 2026-05-07: After obtaining agreement from distribution maintainers to fully disclose Dirty Frag, the entire Dirty Frag document was published.
- 2026-05-08: The [f4c50a4034e6](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=f4c50a4034e62ab75f1d5cdd191dd5f9c77fdff4) patch was merged into mainline.
- 2026-05-08: This vulnerability was assigned CVE-2026-43284.
# RxRPC Page-Cache Write
# CVE-2026-43500: RxRPC Page-Cache Write
## Root Cause
@@ -382,40 +384,41 @@ recvmsg(rxsk_cli, &m, 0)
fcrypt_decrypt(page_address(P) + splice_off, ct, K) // 8 byte STORE: page P[splice_off..+8] = fcrypt_decrypt(C, K)
```
Each STORE plants exactly 8 bytes at file offset (`splice_off`). The HMAC/sechdr verification afterward returns `-EPROTO`, but the STORE is already done.
Each STORE plants exactly 8 bytes at file offset (`splice_off`). The sechdr verification afterward returns `-EPROTO`, but the STORE is already done.
For each of the three positions (off = 4, 6, 8), the exploit runs the following sequence in turn: update K, `add_key`, socket setup, handshake, cksum computation, splice + recvmsg. With last-write-wins, chars 4..15 of `/etc/passwd` line 1 are replaced with the shape `"::0:0:GGGGGG:"`. Finally, when the parent process execs `/usr/bin/su -` along with a PTY, `pam_unix.so nullok` of PAM common-auth accepts the empty passwd field and lets it through without a prompt. su then performs `setresuid(0, 0, 0)` and execs `/bin/bash`, dropping into a root shell. This variant does not use `unshare()`, and `add_key()`, `socket(AF_RXRPC)`, `socket(AF_ALG)` (for cksum computation), `splice()`, and `recvmsg()` are all APIs available to unprivileged users.
## Patch
A patch for this vulnerability does not exist upstream. The [patch](https://lore.kernel.org/all/afKV2zGR6rrelPC7@v4bel/) that I submitted is as follows:
The existing code only checked `skb_cloned(skb)` right before the in-place decrypt, so a non-linear skb pinned into the frag via splice reached the decrypt sink as is. This patch adds `|| skb->data_len` to the gate so that non-linear skbs are also isolated via `skb_copy()`.
The [patch](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=aa54b1d27fe0c2b78e664a34fd0fdf7cd1960d71) extends the gate before in-place decryption from a single `skb_cloned(skb)` check to also catch `skb_has_frag_list(skb) || skb_has_shared_frag(skb)`, so that skbs carrying a chained frag list or externally-shared paged frags are isolated via `skb_copy()` instead of reaching the decrypt sink directly.
```diff
diff --git a/net/rxrpc/call_event.c b/net/rxrpc/call_event.c
index fdd683261226..6c924ef55208 100644
index fdd683261226..2b19b252225e 100644
--- a/net/rxrpc/call_event.c
+++ b/net/rxrpc/call_event.c
@@ -334,7 +334,7 @@ bool rxrpc_input_call_event(struct rxrpc_call *call)
@@ -334,7 +334,9 @@ bool rxrpc_input_call_event(struct rxrpc_call *call)
if (sp->hdr.type == RXRPC_PACKET_TYPE_DATA &&
sp->hdr.securityIndex != 0 &&
- skb_cloned(skb)) {
+ (skb_cloned(skb) || skb->data_len)) {
+ (skb_cloned(skb) ||
+ skb_has_frag_list(skb) ||
+ skb_has_shared_frag(skb))) {
/* Unshare the packet so that it can be
* modified by in-place decryption.
*/
diff --git a/net/rxrpc/conn_event.c b/net/rxrpc/conn_event.c
index a2130d25aaa9..eab7c5f2517a 100644
index a2130d25aaa9..442414d90ba1 100644
--- a/net/rxrpc/conn_event.c
+++ b/net/rxrpc/conn_event.c
@@ -245,7 +245,7 @@ static int rxrpc_verify_response(struct rxrpc_connection *conn,
@@ -245,7 +245,8 @@ static int rxrpc_verify_response(struct rxrpc_connection *conn,
{
int ret;
- if (skb_cloned(skb)) {
+ if (skb_cloned(skb) || skb->data_len) {
+ if (skb_cloned(skb) || skb_has_frag_list(skb) ||
+ skb_has_shared_frag(skb)) {
/* Copy the packet if shared so that we can do in-place
* decryption.
*/
@@ -428,6 +431,8 @@ index a2130d25aaa9..eab7c5f2517a 100644
- 2026-05-07: Submitted detailed information about the vulnerability and the exploit to the linux-distros mailing list. The embargo was set to 5 days, with an agreement that if a third party publishes the exploit on the internet during the embargo period, the Dirty Frag exploit would be published publicly.
- 2026-05-07: Detailed information and the exploit for the esp vulnerability were published publicly by an unrelated third party, breaking the embargo.
- 2026-05-07: After obtaining agreement from distribution maintainers to fully disclose Dirty Frag, the entire Dirty Frag document was published.
- 2026-05-08: CVE-2026-43500 was reserved for tracking this vulnerability.
- 2026-05-10: The [aa54b1d27fe0](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=aa54b1d27fe0c2b78e664a34fd0fdf7cd1960d71) patch was merged into mainline.
# Chaining