在 Java 中使用模数和指数的 RSA 加密

use*_*610 5 java encryption cryptography rsa

我目前正在 Java 上进行 RSA 加密,我必须使用私有和公共模数进行加密。我目前有以下几点:

private void createPublicKey() throws NoSuchAlgorithmException, InvalidKeySpecException {
        String publicModulus = "d2c34017ef94f8ab6696dae66e3c0d1ad186bbd9ce4461b68d7cd017c15bda174045bfef36fbf048" +
                "73cfd6d09e3806af3949f99c3e09d6d3c37f6398d8c63f9a3e39b78a187809822e8bcf912f4c44a8" +
                "92fe6a65a477ddea9582738317317286a2610ba30b6b090c3b8c61ffb64207229b3f01afe928a960" +
                "c5a44c24b26f5f91";

        BigInteger keyInt = new BigInteger(publicModulus, 16);
        BigInteger exponentInt = new BigInteger("10001", 16);
        RSAPublicKeySpec keySpeck = new RSAPublicKeySpec(keyInt, exponentInt);
        KeyFactory keyFactory = KeyFactory.getInstance("RSA");
        publicKey = keyFactory.generatePublic(keySpeck);

    }

private void createPrivateKey() throws NoSuchAlgorithmException, InvalidKeySpecException {
        String privateModulus = "6c97ab6369cf00dd174bacd7c37e6f661d04e5af10670d4d88d30148ec188e63227b8dac0c517cf9" +
                "67aa73cd23684c9165dc269f091bfab33b6c5c7db95b54130e348255c30aaaac1c7f09ef701e0d6f" +
                "6dc142d2e4ed78466cc104e28d50be7adf3863afc021dbdd8b5f0b968b7cd965242c7d8d4b32ee84" +
                "0fac3cad134344c1";
        BigInteger privateModulusInt = new BigInteger(privateModulus, 16);
        BigInteger exponentInt = new BigInteger("10001", 16);
        RSAPrivateKeySpec privateKeySpec = new RSAPrivateKeySpec(privateModulusInt, exponentInt);
        KeyFactory factory = KeyFactory.getInstance("RSA");
        privateKey = factory.generatePrivate(privateKeySpec);
    }
Run Code Online (Sandbox Code Playgroud)

在主要方法中,我有以下内容:

        createPrivateKey();
        createPublicKey();

        String data = "12";

        Cipher cipher1 = Cipher.getInstance("RSA/ECB/NoPadding");
        cipher1.init(Cipher.ENCRYPT_MODE, publicKey);
        byte[] encryptedData = cipher1.doFinal(data.getBytes());

        Cipher cipher2 = Cipher.getInstance("RSA/ECB/NoPadding");
        cipher2.init(Cipher.DECRYPT_MODE,privateKey);
        byte[] decryptedData = cipher2.doFinal(encryptedData);
        System.out.println(new String(decryptedData));
Run Code Online (Sandbox Code Playgroud)

在控制台中,我得到以下信息: ???.7???p;%kV?9y???xa??{ 而不是"12"如果我制作了String data = "12345";,那么我得到:javax.crypto.BadPaddingException: Message is larger than modulus

首先为什么加密和解密不起作用?为什么我不回来了"12"。其次,为什么我的数据不能大于 2 个字符?

注意我正在使用以下网站来获取模数和指数值。

ped*_*ofb 3

创建私钥时出错。您提供的是公共指数而不是私有指数(如 @dave_thomsom_085 评论)私有指数而不是模数

\n\n

更改createPrivateKey()

\n\n
private static PrivateKey createPrivateKey() throws NoSuchAlgorithmException, InvalidKeySpecException {\n        String publicModulus = "d2c34017ef94f8ab6696dae66e3c0d1ad186bbd9ce4461b68d7cd017c15bda174045bfef36fbf048" +\n                "73cfd6d09e3806af3949f99c3e09d6d3c37f6398d8c63f9a3e39b78a187809822e8bcf912f4c44a8" +\n                "92fe6a65a477ddea9582738317317286a2610ba30b6b090c3b8c61ffb64207229b3f01afe928a960" +\n                "c5a44c24b26f5f91";\n        String privateExponent = "6c97ab6369cf00dd174bacd7c37e6f661d04e5af10670d4d88d30148ec188e63227b8dac0c517cf9" +\n                "67aa73cd23684c9165dc269f091bfab33b6c5c7db95b54130e348255c30aaaac1c7f09ef701e0d6f" +\n                "6dc142d2e4ed78466cc104e28d50be7adf3863afc021dbdd8b5f0b968b7cd965242c7d8d4b32ee84" +\n                "0fac3cad134344c1";\n        BigInteger privateExponenInt = new BigInteger(privateExponent, 16);\n        BigInteger keyInt = new BigInteger(publicModulus, 16);\n        RSAPrivateKeySpec privateKeySpec = new RSAPrivateKeySpec(keyInt, privateExponenInt);\n        KeyFactory factory = KeyFactory.getInstance("RSA");\n        return factory.generatePrivate(privateKeySpec);\n    }\n
Run Code Online (Sandbox Code Playgroud)\n\n

此外,出于安全原因,您不应使用未经填充的原始 RSA。使用RSA/ECB/PKCS1Padding或新的 OAEP 填充RSA/ECB/OAEPWithSHA1AndMGF1Padding

\n\n

根据这个答案,您可以使用PKCS1Padding比密钥大小少 11 个字节的数据进行加密。并且使用 OAEP它必须小于密钥模数 \xe2\x80\x93 41 的大小

\n\n

然后,使用您的 1024 位密钥:

\n\n
    \n
  • PKCS1:(1024 bits / 8) - 11 = 117 bytes
  • \n
  • OAEP:(1024 bits / 8) - 42 = 86 bytes
  • \n
\n\n

还建议直接使用 CRT 而不是私有指数

\n\n
RSAPrivateCrtKeySpec privateKeySpec = \n    new RSAPrivateCrtKeySpec(modulus, publicExponent, privateExponent, primeP, primeQ, primeExpP, primeExpQ, crtCoefficient);\n
Run Code Online (Sandbox Code Playgroud)\n