Ich verwende Rijndael, um einige sensible Daten in meinem Programm zu verschlüsseln.
Wenn der Benutzer ein falsches Passwort eingibt, wird die meiste Zeit ein CryptographicException
mit der Meldung "Padding ist ungültig und kann nicht entfernt werden" ausgelöst.
Allerdings wirft CryptStream mit einer sehr geringen Wahrscheinlichkeit keine Ausnahme mit dem falschen Passwort, sondern gibt stattdessen einen falsch entschlüsselten Stream zurück. Mit anderen Worten, es entschlüsselt zu Müll.
Irgendeine Idee, wie Sie dies erkennen / verhindern können? Der einfachste Weg, den ich mir vorstellen kann, wäre, beim Verschlüsseln eine "magische Zahl" am Anfang der Nachricht zu setzen und nach dem Entschlüsseln zu überprüfen, ob sie noch da ist.
Aber wenn es einen einfacheren Weg gibt, würde ich es gerne hören!
HMAC ist was Sie brauchen. Es ist genau für diesen Zweck gemacht. Es kombiniert den Schlüssel und die Nachricht (in diesem Fall wird es Ihr Passwort sein) und hasht sie so, dass sie die Authentizität und Integrität des Inhalts gewährleistet, solange die verwendete Hash-Funktion sicher ist. Sie können den HMAC an die verschlüsselten Daten anhängen und er kann später verwendet werden, um zu überprüfen, ob die Entschlüsselung korrekt durchgeführt wurde.
Prüfsummen sind genau für diesen Zweck. Holen Sie vor dem Verschlüsseln einen Hash Ihrer Daten ein. Verschlüsseln Sie die Daten und legen Sie sie zusammen mit dem Hash in den Speicher. Entschlüsseln Sie nach dem Entschlüsseln den Hash der entschlüsselten Daten und vergleichen Sie diesen mit dem ersten. Wenn Sie einen Crypto-Grade-Hash (d. H. SHA512) verwenden, sind Ihre Daten sicher. Denn genau das macht verschlüsselte Kompressionssoftware.
Für die ultimative Sicherheit können Sie sowohl die Hashes als auch die Daten separat verschlüsseln und dann entschlüsseln und vergleichen. Wenn sowohl Daten als auch Hash zu beschädigten Daten entschlüsseln, gibt es sehr geringe Chancen, dass sie übereinstimmen.
Obwohl ich etwas mit Teoman Soyguls Post über CRC / Hash zustimmen kann, ist eine sehr wichtige Sache zu beachten. Verschlüsseln Sie den Hash niemals, da dies den gefundenen Schlüssel leichter finden kann. Selbst ohne den Hash zu verschlüsseln gab man ihnen eine einfache Möglichkeit zu testen, ob sie das korrekte Passwort erfolgreich erhalten haben; Nehmen wir jedoch an, dass dies bereits möglich ist. Da ich weiß, welche Art von Daten Sie verschlüsselt haben, sei es Text, oder serialisierte Objekte oder was auch immer, ist es wahrscheinlich, dass ich Code schreiben kann, um es zu erkennen.
Das heißt, ich habe Ableitungen des folgenden Codes verwendet, um Daten zu verschlüsseln / entschlüsseln:
%Vor%Ich mag Can Genesers Antwort ; Sie können eine Entschlüsselung nicht ohne den HMAC verifizieren.
Aber wenn Sie einen sehr großen Klartext haben, kann die Entschlüsselung sehr teuer sein. Sie könnten eine Menge Arbeit tun, nur um herauszufinden, dass das Passwort ungültig war. Es wäre schön, in der Lage zu sein, eine schnelle Zurückweisung von falschen Passwörtern zu machen, ohne all diese Arbeit zu erledigen. Es gibt einen Weg mit dem PKCS # 5 PBKDF2 . (Standardisiert in RFC2898 , auf das Ihr c # -Programm in Rfc2898DeriveBytes ).
Normalerweise fordert das Datenprotokoll die Erzeugung des Schlüssels aus einem Passwort und die Verwendung von PBKDF2 mit 1000 Zyklen oder einer bestimmten Anzahl von Sätzen an. Dann vielleicht auch (optional) den Initialisierungsvektor über eine Fortführung desselben Algorithmus.
Um die schnelle Passwort-Überprüfung zu implementieren, generieren Sie zwei weitere Bytes über PBKDF2. Wenn Sie keine IV generieren und verwenden, generieren Sie nur 32 Bytes und behalten Sie die letzten 2. Speichern oder übertragen Sie dieses Bytepaar neben Ihrem Cryptotext. Entschlüsseln Sie auf der Entschlüsselungsseite das Kennwort, generieren Sie den Schlüssel und (möglicherweise wegwerfen) IV, generieren Sie dann die 2 zusätzlichen Bytes und überprüfen Sie sie anhand der gespeicherten Daten. Wenn die Paare nicht übereinstimmen wissen , haben Sie ein falsches Passwort, ohne Entschlüsselung.
Wenn sie übereinstimmen, ist dies keine Garantie dafür, dass das Passwort korrekt ist. Du brauchst dafür immer noch den HMAC des ganzen Klartextes. Aber Sie können sich eine Menge Arbeit und vielleicht sogar die Zeit für die Wandmontage sparen, in den meisten Fällen eines "falschen Passworts" und ohne die Sicherheit des Gesamtsystems zu gefährden.
ps : Sie haben geschrieben:
Der einfachste Weg, den ich mir vorstellen kann, wäre, beim Verschlüsseln eine "magische Zahl" am Anfang der Nachricht zu setzen und zu prüfen, ob sie nach der Entschlüsselung noch da ist.
Vermeiden Sie Klartext in den Cryptotext. Es macht nur einen weiteren Angriffsvektor verfügbar, der es einem Angreifer erleichtert, falsche Wendungen zu eliminieren. Die oben erwähnte Passwortverifikation ist ein anderes Tier, stellt dieses Risiko nicht dar.
Ich benutze diesen Code, um jede Datei zu entschlüsseln. Falsches Passwort in cryptostream.close()
erkannt. Fangen Sie diese Zeile als Fehler, wenn ein falscher Schlüssel zum Entschlüsseln der Datei verwendet wird. Wenn ein Fehler auftritt, schließen Sie einfach den Ausgabestream und geben Sie ihn frei (setzen Sie outputFile
auf Nothing
), und löschen Sie dann die Ausgabedatei. Es funktioniert für mich.
Tags und Links c# encryption encryption-symmetric rijndael rijndaelmanaged