NGINX Rift (CVE-2026-42945): um heap overflow de 18 anos no módulo de reescrita
NGINX Rift (CVE-2026-42945, CVSS 9.2): Um estouro de buffer de heap crítico no módulo de reescrita do NGINX, descoberto autonomamente pelo sistema de análise de IA do deepfirst. Introduzido em 2008 e impactando 18 anos de lançamentos do NGINX, ele permite que um invasor não autenticado realize a execução remota de código com uma única solicitação HTTP criada.
A vulnerabilidade que estava escondida à vista de todos
Em 13 de maio de 2026, F5 e deepfirst divulgaram em conjunto CVE-2026-42945 — um estouro de buffer de heap crítico no ngx_http_rewrite_module do NGINX. A vulnerabilidade estava na base de código desde 2008, introduzida no NGINX 0.6.27, afetando todas as versões subsequentes até 1.30.0.
O que torna esta descoberta particularmente notável é como ela foi encontrada: não por um pesquisador humano auditando manualmente o código, mas pelo sistema autônomo de análise de vulnerabilidades da Deepfirst. O sistema de IA foi apontado para o código-fonte do NGINX e, em seis horas, sinalizou o problema de heap overflow que escapou da detecção humana por 18 anos.
| Métrica | Valor |
|---|---|
| CVE | CVE-2026-42945 |
| CVSS v4.0 | 9.2 (Crítico) |
| Descoberto por | deepfirst (análise autônoma de IA) |
| Introduzido | 2008 (NGINX 0.6.27) |
| Esperado por | 18 anos |
| Tipo de vulnerabilidade | Estouro de buffer de heap (incompatibilidade de comprimento de duas passagens) |
| Autenticação necessária | Nenhum |
| Impacto | Execução remota de código (RCE) ou falha de trabalho (DoS) |
| Corrigir versão | NGINX 1.31.0/1.30.1 |
Versões afetadas
A vulnerabilidade abrange quase todas as linhas de produtos NGINX:
| Produto | Versões afetadas |
|---|---|
| Código aberto NGINX | 0.6.27 a 1.30.0 |
| NGINX Plus | R32 a R36 |
| Gerenciador de instância NGINX | 2.16.0 a 2.21.1 |
| Aplicativo F5 NGINX protege WAF | 4.9.0–4.16.0, 5.1.0–5.8.0 |
| Controlador de entrada NGINX | 3.5.0–3.7.2, 4.0.0–4.0.1, 5.0.0–5.4.1 |
| Malha de gateway NGINX | 1.3.0–1.6.2, 2.0.0–2.5.1 |
Dado que o NGINX alimenta aproximadamente um terço de todos os sites globalmente, o raio de explosão desta vulnerabilidade é enorme.
Aprofundamento Técnico
O design de duas passagens
Para entender o bug, você precisa entender o mecanismo de script do NGINX. Quando o NGINX avalia uma diretiva rewrite ou set, ele opera em duas passagens:
- Comprimento da passagem (
ngx_http_script_len_code): Calcula o tamanho total do buffer necessário para armazenar a saída final - Copiar senha (
ngx_http_script_run/ngx_http_script_copy_code): Aloca um buffer desse tamanho e grava os dados reais
O contrato é simples: a passagem 1 informa exatamente quantos bytes devem ser alocados, a passagem 2 escreve exatamente essa quantidade de bytes. Se os dois discordarem, você terá um estouro de pilha.
Causa raiz: o sinalizador is_args órfão
A vulnerabilidade reside em src/http/ngx_http_script.c. Quando a string de substituição de uma diretiva rewrite contém um ponto de interrogação (?), a função ngx_http_script_start_args_code define um sinalizador no mecanismo de script:
e->is_args = 1;Este sinalizador sinaliza que os componentes URI subsequentes devem ser tratados como argumentos de consulta e escapados por URI (por exemplo, + → %2B, & → %26).
O problema: este sinalizador nunca é redefinido. Ele permanece definido no mecanismo de script principal (e) durante o restante do processamento da solicitação.
A incompatibilidade
Quando uma diretiva set subsequente faz referência a um grupo de captura de regex (por exemplo, $1), o mecanismo de script a avalia. Durante a passagem de comprimento, ngx_http_script_complex_value_code cria um submecanismo novo e zerado (le):
ngx_http_script_len_code_ctx_t le;ngx_memzero(&le, sizeof(ngx_http_script_len_code_ctx_t));Como le.ip e le.is_args são ambos zero, a função de cálculo de comprimento ngx_http_script_copy_capture_len_code pega a ramificação else — ela retorna o comprimento de captura bruto e sem escape.
Durante a passagem de cópia, o código é executado no mecanismo principal (e), onde e->is_args ainda é 1. A função de cópia ngx_http_script_copy_capture_code entra em uma ramificação diferente:
if (e->is_args) { // Escapes the URI: expands + % & from 1 byte to 3 bytes n = ngx_escape_uri(NULL, src, len, NGX_ESCAPE_ARGS); // ...allocates and writes escaped version}Cada caractere evitável no URI controlado pelo invasor (+, %, &) se expande de 1 byte para 3 bytes. O buffer foi dimensionado para o comprimento bruto (sem escape) — a gravação passa da alocação.
// Length pass measures: raw_len bytes// Copy pass writes: raw_len + 2*N bytes (where N = escapable chars)// ↑↑↑ HEAP OVERFLOWEsta é uma clássica violação de contrato em duas passagens, possível porque o estado is_args foi definido por uma diretiva rewrite completamente não relacionada e nunca foi limpo.
Exploração
Os pesquisadores em profundidade desenvolveram uma prova de conceito funcional demonstrando RCE não autenticado contra NGINX com ASLR desativado. As principais propriedades que tornam a exploração prática:| Propriedade | Detalhe |
|—|—|
| Tamanho do estouro | Totalmente controlado pelo invasor (número de +, &, % em URI) |
| Excesso de dados | Controlado pelo invasor (conteúdo de URI escapado) |
| Reprodutibilidade | Determinístico — a mesma solicitação sempre transborda da mesma maneira |
| Tentar novamente o orçamento | Infinito – trabalhadores travados reaparecem com layout de heap idêntico |
| Autenticação | Não é necessário — acessível através da Internet pública |
O orçamento de novas tentativas infinitas é particularmente importante para o desvio de ASLR. A exploração moderna contra ASLR normalmente requer vazamento de informações ou força bruta. Como o NGINX gera trabalhadores substitutos com um layout de heap idêntico após cada falha, um invasor pode fazer tentativas ilimitadas sem nenhum custo.
Os pesquisadores descrevem uma técnica teórica: ao sobrescrever progressivamente os bytes do ponteiro em solicitações repetidas, um invasor pode redirecionar o fluxo de execução para uma carga controlada, derrotando o ASLR sem uma etapa explícita de vazamento de informações.
Condição de gatilho: você foi afetado?
A vulnerabilidade só é acessível se a configuração do NGINX contiver um padrão específico:
# Vulnerable pattern:# 1. A rewrite with ? in replacement AND unnamed capture groups# 2. Followed by another rewrite, if, or set in the same scope
rewrite ^/users/([0-9]+)/profile/(.*)$ /profile.php?id=\$1&tab=\$2 last;O ? em /profile.php?id=$1&tab=$2 define is_args = 1. As capturas sem nome $1, $2 acionam o caminho do código vulnerável quando uma diretiva subsequente as avalia.
Verifique sua configuração
grep -rn 'rewrite.*\?.*\$[0-9]' /etc/nginx/Se isso retornar alguma correspondência, sua configuração será afetada.
Mitigação
Imediato: Atualização
| Versão | Ação |
|---|---|
| Código aberto NGINX | Atualize para 1.31.0 ou 1.30.1 |
| NGINX Plus R36 | Aplicar R36 P4 |
| NGINX Plus R32 | Aplicar R32 P6 |
Solução alternativa: grupos de captura nomeados
Se você não puder atualizar imediatamente, substitua capturas sem nome por capturas nomeadas em cada diretiva rewrite afetada:
# Vulnerable — unnamed captures with ? in replacementrewrite ^/users/([0-9]+)/profile/(.*)$ /profile.php?id=\$1&tab=\$2 last;
# Mitigated — named captures bypass the vulnerable code pathrewrite ^/users/(?<user_id>[0-9]+)/profile/(?<section>.*)$ /profile.php?id=$user_id&tab=$section last;As capturas nomeadas ((?<name>...)) não passam pela lógica de escape vulnerável, porque a função ngx_http_script_copy_capture_code aplica apenas o escape de URI a capturas não nomeadas. Esta alteração de configuração remove a superfície de ataque sem uma atualização binária.
Verifique a correção
# Check versionnginx -v
# After upgrade, verify: should be 1.31.0 or 1.30.1+nginx -v 2>&1 | grep -E '1\.31\.0|1\.30\.[1-9]'Linha do tempo
| Data | Evento |
|---|---|
| 2008 | Vulnerabilidade introduzida no NGINX 0.6.27 (confirmar inicialização do módulo de reescrita) |
| 2026-04 | sistema autônomo deepfirst verifica fonte NGINX, sinaliza heap overflow em 6 horas |
| 2026/04/24 | F5 confirma o assunto e coordena divulgação |
| 13/05/2026 | F5 lança NGINX 1.31.0/1.30.1 com correção; CVE-2026-42945 publicado |
| 14/05/2026 | Este artigo publicado |
Implicações mais amplas: vulnerabilidades descobertas pela IA
CVE-2026-42945 é notável não apenas por sua gravidade, mas por como foi descoberto. Um sistema autônomo de IA encontrou um bug em uma base de código que foi auditada por milhares de engenheiros, pesquisadores de segurança e colaboradores de código aberto ao longo de 18 anos – em seis horas.
Isso segue um padrão que vimos acelerar em 2026:
| Vulnerabilidade | Descoberto por | Hora de encontrar |
|---|---|---|
| Falha na cópia (Linux kernel LPE) | Código Xint (AI) | ~1 hora |
| Dirty Frag (kernel Linux LPE) | Humano (Hyunwoo Kim) | Auditoria manual |
| CVE-2026-42945 (Rift NGINX) | profundidade primeiro (IA autônoma) | 6 horas |
| CVE-2026-42946 (sobreleitura NGINX) | profundidade primeiro (IA autônoma) | Mesma varredura |
A lacuna entre o que um determinado sistema de IA pode encontrar e o que os revisores humanos captaram historicamente está crescendo rapidamente. Para os mantenedores de infraestrutura crítica, isso significa:
- Suponha que haja mais bugs não descobertos em suas dependências — os encontrados até agora são exatamente o que a geração atual de ferramentas de IA pode detectar
- Minimize a superfície de ataque — remova módulos não utilizados, desative recursos desnecessários, use o princípio da menor funcionalidade
- Defesa em profundidade — mesmo que um componente esteja comprometido, outras camadas devem limitar o raio de explosão
O próprio NGINX é um caso interessante: é conhecido por sua base de código limpa e forte histórico de segurança. E, no entanto, um RCE crítico de 18 anos estava escondido à vista de todos. Se o NGINX não estiver protegido contra essa classe de bug, nenhuma base de código C estará.
Conclusão
CVE-2026-42945 (NGINX Rift) é um heap overflow crítico em um dos projetos de software mais amplamente implantados na Internet. Ele não requer autenticação, pode ser acionado pela Internet pública e fornece ao invasor a execução completa do código no processo de trabalho do NGINX.Se você executar o NGINX, presuma que foi afetado — a menos que tenha verificado que sua configuração não contém o padrão de reescrita vulnerável ou que tenha atualizado para 1.31.0/1.30.1.
A vida útil de 18 anos deste bug é um lembrete claro: nossa infraestrutura é mantida unida por código que nunca foi auditado de forma abrangente por ferramentas modernas. A era da IA para descoberta de vulnerabilidades está apenas começando, e devemos esperar mais revelações como esta – e não menos.
Referências
- Pesquisa deepfirst NGINX Rift: https://profundidadefirst.com/research/nginx-rift-achiev-nginx-rce-via-an-18-year-old-vulnerability
- página inicial do deepfirst: https://profundidadefirst.com/nginx-rift
- Comunicado de segurança F5 K000161019: https://my.f5.com/manage/s/article/K000161019
- Avisos de segurança NGINX: https://nginx.org/en/security_advisories.html
- Log de alterações do NGINX (1.31.0): https://nginx.org/en/CHANGES
Infográficos
Figura 1: NGINX Rift — como a incompatibilidade de comprimento do buffer de duas passagens produz um heap overflow