Расшифровка RSA с открытым ключом


У меня есть некоторые проблемы с расшифровкой в моем проекте Android.

Я получаю строку, подписанную закрытым ключом, и я должен проверить(расшифровать) ее с помощью открытого ключа. Я хотел бы получить точно такой же результат, как если бы я использовал функцию PHP-openssl_public_decrypt ( http://php.net/manual/pl/function.openssl-public-decrypt.php )

Я должен сделать это в моем проекте Java, поэтому я могу использовать Java libs (например, BouncyCastle или что-то еще, какие-либо рекомендации? )

Есть идеи, как это решить?

Хорошо, вот мой код. Я получаю открытый ключ вот так
PEMReader reader = new PEMReader(new InputStreamReader(ctx
                .getAssets().open("pubkey.pem")));
        Object obj;
        while ((obj = reader.readObject()) != null) {
             if (obj instanceof RSAPublicKey) {
                pubKey = (RSAPublicKey) obj;
                return pubKey;
            }
        }

И я всегда получаю открытый ключ без каких-либо проблем.

Cipher c = Cipher.getInstance("RSA/NONE/NoPadding", "SC");
c.init(Cipher.DECRYPT_MODE, pubKey);
byte[] result = c.doFinal(data_to_decrypt.getBytes());

И в результате (после преобразования байтов в строку) я получаю 022c06571c6a263b389fcd93159cb311abb880bddf51b7c916dd1ae...

Где функции php возвращают sd8dsa348acvcx87|00454|OK|15000|CDE и это правильный вывод.

1 4

1 ответ:

У Java есть Java Cryptography Extension Framework, который просто предназначен для этих вещей.

BouncyCastle является поставщиком криптографии для этой платформы. Это означает, что он предоставляет вашему расширению Java Cryptography реализации алгоритмов криптографии.

Вы найдете основные классы для этого в пакетах java.security и javax.crypto

Чтобы расшифровать ваше сообщение с помощью открытого ключа, вы можете попробовать следующее:

// Use RSA/NONE/NoPadding as algorithm and BouncyCastle as crypto provider
Cipher asymmetricCipher = Cipher.getInstance("RSA/NONE/NoPadding", "BC");

// asume, that publicKeyBytes contains a byte array representing
// your public key
X509EncodedKeySpec publicKeySpec = new X509EncodedKeySpec(publicKeyBytes);

KeyFactory keyFactory;
keyFactory = KeyFactory.getInstance(publicKeySpec.getFormat());
Key key = keyFactory.generatePublic(publicKeySpec);

// initialize your cipher
asymmetricCipher.init(Cipher.DECRYPT_MODE, key);
// asuming, cipherText is a byte array containing your encrypted message
byte[] plainText = asymmetricCipher.doFinal(cipherText);

Пожалуйста, обратите внимание, что этот пример Очень базовый и не хватает нескольких блоков try catch. Кроме того, вы не должны использовать асимметричный шифр без заполнения, так как это делает вас уязвимым для повторных атак. Вы также можете столкнуться с проблемами с длиной ключа. В некоторых пакетах Java максимально допустимая длина ключа ограничена. Это может быть решено с помощью файлов политики неограниченной силы.

Я надеюсь, что это поможет вам начать работу с криптографией Java.