1 /**
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one or more
4 * contributor license agreements. See the NOTICE file distributed with
5 * this work for additional information regarding copyright ownership.
6 * The ASF licenses this file to You under the Apache License, Version 2.0
7 * (the "License"); you may not use this file except in compliance with
8 * the License. You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 */
18
19 package org.apache.geronimo.util.jce.provider;
20
21 import java.io.ByteArrayOutputStream;
22 import java.io.IOException;
23 import java.math.BigInteger;
24 import java.security.interfaces.RSAPrivateCrtKey;
25 import java.security.spec.RSAPrivateCrtKeySpec;
26
27 import org.apache.geronimo.util.asn1.ASN1Sequence;
28 import org.apache.geronimo.util.asn1.DERNull;
29 import org.apache.geronimo.util.asn1.DEROutputStream;
30 import org.apache.geronimo.util.asn1.pkcs.PKCSObjectIdentifiers;
31 import org.apache.geronimo.util.asn1.pkcs.PrivateKeyInfo;
32 import org.apache.geronimo.util.asn1.pkcs.RSAPrivateKeyStructure;
33 import org.apache.geronimo.util.asn1.x509.AlgorithmIdentifier;
34 import org.apache.geronimo.util.crypto.params.RSAPrivateCrtKeyParameters;
35
36 /**
37 * A provider representation for a RSA private key, with CRT factors included.
38 */
39 public class JCERSAPrivateCrtKey
40 extends JCERSAPrivateKey
41 implements RSAPrivateCrtKey
42 {
43 private BigInteger publicExponent;
44 private BigInteger primeP;
45 private BigInteger primeQ;
46 private BigInteger primeExponentP;
47 private BigInteger primeExponentQ;
48 private BigInteger crtCoefficient;
49
50 /**
51 * construct a private key from it's org.apache.geronimo.util.crypto equivalent.
52 *
53 * @param key the parameters object representing the private key.
54 */
55 JCERSAPrivateCrtKey(
56 RSAPrivateCrtKeyParameters key)
57 {
58 super(key);
59
60 this.publicExponent = key.getPublicExponent();
61 this.primeP = key.getP();
62 this.primeQ = key.getQ();
63 this.primeExponentP = key.getDP();
64 this.primeExponentQ = key.getDQ();
65 this.crtCoefficient = key.getQInv();
66 }
67
68 /**
69 * construct a private key from an RSAPrivateCrtKeySpec
70 *
71 * @param spec the spec to be used in construction.
72 */
73 JCERSAPrivateCrtKey(
74 RSAPrivateCrtKeySpec spec)
75 {
76 this.modulus = spec.getModulus();
77 this.publicExponent = spec.getPublicExponent();
78 this.privateExponent = spec.getPrivateExponent();
79 this.primeP = spec.getPrimeP();
80 this.primeQ = spec.getPrimeQ();
81 this.primeExponentP = spec.getPrimeExponentP();
82 this.primeExponentQ = spec.getPrimeExponentQ();
83 this.crtCoefficient = spec.getCrtCoefficient();
84 }
85
86 /**
87 * construct a private key from another RSAPrivateCrtKey.
88 *
89 * @param key the object implementing the RSAPrivateCrtKey interface.
90 */
91 JCERSAPrivateCrtKey(
92 RSAPrivateCrtKey key)
93 {
94 this.modulus = key.getModulus();
95 this.publicExponent = key.getPublicExponent();
96 this.privateExponent = key.getPrivateExponent();
97 this.primeP = key.getPrimeP();
98 this.primeQ = key.getPrimeQ();
99 this.primeExponentP = key.getPrimeExponentP();
100 this.primeExponentQ = key.getPrimeExponentQ();
101 this.crtCoefficient = key.getCrtCoefficient();
102 }
103
104 /**
105 * construct an RSA key from a private key info object.
106 */
107 JCERSAPrivateCrtKey(
108 PrivateKeyInfo info)
109 {
110 this(new RSAPrivateKeyStructure((ASN1Sequence)info.getPrivateKey()));
111 }
112
113 /**
114 * construct an RSA key from a ASN.1 RSA private key object.
115 */
116 JCERSAPrivateCrtKey(
117 RSAPrivateKeyStructure key)
118 {
119 this.modulus = key.getModulus();
120 this.publicExponent = key.getPublicExponent();
121 this.privateExponent = key.getPrivateExponent();
122 this.primeP = key.getPrime1();
123 this.primeQ = key.getPrime2();
124 this.primeExponentP = key.getExponent1();
125 this.primeExponentQ = key.getExponent2();
126 this.crtCoefficient = key.getCoefficient();
127 }
128
129 /**
130 * return the encoding format we produce in getEncoded().
131 *
132 * @return the encoding format we produce in getEncoded().
133 */
134 public String getFormat()
135 {
136 return "PKCS#8";
137 }
138
139 /**
140 * Return a PKCS8 representation of the key. The sequence returned
141 * represents a full PrivateKeyInfo object.
142 *
143 * @return a PKCS8 representation of the key.
144 */
145 public byte[] getEncoded()
146 {
147 ByteArrayOutputStream bOut = new ByteArrayOutputStream();
148 DEROutputStream dOut = new DEROutputStream(bOut);
149 PrivateKeyInfo info = new PrivateKeyInfo(new AlgorithmIdentifier(PKCSObjectIdentifiers.rsaEncryption, new DERNull()), new RSAPrivateKeyStructure(getModulus(), getPublicExponent(), getPrivateExponent(), getPrimeP(), getPrimeQ(), getPrimeExponentP(), getPrimeExponentQ(), getCrtCoefficient()).getDERObject());
150
151 try
152 {
153 dOut.writeObject(info);
154 dOut.close();
155 }
156 catch (IOException e)
157 {
158 throw new RuntimeException("Error encoding RSA public key");
159 }
160
161 return bOut.toByteArray();
162 }
163
164 /**
165 * return the public exponent.
166 *
167 * @return the public exponent.
168 */
169 public BigInteger getPublicExponent()
170 {
171 return publicExponent;
172 }
173
174 /**
175 * return the prime P.
176 *
177 * @return the prime P.
178 */
179 public BigInteger getPrimeP()
180 {
181 return primeP;
182 }
183
184 /**
185 * return the prime Q.
186 *
187 * @return the prime Q.
188 */
189 public BigInteger getPrimeQ()
190 {
191 return primeQ;
192 }
193
194 /**
195 * return the prime exponent for P.
196 *
197 * @return the prime exponent for P.
198 */
199 public BigInteger getPrimeExponentP()
200 {
201 return primeExponentP;
202 }
203
204 /**
205 * return the prime exponent for Q.
206 *
207 * @return the prime exponent for Q.
208 */
209 public BigInteger getPrimeExponentQ()
210 {
211 return primeExponentQ;
212 }
213
214 /**
215 * return the CRT coefficient.
216 *
217 * @return the CRT coefficient.
218 */
219 public BigInteger getCrtCoefficient()
220 {
221 return crtCoefficient;
222 }
223
224 public boolean equals(Object o)
225 {
226 if ( !(o instanceof RSAPrivateCrtKey) )
227 {
228 return false;
229 }
230
231 if ( o == this )
232 {
233 return true;
234 }
235
236 RSAPrivateCrtKey key = (RSAPrivateCrtKey)o;
237
238 return this.getModulus().equals(key.getModulus())
239 && this.getPublicExponent().equals(key.getPublicExponent())
240 && this.getPrivateExponent().equals(key.getPrivateExponent())
241 && this.getPrimeP().equals(key.getPrimeP())
242 && this.getPrimeQ().equals(key.getPrimeQ())
243 && this.getPrimeExponentP().equals(key.getPrimeExponentP())
244 && this.getPrimeExponentQ().equals(key.getPrimeExponentQ())
245 && this.getCrtCoefficient().equals(key.getCrtCoefficient());
246 }
247
248 public String toString()
249 {
250 StringBuffer buf = new StringBuffer();
251 String nl = System.getProperty("line.separator");
252
253 buf.append("RSA Private CRT Key" + nl);
254 buf.append(" modulus: " + this.getModulus().toString(16) + nl);
255 buf.append(" public exponent: " + this.getPublicExponent().toString(16) + nl);
256 buf.append(" private exponent: " + this.getPrivateExponent().toString(16) + nl);
257 buf.append(" primeP: " + this.getPrimeP().toString(16) + nl);
258 buf.append(" primeQ: " + this.getPrimeQ().toString(16) + nl);
259 buf.append(" primeExponentP: " + this.getPrimeExponentP().toString(16) + nl);
260 buf.append(" primeExponentQ: " + this.getPrimeExponentQ().toString(16) + nl);
261 buf.append(" crtCoefficient: " + this.getCrtCoefficient().toString(16) + nl);
262
263 return buf.toString();
264 }
265 }