RSA cryptography between Python and Java

Piet van Oostrum piet at cs.uu.nl
Mon Jul 27 07:08:27 EDT 2009


>>>>> Paul Rubin <http://phr.cx@NOSPAM.invalid> (PR) wrote:

>PR> Rob Knop <rknop at pobox.com> writes:
>>> Are there any python libraries that will take a public key in this
>>> format and do RSA encoding on it?

>PR> Try www.trevp.com/tlslite

I have looked into tlslite and found no easy way to do this. Maybe I
overlooked it. On the other hand with M2Crypto it isn't that hard.

However, M2Crypto wants to load keys in PEM format rather than the DER
format that the Java getEncoded() produces. It is not hard to convert
this to PEM format: just Base64 encode it and put a header and trailer
line around it. The conversion can be done with openssl or just on the
fly in the Python code.
Please note that the text to be encrypted must be smaller than the key
size (at least 11 bytes smaller). You shouldn't encrypt large data with
RSA anyway: it is too slow. Normally you would encrypt a session key
with RSA and encrypt the data with the session key using a symmetric
algorithms like AES.

Here is an example script:
If your OS doesn't have /dev/urandom you should probably seed OpenSSL's
PRNG to be more secure.
------------------------------------------------------------------------
from M2Crypto import BIO, RSA

pubkey = open("pubkey.der", 'rb').read()

import base64
pubkey = base64.encodestring(pubkey)
pubkey = '-----BEGIN PUBLIC KEY-----\n' + pubkey + '-----END PUBLIC KEY-----'

bio = BIO.MemoryBuffer(pubkey)
rsa = RSA.load_pub_key_bio(bio)

plaintext = "This is my secret text."

codetext = rsa.public_encrypt(plaintext, RSA.pkcs1_padding)

with open("codetext", 'wb') as out:
    out.write(codetext)
------------------------------------------------------------------------
The following Java program decodes this with the corresponding private
key:
------------------------------------------------------------------------
import java.security.*;
import javax.crypto.*;
import java.security.spec.*;
import java.security.interfaces.*;
import java.io.*;

class Decrypt {

    public static void main(String[] args) {      

        byte[] key = null;
        try {
            File file = new File("privkey.der");
            FileInputStream keyfile = new FileInputStream(file);
            key = new byte[(int)file.length()];
            DataInputStream dis= new DataInputStream(keyfile);
            dis.readFully(key);
            dis.close();
        }
        catch(FileNotFoundException e)
        {
            System.out.println("Key file not found" + e);
        }
        catch (IOException e) {
            System.out.println("Can't read key file" + e);
        }

        byte[] codetext = null;
        try {
            File file = new File("codetext");
            FileInputStream codefile = new FileInputStream(file);
            codetext = new byte[(int)file.length()];

            DataInputStream dis = new DataInputStream(codefile);
            dis.readFully(codetext);
            dis.close();
        }
        catch(FileNotFoundException e)
        {
            System.out.println("Code file not found" + e);
        }
        catch (IOException e) {
            System.out.println("Can't read code file" + e);
        }

        try {

            KeyFactory keyFactory = KeyFactory.getInstance("RSA");
            
            PKCS8EncodedKeySpec privSpec = new PKCS8EncodedKeySpec(key);
            RSAPrivateKey rsakey = (RSAPrivateKey) keyFactory.generatePrivate(privSpec);

            Cipher c = Cipher.getInstance("RSA/ECB/PKCS1Padding");

            c.init(Cipher.DECRYPT_MODE, rsakey);
            byte[] decrypted = c.doFinal(codetext);
            System.out.println("Decrypted text:");
            System.out.println(new String(decrypted));

        }
        catch (NoSuchAlgorithmException e) {
            System.out.println("Wrong Algorithm " + e);
        }   
        catch (InvalidKeyException e) {
            System.out.println("Invalid key " + e);
        }   
        catch (IllegalBlockSizeException e) {
            System.out.println("Illegal block size" + e);
        }   
        catch (NoSuchPaddingException e) {
            System.out.println("Illegal padding " + e);
        }   
        catch (BadPaddingException e) {
            System.out.println("Bad padding " + e);
        }   
        catch (InvalidKeySpecException e) {
            System.out.println("Invalid keyspec " + e);
        }   
    }
}
------------------------------------------------------------------------
-- 
Piet van Oostrum <piet at cs.uu.nl>
URL: http://pietvanoostrum.com [PGP 8DAE142BE17999C4]
Private email: piet at vanoostrum.org



More information about the Python-list mailing list