
Mitigação baseada em Seccomp para CVE-2026-31431, uma LPE do kernel Linux. Bloqueia o socket AF_ALG via módulo PAM e wrapper autônomo, com detecção automática de kernels corrigidos.
Uma mitigação leve e reversível baseada em seccomp para CVE-2026-31431, uma vulnerabilidade de escalonamento de privilégios local no subsistema criptográfico algif_aead / authencesn do kernel Linux.
Tipo: Escalonamento de Privilégios Local (LPE)
Componente Afetado: crypto/algif_aead.c do kernel Linux - operação AEAD in-place
Primitiva de Ataque: Uma escrita controlável de 4 bytes no cache de páginas de qualquer arquivo legível através do caminho de escrita temporária (scratch-write) do algoritmo AEAD authencesn. Ao mirar em /etc/passwd, um atacante pode alterar seu UID para 0 (root) e obter um shell root via su.
Kernels Afetados: Confirmado nos kernels 6.12+, 6.17+, 6.18+, e também reproduzido nos kernels RHEL/CentOS 4.18/5.14.
Ambientes Verificados: Rocky Linux 8 (kernel 4.18) e Rocky Linux 9 (kernel 5.14) - exploit totalmente bloqueado, remoção segura confirmada.
Causa Raiz: O commit 72548b093ee3 introduziu a operação AEAD in-place. Quando páginas do cache de páginas emendadas (spliced) são usadas como scatterlist de destino, o campo AAD seqno_lo é incorretamente gravado de volta no cache de páginas durante a descriptografia AEAD.
Correção Upstream: Reverter para operação AEAD out-of-place.
Esta solução possui dois componentes:
Módulo PAM (pam_block_afalg.so) - A defesa primária. Carregado pelo PAM durante a abertura de sessão (pam_sm_open_session), aplica um filtro seccomp BPF que bloqueia socket(AF_ALG, ...) antes que qualquer código do usuário seja executado. Isso cobre TODAS as sessões autenticadas via PAM: su -c, su -, SSH, login TTY, etc.
Binário autônomo (block_afalg) - Opcional. Pode envolver programas específicos para cenários sem PAM (ex.: jobs cron, serviços systemd, invocação manual).
O filtro seccomp:
socket(AF_ALG, ...) (retorna EACCES)setuid, su, sudo)Abertura de sessão PAM (su, ssh, login, etc.)
|
v
pam_block_afalg.so (pam_sm_open_session)
|
+-- Verifica: o kernel é vulnerável? (tenta socket(AF_ALG))
| |
| +-- Não --> retorna PAM_SUCCESS (no-op)
| |
| +-- Sim --> prctl(PR_SET_SECCOMP, filtro BPF)
| |
| +-- filtro seccomp ativo no processo filho do sshd
| +-- herdado pelo shell do usuário e TODOS os processos filhos
| +-- socket(AF_ALG, ...) retorna EACCES
v
Shell / comando do usuário é executado com proteção seccomp
|
+-- su, sudo e todas as outras syscalls funcionam normalmente
+-- Apenas o socket AF_ALG é bloqueado
| Arquivo | Finalidade |
|---|---|
pam_block_afalg.c | Código-fonte do módulo PAM. Aplica o filtro seccomp na abertura de sessão. |
pam_minimal.h | Definições mínimas de tipos PAM (compila sem pam-devel). |
block_afalg.c | Binário wrapper seccomp autônomo. Para uso sem PAM. |
deploy.sh | Script de implantação. Compila, instala e gerencia o módulo PAM. |
gcc (para compilação)libpam (runtime, geralmente pré-instalado)# 1. Compilar o módulo PAM
gcc -Wall -O2 -fPIC -shared -o pam_block_afalg.so pam_block_afalg.c \
/usr/lib64/libpam.so.0
# 2. Instalar (adiciona automaticamente configs PAM ao su, sshd, login)
sudo ./deploy.sh install
# 3. Verificar (deve ser uma NOVA sessão)
cat /proc/self/status | grep Seccomp
# Deve mostrar: Seccomp: 2
python3 -c "
import socket
try:
s = socket.socket(38,2,0); s.close()
print('VULNERABLE')
except OSError:
print('BLOCKED')
"
# Deve mostrar: BLOCKED
# 4. Desinstalar
sudo ./deploy.sh remove
| Comando | Descrição |
|---|---|
deploy.sh install | Compila o módulo PAM, instala em /lib64/security/, adiciona automaticamente configs PAM |
deploy.sh remove | Desinstalação completa: remove o módulo, limpa configs PAM, exclui arquivos |
deploy.sh status | Mostra o estado da instalação, configs PAM, status do kernel |
Para cenários sem PAM, use block_afalg diretamente:
# Compilar
gcc -Wall -O2 -o block_afalg block_afalg.c
# Executar um comando com AF_ALG bloqueado
./block_afalg python3 your_script.py
./block_afalg bash
python3 -c "
import socket
try:
s = socket.socket(38, socket.SOCK_SEQPACKET, 0)
s.close()
print('VULNERABLE: AF_ALG socket available')
except:
print('SAFE: AF_ALG socket blocked or unavailable')
"
# Verificar o status do seccomp
cat /proc/self/status | grep Seccomp
# Seccomp: 0 = não protegido
# Seccomp: 2 = protegido
# Testar o socket AF_ALG
python3 -c "
import socket
try:
s = socket.socket(38,2,0)
s.close()
print('AF_ALG available - NOT protected')
except OSError:
print('AF_ALG blocked - PROTECTED')
"
# Verificar logs do PAM
grep pam_block_afalg /var/log/secure
# Deve mostrar: seccomp filter applied, AF_ALG blocked
__NR_socket no x86_64). Outras arquiteturas precisam atualizar o número da syscall.exec() sem PAM não são cobertas (use block_afalg para esses casos).remove.yum update kernel e depois remova o módulo.Esta ferramenta é fornecida apenas para fins autorizados de teste de segurança e defesa. Use apenas em sistemas que você possui ou que está explicitamente autorizado a avaliar.