venerdì 23 novembre 2012

La sicurezza delle bookmarklet

Scrivo questo post dopo una esperienza con le bookmarklet davvero intensa. Le bookmarklet, similmente ad alcuni tipi di estensioni, sono degli script che - detto molto semplicemente - possono agire sulla pagina web su cui vengono aperte. Le bookmarklet sono azionate dall'utente e generalmente svolgono funzioni di clipping, condivisione, editing etc.
Quanto dico di seguito sulle bookmarklet vale per le estensioni che hanno un comportamento simile di manipolazione del DOM.


Antefatto
Con Searcheeze, e successivamente NextMags, abbiamo sviluppato del codice che veniva iniettato su una pagina qualsiasi ed interagiva con essa (manipolazione DOM, finestre modali etc). Se questa è una cosa banale sul proprio sito, quando si è "ospiti inattesi" di un sito qualsiasi la questione cambia: bisogna evitare di usare nomi di variabili usate nella pagina (compreso il $ di jquery o prototype), avere dei css robusti che reggano a qualsiasi impostazione assurda applicata alla pagina, riuscire a sovrapporsi ad oggetti flash etc. (update: non era facile tempo fa!)
Nulla di impossibile, tutto se po' fà.

Il diavolo fa le pentole, non i coperchi
C'è però una questione che mi sono posto osservando anche le bookmarklet degli altri: cosa succede se la pagina vuole deliberatamente compromettere o modificare il comportamento della bookmarklet?
Solitamente le bookmarklet includono un iframe (soluzione buona e comoda per molti aspetti) e all'interno dell'iframe si svolge il processo a partire dall'autenticazione dell'utente. Ma se la pagina vedesse questo iframe e lo sostituisse con uno "fasullo" cosa accadrebbe? L'utente vedrebbe semplicemente aprirsi la bookmarklet sulla pagina di login del servizio che ha aperto, e naturalmente inserirebbe le sue credenziali. Se il trucco è portato fino in fondo l'utente può anche trovarsi davvero loggato (ma con la password rubata)... Ma andiamo con ordine.

Facciamo i cattivi
Il comportamento della pagina malevola potrebbe essere questo:
- la pagina si mette in ascolto di variazioni sul DOM, oppure ogni tanto controlla gli iframe presenti o quelli di una certa url.
- l'utente apre la bookmarklet che inietta nel DOM il suo iframe.
- la pagina se ne accorge e sostituisce subito questo iframe con uno suo, che può ottenere anche modificando "on the fly" la vera pagina di login del servizio. In questo modo è possibile modificare la action del form per portare dove vogliamo noi, registrarla e rimandare l'utente alla vera pagina finale, facendolo trovare loggato.

A parole so' bboni tutti
Pensate sia difficile? Io ci ho messo 12 minuti in tutto, e non avevo letto questo post ;) L'ho fatto su una bookmarklet famosa, e l'ho fatto provare al buon Carlo Mallone, al corrente dell'esperimento (in realtà è lui che mi ha sfidato a riuscirci).

One in a million?
Ok, ma quante volte capita un sito malevolo su cui vuoi usare una certa bookmarklet? Sicuramente poche volte, ma già basterebbe a dover prestare la giusta attenzione. Ma se pensiamo anche ai siti "hackerati", alle vulnerabilità in sistemi di commenti (sopratutto casarecci) che permettono di inserire degli script nella pagina, vulnerailità di circuiti di banner (vedi questo post su OpenX) etc il numero inizia a diventare importante. Considerando che dove c'è una grande opportunità di rubare dati, si scatenano orde di persone malintenzionate per creare virus creati allo scopo... insomma, non si può dormire tranquilli.

Come proteggersi
Veniamo al dunque: ora che so questo, come faccio a fare un meccanismo di autenticazione sicuro? In realtà a pensarci bene non serve neanche che ci sia l'autenticazione sulla vostra bookmarklet: se l'utente dopo aver cliccato sulla bookmarklet X si trovasse davanti una finestra mai vista, ma con il logo del servizio X ed un invito, che so, a collegarsi tramite il suo account gmail (chiedendo user e pass), si dovrebbe insospettire? Purtroppo questa tecnica se applicata funzionerebbe molto bene. Allora come difendersi?
Non vale la pena scervellarsi lato server, validare la richiesta, il referrer o altro: se la pagina ha preso il controllo di un iframe e riesce a spacciarsi per il servizio richiesto, è troppo tardi per intercettare l'attacco.
La prima cosa che mi viene in mente è un servizio di sorveglianza dell'iframe: la bookmarklet, prima ancora di creare l'iframe, crea ed esegue una funzione javascript che controlla la presenza del suo iframe. Se non lo trova, un refresh della pagina con un alert.
No, non finisce qui. A seconda del tipo di controllo fatto dalla bookmarklet (presenza di un iframe? presenza di iframe di un certo url), la pagina attaccante potrebbe ancora nascondersi facilmente.
La pagina malevola potrebbe anche semplicemente sovrapporsi interamente o sovrapporre in parte la finta schermata della  bookmarklet, l'effetto per l'utente sarebbe lo stesso ed il controllo dell'iframe non funzionerebbe.

Per ogni soluzione che mi viene in mente, trovo sempre un attacco valido...

Resto a rimuginare su altre possibili soluzioni... suggerimenti?






Nessun commento:

Posta un commento