1 /* 2 * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package sun.security.rsa; 27 28 import java.math.BigInteger; 29 30 import java.security.*; 31 import java.security.spec.AlgorithmParameterSpec; 32 import java.security.spec.RSAKeyGenParameterSpec; 33 34 import sun.security.jca.JCAUtil; 35 36 /** 37 * RSA keypair generation. Standard algorithm, minimum key length 512 bit. 38 * We generate two random primes until we find two where phi is relative 39 * prime to the public exponent. Default exponent is 65537. It has only bit 0 40 * and bit 4 set, which makes it particularly efficient. 41 * 42 * @since 1.5 43 * @author Andreas Sterbenz 44 */ 45 public final class RSAKeyPairGenerator extends KeyPairGeneratorSpi { 46 47 // public exponent to use 48 private BigInteger publicExponent; 49 50 // size of the key to generate, >= RSAKeyFactory.MIN_MODLEN 51 private int keySize; 52 53 // PRNG to use 54 private SecureRandom random; 55 56 public RSAKeyPairGenerator() { 57 // initialize to default in case the app does not call initialize() 58 initialize(1024, null); 59 } 60 61 // initialize the generator. See JCA doc 62 public void initialize(int keySize, SecureRandom random) { 63 64 // do not allow unreasonably small or large key sizes, 65 // probably user error 66 try { 67 RSAKeyFactory.checkKeyLengths(keySize, RSAKeyGenParameterSpec.F4, 68 512, 64 * 1024); 69 } catch (InvalidKeyException e) { 70 throw new InvalidParameterException(e.getMessage()); 71 } 72 73 this.keySize = keySize; 74 this.random = random; 75 this.publicExponent = RSAKeyGenParameterSpec.F4; 76 } 77 78 // second initialize method. See JCA doc. 79 public void initialize(AlgorithmParameterSpec params, SecureRandom random) 80 throws InvalidAlgorithmParameterException { 81 82 if (params instanceof RSAKeyGenParameterSpec == false) { 83 throw new InvalidAlgorithmParameterException 84 ("Params must be instance of RSAKeyGenParameterSpec"); 85 } 86 87 RSAKeyGenParameterSpec rsaSpec = (RSAKeyGenParameterSpec)params; 88 int tmpKeySize = rsaSpec.getKeysize(); 89 BigInteger tmpPublicExponent = rsaSpec.getPublicExponent(); 90 91 if (tmpPublicExponent == null) { 92 tmpPublicExponent = RSAKeyGenParameterSpec.F4; 93 } else { 94 if (tmpPublicExponent.compareTo(RSAKeyGenParameterSpec.F0) < 0) { 95 throw new InvalidAlgorithmParameterException 96 ("Public exponent must be 3 or larger"); 97 } 98 if (tmpPublicExponent.bitLength() > tmpKeySize) { 99 throw new InvalidAlgorithmParameterException 100 ("Public exponent must be smaller than key size"); 101 } 102 } 103 104 // do not allow unreasonably large key sizes, probably user error 105 try { 106 RSAKeyFactory.checkKeyLengths(tmpKeySize, tmpPublicExponent, 107 512, 64 * 1024); 108 } catch (InvalidKeyException e) { 109 throw new InvalidAlgorithmParameterException( 110 "Invalid key sizes", e); 111 } 112 113 this.keySize = tmpKeySize; 114 this.publicExponent = tmpPublicExponent; 115 this.random = random; 116 } 117 118 // generate the keypair. See JCA doc 119 public KeyPair generateKeyPair() { 120 // accommodate odd key sizes in case anybody wants to use them 121 int lp = (keySize + 1) >> 1; 122 int lq = keySize - lp; 123 if (random == null) { 124 random = JCAUtil.getSecureRandom(); 125 } 126 BigInteger e = publicExponent; 127 while (true) { 128 // generate two random primes of size lp/lq 129 BigInteger p = BigInteger.probablePrime(lp, random); 130 BigInteger q, n; 131 do { 132 q = BigInteger.probablePrime(lq, random); 133 // convention is for p > q 134 if (p.compareTo(q) < 0) { 135 BigInteger tmp = p; 136 p = q; 137 q = tmp; 138 } 139 // modulus n = p * q 140 n = p.multiply(q); 141 // even with correctly sized p and q, there is a chance that 142 // n will be one bit short. re-generate the smaller prime if so 143 } while (n.bitLength() < keySize); 144 145 // phi = (p - 1) * (q - 1) must be relative prime to e 146 // otherwise RSA just won't work ;-) 147 BigInteger p1 = p.subtract(BigInteger.ONE); 148 BigInteger q1 = q.subtract(BigInteger.ONE); 149 BigInteger phi = p1.multiply(q1); 150 // generate new p and q until they work. typically 151 // the first try will succeed when using F4 152 if (e.gcd(phi).equals(BigInteger.ONE) == false) { 153 continue; 154 } 155 156 // private exponent d is the inverse of e mod phi 157 BigInteger d = e.modInverse(phi); 158 159 // 1st prime exponent pe = d mod (p - 1) 160 BigInteger pe = d.mod(p1); 161 // 2nd prime exponent qe = d mod (q - 1) 162 BigInteger qe = d.mod(q1); 163 164 // crt coefficient coeff is the inverse of q mod p 165 BigInteger coeff = q.modInverse(p); 166 167 try { 168 PublicKey publicKey = new RSAPublicKeyImpl(n, e); 169 PrivateKey privateKey = 170 new RSAPrivateCrtKeyImpl(n, e, d, p, q, pe, qe, coeff); 171 return new KeyPair(publicKey, privateKey); 172 } catch (InvalidKeyException exc) { 173 // invalid key exception only thrown for keys < 512 bit, 174 // will not happen here 175 throw new RuntimeException(exc); 176 } 177 } 178 } 179 180 }