Problems encrypting a String using RSA algorithm in Java

江枫思渺然 提交于 2019-12-01 20:59:09

Encrypted message is an arbitrary byte[], it's not guaranteed that it can be correctly converted to String with particular character encoding, so there is no need to convert it to String.

Another trick is that plaintext should be less than n, otherwise algorithm would produce garbage. When this condition is met, it works fine for me.

Yet another possible problem is that when the first byte of message in greater or equal than 0x80, a negative plaintext would be produced. It can be solved by prepending a zero byte to the bytes of message before converting it to BigInteger, and stripping that byte during inverse conversion.

Hint: What does getBytes do that's different from the string value of message? Why aren't you just doing BigInteger(message); ?

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

public class RSA {  
   private final static BigInteger one      = new BigInteger("1");  
   private final static SecureRandom random = new SecureRandom();

   private BigInteger privateKey;  
   private BigInteger publicKey;  
   private BigInteger modulus;   

   // generate an N-bit (roughly) public and private key  
   RSA(int N) {  
      BigInteger p = BigInteger.probablePrime(N/2, random);  
      BigInteger q = BigInteger.probablePrime(N/2, random);   
      BigInteger phi = (p.subtract(one)).multiply(q.subtract(one));       
      modulus    = p.multiply(q);                                          
      publicKey  = new BigInteger("65537");       
   // common value in practice = 2^16 + 1
      privateKey = publicKey.modInverse(phi);   
   }


   BigInteger encrypt(BigInteger message) {    
      return message.modPow(publicKey, modulus);    
   }  

   BigInteger decrypt(BigInteger encrypted) {     
      return encrypted.modPow(privateKey, modulus);    
   }    

   public String toString() {    
      String s = "";    
      s += "public  = " + publicKey  + "\n";   
      s += "private = " + privateKey + "\n";    
      s += "modulus = " + modulus;    
      return s;    
   }    

   public static void main(String[] args) {    
      int N = Integer.parseInt(args[0]);    
      RSA key = new RSA(N);    
      System.out.println(key);    
      // create random message, encrypt and decrypt   
      BigInteger message = new BigInteger(N-1, random);   
      //// create message by converting string to integer   
      // String s = "test";    
      // byte[] bytes = s.getBytes();    
      // BigInteger message = new BigInteger(s);    
      BigInteger encrypt = key.encrypt(message);    
      BigInteger decrypt = key.decrypt(encrypt);    
      System.out.println("message   = " + message);    
      System.out.println("encrpyted = " + encrypt);    
      System.out.println("decrypted = " + decrypt);    
   }     
}
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!