2017-10-19 116 views
0

我試圖找到Java(本地或BouncyCastle提供程序)實現在PKCS#1中使用給定的參數生成RSA私鑰{e,n,d }。通過使用Java安全模數,公共和私人指數還原RSA私鑰

丹Boneh有paper描述了這樣做的算法。該解決方案在PyCrypto(Python)中可用,以及由Mounir IDRASSI發佈的獨立utility,用於在SFM格式(n,e,d)和CRT格式(p,q,dp,dq,u)之間轉換RSA密鑰)以及其他方式。但是,我無法找到任何準備用於Java的東西。

更新:我發現在https://github.com/martinpaljak/RSAKeyConverter/blob/master/src/opensc/RSAKeyConverter.java

+0

我實施了爲好,直接在Java中不看任何其他代碼,只是論文而已,但可能借用一些算法。但是,它在另一臺計算機上。所以我認爲你想轉換爲CRT,因爲它不完全清楚你在做什麼。 –

回答

0

這樣的實現我在this答案,我將重現這裏提供了一些代碼:

/** 
* Find a factor of n by following the algorithm outlined in Handbook of Applied Cryptography, section 
* 8.2.2(i). See http://cacr.uwaterloo.ca/hac/about/chap8.pdf. 
* 
*/ 

private static BigInteger findFactor(BigInteger e, BigInteger d, BigInteger n) { 
    BigInteger edMinus1 = e.multiply(d).subtract(BigInteger.ONE); 
    int s = edMinus1.getLowestSetBit(); 
    BigInteger t = edMinus1.shiftRight(s); 

    for (int aInt = 2; true; aInt++) { 
     BigInteger aPow = BigInteger.valueOf(aInt).modPow(t, n); 
     for (int i = 1; i <= s; i++) { 
      if (aPow.equals(BigInteger.ONE)) { 
       break; 
      } 
      if (aPow.equals(n.subtract(BigInteger.ONE))) { 
       break; 
      } 
      BigInteger aPowSquared = aPow.multiply(aPow).mod(n); 
      if (aPowSquared.equals(BigInteger.ONE)) { 
       return aPow.subtract(BigInteger.ONE).gcd(n); 
      } 
      aPow = aPowSquared; 
     } 
    } 

} 

public static RSAPrivateCrtKey createCrtKey(RSAPublicKey rsaPub, RSAPrivateKey rsaPriv) throws NoSuchAlgorithmException, InvalidKeySpecException { 

    BigInteger e = rsaPub.getPublicExponent(); 
    BigInteger d = rsaPriv.getPrivateExponent(); 
    BigInteger n = rsaPub.getModulus(); 
    BigInteger p = findFactor(e, d, n); 
    BigInteger q = n.divide(p); 
    if (p.compareTo(q) > 1) { 
     BigInteger t = p; 
     p = q; 
     q = t; 
    } 
    BigInteger exp1 = d.mod(p.subtract(BigInteger.ONE)); 
    BigInteger exp2 = d.mod(q.subtract(BigInteger.ONE)); 
    BigInteger coeff = q.modInverse(p); 
    RSAPrivateCrtKeySpec keySpec = new RSAPrivateCrtKeySpec(n, e, d, p, q, exp1, exp2, coeff); 
    KeyFactory kf = KeyFactory.getInstance("RSA"); 
    return (RSAPrivateCrtKey) kf.generatePrivate(keySpec); 

}