| | |
| | | package com.sun.opends.sdk.util; |
| | | |
| | | |
| | | |
| | | import static com.sun.opends.sdk.messages.Messages.*; |
| | | |
| | | import java.io.*; |
| | |
| | | import org.opends.sdk.LocalizableMessage; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Provides a wrapper class that collects all of the JVM vendor |
| | | * and JDK version specific code in a single place. |
| | | * |
| | | * Provides a wrapper class that collects all of the JVM vendor and JDK version |
| | | * specific code in a single place. |
| | | */ |
| | | public final class Platform { |
| | | public final class Platform |
| | | { |
| | | |
| | | //Prefix that determines which security package to use. |
| | | private static String pkgPrefix; |
| | | /** |
| | | * Default platform class. |
| | | */ |
| | | private static class DefaultPlatformIMPL extends PlatformIMPL |
| | | { |
| | | // normalize method. |
| | | private static final Method NORMALIZE; |
| | | // Normalized form method. |
| | | private static final Object FORM_NFKC; |
| | | |
| | | //IBM security package doesn't appear to support PCKS10, this flags turns |
| | | //off support for that. |
| | | private static boolean certReqAllowed; |
| | | static |
| | | { |
| | | |
| | | //The two security package prefixes (IBM and SUN). |
| | | private static final String IBM_SEC = "com.ibm.security"; |
| | | private static final String SUN_SEC = "sun.security"; |
| | | |
| | | private static final PlatformIMPL IMPL; |
| | | |
| | | static { |
| | | String vendor = System.getProperty("java.vendor"); |
| | | String ver = System.getProperty("java.version"); |
| | | |
| | | if(vendor.startsWith("IBM")) |
| | | Method normalize = null; |
| | | Object formNFKC = null; |
| | | try |
| | | { |
| | | pkgPrefix = IBM_SEC; |
| | | certReqAllowed = false; |
| | | if(ver.startsWith("1.5")) |
| | | final Class<?> normalizer = Class.forName("java.text.Normalizer"); |
| | | final Class<?> normalizerForm = Class |
| | | .forName("java.text.Normalizer$Form"); |
| | | normalize = normalizer.getMethod("normalize", CharSequence.class, |
| | | normalizerForm); |
| | | formNFKC = normalizerForm.getField("NFKD").get(null); |
| | | } |
| | | catch (final Exception ex) |
| | | { |
| | | // Do not use Normalizer. The values are already set to null. |
| | | } |
| | | NORMALIZE = normalize; |
| | | FORM_NFKC = formNFKC; |
| | | } |
| | | |
| | | |
| | | |
| | | @Override |
| | | public void normalize(final StringBuilder buffer) |
| | | { |
| | | try |
| | | { |
| | | final String normal = (String) NORMALIZE |
| | | .invoke(null, buffer, FORM_NFKC); |
| | | buffer.replace(0, buffer.length(), normal); |
| | | } |
| | | catch (final Exception ex) |
| | | { |
| | | // Don't do anything. buffer should be used. |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * IBM JDK 5 platform class. |
| | | */ |
| | | private static class IBM5PlatformIMPL extends PlatformIMPL |
| | | { |
| | | |
| | | @Override |
| | | public void normalize(final StringBuilder buffer) |
| | | { |
| | | // No implementation. |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Platform base class. Performs all of the certificate management functions. |
| | | */ |
| | | private abstract static class PlatformIMPL |
| | | { |
| | | |
| | | // Key size, key algorithm and signature algorithms used. |
| | | private static final int KEY_SIZE = 1024; |
| | | private static final String KEY_ALGORITHM = "rsa"; |
| | | private static final String SIG_ALGORITHM = "SHA1WithRSA"; |
| | | |
| | | // Time values used in validity calculations. |
| | | private static final int SEC_IN_DAY = 24 * 60 * 60; |
| | | private static final int DEFAULT_VALIDITY = 90 * SEC_IN_DAY; |
| | | |
| | | // These two are used to build certificate request files. |
| | | private static final String TMPFILE_PREFIX = "CertificateManager-"; |
| | | private static final String TMPFILE_EXT = ".csr"; |
| | | |
| | | // Methods pulled from the classes. |
| | | private static final String ENCODE_SIGN_METHOD = "encodeAndSign"; |
| | | private static final String GENERATE_METHOD = "generate"; |
| | | private static final String GET_PRIVATE_KEY_METHOD = "getPrivateKey"; |
| | | private static final String GET_SELFSIGNED_CERT_METHOD = "getSelfCertificate"; |
| | | private static final String PRINT_METHOD = "print"; |
| | | |
| | | // Classes needed to manage certificates. |
| | | private static Class<?> certKeyGenClass, x500NameClass, x500SignerClass, |
| | | pkcs10Class; |
| | | |
| | | // Constructors for each of the above classes. |
| | | private static Constructor<?> certKeyGenCons, x500NameCons, x500SignerCons, |
| | | pkcs10Cons; |
| | | |
| | | static |
| | | { |
| | | final String x509pkg = pkgPrefix + ".x509"; |
| | | final String pkcs10Pkg = pkgPrefix + ".pkcs"; |
| | | final String certAndKeyGen = x509pkg + ".CertAndKeyGen"; |
| | | final String x500Name = x509pkg + ".X500Name"; |
| | | final String x500Signer = x509pkg + ".X500Signer"; |
| | | try |
| | | { |
| | | certKeyGenClass = Class.forName(certAndKeyGen); |
| | | x500NameClass = Class.forName(x500Name); |
| | | x500SignerClass = Class.forName(x500Signer); |
| | | if (certReqAllowed) |
| | | { |
| | | IMPL = new IBM5PlatformIMPL(); |
| | | final String pkcs10 = pkcs10Pkg + ".PKCS10"; |
| | | pkcs10Class = Class.forName(pkcs10); |
| | | pkcs10Cons = pkcs10Class.getConstructor(PublicKey.class); |
| | | } |
| | | certKeyGenCons = certKeyGenClass.getConstructor(String.class, |
| | | String.class); |
| | | x500NameCons = x500NameClass.getConstructor(String.class); |
| | | x500SignerCons = x500SignerClass.getConstructor(Signature.class, |
| | | x500NameClass); |
| | | } |
| | | catch (final ClassNotFoundException e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_CLASS_NOT_FOUND.get(e |
| | | .getMessage()); |
| | | throw new ExceptionInInitializerError(msg.toString()); |
| | | } |
| | | catch (final SecurityException e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_SECURITY.get(e.getMessage()); |
| | | throw new ExceptionInInitializerError(msg.toString()); |
| | | } |
| | | catch (final NoSuchMethodException e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_NO_METHOD |
| | | .get(e.getMessage()); |
| | | throw new ExceptionInInitializerError(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | protected PlatformIMPL() |
| | | { |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add the certificate in the specified path to the specified keystore, |
| | | * creating the keystore using the specified type and path if it the |
| | | * keystore doesn't exist. |
| | | * |
| | | * @param ks |
| | | * The keystore to add the certificate to, may be null if it |
| | | * doesn't exist. |
| | | * @param ksType |
| | | * The type to use if the keystore is created. |
| | | * @param ksPath |
| | | * The path to the keystore if it is created. |
| | | * @param alias |
| | | * The alias to store the certificate under. |
| | | * @param pwd |
| | | * The password to use in saving the certificate. |
| | | * @param certPath |
| | | * The path to the file containing the certificate. |
| | | * @throws KeyStoreException |
| | | * If an error occurred adding the certificate to the keystore. |
| | | */ |
| | | public final void addCertificate(KeyStore ks, final String ksType, |
| | | final String ksPath, final String alias, final char[] pwd, |
| | | final String certPath) throws KeyStoreException |
| | | { |
| | | try |
| | | { |
| | | final CertificateFactory cf = CertificateFactory.getInstance("X509"); |
| | | final InputStream inStream = new FileInputStream(certPath); |
| | | if (ks == null) |
| | | { |
| | | ks = KeyStore.getInstance(ksType); |
| | | ks.load(null, pwd); |
| | | } |
| | | // Do not support certificate replies. |
| | | if (ks.entryInstanceOf(alias, KeyStore.PrivateKeyEntry.class)) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_CERT_REPLIES_INVALID |
| | | .get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | else if (!ks.containsAlias(alias) |
| | | || ks |
| | | .entryInstanceOf(alias, KeyStore.TrustedCertificateEntry.class)) |
| | | { |
| | | trustedCert(alias, cf, ks, inStream); |
| | | } |
| | | else |
| | | { |
| | | IMPL = new DefaultPlatformIMPL(); |
| | | final LocalizableMessage msg = ERR_CERTMGR_ALIAS_INVALID.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final FileOutputStream fileOutStream = new FileOutputStream(ksPath); |
| | | ks.store(fileOutStream, pwd); |
| | | fileOutStream.close(); |
| | | inStream.close(); |
| | | } |
| | | catch (final Exception e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_ADD_CERT.get(alias, e |
| | | .getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Delete the specified alias from the specified keystore. |
| | | * |
| | | * @param ks |
| | | * The keystore to delete the alias from. |
| | | * @param ksPath |
| | | * The path to the keystore. |
| | | * @param alias |
| | | * The alias to use in the request generation. |
| | | * @param pwd |
| | | * The keystore password to use. |
| | | * @throws KeyStoreException |
| | | * If an error occurred deleting the alias. |
| | | */ |
| | | public final void deleteAlias(final KeyStore ks, final String ksPath, |
| | | final String alias, final char[] pwd) throws KeyStoreException |
| | | { |
| | | try |
| | | { |
| | | if (ks == null) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_KEYSTORE_NONEXISTANT.get(); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | ks.deleteEntry(alias); |
| | | final FileOutputStream fs = new FileOutputStream(ksPath); |
| | | ks.store(fs, pwd); |
| | | fs.close(); |
| | | } |
| | | catch (final Exception e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_DELETE_ALIAS.get(alias, e |
| | | .getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Generate a certificate request. Note that this methods checks if the |
| | | * certificate request generation is allowed and throws an exception if it |
| | | * isn't supported. Some vendors JDKs aren't compatible with Sun's |
| | | * certificate request generation classes so they aren't supported. |
| | | * |
| | | * @param ks |
| | | * The keystore to use in the request creation. |
| | | * @param ksType |
| | | * The keystore type. |
| | | * @param ksPath |
| | | * The path to the keystore. |
| | | * @param alias |
| | | * The alias to use in the request generation. |
| | | * @param pwd |
| | | * The keystore password to use. |
| | | * @param dn |
| | | * A dn string to use as the certificate subject. |
| | | * @return A file object pointing at the created certificate request. |
| | | * @throws KeyStoreException |
| | | * If the certificate request failed. |
| | | */ |
| | | public final File generateCertificateRequest(final KeyStore ks, |
| | | final String ksType, final String ksPath, final String alias, |
| | | final char[] pwd, final String dn) throws KeyStoreException |
| | | { |
| | | if (!certReqAllowed) |
| | | { |
| | | final String vendor = System.getProperty("java.vendor"); |
| | | final LocalizableMessage msg = ERR_CERTMGR_CERT_SIGN_REQ_NOT_SUPPORTED |
| | | .get(vendor); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final KeyStore keyStore = generateSelfSignedCertificate(ks, ksType, |
| | | ksPath, alias, pwd, dn, DEFAULT_VALIDITY); |
| | | File csrFile; |
| | | try |
| | | { |
| | | csrFile = File.createTempFile(TMPFILE_PREFIX, TMPFILE_EXT); |
| | | csrFile.deleteOnExit(); |
| | | final PrintStream printStream = new PrintStream(new FileOutputStream( |
| | | csrFile.getAbsolutePath())); |
| | | if (keyStore == null) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_KEYSTORE_NONEXISTANT.get(); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final PrivateKey privateKey = getPrivateKey(keyStore, alias, pwd); |
| | | if (privateKey == null) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_PRIVATE_KEY.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final Certificate cert = keyStore.getCertificate(alias); |
| | | if (cert == null) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_ALIAS_NO_CERTIFICATE |
| | | .get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final Signature signature = Signature.getInstance(SIG_ALGORITHM); |
| | | signature.initSign(privateKey); |
| | | final Object request = pkcs10Cons.newInstance(cert.getPublicKey()); |
| | | final Object subject = x500NameCons.newInstance(dn); |
| | | final Object signer = x500SignerCons.newInstance(signature, subject); |
| | | final Method encodeAndSign = pkcs10Class.getMethod(ENCODE_SIGN_METHOD, |
| | | x500SignerClass); |
| | | final Method print = pkcs10Class.getMethod(PRINT_METHOD, |
| | | PrintStream.class); |
| | | encodeAndSign.invoke(request, signer); |
| | | print.invoke(request, printStream); |
| | | printStream.close(); |
| | | } |
| | | catch (final Exception e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_CERT_REQUEST.get(alias, e |
| | | .getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | return csrFile; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Generate a self-signed certificate using the specified alias, dn string |
| | | * and validity period. If the keystore does not exist, create it using the |
| | | * specified type and path. |
| | | * |
| | | * @param ks |
| | | * The keystore to save the certificate in. May be null if it does |
| | | * not exist. |
| | | * @param ksType |
| | | * The keystore type to use if the keystore is created. |
| | | * @param ksPath |
| | | * The path to the keystore if the keystore is created. |
| | | * @param alias |
| | | * The alias to store the certificate under. |
| | | * @param pwd |
| | | * The password to us in saving the certificate. |
| | | * @param dn |
| | | * The dn string used as the certificate subject. |
| | | * @param validity |
| | | * The validity of the certificate in days. |
| | | * @return The keystore that the self-signed certificate was stored in. |
| | | * @throws KeyStoreException |
| | | * If the self-signed certificate cannot be generated. |
| | | */ |
| | | public final KeyStore generateSelfSignedCertificate(KeyStore ks, |
| | | final String ksType, final String ksPath, final String alias, |
| | | final char[] pwd, final String dn, final int validity) |
| | | throws KeyStoreException |
| | | { |
| | | try |
| | | { |
| | | if (ks == null) |
| | | { |
| | | ks = KeyStore.getInstance(ksType); |
| | | ks.load(null, pwd); |
| | | } |
| | | else if (ks.containsAlias(alias)) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_ALIAS_ALREADY_EXISTS |
| | | .get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final Object keypair = certKeyGenCons.newInstance(KEY_ALGORITHM, |
| | | SIG_ALGORITHM); |
| | | final Object subject = x500NameCons.newInstance(dn); |
| | | final Method certAndKeyGenGenerate = certKeyGenClass.getMethod( |
| | | GENERATE_METHOD, int.class); |
| | | certAndKeyGenGenerate.invoke(keypair, KEY_SIZE); |
| | | final Method certAndKeyGetPrivateKey = certKeyGenClass |
| | | .getMethod(GET_PRIVATE_KEY_METHOD); |
| | | final PrivateKey privatevKey = (PrivateKey) certAndKeyGetPrivateKey |
| | | .invoke(keypair); |
| | | final Certificate[] certificateChain = new Certificate[1]; |
| | | final Method getSelfCertificate = certKeyGenClass.getMethod( |
| | | GET_SELFSIGNED_CERT_METHOD, x500NameClass, long.class); |
| | | final int days = validity * SEC_IN_DAY; |
| | | certificateChain[0] = (Certificate) getSelfCertificate.invoke(keypair, |
| | | subject, days); |
| | | ks.setKeyEntry(alias, privatevKey, pwd, certificateChain); |
| | | final FileOutputStream fileOutStream = new FileOutputStream(ksPath); |
| | | ks.store(fileOutStream, pwd); |
| | | fileOutStream.close(); |
| | | } |
| | | catch (final Exception e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_GEN_SELF_SIGNED_CERT.get( |
| | | alias, e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | return ks; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Normalize the data in the specified buffer. |
| | | * |
| | | * @param buffer |
| | | * The buffer to normalize. |
| | | */ |
| | | public abstract void normalize(StringBuilder buffer); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns the private key associated with specified alias and keystore. The |
| | | * keystore was already checked for existance. |
| | | * |
| | | * @param ks |
| | | * The keystore to get the private key from, it must exist. |
| | | * @param alias |
| | | * The alias to get the private key of. |
| | | * @param pwd |
| | | * The password used to get the key from the keystore. |
| | | * @return The private key of related to the alias. |
| | | * @throws KeyStoreException |
| | | * If the alias is not in the keystore, the entry related to the |
| | | * alias is not of |
| | | */ |
| | | private PrivateKey getPrivateKey(final KeyStore ks, final String alias, |
| | | final char[] pwd) throws KeyStoreException |
| | | { |
| | | PrivateKey key = null; |
| | | try |
| | | { |
| | | if (!ks.containsAlias(alias)) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_ALIAS_DOES_NOT_EXIST |
| | | .get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | if (!ks.entryInstanceOf(alias, KeyStore.PrivateKeyEntry.class) |
| | | && !ks.entryInstanceOf(alias, KeyStore.SecretKeyEntry.class)) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_ALIAS_INVALID_ENTRY_TYPE |
| | | .get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | key = (PrivateKey) ks.getKey(alias, pwd); |
| | | } |
| | | catch (final Exception e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_GET_KEY.get(alias, e |
| | | .getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | return key; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Check that the issuer and subject DNs match. |
| | | * |
| | | * @param cert |
| | | * The certificate to examine. |
| | | * @return {@code true} if the certificate is self-signed. |
| | | */ |
| | | private boolean isSelfSigned(final X509Certificate cert) |
| | | { |
| | | return cert.getSubjectDN().equals(cert.getIssuerDN()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Generate a x509 certificate from the input stream. Verification is done |
| | | * only if it is self-signed. |
| | | * |
| | | * @param alias |
| | | * The alias to save the certificate under. |
| | | * @param cf |
| | | * The x509 certificate factory. |
| | | * @param ks |
| | | * The keystore to add the certificate in. |
| | | * @param in |
| | | * The input stream to read the certificate from. |
| | | * @throws KeyStoreException |
| | | * If the alias exists already in the keystore, if the self-signed |
| | | * certificate didn't verify, or the certificate could not be |
| | | * stored. |
| | | */ |
| | | private void trustedCert(final String alias, final CertificateFactory cf, |
| | | final KeyStore ks, final InputStream in) throws KeyStoreException |
| | | { |
| | | try |
| | | { |
| | | if (ks.containsAlias(alias) == true) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_ALIAS_ALREADY_EXISTS |
| | | .get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | final X509Certificate cert = (X509Certificate) cf |
| | | .generateCertificate(in); |
| | | if (isSelfSigned(cert)) |
| | | { |
| | | cert.verify(cert.getPublicKey()); |
| | | } |
| | | ks.setCertificateEntry(alias, cert); |
| | | } |
| | | catch (final Exception e) |
| | | { |
| | | final LocalizableMessage msg = ERR_CERTMGR_TRUSTED_CERT.get(alias, e |
| | | .getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sun 5 JDK platform class. |
| | | */ |
| | | private static class Sun5PlatformIMPL extends PlatformIMPL |
| | | { |
| | | // normalize method. |
| | | private static final Method NORMALIZE; |
| | | // Normalized form method. |
| | | private static final Object FORM_NFKC; |
| | | |
| | | static |
| | | { |
| | | Method normalize = null; |
| | | Object formNFKC = null; |
| | | try |
| | | { |
| | | final Class<?> normalizer = Class.forName("sun.text.Normalizer"); |
| | | formNFKC = normalizer.getField("DECOMP_COMPAT").get(null); |
| | | final Class<?> normalizerForm = Class |
| | | .forName("sun.text.Normalizer$Mode"); |
| | | normalize = normalizer.getMethod("normalize", String.class, |
| | | normalizerForm, Integer.TYPE); |
| | | } |
| | | catch (final Exception ex) |
| | | { |
| | | // Do not use Normalizer. The values are already set to null. |
| | | } |
| | | NORMALIZE = normalize; |
| | | FORM_NFKC = formNFKC; |
| | | } |
| | | |
| | | |
| | | |
| | | @Override |
| | | public void normalize(final StringBuilder buffer) |
| | | { |
| | | try |
| | | { |
| | | final String normal = (String) NORMALIZE.invoke(null, |
| | | buffer.toString(), FORM_NFKC, 0); |
| | | buffer.replace(0, buffer.length(), normal); |
| | | } |
| | | catch (final Exception ex) |
| | | { |
| | | // Don't do anything. buffer should be used. |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | // Prefix that determines which security package to use. |
| | | private static String pkgPrefix; |
| | | |
| | | // IBM security package doesn't appear to support PCKS10, this flags turns |
| | | // off support for that. |
| | | private static boolean certReqAllowed; |
| | | |
| | | // The two security package prefixes (IBM and SUN). |
| | | private static final String IBM_SEC = "com.ibm.security"; |
| | | |
| | | private static final String SUN_SEC = "sun.security"; |
| | | |
| | | private static final PlatformIMPL IMPL; |
| | | |
| | | static |
| | | { |
| | | final String vendor = System.getProperty("java.vendor"); |
| | | final String ver = System.getProperty("java.version"); |
| | | |
| | | if (vendor.startsWith("IBM")) |
| | | { |
| | | pkgPrefix = IBM_SEC; |
| | | certReqAllowed = false; |
| | | if (ver.startsWith("1.5")) |
| | | { |
| | | IMPL = new IBM5PlatformIMPL(); |
| | | } |
| | | else |
| | | { |
| | | pkgPrefix = SUN_SEC; |
| | | certReqAllowed = true; |
| | | if(ver.startsWith("1.5")) |
| | | { |
| | | IMPL = new Sun5PlatformIMPL(); |
| | | } |
| | | else |
| | | { |
| | | IMPL = new DefaultPlatformIMPL(); |
| | | } |
| | | IMPL = new DefaultPlatformIMPL(); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Platform base class. Performs all of the certificate management functions. |
| | | */ |
| | | private abstract static class PlatformIMPL { |
| | | |
| | | //Key size, key algorithm and signature algorithms used. |
| | | private static final int KEY_SIZE = 1024; |
| | | private static final String KEY_ALGORITHM = "rsa"; |
| | | private static final String SIG_ALGORITHM = "SHA1WithRSA"; |
| | | |
| | | //Time values used in validity calculations. |
| | | private static final int SEC_IN_DAY = 24 * 60 * 60; |
| | | private static final int DEFAULT_VALIDITY = 90 * SEC_IN_DAY; |
| | | |
| | | //These two are used to build certificate request files. |
| | | private static final String TMPFILE_PREFIX = "CertificateManager-"; |
| | | private static final String TMPFILE_EXT = ".csr"; |
| | | |
| | | //Methods pulled from the classes. |
| | | private static final String ENCODE_SIGN_METHOD = "encodeAndSign"; |
| | | private static final String GENERATE_METHOD = "generate"; |
| | | private static final String GET_PRIVATE_KEY_METHOD = "getPrivateKey"; |
| | | private static final String GET_SELFSIGNED_CERT_METHOD = |
| | | "getSelfCertificate"; |
| | | private static final String PRINT_METHOD = "print"; |
| | | |
| | | //Classes needed to manage certificates. |
| | | private static Class<?> certKeyGenClass, X500NameClass, |
| | | X500SignerClass, PKCS10Class; |
| | | |
| | | //Constructors for each of the above classes. |
| | | private static Constructor<?> certKeyGenCons, X500NameCons, |
| | | X500SignerCons, pkcs10Cons; |
| | | |
| | | static { |
| | | String x509pkg = pkgPrefix + ".x509"; |
| | | String pkcs10Pkg = pkgPrefix + ".pkcs"; |
| | | String certAndKeyGen= x509pkg + ".CertAndKeyGen"; |
| | | String X500Name = x509pkg + ".X500Name"; |
| | | String X500Signer = x509pkg + ".X500Signer"; |
| | | try { |
| | | certKeyGenClass = Class.forName(certAndKeyGen); |
| | | X500NameClass = Class.forName(X500Name); |
| | | X500SignerClass = Class.forName(X500Signer); |
| | | if(certReqAllowed) { |
| | | String pkcs10 = pkcs10Pkg + ".PKCS10"; |
| | | PKCS10Class = Class.forName(pkcs10); |
| | | pkcs10Cons = PKCS10Class.getConstructor(PublicKey.class); |
| | | } |
| | | certKeyGenCons = |
| | | certKeyGenClass.getConstructor(String.class, String.class); |
| | | X500NameCons = X500NameClass.getConstructor(String.class); |
| | | X500SignerCons = |
| | | X500SignerClass.getConstructor(Signature.class, X500NameClass); |
| | | } catch (ClassNotFoundException e) { |
| | | LocalizableMessage msg = ERR_CERTMGR_CLASS_NOT_FOUND.get(e.getMessage()); |
| | | throw new ExceptionInInitializerError(msg.toString()); |
| | | } catch (SecurityException e) { |
| | | LocalizableMessage msg = ERR_CERTMGR_SECURITY.get(e.getMessage()); |
| | | throw new ExceptionInInitializerError(msg.toString()); |
| | | } catch (NoSuchMethodException e) { |
| | | LocalizableMessage msg = ERR_CERTMGR_NO_METHOD.get(e.getMessage()); |
| | | throw new ExceptionInInitializerError(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | protected PlatformIMPL() {} |
| | | |
| | | /** |
| | | * Generate a certificate request. Note that this methods checks if |
| | | * the certificate request generation is allowed and throws an |
| | | * exception if it isn't supported. Some vendors JDKs aren't compatible |
| | | * with Sun's certificate request generation classes so they aren't |
| | | * supported. |
| | | * |
| | | * @param ks The keystore to use in the request creation. |
| | | * @param ksType The keystore type. |
| | | * @param ksPath The path to the keystore. |
| | | * @param alias The alias to use in the request generation. |
| | | * @param pwd The keystore password to use. |
| | | * @param dn A dn string to use as the certificate subject. |
| | | * |
| | | * @return A file object pointing at the created certificate request. |
| | | * @throws KeyStoreException If the certificate request failed. |
| | | */ |
| | | public final File |
| | | generateCertificateRequest(KeyStore ks, String ksType, String ksPath, |
| | | String alias, char[] pwd, String dn) throws KeyStoreException { |
| | | if(!certReqAllowed) { |
| | | String vendor = System.getProperty("java.vendor"); |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_CERT_SIGN_REQ_NOT_SUPPORTED.get(vendor); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | KeyStore keyStore = generateSelfSignedCertificate(ks, ksType, ksPath, |
| | | alias, pwd, dn, DEFAULT_VALIDITY); |
| | | File csrFile; |
| | | try { |
| | | csrFile = File.createTempFile(TMPFILE_PREFIX, TMPFILE_EXT); |
| | | csrFile.deleteOnExit(); |
| | | PrintStream printStream = |
| | | new PrintStream(new FileOutputStream(csrFile.getAbsolutePath())); |
| | | if(keyStore == null) { |
| | | LocalizableMessage msg = ERR_CERTMGR_KEYSTORE_NONEXISTANT.get(); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | PrivateKey privateKey = getPrivateKey(keyStore, alias, pwd); |
| | | if(privateKey == null) { |
| | | LocalizableMessage msg = ERR_CERTMGR_PRIVATE_KEY.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | Certificate cert = keyStore.getCertificate(alias); |
| | | if(cert == null) { |
| | | LocalizableMessage msg = ERR_CERTMGR_ALIAS_NO_CERTIFICATE.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | Signature signature = Signature.getInstance(SIG_ALGORITHM); |
| | | signature.initSign(privateKey); |
| | | Object request = pkcs10Cons.newInstance(cert.getPublicKey()); |
| | | Object subject = X500NameCons.newInstance(dn); |
| | | Object signer = |
| | | X500SignerCons.newInstance(signature, subject); |
| | | Method encodeAndSign = |
| | | PKCS10Class.getMethod(ENCODE_SIGN_METHOD, X500SignerClass); |
| | | Method print = |
| | | PKCS10Class.getMethod(PRINT_METHOD, PrintStream.class); |
| | | encodeAndSign.invoke(request, signer); |
| | | print.invoke(request, printStream); |
| | | printStream.close(); |
| | | } catch (Exception e) { |
| | | LocalizableMessage msg = ERR_CERTMGR_CERT_REQUEST.get(alias,e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | return csrFile; |
| | | } |
| | | |
| | | /** |
| | | * Delete the specified alias from the specified keystore. |
| | | * |
| | | * @param ks The keystore to delete the alias from. |
| | | * @param ksPath The path to the keystore. |
| | | * @param alias The alias to use in the request generation. |
| | | * @param pwd The keystore password to use. |
| | | * |
| | | * @throws KeyStoreException If an error occurred deleting the alias. |
| | | */ |
| | | public final void deleteAlias(KeyStore ks, String ksPath, |
| | | String alias, char[] pwd) throws KeyStoreException { |
| | | try { |
| | | if(ks == null) { |
| | | LocalizableMessage msg = ERR_CERTMGR_KEYSTORE_NONEXISTANT.get(); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | ks.deleteEntry(alias); |
| | | FileOutputStream fs = new FileOutputStream(ksPath); |
| | | ks.store(fs, pwd); |
| | | fs.close(); |
| | | } catch (Exception e) { |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_DELETE_ALIAS.get(alias,e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Add the certificate in the specified path to the specified keystore, |
| | | * creating the keystore using the specified type and path if it the |
| | | * keystore doesn't exist. |
| | | * |
| | | * @param ks The keystore to add the certificate to, may be null if it |
| | | * doesn't exist. |
| | | * @param ksType The type to use if the keystore is created. |
| | | * @param ksPath The path to the keystore if it is created. |
| | | * @param alias The alias to store the certificate under. |
| | | * @param pwd The password to use in saving the certificate. |
| | | * @param certPath The path to the file containing the certificate. |
| | | * @throws KeyStoreException If an error occurred adding the |
| | | * certificate to the keystore. |
| | | */ |
| | | public final void addCertificate(KeyStore ks, String ksType, |
| | | String ksPath, String alias, char[] pwd, String certPath) |
| | | throws KeyStoreException { |
| | | try { |
| | | CertificateFactory cf = CertificateFactory.getInstance("X509"); |
| | | InputStream inStream = new FileInputStream(certPath); |
| | | if(ks == null) { |
| | | ks = KeyStore.getInstance(ksType); |
| | | ks.load(null, pwd); |
| | | } |
| | | //Do not support certificate replies. |
| | | if (ks.entryInstanceOf(alias ,KeyStore.PrivateKeyEntry.class)) { |
| | | LocalizableMessage msg = ERR_CERTMGR_CERT_REPLIES_INVALID.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } else if(!ks.containsAlias(alias) || |
| | | ks.entryInstanceOf(alias, |
| | | KeyStore.TrustedCertificateEntry.class)) |
| | | trustedCert(alias, cf, ks, inStream); |
| | | else { |
| | | LocalizableMessage msg = ERR_CERTMGR_ALIAS_INVALID.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | FileOutputStream fileOutStream = new FileOutputStream(ksPath); |
| | | ks.store(fileOutStream, pwd); |
| | | fileOutStream.close(); |
| | | inStream.close(); |
| | | } catch (Exception e) { |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_ADD_CERT.get(alias, e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Generate a self-signed certificate using the specified alias, dn |
| | | * string and validity period. If the keystore does not exist, create it |
| | | * using the specified type and path. |
| | | * |
| | | * @param ks The keystore to save the certificate in. May be null if it |
| | | * does not exist. |
| | | * @param ksType The keystore type to use if the keystore is created. |
| | | * @param ksPath The path to the keystore if the keystore is created. |
| | | * @param alias The alias to store the certificate under. |
| | | * @param pwd The password to us in saving the certificate. |
| | | * @param dn The dn string used as the certificate subject. |
| | | * @param validity The validity of the certificate in days. |
| | | * @return The keystore that the self-signed certificate was stored in. |
| | | * |
| | | * @throws KeyStoreException If the self-signed certificate cannot be |
| | | * generated. |
| | | */ |
| | | public final |
| | | KeyStore generateSelfSignedCertificate(KeyStore ks, String ksType, |
| | | String ksPath, String alias, char[] pwd, String dn, int validity) |
| | | throws KeyStoreException { |
| | | try { |
| | | if(ks == null) { |
| | | ks = KeyStore.getInstance(ksType); |
| | | ks.load(null, pwd); |
| | | } else if(ks.containsAlias(alias)) { |
| | | LocalizableMessage msg = ERR_CERTMGR_ALIAS_ALREADY_EXISTS.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | Object keypair = |
| | | certKeyGenCons.newInstance(KEY_ALGORITHM, SIG_ALGORITHM); |
| | | Object subject = X500NameCons.newInstance(dn); |
| | | Method certAndKeyGenGenerate = |
| | | certKeyGenClass.getMethod(GENERATE_METHOD, int.class); |
| | | certAndKeyGenGenerate.invoke(keypair, KEY_SIZE); |
| | | Method certAndKeyGetPrivateKey = |
| | | certKeyGenClass.getMethod(GET_PRIVATE_KEY_METHOD); |
| | | PrivateKey privatevKey = |
| | | (PrivateKey) certAndKeyGetPrivateKey.invoke(keypair); |
| | | Certificate[] certificateChain = new Certificate[1]; |
| | | Method getSelfCertificate = |
| | | certKeyGenClass.getMethod(GET_SELFSIGNED_CERT_METHOD, |
| | | X500NameClass,long.class); |
| | | int days = validity * SEC_IN_DAY; |
| | | certificateChain[0] = |
| | | (Certificate) getSelfCertificate.invoke(keypair, subject, days); |
| | | ks.setKeyEntry(alias, privatevKey, pwd, certificateChain); |
| | | FileOutputStream fileOutStream = new FileOutputStream(ksPath); |
| | | ks.store(fileOutStream, pwd); |
| | | fileOutStream.close(); |
| | | } catch (Exception e) { |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_GEN_SELF_SIGNED_CERT.get(alias, e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | return ks; |
| | | } |
| | | |
| | | /** |
| | | * Generate a x509 certificate from the input stream. Verification is |
| | | * done only if it is self-signed. |
| | | * |
| | | * @param alias The alias to save the certificate under. |
| | | * @param cf The x509 certificate factory. |
| | | * @param ks The keystore to add the certificate in. |
| | | * @param in The input stream to read the certificate from. |
| | | * @throws KeyStoreException If the alias exists already in the |
| | | * keystore, if the self-signed certificate didn't verify, or |
| | | * the certificate could not be stored. |
| | | */ |
| | | private void trustedCert(String alias, CertificateFactory cf, |
| | | KeyStore ks, InputStream in) throws KeyStoreException { |
| | | try { |
| | | if (ks.containsAlias(alias) == true) { |
| | | LocalizableMessage msg = ERR_CERTMGR_ALIAS_ALREADY_EXISTS.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | X509Certificate cert = (X509Certificate) cf.generateCertificate(in); |
| | | if (isSelfSigned(cert)) |
| | | cert.verify(cert.getPublicKey()); |
| | | ks.setCertificateEntry(alias, cert); |
| | | } catch (Exception e) { |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_TRUSTED_CERT.get(alias,e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Check that the issuer and subject DNs match. |
| | | * |
| | | * @param cert The certificate to examine. |
| | | * @return {@code true} if the certificate is self-signed. |
| | | */ |
| | | private boolean isSelfSigned(X509Certificate cert) { |
| | | return cert.getSubjectDN().equals(cert.getIssuerDN()); |
| | | } |
| | | |
| | | /** |
| | | * Returns the private key associated with specified alias and keystore. |
| | | * The keystore was already checked for existance. |
| | | * |
| | | * @param ks The keystore to get the private key from, it must exist. |
| | | * @param alias The alias to get the private key of. |
| | | * @param pwd The password used to get the key from the keystore. |
| | | * @return The private key of related to the alias. |
| | | * |
| | | * @throws KeyStoreException If the alias is not in the keystore, the |
| | | * entry related to the alias is not of |
| | | */ |
| | | private PrivateKey getPrivateKey(KeyStore ks, String alias, char[] pwd) |
| | | throws KeyStoreException { |
| | | PrivateKey key = null; |
| | | try { |
| | | if(!ks.containsAlias(alias)) { |
| | | LocalizableMessage msg = ERR_CERTMGR_ALIAS_DOES_NOT_EXIST.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | if(!ks.entryInstanceOf(alias, KeyStore.PrivateKeyEntry.class) && |
| | | !ks.entryInstanceOf(alias, KeyStore.SecretKeyEntry.class)) { |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_ALIAS_INVALID_ENTRY_TYPE.get(alias); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | key = (PrivateKey)ks.getKey(alias, pwd); |
| | | } catch (Exception e) { |
| | | LocalizableMessage msg = |
| | | ERR_CERTMGR_GET_KEY.get(alias,e.getMessage()); |
| | | throw new KeyStoreException(msg.toString()); |
| | | } |
| | | return key; |
| | | } |
| | | |
| | | /** |
| | | * Normalize the data in the specified buffer. |
| | | * |
| | | * @param buffer The buffer to normalize. |
| | | */ |
| | | public abstract void normalize(StringBuilder buffer); |
| | | } |
| | | |
| | | //Prevent instantiation. |
| | | private Platform() {} |
| | | |
| | | /** |
| | | * Add the certificate in the specified path to the provided keystore; |
| | | * creating the keystore with the provided type and path if it doesn't |
| | | * exist. |
| | | * |
| | | * @param ks The keystore to add the certificate to, may be null if it |
| | | * doesn't exist. |
| | | * @param ksType The type to use if the keystore is created. |
| | | * @param ksPath The path to the keystore if it is created. |
| | | * @param alias The alias to store the certificate under. |
| | | * @param pwd The password to use in saving the certificate. |
| | | * @param certPath The path to the file containing the certificate. |
| | | * |
| | | * @throws KeyStoreException If an error occurred adding the |
| | | * certificate to the keystore. |
| | | */ |
| | | public static void addCertificate(KeyStore ks, String ksType, String ksPath, |
| | | String alias, char[] pwd, String certPath) throws KeyStoreException { |
| | | IMPL.addCertificate(ks,ksType, ksPath, alias, pwd, certPath); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Delete the specified alias from the provided keystore. |
| | | * |
| | | * @param ks The keystore to delete the alias from. |
| | | * @param ksPath The path to the keystore. |
| | | * @param alias The alias to use in the request generation. |
| | | * @param pwd The keystore password to use. |
| | | * |
| | | * @throws KeyStoreException If an error occurred deleting the alias. |
| | | */ |
| | | public static void deleteAlias(KeyStore ks, String ksPath, String alias, |
| | | char[] pwd) throws KeyStoreException { |
| | | IMPL.deleteAlias(ks, ksPath, alias, pwd); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Generate a certificate request using the specified parameters. |
| | | * |
| | | * @param ks The keystore to use in the request creation. |
| | | * @param ksType The keystore type. |
| | | * @param ksPath The path to the keystore. |
| | | * @param alias The alias to use in the request generation. |
| | | * @param pwd The keystore password to use. |
| | | * @param dn A dn string to use as the certificate subject. |
| | | * @return A file object pointing at the created certificate request. |
| | | * |
| | | * @throws KeyStoreException If the certificate request failed. |
| | | */ |
| | | public static File generateCertificateRequest(KeyStore ks, String ksType, |
| | | String ksPath, String alias, char[] pwd, String dn) |
| | | throws KeyStoreException { |
| | | return IMPL.generateCertificateRequest(ks, ksType, ksPath, alias, |
| | | pwd, dn); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Generate a self-signed certificate using the specified alias, dn |
| | | * string and validity period. If the keystore does not exist, it will be |
| | | * created using the specified keystore type and path. |
| | | * |
| | | * @param ks The keystore to save the certificate in. May be null if it |
| | | * does not exist. |
| | | * @param ksType The keystore type to use if the keystore is created. |
| | | * @param ksPath The path to the keystore if the keystore is created. |
| | | * @param alias The alias to store the certificate under. |
| | | * @param pwd The password to us in saving the certificate. |
| | | * @param dn The dn string used as the certificate subject. |
| | | * @param validity The validity of the certificate in days. |
| | | * |
| | | * @throws KeyStoreException If the self-signed certificate cannot be |
| | | * generated. |
| | | */ |
| | | public static void generateSelfSignedCertificate(KeyStore ks, String ksType, |
| | | String ksPath, String alias, char[] pwd, String dn, int validity) |
| | | throws KeyStoreException { |
| | | IMPL.generateSelfSignedCertificate(ks, ksType, ksPath, alias, pwd, dn, |
| | | validity); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sun 5 JDK platform class. |
| | | */ |
| | | private static class Sun5PlatformIMPL extends PlatformIMPL { |
| | | //normalize method. |
| | | private static final Method NORMALIZE; |
| | | //Normalized form method. |
| | | private static final Object FORM_NFKC; |
| | | |
| | | static { |
| | | Method normalize = null; |
| | | Object formNFKC = null; |
| | | try { |
| | | Class<?> normalizer = Class.forName("sun.text.Normalizer"); |
| | | formNFKC = normalizer.getField("DECOMP_COMPAT").get(null); |
| | | Class<?> normalizerForm = Class.forName("sun.text.Normalizer$Mode"); |
| | | normalize = normalizer.getMethod("normalize", String.class, |
| | | normalizerForm, Integer.TYPE); |
| | | } |
| | | catch (Exception ex) { |
| | | // Do not use Normalizer. The values are already set to null. |
| | | } |
| | | NORMALIZE = normalize; |
| | | FORM_NFKC = formNFKC; |
| | | } |
| | | |
| | | |
| | | @Override |
| | | public void normalize(StringBuilder buffer) { |
| | | try { |
| | | String normal = |
| | | (String) NORMALIZE.invoke(null, buffer.toString(), FORM_NFKC,0); |
| | | buffer.replace(0,buffer.length(),normal); |
| | | } |
| | | catch(Exception ex) { |
| | | //Don't do anything. buffer should be used. |
| | | } |
| | | else |
| | | { |
| | | pkgPrefix = SUN_SEC; |
| | | certReqAllowed = true; |
| | | if (ver.startsWith("1.5")) |
| | | { |
| | | IMPL = new Sun5PlatformIMPL(); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Default platform class. |
| | | */ |
| | | private static class DefaultPlatformIMPL extends PlatformIMPL { |
| | | //normalize method. |
| | | private static final Method NORMALIZE; |
| | | //Normalized form method. |
| | | private static final Object FORM_NFKC; |
| | | |
| | | static { |
| | | |
| | | Method normalize = null; |
| | | Object formNFKC = null; |
| | | try { |
| | | Class<?> normalizer = Class.forName("java.text.Normalizer"); |
| | | Class<?> normalizerForm = Class.forName("java.text.Normalizer$Form"); |
| | | normalize = normalizer.getMethod("normalize", CharSequence.class, |
| | | normalizerForm); |
| | | formNFKC = normalizerForm.getField("NFKD").get(null); |
| | | } |
| | | catch (Exception ex) { |
| | | // Do not use Normalizer. The values are already set to null. |
| | | } |
| | | NORMALIZE = normalize; |
| | | FORM_NFKC = formNFKC; |
| | | } |
| | | |
| | | |
| | | @Override |
| | | public void normalize(StringBuilder buffer) { |
| | | try { |
| | | String normal = (String) NORMALIZE.invoke(null, buffer, FORM_NFKC); |
| | | buffer.replace(0,buffer.length(),normal); |
| | | } |
| | | catch(Exception ex) { |
| | | //Don't do anything. buffer should be used. |
| | | } |
| | | else |
| | | { |
| | | IMPL = new DefaultPlatformIMPL(); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * IBM JDK 5 platform class. |
| | | */ |
| | | private static class IBM5PlatformIMPL extends PlatformIMPL { |
| | | |
| | | @Override |
| | | public void normalize(StringBuilder buffer) { |
| | | //No implementation. |
| | | } |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Normalize the specified buffer. |
| | | * |
| | | * @param buffer The buffer to normalize. |
| | | */ |
| | | public static void normalize(StringBuilder buffer) { |
| | | IMPL.normalize(buffer); |
| | | } |
| | | |
| | | /** |
| | | * Test if a platform java vendor property starts with the specified |
| | | * vendor string. |
| | | * |
| | | * @param vendor The vendor to check for. |
| | | * @return {@code true} if the java vendor starts with the specified vendor |
| | | * string. |
| | | */ |
| | | public static boolean isVendor(String vendor) { |
| | | String javaVendor = System.getProperty("java.vendor"); |
| | | return javaVendor.startsWith(vendor); |
| | | } |
| | | |
| | | /** |
| | | * Add the certificate in the specified path to the provided keystore; |
| | | * creating the keystore with the provided type and path if it doesn't exist. |
| | | * |
| | | * @param ks |
| | | * The keystore to add the certificate to, may be null if it doesn't |
| | | * exist. |
| | | * @param ksType |
| | | * The type to use if the keystore is created. |
| | | * @param ksPath |
| | | * The path to the keystore if it is created. |
| | | * @param alias |
| | | * The alias to store the certificate under. |
| | | * @param pwd |
| | | * The password to use in saving the certificate. |
| | | * @param certPath |
| | | * The path to the file containing the certificate. |
| | | * @throws KeyStoreException |
| | | * If an error occurred adding the certificate to the keystore. |
| | | */ |
| | | public static void addCertificate(final KeyStore ks, final String ksType, |
| | | final String ksPath, final String alias, final char[] pwd, |
| | | final String certPath) throws KeyStoreException |
| | | { |
| | | IMPL.addCertificate(ks, ksType, ksPath, alias, pwd, certPath); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Delete the specified alias from the provided keystore. |
| | | * |
| | | * @param ks |
| | | * The keystore to delete the alias from. |
| | | * @param ksPath |
| | | * The path to the keystore. |
| | | * @param alias |
| | | * The alias to use in the request generation. |
| | | * @param pwd |
| | | * The keystore password to use. |
| | | * @throws KeyStoreException |
| | | * If an error occurred deleting the alias. |
| | | */ |
| | | public static void deleteAlias(final KeyStore ks, final String ksPath, |
| | | final String alias, final char[] pwd) throws KeyStoreException |
| | | { |
| | | IMPL.deleteAlias(ks, ksPath, alias, pwd); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Generate a certificate request using the specified parameters. |
| | | * |
| | | * @param ks |
| | | * The keystore to use in the request creation. |
| | | * @param ksType |
| | | * The keystore type. |
| | | * @param ksPath |
| | | * The path to the keystore. |
| | | * @param alias |
| | | * The alias to use in the request generation. |
| | | * @param pwd |
| | | * The keystore password to use. |
| | | * @param dn |
| | | * A dn string to use as the certificate subject. |
| | | * @return A file object pointing at the created certificate request. |
| | | * @throws KeyStoreException |
| | | * If the certificate request failed. |
| | | */ |
| | | public static File generateCertificateRequest(final KeyStore ks, |
| | | final String ksType, final String ksPath, final String alias, |
| | | final char[] pwd, final String dn) throws KeyStoreException |
| | | { |
| | | return IMPL.generateCertificateRequest(ks, ksType, ksPath, alias, pwd, dn); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Generate a self-signed certificate using the specified alias, dn string and |
| | | * validity period. If the keystore does not exist, it will be created using |
| | | * the specified keystore type and path. |
| | | * |
| | | * @param ks |
| | | * The keystore to save the certificate in. May be null if it does |
| | | * not exist. |
| | | * @param ksType |
| | | * The keystore type to use if the keystore is created. |
| | | * @param ksPath |
| | | * The path to the keystore if the keystore is created. |
| | | * @param alias |
| | | * The alias to store the certificate under. |
| | | * @param pwd |
| | | * The password to us in saving the certificate. |
| | | * @param dn |
| | | * The dn string used as the certificate subject. |
| | | * @param validity |
| | | * The validity of the certificate in days. |
| | | * @throws KeyStoreException |
| | | * If the self-signed certificate cannot be generated. |
| | | */ |
| | | public static void generateSelfSignedCertificate(final KeyStore ks, |
| | | final String ksType, final String ksPath, final String alias, |
| | | final char[] pwd, final String dn, final int validity) |
| | | throws KeyStoreException |
| | | { |
| | | IMPL.generateSelfSignedCertificate(ks, ksType, ksPath, alias, pwd, dn, |
| | | validity); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Test if a platform java vendor property starts with the specified vendor |
| | | * string. |
| | | * |
| | | * @param vendor |
| | | * The vendor to check for. |
| | | * @return {@code true} if the java vendor starts with the specified vendor |
| | | * string. |
| | | */ |
| | | public static boolean isVendor(final String vendor) |
| | | { |
| | | final String javaVendor = System.getProperty("java.vendor"); |
| | | return javaVendor.startsWith(vendor); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Normalize the specified buffer. |
| | | * |
| | | * @param buffer |
| | | * The buffer to normalize. |
| | | */ |
| | | public static void normalize(final StringBuilder buffer) |
| | | { |
| | | IMPL.normalize(buffer); |
| | | } |
| | | |
| | | |
| | | |
| | | // Prevent instantiation. |
| | | private Platform() |
| | | { |
| | | } |
| | | } |
| | | |