von Sandro Affentranger

Datenlecks – Vorfälle, bei denen Unberechtigte Zugriff auf Datensammlungen erhalten haben – kommen immer wieder vor. Um zu verhindern, dass in einem solchen Fall Benutzerpasswörter kompromittiert werden, ist es wichtig, dass diese nicht einfach im Klartext abgespeichert werden. Stattdessen sollten sie stets nur «gehasht» abgespeichert werden. Dieser Artikel beleuchtet, welche Hashfunktionen sich dafür eignen.

Einführung

Fast schon wöchentlich kann man von einem neuen Datenleck lesen, bei dem es Hacker geschafft haben, sich in fremde Datenbanken einzuhacken und die darin gespeicherten Daten auszulesen. Unter diesen Daten befinden sich oftmals Benutzerinformationen wie E-Mail-Adressen und Passwörter. Auf der Webseite Have I Been Pwned? [1] werden Datenlecks gesammelt und analysiert. Internetnutzer können dort überprüfen, ob ihre persönlichen Daten geleakt wurden oder nicht.

Genau für solche Fälle sollten Passwörter nicht einfach im Klartext abgespeichert werden. Stattdessen sollten Passwörter «gehasht» und nur der Hashwert (kurz: Hash) eines Passwortes abgespeichert werden. Hashfunktionen [2] sind sogenannte Einwegfunktionen. Solche Funktionen sind leicht zu berechnen, aber nur schwer umzukehren. Für ein Passwort heisst das, dass sich der Hash davon leicht berechnen lässt, aber es ist extrem schwierig, ein Passwort nur anhand des Hashes herauszufinden. Angreifern bleibt nur die Möglichkeit, für alle möglichen Passwörter den Hash zu berechnen und mit dem gegebenen Hash zu vergleichen.

Leider haben Benutzer keinen Einfluss darauf, wie ihre Passwörter abgespeichert werden. Meistens wissen sie nicht einmal, wie ihre Passwörter gespeichert werden. Falls man sein Passwort vergessen hat, deshalb von der «Passwort vergessen»-Funktion einer Webseite Gebrauch macht und daraufhin sein altes Passwort im Klartext per E-Mail zugeschickt bekommt, dann weiss man, dass das Passwort entweder im Klartext oder in reversibler Form abgespeichert wird. Beide Fälle sind problematisch und man sollte auf Nummer sicher gehen, dass das gleiche Passwort nicht auch bei anderen Webdiensten verwendet wird.

Wie Passwörter abgespeichert werden

Studien darüber, wie Passwörter abgespeichert werden, gibt es nur wenige. Dies ist nicht verwunderlich, da diese Information meist nicht öffentlich verfügbar ist und wenn doch, dann heisst es meist nur, dass die Passwörter sicher gespeichert würden.

Naiakshina et al. untersuchten 2017 [3] und 2018 [4], ob Studenten Passwörter sicher abspeichern, wenn sie eine Applikation entwickeln, die Passwörter für die Authentifizierung von Benutzern verwendet. Die Studenten wurden im Rahmen der Studie damit beauftragt, die Registrierung für eine soziale Netzwerkplattform zu programmieren. Teil der Aufgabe war die sichere Speicherung der Passwörter. Jedoch wurde nur die Hälfte der Studenten darüber in Kenntnis gesetzt. Die andere Hälfe wurde nicht explizit darüber informiert, dass die Sicherheit der Registrierung ebenfalls eine Anforderung des Projektes war.

Die Auswertung ergab, dass keiner der Studenten, der nicht aufgefordert wurde, Passwörter sicher abzuspeichern, dies tat. Die Studenten fühlten sich nicht für die Sicherheit ihrer Implementation verantwortlich, weil dies bei ihnen nicht explizit gefordert wurde.

Im Anschluss an den Programmierteil wurden die Studenten zu ihrem Wissen über Sicherheit befragt. Mehrheitlich wussten die Studenten, was Hashing ist. Jedoch zeigte sich, dass das Wissen über sichere Software nicht automatisch zu sicherer Software führte. Die Funktionalität der Implementation stand im Vordergrund. Die Sicherheit war höchstens ein nachträglicher Gedanke.

Mehrere Studenten gaben bei der anschliessenden Befragung an, dass sie die Passwörter sicher abgespeichert hätten, wenn sie die Registrierung tatsächlich für eine Firma implementiert hätten und nicht im Rahmen eines Projektes während ihres Studiums. Naiakshina et al. wollten deshalb daraufhin herausfinden, ob das tatsächlich der Fall gewesen wäre und wiederholten die Studie 2019 [5] mit Freelance-Entwicklern.

Über eine Plattform heuerten sie über 40 Entwickler an, die daraufhin ebenfalls den Registrierungsteil einer sozialen Netzwerkplattform entwickelten. Die Ergebnisse dieser Studie waren ernüchternd. Auch die Mehrheit der Freelancer speicherte die Passwörter nicht sicher ab, wenn sie nicht explizit dazu aufgefordert wurden. Es gab zudem viele Missverständnisse, was die sichere Speicherung von Passwörtern betraf, oder es wurden veraltete Methoden eingesetzt, die nicht mehr den aktuellen Empfehlungen entsprechen oder inzwischen gar als schlichtweg unsicher gelten.

Nur 4 der 22 Freelancer, die nicht zuvor explizit darauf hingewiesen wurden, speicherten Passwörter nicht im Klartext ab. Alle anderen wurden im Nachhinein jeweils noch aufgefordert, Passwörter sicher abzuspeichern und ihre Implementation anzupassen.

Tabelle 1 zeigt, welche Algorithmen verwendet wurden, um Passwörter abzuspeichern.

Methode Anzahl Lösungen *
Base64 8
MD5 10
SHA1 1
SHA256 5
HMAC-SHA1 1
Symmetrisch (3DES) 3
Symmetrisch (AES) 3
PBKDF2 5
Bcrypt 7

Tabelle 1: Resultate der Studie

*Nachdem Entwickler, die keine sichere Lösung implementiert hatten, aufgefordert wurden, Passwörter sicher abzuspeichern.

8 der 43 Entwickler speicherten die Passwörter Base64-enkodiert ab. Base64 ist ein Verfahren für die Kodierung von binären Daten. Zwar ist das Passwort dann nicht mehr mit blossem Auge zu erkennen, aber es ist trivial Base64-kodierte Daten wieder zu dekodieren.

10 der 43 Entwickler verwendeten den Hashalgorithmus MD5, welcher schon seit über 10 Jahren als kryptographisch gebrochen gilt. 2 Entwickler verwendeten SHA1, respektive HMAC-SHA1, der ebenfalls als gebrochen gilt.

6 Entwickler verschlüsselten die Passwörter symmetrisch. Die Hälfte davon verwendete dazu den Verschlüsselungsalgorithmus Triple-DES (3DES), der für mehrere Angriffe anfällig ist und nicht mehr verwendet werden sollte. Jedoch gilt generell, dass Passwörter nicht verschlüsselt abgespeichert werden sollten, da ein Angreifer, welcher das System, auf dem die Passwörter gespeichert sind, kompromittiert, oft auch in den Besitz des Schlüssels gelangt, der für die Verschlüsselung verwendet wurde. Danach kann er alle verschlüsselten Passwörter einfach entschlüsseln. Ausserdem verwendeten die meisten dieser Entwickler für die Verschlüsselung Passwörter, die ziemlich einfach zu erraten gewesen wären. Des Weiteren besteht bei verschlüsselten Passwörtern die Möglichkeit, dass ein interner Mitarbeiter mit bösartigen Absichten die Passwörter herausfinden kann.

5 Entwickler verwendeten die Hashfunktion SHA256. Diese Hashfunktion ist nicht darauf ausgelegt, Passwörter zu hashen und wurde auf Performance hin optimiert. Das führt dazu, dass SHA256-Hashes schneller geknackt werden können.

Nur 12 der Entwickler verwendeten PBKDF2 oder Bcrypt. Beides sind moderne Algorithmen, die sich für das Hashen von Passwörtern eignen.

Keiner der Entwickler verwendete einen speicherintensiven Hashalgorithmus wie Argon2 oder Scrypt, welche dem aktuellen Stand der Technik entsprechen.

Wie kommt es dazu, dass so viele veraltete Algorithmen verwendet wurden? Einerseits ergab sich aus den Interviews, dass Entwickler diese teilweise einsetzten, weil sie das schon seit Jahren so machen, ohne sich zu informieren, was zurzeit empfohlen wird. Andererseits zeigte sich, dass sowohl die Studenten als auch die Freelancer teilweise Code aus dem Internet kopierten. Zwar spricht nichts dagegen, Code zu kopieren, jedoch ist es so, dass der Code, den man findet, nicht immer aktuell ist. Acar et al [6] fanden heraus, dass Antworten auf Stack Overflow [7] (einer Internetplattform, auf der Fragen zur Softwareentwicklung gestellt werden können) einfach zu verwenden sind, aber in weniger Sicherheit resultieren als offizielle API-Dokumentation.

Wie Passwörter abgespeichert werden sollten

Passwörter müssen gehasht abgespeichert werden. So viel ist klar. Aber nicht jede Hashfunktion eignet sich zum Hashen von Passwörtern! Unterschiedliche Hashfunktionen haben unterschiedliche Verwendungszwecke. Es sollten nur Passworthashfunktionen oder Schlüsselableitungsfunktionen verwendet werden, da diese Funktionen Merkmale besitzen, die Brute-Force-Attacken stark erschweren.

Empfohlene Funktionen sind (u.a. gestützt auf [8] und [9]):

  • Argon2: Argon2 ist eine Familie von Passworthashingfunktionen und ging als Sieger der Password Hashing Competition [10] im Jahr 2015 hervor. Argon2 stellt zurzeit die beste Wahl für das Hashen von Passwörtern dar. Da die Funktionen aber noch relativ neu sind, werden sie auf älteren Systemen zum Teil noch nicht unterstützt.
  • Scrypt: Scrypt ist ebenfalls eine neuere Funktion, die so konstruiert wurde, dass eine bestimmte Menge an Arbeitsspeicher für die Berechnung benötigt wird. Dies soll die Parallelisierung teurer machen. Da Scrypt ebenfalls eine eher neuere Funktion ist, hat sie den gleichen Nachteil wie Argon2 bezüglich der Unterstützung.
  • Bcrypt: Bcrypt wurde gleicherweise so entworfen, dass die Berechnung möglichst aufwändig ist. Über einen einstellbaren Kostenfaktor kann konfiguriert werden, wie lange die Berechnung eines Hashes dauern soll. Bcrypt ist der wohl am meisten unterstützte Algorithmus.
  • PBKDF2: PBKDF2 ist eine Schlüsselableitungsfunktion, die aus einem Passwort einen kryptographischen Schlüssel ableiten kann. Die Funktion eignet sich allerdings auch für das Hashen von Passwörtern. PBKDF2 ist nicht speicherintensiv und kann daher für GPU optimiert werden.

Falls die gewählte Hashfunktion über einen konfigurierbaren Kostenfaktor, wie zum Beispiel die Anzahl von Hashrunden oder den Speicherverbrauch, verfügt, sollte dieser an das entsprechende System angepasst werden. Der Wert sollte so hoch wie möglich gewählt werden, abhängig davon wie es das System, auf dem der Hash berechnet wird, zulässt.

Da Hardware ständig leistungsfähiger und auch billiger wird, ist es wichtig, dass auch der Kostenfaktor von Zeit zu Zeit erhöht wird. Dabei kann entsprechend der Methoden, die im nächsten Kapitel für den Wechsel der Hashfunktion vorgestellt werden, vorgegangen werden.

Wenn ein Passwort von mehreren Benutzern verwendet wird, kommt dabei auch der gleiche Hash heraus. Um das zu vermeiden, soll bei der Berechnung des Hashes das Passwort mit einem zufälligen Wert – dem sogenannten Salt – verknüpft werden. Der Salt wird dabei zufällig gewählt. Dies führt nicht nur dazu, dass für das gleiche Passwort unterschiedliche Hashes berechnet werden, sondern auch, dass das Knacken von Passworthashes erschwert wird. Gewisse Passworthashingfunktionen verwenden automatisch Salts für die Berechnung des Hashes. Bei anderen Funktionen muss das Salting selbst implementiert werden. Dazu sollte mit einem kryptographisch sicheren Zufallszahlengenerator eine zufällige Zeichenfolge generiert werden. Danach werden der Salt und das Passwort verkettet und die resultierende Zeichenfolge wird der Hashfunktion übergeben. Der Salt muss zusammen mit dem Hash in der Datenbank abgelegt werden, damit die Überprüfung eines Passwortes möglich ist.

Passwörter können nicht nur gesalzen, sondern auch gepfeffert werden. Salting und Peppering funktionieren grundsätzlich ganz ähnlich, aber anders als Salts ist der Pepper für alle gespeicherten Passwörter gleich. Der Pepper wird dann auch nicht in der Datenbank zusammen mit den Passworthashes gespeichert, sondern an einem separaten Ort. Der Zweck des Peppers ist zu verhindern, dass ein Angreifer gestohlene Hashes knacken kann, wenn er nur Zugriff auf die Datenbank hat.

Migration der Passworthashfunktion

Was aber, wenn man plötzlich merkt, dass die derzeitig verwendete Passworthashfunktion nicht sicher oder nicht mehr zeitgemäss ist? Wie soll in einem solchen Fall vorgegangen werden? Hier gibt es mehrere mögliche Vorgehensweisen:

  • Zurücksetzen der Passwörter: Ab dem Zeitpunkt der Migration werden alle Benutzer bei der Anmeldung gezwungen ihr Passwort zu ändern. Das alte Passwort wird nicht länger akzeptiert. Der Vorteil bei dieser Methode ist, dass die neue Hashfunktion umgehend in Kraft tritt. Der Nachteil ist jedoch, dass alle Benutzer gezwungen werden ihr Passwort zu ändern. Dieses Vorgehen führt sehr wahrscheinlich zu einem erhöhten Aufkommen an Supportanfragen. Des Weiteren kann es zu Problemen kommen, wenn ein Benutzer das Passwort nicht zurücksetzen kann, zum Beispiel weil er keinen Zugang mehr zum E-Mail-Konto hat, das er bei der Erstellung des Benutzerkontos angegeben hat.
  • Wechsel der Funktion nach der Anmeldung: Bei der Anmeldung wird das Passwort des Benutzers mit dem alten gespeicherten Hash verglichen. Wenn das Passwort korrekt ist, wird es mit der neuen Hashfunktion gehasht und abgespeichert. Dazu muss für jeden Benutzer klar sein, welche Hashfunktion verwendet wird. Entweder anhand des gespeicherten Hashes (z.B. aufgrund der Länge) oder anhand einer zusätzlichen Spalte in der Datenbank. Es muss sichergestellt werden, dass der alte Hash bei der Anmeldung nicht mehr berücksichtigt wird. Der Vorteil dieser Methode ist, dass die Benutzer nichts davon mitbekommen. Der Nachteil ist jedoch, dass solange sich ein Benutzer nicht anmeldet, er nicht auf die neue Hashfunktion migriert wird.
  • Doppelt hashen: Diese Variante ähnelt der vorangegangenen, aber es werden alle alten Hashes mit der neuen Passworthashfunktion gehasht und abgespeichert. Damit wird sichergestellt, dass keine alten Hashes mehr in der Datenbank vorkommen. Der Vorteil dieser Methode ist ebenfalls, dass die Migration der Passworthashfunktion im Hintergrund geschieht, ohne dass die Benutzer etwas davon mitbekommen. Jedoch führt dieser Ansatz zu einer neuen Schwachstelle. Wenn es einem Angreifer gelingt, sowohl an die doppelt gehashten Passwörter als auch Passwörter, die mit der alten Hashfunktion gehasht wurden, zu gelangen (zum Beispiel aus einer komplett anderen Datenbank oder von bekannten Datenlecks), kann er versuchen Passwörter herauszufinden, indem er die Liste der alten Hashes als Eingabe für die neue Hashfunktion verwendet, ohne dass die alten Hashes geknackt wurden.

Diese Möglichkeiten wirken sich unterschiedlich stark auf die Benutzer aus und müssen dementsprechend gegeneinander abgewogen werden. Theoretisch wäre es auch möglich, ab einem bestimmten Zeitpunkt die Hashfunktion bei einer erfolgreichen Anmeldung zu wechseln und zu einem späteren Zeitpunkt eine Passwortänderung für alle Benutzer zu erzwingen, die sich in der Zwischenzeit nicht angemeldet haben.

Fazit

Nicht jede Hashfunktion eignet sich zum Hashen von Passwörtern. Deshalb ist die Aussage, dass Passwörter gehasht abgespeichert werden sollen, nicht ausreichend präzise. Es sollte eine Hashfunktion eingesetzt werden, die speziell für das Hashen von Passwörtern konstruiert wurde.

Ausserdem sollte regelmässig überprüft werden, ob die verwendete Hashfunktion und der allfällige Kostenfaktor noch zeitgemäss sind. Falls dies nicht länger der Fall ist, sollte die Funktion bzw. der Kostenfaktor angepasst werden.

Wie die Studien von Naiakshina et al gezeigt haben, ist es wichtig, dass bei Spezifikationen auch die Sicherheitsanforderungen aufgeführt werden müssen. Ansonsten ergibt sich die Gefahr, dass die Spezifikation umgesetzt wird, ohne dass der Sicherheit Beachtung geschenkt wird. Sicherheit muss ebenfalls zu einer Priorität erklärt werden und auf dieselbe Ebene gestellt werden wie funktionale Korrektheit.

Über den Autor

Sandro Affentranger studierte Informatik an der ETH Zürich und verbrachte ein Austauschsemester an der Königlichen Technischen Hochschule (KTH) in Stockholm, Schweden. Im Masterstudium spezialisierte er sich auf Informationssicherheit und schrieb seine Masterarbeit im Bereich anonyme Kommunikation in zukünftigen Internetarchitekturen. Während seines Studiums absolvierte Sandro Affentranger ein Praktikum als Software-Entwickler bei einem Schweizer Informatik-Dienstleister, wo er mit der Entwicklung einer Web-Applikation beschäftigt war. Danach arbeitete er weiter als Teilzeit-Software-Entwickler und war zuständig für die Programmierung von mobilen Applikationen. Seit Oktober 2017 ist er bei Oneconsult als Penetration Tester angestellt und seit Dezember 2020 als Senior Penetration Tester. Sandro Affentranger ist Offensive Security Web Expert (OSWE), Offensive Security Certified Professional (OSCP) und zertifizierter OSSTMM Professional Security Tester (OPST).

Über Oneconsult

Die Oneconsult-Unternehmensgruppe ist seit 2003 Ihr renommierter Schweizer Cyber Security Services Partner mit Büros in der Schweiz und Deutschland und 2000+ weltweit durchgeführten Security-Projekten.

Erhalten Sie kompetente Beratung vom inhabergeführten und herstellerunabhängigen Cyber Security-Spezialisten mit 40+ hochqualifizierten Cyber Security Experten, darunter zertifizierte Ethical Hacker / Penetration Tester (OPST, OPSA, OSCP, OSCE, GXPN), IT-Forensiker (GCFA, GCFE, GREM, GNFA), ISO Security Auditoren (ISO 27001 Lead Auditor, ISO 27005 Risk Manager, ISO 27035 Incident Manager) und dedizierte IT Security Researcher, um auch Ihre anspruchsvollsten Herausforderungen im Informationssicherheitsbereich zu bewältigen. Gemeinsam gehen wir Ihre externen und internen Bedrohungen wie Malware-Infektionen, Hacker-Attacken und APT sowie digitalen Betrug und Datenverlust mit Kerndienstleistungen wie Penetration Tests / Ethical Hacking, APT Tests unter Realbedingungen und ISO 27001 Security Audits an. Bei Notfällen können Sie rund um die Uhr (24 h x 365 Tage) auf die Unterstützung des Digital Forensics & Incident Response (DFIR) Expertenteams von Oneconsult zählen.

www.oneconsult.com


[1]: https://haveibeenpwned.com/
[2]: https://de.wikipedia.org/wiki/Hashfunktion
[3]: A. Naiakshina, A. Danilova, C. Tiefenau, M. Herzog, S. Dechand und M. Smith, „Why do developers get password storage wrong?: A qualitative usability study.“, Proceedings of the 2017 ACM SIGSAC Conference on Computer and Communications Security, pp. 311-328, 2017
[4]: A. Naiakshina, A. Danilova, C. Tiefenau und S. Matthew, „Deception task design in developer password studies: exploring a student sample.“, Fourteenth Symposium on Usable Privacy and Security (SOUPS) 2018, pp. 297-313, 2018
[5]: A. Naiakshina, A. Danilova, E. Gerlitz, E. von Zezschwitz und M. Smith, „»If you want, I can store the encrypted password.» A Password-Storage Field Study with Freelance Developers.“, Proceedings of the 2019 CHI Conference on Human Factors in Computing Systems, pp. 1-12, 2019
[6]: Y. Acar, M. Backes, S. Fahl, D. Kim, L. M. Mazurek und C. Stransky, „You Get Where You’re Looking For – The Impact of Information Sources on Code Security“, 2016 IEEE Symposium on Security and Privacy, pp. 289-306, 2016
[7]: https://stackoverflow.com/questions/
[8]: https://tools.ietf.org/html/draft-ietf-kitten-password-storage-02#section-5
[9]: https://cheatsheetseries.owasp.org/cheatsheets/Password_Storage_Cheat_Sheet.html#modern-algorithms
[10]: https://password-hashing.net