Vorgehensweise: Entschlüsseln von XML-Elementen mit asymmetrischen Schlüsseln

Sie können die Klassen im System.Security.Cryptography.Xml-Namespace verwenden, um ein Element in einem XML-Dokument zu verschlüsseln und zu entschlüsseln. XML-Verschlüsselung ist ein gängiges Verfahren zum Austauschen oder Speichern von verschlüsselten XML-Daten, ohne sich Gedanken machen zu müssen, dass die Daten einfach gelesen werden können. Weitere Informationen zum XML-Verschlüsselungsstandard, finden Sie in der W3C-Empfehlung (World Wide Web Consortium) XML Signature Syntax and Processing.

Hinweis

Der Code in diesem Artikel gilt für Windows.

Im Beispiel in dieser Vorgehensweise wird ein XML-Element entschlüsselt, das mithilfe der unter Vorgehensweise: Verschlüsseln von XML-Elementen mit asymmetrischen Schlüsseln beschriebenen Methoden verschlüsselt wurde. Im Beispiel wird ein <EncryptedData>-Element gesucht, wird dieses Element entschlüsselt, und wird das Element dann durch das ursprüngliche Klartext-XML-Element ersetzt.

In diesem Beispiel wird ein XML-Element mithilfe zweier Schlüssel entschlüsselt. Ein zuvor generierter privater RSA-Schlüssel wird aus einem Schlüsselcontainer abgerufen. Anschließend wird der RSA-Schlüssel verwendet, um einen Sitzungsschlüssels zu entschlüsseln, der im <EncryptedKey>-Element des <EncryptedData>-Elements gespeichert ist. In dem Beispiel wird dann der Sitzungsschlüssel verwendet, um das XML-Element zu entschlüsseln.

Das Beispiel eignet sich für Situationen, in denen mehrere Anwendungen verschlüsselte Daten gemeinsam nutzen müssen, oder in denen eine Anwendung verschlüsselte Daten zwischen den Zeiten speichern muss, in denen sie ausgeführt wird.

So entschlüsseln Sie ein XML-Element mit einem asymmetrischen Schlüsseln

  1. Erstellen Sie ein CspParameters-Objekt, und geben Sie den Namen des Schlüsselcontainers an.

    CspParameters cspParams = new CspParameters();
    cspParams.KeyContainerName = "XML_ENC_RSA_KEY";
    
    Dim cspParams As New CspParameters()
    cspParams.KeyContainerName = "XML_ENC_RSA_KEY"
    
  2. Rufen Sie einen zuvor generierten asymmetrischen Schlüssel aus dem Schlüsselcontainer mithilfe des RSACryptoServiceProvider-Objekts ab. Der Schlüssel wird automatisch aus dem Schlüsselcontainer abgerufen, wenn Sie das CspParameters-Objekt an den RSACryptoServiceProvider-Konstruktor übergeben.

    RSACryptoServiceProvider rsaKey = new RSACryptoServiceProvider(cspParams);
    
    Dim rsaKey As New RSACryptoServiceProvider(cspParams)
    
  3. Erstellen Sie ein neues EncryptedXml-Objekt, um das Dokument zu entschlüsseln.

    // Create a new EncryptedXml object.
    EncryptedXml exml = new EncryptedXml(Doc);
    
    ' Create a new EncryptedXml object.
    Dim exml As New EncryptedXml(Doc)
    
  4. Fügen Sie eine Schlüssel/Name-Zuordnung hinzu, um den RSA-Schlüssel dem Element im Dokument zuzuordnen, das entschlüsselt werden soll. Sie müssen für den Schlüssel den Namen verwenden, den Sie beim Verschlüsseln des Dokuments verwendet haben. Beachten Sie, dass dieser Name nicht mit dem Namen identisch ist, mit dem der Schlüssel in dem Schlüsselcontainer identifiziert wird, der in Schritt 1 angegeben wurde.

    exml.AddKeyNameMapping(KeyName, Alg);
    
    exml.AddKeyNameMapping(KeyName, Alg)
    
  5. Rufen Sie die DecryptDocument-Methode auf, um das <EncryptedData>-Element zu entschlüsseln. Diese Methode verwendet den RSA-Schlüssel, um den Sitzungsschlüssel zu entschlüsseln, und verwendet diesen dann automatisch, um das XML-Element zu entschlüsseln. Außerdem ersetzt die Methode automatisch das <EncryptedData>-Element durch den ursprünglichen Klartext.

    exml.DecryptDocument();
    
    exml.DecryptDocument()
    
  6. Speichern Sie das XML-Dokument.

    xmlDoc.Save("test.xml");
    
    xmlDoc.Save("test.xml")
    

Beispiel

Für dieses Beispiel wird angenommen, dass eine Datei namens test.xml im selben Verzeichnis wie das kompilierte Programm vorhanden ist. Außerdem wird angenommen, dass test.xml ein XML-Element enthält, das mithilfe der unter Vorgehensweise: Verschlüsseln von XML-Elementen mit asymmetrischen Schlüsseln beschriebenen Methoden verschlüsselt wurde.


using System;
using System.Xml;
using System.Security.Cryptography;
using System.Security.Cryptography.Xml;
using System.Runtime.Versioning;

[SupportedOSPlatform("windows")]
class Program
{
    static void Main(string[] args)
    {
        // Create an XmlDocument object.
        XmlDocument xmlDoc = new XmlDocument();

        // Load an XML file into the XmlDocument object.
        try
        {
            xmlDoc.PreserveWhitespace = true;
            xmlDoc.Load("test.xml");
        }
        catch (Exception e)
        {
            Console.WriteLine(e.Message);
        }
        CspParameters cspParams = new CspParameters();
        cspParams.KeyContainerName = "XML_ENC_RSA_KEY";

        // Get the RSA key from the key container.  This key will decrypt
        // a symmetric key that was imbedded in the XML document.
        RSACryptoServiceProvider rsaKey = new RSACryptoServiceProvider(cspParams);

        try
        {

            // Decrypt the elements.
            Decrypt(xmlDoc, rsaKey, "rsaKey");

            // Save the XML document.
            xmlDoc.Save("test.xml");

            // Display the encrypted XML to the console.
            Console.WriteLine();
            Console.WriteLine("Decrypted XML:");
            Console.WriteLine();
            Console.WriteLine(xmlDoc.OuterXml);
        }
        catch (Exception e)
        {
            Console.WriteLine(e.Message);
        }
        finally
        {
            // Clear the RSA key.
            rsaKey.Clear();
        }

        Console.ReadLine();
    }

    public static void Decrypt(XmlDocument Doc, RSA Alg, string KeyName)
    {
        // Check the arguments.
        if (Doc == null)
            throw new ArgumentNullException("Doc");
        if (Alg == null)
            throw new ArgumentNullException("Alg");
        if (KeyName == null)
            throw new ArgumentNullException("KeyName");
        // Create a new EncryptedXml object.
        EncryptedXml exml = new EncryptedXml(Doc);

        // Add a key-name mapping.
        // This method can only decrypt documents
        // that present the specified key name.
        exml.AddKeyNameMapping(KeyName, Alg);

        // Decrypt the element.
        exml.DecryptDocument();
    }
}
Imports System.Xml
Imports System.Security.Cryptography
Imports System.Security.Cryptography.Xml

Module Program

    Sub Main(ByVal args() As String)

        ' Create an XmlDocument object.
        Dim xmlDoc As New XmlDocument()

        ' Load an XML file into the XmlDocument object.
        Try
            xmlDoc.PreserveWhitespace = True
            xmlDoc.Load("test.xml")
        Catch e As Exception
            Console.WriteLine(e.Message)
        End Try
        Dim cspParams As New CspParameters()
        cspParams.KeyContainerName = "XML_ENC_RSA_KEY"
        ' Get the RSA key from the key container.  This key will decrypt 
        ' a symmetric key that was imbedded in the XML document. 
        Dim rsaKey As New RSACryptoServiceProvider(cspParams)
        Try

            ' Decrypt the elements.
            Decrypt(xmlDoc, rsaKey, "rsaKey")

            ' Save the XML document.
            xmlDoc.Save("test.xml")
            ' Display the encrypted XML to the console.
            Console.WriteLine()
            Console.WriteLine("Decrypted XML:")
            Console.WriteLine()
            Console.WriteLine(xmlDoc.OuterXml)
        Catch e As Exception
            Console.WriteLine(e.Message)
        Finally
            ' Clear the RSA key.
            rsaKey.Clear()
        End Try


        Console.ReadLine()

    End Sub



    Sub Decrypt(ByVal Doc As XmlDocument, ByVal Alg As RSA, ByVal KeyName As String)
        ' Check the arguments.  
        ArgumentNullException.ThrowIfNull(Doc)
        ArgumentNullException.ThrowIfNull(Alg)
        ArgumentNullException.ThrowIfNull(KeyName)

        ' Create a new EncryptedXml object.
        Dim exml As New EncryptedXml(Doc)
        ' Add a key-name mapping.
        ' This method can only decrypt documents
        ' that present the specified key name.
        exml.AddKeyNameMapping(KeyName, Alg)
        ' Decrypt the element.
        exml.DecryptDocument()
    End Sub
End Module

Kompilieren des Codes

.NET-Sicherheit

Speichern Sie einen symmetrischen kryptografischen Schlüssel nie im Klartextformat, und übertragen Sie einen symmetrischen Schlüssel nie im Klartextformat zwischen Computern. Außerdem sollten Sie den privaten Schlüssel eines asymmetrischen Schlüsselpaars niemals in Klartext speichern oder übertragen. Weitere Informationen zu symmetrischen und asymmetrischen kryptografischen Schlüsseln finden Sie unter Generieren von Schlüsseln für die Verschlüsselung und Entschlüsselung.

Sie sollten einen Schlüssel niemals direkt in Ihren Quellcode einbetten. Eingebettete Schlüssel können problemlos aus einer Assembly gelesen werden, indem Sie Ildasm.exe (IL-Disassembler) verwenden oder die Assembly in einem Text-Editor öffnen.

Wenn Sie einen kryptografischen Schlüssel nicht mehr benötigen, entfernen Sie ihn aus dem Arbeitsspeicher, indem Sie jedes Byte auf 0 (null) festlegen oder indem Sie die Clear-Methode der verwalteten Kryptografieklasse aufrufen. Kryptografische Schlüssel können manchmal von einem Debugger aus dem Arbeitsspeicher oder von einer Festplatte gelesen werden, falls der entsprechende Arbeitsspeicherbereich auf den Datenträger ausgelagert wurde.

Weitere Informationen