解密Android RSA:无效的密文异常

时间:2015-11-02 22:41:49

标签: java android encryption cryptography

我正在创建一个跨平台的Android / Windows应用程序。

我使用此代码在Android中生成公钥,我可以使用从Windows应用程序生成的测试公钥:

         String AppKeyPub = "MIGHAoGBAONcDWYnbGGOIG1wfHy8v54/2Ch2ZCewcM6TGGtnvHOa/53ekPlCYHXG5UDeaCUxPwPK" +
"Fx9qikj04nxF+tKl9GnV4RS+3kDQPkunlJ4pk52PiKVGaVpOWOli1Y31zJJZ9ufqLySEycJVuqiI" +
"Z9kektzkHdAIxNKlPDn4GQa2mjz/AgER"; 

            try {
                // PREP PUBLIC KEY
                byte[] decoded = Base64.decode(AppKeyPub,0);
                org.bouncycastle.asn1.pkcs.RSAPublicKey pkcs1PublicKey = org.bouncycastle.asn1.pkcs.RSAPublicKey.getInstance(decoded);
                BigInteger modulus = pkcs1PublicKey.getModulus();
                BigInteger publicExponent = pkcs1PublicKey.getPublicExponent();
                RSAPublicKeySpec keySpec = new RSAPublicKeySpec(modulus, publicExponent);
                KeyFactory kf = KeyFactory.getInstance("RSA");
                PublicKey publicKey = kf.generatePublic(keySpec);

然后我使用此代码加密测试消息:

byte[] input = "Hello from Android!".getBytes("UTF-8");
        Cipher cipher = Cipher.getInstance("RSA", "BC");
        cipher.init(Cipher.ENCRYPT_MODE, publicKey);                

        byte[] cipherText = new byte[cipher.getOutputSize(input.length)];
        int ctLength = cipher.update(input, 0, input.length, cipherText, 0);
        ctLength += cipher.doFinal(cipherText, ctLength);
        String encodedData = Base64.encodeToString(cipherText, messageCount);
        System.out.println(new String(encodedData));
        System.out.println(ctLength);

这是Android生成的加密测试消息:

  

fy1l1g / Tpxer4mR3bO6WQdfmi93I / YjpZZDGvIiZ6UU / VZWhnmgmuU1zM6EqwppqQTMkfsKPk5kAWhSYH8 + tbyvgh / Cd48rTKJ39MCfnwCNZvSvNKETZbhgy5fVGL / Uisn16AOae0DI4gV4kubrGswhEFUpyp8seAPclKgHbGuQ =

问题是,当我尝试解密Windows应用程序中的消息时,它失败并显示错误消息:

  

RSA / OAEP-MGF1(SHA-1):无效密文

我尝试了不同的Android BC算法组合,它们都给了我相同的结果。我也试过no_wrap no_padding等。谁能告诉我我做错了什么?感谢您的任何建议。

1 个答案:

答案 0 :(得分:1)

您在Windows应用中有OAEP填充。至少在以后的版本中,OAEP填充是默认值。我将向您展示如何执行OAEP填充 - 可能是在不太知名的KEM方案之后 - 可能是RSA最安全的方案:

Cipher cipher = Cipher.getInstance("RSA/NONE/OAEPPADDING", "BC");
cipher.init(Cipher.ENCRYPT_MODE, publicKey);                
byte[] cipherText = new byte[cipher.getOutputSize(input.length)];
int ctLength = cipher.update(input, 0, input.length, cipherText, 0);
ctLength += cipher.doFinal(cipherText, ctLength);