1

This is simply for fun. This will not be used for any actual encryption. I'm only first year comp sci student and love cryptography.

This took a long time to get working. At approximately N = 18, it begins breaking down. It won't encrypt messages properly after that point. I'm not sure why. Any insights? I'd also appreciate any links you could provide me to tutorials or interesting reading about Cryptography.

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

/**
 * Cryptography.
 *
 * Generates public and private keys used in encryption and 
 * decryption
 * 
 */
public class RSA
{
    private final static BigInteger one = new BigInteger("1");
    private final static SecureRandom random = new SecureRandom();

    // prime numbers
    private BigInteger p;
    private BigInteger q;

    // modulus
    private BigInteger n;

    // totient
    private BigInteger t;

    // public key
    private BigInteger e;

    // private key
    private BigInteger d;

    private String cipherText;

    /**
     * Constructor for objects of class RSA
     */
    public RSA(int N)
    {
        p = BigInteger.probablePrime(N/2, random);
        q = BigInteger.probablePrime(N/2, random);

        // initialising modulus
        n = p.multiply(q);

        // initialising t by euclid's totient function (p-1)(q-1)
        t = (p.subtract(one)).multiply(q.subtract(one));

        // initialising public key ~ 65537 is common public key
        e = new BigInteger("65537");
    }

    public int generatePrivateKey()
    {
         d = e.modInverse(t);
         return d.intValue();
    }

    public String encrypt(String plainText)
    {
        String encrypted = "";
        int j = 0;
        for(int i = 0; i < plainText.length(); i++){
            char m = plainText.charAt(i);
            BigInteger bi1 = BigInteger.valueOf(m);
            BigInteger bi2 = bi1.modPow(e, n);
            j = bi2.intValue();
            m = (char) j;
            encrypted += m;
        }
        cipherText = encrypted;
        return encrypted;
    }

    public String decrypt()
    {
        String decrypted = "";
        int j = 0;
        for(int i = 0; i < cipherText.length(); i++){
            char c = cipherText.charAt(i);
            BigInteger bi1 = BigInteger.valueOf(c);
            BigInteger bi2 = bi1.modPow(d, n);
            j = bi2.intValue();
            c = (char) j;
            decrypted += c;
        }
        return decrypted;
    }
}
3
  • You'll need to be more specific with what you mean by "breaking down", by not encrypting messages "properly", and whether it works with N<18 or N>18. Also, as it stands you are using RSA in ECB mode, whereas you ought to be using a hybrid scheme. Commented Jan 9, 2011 at 10:36
  • Oh, and as for texts to read - Cryptography Engineering by Schneier, Ferguson and Kohno. Commented Jan 9, 2011 at 10:37
  • The encryption works, but decryption does not with N > 18. Thanks for the reading suggestion, I will get it from the library asap! Commented Jan 9, 2011 at 10:55

1 Answer 1

2

Your encryption can trivially broken since you only have 2^16 different messages. RSA is only secure if correct padding (OEP) is used. And of course the cyphertext takes 100x as much space as the plaintext since you map one char to one RSA block.

j = bi2.intValue();
m = (char) j;

Both of these operations horribly overflow. bi2 is a BigInteger for a reason. It just doesn't fit an 32 bit integer/16 bit char. Since truncating the integer loses most of the bits, the decryption won't work since you corrupted the cyphertext.

Sign up to request clarification or add additional context in comments.

1 Comment

Ah, that makes a lot of sense. Thanks. I'll read up on correct padding. I have a lot to learn.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.