
Exploit de escalada de privilégios local para CVE-2026-31431, uma sobrescrita de page-cache via AF_ALG + splice no kernel Linux. Inclui PoC, script de detecção BPFtrace e ambiente de teste QEMU para pesquisa de segurança autorizada.
Escalação de privilégios local no kernel Linux via AF_ALG + sobrescrita do page-cache com splice
Apenas para pesquisa de segurança autorizada, testes de penetração e fins educacionais. Não use contra sistemas que você não possui ou para os quais não tem permissão explícita por escrito para testar.
CVE-2026-31431 é uma vulnerabilidade de escalação de privilégios local (LPE) no kernel Linux. Um
usuário local sem privilégios pode obter acesso root combinando a interface de socket AF_ALG com
splice() para realizar uma escrita autenticada diretamente em uma página do page-cache pertencente a um
binário setuid.
O exploit sobrescreve o binário su no page-cache sem modificar o inode no disco,
contornando mecanismos de integridade que dependem apenas de metadados de arquivo ou checksums em nível de bloco.
| Campo | Valor |
|---|---|
| ID CVE | CVE-2026-31431 |
| Tipo | Escalação de Privilégios Local (LPE) |
| Pontuação CVSS v3.1 | 7.8 Alta — AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H (fonte: kernel.org) |
| Subsistemas do kernel | crypto/af_alg.c, mm/splice.c |
| Vetor de ataque | Local — requer conta de usuário sem privilégios |
| Causa raiz | algif_aead aceita sendfile() sobre um socket AEAD sem impor semânticas de copy-on-write na página do page-cache mapeada antes de splice() concluir a transferência |
| Distro | Versão do kernel | Arquitetura |
|---|---|---|
| Ubuntu 24.04 LTS | 6.17.0-1007-aws | x86_64 |
| Amazon Linux 2023 | 6.18.8-9.213.amzn2023 | x86_64 |
| RHEL 10.1 | 6.12.0-124.45.1.el10_1 | x86_64 |
| SUSE 16 | 6.12.0-160000.9-default | x86_64 |
| Raspberry Pi OS (Pi 5) | 6.12.75+rpt-rpi-2712 | aarch64 |
.
├── exploit.py # PoC — sobrescrita do page-cache e escalação de privilégios
├── detect.bt # Script BPFtrace para detecção em tempo real
├── run-vm.sh # Automação de ambiente de teste QEMU (opcional)
├── PAYLOAD.md # Análise de codificação do payload (hex → zlib → ELF → shellcode)
└── LICENSE
Execute exploit.py como um usuário local sem privilégios em qualquer sistema vulnerável — não é necessário sudo:
python3 exploit.py
O script executa os seguintes passos:
AF_ALG (algif_aead) e localiza o binário su.su como um descritor de arquivo bruto e sobrescreve suas páginas do page-cache via
AF_ALG + sendfile.Arquiteturas suportadas:
| Arquitetura | Variantes |
|---|---|
| x86_64 | — |
| aarch64 | — |
| riscv64 | — |
| ppc64le | — |
| arm | armv5l, armv6l, armv7l |
| x86 32-bit | i386, i486, i586, i686 |
| MIPS 64-bit | mips64, mips64el |
| LoongArch | loong64, loongarch64 |
| s390x | — |
Monitore tentativas de exploração em tempo real com detect.bt. Requer root:
sudo bpftrace detect.bt
# ou
doas bpftrace detect.bt
O script rastreia três indicadores por PID usando uma máscara de bits em @suspect[pid]:
| Bit | Syscall | Indicador |
|---|---|---|
0x1 | socket(AF_ALG, SOCK_SEQPACKET) | Socket AF_ALG criado |
0x2 | setsockopt(SOL_ALG, ...) | Operação criptográfica configurada |
0x4 | sendmsg(MSG_MORE) + splice() | Tentativa de sobrescrita do page-cache |
Um alerta é disparado quando todos os três bits estão definidos (@suspect[pid] == 0x7) no mesmo PID.
exploit.pyAF_ALG/algif_aead carregadodetect.btbpftrace ≥ 0.12# Ubuntu/Debian
sudo apt install bpftrace
# RHEL/CentOS/Fedora
sudo dnf install bpftrace
# Amazon Linux
sudo yum install bpftrace
# SUSE
sudo zypper install bpftrace
# Alpine
sudo apk add bpftrace
Atualize o pacote do kernel da sua distribuição para uma versão que inclua o commit da linha principal
a664bf3d603d,
que reverte a otimização in-place do algif_aead de 2017 para que páginas do page-cache não possam mais
acabar no scatterlist de destino gravável. A maioria das grandes distribuições já está distribuindo a correção.
algif_aead (enquanto aguarda um patch)O blacklist pode ser contornado com um modprobe algif_aead explícito. A diretiva install .../bin/false
substitui completamente o comando de instalação, fazendo com que toda tentativa de carregamento falhe:
echo "install algif_aead /bin/false" | sudo tee /etc/modprobe.d/disable-algif.conf
sudo rmmod algif_aead 2>/dev/null || true