none
Passwort sicher im Quelltext hinterlegen RRS feed

  • Frage

  • Hallo zusammen,

    ich komme bei folgendem Problem nicht weiter. Wie kann ich in einer .NET Applikation eine Zeichenkette hart kodieren, ohne dass diese,

    durch z. B. .net refector, aus der assembly wieder ausgelesen werden kann.

    Die Anwendung ver- und entschlüsslt z. B. Konfigurationsdateien mit AES.

    Weiß jemand rat?

    Vielen Dank

    3b

    Samstag, 13. November 2010 18:41

Antworten

  • Hallo 3b

    > z. B. .net refector, aus der assembly wieder ausgelesen werden kann

    diese Fakten sind bekannt und im Prinzip mal schon 'by design'.

    Entweder du schreibst/verpackst selber den wichtigsten Teil deiner App in (unmanaged) C++ um,
    oder kaufst  (von sehr kleinen Firmen!) fragwürdige Tools wie zB  (ohne Gewähr):
    http://www.eziriz.com/
    welche vom Original- .NET Konzept fast nichts mehr übriglassen.
       (IMHO wenn sogar .NET Framework Dateien verfälscht, dann ist Microsofts Copyright verletzt)

    Mehr:
    http://stackoverflow.com/questions/1276237/preventing-decompilation-of-c-application
    http://stackoverflow.com/questions/2478230/how-can-i-protect-my-net-assemblies-from-decompilation
    http://stackoverflow.com/questions/2525/best-net-obfuscation-tools-strategy
    http://stackoverflow.com/questions/2129442/hiding-the-contents-of-your-compiled-applications-exe-dll-c-code
    http://stackoverflow.com/questions/140750/is-it-possible-to-compile-net-il-code-to-machine-code
    http://stackoverflow.com/questions/71195/should-you-obfuscate-a-commercial-net-application


    Aber schlussendlich hast du auch hier immer native Code der ausgeführt werden muss,
    inklusive Interaktionen mit OS-APIs  (oder Crypto-Providern);
    mit etwas (mehr) Aufwand kann man auch native-Code hacken (disassemblieren, hooks).

    Alternativ, Lösungen wo gar kein kritischer Code mehr auf dem Client läuft,
    etwa Web/Cloud/Virtual/Terminal -Apps/Services usw.

    • Als Antwort markiert 3b Montag, 15. November 2010 18:40
    Sonntag, 14. November 2010 09:22
  • Hallo 3b,

    > Passwort sicher im Quelltext hinterlegen

    Die kurze Antwort: Das geht einfach nicht.

    Die längere Erklärung: Du implizierst öffentlichen Zugriff auf die Assembly und öffentlichen Zugriff auf das Paswort! - Sowohl der Schlüssel (Key) als auch der Initialisierungvektor (IV) müssen bei symmetrischen Verschlüsselungsverfahren wie AES aber vor nichtauthorisierten Benutzern geheim gehalten werden! Sonst ist die ganze Mühe sinnlos. Die Speicherung des Schlüssels oder von anderen sicherheitssensitiven Informationen in einer öffentlichen .NET-Assembly kommt daher gar nicht erst in Frage. Auch nicht in obfuszierter oder binär-steganographischer Form!

    Wenn Dir die Sicherheit Deines Schlüssels am Herzen liegt, würde ich Dir vorschlagen, den symmetrischen Schlüssel und evtl. auch den IV zunächst in eine passwortgeschützte PFX-Datei zu speichern (für jeden Kunden wird die PFX-Datei mit einem eindeutigen Passwort generiert). Diese Datei übermittelst Du z.B. bei der Aktivierung der Software an den berechtigten Empfänger (mit dem öffentlichen Schlüssel des Empfängers verschlüsst und über SSL). Beim Empfänger wird die Datei entschlüsselt und zusätzlich zu den inhärenten Windows-Sicherheitsmechanismen über ACL vor unbefugtem Zugriff geschützt. Das Passwort für die PFX-Datei verschickst Du dem Kunden zeitverzögert über einen anderen, out-of-band Kanal (z.B. Brief, Telefon, E-Mail usw.). Auch wenn das Passwort für die PFX-Datei nun unterwegs abgefangen/abgehört wird, ist es nutzlos wenn die entsprechende PFX-Datei mit dem Schlüssel fehlt. Achtung: Nur das PFX-Passwort ist kundenspezifisch, nicht aber der Schlüssel - sonst könnte Deine Anwendung die verschlüsselten internen Ressourcen nicht entschlüsseln.

    Bleibt noch die Gefahr, dass der Empfänger selbst, der ja ein PFX-Passwort hat, Dein/Euer Vertrauen bewußt oder unbewußt mißbraucht. Hier sollte man sich die Frage stellen, wem denn die verschlüsselten Daten gehören. Gehören die Daten dem Empfänger (z.B. Zugriff auf das eigene Kunden-Konto), ist alles klar, das Szenario geht auf. Stellst Du aber fest, dass Du gerade dabei bist, die Logindaten zu DEINEM Server in möglicherweise unbekannte/feindliche Hände zu übergeben, mußt Du definitiv Halt machen und die Sicherheitsarchitektur Deiner Anwendung überdenken (Du könntest - vergleichsweise - genausogut den Schlüssel auf dem Tresor liegen lassen).

    Wenn Du AES benutzt, ist die Sicherheit Deines Schlüssels von oberster Priorität. Schütze ihn so gut Du kannst und sorge dafür, dass der Empfänger es ebenfalls tut.

    Kryptografische Dienste:
    http://msdn.microsoft.com/de-de/library/92f9ye3s.aspx

    Gruß
    Marcel

    • Als Antwort vorgeschlagen Marcel Roma Montag, 15. November 2010 22:01
    • Als Antwort markiert 3b Mittwoch, 17. November 2010 12:44
    Montag, 15. November 2010 21:49
  • Hallo 3b und Marcel

    ich glaube nicht, dass hier eine noch so raffinierte Verschlüsselung/Schlüsselverwaltung gross/insgesamt hilft.
    Denn schlussendlich muss die (.NET) App ja mit den entschlüsselten Klartextdaten (3b: "Konfigurationsdateien") beginnen produktiv zu arbeiten, und ein Angriff (oder Code-Patch) genau an dieser Stelle ist kaum zu verhindern.
    Mit native Code wird da der Angriff meist (etwas) schwieriger als bei einer pure managed App.

    Schlussendlich reduziert sich das Problem immer auf das ausführen von (hier: gegenseitig)  untrusted, native Code, was bei der gängigen Windows-PC -Plattform mit Software alleine fast nicht zu regeln ist
      (bzw bloss administrativ auf einen zentralen Server des Kundens ausgelagert würde).

    Daher gibt es ja HW-Konzepte wie  (neben USB-Dongles) zB fix eingebaute:
    http://en.wikipedia.org/wiki/Trusted_Platform_Module

    welche wieder ein bisschen mehr Kontrollen ermöglichen  (oft halt gegen etwas weniger Privacy).
    Aber auch hier muss das OS (kernel/driver) mitspielen und müsste daher selber möglichst gegen Manipulationen geschützt sein.
    Dies führt dann aber auch nur weiter von verschlüsselten Festplatten bis verifizierte HW (Mainboard, BIOS).
    Daher gibts etwa ua:
    http://www.intel.com/technology/malwarereduction/

    Und zuletzt könnte ein entspechend ausgerüstetes Labor immer noch auf diversen elektronischen Ebenen angreifen.
    Was dann zur (ab Werk!) vollständig geschützten (versiegelten) Hardware führt, mit zB selbstlöschenden Kryptospeichern beim brechen eines Siegels.

    Mein Praxis-Tipp:
    wenn überhaupt nötig nehme man eine 'einfache' Lösung die den 'Gelegenheits-Dieb' abhält.
    Alle anderen Massnahmen lenken oft nur gerade noch mehr Aufmerksamkeit der Profi-Hacker auf die spezifischen Schwachpunkte einer Architektur/App!
    • Als Antwort markiert 3b Mittwoch, 17. November 2010 12:45
    Montag, 15. November 2010 22:56
  • Hallo Thomas,

    Ich glaube nicht, dass hier eine noch so raffinierte Verschlüsselung/Schlüsselverwaltung gross/insgesamt hilft.
    Denn schlussendlich muss die (.NET) App ja mit den entschlüsselten Klartextdaten (3b: "Konfigurationsdateien") beginnen produktiv zu arbeiten.

    Eine Anwendung ist nur dann als sicher zu betrachten, wenn trotz offengelegter Sicherheitsarchitektur sehr wenig bis keine Angriffsfläche vorhanden ist. "Ein bischen Sicherheit" gibt's nicht. Hinterlegt man den Schlüssel in der Assembly selbst, oder benutzt man einen Obfuscator bietet das keine Sicherheit, sondern nur Verschleierung. Konfigurationsdateien können cryptographisch sicher gespeichert werden (ob ganz, als Datei, oder nur Teile der enthaltenen Information). Aber dafür ist die Wahl des Verschlüsselungsverfahrens sowie die Verwaltung des Schlüssels von oberster Priorität. Erhält der Angreifer physischen Zugriff auf die Maschine und auf die Kommunikationskanäle, ist das Resultat leicht zu erahnen (aber für die Sicherung des Zugangs zur Maschine kann nicht der Programmierer verantwortlich gemacht werden). Dem Angreifer dürfen eben nicht alle Puzzle-Teile in die Hand gedrückt werden.

    Es gibt viele Quellen, die beschreiben, wie Konfigurationsdateien geschützt werden können (z.B: Übersicht über die geschützte Konfiguration), aber nur wenige Quellen, die zeigen, wie der Schlüssel bei einer symmetrischen Verschlüsselung sicher gespeichert werden kann. Ich hab's hier zumindest grob skizziert.


    Gruß
    Marcel

    • Als Antwort markiert 3b Mittwoch, 17. November 2010 12:45
    Dienstag, 16. November 2010 08:29

Alle Antworten

  • Hallo 3b

    > z. B. .net refector, aus der assembly wieder ausgelesen werden kann

    diese Fakten sind bekannt und im Prinzip mal schon 'by design'.

    Entweder du schreibst/verpackst selber den wichtigsten Teil deiner App in (unmanaged) C++ um,
    oder kaufst  (von sehr kleinen Firmen!) fragwürdige Tools wie zB  (ohne Gewähr):
    http://www.eziriz.com/
    welche vom Original- .NET Konzept fast nichts mehr übriglassen.
       (IMHO wenn sogar .NET Framework Dateien verfälscht, dann ist Microsofts Copyright verletzt)

    Mehr:
    http://stackoverflow.com/questions/1276237/preventing-decompilation-of-c-application
    http://stackoverflow.com/questions/2478230/how-can-i-protect-my-net-assemblies-from-decompilation
    http://stackoverflow.com/questions/2525/best-net-obfuscation-tools-strategy
    http://stackoverflow.com/questions/2129442/hiding-the-contents-of-your-compiled-applications-exe-dll-c-code
    http://stackoverflow.com/questions/140750/is-it-possible-to-compile-net-il-code-to-machine-code
    http://stackoverflow.com/questions/71195/should-you-obfuscate-a-commercial-net-application


    Aber schlussendlich hast du auch hier immer native Code der ausgeführt werden muss,
    inklusive Interaktionen mit OS-APIs  (oder Crypto-Providern);
    mit etwas (mehr) Aufwand kann man auch native-Code hacken (disassemblieren, hooks).

    Alternativ, Lösungen wo gar kein kritischer Code mehr auf dem Client läuft,
    etwa Web/Cloud/Virtual/Terminal -Apps/Services usw.

    • Als Antwort markiert 3b Montag, 15. November 2010 18:40
    Sonntag, 14. November 2010 09:22
  • Hallo 3b,

    > Passwort sicher im Quelltext hinterlegen

    Die kurze Antwort: Das geht einfach nicht.

    Die längere Erklärung: Du implizierst öffentlichen Zugriff auf die Assembly und öffentlichen Zugriff auf das Paswort! - Sowohl der Schlüssel (Key) als auch der Initialisierungvektor (IV) müssen bei symmetrischen Verschlüsselungsverfahren wie AES aber vor nichtauthorisierten Benutzern geheim gehalten werden! Sonst ist die ganze Mühe sinnlos. Die Speicherung des Schlüssels oder von anderen sicherheitssensitiven Informationen in einer öffentlichen .NET-Assembly kommt daher gar nicht erst in Frage. Auch nicht in obfuszierter oder binär-steganographischer Form!

    Wenn Dir die Sicherheit Deines Schlüssels am Herzen liegt, würde ich Dir vorschlagen, den symmetrischen Schlüssel und evtl. auch den IV zunächst in eine passwortgeschützte PFX-Datei zu speichern (für jeden Kunden wird die PFX-Datei mit einem eindeutigen Passwort generiert). Diese Datei übermittelst Du z.B. bei der Aktivierung der Software an den berechtigten Empfänger (mit dem öffentlichen Schlüssel des Empfängers verschlüsst und über SSL). Beim Empfänger wird die Datei entschlüsselt und zusätzlich zu den inhärenten Windows-Sicherheitsmechanismen über ACL vor unbefugtem Zugriff geschützt. Das Passwort für die PFX-Datei verschickst Du dem Kunden zeitverzögert über einen anderen, out-of-band Kanal (z.B. Brief, Telefon, E-Mail usw.). Auch wenn das Passwort für die PFX-Datei nun unterwegs abgefangen/abgehört wird, ist es nutzlos wenn die entsprechende PFX-Datei mit dem Schlüssel fehlt. Achtung: Nur das PFX-Passwort ist kundenspezifisch, nicht aber der Schlüssel - sonst könnte Deine Anwendung die verschlüsselten internen Ressourcen nicht entschlüsseln.

    Bleibt noch die Gefahr, dass der Empfänger selbst, der ja ein PFX-Passwort hat, Dein/Euer Vertrauen bewußt oder unbewußt mißbraucht. Hier sollte man sich die Frage stellen, wem denn die verschlüsselten Daten gehören. Gehören die Daten dem Empfänger (z.B. Zugriff auf das eigene Kunden-Konto), ist alles klar, das Szenario geht auf. Stellst Du aber fest, dass Du gerade dabei bist, die Logindaten zu DEINEM Server in möglicherweise unbekannte/feindliche Hände zu übergeben, mußt Du definitiv Halt machen und die Sicherheitsarchitektur Deiner Anwendung überdenken (Du könntest - vergleichsweise - genausogut den Schlüssel auf dem Tresor liegen lassen).

    Wenn Du AES benutzt, ist die Sicherheit Deines Schlüssels von oberster Priorität. Schütze ihn so gut Du kannst und sorge dafür, dass der Empfänger es ebenfalls tut.

    Kryptografische Dienste:
    http://msdn.microsoft.com/de-de/library/92f9ye3s.aspx

    Gruß
    Marcel

    • Als Antwort vorgeschlagen Marcel Roma Montag, 15. November 2010 22:01
    • Als Antwort markiert 3b Mittwoch, 17. November 2010 12:44
    Montag, 15. November 2010 21:49
  • Hallo 3b und Marcel

    ich glaube nicht, dass hier eine noch so raffinierte Verschlüsselung/Schlüsselverwaltung gross/insgesamt hilft.
    Denn schlussendlich muss die (.NET) App ja mit den entschlüsselten Klartextdaten (3b: "Konfigurationsdateien") beginnen produktiv zu arbeiten, und ein Angriff (oder Code-Patch) genau an dieser Stelle ist kaum zu verhindern.
    Mit native Code wird da der Angriff meist (etwas) schwieriger als bei einer pure managed App.

    Schlussendlich reduziert sich das Problem immer auf das ausführen von (hier: gegenseitig)  untrusted, native Code, was bei der gängigen Windows-PC -Plattform mit Software alleine fast nicht zu regeln ist
      (bzw bloss administrativ auf einen zentralen Server des Kundens ausgelagert würde).

    Daher gibt es ja HW-Konzepte wie  (neben USB-Dongles) zB fix eingebaute:
    http://en.wikipedia.org/wiki/Trusted_Platform_Module

    welche wieder ein bisschen mehr Kontrollen ermöglichen  (oft halt gegen etwas weniger Privacy).
    Aber auch hier muss das OS (kernel/driver) mitspielen und müsste daher selber möglichst gegen Manipulationen geschützt sein.
    Dies führt dann aber auch nur weiter von verschlüsselten Festplatten bis verifizierte HW (Mainboard, BIOS).
    Daher gibts etwa ua:
    http://www.intel.com/technology/malwarereduction/

    Und zuletzt könnte ein entspechend ausgerüstetes Labor immer noch auf diversen elektronischen Ebenen angreifen.
    Was dann zur (ab Werk!) vollständig geschützten (versiegelten) Hardware führt, mit zB selbstlöschenden Kryptospeichern beim brechen eines Siegels.

    Mein Praxis-Tipp:
    wenn überhaupt nötig nehme man eine 'einfache' Lösung die den 'Gelegenheits-Dieb' abhält.
    Alle anderen Massnahmen lenken oft nur gerade noch mehr Aufmerksamkeit der Profi-Hacker auf die spezifischen Schwachpunkte einer Architektur/App!
    • Als Antwort markiert 3b Mittwoch, 17. November 2010 12:45
    Montag, 15. November 2010 22:56
  • Hallo Thomas,

    Ich glaube nicht, dass hier eine noch so raffinierte Verschlüsselung/Schlüsselverwaltung gross/insgesamt hilft.
    Denn schlussendlich muss die (.NET) App ja mit den entschlüsselten Klartextdaten (3b: "Konfigurationsdateien") beginnen produktiv zu arbeiten.

    Eine Anwendung ist nur dann als sicher zu betrachten, wenn trotz offengelegter Sicherheitsarchitektur sehr wenig bis keine Angriffsfläche vorhanden ist. "Ein bischen Sicherheit" gibt's nicht. Hinterlegt man den Schlüssel in der Assembly selbst, oder benutzt man einen Obfuscator bietet das keine Sicherheit, sondern nur Verschleierung. Konfigurationsdateien können cryptographisch sicher gespeichert werden (ob ganz, als Datei, oder nur Teile der enthaltenen Information). Aber dafür ist die Wahl des Verschlüsselungsverfahrens sowie die Verwaltung des Schlüssels von oberster Priorität. Erhält der Angreifer physischen Zugriff auf die Maschine und auf die Kommunikationskanäle, ist das Resultat leicht zu erahnen (aber für die Sicherung des Zugangs zur Maschine kann nicht der Programmierer verantwortlich gemacht werden). Dem Angreifer dürfen eben nicht alle Puzzle-Teile in die Hand gedrückt werden.

    Es gibt viele Quellen, die beschreiben, wie Konfigurationsdateien geschützt werden können (z.B: Übersicht über die geschützte Konfiguration), aber nur wenige Quellen, die zeigen, wie der Schlüssel bei einer symmetrischen Verschlüsselung sicher gespeichert werden kann. Ich hab's hier zumindest grob skizziert.


    Gruß
    Marcel

    • Als Antwort markiert 3b Mittwoch, 17. November 2010 12:45
    Dienstag, 16. November 2010 08:29