src/java.base/share/classes/sun/security/pkcs10/PKCS10.java
author valeriep
Mon, 21 May 2018 23:40:52 +0000
changeset 50204 3195a713e24d
parent 47216 71c04702a3d5
child 53351 bdb29aa5fd31
child 56592 b1902b22005e
permissions -rw-r--r--
8146293: Add support for RSASSA-PSS Signature algorithm Summary: add RSASSA-PSS key and signature support to SunRsaSign provider Reviewed-by: wetmore
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     1
/*
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
     2
 * Copyright (c) 1996, 2018, Oracle and/or its affiliates. All rights reserved.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
90ce3da70b43 Initial load
duke
parents:
diff changeset
     4
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
90ce3da70b43 Initial load
duke
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
5506
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4350
diff changeset
     7
 * published by the Free Software Foundation.  Oracle designates this
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
5506
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4350
diff changeset
     9
 * by Oracle in the LICENSE file that accompanied this code.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    10
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
90ce3da70b43 Initial load
duke
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
90ce3da70b43 Initial load
duke
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
90ce3da70b43 Initial load
duke
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
90ce3da70b43 Initial load
duke
parents:
diff changeset
    15
 * accompanied this code).
90ce3da70b43 Initial load
duke
parents:
diff changeset
    16
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
90ce3da70b43 Initial load
duke
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    20
 *
5506
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4350
diff changeset
    21
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4350
diff changeset
    22
 * or visit www.oracle.com if you need additional information or have any
202f599c92aa 6943119: Rebrand source copyright notices
ohair
parents: 4350
diff changeset
    23
 * questions.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    24
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    25
90ce3da70b43 Initial load
duke
parents:
diff changeset
    26
10782
01689c7b34ac 6953295: Move few sun.security.{util, x509, pkcs} classes used by keytool/jarsigner to another package
mullan
parents: 10336
diff changeset
    27
package sun.security.pkcs10;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    28
90ce3da70b43 Initial load
duke
parents:
diff changeset
    29
import java.io.PrintStream;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    30
import java.io.IOException;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    31
import java.math.BigInteger;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    32
90ce3da70b43 Initial load
duke
parents:
diff changeset
    33
import java.security.cert.CertificateException;
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
    34
import java.security.*;
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
    35
import java.security.spec.AlgorithmParameterSpec;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    36
16020
b57c48f16179 8006182: cleanup to use java.util.Base64 in java security component, providers, and regression tests
msheppar
parents: 10782
diff changeset
    37
import java.util.Base64;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    38
90ce3da70b43 Initial load
duke
parents:
diff changeset
    39
import sun.security.util.*;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    40
import sun.security.x509.AlgorithmId;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    41
import sun.security.x509.X509Key;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    42
import sun.security.x509.X500Name;
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
    43
import sun.security.util.SignatureUtil;
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
    44
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
    45
90ce3da70b43 Initial load
duke
parents:
diff changeset
    46
/**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    47
 * A PKCS #10 certificate request is created and sent to a Certificate
90ce3da70b43 Initial load
duke
parents:
diff changeset
    48
 * Authority, which then creates an X.509 certificate and returns it to
90ce3da70b43 Initial load
duke
parents:
diff changeset
    49
 * the entity that requested it. A certificate request basically consists
90ce3da70b43 Initial load
duke
parents:
diff changeset
    50
 * of the subject's X.500 name, public key, and optionally some attributes,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    51
 * signed using the corresponding private key.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    52
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    53
 * The ASN.1 syntax for a Certification Request is:
90ce3da70b43 Initial load
duke
parents:
diff changeset
    54
 * <pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    55
 * CertificationRequest ::= SEQUENCE {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    56
 *    certificationRequestInfo CertificationRequestInfo,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    57
 *    signatureAlgorithm       SignatureAlgorithmIdentifier,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    58
 *    signature                Signature
90ce3da70b43 Initial load
duke
parents:
diff changeset
    59
 *  }
90ce3da70b43 Initial load
duke
parents:
diff changeset
    60
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    61
 * SignatureAlgorithmIdentifier ::= AlgorithmIdentifier
90ce3da70b43 Initial load
duke
parents:
diff changeset
    62
 * Signature ::= BIT STRING
90ce3da70b43 Initial load
duke
parents:
diff changeset
    63
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    64
 * CertificationRequestInfo ::= SEQUENCE {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    65
 *    version                 Version,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    66
 *    subject                 Name,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    67
 *    subjectPublicKeyInfo    SubjectPublicKeyInfo,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    68
 *    attributes [0] IMPLICIT Attributes
90ce3da70b43 Initial load
duke
parents:
diff changeset
    69
 * }
90ce3da70b43 Initial load
duke
parents:
diff changeset
    70
 * Attributes ::= SET OF Attribute
90ce3da70b43 Initial load
duke
parents:
diff changeset
    71
 * </pre>
90ce3da70b43 Initial load
duke
parents:
diff changeset
    72
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    73
 * @author David Brownell
90ce3da70b43 Initial load
duke
parents:
diff changeset
    74
 * @author Amit Kapoor
90ce3da70b43 Initial load
duke
parents:
diff changeset
    75
 * @author Hemma Prafullchandra
90ce3da70b43 Initial load
duke
parents:
diff changeset
    76
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    77
public class PKCS10 {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    78
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    79
     * Constructs an unsigned PKCS #10 certificate request.  Before this
90ce3da70b43 Initial load
duke
parents:
diff changeset
    80
     * request may be used, it must be encoded and signed.  Then it
90ce3da70b43 Initial load
duke
parents:
diff changeset
    81
     * must be retrieved in some conventional format (e.g. string).
90ce3da70b43 Initial load
duke
parents:
diff changeset
    82
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    83
     * @param publicKey the public key that should be placed
90ce3da70b43 Initial load
duke
parents:
diff changeset
    84
     *          into the certificate generated by the CA.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    85
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    86
    public PKCS10(PublicKey publicKey) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    87
        subjectPublicKeyInfo = publicKey;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    88
        attributeSet = new PKCS10Attributes();
90ce3da70b43 Initial load
duke
parents:
diff changeset
    89
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
    90
90ce3da70b43 Initial load
duke
parents:
diff changeset
    91
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    92
     * Constructs an unsigned PKCS #10 certificate request.  Before this
90ce3da70b43 Initial load
duke
parents:
diff changeset
    93
     * request may be used, it must be encoded and signed.  Then it
90ce3da70b43 Initial load
duke
parents:
diff changeset
    94
     * must be retrieved in some conventional format (e.g. string).
90ce3da70b43 Initial load
duke
parents:
diff changeset
    95
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    96
     * @param publicKey the public key that should be placed
90ce3da70b43 Initial load
duke
parents:
diff changeset
    97
     *          into the certificate generated by the CA.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    98
     * @param attributes additonal set of PKCS10 attributes requested
90ce3da70b43 Initial load
duke
parents:
diff changeset
    99
     *          for in the certificate.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   100
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   101
    public PKCS10(PublicKey publicKey, PKCS10Attributes attributes) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   102
        subjectPublicKeyInfo = publicKey;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   103
        attributeSet = attributes;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   104
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   105
90ce3da70b43 Initial load
duke
parents:
diff changeset
   106
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   107
     * Parses an encoded, signed PKCS #10 certificate request, verifying
90ce3da70b43 Initial load
duke
parents:
diff changeset
   108
     * the request's signature as it does so.  This constructor would
90ce3da70b43 Initial load
duke
parents:
diff changeset
   109
     * typically be used by a Certificate Authority, from which a new
90ce3da70b43 Initial load
duke
parents:
diff changeset
   110
     * certificate would then be constructed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   111
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   112
     * @param data the DER-encoded PKCS #10 request.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   113
     * @exception IOException for low level errors reading the data
90ce3da70b43 Initial load
duke
parents:
diff changeset
   114
     * @exception SignatureException when the signature is invalid
90ce3da70b43 Initial load
duke
parents:
diff changeset
   115
     * @exception NoSuchAlgorithmException when the signature
90ce3da70b43 Initial load
duke
parents:
diff changeset
   116
     *  algorithm is not supported in this environment
90ce3da70b43 Initial load
duke
parents:
diff changeset
   117
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   118
    public PKCS10(byte[] data)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   119
    throws IOException, SignatureException, NoSuchAlgorithmException {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   120
        DerInputStream  in;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   121
        DerValue[]      seq;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   122
        AlgorithmId     id;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   123
        byte[]          sigData;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   124
        Signature       sig;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   125
90ce3da70b43 Initial load
duke
parents:
diff changeset
   126
        encoded = data;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   127
90ce3da70b43 Initial load
duke
parents:
diff changeset
   128
        //
90ce3da70b43 Initial load
duke
parents:
diff changeset
   129
        // Outer sequence:  request, signature algorithm, signature.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   130
        // Parse, and prepare to verify later.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   131
        //
90ce3da70b43 Initial load
duke
parents:
diff changeset
   132
        in = new DerInputStream(data);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   133
        seq = in.getSequence(3);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   134
90ce3da70b43 Initial load
duke
parents:
diff changeset
   135
        if (seq.length != 3)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   136
            throw new IllegalArgumentException("not a PKCS #10 request");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   137
90ce3da70b43 Initial load
duke
parents:
diff changeset
   138
        data = seq[0].toByteArray();            // reusing this variable
90ce3da70b43 Initial load
duke
parents:
diff changeset
   139
        id = AlgorithmId.parse(seq[1]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   140
        sigData = seq[2].getBitString();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   141
90ce3da70b43 Initial load
duke
parents:
diff changeset
   142
        //
90ce3da70b43 Initial load
duke
parents:
diff changeset
   143
        // Inner sequence:  version, name, key, attributes
90ce3da70b43 Initial load
duke
parents:
diff changeset
   144
        //
90ce3da70b43 Initial load
duke
parents:
diff changeset
   145
        BigInteger      serial;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   146
        DerValue        val;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   147
90ce3da70b43 Initial load
duke
parents:
diff changeset
   148
        serial = seq[0].data.getBigInteger();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   149
        if (!serial.equals(BigInteger.ZERO))
90ce3da70b43 Initial load
duke
parents:
diff changeset
   150
            throw new IllegalArgumentException("not PKCS #10 v1");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   151
90ce3da70b43 Initial load
duke
parents:
diff changeset
   152
        subject = new X500Name(seq[0].data);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   153
        subjectPublicKeyInfo = X509Key.parse(seq[0].data.getDerValue());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   154
90ce3da70b43 Initial load
duke
parents:
diff changeset
   155
        // Cope with a somewhat common illegal PKCS #10 format
90ce3da70b43 Initial load
duke
parents:
diff changeset
   156
        if (seq[0].data.available() != 0)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   157
            attributeSet = new PKCS10Attributes(seq[0].data);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   158
        else
90ce3da70b43 Initial load
duke
parents:
diff changeset
   159
            attributeSet = new PKCS10Attributes();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   160
90ce3da70b43 Initial load
duke
parents:
diff changeset
   161
        if (seq[0].data.available() != 0)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   162
            throw new IllegalArgumentException("illegal PKCS #10 data");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   163
90ce3da70b43 Initial load
duke
parents:
diff changeset
   164
        //
90ce3da70b43 Initial load
duke
parents:
diff changeset
   165
        // OK, we parsed it all ... validate the signature using the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   166
        // key and signature algorithm we found.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   167
        //
90ce3da70b43 Initial load
duke
parents:
diff changeset
   168
        try {
44046
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   169
            sigAlg = id.getName();
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   170
            sig = Signature.getInstance(sigAlg);
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   171
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   172
            sig.initVerify(subjectPublicKeyInfo);
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   173
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   174
            // set parameters after Signature.initSign/initVerify call,
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   175
            // so the deferred provider selections occur when key is set
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   176
            SignatureUtil.specialSetParameter(sig, id.getParameters());
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   177
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   178
            sig.update(data);
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   179
            if (!sig.verify(sigData)) {
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   180
                throw new SignatureException("Invalid PKCS #10 signature");
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   181
            }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   182
        } catch (InvalidKeyException e) {
50204
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   183
            throw new SignatureException("Invalid key");
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   184
        } catch (InvalidAlgorithmParameterException e) {
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   185
            throw new SignatureException("Invalid signature parameters", e);
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   186
        } catch (ProviderException e) {
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   187
            throw new SignatureException("Error parsing signature parameters",
3195a713e24d 8146293: Add support for RSASSA-PSS Signature algorithm
valeriep
parents: 47216
diff changeset
   188
                e.getCause());
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   189
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   190
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   191
90ce3da70b43 Initial load
duke
parents:
diff changeset
   192
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   193
     * Create the signed certificate request.  This will later be
90ce3da70b43 Initial load
duke
parents:
diff changeset
   194
     * retrieved in either string or binary format.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   195
     *
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   196
     * @param subject identifies the signer (by X.500 name).
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   197
     * @param signature private key and signing algorithm to use.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   198
     * @exception IOException on errors.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   199
     * @exception CertificateException on certificate handling errors.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   200
     * @exception SignatureException on signature handling errors.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   201
     */
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   202
    public void encodeAndSign(X500Name subject, Signature signature)
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   203
    throws CertificateException, IOException, SignatureException {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   204
        DerOutputStream out, scratch;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   205
        byte[]          certificateRequestInfo;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   206
        byte[]          sig;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   207
90ce3da70b43 Initial load
duke
parents:
diff changeset
   208
        if (encoded != null)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   209
            throw new SignatureException("request is already signed");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   210
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   211
        this.subject = subject;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   212
90ce3da70b43 Initial load
duke
parents:
diff changeset
   213
        /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
   214
         * Encode cert request info, wrap in a sequence for signing
90ce3da70b43 Initial load
duke
parents:
diff changeset
   215
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   216
        scratch = new DerOutputStream();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   217
        scratch.putInteger(BigInteger.ZERO);            // PKCS #10 v1.0
90ce3da70b43 Initial load
duke
parents:
diff changeset
   218
        subject.encode(scratch);                        // X.500 name
90ce3da70b43 Initial load
duke
parents:
diff changeset
   219
        scratch.write(subjectPublicKeyInfo.getEncoded()); // public key
90ce3da70b43 Initial load
duke
parents:
diff changeset
   220
        attributeSet.encode(scratch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   221
90ce3da70b43 Initial load
duke
parents:
diff changeset
   222
        out = new DerOutputStream();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   223
        out.write(DerValue.tag_Sequence, scratch);      // wrap it!
90ce3da70b43 Initial load
duke
parents:
diff changeset
   224
        certificateRequestInfo = out.toByteArray();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   225
        scratch = out;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   226
90ce3da70b43 Initial load
duke
parents:
diff changeset
   227
        /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
   228
         * Sign it ...
90ce3da70b43 Initial load
duke
parents:
diff changeset
   229
         */
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   230
        signature.update(certificateRequestInfo, 0,
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   231
                certificateRequestInfo.length);
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   232
        sig = signature.sign();
44046
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   233
        sigAlg = signature.getAlgorithm();
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   234
90ce3da70b43 Initial load
duke
parents:
diff changeset
   235
        /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
   236
         * Build guts of SIGNED macro
90ce3da70b43 Initial load
duke
parents:
diff changeset
   237
         */
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   238
        AlgorithmId algId = null;
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   239
        try {
10336
0bb1999251f8 7064075: Security libraries don't build with javac -Xlint:all,-deprecation -Werror
jjg
parents: 5506
diff changeset
   240
            algId = AlgorithmId.get(signature.getAlgorithm());
4350
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   241
        } catch (NoSuchAlgorithmException nsae) {
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   242
            throw new SignatureException(nsae);
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   243
        }
2a593a20d962 6876158: Remove dependencies on Signer, Certificate, Identity, IdentityScope classes from java.security pkg
vinnie
parents: 2
diff changeset
   244
        algId.encode(scratch);     // sig algorithm
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   245
        scratch.putBitString(sig);                      // sig
90ce3da70b43 Initial load
duke
parents:
diff changeset
   246
90ce3da70b43 Initial load
duke
parents:
diff changeset
   247
        /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
   248
         * Wrap those guts in a sequence
90ce3da70b43 Initial load
duke
parents:
diff changeset
   249
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   250
        out = new DerOutputStream();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   251
        out.write(DerValue.tag_Sequence, scratch);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   252
        encoded = out.toByteArray();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   253
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   254
90ce3da70b43 Initial load
duke
parents:
diff changeset
   255
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   256
     * Returns the subject's name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   257
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   258
    public X500Name getSubjectName() { return subject; }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   259
90ce3da70b43 Initial load
duke
parents:
diff changeset
   260
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   261
     * Returns the subject's public key.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   262
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   263
    public PublicKey getSubjectPublicKeyInfo()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   264
        { return subjectPublicKeyInfo; }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   265
90ce3da70b43 Initial load
duke
parents:
diff changeset
   266
    /**
44046
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   267
     * Returns the signature algorithm.
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   268
     */
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   269
    public String getSigAlg() { return sigAlg; }
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   270
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   271
    /**
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   272
     * Returns the additional attributes requested.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   273
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   274
    public PKCS10Attributes getAttributes()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   275
        { return attributeSet; }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   276
90ce3da70b43 Initial load
duke
parents:
diff changeset
   277
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   278
     * Returns the encoded and signed certificate request as a
90ce3da70b43 Initial load
duke
parents:
diff changeset
   279
     * DER-encoded byte array.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   280
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   281
     * @return the certificate request, or null if encodeAndSign()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   282
     *          has not yet been called.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   283
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   284
    public byte[] getEncoded() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   285
        if (encoded != null)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   286
            return encoded.clone();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   287
        else
90ce3da70b43 Initial load
duke
parents:
diff changeset
   288
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   289
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   290
90ce3da70b43 Initial load
duke
parents:
diff changeset
   291
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   292
     * Prints an E-Mailable version of the certificate request on the print
90ce3da70b43 Initial load
duke
parents:
diff changeset
   293
     * stream passed.  The format is a common base64 encoded one, supported
90ce3da70b43 Initial load
duke
parents:
diff changeset
   294
     * by most Certificate Authorities because Netscape web servers have
90ce3da70b43 Initial load
duke
parents:
diff changeset
   295
     * used this for some time.  Some certificate authorities expect some
90ce3da70b43 Initial load
duke
parents:
diff changeset
   296
     * more information, in particular contact information for the web
90ce3da70b43 Initial load
duke
parents:
diff changeset
   297
     * server administrator.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   298
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   299
     * @param out the print stream where the certificate request
90ce3da70b43 Initial load
duke
parents:
diff changeset
   300
     *  will be printed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   301
     * @exception IOException when an output operation failed
90ce3da70b43 Initial load
duke
parents:
diff changeset
   302
     * @exception SignatureException when the certificate request was
90ce3da70b43 Initial load
duke
parents:
diff changeset
   303
     *  not yet signed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   304
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   305
    public void print(PrintStream out)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   306
    throws IOException, SignatureException {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   307
        if (encoded == null)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   308
            throw new SignatureException("Cert request was not signed");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   309
90ce3da70b43 Initial load
duke
parents:
diff changeset
   310
29596
70399c7a7f5a 8074935: jdk8 keytool doesn't validate pem files for RFC 1421 correctness, as jdk7 did
weijun
parents: 25859
diff changeset
   311
        byte[] CRLF = new byte[] {'\r', '\n'};
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   312
        out.println("-----BEGIN NEW CERTIFICATE REQUEST-----");
29596
70399c7a7f5a 8074935: jdk8 keytool doesn't validate pem files for RFC 1421 correctness, as jdk7 did
weijun
parents: 25859
diff changeset
   313
        out.println(Base64.getMimeEncoder(64, CRLF).encodeToString(encoded));
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   314
        out.println("-----END NEW CERTIFICATE REQUEST-----");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   315
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   316
90ce3da70b43 Initial load
duke
parents:
diff changeset
   317
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   318
     * Provides a short description of this request.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   319
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   320
    public String toString() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   321
        return "[PKCS #10 certificate request:\n"
90ce3da70b43 Initial load
duke
parents:
diff changeset
   322
            + subjectPublicKeyInfo.toString()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   323
            + " subject: <" + subject + ">" + "\n"
90ce3da70b43 Initial load
duke
parents:
diff changeset
   324
            + " attributes: " + attributeSet.toString()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   325
            + "\n]";
90ce3da70b43 Initial load
duke
parents:
diff changeset
   326
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   327
90ce3da70b43 Initial load
duke
parents:
diff changeset
   328
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   329
     * Compares this object for equality with the specified
90ce3da70b43 Initial load
duke
parents:
diff changeset
   330
     * object. If the <code>other</code> object is an
90ce3da70b43 Initial load
duke
parents:
diff changeset
   331
     * <code>instanceof</code> <code>PKCS10</code>, then
90ce3da70b43 Initial load
duke
parents:
diff changeset
   332
     * its encoded form is retrieved and compared with the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   333
     * encoded form of this certificate request.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   334
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   335
     * @param other the object to test for equality with this object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   336
     * @return true iff the encoded forms of the two certificate
90ce3da70b43 Initial load
duke
parents:
diff changeset
   337
     * requests match, false otherwise.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   338
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   339
    public boolean equals(Object other) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   340
        if (this == other)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   341
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   342
        if (!(other instanceof PKCS10))
90ce3da70b43 Initial load
duke
parents:
diff changeset
   343
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   344
        if (encoded == null) // not signed yet
90ce3da70b43 Initial load
duke
parents:
diff changeset
   345
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   346
        byte[] otherEncoded = ((PKCS10)other).getEncoded();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   347
        if (otherEncoded == null)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   348
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   349
90ce3da70b43 Initial load
duke
parents:
diff changeset
   350
        return java.util.Arrays.equals(encoded, otherEncoded);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   351
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   352
90ce3da70b43 Initial load
duke
parents:
diff changeset
   353
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   354
     * Returns a hashcode value for this certificate request from its
90ce3da70b43 Initial load
duke
parents:
diff changeset
   355
     * encoded form.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   356
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   357
     * @return the hashcode value.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   358
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   359
    public int hashCode() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   360
        int     retval = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   361
        if (encoded != null)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   362
            for (int i = 1; i < encoded.length; i++)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   363
             retval += encoded[i] * i;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   364
        return(retval);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   365
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   366
90ce3da70b43 Initial load
duke
parents:
diff changeset
   367
    private X500Name            subject;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   368
    private PublicKey           subjectPublicKeyInfo;
44046
762e807bfac1 8171319: keytool should print out warnings when reading or generating cert/cert req using weak algorithms
weijun
parents: 29596
diff changeset
   369
    private String              sigAlg;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   370
    private PKCS10Attributes    attributeSet;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   371
    private byte[]              encoded;        // signed
90ce3da70b43 Initial load
duke
parents:
diff changeset
   372
}