Protezione dei dati crittografati in caso di SQL injection

5

Diciamo che c'è un'applicazione web, con dati crittografati. per esempio. un sito web in cui i pazienti lasciano note ai loro medici.

Un paziente accede, lascia una nota, quella nota viene crittografata usando la crittografia simmetrica e inserita nel database, l'utente può ancora vedere la sua nota se mai torna indietro, la nota viene decifrata e può vederla. Il medico esegue il login, passa a una nota del paziente e viene decodificato e stampato.

Ma l'app è vulnerabile all'iniezione SQL. Un hacker lo trova, apre un account nell'applicazione web e crea una nota fittizia. Quindi usa l'iniezione SQL e copia qualcun altro della nota crittografata e incolla il contenuto nella sua nota (la sua riga nella tabella). Quando torna all'applicazione per visualizzarlo, viene decifrato.

Come puoi impedire all'hacker di visualizzare altre note crittografate?

    
posta Mehdi 01.02.2018 - 13:22
fonte

7 risposte

16

Se comprendo correttamente la tua domanda, il tuo sistema utilizza la stessa chiave per crittografare e decrittografare il messaggio sia per il paziente che per il medico.

In questo caso il tuo attacco è teoricamente possibile partendo dal presupposto che tu possa leggere il messaggio di un altro utente e inserirlo nel DB come tuo messaggio.

La mitigazione in termini di crittografia contro questa sarebbe una chiave univoca per utente o utilizzando coppie di chiavi pubbliche / private per crittografare i dati con ogni utente che ha ancora una chiave univoca per ulteriore sicurezza e limitazione del danno in caso di violazione.

Altri meccanismi includerebbero una difesa adeguata contro l'iniezione SQL sanificando l'input e anche un sistema di verifica degli utenti per garantire che ogni utente registrato sia un paziente legittimo, questo riduce il pool di aggressori ma non dovrebbe essere invocato da solo.

    
risposta data 01.02.2018 - 13:37
fonte
12

Il problema qui è che ogni nota è crittografata con la stessa chiave di crittografia. Ciò rende l'app più vulnerabile di quanto avrebbe dovuto essere.

Considera invece questa configurazione:

  • Ogni utente, medico e paziente ha la propria coppia di chiavi pubblica-privata.
  • Le chiavi pubbliche vengono archiviate crittografate con una chiave a livello di applicazione memorizzata all'esterno del database ..
  • Le chiavi private vengono archiviate crittografate con una chiave personale derivata dalla password dell'utente.
  • Ogni singola nota è crittografata con la sua unica chiave casuale. Quella chiave viene memorizzata in due versioni crittografate, una crittografata con la chiave pubblica dei pazienti e una con la chiave pubblica dei medici.

Non prendere questo come un progetto per il sistema perfetto. Ci sono molti modi per farlo, e forse meglio di questo. Ma è un esempio di un sistema in cui l'accesso in lettura e scrittura al solo database (ad esempio nel caso di SQLi) non consente all'hacker di accedere immediatamente a tutti i dati in testo non crittografato.

Modifica: se vuoi che tutti i medici siano in grado di leggere tutte le note, le cose diventano un po 'più scosse. Chiunque abbia accesso in scrittura all'intero database sarà in grado di trasformarsi da medico. Quindi è necessario limitare il più possibile l'accesso in scrittura alla tabella dei medici!

Non dare all'utente DB l'app Web sta utilizzando l'accesso in scrittura a quella tabella e usa un altro sistema più limitato (ad esempio disponibile solo su qualche intranet) per creare nuovi medici. O richiedere che ogni riga nella tabella del medico sia firmata crittograficamente o qualcosa del genere. O ancora meglio, leggi la grande risposta di Lie Ryans .

Conclusione: la lezione da portare via qui è che la crittografia richiede più di un semplice algoritmo, un messaggio e una chiave. È quando inizi a pensare a come gestire le chiavi che le cose si complicano e hai bisogno di soluzioni che siano strongmente dipendenti dal contesto.

    
risposta data 01.02.2018 - 13:53
fonte
7

Penso che tu sia troppo risucchiato in un attacco specifico. Voglio dire, sei preoccupato che un accesso SQL con accesso CRUD completo alla tabella delle note (e possibilmente di più?) Proverà a leggere gli appunti di altri medici?

  • Cosa succede se eliminano selettivamente una nota per un giorno specifico?
  • Cosa succede se sostituiscono una nota del medico con una che hanno creato?
  • Cosa succede se cambiano quale medico ha emesso una nota?
  • Cosa succede se scramble tutte le note e tenta di estrarre una minaccia ransomware?

Sì, sarebbe bello crittografare le note dei medici usando chiavi diverse (anche se è semplice come: [AppWideKey] + [DoctorID]) Ma il tuo focus dovrebbe probabilmente essere: "Se un SQL Injection Attack ha successo , l'hacker verrà registrato in SQL come AppUserX. Come posso minimizzare il danno che può fare AppUserX? " E la risposta è di solito: chiedi loro di usare Stored Procedures per ottenere i loro dati, solo lascia che i proc memorizzati facciano la minima quantità per soddisfare le esigenze dell'app, e non dare all'utente l'accesso diretto alle tabelle.

    
risposta data 01.02.2018 - 16:44
fonte
6

Devi criptare ogni nota con la sua chiave segreta. Dovresti usare una nuova chiave simmetrica per ogni nota. Questa chiave simmetrica è chiamata chiave di sessione.

Ora il problema diventa come distribuire la chiave di sessione ai destinatari e solo ai destinatari. Per questo, hai bisogno della crittografia a chiave pubblica.

È necessario rilasciare a ciascun partecipante del sistema (pazienti e medici) la propria coppia di chiavi personale. La chiave pubblica può essere memorizzata sul server non crittografato, ma la chiave privata non deve essere memorizzata sul server in chiaro. È necessario crittografare la chiave privata sul server utilizzando la password dell'utente oppure gli utenti dovrebbero essere tenuti a memorizzare la propria chiave privata in modo sicuro per se stessi.

Un paziente può inviare un messaggio privato a un determinato medico generando una nuova chiave di sessione e crittografando un messaggio con esso, quindi crittografando la chiave di sessione con la chiave pubblica del medico. Puoi anche inviare un messaggio a più destinatari crittografando la chiave di sessione su più chiavi pubbliche.

Facoltativamente, potresti avere un'autorità di certificazione che controlla l'identità di un partecipante (ad esempio richiedendo un ID di foto) e firma la chiave pubblica del partecipante per affermare che il controllo di identità è stato eseguito e allegare attributi firmati che asseriscono ruolo (s).

A questo punto, hai un meccanismo per la crittografia point-to-point, questi sono essenzialmente il modo in cui funziona lo schema S / MIME e PGP.

È possibile creare una messaggistica di gruppo, in modo che pazienti e / o medici possano inviare un messaggio a un gruppo numeroso (ad esempio un paziente può inviare un messaggio crittografato al gruppo di podologi, senza consentire al gruppo odontoiatrico di leggere il messaggio), senza che nessuno debba conoscere l'identità del singolo membro. Questa è chiamata crittografia multi-cast.

Il modo in cui crei la messaggistica di gruppo è che devi creare una coppia di chiavi di gruppo. Una coppia di chiavi di gruppo consiste in una chiave privata che viene distribuita a tutti i membri del gruppo e una chiave pubblica che viene distribuita a chiunque abbia bisogno di inviare messaggi al gruppo. Ciò consente a membri e non membri di inviare un messaggio a tutti solo in quel gruppo. Per inviare un messaggio di gruppo, crittografare la chiave di sessione per quel messaggio con la chiave pubblica del gruppo.

Tieni presente che nella maggior parte dei casi, dovrai creare una nuova chiave di gruppo ogni volta che l'appartenenza a un gruppo cambia (ad esempio, qualcuno lascia il gruppo o una nuova persona è entrata nel gruppo.)

    
risposta data 01.02.2018 - 16:56
fonte
1

La crittografia descritta non ti protegge da molti scenari. Ti proteggerà nel caso in cui il database MySQL venga rubato, ma le chiavi di crittografia non lo sono. Ma dal momento che il database è dietro l'applicazione, è l'applicazione che di solito si rompe prima, e poi il database, quindi in uno scenario reale, entrambe le chiavi con l'applicazione e il database verrebbero rubate.

Per proteggere l'applicazione da questo, è necessario risolvere SQL Injection, che è facile da fare e semplice. È facile assicurarsi che tutte le applicazioni siano resilienti alle Iniezioni SQL, tutto ciò che serve è modificare ogni query nel database, ad es. in che modo sta usando le istruzioni preparate.

Indipendentemente dall'entità e complessità dell'applicazione o dal numero di linguaggi e framework utilizzati, questo è un lavoro semplice e molto efficace. Avere ordinato SQL Injections è la cosa fondamentale da fare.

Ci sono molti altri modi per proteggere l'hacker dal fare ciò che descrivi. Ad esempio, le variabili di controllo passate all'applicazione, di solito vengono eseguite da qualcosa chiamato WAF, è inoltre possibile incorporare il rilevamento degli attacchi SQL Injection nel codice in cima alla catena di elaborazione.

    
risposta data 01.02.2018 - 13:36
fonte
1

Se disponi di controlli di accesso efficaci, solo i pazienti stessi dovrebbero essere in grado di creare nuove note sul loro profilo. Un medico dovrebbe essere in grado di leggere la nota e aggiungere commenti alla nota, ma non eliminare o aggiornare la nota. Ciò dovrebbe rendere immutabile la nota originale: concedere l'inserimento dell'applicazione ma non aggiornare i privilegi nella tabella delle note. Questo dovrebbe anche mitigare l'attacco di iniezione.

Potresti anche associare note a sessioni di utenti in modo che un medico possa vedere solo le note di un utente associato a sessioni valide e qualsiasi inserimento eseguito tramite SQLi non venga mostrato - un lavoro di normalizzazione del database potrebbe rimuoverli.

Per gli utenti che potrebbero disporre di ulteriori privilegi tramite l'interfaccia web - ad es. un superutente, è possibile limitare l'accesso alla risorsa superutente a specifici indirizzi IP (ad esempio, il sistema della sede centrale) utilizzando httpd.conf o simile.

    
risposta data 01.02.2018 - 14:28
fonte
1

Stai usando query parametrizzate? Questo dovrebbe prevenire l'iniezione SQL non sofisticata.

Dovresti avere 1 chiave univoca per utente. Gli utenti si registrano con un indirizzo e-mail & parola d'ordine? Potresti usare la password.

Generare una chiave per ogni utente quando si registrano e memorizzarlo nel database sembra stupido. Aggiungeva solo 1 ulteriore passaggio richiesto per eseguire l'attacco originale. In realtà, non si dovrebbe nemmeno memorizzare la password dell'utente nel database. Tu sei? E stai usando HTTPS?

    
risposta data 01.02.2018 - 17:51
fonte

Leggi altre domande sui tag