Für unsere Leser, die mit dem, was ein Hash -Algorithmus ist, nicht vertraut sind, ist es nichts weiter als eine Einweg -Funktion, die Daten mit variabler Länge an Daten mit fester Länge abbildert. Wenn wir also die obige Definition analysieren, müssen wir die folgenden Anforderungen und Merkmale solcher Algorithmen verstehen:
Sie werden auch als „Pseudo-Random-Funktionen“ bezeichnet, was bedeutet, dass die Ausgabe einer Hashing-Funktion von einem echten Zufallszahlengenerator (oder TRNG) nicht zu unterscheiden sein sollte.
Die Tatsache, dass die Ausgabe einer Hash -Funktion unter Verwendung eines effizienten Algorithmus nicht wieder zum Eingang zurückgekehrt werden kann, bedeutet nicht, dass sie nicht geknackt werden kann. Datenbanken, die Hashes von gemeinsamen Wörtern und kurzen Zeichenfolgen enthalten, sind in der Regel in unserer Reichweite mit einer einfachen Google -Suche. Außerdem können gemeinsame Saiten leicht und schnell gezwungen oder mit einem Wörterbuchangriff gezwungen werden.
Hier ist ein kurzes Video darüber, wie ein Tool wie SQLMAP über die SQL -Injektion durch Bruteforcing MD5 -Hashes in einer Datenbank Kennwörter knacken kann.
Außerdem hätten wir einfach die einfachsten Angriffe ausführen können ... schnappen Sie sich einfach den Hash und Google It ... die Chancen stehen gut, dass der Hash in einer Online -Datenbank existiert. Beispiele für Hash -Datenbanken sind:
Wir müssen auch berücksichtigen, dass, da 2 oder mehr identische Kennwörter tatsächlich den gleichen Hash -Wert haben, das Cracking One Hash Ihnen automatisch die Kennwörter jedes einzelnen Benutzers gibt, die das gleiche verwendeten. Um klar zu sein, sagen Sie, Sie haben Tausende von Benutzern, es ist sehr wahrscheinlich, dass ein angemessener Teil davon das berüchtigte Passwort „123456“ verwendet. Der MD5 -Hash -Wert dieses Passwort das '123456' Passwort.
Um diesen Angriff abzumildern, wurden Salze häufig, sind aber offensichtlich nicht für die heutige Rechenleistung, insbesondere wenn die Salzschnur kurz ist, was sie brutalgeschützt macht.
Die Grundkennwort-/Salzfunktion ist definiert als:
f (Passwort, Salz) = Hash (Passwort Salz)
Um einen Brute-Force-Angriff zu mildern, sollte ein Salz bis zu 64 Zeichen betragen. Um einen Benutzer später zu authentifizieren, muss das Salz in einfacher Text in der Datenbank gespeichert werden, also:
<span>if (hash([provided password] + [stored salt]) == [stored hash]) then user is authenticated</span>
Da jeder Benutzer ein völlig anderes Salz hat, vermeidet dies auch das Problem mit einfachen Hashes, wobei wir leicht erkennen können, ob 2 oder mehr Benutzer dasselbe Passwort verwenden. Jetzt werden die Hashes anders sein. Wir können den Passwort -Hash auch nicht mehr direkt nehmen und versuchen, es zu googeln. Mit einem langen Salz ist auch ein Brute-Force-Angriff unwahrscheinlich. Wenn ein Angreifer jedoch durch einen SQL-Injektionsangriff oder einen direkten Zugriff auf die Datenbank auf dieses Salz erhält, wird ein Brute-Force- oder ein Wörterbuchangriff wahrscheinlich, insbesondere wenn Ihre Benutzer gemeinsame Passwörter verwenden (wie '123456'):
<span>Generate some string or get entry from dictionary </span><span>Concatenate with salt </span><span>Apply hash algorithm </span><span>If generated hash == hash in database then Bingo </span><span>else continue iterating</span>
Aber selbst wenn ein Kennwort geknackt wird, gibt dies nicht automatisch das Kennwort für jeden Benutzer, der es verwendet hat, da kein Benutzer denselben gespeicherten Hash haben sollte.
Um ein gutes Salz zu erzeugen, sollten wir einen guten Zufallszahlengenerator haben. Wenn der Rand () -Funktion von PHP automatisch in Ihrem Kopf aufgetaucht ist, vergessen Sie sie sofort.
Es gibt einen hervorragenden Artikel über Zufälligkeit in random.org. Einfach ausgedrückt, ein Computer kann nicht von zufälligen Daten selbst denken. Computer werden als deterministische Maschinen angesehen, was bedeutet, dass jeder einzelne Algorithmus, den ein Computer mit genau gleicher Eingabe ausführen kann, immer denselben Ausgang erzeugt.
Wenn eine Zufallszahl auf den Computer angefordert wird, wird in der Regel Eingaben aus mehreren Quellen wie Umgebungsvariablen (Datum, Uhrzeit, Anzahl der Les-/geschriebenen Bytes, Verfügbarkeit, Verfügbarkeit) erhalten, und wenden Sie dann einige Berechnungen auf, um Zufällige Daten. Dies ist der Grund, warum zufällige Daten, die durch einen Algorithmus angegeben sind, als Pseudo -zufällig bezeichnet werden, und daher ist es wichtig, sich von einer echten Zufallsdatenquelle zu unterscheiden. Wenn wir irgendwie in der Lage sind, die genauen Bedingungen nach der Ausführung eines Pseudo-Random-Zahlengenerators (oder PRNG) nachzubilden, haben wir automatisch die ursprüngliche generierte Nummer. Wenn ein PRNG nicht ordnungsgemäß implementiert ist, ist es außerdem möglich, Muster in den generierten Daten zu entdecken. Wenn Muster vorhanden sind, können wir das Ergebnis vorhersagen. Es ist zwar nicht klar, welche PHP- oder Windows -Version verwendet wird, aber Sie können sofort feststellen, dass etwas nicht stimmt, indem Sie sich die Bitmap ansehen, die mit Rand () verwendet wird:
Wenn Sie zufällige Daten generieren müssen, verwenden Sie bitte OpenSSL_RANDOM_PSEUDO_BYTES (), die ab Php 5> = 5.3.0 verfügbar sind. Es hat sogar das Crypto_Strong -Flag, das Ihnen sagt, ob die Bytes sicher genug sind.
Hier ist ein schnelles Code -Beispiel, mit dem zufällige Zeichenfolgen mit OpenSSL_RANDOM_PSEUDO_BYTES ()
generiert werden können
<span>if (hash([provided password] + [stored salt]) == [stored hash]) then user is authenticated</span>
Um die Brute-Force-Angriffe weiter zu mildern, können wir die Kennwortdeting-Technik implementieren. Dies ist nur ein iterativer oder rekursiv
Um ein durch Dehnen gesicherter Passwort zu knacken, sollte der Angreifer:
Dies macht einen Angriff unwahrscheinlich… aber nicht unmöglich. Um die 1 -Sekunden -Verzögerung zu überwinden, sollte ein Angreifer über höhere Hardwarespezifikationen verfügen als der Computer, für den der Algorithmus eingestellt wurde, etwas, das einen hohen Kosten bedeuten könnte, sodass der Angriff unerschwinglich teuer wird.
Sie können auch Standardalgorithmen verwenden, wie PBKDF2, eine kennwortbasierte Schlüsselabgabefunktion
<span>if (hash([provided password] + [stored salt]) == [stored hash]) then user is authenticated</span>
Es gibt auch Zeit- und Speicher -intensive Algorithmen wie Bcrypt (über die Crypt () -Funktion) und Scrypt
<span>Generate some string or get entry from dictionary </span><span>Concatenate with salt </span><span>Apply hash algorithm </span><span>If generated hash == hash in database then Bingo </span><span>else continue iterating</span>
wobei $ cost der Arbeitsfaktor ist und $ salz eine zufällige Zeichenfolge, die Sie mit der Funktion Secure_Rand () oben generieren können.
Der Workload -Faktor hängt vollständig vom Zielsystem ab. Sie können mit einem Faktor von „09“ beginnen und ihn erhöhen, bis der Betrieb in ca. 1 Sekunde.
Ab PHP 5> = 5.5.0 Sie können die neue Funktion password_hash () verwenden, die Bcrypt als Standardmethode für Hashing verwendet.
Es gibt noch keine Scrypt -Unterstützung in PHP, aber Sie können die Scrypt -Implementierung von DomBlack überprüfen.
Hashing und Verschleierung (oder Verschlüsseln ) sind Begriffe, die oft verwirrt sind. Wie ich bereits erwähnt habe, ist Hashing eine Pseudo-Random-Funktion, während die Cyphering im Allgemeinen eine „Pseudo-Random-Permutation“ ist. Dies bedeutet, dass die Eingabenachricht so geschnitten und verändert wird, dass die Ausgabe von einem TRNG nicht zu unterscheiden ist. Die Ausgabe kann jedoch wieder in den ursprünglichen Eingang umgewandelt werden. Diese Transformation erfolgt mit einem Verschlüsselungsschlüssel, ohne die es unmöglich sein sollte, die Ausgabe in die ursprüngliche Nachricht erneut zu verwandeln.
Ciphering hat einen weiteren großen Unterschied zu Hashing. Während der Ausgangsnachrichtenraum von Hashing endlich ist, ist die Verschlechterung der Ausgangsnachrichtenraum unendlich, da die Beziehung zwischen Eingabe und Ausgabe 1: 1 beträgt, daher sollten Kollisionen nicht bestehen.
Man muss sehr vorsichtig sein, wie die Verschlüsselungstechniken korrekt angewendet werden können, und der Ansicht, dass nur durch die Anwendung eines Verschlüsselungsalgorithmus auf sensible Daten ausreicht, um es sicher zu halten, da viele Probleme vorhanden sind, die zu Datenlecks führen könnten. In der Regel sollten Sie niemals in Betracht ziehen, Ihre eigene Verschlüsselungsimplementierung
anzuwendenIn letzter Zeit hatte Adobe ein massives Datenleck der Benutzerdatenbank, da sie fälschlicherweise Verschlüsselungstechniken angewendet haben und ich sie als Beispiel dafür nehme, was nicht zu tun ist. Ich werde versuchen, so einfach wie möglich zu sein und die Dinge wirklich einfach zu halten.
Betrachten Sie das folgende Schema:
Nehmen wir an, der einfache Textinhalt der Tabelle lautet wie folgt:
Jetzt hat jemand bei Adobe beschlossen, die Passwörter abzuschließen, aber zwei große Fehler gemacht:
Nehmen wir zum Beispiel an, dass unsere Daten nach der Anwendung eines Enciphering -Algorithmus auf das Kennwortfeld wie folgt aussehen:
Während die Kennwörter nicht einfach entschlüsselt werden können, können wir den Verschlüsselungsschlüssel auf einfache Weise nicht kennen, indem wir die Daten untersuchen, die feststellen, dass die Aufzeichnung von 2 und 7 das gleiche Passwort sowie 3 und 6 teilen. Hier kommt das Feld Passwort Hinweis ins Spiel. Aufzeichnung 6 Hinweis lautet
"Ich bin eins!", was uns nicht viele Informationen gibt, aber der Hinweis von Aufzeichnung 3 ... wir können sicher erraten, dass das Passwort "Queen" ist. Aufzeichnungen 2 und 7 Hinweise geben nicht alleine viele Informationen, aber wenn wir sie gemeinsam ansehen, wie viele Feiertage haben der gleiche Name wie ein beängstigender Film? Jetzt haben wir Zugriff auf das Konto aller, die „Halloween“ als Passwort verwendet haben.
Um das Risiko von Datenlecks zu mildern, ist es besser, auf Hashing -Techniken zu wechseln. Wenn Sie jedoch Verschlüsselungstechniken verwenden müssen, um Passwörter zu speichern, können wir eine optimierbare Verschlüsselung verwenden. Der Begriff sieht ausgefallen aus, ist aber sehr einfach. Nehmen wir an, wir haben Tausende von Benutzern und möchten alle Passwörter verschlüsseln. Wie wir gesehen haben, können wir für jedes Kennwort nicht den gleichen Verschlüsselungsschlüssel verwenden, da die Daten Risiken ausmachen (und andere anspruchsvolle Angriffe werden möglich). Für jeden Benutzer können wir jedoch keinen einzigartigen Schlüssel verwenden, da das Speichern dieser Schlüssel für sich selbst zu einem Sicherheitsrisiko wird. Was wir tun müssen, ist, einen einzelnen Schlüssel zu generieren und ein
"tweak"zu verwenden, das für jeden Benutzer eindeutig ist, und sowohl der Schlüssel als auch der Tweak zusammen ist der Verschlüsselungsschlüssel für jeden Datensatz. Die einfachste verfügbare Verbesserungen ist der Hauptschlüssel, der per Definition für jeden Datensatz in der Tabelle nur eindeutig ist (obwohl ich nicht empfehle, ihn zu verwenden, dient dies nur zum Demonstration des Konzepts):
f (Schlüssel, primärkey) = Key PrimaryKey Oben habe ich einfach sowohl den Verschlüsselungsschlüssel als auch den Wert des Primärschlüssels, um den endgültigen Verschlüsselungsschlüssel zu erzeugen. Anstatt den Primärschlüssel als Tweak zu verwenden, möchten Sie auch einen Nonce (ähnlich wie ein Salz) für jeden Datensatz als Tweak generieren.
Nachdem sie eine optimierbare Verschlüsselung auf die Benutzertabelle angewendet hat, sieht es jetzt nach Folgendes aus:
Natürlich haben wir immer noch das Problem mit Passwort Hinweis, aber jetzt hat jeder Datensatz einen eindeutigen Wert, sodass nicht ersichtlich, welche Benutzer dasselbe Passwort verwenden.
Ich möchte betonen, dass die Verschlüsselung nicht die beste Lösung ist und wenn möglich vermieden werden sollte, um Passwörter zu speichern, da viele Schwächen injiziert werden können. Denken Sie daran, dass selbst bewährte Lösungen ihre Schwächen haben.
Es gibt keine perfekte Lösung und das Risiko, dass jemand, der unsere Sicherheitsmaßnahmen bricht, jeden Tag wächst. Kryptografische und Datensicherheitsstudien und Forschungen werden jedoch fortgesetzt. Die relative jüngste Definition von Schwammfunktionen wächst unser Toolkit jedoch täglich.
Das obige ist der detaillierte Inhalt vonRisiken und Herausforderungen des Passworthashings. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!