Advanced   Java   Services Verschlüsseln und Entschlüsseln Back Next Up Home


Grundlagen

Wir unterscheiden zwischen symmetrischer und asymmetrischer Verschlüsselung. Bei der symmetrischen Verschlüsselung verwendet man zum Ver- und Entschlüsseln ein- und denselben Schlüssel. Dieser muß also beiden Parteien bekannt sein. Bei der asymmetrischen Verschlüsselung dagegen gibt es zwei Schlüssel, einen öffentlichen und einen privaten. Jeder, der den öffentlichen Schlüssel hat kann damit Daten verschlüsseln, aber nur wer den privaten Schlüssel hat, kann die Daten wieder entschlüsseln. Wie diese Verschlüsselungen im einzelnen arbeiten wird hier nicht besprochen, hier dazu nur soviel: Bei der Verschlüsselung werden schon länger große Primzahlen verwendet. Das Multiplizieren auch von zwei sehr großen Primzahlen ist relativ einfach, das Zerlegen des entstandenen Produkts aber schwer, wenn man die Faktoren nicht kennt. Hierzu ein Beispiel:

Die beiden größten Primzahlen unter 10000 sind 9967 und 9973, ihr Produkt ist die Zahl 99400891, die abgerundete Wurzel daraus 9969. Um den ganzzahligen Teiler zu finden müßte man alle Zahlen von 2 bis 9969 durchprobieren. Natürlich kann man gerade Zahlen und durch 3 teilbare Zahlen überspringen (Teilungsregeln), aber selbst dann bleiben bei diesem einfachen Beispiel noch über 3000 Zahlen übrig die man durchprobieren müßte. Und natürlich kann man noch sehr viel besser filtern. Nimmt man aber genügend große Primzahlen, so ist ein solcher Brute-Force-Angriff technisch zwar möglich, aber unrealistisch, da er viel zu lange dauert - zumindest solange die Technik nicht soweit fortgeschritten ist, daß eine Zerlegung in angemessener Zeit möglich ist. Sobald dies aber möglich ist, ist es auch möglich noch größere Primzahlen zu finden deren Produkt man noch nicht zerlegen kann - und damit beginnt das Katz- und Mausspiel von vorne.

Eine lesenswerte Einführung zu dieser Thematik findet man auf Wikipedia


Übersicht über Symmetrische Schlüssel



NameseitBlockgröße (bit)Schlüssellängen (bit)EntwicklerLizenz Verwendung durch, Anwendung inQuelle
DES (Data Encryption Standard) 1975 64 56 Weiterentwicklung des maßgeblich von Horst Feistel entwickelten Algorithmus "Lucifer" durch ein Team von Entwicklern bei IBM ? Geldautomaten Data Encryption Standard (wikipedia)
Triple-DES
(3DES, DESede)
1981 64 168 (effektiv 112) Walter Tuchman, Ralph Merkle, Martin Hellman u.a. ? HBCI (home banking computer interface) Triple DES (wikipedia)
Uni Oldenburg
IDEA 1990 64 128 ETH Zürich Ascom Systec Anwendung in PGP International Data Encryption Algorithm (wikipedia)
Blowfish 1993 64 32 bis 448 Bruce Schneider public domain OpenSource-Software (Linux) Blowfish (wikipedia)
Twofish 1999 128 128, 192, 256 Nachfolger von Blowfish
Bruce Schneider, Niels Ferguson, John Kelsey, Doug Whiting, David Wagner, Chris Hall (Schneider empfiewhlt mittlerweile Twofish anzuwenden)
public domain Windows Twofish (wikipedia
AES 2000 128 128, 192, 256 Joan Daemen und Vincent Rijmen public domain in den USA für staatliche Dokumente mit höchster Geheimhaltungsstufe Advanced Encryption Standard (wikipedia)

Siehe auch Verschluesselungs-Algorithmen (www.heise.de)


Java Cryptography Extension

Es gibt in Java eine generelle Einschränkung was die Schlüsselgröße angeht, Java unterstützt per default nur Schlüssel bis 128 bit. Der Grund dafür ist, daß in einigen Ländern Schlüssel mit einer Länge von mehr als 128 bit nicht erlaubt sind (warum wohl... ?). Initialisaiert man also einen KeyGenerator mit mehr als 128 bit, so erhält man die folgende Exception java.security.InvalidKeyException: Illegal key size or default parameters

Will man längere Schlüssel wie etwa Blowfish mit 448 bit, so muß man die Java Cryptography Extension (JCE) Unlimited Strength Jurisdiction Policy Files 8 herunterladen. Die Datei mit dem Namen jce_policy-8.zip enthält einen Ordner UnlimitedJCEPolicyJDK8 mit den Archiven local_policy.jar und US_export_policy.jar. Diese müssen ins Vezeichnis ${java.home}/jre/lib/security/ gebracht werden. Diese jar-Dateien enthalten keinen Bytecode sondern Textdateien, die mit grant Rechte vergeben oder einschränken.

Das Verzeichnis enthält bereits diese zwei Dateien jedoch mit teilweise anderem Inhalt. Bei der Installation der JRE muß auf länderspezifische Gegebenheiten Rücksicht genommen werden, da nicht in allen Ländern alle Schlüssellängen erlaubt sind. So sind in der Datei default_local.policy Einschränkungen, damit die JRE in allen Ländern installiert werden kann. Die Standarddatei sieht daher folgendermaßen aus:

// Some countries have import limits on crypto strength. This policy file
// is worldwide importable.

grant {
    permission javax.crypto.CryptoPermission "DES", 64;
    permission javax.crypto.CryptoPermission "DESede", *;
    permission javax.crypto.CryptoPermission "RC2", 128,
                                     "javax.crypto.spec.RC2ParameterSpec", 128;
    permission javax.crypto.CryptoPermission "RC4", 128;
    permission javax.crypto.CryptoPermission "RC5", 128,
          "javax.crypto.spec.RC5ParameterSpec", *, 12, *;
    permission javax.crypto.CryptoPermission "RSA", *;
    permission javax.crypto.CryptoPermission *, 128;
};

Die von Oracle heruntergeladene Datei default_local.policy vergibt hier deutlich mehr Rechte:

// Country-specific policy file for countries with no limits on crypto strength.
grant {
    // There is no restriction to any algorithms.
    permission javax.crypto.CryptoAllPermission;
};

Wenn man das weiß kann man natürlich auch einfach die vorhandene policy-Datei entsprechend editieren.

Siehe auch    stackoverflow - java-security-invalidkeyexception   und   stackoverflow - java-security-illegal-key-size


Ver- und Entschlüsseln am Beispiel des BlowFish-Algorithmus

Wir zeigen das Vorgehen an Hand des BlowFish-Algorithmus. Für andere symmetrische Algorithmen kann man im Wesentlichen geauso vorgehen.

Man kann das Vorgehen in Java in die folgende Schritte einteilen

  1. Einen KeyGenerator für eine bestimmte Art der Verschluesselung generieren.
  2. KeyGenerator initialisieren.
  3. Key erzeugen
  4. Cipherinstanz zum gewählten Verschlüsselungsalgorithmus erzeugen
  5. Verschlüsselungsmodus einschalten und das in Schritt 3 erzeugte Keyobjekt übergeben
  6. Daten in ein Bytearray verwandeln und mit der Methode doFinal verschlüsseln
  7. Verschlüsseltes Bytearray senden
  8. Bytearray entschlüsseln

Die Umsetzung im Einzelnen

private static void blowFish()
{
// Verschluesseln mit einem privaten symmetrischen schlüssel

  try
  {
     // Schritt 1: Einen KeyGenerator für eine bestimmte Art der Verschluesselung generieren. (caseINsensitiv)
     KeyGenerator blowFishKG = KeyGenerator.getInstance("BlowFish"); // NoSuchAlgorithmException
     // Infos
     System.out.println("Info KeyGenerator");                // javax.crypto.KeyGenerator@10421f5
     System.out.println("Class:     " + blowFishKG);                // javax.crypto.KeyGenerator@10421f5
     System.out.println("Algorithm: " + blowFishKG.getAlgorithm()); // BlowFish
     System.out.println("Provider:  " + blowFishKG.getProvider());  // SunJCE version 1.8
     System.out.println();

     // Schritt 2: Den KeyGenerator initialisieren.
     // init kann entfallen, dann wird ein Standardwert genommen, welcher ???
     // Keysize must be multiple of 8, and can only range from 32 to 448 (inclusive)
     // JCE installiert, dann geht es bis 448
     // es gibt 5 init()-Methoden, hioer wird die einfachste verwendet
     blowFishKG.init(448); // InvalidParameterException:

     // Schritt 3: Key erzeugen
     SecretKey  secretKey =  blowFishKG.generateKey();
     // Infos
     System.out.println("Info SecretKey");                // javax.crypto.KeyGenerator@10421f5
     System.out.println("Class:     " + secretKey.getClass()); // class javax.crypto.spec.SecretKeySpec
     System.out.println("Algorithm: " + secretKey.getAlgorithm()); // class javax.crypto.spec.SecretKeySpec
     System.out.println("Format:    " + secretKey.getFormat()); // class javax.crypto.spec.SecretKeySpec
     System.out.println();

     // Schritt 4: Cipherinstanz zum gewählten Verschlüsselungsalgorithmus erzeugen
     Cipher cipher = Cipher.getInstance("BlowFish"); // NoSuchPaddingException
     //Infos
     System.out.println("Info Cipher");                // javax.crypto.KeyGenerator@10421f5
     System.out.println("Class:     " + cipher.getClass()); //
     System.out.println("Algorithm: " + cipher.getAlgorithm());
     System.out.println("BlockSize: " + cipher.getBlockSize());
     System.out.println();

     // Schritt 5: Verschlüsselungsmodus einschalten und das in Schritt 3 erzeugte Keyobjekt übergeben
     cipher.init(Cipher.ENCRYPT_MODE, secretKey); // InvalidKeyException
     // wenn man init wegläßt, dann IllegalStateException: Cipher not initialized

     // Schritt 6: Daten in ein Bytearray verwandeln und mit der Methode doFinal verschlüsseln
     System.out.println("Info Data");
     String klarText = "Der Mensch kann zwar tun was er will, aber er kann nicht wollen, was er will. [Arthur Schopenhauer (1788  1860)]";
     System.out.println("Text to encrypt:           " + klarText);
     byte[] arrayToEncrypt = klarText.getBytes();
     byte[] encryptedArray = cipher.doFinal(klarText.getBytes()); // IllegalBlockSizeException, BadPaddingException
     System.out.println("Array to Encrypt length:   " + arrayToEncrypt.length);
     System.out.println("Encrypted Array length:    " + encryptedArray.length);

     // verschlüsselten String ausgeben
     String encryptedString = new String(encryptedArray);  //
     System.out.println("Encrypted Bytes as String:\n" + encryptedString);
     System.out.println();

     // Schritt 7: Verschlüsseltes Bytearray senden...

     // Schritt 8: Entschlüsseln
     cipher.init(Cipher.DECRYPT_MODE, secretKey); // InvalidKeyException
     byte[] decryptedArray = cipher.doFinal(encryptedArray); // IllegalBlockSizeException, BadPaddingException
     String decryptedString = new String(decryptedArray);
     System.out.println("Info Decrypt");
     System.out.println("Decrypted Array length: " + decryptedArray.length);
     System.out.println("Decrypted String:       " + decryptedString);
  }
  catch(NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException  ex)
  {
     ex.printStackTrace();
  }
}

Eine mögliche Ausgabe

Info KeyGenerator
Class:     javax.crypto.KeyGenerator@10421f5
Algorithm: BlowFish
Provider:  SunJCE version 1.8

Info SecretKey
Class:     class javax.crypto.spec.SecretKeySpec
Algorithm: Blowfish
Format:    RAW

Info Cipher
Class:     class javax.crypto.Cipher
Algorithm: BlowFish
BlockSize: 8

Info Data
Text to encrypt:           Der Mensch kann zwar tun was er will, aber er kann nicht wollen, was er will. [Arthur Schopenhauer (1788  1860)]
Array to Encrypt length:   113
Encrypted Array length:    120
Encrypted Bytes as String:
gR36̠᱉ÄXmԣq:?>׳?u|\n0s?2AZFK
                                                                           e2/s
                                                                                       VP
Info Decrypt
Decrypted Array length: 113
Decrypted String:       Der Mensch kann zwar tun was er will, aber er kann nicht wollen, was er will. [Arthur Schopenhauer (1788  1860)]

Vor- und Nachteile der symmetrischen Verschlüsselung

Übersicht über asymmetrische Schlüssel

Auf den mathematischen Hintergrund wird hier nicht eingegangen. Einiges dazu findet man unter den in der Tabelle angegeben Links zu Wikipedia.

NameseitEntwicklerQuelle
Diffie-Hellman 1976 Whitfield Diffie, Martin Hellman, Ralph Merkle. Diffie-Hellman Schlüsselaustausch (wikipedia)
RSA 1977 Ronald L. Rivest, Adi Shamir und Leonard Adleman RSA Encryption (wikipedia)
Merkle-Hellman 1978 Ralph Merkle, Martin Hellman u.a. Merkle-Hellman Encryption (wikipedia)
McEliece 1978 Robert J. McEliece McEliece Encryption (wikipedia)
Rabin 1979 Michael O. Rabin Rabin Encryption(wikipedia)
Chor-Rivest 1984 Chor-Rivest Encryption
Elgamal 1985 Taher Elgamal Elgamal Encryption (wikipedia)


Ver- und Entschlüsseln am Beispiel des RSA-Algorithmus

Wir zeigen das Vorgehen an Hand des RSA-Algorithmus. Der Unterschied zum ersten Fall ist im wesentlichen, daß nun zwei Schlüssel erzeugt werden, ein öffentlicher und ein privater.

Man kann das Vorgehen in Java in die folgende Schritte einteilen

  1. Einen KeyPairGenerator für eine bestimmte Art der Verschlüsselung generieren.
  2. KeyPairGenerator initialisieren.
  3. PublicKey und PrivateKey erzeugen
  4. Cipherinstanz zum gewählten Verschlüsselungsalgorithmus erzeugen
  5. Verschlüsselungsmodus einschalten und das in Schritt 3 erzeugte PublicKeyobjekt übergeben
  6. Daten in ein Bytearray verwandeln und mit der Methode doFinal verschlüsseln
  7. Verschlüsseltes Bytearray senden
  8. Bytearray mit Hilfe des PrivateKey entschlüsseln

Die Umsetzung im Einzelnen

 private static void rsa()
 {
    try
    {
       // Schritt 1: Einen KeyPairGenerator für eine bestimmte Art der Verschluesselung generieren.
       // caseINsensitiv
       KeyPairGenerator rsaKPG = KeyPairGenerator.getInstance("RSA"); // NoSuchAlgorithmException
       // Infos
       System.out.println("Info KeyPairGenerator");
       System.out.println("Class:     " + rsaKPG);                // java.security.KeyPairGenerator$Delegate
       System.out.println("Algorithm: " + rsaKPG.getAlgorithm()); // RSA
       System.out.println("Provider:  " + rsaKPG.getProvider());  // SunRsaSign version 1.8
       System.out.println();

       // Schriit 2: Den KeyPairGenerator initialisieren mit der Methode initialize()
       // es gibt 4 initialize()-Methoden, hier wird die einfachste verwendet
       // Methode kann entfallen, dann wird als Standardwert 1024 genommen
       rsaKPG.initialize(2048);  // Bitlänge des Modulos
       // java.security.InvalidParameterException: RSA keys must be at least 512 bits long
       // Die Größe des Modulos bestimmt die Länge des zu verschlüsselnden Textes
       // Mit einer Bitlänge von 800 etwa kann man nur Texte bis 102 byte Länge verschlüsseln

       // Schritt 3a: KeyPair erzeugen
       KeyPair kp = rsaKPG.generateKeyPair();

       // Schritt 3b: PublicKey erzeugen
       Key publicKey = kp.getPublic();
       System.out.println("Info PublicKey");
       System.out.println("Class:     " + publicKey.getClass());     // sun.security.rsa.RSAPublicKeyImpl
       System.out.println("toString:  " + publicKey);
       System.out.println("Algorithm: " + publicKey.getAlgorithm()); // RSA
       System.out.println("Format:    " + publicKey.getFormat());    // X.509
       System.out.println();

       // Schritt 3c: PrivateKey erzeugen
       Key privateKey = kp.getPrivate();
       System.out.println("Info PrivateKey");
       System.out.println("Class:     " + privateKey);             // sun.security.rsa.RSAPrivateCrtKeyImpl

       System.out.println("Format:    " + privateKey.getFormat()); // PKCS#8
       System.out.println();

       // Schritt 4: Cipherinstanz zum gewählten Verschlüsselungsalgorithmus erzeugen
       Cipher cipher = Cipher.getInstance("RSA"); // NoSuchPaddingException

       // Schritt 5: Verschlüsselungsmodus einschalten und das in Schritt 3 erzeugte PublicKey-Objekt übergeben
       cipher.init(Cipher.ENCRYPT_MODE, publicKey);  // InvalidKeyException
       // wenn man init wegläßt, dann IllegalStateException: Cipher not initialized

       // Schritt 6: Daten in ein Bytearray verwandeln und mit der Methode doFinal verschlüsseln
       String klarText = "Der Mensch kann zwar tun was er will, aber er kann nicht wollen, was er will. [Arthur Schopenhauer (1788  1860)]";
       System.out.println("Text to encrypt:           " + klarText);
       byte[] arrayToEncrypt = klarText.getBytes();
       System.out.println("Array to Encrypt length:   " + arrayToEncrypt.length);
       byte[] encryptedArray = cipher.doFinal(klarText.getBytes()); // IllegalBlockSizeException, BadPaddingException
       System.out.println("Encrypted Array length:    " + encryptedArray.length);

       // verschlüsselten String ausgeben
       String encryptedString = new String(encryptedArray);  //
       System.out.println("Encrypted Bytes as String: " + encryptedString);
       System.out.println();

       // Schritt 7: verschlüsseltes Bytearray senden...

       // Schritt 8: Entschlüsseln
       cipher.init(Cipher.DECRYPT_MODE, privateKey); // InvalidKeyException
       byte[] decryptedArray = cipher.doFinal(encryptedArray); // IllegalBlockSizeException, BadPaddingException
       String decryptedString = new String(decryptedArray);
       System.out.println("Info Decrypt");
       System.out.println("Decrypted Array length: " + decryptedArray.length);
       System.out.println("Decrypted String:       " + decryptedString);
    }
    catch(NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException ex)
    {
       ex.printStackTrace();
    }
 }

Eine mögliche Ausgabe

Info KeyPairGenerator
Class:     java.security.KeyPairGenerator$Delegate@139a55
Algorithm: RSA
Provider:  SunRsaSign version 1.8

Info PublicKey
Class:     class sun.security.rsa.RSAPublicKeyImpl
toString:  Sun RSA public key, 2048 bits
modulus:   2583465803882812016436925079346213543584359728787861396798624130481322147905244512181455917214667104
           5377297261986481529401723697704778245537672061378534631213496311201198395324579833978194246741494777
           6288823900060794631681491362898516036246404029159316973980261192672349396383432278022040809193788386
           8171452012271173419442180809264349123094517891162282880649375597850077760633083138372848698198508432
           8345584819405686686373455565242627648975732550000152576669486358027910634460368800739199769074027974
           9705646012825420075404566466322336375039793397203082543078798019198406135876254693057424300998631891
           59763912388112187
public exponent: 65537
Algorithm: RSA
Format:    X.509

Info PrivateKey
Class:  sun.security.rsa.RSAPrivateCrtKeyImpl@fff2e0e5
Format: PKCS#8

Text to encrypt:           Der Mensch kann zwar tun was er will, aber er kann nicht wollen, was er will. [Arthur Schopenhauer (1788  1860)]
Array to Encrypt length:   113
Encrypted Array length:    256
Encrypted Bytes as String:
+㋅x?O5d˜ünö4H]XÖ|J8Ö?sz*7Änكh2%?tz\G%7<8TQC&
ﷲ9,7έ?YCÖ(7<??PHҴ0 \i'|19ÖT,sc=J)F!TK

Info Decrypt
Decrypted Array length: 113
Decrypted String:       Der Mensch kann zwar tun was er will, aber er kann nicht wollen, was er will. [Arthur Schopenhauer (1788  1860)]

Vor- und Nachteile der asymmetrischen Verschlüsselung

Performancevergleich

Selbst bei diesen kleinen Beispielprogrammen stützt ein Performancevergleich die Aussagen über die Zeitdauer des Verschlüsselns und Entschlüsselns, in beiden Beispielen wurde ja der gleiche String verschlüsselt. Hier die Zeiten für jeweils fünf Abläufe (in Eclipse)


BlowFish
BlowFish Dauer Verschlüsseln : 312 ms
BlowFish Dauer Entschlüsseln : 0 ms

BlowFish Dauer Verschlüsseln : 296 ms
BlowFish Dauer Entschlüsseln : 0 ms

BlowFish Dauer Verschlüsseln : 343 ms
BlowFish Dauer Entschlüsseln : 0 nanosec

BlowFish Dauer Verschlüsseln : 297 ms
BlowFish Dauer Entschlüsseln : 0 nanosec

BlowFish Dauer Verschlüsseln : 297 ms
BlowFish Dauer Entschlüsseln : 0 nanosec

RSA
RSA Dauer Verschlüsseln : 1389 ms
RSA Dauer Entschlüsseln : 32 ms
Gesamt : 1421

RSA Dauer Verschlüsseln : 1935 ms
RSA Dauer Entschlüsseln : 32 ms
Gesamt : 1967

RSA Dauer Verschlüsseln : 1154 ms
RSA Dauer Entschlüsseln : 31 ms
Gesamt : 1185

RSA Dauer Verschlüsseln : 4088 ms
RSA Dauer Entschlüsseln : 47 ms
Gesamt : 4135

RSA Dauer Verschlüsseln : 983 ms
RSA Dauer Entschlüsseln : 31 ms
Gesamt : 1014

Man sieht sieht klar, daß RSA deutlich langsamer ist als BlowFish.


Hybride Verschlüsselung

Die hybride Verschlüsselung kombiniert die symmetrische und die asymmetrische Verschlüsselung und beseitigt damit die Nachteile beider Verfahren.

Bei der asymmetrischen Verschlüsselung erzeugt man einen öffentliche und einen privaten Schlüssel, den für eine symmetrische Verschlüsselung erzeugte Schlüssel nennen wir den geheimen Schlüssel. Mit dem geheimen Schlüssel werden die Daten verschlüsselt. Das Problem ist nun, daß der geheime Schlüssel dem Partner übermittelt werden muß. Dazu verwendet man das asymmetrische Schlüsselpaar indem man den geheimen Schlüssel asymmetrisch verschlüsselt und so verschickt.

Im folgenden werden zwei Varianten eines Schlüsseltausches beschrieben. Die Ausgangssituation ist in beiden Fällen dieselbe.

Ausgangssituation:

Alice                    möchte an Bob geheime Daten senden                             Bob
        ------------------------------------------------------------------------------>

Variante 1

In der ersten Variante erzeugt Alice den geheimen und Bob den öffentlichen Schlüssel.

Schritt 1:

Alice                                                                                   Bob
erzeugt geheimen Schlüssel                                                              erzeugt asymmetrisches Schlüsselpaar

Schritt 2:

Alice                   Bob gibt Alice den öffentlichen Schlüssel                       Bob
        <------------------------------------------------------------------------------

Schritt 3:

Alice                                                                                    Bob
verschlüsselt ihre Daten mit ihrem
geheimen Schlüssel UND den geheimen
Schlüssel mit dem öffentlichen Schlüssel

Schritt 4:

Alice           schickt verschlüsselte Daten und verschlüsselten Schlüssel an           Bob
        ------------------------------------------------------------------------------>

Schritt 5:

Alice                                                                                    Bob
                                                                                         entschlüsselt mit privaten Schlüssel den
                                                                                         geheimen Schlüssel und mit diesem die Daten

Variante 2

Nun die zweite Variante. Hier ist es genau umgekehrt, Alice erzeugt den asymmetrischen und Bob den symmetrischjen Schlüssel.

Schritt 1:

Alice                                                                                   Bob
erzeugt asymmetrisches Schlüsselpaar                                                    erzeugt geheimen Schlüssel

Schritt 2:

Alice                   Alice gibt Bob den öffentlichen Schlüssel                       Bob
        ------------------------------------------------------------------------------>

Schritt 3:

Alice                                                                                    Bob
                                                                                         verschlüsselt mit dem öffentlichen Schlüssel
                                                                                         den geheimen Schlüssel
                  Bob schickt den verschlüsselten geheimen Schlüssel an Alice
        <------------------------------------------------------------------------------

Schritt 4:

Alice entschlüsselt den geheimen Schlüssel
und verschlüsselt damit ihre Daten

Schritt 5:

Alice                         schickt verschlüsselte Daten                               Bob
        ------------------------------------------------------------------------------>
                                                                                         entschlüsselt mit dem geheimen Schlüssel
                                                                                         die Daten
Valid XHTML 1.0 Strict top Back Next Up Home