diff options
author | Ade Lee <alee@redhat.com> | 2011-12-07 16:58:12 -0500 |
---|---|---|
committer | Ade Lee <alee@redhat.com> | 2011-12-07 16:58:12 -0500 |
commit | 32150d3ee32f8ac27118af7c792794b538c78a2f (patch) | |
tree | 52dd96f664a6fa51be25b28b6f10adc5f2c9f660 /pki/base/util/src/netscape/security/pkcs/PKCS8Key.java | |
parent | f05d58a46795553beb8881039cc922974b40db34 (diff) | |
download | pki-32150d3ee32f8ac27118af7c792794b538c78a2f.tar.gz pki-32150d3ee32f8ac27118af7c792794b538c78a2f.tar.xz pki-32150d3ee32f8ac27118af7c792794b538c78a2f.zip |
Formatting
Formatted project according to eclipse project settings
Diffstat (limited to 'pki/base/util/src/netscape/security/pkcs/PKCS8Key.java')
-rw-r--r-- | pki/base/util/src/netscape/security/pkcs/PKCS8Key.java | 561 |
1 files changed, 276 insertions, 285 deletions
diff --git a/pki/base/util/src/netscape/security/pkcs/PKCS8Key.java b/pki/base/util/src/netscape/security/pkcs/PKCS8Key.java index 20a788fcb..5d05b0663 100644 --- a/pki/base/util/src/netscape/security/pkcs/PKCS8Key.java +++ b/pki/base/util/src/netscape/security/pkcs/PKCS8Key.java @@ -40,7 +40,7 @@ import netscape.security.x509.AlgorithmId; /** * Holds a PKCS#8 key, for example a private key - * + * * @version 1.30, 97/12/10 * @author Dave Brownell * @author Benjamin Renaud @@ -61,394 +61,385 @@ public class PKCS8Key implements PrivateKey { /* The version for this key */ public static final BigInteger VERSION = BigInteger.valueOf(0); - + /** - * Default constructor. The key constructed must have its key - * and algorithm initialized before it may be used, for example - * by using <code>decode</code>. + * Default constructor. The key constructed must have its key and algorithm + * initialized before it may be used, for example by using + * <code>decode</code>. */ - public PKCS8Key() { } + public PKCS8Key() { + } /* - * Build and initialize as a "default" key. All PKCS#8 key - * data is stored and transmitted losslessly, but no knowledge - * about this particular algorithm is available. + * Build and initialize as a "default" key. All PKCS#8 key data is stored + * and transmitted losslessly, but no knowledge about this particular + * algorithm is available. */ - private PKCS8Key (AlgorithmId algid, byte key []) - throws InvalidKeyException { - this.algid = algid; - this.key = key; - encode(); + private PKCS8Key(AlgorithmId algid, byte key[]) throws InvalidKeyException { + this.algid = algid; + this.key = key; + encode(); } /** - * Construct PKCS#8 subject public key from a DER value. If - * the runtime environment is configured with a specific class for - * this kind of key, a subclass is returned. Otherwise, a generic - * PKCS8Key object is returned. + * Construct PKCS#8 subject public key from a DER value. If the runtime + * environment is configured with a specific class for this kind of key, a + * subclass is returned. Otherwise, a generic PKCS8Key object is returned. + * + * <P> + * This mechanism gurantees that keys (and algorithms) may be freely + * manipulated and transferred, without risk of losing information. Also, + * when a key (or algorithm) needs some special handling, that specific need + * can be accomodated. * - * <P>This mechanism gurantees that keys (and algorithms) may be - * freely manipulated and transferred, without risk of losing - * information. Also, when a key (or algorithm) needs some special - * handling, that specific need can be accomodated. - * * @param in the DER-encoded SubjectPublicKeyInfo value * @exception IOException on data format errors */ - public static PKCS8Key parse (DerValue in) throws IOException - { - AlgorithmId algorithm; - PKCS8Key subjectKey; - - if (in.tag != DerValue.tag_Sequence) - throw new IOException ("corrupt private key"); - - BigInteger parsedVersion = in.data.getInteger().toBigInteger(); - if (!VERSION.equals(parsedVersion)) { - throw new IOException("version mismatch: (supported: " + - VERSION + ", parsed: " + - parsedVersion); - } - - algorithm = AlgorithmId.parse (in.data.getDerValue ()); - - try { - subjectKey = buildPKCS8Key (algorithm, in.data.getOctetString ()); - - } catch (InvalidKeyException e) { - throw new IOException("corrupt private key"); - } - - if (in.data.available () != 0) - throw new IOException ("excess private key"); - return subjectKey; + public static PKCS8Key parse(DerValue in) throws IOException { + AlgorithmId algorithm; + PKCS8Key subjectKey; + + if (in.tag != DerValue.tag_Sequence) + throw new IOException("corrupt private key"); + + BigInteger parsedVersion = in.data.getInteger().toBigInteger(); + if (!VERSION.equals(parsedVersion)) { + throw new IOException("version mismatch: (supported: " + VERSION + + ", parsed: " + parsedVersion); + } + + algorithm = AlgorithmId.parse(in.data.getDerValue()); + + try { + subjectKey = buildPKCS8Key(algorithm, in.data.getOctetString()); + + } catch (InvalidKeyException e) { + throw new IOException("corrupt private key"); + } + + if (in.data.available() != 0) + throw new IOException("excess private key"); + return subjectKey; } /** - * Parse the key bits. This may be redefined by subclasses to take - * advantage of structure within the key. For example, RSA public - * keys encapsulate two unsigned integers (modulus and exponent) as - * DER values within the <code>key</code> bits; Diffie-Hellman and - * DSS/DSA keys encapsulate a single unsigned integer. - * - * <P>This function is called when creating PKCS#8 SubjectPublicKeyInfo - * values using the PKCS8Key member functions, such as <code>parse</code> - * and <code>decode</code>. - * + * Parse the key bits. This may be redefined by subclasses to take advantage + * of structure within the key. For example, RSA public keys encapsulate two + * unsigned integers (modulus and exponent) as DER values within the + * <code>key</code> bits; Diffie-Hellman and DSS/DSA keys encapsulate a + * single unsigned integer. + * + * <P> + * This function is called when creating PKCS#8 SubjectPublicKeyInfo values + * using the PKCS8Key member functions, such as <code>parse</code> and + * <code>decode</code>. + * * @exception IOException if a parsing error occurs. * @exception InvalidKeyException if the key encoding is invalid. */ - protected void parseKeyBits () throws IOException, InvalidKeyException { - encode(); + protected void parseKeyBits() throws IOException, InvalidKeyException { + encode(); } /* - * Factory interface, building the kind of key associated with this - * specific algorithm ID or else returning this generic base class. - * See the description above. + * Factory interface, building the kind of key associated with this specific + * algorithm ID or else returning this generic base class. See the + * description above. */ - public static PKCS8Key buildPKCS8Key (AlgorithmId algid, byte[] key) - throws IOException, InvalidKeyException - { - /* - * Use the algid and key parameters to produce the ASN.1 encoding - * of the key, which will then be used as the input to the - * key factory. - */ - DerOutputStream pkcs8EncodedKeyStream = new DerOutputStream(); - encode(pkcs8EncodedKeyStream, algid, key); - PKCS8EncodedKeySpec pkcs8KeySpec - = new PKCS8EncodedKeySpec(pkcs8EncodedKeyStream.toByteArray()); - - try { - // Instantiate the key factory of the appropriate algorithm - KeyFactory keyFac = KeyFactory.getInstance(algid.getName()); - - // Generate the private key - PrivateKey privKey = keyFac.generatePrivate(pkcs8KeySpec); - - if (privKey instanceof PKCS8Key) { - /* - * Return specialized PKCS8Key, where the structure within the - * key has been parsed - */ - return (PKCS8Key)privKey; - } - } catch (NoSuchAlgorithmException e) { - // Return generic PKCS8Key with opaque key data (see below) - } catch (InvalidKeySpecException e) { - // Return generic PKCS8Key with opaque key data (see below) - } - - /* - * Try again using JDK1.1-style for backwards compatibility. - */ - String classname = ""; - try { - Properties props; - String keytype; - Provider sunProvider; - - sunProvider = Security.getProvider("SUN"); - if (sunProvider == null) - throw new InstantiationException(); - classname = sunProvider.getProperty("PrivateKey.PKCS#8." + - algid.getName()); - if (classname == null) { - throw new InstantiationException(); - } - - Class keyClass = Class.forName(classname); - Object inst; - PKCS8Key result; - - inst = keyClass.newInstance(); - if (inst instanceof PKCS8Key) { - result = (PKCS8Key) inst; - result.algid = algid; - result.key = key; - result.parseKeyBits(); - return result; - } - } catch (ClassNotFoundException e) { - } catch (InstantiationException e) { - } catch (IllegalAccessException e) { - // this should not happen. - throw new IOException (classname + " [internal error]"); - } - - PKCS8Key result = new PKCS8Key(); - result.algid = algid; - result.key = key; - return result; + public static PKCS8Key buildPKCS8Key(AlgorithmId algid, byte[] key) + throws IOException, InvalidKeyException { + /* + * Use the algid and key parameters to produce the ASN.1 encoding of the + * key, which will then be used as the input to the key factory. + */ + DerOutputStream pkcs8EncodedKeyStream = new DerOutputStream(); + encode(pkcs8EncodedKeyStream, algid, key); + PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec( + pkcs8EncodedKeyStream.toByteArray()); + + try { + // Instantiate the key factory of the appropriate algorithm + KeyFactory keyFac = KeyFactory.getInstance(algid.getName()); + + // Generate the private key + PrivateKey privKey = keyFac.generatePrivate(pkcs8KeySpec); + + if (privKey instanceof PKCS8Key) { + /* + * Return specialized PKCS8Key, where the structure within the + * key has been parsed + */ + return (PKCS8Key) privKey; + } + } catch (NoSuchAlgorithmException e) { + // Return generic PKCS8Key with opaque key data (see below) + } catch (InvalidKeySpecException e) { + // Return generic PKCS8Key with opaque key data (see below) + } + + /* + * Try again using JDK1.1-style for backwards compatibility. + */ + String classname = ""; + try { + Properties props; + String keytype; + Provider sunProvider; + + sunProvider = Security.getProvider("SUN"); + if (sunProvider == null) + throw new InstantiationException(); + classname = sunProvider.getProperty("PrivateKey.PKCS#8." + + algid.getName()); + if (classname == null) { + throw new InstantiationException(); + } + + Class keyClass = Class.forName(classname); + Object inst; + PKCS8Key result; + + inst = keyClass.newInstance(); + if (inst instanceof PKCS8Key) { + result = (PKCS8Key) inst; + result.algid = algid; + result.key = key; + result.parseKeyBits(); + return result; + } + } catch (ClassNotFoundException e) { + } catch (InstantiationException e) { + } catch (IllegalAccessException e) { + // this should not happen. + throw new IOException(classname + " [internal error]"); + } + + PKCS8Key result = new PKCS8Key(); + result.algid = algid; + result.key = key; + return result; } /** * Returns the algorithm to be used with this key. */ - public String getAlgorithm() { - return algid.getName(); + public String getAlgorithm() { + return algid.getName(); } /** * Returns the algorithm ID to be used with this key. */ - public AlgorithmId getAlgorithmId () { return algid; } + public AlgorithmId getAlgorithmId() { + return algid; + } /** * PKCS#8 sequence on the DER output stream. */ - public final void encode(DerOutputStream out) throws IOException - { - encode(out, this.algid, this.key); + public final void encode(DerOutputStream out) throws IOException { + encode(out, this.algid, this.key); } /** * Returns the DER-encoded form of the key as a byte array. */ public synchronized byte[] getEncoded() { - byte[] result = null; - try { - result = encode(); - } catch (InvalidKeyException e) { - } - return result; + byte[] result = null; + try { + result = encode(); + } catch (InvalidKeyException e) { + } + return result; } /** * Returns the format for this key: "PKCS#8" */ public String getFormat() { - return "PKCS#8"; + return "PKCS#8"; } /** * Returns the DER-encoded form of the key as a byte array. - * + * * @exception InvalidKeyException if an encoding error occurs. */ public byte[] encode() throws InvalidKeyException { - if (encodedKey == null) { - try { - DerOutputStream out; - - out = new DerOutputStream (); - encode (out); - encodedKey = out.toByteArray(); - - } catch (IOException e) { - throw new InvalidKeyException ("IOException : " + - e.getMessage()); - } - } - return copyEncodedKey(encodedKey); + if (encodedKey == null) { + try { + DerOutputStream out; + + out = new DerOutputStream(); + encode(out); + encodedKey = out.toByteArray(); + + } catch (IOException e) { + throw new InvalidKeyException("IOException : " + e.getMessage()); + } + } + return copyEncodedKey(encodedKey); } /* * Returns a printable representation of the key */ - public String toString () - { - netscape.security.util.PrettyPrintFormat pp = - new netscape.security.util.PrettyPrintFormat(" ", 20); - String keybits = pp.toHexString(key); - - return "algorithm = " + algid.toString () - + ", unparsed keybits = \n" + keybits; + public String toString() { + netscape.security.util.PrettyPrintFormat pp = new netscape.security.util.PrettyPrintFormat( + " ", 20); + String keybits = pp.toHexString(key); + + return "algorithm = " + algid.toString() + ", unparsed keybits = \n" + + keybits; } - /** - * Initialize an PKCS8Key object from an input stream. The data - * on that input stream must be encoded using DER, obeying the - * PKCS#8 format: a sequence consisting of a version, an algorithm - * ID and a bit string which holds the key. (That bit string is - * often used to encapsulate another DER encoded sequence.) - * - * <P>Subclasses should not normally redefine this method; they should - * instead provide a <code>parseKeyBits</code> method to parse any - * fields inside the <code>key</code> member. - * - * @param in an input stream with a DER-encoded PKCS#8 - * SubjectPublicKeyInfo value - * + /** + * Initialize an PKCS8Key object from an input stream. The data on that + * input stream must be encoded using DER, obeying the PKCS#8 format: a + * sequence consisting of a version, an algorithm ID and a bit string which + * holds the key. (That bit string is often used to encapsulate another DER + * encoded sequence.) + * + * <P> + * Subclasses should not normally redefine this method; they should instead + * provide a <code>parseKeyBits</code> method to parse any fields inside the + * <code>key</code> member. + * + * @param in an input stream with a DER-encoded PKCS#8 SubjectPublicKeyInfo + * value + * * @exception InvalidKeyException if a parsing error occurs. */ - public void decode(InputStream in) throws InvalidKeyException - { - DerValue val; - - try { - val = new DerValue (in); - if (val.tag != DerValue.tag_Sequence) - throw new InvalidKeyException ("invalid key format"); - - - BigInteger version = val.data.getInteger().toBigInteger(); - if (!version.equals(PKCS8Key.VERSION)) { - throw new IOException("version mismatch: (supported: " + - PKCS8Key.VERSION + ", parsed: " + - version); - } - algid = AlgorithmId.parse (val.data.getDerValue ()); - key = val.data.getOctetString (); - parseKeyBits (); - if (val.data.available () != 0) - throw new InvalidKeyException ("excess key data"); - - } catch (IOException e) { - // e.printStackTrace (); - throw new InvalidKeyException("IOException : " + - e.getMessage()); - } + public void decode(InputStream in) throws InvalidKeyException { + DerValue val; + + try { + val = new DerValue(in); + if (val.tag != DerValue.tag_Sequence) + throw new InvalidKeyException("invalid key format"); + + BigInteger version = val.data.getInteger().toBigInteger(); + if (!version.equals(PKCS8Key.VERSION)) { + throw new IOException("version mismatch: (supported: " + + PKCS8Key.VERSION + ", parsed: " + version); + } + algid = AlgorithmId.parse(val.data.getDerValue()); + key = val.data.getOctetString(); + parseKeyBits(); + if (val.data.available() != 0) + throw new InvalidKeyException("excess key data"); + + } catch (IOException e) { + // e.printStackTrace (); + throw new InvalidKeyException("IOException : " + e.getMessage()); + } } public void decode(byte[] encodedKey) throws InvalidKeyException { - decode(new ByteArrayInputStream(encodedKey)); + decode(new ByteArrayInputStream(encodedKey)); } /** - * Serialization write ... PKCS#8 keys serialize as - * themselves, and they're parsed when they get read back. + * Serialization write ... PKCS#8 keys serialize as themselves, and they're + * parsed when they get read back. */ - private synchronized void - writeObject (java.io.ObjectOutputStream stream) - throws IOException { - stream.write(getEncoded()); + private synchronized void writeObject(java.io.ObjectOutputStream stream) + throws IOException { + stream.write(getEncoded()); } /** - * Serialization read ... PKCS#8 keys serialize as - * themselves, and they're parsed when they get read back. + * Serialization read ... PKCS#8 keys serialize as themselves, and they're + * parsed when they get read back. */ - private synchronized void readObject (ObjectInputStream stream) - throws IOException { + private synchronized void readObject(ObjectInputStream stream) + throws IOException { - try { - decode(stream); + try { + decode(stream); - } catch (InvalidKeyException e) { - e.printStackTrace(); - throw new IOException("deserialized key is invalid: " + - e.getMessage()); - } + } catch (InvalidKeyException e) { + e.printStackTrace(); + throw new IOException("deserialized key is invalid: " + + e.getMessage()); + } } /* * Make a copy of the encoded key. */ private byte[] copyEncodedKey(byte[] encodedKey) { - int len = encodedKey.length; - byte[] copy = new byte[len]; - System.arraycopy(encodedKey, 0, copy, 0, len); - return copy; + int len = encodedKey.length; + byte[] copy = new byte[len]; + System.arraycopy(encodedKey, 0, copy, 0, len); + return copy; } /* * Produce PKCS#8 encoding from algorithm id and key material. */ static void encode(DerOutputStream out, AlgorithmId algid, byte[] key) - throws IOException { - DerOutputStream tmp = new DerOutputStream(); - tmp.putInteger(new BigInt(VERSION.toByteArray())); - algid.encode(tmp); - tmp.putOctetString(key); - out.write(DerValue.tag_Sequence, tmp); + throws IOException { + DerOutputStream tmp = new DerOutputStream(); + tmp.putInteger(new BigInt(VERSION.toByteArray())); + algid.encode(tmp); + tmp.putOctetString(key); + out.write(DerValue.tag_Sequence, tmp); } /** - * Compares two private keys. This returns false if the object with which - * to compare is not of type <code>Key</code>. - * Otherwise, the encoding of this key object is compared with the - * encoding of the given key object. - * + * Compares two private keys. This returns false if the object with which to + * compare is not of type <code>Key</code>. Otherwise, the encoding of this + * key object is compared with the encoding of the given key object. + * * @param object the object with which to compare - * @return <code>true</code> if this key has the same encoding as the - * object argument; <code>false</code> otherwise. + * @return <code>true</code> if this key has the same encoding as the object + * argument; <code>false</code> otherwise. */ public boolean equals(Object object) { - if (this == object) { - return true; - } - - if (object instanceof Key) { - - // this encoding - byte[] b1; - if (encodedKey != null) { - b1 = encodedKey; - } else { - b1 = getEncoded(); - } - - // that encoding - byte[] b2 = ((Key)object).getEncoded(); - - // do the comparison - int i; - if (b1.length != b2.length) - return false; - for (i = 0; i < b1.length; i++) { - if (b1[i] != b2[i]) { - return false; - } - } - return true; - } - - return false; + if (this == object) { + return true; + } + + if (object instanceof Key) { + + // this encoding + byte[] b1; + if (encodedKey != null) { + b1 = encodedKey; + } else { + b1 = getEncoded(); + } + + // that encoding + byte[] b2 = ((Key) object).getEncoded(); + + // do the comparison + int i; + if (b1.length != b2.length) + return false; + for (i = 0; i < b1.length; i++) { + if (b1[i] != b2[i]) { + return false; + } + } + return true; + } + + return false; } /** - * Calculates a hash code value for this object. Objects - * which are equal will also have the same hashcode. + * Calculates a hash code value for this object. Objects which are equal + * will also have the same hashcode. */ public int hashCode() { int retval = 0; - byte[] b1 = getEncoded(); + byte[] b1 = getEncoded(); for (int i = 1; i < b1.length; i++) { retval += b1[i] * i; } - return(retval); + return (retval); } } |