src/java.base/share/classes/sun/security/rsa/RSAKeyPairGenerator.java
branchJDK-8145252-TLS13-branch
changeset 56542 56aaa6cb3693
parent 47421 f9e03aef3a49
child 56592 b1902b22005e
equal deleted inserted replaced
56541:92cbbfc996f3 56542:56aaa6cb3693
     1 /*
     1 /*
     2  * Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
     2  * Copyright (c) 2003, 2018, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     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
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.  Oracle designates this
     7  * published by the Free Software Foundation.  Oracle designates this
    31 import java.security.spec.AlgorithmParameterSpec;
    31 import java.security.spec.AlgorithmParameterSpec;
    32 import java.security.spec.RSAKeyGenParameterSpec;
    32 import java.security.spec.RSAKeyGenParameterSpec;
    33 
    33 
    34 import sun.security.jca.JCAUtil;
    34 import sun.security.jca.JCAUtil;
    35 import static sun.security.util.SecurityProviderConstants.DEF_RSA_KEY_SIZE;
    35 import static sun.security.util.SecurityProviderConstants.DEF_RSA_KEY_SIZE;
       
    36 import static sun.security.util.SecurityProviderConstants.DEF_RSASSA_PSS_KEY_SIZE;
       
    37 import sun.security.x509.AlgorithmId;
       
    38 import static sun.security.rsa.RSAUtil.KeyType;
    36 
    39 
    37 /**
    40 /**
    38  * RSA keypair generation. Standard algorithm, minimum key length 512 bit.
    41  * RSA keypair generation. Standard algorithm, minimum key length 512 bit.
    39  * We generate two random primes until we find two where phi is relative
    42  * We generate two random primes until we find two where phi is relative
    40  * prime to the public exponent. Default exponent is 65537. It has only bit 0
    43  * prime to the public exponent. Default exponent is 65537. It has only bit 0
    41  * and bit 4 set, which makes it particularly efficient.
    44  * and bit 4 set, which makes it particularly efficient.
    42  *
    45  *
    43  * @since   1.5
    46  * @since   1.5
    44  * @author  Andreas Sterbenz
    47  * @author  Andreas Sterbenz
    45  */
    48  */
    46 public final class RSAKeyPairGenerator extends KeyPairGeneratorSpi {
    49 public abstract class RSAKeyPairGenerator extends KeyPairGeneratorSpi {
    47 
    50 
    48     // public exponent to use
    51     // public exponent to use
    49     private BigInteger publicExponent;
    52     private BigInteger publicExponent;
    50 
    53 
    51     // size of the key to generate, >= RSAKeyFactory.MIN_MODLEN
    54     // size of the key to generate, >= RSAKeyFactory.MIN_MODLEN
    52     private int keySize;
    55     private int keySize;
    53 
    56 
       
    57     private final KeyType type;
       
    58     private AlgorithmId rsaId;
       
    59 
    54     // PRNG to use
    60     // PRNG to use
    55     private SecureRandom random;
    61     private SecureRandom random;
    56 
    62 
    57     public RSAKeyPairGenerator() {
    63     RSAKeyPairGenerator(KeyType type, int defKeySize) {
       
    64         this.type = type;
    58         // initialize to default in case the app does not call initialize()
    65         // initialize to default in case the app does not call initialize()
    59         initialize(DEF_RSA_KEY_SIZE, null);
    66         initialize(defKeySize, null);
    60     }
    67     }
    61 
    68 
    62     // initialize the generator. See JCA doc
    69     // initialize the generator. See JCA doc
    63     public void initialize(int keySize, SecureRandom random) {
    70     public void initialize(int keySize, SecureRandom random) {
    64 
       
    65         // do not allow unreasonably small or large key sizes,
       
    66         // probably user error
       
    67         try {
    71         try {
    68             RSAKeyFactory.checkKeyLengths(keySize, RSAKeyGenParameterSpec.F4,
    72             initialize(new RSAKeyGenParameterSpec(keySize,
    69                 512, 64 * 1024);
    73                     RSAKeyGenParameterSpec.F4), null); 
    70         } catch (InvalidKeyException e) {
    74         } catch (InvalidAlgorithmParameterException iape) {
    71             throw new InvalidParameterException(e.getMessage());
    75             throw new InvalidParameterException(iape.getMessage());
    72         }
    76         }
    73 
       
    74         this.keySize = keySize;
       
    75         this.random = random;
       
    76         this.publicExponent = RSAKeyGenParameterSpec.F4;
       
    77     }
    77     }
    78 
    78 
    79     // second initialize method. See JCA doc.
    79     // second initialize method. See JCA doc.
    80     public void initialize(AlgorithmParameterSpec params, SecureRandom random)
    80     public void initialize(AlgorithmParameterSpec params, SecureRandom random)
    81             throws InvalidAlgorithmParameterException {
    81             throws InvalidAlgorithmParameterException {
    82 
       
    83         if (params instanceof RSAKeyGenParameterSpec == false) {
    82         if (params instanceof RSAKeyGenParameterSpec == false) {
    84             throw new InvalidAlgorithmParameterException
    83             throw new InvalidAlgorithmParameterException
    85                 ("Params must be instance of RSAKeyGenParameterSpec");
    84                 ("Params must be instance of RSAKeyGenParameterSpec");
    86         }
    85         }
    87 
    86 
    88         RSAKeyGenParameterSpec rsaSpec = (RSAKeyGenParameterSpec)params;
    87         RSAKeyGenParameterSpec rsaSpec = (RSAKeyGenParameterSpec)params;
    89         int tmpKeySize = rsaSpec.getKeysize();
    88         int tmpKeySize = rsaSpec.getKeysize();
    90         BigInteger tmpPublicExponent = rsaSpec.getPublicExponent();
    89         BigInteger tmpPublicExponent = rsaSpec.getPublicExponent();
       
    90         AlgorithmParameterSpec tmpParams = rsaSpec.getKeyParams();
    91 
    91 
    92         if (tmpPublicExponent == null) {
    92         if (tmpPublicExponent == null) {
    93             tmpPublicExponent = RSAKeyGenParameterSpec.F4;
    93             tmpPublicExponent = RSAKeyGenParameterSpec.F4;
    94         } else {
    94         } else {
    95             if (tmpPublicExponent.compareTo(RSAKeyGenParameterSpec.F0) < 0) {
    95             if (tmpPublicExponent.compareTo(RSAKeyGenParameterSpec.F0) < 0) {
   107             RSAKeyFactory.checkKeyLengths(tmpKeySize, tmpPublicExponent,
   107             RSAKeyFactory.checkKeyLengths(tmpKeySize, tmpPublicExponent,
   108                 512, 64 * 1024);
   108                 512, 64 * 1024);
   109         } catch (InvalidKeyException e) {
   109         } catch (InvalidKeyException e) {
   110             throw new InvalidAlgorithmParameterException(
   110             throw new InvalidAlgorithmParameterException(
   111                 "Invalid key sizes", e);
   111                 "Invalid key sizes", e);
       
   112         }
       
   113 
       
   114         try {
       
   115             this.rsaId = RSAUtil.createAlgorithmId(type, tmpParams);
       
   116         } catch (ProviderException e) {
       
   117             throw new InvalidAlgorithmParameterException(
       
   118                 "Invalid key parameters", e);
   112         }
   119         }
   113 
   120 
   114         this.keySize = tmpKeySize;
   121         this.keySize = tmpKeySize;
   115         this.publicExponent = tmpPublicExponent;
   122         this.publicExponent = tmpPublicExponent;
   116         this.random = random;
   123         this.random = random;
   164 
   171 
   165             // crt coefficient coeff is the inverse of q mod p
   172             // crt coefficient coeff is the inverse of q mod p
   166             BigInteger coeff = q.modInverse(p);
   173             BigInteger coeff = q.modInverse(p);
   167 
   174 
   168             try {
   175             try {
   169                 PublicKey publicKey = new RSAPublicKeyImpl(n, e);
   176                 PublicKey publicKey = new RSAPublicKeyImpl(rsaId, n, e);
   170                 PrivateKey privateKey =
   177                 PrivateKey privateKey = new RSAPrivateCrtKeyImpl(
   171                         new RSAPrivateCrtKeyImpl(n, e, d, p, q, pe, qe, coeff);
   178                     rsaId, n, e, d, p, q, pe, qe, coeff);
   172                 return new KeyPair(publicKey, privateKey);
   179                 return new KeyPair(publicKey, privateKey);
   173             } catch (InvalidKeyException exc) {
   180             } catch (InvalidKeyException exc) {
   174                 // invalid key exception only thrown for keys < 512 bit,
   181                 // invalid key exception only thrown for keys < 512 bit,
   175                 // will not happen here
   182                 // will not happen here
   176                 throw new RuntimeException(exc);
   183                 throw new RuntimeException(exc);
   177             }
   184             }
   178         }
   185         }
   179     }
   186     }
   180 
   187 
       
   188     public static final class Legacy extends RSAKeyPairGenerator {
       
   189         public Legacy() {
       
   190             super(KeyType.RSA, DEF_RSA_KEY_SIZE);
       
   191         }
       
   192     }
       
   193 
       
   194     public static final class PSS extends RSAKeyPairGenerator {
       
   195         public PSS() {
       
   196             super(KeyType.PSS, DEF_RSASSA_PSS_KEY_SIZE);
       
   197         }
       
   198     }
   181 }
   199 }