
Laboratorio basato su Docker che dimostra la vulnerabilità di parsing URI di Nginx CVE-2013-4547 con sfruttamento passo-passo per bypass dei privilegi ed esecuzione di codice.
Versioni interessate: Nginx 0.8.41 ~ 1.4.3 / 1.5.0 ~ 1.5.7
Link di riferimento:
Questa vulnerabilità non ha molto a che fare con l'esecuzione di codice; la causa principale è l'errata interpretazione dell'URI della richiesta, che porta a ottenere erroneamente il nome del file richiesto dall'utente, causando conseguenze come il bypass delle autorizzazioni e l'esecuzione di codice.
Ad esempio, quando Nginx identifica una richiesta che termina con .php, la invia a fastcgi per l'analisi. Una configurazione tipica è la seguente:
location ~ \.php$ {
include fastcgi_params;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME /var/www/html$fastcgi_script_name;
fastcgi_param DOCUMENT_ROOT /var/www/html;
}
In condizioni normali (con pathinfo disabilitato), solo i file con estensione .php vengono inviati a fastcgi per l'analisi.
Tuttavia, in presenza di CVE-2013-4547, se richiediamo 1.gif[0x20][0x00].php, questo URI corrisponde all'espressione regolare \.php$ e può entrare in questo blocco location; ma una volta entrato, Nginx interpreta erroneamente che il file richiesto sia 1.gif[0x20] e imposta questo valore come SCRIPT_FILENAME inviandolo a fastcgi.
fastcgi analizza il file in base al valore di SCRIPT_FILENAME, provocando così una vulnerabilità di analisi.
Pertanto, è sufficiente caricare un file con uno spazio finale per far sì che PHP lo analizzi.
Un altro esempio: molti siti limitano gli IP che possono accedere all'area di amministrazione:
location /admin/ {
allow 127.0.0.1;
deny all;
}
Possiamo richiedere il seguente URI: /test[0x20]/../admin/index.php. Questo URI non corrisponde a /admin/ nel blocco location, bypassando così la verifica IP; ma alla fine viene richiesto il file /test[0x20]/../admin/index.php, che è /admin/index.php, riuscendo ad accedere all'area di amministrazione. (Questo presuppone che esista una directory chiamata test : è una caratteristica del sistema Linux; se la directory non esiste, anche saltando al livello superiore, verrà generato un errore di file inesistente; in Windows non c'è questa limitazione)
Avvia l'ambiente vulnerabile:
docker-compose build
docker-compose up -d
Dopo l'avvio, visita http://your-ip:8080/ per vedere una pagina di caricamento.
Questo ambiente utilizza una lista nera per la validazione; non possiamo caricare file con estensione .php, quindi dobbiamo sfruttare CVE-2013-4547. Carichiamo un file chiamato 1.gif (nota lo spazio finale):

Visita http://your-ip:8080/uploadfiles/1.gif[0x20][0x00].php e noterai che PHP è stato interpretato:

Nota: [0x20] è uno spazio, [0x00] è \0. Questi due caratteri non necessitano di codifica.