当前位置: 首页 > 知识库问答 >
问题:

来自RSAPrivateKeySpec javax.crypto.BadPaddingException的Java RSA密钥:解密错误

宰父存
2023-03-14

我有一个没有Java加密库的RSA代码类。很管用。

import java.math.BigInteger;
import java.security.SecureRandom;
import java.util.Random;

public class RSA {

    public static RSAKeyPair generateKeyPair(int keysize) {
        Random rnd = new SecureRandom();
        BigInteger p = new BigInteger(keysize / 2, 100, rnd);
        BigInteger q = new BigInteger(keysize / 2, 100, rnd);
        BigInteger n = p.multiply(q);
        BigInteger phi = p.subtract(BigInteger.ONE).multiply(q.subtract(BigInteger.ONE));
        BigInteger e;
        do {
            e = new BigInteger(phi.bitLength(), rnd);
        } while (e.compareTo(BigInteger.ONE) <= 0 || e.compareTo(phi) >= 0 || !e.gcd(phi).equals(BigInteger.ONE));
        BigInteger d = e.modInverse(phi);
        return new RSAKeyPair(new RSAPublicKey(e, n), new RSAPrivateKey(d, n), n);
    }

    public static BigInteger encrypt(BigInteger m, RSAPublicKey key) {
        return m.modPow(key.getPublicExponent(), key.getModulus());
    }

    public static BigInteger decrypt(BigInteger c, RSAPrivateKey key) {
        return c.modPow(key.getPrivateExponent(), key.getModulus());
    }

}

class RSAPublicKey {
    private BigInteger e;
    private BigInteger n;

    public RSAPublicKey(BigInteger e, BigInteger n) {
        this.e = e;
        this.n = n;
    }

    public BigInteger getPublicExponent() {
        return e;
    }

    public BigInteger getModulus() {
        return n;
    }
}

class RSAPrivateKey {
    private BigInteger d;
    private BigInteger n;

    public RSAPrivateKey(BigInteger d, BigInteger n) {
        this.d = d;
        this.n = n;
    }

    public BigInteger getPrivateExponent() {
        return d;
    }

    public BigInteger getModulus() {
        return n;
    }
}

class RSAKeyPair {
    private RSAPublicKey pub;
    private RSAPrivateKey priv;
    private BigInteger modulus;

    public RSAKeyPair(RSAPublicKey pub, RSAPrivateKey priv, BigInteger modulus) {
        this.pub = pub;
        this.priv = priv;
        this.modulus = modulus;
    }

    public RSAPublicKey getPublicKey() {
        return pub;
    }

    public RSAPrivateKey getPrivateKey() {
        return priv;
    }

    public BigInteger getModulus() {
        return modulus;
    }
}

但是,当我从RSAPrivateKeySpec创建一个Java库PrivateKey,从类中的RSAPrivateKey创建一个模数和指数,并使用Java加密库a使用类encrypted BigInteger进行加密时,它会抛出javax.crypto.BadPaddingException:Decryption error。这里:

RSAKeyPair pair = generateKeyPair(1024);
        BigInteger encrypted = encrypt(new BigInteger("123456789"), pair.getPublicKey());
        KeyFactory factory = KeyFactory.getInstance("RSA");
        RSAPrivateKeySpec privSpec = new RSAPrivateKeySpec(pair.getPrivateKey().getModulus(), pair.getPrivateKey().getPrivateExponent());
        PrivateKey priv = factory.generatePrivate(privSpec);
        Cipher cip = Cipher.getInstance("RSA");
        cip.init(Cipher.DECRYPT_MODE, priv);
        System.out.println(new BigInteger(cip.doFinal(encrypted.toByteArray())));

为什么?

对不起,我的英语不好

共有1个答案

狄卓君
2023-03-14

cipher.getinstance()的输入可以有两种形式:

  • “算法/模式/填充”或
  • 算法

当您只指定cipher.getinstance(“RSA”);时,您将得到默认的填充,并且由于加密不包括填充,因此当试图删除预期的填充时,解密将失败。

尝试类似的方法来获得一个没有填充的RSA密码:

Cipher cip = Cipher.getInstance("rsa/ecb/nopadding");
 类似资料:
  • 我在C#程序(我在下面提到)中使用了RSA非对称密钥加密算法,我必须通过java程序加密数据。我希望我的java程序生成与C#程序相同的加密密钥。 公钥: C#加密程序: Java加密方案: 我尝试了上述java程序,但结果如下: O+gw 7+X hY x A 9 ltD V 5 zE RsF 4 Dy Xg MTc/gx 82 wR tT 1 x fR 3 su Y 0 XB JLa dp 7

  • 我编写了一个简单的Java AES加密和解密,如下所示(用于学习): 编辑: 我想我搞错了。黑客可能不会使用我的程序来解密。所以对于AES来说,如果一个人解密失败,他会知道解密失败,但不会像我想的那样,从解密中得到错误的字节?这太可怕了...

  • 问题内容: 我正在使用静态方法在类中使用javax.crypto加密和解密消息。我有2个使用cipher和dcipher的静态方法,以完成他们应该做的事情,我需要初始化一些变量(也是静态的)。但是,当我尝试使用它时,我得到的InvalidKeyException与我提供给ecipher.init(…)的参数。我找不到原因。这是代码: 问题答案: AES-256(和AES-192)要求为JRE安装无

  • 我正在编写android应用程序,使AES加密/解密的文件。我希望能够检测是否指定了不正确的密码,因此不匹配的密钥是为解密派生的。我使用aes/cbc/pkcs7padding和256位密钥。如果我执行cipher.doFinal(),我可以尝试/捕捉BadPaddingException,它会告诉我有些地方出错了,可能是key不正确。但是如果我使用CipherInputStream读取加密文件,

  • 这是我的密码 抱歉,如果我的代码一团糟。

  • 问题内容: 我正在使用3DESC解密数据,但出现以下异常 我的代码: 打印上面使用的所有字节数组 问题答案: DES- EDE密码可与3个不同的子密钥一起使用,因此密钥大小应为24字节(3乘8字节)。如果您只想使用2个键(即在此模式下,第一个键==最后一个键),则只需复制键数组的前8个字节。