RSA BadPaddingException:数据必须从零开始

发布于 2024-08-30 11:04:10 字数 2190 浏览 4 评论 0原文

我尝试在Java程序中实现RSA算法。我面临“BadPaddingException:数据必须从零开始”。 以下是用于加密和解密我的数据的方法:

public byte[] encrypt(byte[] input)  throws Exception
{
    Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");//
    cipher.init(Cipher.ENCRYPT_MODE, this.publicKey);
    return cipher.doFinal(input);
}

public byte[] decrypt(byte[] input)  throws Exception
{   
    Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");///
    cipher.init(Cipher.DECRYPT_MODE, this.privateKey);
    return cipher.doFinal(input);
}

私钥和公钥属性是这样从文件中读取的:

public PrivateKey readPrivKeyFromFile(String keyFileName) throws IOException {
    PrivateKey key = null;
    try {
        FileInputStream fin = new FileInputStream(keyFileName);
        ObjectInputStream ois = new ObjectInputStream(fin);
        BigInteger m = (BigInteger) ois.readObject();
        BigInteger e = (BigInteger) ois.readObject();
        RSAPrivateKeySpec keySpec = new RSAPrivateKeySpec(m, e);
        KeyFactory fact = KeyFactory.getInstance("RSA");
        key = fact.generatePrivate(keySpec);
        ois.close();
    }
    catch (Exception e) {
       e.printStackTrace();
    }
    return key;
}

私钥和公钥是这样创建的:

public void Initialize() throws Exception
{
    KeyPairGenerator keygen = KeyPairGenerator.getInstance("RSA");
    keygen.initialize(2048);
    keyPair = keygen.generateKeyPair();
    KeyFactory fact = KeyFactory.getInstance("RSA");
    RSAPublicKeySpec pub = fact.getKeySpec(keyPair.getPublic(), RSAPublicKeySpec.class);
    RSAPrivateKeySpec priv = fact.getKeySpec(keyPair.getPrivate(), RSAPrivateKeySpec.class);

    saveToFile("public.key", pub.getModulus(), pub.getPublicExponent());
    saveToFile("private.key", priv.getModulus(), priv.getPrivateExponent());
}

然后保存在文件中:

public void saveToFile(String fileName, BigInteger mod, BigInteger exp) throws IOException {
    FileOutputStream f = new FileOutputStream(fileName);
    ObjectOutputStream oos = new ObjectOutputStream(f);
    oos.writeObject(mod);
    oos.writeObject(exp);
    oos.close();
}

我不知道问题是如何产生的。任何帮助将不胜感激!

提前致谢。

I try to implement an RSA algorithm in a Java program. I am facing the "BadPaddingException : data must start with zero".
Here are the methods used to encrypt and decrypt my data :

public byte[] encrypt(byte[] input)  throws Exception
{
    Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");//
    cipher.init(Cipher.ENCRYPT_MODE, this.publicKey);
    return cipher.doFinal(input);
}

public byte[] decrypt(byte[] input)  throws Exception
{   
    Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");///
    cipher.init(Cipher.DECRYPT_MODE, this.privateKey);
    return cipher.doFinal(input);
}

privateKey and publicKey attributes are read from files this way :

public PrivateKey readPrivKeyFromFile(String keyFileName) throws IOException {
    PrivateKey key = null;
    try {
        FileInputStream fin = new FileInputStream(keyFileName);
        ObjectInputStream ois = new ObjectInputStream(fin);
        BigInteger m = (BigInteger) ois.readObject();
        BigInteger e = (BigInteger) ois.readObject();
        RSAPrivateKeySpec keySpec = new RSAPrivateKeySpec(m, e);
        KeyFactory fact = KeyFactory.getInstance("RSA");
        key = fact.generatePrivate(keySpec);
        ois.close();
    }
    catch (Exception e) {
       e.printStackTrace();
    }
    return key;
}

Private key and Public key are created this way :

public void Initialize() throws Exception
{
    KeyPairGenerator keygen = KeyPairGenerator.getInstance("RSA");
    keygen.initialize(2048);
    keyPair = keygen.generateKeyPair();
    KeyFactory fact = KeyFactory.getInstance("RSA");
    RSAPublicKeySpec pub = fact.getKeySpec(keyPair.getPublic(), RSAPublicKeySpec.class);
    RSAPrivateKeySpec priv = fact.getKeySpec(keyPair.getPrivate(), RSAPrivateKeySpec.class);

    saveToFile("public.key", pub.getModulus(), pub.getPublicExponent());
    saveToFile("private.key", priv.getModulus(), priv.getPrivateExponent());
}

and then saved in files :

public void saveToFile(String fileName, BigInteger mod, BigInteger exp) throws IOException {
    FileOutputStream f = new FileOutputStream(fileName);
    ObjectOutputStream oos = new ObjectOutputStream(f);
    oos.writeObject(mod);
    oos.writeObject(exp);
    oos.close();
}

I can't figured out how the problem come from. Any help would be appreciate !

Thanks in advance.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

路还长,别太狂 2024-09-06 11:04:11

原则上,代码看起来不错——我会进行一些登录,以确保您生成的密钥确实是随后从文件中读取的密钥(您不会做一些愚蠢的事情,例如使用新密钥生成数据,例如,然后尝试用旧的阅读它?)

In principle the code looks OK -- I would put some logging in to make sure the key you're generating is genuinely the one that is then read from the file (you're not doing something silly like generating data with a new key, then trying to read it with an old one, for example?)

成熟稳重的好男人 2024-09-06 11:04:11

到目前为止,我已经追踪到 CipherSpi.engineDoFinal()。对 BadPaddingException 提供的解释是

[当]密码处于解密模式,并且已请求(取消)填充,但解密的数据不受适当的填充字节限制时抛出

更具体的行为似乎与 Spi 相关。你知道你用的是什么SPI吗?只是默认吗?

编辑:
不幸的是,我很难追踪默认的 Spi 是什么。看起来它是在 Cipher.java 的 chooseFirstProvider() 方法中选择的,此处第 644 至 721 行。如果你手边有一个调试器,你可能想找出你有什么 Spi,然后检查它的文档...但我仍然认为更有可能是输入发生了问题,而不是逻辑(我问过这个问题)早些时候,在评论中)。

So far, I've tracked this down to CipherSpi.engineDoFinal(). The explanation provided for BadPaddingException is

[Thrown when the] cipher is in decryption mode, and (un)padding has been requested, but the decrypted data is not bounded by the appropriate padding bytes

More specific behavior seems to be Spi-dependent. Do you know what Spi you're using? Just the default?

EDIT:
Unfortunately, I'm having a hard time tracking down what the default Spi is. It looks like it's chosen in Cipher.java's chooseFirstProvider() method, lines 644 to 721 here. If you have a debugger handy, you might want to find out what Spi you have, then check the documentation for it... but I still think it's more likely that something's going on with the input, not the logic (I asked about that earlier, in a comment).

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文