為給定的模量和指數生成RSA密鑰。

[英]Generating RSA keys for given modulus and exponent


I have been asked to generate the RSA key using given modulus and exponent values. But I have idea only about generating the keys without specifying the modulus and exponent. Whatever the value I am given is seems to be big integer values. I searched about this in web and worked out some thing, But it could not went through success.

我被要求使用給定的模量和指數值生成RSA密鑰。但我只知道在不指定模量和指數的情況下生成鍵。不管我給出的值是多少,都是大整數。我在網上搜索了一下,找到了一些東西,但沒有成功。

So if anybody has done this before, can they give me some hints please?

所以如果有人以前做過這個,他們能給我一些提示嗎?

This is sample program we have tried with given values.

這是我們用給定值嘗試過的樣本程序。

import java.io.UnsupportedEncodingException;
import java.math.BigInteger;
import java.security.KeyFactory;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.spec.RSAKeyGenParameterSpec;
import java.security.spec.RSAPrivateKeySpec;
import java.security.spec.RSAPublicKeySpec;

public class Sample {
        public static void main( String args[] ) {

                BigInteger modulus  = new BigInteger("350871044328208704010580786055405681");
                BigInteger exponent = new BigInteger("545161406957801571");

                try {                    
                        RSAPublicKeySpec spec = new RSAPublicKeySpec(modulus, exponent);
                        RSAPrivateKeySpec privateSpec = new RSAPrivateKeySpec(modulus, exponent);

                        KeyFactory factory = KeyFactory.getInstance("RSA");

                        PublicKey pub = factory.generatePublic(spec);
                        PrivateKey priv = factory.generatePrivate(privateSpec); 

                        System.out.println("Public Key : "+ byteArrayToHexString( pub.getEncoded() ));
                        System.out.println("Private Key : "+ byteArrayToHexString( priv.getEncoded() ));
                }                        
                catch( Exception e ) {   
                        System.out.println(e.toString());       
                }                        
        }         
        public static String byteArrayToHexString(byte[] bytes)          
        {         
                StringBuffer buffer = new StringBuffer();
                for(int i=0; i<bytes.length; i++)
                {                        
                        if(((int)bytes[i] & 0xff) < 0x10)       
                                buffer.append("0");                               
                        buffer.append(Long.toString((int) bytes[i] & 0xff, 16));
                }                        
                return buffer.toString();
        }         
}

ERROR:

錯誤:

java.security.spec.InvalidKeySpecException: java.security.InvalidKeyException: RSA keys must be at least 512 bits long

java.security.spec。InvalidKeySpecException:java.security。無效鍵異常:RSA密鑰必須至少為512位。

1 个解决方案

#1


6  

I give you some information about RSA. First of all in RSA keys the modulus = p·q where p and q are distinct prime numbers, the modulus length it's the key length. So when you are receiving the exception:

我給你一些RSA的信息。首先,在RSA密鑰中,模量= p·q, p和q是不同的素數,模長是關鍵長度。所以當你收到一個例外:

java.security.spec.InvalidKeySpecException: java.security.InvalidKeyException: RSA keys must be at least 512 bits long

java.security.spec。InvalidKeySpecException:java.security。無效鍵異常:RSA密鑰必須至少為512位。

This means that your modulus at least must be 512 bits long.

這意味着你的模數至少必須是512位長。

Besides in your code there is also another error, you're using the same exponent for public and private key, but this exponents must be different numbers.

除了代碼中還有另一個錯誤,你使用的是公共和私鑰的相同指數,但這個指數必須是不同的數字。

In resume you have to calculate the modulus, public exponent and private exponent with java.math.BigInteger following the RSA key generation algorithm to generate a correct keys. I give you an example from your code:

在簡歷中,你必須計算模量,公共指數和私有指數。使用RSA密鑰生成算法生成正確密鑰的BigInteger。我給你一個例子,你的代碼:

import java.math.BigInteger;
import java.security.KeyFactory;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.SecureRandom;
import java.security.spec.RSAPrivateKeySpec;
import java.security.spec.RSAPublicKeySpec;

public class Sample {
    public static void main( String args[] ) {

        int keySize = 512;  
        SecureRandom random = new SecureRandom();
        // Choose two distinct prime numbers p and q.
        BigInteger p = BigInteger.probablePrime(keySize/2,random);
        BigInteger q = BigInteger.probablePrime(keySize/2,random);
        // Compute n = pq (modulus)
        BigInteger modulus = p.multiply(q);
        // Compute φ(n) = φ(p)φ(q) = (p − 1)(q − 1) = n - (p + q -1), where φ is Euler's totient function.
        // and choose an integer e such that 1 < e < φ(n) and gcd(e, φ(n)) = 1; i.e., e and φ(n) are coprime.
        BigInteger m = (p.subtract(BigInteger.ONE)).multiply(q.subtract(BigInteger.ONE));
        BigInteger publicExponent = getCoprime(m,random);
        // Determine d as d ≡ e−1 (mod φ(n)); i.e., d is the multiplicative inverse of e (modulo φ(n)).
        BigInteger privateExponent = publicExponent.modInverse(m);


        try {                    
            RSAPublicKeySpec spec = new RSAPublicKeySpec(modulus, publicExponent);
            RSAPrivateKeySpec privateSpec = new RSAPrivateKeySpec(modulus, privateExponent);

            KeyFactory factory = KeyFactory.getInstance("RSA");

            PublicKey pub = factory.generatePublic(spec);
            PrivateKey priv = factory.generatePrivate(privateSpec); 

            System.out.println("Public Key : "+ byteArrayToHexString( pub.getEncoded() ));
            System.out.println("Private Key : "+ byteArrayToHexString( priv.getEncoded() ));
        }                        
        catch( Exception e ) {   
            System.out.println(e.toString());       
        }                        
    }         

    public static BigInteger getCoprime(BigInteger m, SecureRandom random) {
        int length = m.bitLength()-1;
        BigInteger e = BigInteger.probablePrime(length,random);
        while (! (m.gcd(e)).equals(BigInteger.ONE) ) {
            e = BigInteger.probablePrime(length,random);
        }
        return e;
    }


    public static String byteArrayToHexString(byte[] bytes)          
    {         
        StringBuffer buffer = new StringBuffer();
        for(int i=0; i<bytes.length; i++)
        {                        
            if(((int)bytes[i] & 0xff) < 0x10)       
                buffer.append("0");                               
            buffer.append(Long.toString((int) bytes[i] & 0xff, 16));
        }                        
        return buffer.toString();
    }         
}

Hope this help,

希望這個有幫助,


注意!

本站翻译的文章,版权归属于本站,未经许可禁止转摘,转摘请注明本文地址:https://www.itdaan.com/blog/2014/07/03/79b2a6038000eebdacace22fe2939d8a.html



 
粤ICP备14056181号  © 2014-2021 ITdaan.com