Hallo Dennis,
Ich überlege mir gerade, wie das wohl mit Auth Digest funktioniert. Auth Digest wäre ja vom Prinzip her Challenge-Response…
Ja, ist es auch.
Für den Server bedeutet dies meines Erachtens einen Mehraufwand - herkömmlicherweise kann z.B. Apache ja jeden Request für sich getrennt behandeln. Bei Auth Digest müsste Apache ja aber im Hintergrund eine Art Session führen, da er sich merken muss, welchem Client er welchen Zufallswert rausgegeben hat, oder?
Ja.
Würde mich mal interessieren wie man so etwas realisiert, unter anderem wenn man gar nicht weiß, welcher Prozess oder Thread den zweiten Request des Clients erhält.
mod_auth_digest nutzt Shared Memory Segmente, um das zu speichern. Übrigens: mod_auth_digest implementiert Digest Auth auch nicht vollständig, es funktioniert zwar (wenn der Browser es kann), aber einige Aspekte der Spezifikation (z.B. MD5-sess) sind nicht implementiert, d.h. alle Features, die in Digest Auth vorgesehen sind, kannst Du nicht nutzen.
Und Usern, welche Javascript deaktiviert haben, keine Sicherheit bieten? Nun gut, man könnte es auch andersrum sehen: Usern, welche Javascript aktiviert haben zusätzliche Sicherheit bieten!
Ja, darum ging es mir.
wobei bei ich wie gesagt im Zweifelsfall einfach SSL/TLS wählen würde, mit CAcert und einem Root-Server ist das auch schnell realisiert ;-)
Wie viele Leute, die zum Beispiel ein eigenes Weblog benutzen, verwenden sowas? Bzw. ist es für die praktikabel, sowas zu verwenden?
Ja, deswegen schrieb ich ja, dass Challenge-Response gegen Live-Angriffe (!) nichts bewirkt [*].
Genau, allerdings nur, wenn man eine „Session” verwendet, also einen sich nicht ändernden Schlüssel, mit welchem man Zugang erhält. Das war ja eigentlich auch alles was ich sagen wollte - ich sehe keinen Sinn darin, aufwendig ein Challenge-Response Login-Verfahren zu programmieren mit jeder Menge Javascript auf der Client-Seite, wenn letztendlich im Anschluss daran nur der Session-Schlüssel abgehört werden muss, damit das System geknackt ist.
Naja, sobald man sich ausloggt, ist der Session-Key ja nichts mehr wert. Das heißt: Wenn jemand nicht genau in dem Zeitraum, in dem Du eingeloggt bist, etwas macht, dann nützt ihm der Session-Key auch nichts.
Zudem: Wenn Du in der Session die IP-Adresse speicherst, dann kannst Du so etwas größtenteils verhindern (nicht komplett, es gibt immer noch mögliche Angriffe - jedoch *sehr* aufwendig). Das muss allerdings deaktivierbar für den User sein, weil manche User sich zwangsweise hinter ändernden IPs bewegen (z.B. AOL-User mit Proxy).
Mit IP-Sperrre bleiben natürlich immer noch Man-in-the-middle-Angriffe (dagegen ist Challenge-Response zwar an sich immun, allerdings kann ja der JS-Code zum Hashen der Zugangsdaten einfach entfernt werden), Man-in-the-middle ist aber weitaus aufwendiger, als bloßes Lauschen.
Ist immer die Frage, wogegen man sich absichern will. Stell Dir doch einfach eine typische Weblog- oder Forensoftware vor. Die wenigsten Leute können es sich leisten, den Adminzugang über SSL/TLS zu bewerkstelligen (hey, sogar wir hier bei SELFHTML verwenden kein SSL/TLS für das Forum weil wir den normalen Usern keine Zertifikatswarnung vorsetzen wollen und ein HTTP/HTTPS-Mischmasch extrem verwirrend wäre und nur zu Problemen führen würde). Und klar, HTTP bekommt man nicht vollkommen abgesichert, Man-in-the-middle ist da immer problematisch (wenn man's mit Javascript macht, das man als MITM einfach entfernen kann, wenn der Browser was direkt implementiert natürlich nicht).
Ich persönlich stelle mich auf folgenden Standpunkt: Kann man die jetztige Situation irgendwie verbessern? Im Moment ist es nämlich bei Formular-Logins extrem trivial die Auth-Daten abzufangen, gerade in offenen WLANs oder ähnlichem. Und mit einigen Maßnahmen man könnte es einem Angreifer sehr (!) viel schwerer machen, Zugang zum System zu erhalten.
Denn: Einfach mal einen Rechner in ein offenes WLAN stellen und Zugangsdaten mitsniffen lassen und sie sich hinterher schön ausgeben lassen ist sehr einfach - gibt's auch Programme dazu. Mit einem Rechner Live das mögliche Eingeben von Zugangsdaten beobachten und sich die Session-ID krallen und während der Zeit, in der der Benutzer eingeloggt ist, etwas zu machen, ist schon aufwendiger. Bei einer IP-Sperre der Session seine eigene IP zu fälschen und den kompletten TCP-Handshake + Request durchzudrücken, bevor der richtige Rechner ein RST-Paket schickt halte ich für wahnsinnig aufwädig. Und Man-in-the-middle halte ich im Normalfall für nicht allzu praktikabel - wobei es hier Ausnahmen gibt (jemand simuliert auf einen Flughafen einen Hotspot der Telekom o.ä. obwohl er eigentlich einen bösartigen Rechner mit transparentem Proxy betreibt etc.).
Wenn ich das richtig sehe, ist dies aber im Falle von Auth Digest aber nicht der Fall, oder? Hier müssten doch eigentlich bei jedem Request die Zugangsdaten übermittelt werden, wie bei Auth Basic. Und weil die URL mit als Salz für den Hash genommen wird, ist der übertragene Schlüssel bei jedem Request anders.
[+nonce-counter-Zeug]
Ja.
[Session fixation, session_regenerate_id()]
Stimmt, an den Aspekt habe ich noch gar nicht gedacht, sofern der Server also Session-IDs über GET-Parameter akzeptiert sollte man hier gezielt vorbeugen.
Nicht nur dort. Es ist auch denkbar, fremde Session-Cookies zu "injecten". Drei Beispiele (gibt vermutlich noch mehr):
1. Cookies dürfen nur für Second Level Domains gesetzt werden, damit man keine Cookies für .com etc. setzen kann. Allerdings nützt das nur begenzt etwas:
1a. Wenn man aber zum Beispiel Webspace nur als Subdomain hat, z.B. meinname.gratishoster.example, könnte jemand anderes mit einem anderen Account auf gratishoster.example - boesewicht.gratishoster.example - Dir für die gesamte (!) gratishoster.example-Domain einen Cookie setzen, der dann auch an meinname.gratishoster.example gesendet wird - mit der falschen Session-ID.
1b. Es gibt ja "Quasi-Toplevel-Domains" wie .co.uk, .com.ar etc. - einige davon stehen bei Browsern bereits auf einer Art Blacklist, andere nicht. Und zumindest bei .com.ar funktioniert das Setzen von Cookies für die gesamte "Quasi-TLD" von einer Domain wie *****.com.ar aus (probier's aus, /etc/hosts ist dabei Dein Freund ;-)).
2. Sollte es eine XSS-Lücke in der Seite geben, kann Javascript injeziert werden, das so einen Cookie setzt (der im Idealfall auch noch länger lebt, dass das nichtmal ein Live-Angriff sein muss!). Und selbst wenn die Seite selbst sicher ist, kann auf einer beliebigen (!) Subdomain eine XSS-Lücke bestehen, dann war's das auch schon.
Gut, zu 2 wäre noch zu sagen, dass es eine Möglichkeit gibt (geht allerdings nicht in allen Browsern), Cookies vor Javascript abzuschotten, das nützt aber nur dann etwas, wenn der Cookie bereits gesetzt wurde, d.h. es verhindert effektiv nur ein Auslesen eines bestehenden Session-Cookies durch XSS-Attacken - nicht jedoch das *vorherige* Setzen eines eigenen.
----------------------- schnipp ---------------
Allgemeines noch zu Challenge-Response (ich hatte auch im Chat eine interessante Diskussion deswegen): Challenge-Response hat den großen Nachteil, dass man sich mit den Informationen, die auf dem Server gespeichert sind, einloggen kann. Das heißt: Taucht die User-DB irgendwann einmal im Internet auf, so kann sich bei Challenge-Response jeder mit den dort vorhandene Informationen einloggen. Selbst wenn die Daten gehasht und gesaltet gespeichert werden: Der Client muss genau diesen Prozess bei sich mit dem gleichen Hash und Salt nachbauen, damit er das gleiche Ergebnis erzeugen kann, wie der Server. Daher ist es bei Challenge-Response im Prinzip relativ sinnlos, die Passwörter zu hashen / salten, weil der Zugang damit trotzdem möglich wird.
Henryk hat mich im Chat allerdings auf ein Projekt namens SRP aufmerksam gemacht. Das dort vorgeschlagene Protokoll bewerkstelligt folgendes:
a) Das Passwort wandert nie im Klartext über die Leitung.
b) Der Server kennt nur ein gehashtes, gesaltetes Passwort, nicht das Klartextpasswort.
c) Der Client *muss* das Klartextpasswort kennen, um sich einloggen zu können.
d) Der Server kann das Klartextpasswort aus den ihm zur Verfügung stehenden Daten auch nach der Authentifizierung nicht rekonstruieren.
e) Der Client kann verifizieren, dass der Server einen korrekten Hash des Passworts kennt.
f) Sollte die User-DB des Servers veröffentlicht werden, kann ein Angreifer sich damit nicht einloggen (der Client muss). Er kann natürlich weiterhin Wörterbuchangriffe gegen die Hashes fahren. Allerdings kann er sich dem Client gegenüber als gültiger Server ausgeben (weil er ja jetzt den Hash kennt).
g) Man-in-the-middle funktioniert nicht.
h) Server- und Client handeln einen gemeinsamen Schlüssel aus, der nur ihnen bekannt ist.
Ich werde damit in nächster Zeit mal etwas rumspielen, wollte es nur mal erwähnt haben, vielleicht interessiert's Dich auch.
Viele Grüße,
Christian