View Javadoc

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.io.ObjectInputStream;
24  import java.io.ObjectOutputStream;
25  import java.math.BigInteger;
26  import java.util.Enumeration;
27  import java.util.Hashtable;
28  import java.util.Vector;
29  
30  import javax.crypto.interfaces.DHPrivateKey;
31  import javax.crypto.spec.DHParameterSpec;
32  import javax.crypto.spec.DHPrivateKeySpec;
33  
34  import org.apache.geronimo.util.asn1.ASN1Sequence;
35  import org.apache.geronimo.util.asn1.DEREncodable;
36  import org.apache.geronimo.util.asn1.DERInteger;
37  import org.apache.geronimo.util.asn1.DERObjectIdentifier;
38  import org.apache.geronimo.util.asn1.DEROutputStream;
39  import org.apache.geronimo.util.asn1.pkcs.DHParameter;
40  import org.apache.geronimo.util.asn1.pkcs.PKCSObjectIdentifiers;
41  import org.apache.geronimo.util.asn1.pkcs.PrivateKeyInfo;
42  import org.apache.geronimo.util.asn1.x509.AlgorithmIdentifier;
43  import org.apache.geronimo.util.crypto.params.DHPrivateKeyParameters;
44  import org.apache.geronimo.util.jce.interfaces.PKCS12BagAttributeCarrier;
45  
46  public class JCEDHPrivateKey
47      implements DHPrivateKey, PKCS12BagAttributeCarrier
48  {
49      BigInteger      x;
50  
51      DHParameterSpec dhSpec;
52  
53      private Hashtable   pkcs12Attributes = new Hashtable();
54      private Vector      pkcs12Ordering = new Vector();
55  
56      protected JCEDHPrivateKey()
57      {
58      }
59  
60      JCEDHPrivateKey(
61          DHPrivateKey    key)
62      {
63          this.x = key.getX();
64          this.dhSpec = key.getParams();
65      }
66  
67      JCEDHPrivateKey(
68          DHPrivateKeySpec    spec)
69      {
70          this.x = spec.getX();
71          this.dhSpec = new DHParameterSpec(spec.getP(), spec.getG());
72      }
73  
74      JCEDHPrivateKey(
75          PrivateKeyInfo  info)
76      {
77          DHParameter     params = new DHParameter((ASN1Sequence)info.getAlgorithmId().getParameters());
78          DERInteger      derX = (DERInteger)info.getPrivateKey();
79  
80          this.x = derX.getValue();
81          if (params.getL() != null)
82          {
83              this.dhSpec = new DHParameterSpec(params.getP(), params.getG(), params.getL().intValue());
84          }
85          else
86          {
87              this.dhSpec = new DHParameterSpec(params.getP(), params.getG());
88          }
89      }
90  
91      JCEDHPrivateKey(
92          DHPrivateKeyParameters  params)
93      {
94          this.x = params.getX();
95          this.dhSpec = new DHParameterSpec(params.getParameters().getP(), params.getParameters().getG());
96      }
97  
98      public String getAlgorithm()
99      {
100         return "DH";
101     }
102 
103     /**
104      * return the encoding format we produce in getEncoded().
105      *
106      * @return the string "PKCS#8"
107      */
108     public String getFormat()
109     {
110         return "PKCS#8";
111     }
112 
113     /**
114      * Return a PKCS8 representation of the key. The sequence returned
115      * represents a full PrivateKeyInfo object.
116      *
117      * @return a PKCS8 representation of the key.
118      */
119     public byte[] getEncoded()
120     {
121         ByteArrayOutputStream   bOut = new ByteArrayOutputStream();
122         DEROutputStream         dOut = new DEROutputStream(bOut);
123         PrivateKeyInfo          info = new PrivateKeyInfo(new AlgorithmIdentifier(PKCSObjectIdentifiers.dhKeyAgreement, new DHParameter(dhSpec.getP(), dhSpec.getG(), dhSpec.getL()).getDERObject()), new DERInteger(getX()));
124 
125         try
126         {
127             dOut.writeObject(info);
128             dOut.close();
129         }
130         catch (IOException e)
131         {
132             throw new RuntimeException("Error encoding DH private key");
133         }
134 
135         return bOut.toByteArray();
136     }
137 
138     public DHParameterSpec getParams()
139     {
140         return dhSpec;
141     }
142 
143     public BigInteger getX()
144     {
145         return x;
146     }
147 
148     private void readObject(
149         ObjectInputStream   in)
150         throws IOException, ClassNotFoundException
151     {
152         x = (BigInteger)in.readObject();
153 
154         this.dhSpec = new DHParameterSpec((BigInteger)in.readObject(), (BigInteger)in.readObject(), in.readInt());
155     }
156 
157     private void writeObject(
158         ObjectOutputStream  out)
159         throws IOException
160     {
161         out.writeObject(this.getX());
162         out.writeObject(dhSpec.getP());
163         out.writeObject(dhSpec.getG());
164         out.writeInt(dhSpec.getL());
165     }
166 
167     public void setBagAttribute(
168         DERObjectIdentifier oid,
169         DEREncodable        attribute)
170     {
171         pkcs12Attributes.put(oid, attribute);
172         pkcs12Ordering.addElement(oid);
173     }
174 
175     public DEREncodable getBagAttribute(
176         DERObjectIdentifier oid)
177     {
178         return (DEREncodable)pkcs12Attributes.get(oid);
179     }
180 
181     public Enumeration getBagAttributeKeys()
182     {
183         return pkcs12Ordering.elements();
184     }
185 }