DiffieHellman密钥交换到AES或DESede在Java中

时间:2014-11-09 13:23:42

标签: java encryption cryptography aes

代码使用DiffieHellman和DES加密。 DES不安全,我想使用DESede或AES。

SecretKeyFactory skf = SecretKeyFactory.getInstance("DESede");

SecretKeyFactory skf = SecretKeyFactory.getInstance("AES");

两者都失败了

SecretKeyFactory skf = SecretKeyFactory.getInstance("DES");
然而

工作(但是指出太弱了) 这是我的模块代码(下面的testclass)目前使用已实现的" DES"

import java.security.AlgorithmParameterGenerator;
import java.security.AlgorithmParameters;
import java.security.InvalidAlgorithmParameterException;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.spec.InvalidParameterSpecException;

import javax.crypto.KeyAgreement;
import javax.crypto.SecretKey;
import javax.crypto.SecretKeyFactory;
import javax.crypto.spec.DESKeySpec;
import javax.crypto.spec.DHParameterSpec;

/**
 * Diffie-Hellman module for demonstrating KeyAgreement Algorithm
 */
public class DiffieHellmanModule {
    private static KeyPairGenerator kpg;
    static {        
        try {
            // Create the parameter generator for a 512-bit DH key pair
            AlgorithmParameterGenerator paramGen = AlgorithmParameterGenerator.getInstance("DH");
            paramGen.init(512);
            // Generate the parameters Prime p and root g
            AlgorithmParameters params = paramGen.generateParameters();
            // Use the params p and g to create a DiffieHellmanSpec
            DHParameterSpec dhSpec
                = (DHParameterSpec)params.getParameterSpec(DHParameterSpec.class);
            //Generates and inits a KeyPairGenerator
            kpg = KeyPairGenerator.getInstance("DH");
            kpg.initialize(dhSpec);
        } catch (NoSuchAlgorithmException | InvalidAlgorithmParameterException e) {
            e.printStackTrace();
        } catch (InvalidParameterSpecException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

    /**
     * Create KeyAgreement and generate secret key
     * 
     * @param prk_self
     *            the private key from the user who wants to generate the secret
     *            key
     * @param pbk_peer
     *            the public key from the user whom is to be agree on the secret
     *            key with
     * @param lastPhase
     *            flag which indicates whether or not this is the last phase of
     *            this key agreement
     * @return the secret key
     */
    public static SecretKey agreeSecretKey(PrivateKey prk_self,
            PublicKey pbk_peer, boolean lastPhase) throws Exception {
     // instantiates and inits a KeyAgreement
        KeyAgreement ka = KeyAgreement.getInstance("DH");
        ka.init(prk_self);
     // Computes the KeyAgreement
        ka.doPhase(pbk_peer, lastPhase);
     // Generates the shared secret
        byte[] bkey = ka.generateSecret();
     // Generates a DES key
        SecretKeyFactory skf = SecretKeyFactory.getInstance("DES");
        DESKeySpec desSpec = new DESKeySpec(bkey);
        SecretKey key = skf.generateSecret(desSpec);
        return key;
        //return new SecretKeySpec(bkey, "AES");
    }

    /**
     * Generate a key pair of algorithm "DiffieHellman"
     * 
     * @return the public and private key pair
     */
    public static KeyPair genDHKeyPair() {
        return kpg.genKeyPair();
    }
}

识别TestClass

import java.security.KeyPair;
import java.security.PrivateKey;
import java.security.PublicKey;

import javax.crypto.Cipher;
import javax.crypto.SecretKey;

public class DHTest {

    public static void main(String[] args) {
        //Generates keyPairs for Alice and Bob
        KeyPair kp1 = DiffieHellmanModule.genDHKeyPair();
        KeyPair kp2 = DiffieHellmanModule.genDHKeyPair();
        //Gets the public key of Alice(g^X mod p) and Bob (g^Y mod p)
        PublicKey pbk1 = kp1.getPublic();
        PublicKey pbk2 = kp2.getPublic();
        //Gets the private key of Alice X and Bob Y
        PrivateKey prk1 = kp1.getPrivate();
        PrivateKey prk2 = kp2.getPrivate();
        try {
            //Computes secret keys for Alice (g^Y mod p)^X mod p == Bob (g^X mod p)^Y mod p
            SecretKey key1 = DiffieHellmanModule.agreeSecretKey(prk1, pbk2, true);
            SecretKey key2 = DiffieHellmanModule.agreeSecretKey(prk2, pbk1, true);
            //Instantiate the Cipher of algorithm "DES"
            Cipher c = Cipher.getInstance("DES/ECB/PKCS5Padding");
            //Init the cipher with Alice's key1
            c.init(Cipher.ENCRYPT_MODE, key1);
            //Compute the cipher text = E(key,plainText)
            byte[] ciphertext = c.doFinal("Stand and unfold yourself".getBytes());
            //prints ciphertext
            System.out.println("Encrypted: " + new String(ciphertext,"utf-8"));
            //inits the encryptionMode
            c.init(Cipher.DECRYPT_MODE, key2);
            //Decrypts and print
            System.out.println("Decrypted: " + new String(c.doFinal(ciphertext), "utf-8"));
            System.out.println("Done");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

}

1 个答案:

答案 0 :(得分:1)

好的,因为您花时间创建了MCVE:

这个例子:

  • 删除了一些类和注释,以使其更紧凑
  • 使用预定义的参数,通常不应生成参数
  • 使用SHA-256的最左边的字节作为穷人密钥派生函数
  • 删除了SecretKeyFactory,因为AES不需要它

代码中还有一些注释,标有===

import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.util.Arrays;

import javax.crypto.Cipher;
import javax.crypto.KeyAgreement;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;

/**
 * Diffie-Hellman module for demonstrating KeyAgreement Algorithm
 */
public class DiffieHellmanModule {

    private static final int AES_KEY_SIZE = 128;

    public static void main(String[] args) {
        // Generates keyPairs for Alice and Bob
        KeyPair kp1 = DiffieHellmanModule.genDHKeyPair();
        KeyPair kp2 = DiffieHellmanModule.genDHKeyPair();
        // Gets the public key of Alice(g^X mod p) and Bob (g^Y mod p)
        PublicKey pbk1 = kp1.getPublic();
        PublicKey pbk2 = kp2.getPublic();
        // Gets the private key of Alice X and Bob Y
        PrivateKey prk1 = kp1.getPrivate();
        PrivateKey prk2 = kp2.getPrivate();
        try {
            // Computes secret keys for Alice (g^Y mod p)^X mod p == Bob (g^X
            // mod p)^Y mod p
            SecretKey key1 = DiffieHellmanModule.agreeSecretKey(prk1, pbk2,
                    true);
            SecretKey key2 = DiffieHellmanModule.agreeSecretKey(prk2, pbk1,
                    true);
            // Instantiate the Cipher of algorithm "DES"
            Cipher c = Cipher.getInstance("AES/ECB/PKCS5Padding");
            // Init the cipher with Alice's key1
            c.init(Cipher.ENCRYPT_MODE, key1);
            // Compute the cipher text = E(key,plainText)
            byte[] ciphertext = c.doFinal("Stand and unfold yourself"
                    .getBytes());
            // prints ciphertext
            System.out.println("Encrypted: " + new String(ciphertext, "utf-8"));
            // inits the encryptionMode
            c.init(Cipher.DECRYPT_MODE, key2);
            // Decrypts and print
            System.out.println("Decrypted: "
                    + new String(c.doFinal(ciphertext), "utf-8"));
            System.out.println("Done");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private static KeyPairGenerator kpg;

    static {
        try {
            // === Generates and inits a KeyPairGenerator ===

            // changed this to use default parameters, generating your
            // own takes a lot of time and should be avoided
            // use ECDH or a newer Java (8) to support key generation with
            // higher strength
            kpg = KeyPairGenerator.getInstance("DH");
            kpg.initialize(1024);
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
    }

    public static SecretKey agreeSecretKey(PrivateKey prk_self,
            PublicKey pbk_peer, boolean lastPhase) throws Exception {
        // instantiates and inits a KeyAgreement
        KeyAgreement ka = KeyAgreement.getInstance("DH");
        ka.init(prk_self);
        // Computes the KeyAgreement
        ka.doPhase(pbk_peer, lastPhase);
        // Generates the shared secret
        byte[] secret = ka.generateSecret();

        // === Generates an AES key ===

        // you should really use a Key Derivation Function instead, but this is
        // rather safe

        MessageDigest sha256 = MessageDigest.getInstance("SHA-256"); 
        byte[] bkey = Arrays.copyOf(
                sha256.digest(secret), AES_KEY_SIZE / Byte.SIZE);

        SecretKey desSpec = new SecretKeySpec(bkey, "AES");
        return desSpec;
    }

    public static KeyPair genDHKeyPair() {
        return kpg.genKeyPair();
    }
}