it-swarm-eu.dev

Ist ein HMAC-Passwort sicherer als ein verschlüsseltes oder verschlüsseltes Passwort?

Welche Option sollte ich wählen, eine HMAC zum sicheren Speichern eines Passworts oder eine bcrypt- oder scrypt-Bibliothek?

25
user917279

Um Ihnen einen guten Überblick über die Probleme und Feinheiten bei der Berechnung von Passwort-Hashes zu geben und um zu erklären, warum HMAC für dieses Problem nicht geeignet ist, werde ich eine viel umfassendere Antwort geben, als für die direkte Beantwortung der Frage wirklich erforderlich ist.

Ein HMAC-Hash-Algorithmus ist im Wesentlichen nur eine verschlüsselte Version eines normalen Hash-Algorithmus. Es wird normalerweise verwendet, um die Integrität und Authentizität zu überprüfen. Die übliche Notation hierfür ist H(m,k) = h, wobei H der HMAC-Hash-Algorithmus ist, m die Nachricht ist, k der Schlüssel ist und h ist der resultierende Hash. Die Idee ist, dass zwei Parteien, die ein geheimes k teilen, überprüfen können, ob die andere Person der Autor von m ist. Darüber hinaus kann ein Angreifer keinen Nachrichten-Hash fälschen, ohne k zu kennen.

Dies geschieht wie folgt:

  1. Alice und Bob kennen beide einen gemeinsamen geheimen Schlüssel k.
  2. Alice schreibt eine Nachricht m und berechnet den HMAC-Hash davon unter Verwendung von k, d. H. H(m,k) = h.
  3. Alice sendet die Nachricht m und den Hash h an Bob.
  4. Bob berechnet H(m,k) und vergleicht es mit dem Hash h, den Alice gesendet hat. Wenn die Hashes übereinstimmen, weiß er, dass Alice die Nachricht gesendet hat und dass sie nicht geändert wurde, nachdem sie sie gehasht hat.

Nachdem Sie nun verstanden haben, was HMAC ist, gehen wir zu dem über, was Sie wirklich möchten - Speichern von Passwörtern in einer Datenbank.

Vor vielen Jahren war es üblich, Passwörter im Klartext in Datenbanken zu speichern. Dies war eine schlechte Idee, da der Angreifer bei einer Kompromittierung der Datenbank alle Kennwörter erhielt. Um dem entgegenzuwirken, haben wir begonnen, Passwörter in der Datenbank mithilfe von kryptografischen Einweg-Hash-Algorithmen zu haschen. MD5 wurde populär, aber darin entdeckte Schwächen (Kollisionen, Teilvorbilder usw.) bedeuten, dass es nicht mehr empfohlen wird. Viele Leute sind auf SHA1 umgezogen, was sicherer ist.

Das Problem bei diesem Ansatz ist, dass es möglich ist, eine riesige Tabelle mit Hashes und den entsprechenden Klartexten zu erstellen. Diese heißen Regenbogentabellen . Sie arbeiten an dem Konzept, dass es effizienter ist, eine große Liste von Hashes für alle möglichen Passwörter (innerhalb eines bestimmten Satzes) zu berechnen und diese dann zu speichern, damit sie später schnell abgefragt werden können. Anstatt einzelne Hashes brutal zu erzwingen, wurde es möglich, die Datenbank einfach nach einem Hash abzufragen und den Klartext sofort zurückzugeben.

Um dies zu beheben, erfanden Sicherheits-Nerds Salze. Salze sind große eindeutige Zufallswerte, die an Kennwörter angehängt werden, bevor sie gehasht werden. Dieses Salz wird mit dem Hash gespeichert, damit es später erneut berechnet werden kann. Also berechnen wir H(m+s) = h und speichern dann h und s in der Datenbank. Dies bietet einen signifikanten Schutz gegen Regenbogentabellen , da im Wesentlichen für jedes Salz eine separate Regenbogentabelle generiert werden muss.

Also wechselten die Bösen zurück zu Wörterbuchangriffen und Brute-Force-Cracking. Mit dem Aufkommen des GPU-Computing wurde es möglich, Milliarden von Hashes pro Sekunde auf einer mäßig leistungsstarken Grafikkarte zu berechnen. Tatsächlich haben die Leute Computer gebaut, die fast 50 Milliarden MD5-Hashes pro Sekunde - ziemlich beeindruckend/beängstigend berechnen können. Der Grund, warum GPUs dazu in der Lage sind, besteht darin, dass sie für eine große Anzahl paralleler Skalaroperationen ausgelegt sind. Skalare Operationen sind mathematische und logische Operationen, die keine Verzweigungen beinhalten - d. H. Sie müssen nicht viel/nichts tun "wenn x dann y tun". Kryptografische Hash-Algorithmen passen in der Regel in dieses Modell.

Um dies zu erschweren, müssen wir die Hash-Operation langsam genug machen, um das brutale Forcen unmöglich zu machen. Normale Hash-Algorithmen (z. B. SHA1) sind so konzipiert, dass sie schnell sind, was sie für diesen Zweck ungeeignet macht. HMAC fügt sehr wenig Overhead und keinen zusätzlichen Sicherheitsspielraum hinzu, daher ist es auch hier nicht sehr nützlich.

Das Erstellen eines langsamen kryptografischen Hash-Algorithmus ist leichter gesagt als getan - es ist sehr schwierig, einen zu finden, der langsam, irreduzibel (d. H. Nicht über seinen aktuellen Status hinaus optimierbar) und sicher ist. Es gibt drei beliebte Hash-Funktionen, die dies tun können: PBKDF2 , bcrypt und scrypt . Diese werden als adaptive Schlüsselableitungsfunktionen bezeichnet, da sie zusammen mit Klartext und Salt einen Arbeitsfaktorwert akzeptieren. Der Arbeitsfaktor ändert die Zeit, die zum Berechnen des Hashs benötigt wird, und soll vor zukünftigen Hardwareverbesserungen schützen.

Für einen adaptiven Schlüsselableitungsalgorithmus H berechnen wir H(m,s,w) = h, wobei m die Nachricht (Passwort) ist, s das Salz ist und w ist der Arbeitsfaktor. Das resultierende h enthält normalerweise s und w, so dass eine Überprüfungsfunktion später denselben Hash mit denselben Parametern berechnen kann. Der Arbeitsfaktor steuert im Allgemeinen die Anzahl der durchgeführten Iterationen eines internen kryptografischen Grundelements. Das Ziel ist es, dass die Berechnung lange genug dauert, um das Knacken unmöglich zu machen, aber die vorhandenen Ressourcen nicht zu überschreiten.

Um mehr Sicherheit gegen dediziertes hardwarebasiertes Cracken zu bieten, stellt scrypt sicher, dass die Hash-Berechnung sowohl CPU-hart als auch speicherhart ist, d. H. Es werden erhebliche CPU- und Speicherressourcen benötigt, um den Hash-Wert zu erzeugen. Dies ist wichtig, da FPGAs normalerweise nur sehr wenig unmittelbaren Speicher haben.

Nun stellt sich die offensichtliche Frage: Wenn ich meine Site für die Verwendung von bcrypt einrichte, bedeutet das nicht, dass mein Server ständig CPU-intensive Hashes berechnen muss? Wenn Sie sie auf Ihrem Server ausführen, sollten Sie dies berücksichtigen. Eine bessere Lösung besteht darin, den Client den Hash berechnen zu lassen und ihn dann über SSL an den Server zu senden. Der Server kann es dann mit dem Wert in der Datenbank vergleichen. Dies stellt sicher, dass der Kennwort-Hash nicht leicht geknackt werden kann, wenn er gestohlen wird (z. B. durch einen Datenbankkompromiss), und dass Ihr Server nicht durch den Aufwand für die Berechnung des Kennwort-Hash überfordert wird. Für Websites können Sie jsBcrypt verwenden.  Update: Diese Methode wurde von einem Kommentator unten als fehlerhaft bezeichnet. Benutze es nicht.

Hoffentlich gibt Ihnen dies einen guten Überblick über die Situation und warum HMAC für diese Art der Verwendung nicht geeignet ist.

37
Polynomial

HMAC ist ein Nachrichtenauthentifizierungscode ; es benutzt einen Schlüssel. Bcrypt nicht. Somit ist die Wahl nicht neutral; man kann sich nicht vorstellen, dass alle Dinge sonst gleich sind, weil sie es nicht sind.

Obwohl nominell für Integritätsprüfungen, kommt es vor, dass sich HMAC (bei Verwendung mit einer einigermaßen sicheren Hash-Funktion, z. B. SHA-256 oder sogar SHA-1) irgendwie wie "eine Hash-Funktion mit einem Schlüssel" verhält. Dies ist keine generische Eigenschaft von MAC-Algorithmen, funktioniert jedoch mit HMAC (daher kann es als Grundlage für einen Zufallsgenerator namens Hmac_DRBG verwendet werden). Dies macht HMAC zu einer potenziellen Wahl für das Passwort-Hashing.

Wenn Sie Ihr Passwort mit HMAC "hashen" und der Angreifer Ihre Datei/Datenbank mit dem Hash-Passwort , aber nicht den HMAC-Schlüssel abrufen könnte, wird der Angreifer dies tun nicht in der Lage sein, die Passwörter zu knacken. In diesem Szenario ist HMAC "besser" als bcrypt/scrypt. Dies ist jedoch ein Edge-Fall. Wir haben Hash-Passwörter, weil wir uns über Rand-Szenarien Sorgen machen, in denen der Angreifer könnte die Sicherheit genug verletzt, um einen schreibgeschützten Zugriff auf einen Teil der Serverdateien zu erhalten, aber nicht a Lesen-Schreiben Zugriff. Die Hash-with-HMAC-Methode ist für ein Rand-Quadrat-Szenario vorgesehen, bei dem der schreibgeschützte Angreifer das Hash-Kennwort erhalten kann, nicht jedoch den Schlüssel, der dennoch auf demselben Server gespeichert ist.

Wenn der Angreifer den Schlüssel erhalten könnte, wird HMAC nur eine einfache Hash-Funktion für ihn, und in diesem Fall ist HMAC viel schlechter als bcrypt, weil es ungesalzen und zu verdammt ist schnell. Es ist, als ob die Passwörter mit einem Paar von SHA-1-Aufrufen gehasht wurden. Dieses Szenario ist nicht weniger wahrscheinlich als das vorherige, und daher müssen wir die Verwendung von HMAC allein als zu riskant betrachten .


Für das Beste aus beiden Welten wenden Sie HMAC auf das Benutzerkennwort an, und dann verarbeiten Sie die HMAC-Ausgabe durch - bcrypt ; Sie speichern die Ausgabe von bcrypt. Da bcrypt-Implementierungen das Kennwort als Zeichenfolge erwarten, müssten Sie die HMAC-Ausgabe (hexadezimal, Base64 ...) codieren.

Dies ist komplexer als bcrypt allein, da zwei Funktionen anstelle einer verwendet werden und der Schlüssel (was das heikle Problem der Schlüsselverwaltung mit sich bringt: Generierung, Speicherung, Sicherung ...). Da die Komplexität schlecht ist, würde ich dagegen empfehlen; Verwenden Sie einfach bcrypt alleine und fügen Sie keinen HMAC hinzu. Dies ist jedoch Ihr Anruf; Wenn Sie wirklich wollen die HMAC, verwenden Sie es zusätzlich zu bcrypt, nicht statt bcrypt.

(Hinweis: Das ist bcrypt auf der HMAC-Ausgabe, nicht umgekehrt, was aufgrund des in der bcrypt-Ausgabe enthaltenen Salzes nicht funktionieren würde.)

9
Thomas Pornin

HMAC ist sehr schnell ausgelegt und bietet in diesem Zusammenhang eine gute Möglichkeit, dem Kennwort Salt hinzuzufügen, anstatt es nur anzuhängen. Bcrypt ist aufgrund der langsamen Initialisierung viel langsamer, während Scrypt sogar langsamer als Bcrypt ist, da es absichtlich so konzipiert ist. Scrypt wurde entwickelt, um das brutale Erzwingen sehr rechenintensiv zu machen. Es verbraucht viel CPU, Speicher und ist auch auf GPUs langsam zu verwenden.

Mehr zum Verschlüsseln

2
Matrix