Stefano Carli da oggi senza olio di palma

Decodifica del malware PHP Filesman

Recentemente mi è capitato di leggere questa domanda fatta su stackoverflow.com nella quale un utente, trovando in un file php del proprio sito Wordpress del codice particolare, ne chiede il significato.

Today I checked my wordpress website and I observed that one php file had the following code in it: According to THIS it is a encode(eval64)) hack. What’s the meaning of the code below? Is this the same as the base encode eval64 hack?

In questo articolo proverò ad analizzare il codice dato, che per completezza riporto anche su pastebin.

1. Scopo e metodologia utilizzata

Proviamo a tradurre il codice in modo da renderlo leggibile o utilizzabile in modo da capirne lo scopo. Per fare questo porterò avanti un’azione di decodifica suddivisa in passi successivi che chiamerò stage. Per ogni passo costruirò un diagramma che permetterà di tenere traccia delle azioni effettuate. Di seguito un diagramma della la situazione iniziale:

Stage0

Legenda

2. Analisi preliminare del codice

<?
$auth_pass = "2fba9596aec8aeb14a88461bbd708f97";
$color = "#df5";
$default_action = 'FilesMan';
$default_use_ajax = true;
$default_charset = 'Windows-1251';

$xYEzDu6r3EZT="Lunga variabile";
eval(base64_decode("Codice offuscato"));
return;
?>

Il codice contiene sei variabili ed un comando eval. Possiamo fare subito alcune considerazioni:

3. Decodifica del codice

3.1 Stage 1: eval e base64_decode

In modo da avere in output la decodifica del codice offuscato, sostituiamo ad eval il comando echo, come nel seguente esempio:

echo base64_decode("Codice offuscato");

Il codice decodificato restituisce due nuovi comandi eval(base64_decode(“Stringa”)), segnalati in viola nell’immagine di seguito (cliccare sull’immagine per ingrandirla). Si tratta quindi di codice codificato in base64 più e più volte in modo da risultare quanto meno riconoscibile possibile. FilesMan-Decode-Step01 Aggiungiamo al diagramma di partenza il primo passo di decodifica eseguito. Si vede chiaramente come, da una prima espressione da valutare, ne nascano altre due. È da subito evidente come siano state applicate metodologie di offuscamento sul codice originale più e più volte, nel tentativo di renderlo difficilmente leggibile. Armiamoci di pazienza perché probabilmente la decodifica richiederà molti di questi passi. Stage1

3.2 Stage 2

Valutiamo le due espressioni appena trovate: Valutando la prima troviamo due nuove espressioni eval(base64_decode(“Stringa”)) FilesMan-Decode-Step02 Valutando la seconda espressione otteniamo finalmente qualcosa di più comprensibile. FilesMan-Decode-Step03 Il risultato è un ciclo for, oltre all’espressione di innesco eval. Possiamo riscrivere questa porzione di codice indentandolo correttamente. FilesMan-Decode-Step04 La variabile $xltUlCb5Gxs è il contatore del ciclo. Per rendere il codice più leggibile possiamo indicarla con $i. Le variabili $x7st79VVrvR e $xWxG9z44O0p hanno ancora un valore sconosciuto, in quanto nel nostro lavoro di decodifica non le abbiamo ancora incontrate. La variabile $xYEzDu6r3EZT è quella variabile a noi nota fin dall’inizio, che abbiamo indicato come “lunga variabile”. Stage2

3.3 Stage 3

Il primo eval diventa FilesMan-Decode-Step05 Il secondo eval diventa FilesMan-Decode-Step05-1 Il ciclo for diventa FilesMan-Decode-Step05-2 La situazione attuale Stage3 

3.4 Stage 4: il ciclo for

A questo punto la situazione va delineandosi. La chiave di volta del codice è in questo momento il ciclo for. Per capire cosa il ciclo produce proviamo a valutarlo. Lo facciamo riprendendo la variabile $xYEzDu6r3EZT, decodificandola in base64, trovandone la lunghezza e sostituendo i valori trovati all’interno del ciclo for dove opportuno. Al solito la eval diventa echo per valutare l’output prodotto dal ciclo; tale output è parzialmente visibile nella parte bassa della figura. FilesMan-Decode-Step06 Per maggiore chiarezza indico l’output di seguito: FilesMan-Decode-Step07 l’ultima parte del diagramma [caption id=”attachment_497” align=”alignnone” width=”669”]Stage4 Diagramma: Fase 4[/caption]  

3.5 Stage 5: gli ultimi passi

Dovremmo finalmente essere vicini alla soluzione. Proviamo a valutare la funzione solidstate, in modo da farci ritornare la variabile $lol. FilesMan-Decode-Step08 La funzione ritorna di nuovo un codice da decodificare. È interessante notare come questa volta non si utilizzi eval come innesco, ma la funzione preg_replace con il modificatore di criterio e. Ne ho già parlato in un mio precedente articolo.

3.6 Stage 6: eval, gzinflate e base64_decode

Valutiamo quindi il contenuto di $source e ne otteniamo una nuova espressione eval. FilesMan-Decode-Step09  

3.7 Stage 7: il codice finale

Come ormai di consueto valutiamo l’espressione. Finalmente siamo arrivati alla fine. Davanti a noi il codice in chiaro! FilesMan-Decode-Step10 Di seguito il diagramma completo [caption id=”attachment_503” align=”alignnone” width=”1024”]FilesMan Diagramma completo[/caption] [hr]

4. Che cosa fa?

È stato indubbiamente un lungo viaggio. A questo punto vogliamo ovviamente sapere cosa fa questo codice. Essendo semplice codice PHP creiamo una pagina ad hoc, e visualizziamolo nel nostro browser.

FilesMen-usage

Notiamo che la backdoor è molto completa. Ha un file manager, una console, un SQL browser, un interprete PHP e molto altro. FilesMen-usage1 Molto interessante è la possibilità di convertire le stringe in una vasta quantità di formati, cercare file sul computer o hash su internet. Degni di nota sono anche lo strumento di bruteforce, quello di rete e l’auto-rimozione del codice malevolo.