2009-05-06 31 views
18

Un article che mi sono imbattuto qui a SO forniti i collegamenti per other articles che a sua volta fornito i link a evenmorearticles eccCome memorizzare le password * correttamente *?

E alla fine mi è stato lasciato completamente perplesso - quindi qual è il modo migliore per conservare password nel DB? Da quello che posso mettere insieme dovresti:

  • Utilizzare un lungo (almeno 128 bit completamente random), che viene memorizzato in testo normale accanto alla password;
  • Utilizzare diverse iterazioni di SHA-256 (o anche maggiore livello SHA) sulla password salata.

Ma ... più leggo sulla crittografia e più mi rendo conto che non capisco davvero nulla, e che le cose che avevo pensato per essere vero per gli anni sono in realtà sono flat out sbagliato. Ci sono esperti in materia qui?

Aggiunto: Sembra che ad alcune persone manchi il punto. Ripeto l'ultimo link sopra riportato. Questo dovrebbe chiarire le mie preoccupazioni.

https://www.nccgroup.trust/us/about-us/newsroom-and-events/blog/2007/july/enough-with-the-rainbow-tables-what-you-need-to-know-about-secure-password-schemes/

+0

Hai esattamente ragione. Non memorizzare le password - memorizza gli hash delle password. Qual è la tua vera domanda? Quale parte della salatura e dell'hashing è confusa? O sei semplicemente infelice perché questo è nuovo per te? Che consiglio contraddittorio hai trovato? –

+0

è per la convalida dell'utente nel tuo programma o stai cercando di creare un gestore di password in cui devi restituire la password? – Audioillity

+2

Non c'è una risposta 'corretta'. Il livello di sicurezza dipende molto dal contesto dell'applicazione. Una macchina isolata (non fisicamente connessa a una rete) può avere meno hashing delle password rispetto a un database con connessione Web. Inoltre, il tuo database non dovrebbe mai essere direttamente accessibile alla rete, dovrebbe esserci sempre un livello di accesso tra l'utente e il database. E l'hashing/salting delle password è inutile se la password viene inviata al database/livello di accesso in formato di testo normale. – Skizz

risposta

12

Hai capito bene. Solo due suggerimenti:

  1. Se un giorno SHA1 diventa troppo debole e si desidera utilizzare qualcosa di diverso, è impossibile unhash le vecchie password e rimaneggiamento con il nuovo regime. Per questo motivo, suggerisco di allegare ad ogni password un numero di "versione" che ti indichi quale schema hai usato (lunghezza del sale, quale hash, quante volte). Se un giorno hai bisogno di passare da SHA a qualcosa di più forte, puoi creare password di nuovo stile mentre hai ancora password vecchie nel database e distinguerle ancora. Migrare gli utenti al nuovo schema sarà più facile.

  2. Le password passano ancora da utente a sistema senza crittografia. Guarda su SRP se questo è un problema. SRP è così nuovo che dovresti essere un po 'paranoico nell'implementarlo, ma finora sembra promettente.

Edit: Risulta bcrypt mi ​​ha battuto ad esso sul numero 1. L'idea informazioni memorizzate è (costo, sale, hash), dove il costo è quante volte la hashing è stato fatto. Sembra che bcrypt abbia fatto qualcosa di giusto. Aumentare il numero di volte che l'hash può essere fatto senza l'intervento dell'utente.

+1

+1 per l'idea di registrare una versione per le password. Riesco a vedere che è utile in futuro .... – Matt

+1

Questa è in realtà una cattiva idea poiché inutilmente complica la soluzione rendendo conto di un problema che non esiste ancora. Violazione classica del principio YAGNI. –

+1

+1 per affrontare un problema reale. La radicale negazione di Kiff è facilmente smentita con esempi del problema che viene posto qui su SO. Come qualcuno che ha dovuto chiedere a decine di migliaia di utenti di scegliere nuove password in un breve periodo di tempo, mi sarebbe piaciuto avere un percorso di migrazione più fluido. – erickson

0

penso che non c'è iterazione extra sulla password necessaria, juste assicurarsi che non v'è un sale, e un Complexe uno;) Io personnaly uso SHA-1 combinato con 2 frasi chiave di sale.

+0

Erm ... http://www.schneier.com/blog/archives/2005/02/sha1_broken.html – chaos

+1

L'hashing a 1 pass ha una vulnerabilità.È possibile enumerare una serie di candidati molto probabile che portano all'hash. Passate multiple fanno sì che le tabelle arcobaleno crescano rapidamente, quindi l'hashing 256x. http://en.wikipedia.org/wiki/Rainbow_table –

+0

Io uso SHA-512, dato che lo spazio (e il tempo dell'algoritmo) non è un problema, e c'è un documento che mostra collisioni in SHA-1 ... comunque io sono solo paranoico. – MichaelICE

2

In verità dipende da cosa sono le password. Si dovrebbe prendere cura di memorizzare qualsiasi password con cura, ma a volte è necessaria molta più cura di altri. Come regola generale, tutte le password dovrebbero essere sottoposte a hash e ogni password dovrebbe avere un valore univoco.

In realtà, i sali non devono essere così complessi, anche quelli piccoli possono causare un vero incubo per i cracker che cercano di entrare nel sistema. Vengono aggiunti a una password per impedire l'utilizzo delle tabelle Rainbow per hackerare le password di più account. Non aggiungerei una singola lettera dell'alfabeto a una password e chiamarla salata, ma non è necessario renderla una guida univoca che viene crittografata da qualche altra parte nel database.

Un'altra cosa riguardante i sali. La chiave per creare una password + sale funziona quando l'hashing è la complessità della combinazione dei due. Se si dispone di una password di 12 caratteri e si aggiunge un 1 carattere saltato, il sale non fa molto, ma crackare la password è ancora un'impresa monumentale. È vero anche il contrario.

0

La lunghezza del sale non ha importanza, purché sia ​​univoca per un utente. Il motivo per un salt è che un determinato tentativo generato con una corrispondenza hash è utile solo per una singola riga della tabella utenti nel DB.

+3

Non importa. Ciò che il tuo sale sta effettivamente facendo è aumentare le dimensioni del tavolo arcobaleno che deve essere usato per rompere i tuoi hash. Un breve sale non fa molto in questo modo. (Uno dei problemi principali che i sali stanno superando è che gli utenti scelgono password brevi.) – chaos

+0

Non importa, ma solo fino a un certo punto. Per ogni bit di sale che aggiungi, raddoppi i requisiti di spazio necessari per un attacco di dizionario (o l'attaccante deve tagliare il suo dizionario a metà). Se esiste una buona politica di selezione della password (lunghezza minima, requisito per casi misti, cifre, segni di punteggiatura), probabilmente sarete al sicuro con i vecchi sali a 12 bit. Tuttavia, potrebbe anche usare 64 bit ed essere al sicuro ovunque. Nessuno ha davvero spazio per i dizionari 10^19, anche se sono veramente piccoli. – erickson

0

Detto semplicemente, utilizzare un algoritmo di hash crittograficamente sicuro e un po 'di sale per le password, che dovrebbe essere sufficiente per il 99,99% di tutti i casi di utilizzo. Il collegamento debole sarà il codice che controlla la password e l'immissione della password.

+0

Fintanto che fornire una sicurezza migliore è complicato quanto altre 5 linee di codice banali, mi piacerebbe optare per l'opzione migliore in tutti i casi d'uso. –

+0

Non penso che lo otterrete in "5 altre banali code di codice" ... ma leggerò anche le altre risposte e commenti qui, forse mi metteranno alla prova. – Lucero

+0

Altre cinque righe di codice e una colonna del database. – chaos

1

Uso:

  1. archiviazione password con hash
  2. Un sale al livello di utente 128+ bit, casuale, rigenerata (cioèsi fanno nuovi sali quando si creano nuovi hash delle password, non si mantiene costantemente lo stesso sale per un dato utente)
  3. Un metodo di hashing forte e computazionalmente costoso
  4. Metodologia leggermente diversa (algoritmo hash, quanti hashing iterazioni che si utilizzano, quale ordine i sali sono concatenati in, qualcosa) da entrambe le eventuali 'guide di implementazione standard' come questi e da qualsiasi altra applicazione di memorizzazione delle password che hai scritto
+1

128 bit è eccessivo. Anche i 64 bit sono eccessivi, quindi è quello che uso. Non c'è nemmeno bisogno di un "livello di sistema salt" a meno che il "livello utente sal" sia in qualche modo prevedibile per un utente (come l'utilizzo del proprio nome). È più semplice e sicuro usare solo un RNG crittografico per il sale. – erickson

+0

Overkill? Mi piace eccessivo. Il livello di sistema sale è la difesa approfondita per l'evento che il contenuto del tuo database è compromesso senza che il tuo codice sorgente venga compromesso. Concordato che i sali dovrebbero essere il rumore, non le informazioni dell'utente. – chaos

+0

Non capisco. Fatto correttamente, il digest, il sale e il codice sorgente potrebbero essere resi noti che sarebbe comunque impossibile per un utente malintenzionato scoprire la password. Quando dici che il database potrebbe essere compromesso, cosa intendi? Cosa intendi per compromesso? – erickson

Problemi correlati