# HG changeset patch # User vinnie # Date 1419352257 0 # Node ID 47080f9ae75048350fa1a19a0b9ce51cba58dcc9 # Parent 0cbef7c46996b16fef1459689d3ea7c0c3db2c84 8044445: JEP 229: Create PKCS12 Keystores by Default Reviewed-by: mullan, weijun diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/com/sun/crypto/provider/JceKeyStore.java --- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/JceKeyStore.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/JceKeyStore.java Tue Dec 23 16:30:57 2014 +0000 @@ -898,4 +898,20 @@ md.update("Mighty Aphrodite".getBytes("UTF8")); return md; } + + /** + * Probe the first few bytes of the keystore data stream for a valid + * JCEKS keystore encoding. + */ + @Override + public boolean engineProbe(InputStream stream) throws IOException { + DataInputStream dataStream; + if (stream instanceof DataInputStream) { + dataStream = (DataInputStream)stream; + } else { + dataStream = new DataInputStream(stream); + } + + return JCEKS_MAGIC == dataStream.readInt(); + } } diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/java/security/KeyStore.java --- a/jdk/src/java.base/share/classes/java/security/KeyStore.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/java/security/KeyStore.java Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -92,9 +92,23 @@ * be used (in a variety of formats). * *

Typical ways to request a KeyStore object include + * specifying an existing keystore file, * relying on the default type and providing a specific keystore type. * *

* *

Before a keystore can be accessed, it must be - * {@link #load(java.io.InputStream, char[]) loaded}. + * {@link #load(java.io.InputStream, char[]) loaded} + * (unless it was already loaded during instantiation). *

  *    KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
  *
@@ -179,6 +194,7 @@
 
 public class KeyStore {
 
+    private static final Debug kdebug = Debug.getInstance("keystore");
     private static final Debug pdebug =
                         Debug.getInstance("provider", "Provider");
     private static final boolean skipDebug =
@@ -1594,6 +1610,188 @@
     }
 
     /**
+     * Returns a loaded keystore object of the appropriate keystore type.
+     * First the keystore type is determined by probing the specified file.
+     * Then a keystore object is instantiated and loaded using the data from
+     * that file.
+     * A password may be supplied to unlock the keystore data or perform an
+     * integrity check.
+     *
+     * 

+ * This method traverses the list of registered security {@link Providers}, + * starting with the most preferred Provider. + * For each {@link KeyStoreSpi} implementation supported by a Provider, + * it invokes the {@link engineProbe} method to determine if it supports + * the specified keystore. + * A new KeyStore object is returned that encapsulates the KeyStoreSpi + * implementation from the first Provider that supports the specified file. + * + *

Note that the list of registered providers may be retrieved via + * the {@link Security#getProviders() Security.getProviders()} method. + * + * @param file the keystore file + * @param password the keystore password, which may be {@code null} + * + * @return a keystore object loaded with keystore data + * + * @throws KeyStoreException if no Provider supports a KeyStoreSpi + * implementation for the specified keystore file. + * @throws IOException if there is an I/O or format problem with the + * keystore data, if a password is required but not given, + * or if the given password was incorrect. If the error is + * due to a wrong password, the {@link Throwable#getCause cause} + * of the {@code IOException} should be an + * {@code UnrecoverableKeyException}. + * @throws NoSuchAlgorithmException if the algorithm used to check the + * integrity of the keystore cannot be found. + * @throws CertificateException if any of the certificates in the + * keystore could not be loaded. + * @throws IllegalArgumentException if file does not exist or does not + * refer to a normal file. + * @throws NullPointerException if file is {@code null}. + * @throws SecurityException if a security manager exists and its + * {@link java.lang.SecurityManager#checkRead} method denies + * read access to the specified file. + * + * @see Provider + * + * @since 1.9 + */ + public static final KeyStore getInstance(File file, char[] password) + throws KeyStoreException, IOException, NoSuchAlgorithmException, + CertificateException { + return getInstance(file, password, null, true); + } + + /** + * Returns a loaded keystore object of the appropriate keystore type. + * First the keystore type is determined by probing the specified file. + * Then a keystore object is instantiated and loaded using the data from + * that file. + * A {@code LoadStoreParameter} may be supplied which specifies how to + * unlock the keystore data or perform an integrity check. + * + *

+ * This method traverses the list of registered security {@link Providers}, + * starting with the most preferred Provider. + * For each {@link KeyStoreSpi} implementation supported by a Provider, + * it invokes the {@link engineProbe} method to determine if it supports + * the specified keystore. + * A new KeyStore object is returned that encapsulates the KeyStoreSpi + * implementation from the first Provider that supports the specified file. + * + *

Note that the list of registered providers may be retrieved via + * the {@link Security#getProviders() Security.getProviders()} method. + * + * @param file the keystore file + * @param param the {@code LoadStoreParameter} that specifies how to load + * the keystore, which may be {@code null} + * + * @return a keystore object loaded with keystore data + * + * @throws KeyStoreException if no Provider supports a KeyStoreSpi + * implementation for the specified keystore file. + * @throws IOException if there is an I/O or format problem with the + * keystore data. If the error is due to an incorrect + * {@code ProtectionParameter} (e.g. wrong password) + * the {@link Throwable#getCause cause} of the + * {@code IOException} should be an + * {@code UnrecoverableKeyException}. + * @throws NoSuchAlgorithmException if the algorithm used to check the + * integrity of the keystore cannot be found. + * @throws CertificateException if any of the certificates in the + * keystore could not be loaded. + * @throws IllegalArgumentException if file does not exist or does not + * refer to a normal file, or if param is not recognized. + * @throws NullPointerException if file is {@code null}. + * @throws SecurityException if a security manager exists and its + * {@link java.lang.SecurityManager#checkRead} method denies + * read access to the specified file. + * + * @see Provider + * + * @since 1.9 + */ + public static final KeyStore getInstance(File file, + LoadStoreParameter param) throws KeyStoreException, IOException, + NoSuchAlgorithmException, CertificateException { + return getInstance(file, null, param, false); + } + + // Used by getInstance(File, char[]) & getInstance(File, LoadStoreParameter) + private static final KeyStore getInstance(File file, char[] password, + LoadStoreParameter param, boolean hasPassword) + throws KeyStoreException, IOException, NoSuchAlgorithmException, + CertificateException { + + if (file == null) { + throw new NullPointerException(); + } + + if (file.isFile() == false) { + throw new IllegalArgumentException( + "File does not exist or it does not refer to a normal file: " + + file); + } + + KeyStore keystore = null; + + try (DataInputStream dataStream = + new DataInputStream( + new BufferedInputStream( + new FileInputStream(file)))) { + + dataStream.mark(Integer.MAX_VALUE); + + // Detect the keystore type + for (String type : Security.getAlgorithms("KeyStore")) { + Object[] objs = null; + + try { + objs = Security.getImpl(type, "KeyStore", (String)null); + + KeyStoreSpi impl = (KeyStoreSpi)objs[0]; + if (impl.engineProbe(dataStream)) { + + if (kdebug != null) { + kdebug.println(type + " keystore detected: " + + file); + } + + keystore = new KeyStore(impl, (Provider)objs[1], type); + break; + } + } catch (NoSuchAlgorithmException | NoSuchProviderException e) { + // ignore + if (kdebug != null) { + kdebug.println(type + " not found - " + e); + } + } catch (IOException e) { + // ignore + if (kdebug != null) { + kdebug.println("I/O error in " + file + " - " + e); + } + } + dataStream.reset(); // prepare the stream for the next probe + } + + // Load the keystore data + if (keystore != null) { + if (hasPassword) { + dataStream.reset(); // prepare the stream for loading + keystore.load(dataStream, password); + } else { + keystore.load(param); + } + return keystore; + } + } + + throw new KeyStoreException("Unrecognized keystore format: " + + keystore); + } + + /** * A description of a to-be-instantiated KeyStore object. * *

An instance of this class encapsulates the information needed to @@ -1713,7 +1911,7 @@ * by invoking the CallbackHandler. * *

Subsequent calls to {@link #getKeyStore} return the same object - * as the initial call. If the initial call to failed with a + * as the initial call. If the initial call failed with a * KeyStoreException, subsequent calls also throw a * KeyStoreException. * @@ -1760,6 +1958,50 @@ AccessController.getContext()); } + /** + * Returns a new Builder object. + * + *

The first call to the {@link #getKeyStore} method on the returned + * builder will create a KeyStore using {@code file} to detect the + * keystore type and then call its {@link KeyStore#load load()} method. + * It uses the same algorithm to determine the keystore type as + * described in {@link KeyStore#getInstance(File, LoadStoreParameter)}. + * The {@code inputStream} argument is constructed from {@code file}. + * If {@code protection} is a {@code PasswordProtection}, the password + * is obtained by calling the {@code getPassword} method. + * Otherwise, if {@code protection} is a + * {@code CallbackHandlerProtection}, + * the password is obtained by invoking the CallbackHandler. + * + *

Subsequent calls to {@link #getKeyStore} return the same object + * as the initial call. If the initial call failed with a + * KeyStoreException, subsequent calls also throw a KeyStoreException. + * + *

Calls to {@link #getProtectionParameter getProtectionParameter()} + * will return a {@link KeyStore.PasswordProtection PasswordProtection} + * object encapsulating the password that was used to invoke the + * {@code load} method. + * + *

Note that the {@link #getKeyStore} method is executed + * within the {@link AccessControlContext} of the code invoking this + * method. + * + * @return a new Builder object + * @param file the File that contains the KeyStore data + * @param protection the ProtectionParameter securing the KeyStore data + * @throws NullPointerException if file or protection is null + * @throws IllegalArgumentException if protection is not an instance + * of either PasswordProtection or CallbackHandlerProtection; or + * if file does not exist or does not refer to a normal file + * + * @since 1.9 + */ + public static Builder newInstance(File file, + ProtectionParameter protection) { + + return newInstance("", null, file, protection); + } + private static final class FileBuilder extends Builder { private final String type; @@ -1817,42 +2059,46 @@ } public KeyStore run0() throws Exception { KeyStore ks; - if (provider == null) { - ks = KeyStore.getInstance(type); + char[] password = null; + + // Acquire keystore password + if (protection instanceof PasswordProtection) { + password = + ((PasswordProtection)protection).getPassword(); + keyProtection = protection; } else { - ks = KeyStore.getInstance(type, provider); - } - InputStream in = null; - char[] password = null; - try { - in = new FileInputStream(file); - if (protection instanceof PasswordProtection) { - password = - ((PasswordProtection)protection).getPassword(); - keyProtection = protection; - } else { - CallbackHandler handler = - ((CallbackHandlerProtection)protection) + CallbackHandler handler = + ((CallbackHandlerProtection)protection) .getCallbackHandler(); - PasswordCallback callback = new PasswordCallback - ("Password for keystore " + file.getName(), + PasswordCallback callback = new PasswordCallback + ("Password for keystore " + file.getName(), false); - handler.handle(new Callback[] {callback}); - password = callback.getPassword(); - if (password == null) { - throw new KeyStoreException("No password" + - " provided"); - } - callback.clearPassword(); - keyProtection = new PasswordProtection(password); + handler.handle(new Callback[] {callback}); + password = callback.getPassword(); + if (password == null) { + throw new KeyStoreException("No password" + + " provided"); } - ks.load(in, password); - return ks; - } finally { - if (in != null) { - in.close(); + callback.clearPassword(); + keyProtection = new PasswordProtection(password); + } + + if (type.isEmpty()) { + // Instantiate keystore and load keystore data + ks = KeyStore.getInstance(file, password); + } else { + // Instantiate keystore + if (provider == null) { + ks = KeyStore.getInstance(type); + } else { + ks = KeyStore.getInstance(type, provider); + } + // Load keystore data + try (InputStream in = new FileInputStream(file)) { + ks.load(in, password); } } + return ks; } }; try { @@ -1998,5 +2244,4 @@ return protection; } } - } diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/java/security/KeyStoreSpi.java --- a/jdk/src/java.base/share/classes/java/security/KeyStoreSpi.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/java/security/KeyStoreSpi.java Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1998, 2013, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -590,4 +590,27 @@ } return false; } + + /** + * Probes the specified input stream to determine whether it contains a + * keystore that is supported by this implementation, or not. + * + *

+ * @implSpec + * This method returns false by default. Keystore implementations should + * override this method to peek at the data stream directly or to use other + * content detection mechanisms. + * + * @param stream the keystore data to be probed + * + * @return true if the keystore data is supported, otherwise false + * + * @throws IOException if there is an I/O problem with the keystore data. + * @throws NullPointerException if stream is {@code null}. + * + * @since 1.9 + */ + public boolean engineProbe(InputStream stream) throws IOException { + return false; + } } diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/sun/security/pkcs12/PKCS12KeyStore.java --- a/jdk/src/java.base/share/classes/sun/security/pkcs12/PKCS12KeyStore.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/sun/security/pkcs12/PKCS12KeyStore.java Tue Dec 23 16:30:57 2014 +0000 @@ -69,6 +69,8 @@ import sun.security.pkcs.ContentInfo; import sun.security.x509.AlgorithmId; import sun.security.pkcs.EncryptedPrivateKeyInfo; +import sun.security.provider.JavaKeyStore.JKS; +import sun.security.util.KeyStoreDelegator; /** @@ -129,6 +131,13 @@ */ public final class PKCS12KeyStore extends KeyStoreSpi { + // special PKCS12 keystore that supports PKCS12 and JKS file formats + public static final class DualFormatPKCS12 extends KeyStoreDelegator { + public DualFormatPKCS12() { + super("PKCS12", PKCS12KeyStore.class, "JKS", JKS.class); + } + } + public static final int VERSION_3 = 3; private static final String[] KEY_PROTECTION_ALGORITHM = { @@ -1053,6 +1062,39 @@ } /** + * Determines if the keystore {@code Entry} for the specified + * {@code alias} is an instance or subclass of the specified + * {@code entryClass}. + * + * @param alias the alias name + * @param entryClass the entry class + * + * @return true if the keystore {@code Entry} for the specified + * {@code alias} is an instance or subclass of the + * specified {@code entryClass}, false otherwise + * + * @since 1.5 + */ + @Override + public boolean + engineEntryInstanceOf(String alias, + Class entryClass) + { + if (entryClass == KeyStore.TrustedCertificateEntry.class) { + return engineIsCertificateEntry(alias); + } + + Entry entry = entries.get(alias.toLowerCase(Locale.ENGLISH)); + if (entryClass == KeyStore.PrivateKeyEntry.class) { + return (entry != null && entry instanceof PrivateKeyEntry); + } + if (entryClass == KeyStore.SecretKeyEntry.class) { + return (entry != null && entry instanceof SecretKeyEntry); + } + return false; + } + + /** * Returns the (alias) name of the first keystore entry whose certificate * matches the given certificate. * @@ -1084,7 +1126,7 @@ } else { continue; } - if (certElem.equals(cert)) { + if (certElem != null && certElem.equals(cert)) { return alias; } } @@ -1923,7 +1965,12 @@ safeContentsData = safeContents.getData(); } else if (contentType.equals((Object)ContentInfo.ENCRYPTED_DATA_OID)) { if (password == null) { - continue; + + if (debug != null) { + debug.println("Warning: skipping PKCS#7 encryptedData" + + " content-type - no password was supplied"); + } + continue; } if (debug != null) { @@ -1965,8 +2012,9 @@ password = new char[1]; continue; } - throw new IOException( - "failed to decrypt safe contents entry: " + e, e); + throw new IOException("keystore password was incorrect", + new UnrecoverableKeyException( + "failed to decrypt safe contents entry: " + e)); } } } else { @@ -2284,4 +2332,73 @@ counter++; return (String.valueOf(counter)); } + + /* + * PKCS12 permitted first 24 bytes: + * + * 30 82 -- -- 02 01 03 30 82 -- -- 06 09 2A 86 48 86 F7 0D 01 07 01 A0 8- + * 30 -- 02 01 03 30 -- 06 09 2A 86 48 86 F7 0D 01 07 01 A0 -- 04 -- -- -- + * 30 81 -- 02 01 03 30 81 -- 06 09 2A 86 48 86 F7 0D 01 07 01 A0 81 -- 04 + * 30 82 -- -- 02 01 03 30 81 -- 06 09 2A 86 48 86 F7 0D 01 07 01 A0 81 -- + * 30 83 -- -- -- 02 01 03 30 82 -- -- 06 09 2A 86 48 86 F7 0D 01 07 01 A0 + * 30 83 -- -- -- 02 01 03 30 83 -- -- -- 06 09 2A 86 48 86 F7 0D 01 07 01 + * 30 84 -- -- -- -- 02 01 03 30 83 -- -- -- 06 09 2A 86 48 86 F7 0D 01 07 + * 30 84 -- -- -- -- 02 01 03 30 84 -- -- -- -- 06 09 2A 86 48 86 F7 0D 01 + */ + + private static final long[][] PKCS12_HEADER_PATTERNS = { + { 0x3082000002010330L, 0x82000006092A8648L, 0x86F70D010701A080L }, + { 0x3000020103300006L, 0x092A864886F70D01L, 0x0701A00004000000L }, + { 0x3081000201033081L, 0x0006092A864886F7L, 0x0D010701A0810004L }, + { 0x3082000002010330L, 0x810006092A864886L, 0xF70D010701A08100L }, + { 0x3083000000020103L, 0x3082000006092A86L, 0x4886F70D010701A0L }, + { 0x3083000000020103L, 0x308200000006092AL, 0x864886F70D010701L }, + { 0x3084000000000201L, 0x0330820000000609L, 0x2A864886F70D0107L }, + { 0x3084000000000201L, 0x0330820000000006L, 0x092A864886F70D01L } + }; + + private static final long[][] PKCS12_HEADER_MASKS = { + { 0xFFFF0000FFFFFFFFL, 0xFF0000FFFFFFFFFFL, 0xFFFFFFFFFFFFFFF0L }, + { 0xFF00FFFFFFFF00FFL, 0xFFFFFFFFFFFFFFFFL, 0xFFFFFF00FF000000L }, + { 0xFFFF00FFFFFFFFFFL, 0x00FFFFFFFFFFFFFFL, 0xFFFFFFFFFFFF00FFL }, + { 0xFFFF0000FFFFFFFFL, 0xFF00FFFFFFFFFFFFL, 0xFFFFFFFFFFFFFF00L }, + { 0xFFFF000000FFFFFFL, 0xFFFF0000FFFFFFFFL, 0xFFFFFFFFFFFFFFFFL }, + { 0xFFFF000000FFFFFFL, 0xFFFF000000FFFFFFL, 0xFFFFFFFFFFFFFFFFL }, + { 0xFFFF00000000FFFFL, 0xFFFFFF000000FFFFL, 0xFFFFFFFFFFFFFFFFL }, + { 0xFFFF00000000FFFFL, 0xFFFFFF00000000FFL, 0xFFFFFFFFFFFFFFFFL } + }; + + /** + * Probe the first few bytes of the keystore data stream for a valid + * PKCS12 keystore encoding. + */ + @Override + public boolean engineProbe(InputStream stream) throws IOException { + + DataInputStream dataStream; + if (stream instanceof DataInputStream) { + dataStream = (DataInputStream)stream; + } else { + dataStream = new DataInputStream(stream); + } + + long firstPeek = dataStream.readLong(); + long nextPeek = dataStream.readLong(); + long finalPeek = dataStream.readLong(); + boolean result = false; + + for (int i = 0; i < PKCS12_HEADER_PATTERNS.length; i++) { + if (PKCS12_HEADER_PATTERNS[i][0] == + (firstPeek & PKCS12_HEADER_MASKS[i][0]) && + (PKCS12_HEADER_PATTERNS[i][1] == + (nextPeek & PKCS12_HEADER_MASKS[i][1])) && + (PKCS12_HEADER_PATTERNS[i][2] == + (finalPeek & PKCS12_HEADER_MASKS[i][2]))) { + result = true; + break; + } + } + + return result; + } } diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/sun/security/provider/JavaKeyStore.java --- a/jdk/src/java.base/share/classes/sun/security/provider/JavaKeyStore.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/sun/security/provider/JavaKeyStore.java Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -31,9 +31,11 @@ import java.security.cert.CertificateFactory; import java.security.cert.CertificateException; import java.util.*; + import sun.misc.IOUtils; - import sun.security.pkcs.EncryptedPrivateKeyInfo; +import sun.security.pkcs12.PKCS12KeyStore; +import sun.security.util.KeyStoreDelegator; /** * This class provides the keystore implementation referred to as "JKS". @@ -49,7 +51,7 @@ * @since 1.2 */ -abstract class JavaKeyStore extends KeyStoreSpi { +public abstract class JavaKeyStore extends KeyStoreSpi { // regular JKS public static final class JKS extends JavaKeyStore { @@ -65,6 +67,13 @@ } } + // special JKS that supports JKS and PKCS12 file formats + public static final class DualFormatJKS extends KeyStoreDelegator { + public DualFormatJKS() { + super("JKS", JKS.class, "PKCS12", PKCS12KeyStore.class); + } + } + private static final int MAGIC = 0xfeedfeed; private static final int VERSION_1 = 0x01; private static final int VERSION_2 = 0x02; @@ -799,4 +808,20 @@ md.update("Mighty Aphrodite".getBytes("UTF8")); return md; } + + /** + * Probe the first few bytes of the keystore data stream for a valid + * JKS keystore encoding. + */ + @Override + public boolean engineProbe(InputStream stream) throws IOException { + DataInputStream dataStream; + if (stream instanceof DataInputStream) { + dataStream = (DataInputStream)stream; + } else { + dataStream = new DataInputStream(stream); + } + + return MAGIC == dataStream.readInt(); + } } diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/sun/security/provider/Sun.java --- a/jdk/src/java.base/share/classes/sun/security/provider/Sun.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/sun/security/provider/Sun.java Tue Dec 23 16:30:57 2014 +0000 @@ -40,7 +40,7 @@ private static final String INFO = "SUN " + "(DSA key/parameter generation; DSA signing; SHA-1, MD5 digests; " + - "SecureRandom; X.509 certificates; JKS & DKS keystores; " + + "SecureRandom; X.509 certificates; PKCS12, JKS & DKS keystores; " + "PKIX CertPathValidator; " + "PKIX CertPathBuilder; LDAP, Collection CertStores, JavaPolicy Policy; " + "JavaLoginConfig Configuration)"; diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/sun/security/provider/SunEntries.java --- a/jdk/src/java.base/share/classes/sun/security/provider/SunEntries.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/sun/security/provider/SunEntries.java Tue Dec 23 16:30:57 2014 +0000 @@ -228,7 +228,10 @@ /* * KeyStore */ - map.put("KeyStore.JKS", "sun.security.provider.JavaKeyStore$JKS"); + map.put("KeyStore.PKCS12", + "sun.security.pkcs12.PKCS12KeyStore$DualFormatPKCS12"); + map.put("KeyStore.JKS", + "sun.security.provider.JavaKeyStore$DualFormatJKS"); map.put("KeyStore.CaseExactJKS", "sun.security.provider.JavaKeyStore$CaseExactJKS"); map.put("KeyStore.DKS", "sun.security.provider.DomainKeyStore$DKS"); diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/sun/security/tools/keytool/Main.java --- a/jdk/src/java.base/share/classes/sun/security/tools/keytool/Main.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/classes/sun/security/tools/keytool/Main.java Tue Dec 23 16:30:57 2014 +0000 @@ -124,6 +124,7 @@ private Set> providers = null; private String storetype = null; + private boolean hasStoretypeOption = false; private String srcProviderName = null; private String providerName = null; private String pathlist = null; @@ -483,11 +484,13 @@ } else if (collator.compare(flags, "-storetype") == 0 || collator.compare(flags, "-deststoretype") == 0) { storetype = args[++i]; + hasStoretypeOption = true; } else if (collator.compare(flags, "-srcstorepass") == 0) { srcstorePass = getPass(modifier, args[++i]); passwords.add(srcstorePass); } else if (collator.compare(flags, "-srcstoretype") == 0) { srcstoretype = args[++i]; + hasStoretypeOption = true; } else if (collator.compare(flags, "-srckeypass") == 0) { srckeyPass = getPass(modifier, args[++i]); passwords.add(srckeyPass); @@ -809,36 +812,42 @@ } // Create new keystore - if (providerName == null) { - keyStore = KeyStore.getInstance(storetype); + // Probe for keystore type when filename is available + if (ksfile != null && ksStream != null && providerName == null && + hasStoretypeOption == false) { + keyStore = KeyStore.getInstance(ksfile, storePass); } else { - keyStore = KeyStore.getInstance(storetype, providerName); - } - - /* - * Load the keystore data. - * - * At this point, it's OK if no keystore password has been provided. - * We want to make sure that we can load the keystore data, i.e., - * the keystore data has the right format. If we cannot load the - * keystore, why bother asking the user for his or her password? - * Only if we were able to load the keystore, and no keystore - * password has been provided, will we prompt the user for the - * keystore password to verify the keystore integrity. - * This means that the keystore is loaded twice: first load operation - * checks the keystore format, second load operation verifies the - * keystore integrity. - * - * If the keystore password has already been provided (at the - * command line), however, the keystore is loaded only once, and the - * keystore format and integrity are checked "at the same time". - * - * Null stream keystores are loaded later. - */ - if (!nullStream) { - keyStore.load(ksStream, storePass); - if (ksStream != null) { - ksStream.close(); + if (providerName == null) { + keyStore = KeyStore.getInstance(storetype); + } else { + keyStore = KeyStore.getInstance(storetype, providerName); + } + + /* + * Load the keystore data. + * + * At this point, it's OK if no keystore password has been provided. + * We want to make sure that we can load the keystore data, i.e., + * the keystore data has the right format. If we cannot load the + * keystore, why bother asking the user for his or her password? + * Only if we were able to load the keystore, and no keystore + * password has been provided, will we prompt the user for the + * keystore password to verify the keystore integrity. + * This means that the keystore is loaded twice: first load operation + * checks the keystore format, second load operation verifies the + * keystore integrity. + * + * If the keystore password has already been provided (at the + * command line), however, the keystore is loaded only once, and the + * keystore format and integrity are checked "at the same time". + * + * Null stream keystores are loaded later. + */ + if (!nullStream) { + keyStore.load(ksStream, storePass); + if (ksStream != null) { + ksStream.close(); + } } } @@ -1881,6 +1890,7 @@ boolean isPkcs11 = false; InputStream is = null; + File srcksfile = null; if (P11KEYSTORE.equalsIgnoreCase(srcstoretype) || KeyStoreUtil.isWindowsKeyStore(srcstoretype)) { @@ -1893,7 +1903,7 @@ isPkcs11 = true; } else { if (srcksfname != null) { - File srcksfile = new File(srcksfname); + srcksfile = new File(srcksfname); if (srcksfile.exists() && srcksfile.length() == 0) { throw new Exception(rb.getString ("Source.keystore.file.exists.but.is.empty.") + @@ -1908,10 +1918,16 @@ KeyStore store; try { - if (srcProviderName == null) { - store = KeyStore.getInstance(srcstoretype); + // Probe for keystore type when filename is available + if (srcksfile != null && is != null && srcProviderName == null && + hasStoretypeOption == false) { + store = KeyStore.getInstance(srcksfile, srcstorePass); } else { - store = KeyStore.getInstance(srcstoretype, srcProviderName); + if (srcProviderName == null) { + store = KeyStore.getInstance(srcstoretype); + } else { + store = KeyStore.getInstance(srcstoretype, srcProviderName); + } } if (srcstorePass == null diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/classes/sun/security/util/KeyStoreDelegator.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/jdk/src/java.base/share/classes/sun/security/util/KeyStoreDelegator.java Tue Dec 23 16:30:57 2014 +0000 @@ -0,0 +1,306 @@ +/* + * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +package sun.security.util; + +import java.io.*; +import java.security.*; +import java.security.cert.Certificate; +import java.security.cert.CertificateFactory; +import java.security.cert.CertificateException; +import java.util.*; + +import sun.security.util.Debug; + +/** + * This class delegates to a primary or secondary keystore implementation. + * + * @since 1.9 + */ + +public class KeyStoreDelegator extends KeyStoreSpi { + + private static final String KEYSTORE_TYPE_COMPAT = "keystore.type.compat"; + private static final Debug debug = Debug.getInstance("keystore"); + + private String primaryType; // the primary keystore's type + private String secondaryType; // the secondary keystore's type + private Class primaryKeyStore; + // the primary keystore's class + private Class secondaryKeyStore; + // the secondary keystore's class + private String type; // the delegate's type + private KeyStoreSpi keystore; // the delegate + private boolean compatModeEnabled = true; + + public KeyStoreDelegator( + String primaryType, + Class primaryKeyStore, + String secondaryType, + Class secondaryKeyStore) { + + // Check whether compatibility mode has been disabled + compatModeEnabled = "true".equalsIgnoreCase( + AccessController.doPrivileged((PrivilegedAction) () -> + Security.getProperty(KEYSTORE_TYPE_COMPAT))); + + if (compatModeEnabled) { + this.primaryType = primaryType; + this.secondaryType = secondaryType; + this.primaryKeyStore = primaryKeyStore; + this.secondaryKeyStore = secondaryKeyStore; + } else { + this.primaryType = primaryType; + this.secondaryType = null; + this.primaryKeyStore = primaryKeyStore; + this.secondaryKeyStore = null; + + if (debug != null) { + debug.println("WARNING: compatibility mode disabled for " + + primaryType + " and " + secondaryType + " keystore types"); + } + } + } + + @Override + public Key engineGetKey(String alias, char[] password) + throws NoSuchAlgorithmException, UnrecoverableKeyException { + return keystore.engineGetKey(alias, password); + } + + @Override + public Certificate[] engineGetCertificateChain(String alias) { + return keystore.engineGetCertificateChain(alias); + } + + @Override + public Certificate engineGetCertificate(String alias) { + return keystore.engineGetCertificate(alias); + } + + @Override + public Date engineGetCreationDate(String alias) { + return keystore.engineGetCreationDate(alias); + } + + @Override + public void engineSetKeyEntry(String alias, Key key, char[] password, + Certificate[] chain) throws KeyStoreException { + keystore.engineSetKeyEntry(alias, key, password, chain); + } + + @Override + public void engineSetKeyEntry(String alias, byte[] key, Certificate[] chain) + throws KeyStoreException { + keystore.engineSetKeyEntry(alias, key, chain); + } + + @Override + public void engineSetCertificateEntry(String alias, Certificate cert) + throws KeyStoreException { + keystore.engineSetCertificateEntry(alias, cert); + } + + @Override + public void engineDeleteEntry(String alias) throws KeyStoreException { + keystore.engineDeleteEntry(alias); + } + + @Override + public Enumeration engineAliases() { + return keystore.engineAliases(); + } + + @Override + public boolean engineContainsAlias(String alias) { + return keystore.engineContainsAlias(alias); + } + + @Override + public int engineSize() { + return keystore.engineSize(); + } + + @Override + public boolean engineIsKeyEntry(String alias) { + return keystore.engineIsKeyEntry(alias); + } + + @Override + public boolean engineIsCertificateEntry(String alias) { + return keystore.engineIsCertificateEntry(alias); + } + + @Override + public String engineGetCertificateAlias(Certificate cert) { + return keystore.engineGetCertificateAlias(cert); + } + + @Override + public KeyStore.Entry engineGetEntry(String alias, + KeyStore.ProtectionParameter protParam) + throws KeyStoreException, NoSuchAlgorithmException, + UnrecoverableEntryException { + return keystore.engineGetEntry(alias, protParam); + } + + @Override + public void engineSetEntry(String alias, KeyStore.Entry entry, + KeyStore.ProtectionParameter protParam) + throws KeyStoreException { + keystore.engineSetEntry(alias, entry, protParam); + } + + @Override + public boolean engineEntryInstanceOf(String alias, + Class entryClass) { + return keystore.engineEntryInstanceOf(alias, entryClass); + } + + @Override + public void engineStore(OutputStream stream, char[] password) + throws IOException, NoSuchAlgorithmException, CertificateException { + + if (debug != null) { + debug.println("Storing keystore in " + type + " format"); + } + keystore.engineStore(stream, password); + } + + @Override + public void engineLoad(InputStream stream, char[] password) + throws IOException, NoSuchAlgorithmException, CertificateException { + + // A new keystore is always created in the primary keystore format + if (stream == null) { + try { + keystore = primaryKeyStore.newInstance(); + + } catch (InstantiationException | IllegalAccessException e) { + // can safely ignore + } + type = primaryType; + + if (debug != null) { + debug.println("Creating a new keystore in " + type + " format"); + } + keystore.engineLoad(stream, password); + + } else { + // First try the primary keystore then try the secondary keystore + try (InputStream bufferedStream = new BufferedInputStream(stream)) { + bufferedStream.mark(Integer.MAX_VALUE); + + try { + keystore = primaryKeyStore.newInstance(); + type = primaryType; + keystore.engineLoad(bufferedStream, password); + + } catch (Exception e) { + + // incorrect password + if (e instanceof IOException && + e.getCause() instanceof UnrecoverableKeyException) { + throw (IOException)e; + } + + try { + // Ignore secondary keystore when no compatibility mode + if (!compatModeEnabled) { + throw e; + } + + keystore = secondaryKeyStore.newInstance(); + type = secondaryType; + bufferedStream.reset(); + keystore.engineLoad(bufferedStream, password); + + if (debug != null) { + debug.println("WARNING: switching from " + + primaryType + " to " + secondaryType + + " keystore file format has altered the " + + "keystore security level"); + } + + } catch (InstantiationException | + IllegalAccessException e2) { + // can safely ignore + + } catch (IOException | + NoSuchAlgorithmException | + CertificateException e3) { + + // incorrect password + if (e3 instanceof IOException && + e3.getCause() instanceof + UnrecoverableKeyException) { + throw (IOException)e3; + } + // rethrow the outer exception + if (e instanceof IOException) { + throw (IOException)e; + } else if (e instanceof CertificateException) { + throw (CertificateException)e; + } else if (e instanceof NoSuchAlgorithmException) { + throw (NoSuchAlgorithmException)e; + } + } + } + } + + if (debug != null) { + debug.println("Loaded a keystore in " + type + " format"); + } + } + } + + /** + * Probe the first few bytes of the keystore data stream for a valid + * keystore encoding. Only the primary keystore implementation is probed. + */ + @Override + public boolean engineProbe(InputStream stream) throws IOException { + + boolean result = false; + + try { + keystore = primaryKeyStore.newInstance(); + type = primaryType; + result = keystore.engineProbe(stream); + + } catch (Exception e) { + throw new IOException(e); + + } finally { + // reset + if (result == false) { + type = null; + keystore = null; + } + } + + return result; + } +} diff -r 0cbef7c46996 -r 47080f9ae750 jdk/src/java.base/share/conf/security/java.security --- a/jdk/src/java.base/share/conf/security/java.security Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/src/java.base/share/conf/security/java.security Tue Dec 23 16:30:57 2014 +0000 @@ -183,7 +183,17 @@ # # Default keystore type. # -keystore.type=jks +keystore.type=pkcs12 + +# +# Controls compatibility mode for JKS and PKCS12 keystore types. +# +# When set to 'true', both JKS and PKCS12 keystore types support loading +# keystore files in either JKS or PKCS12 format. When set to 'false' the +# JKS keystore type supports loading only JKS keystore files and the PKCS12 +# keystore type supports loading only PKCS12 keystore files. +# +keystore.type.compat=true # # List of comma-separated packages that start with or equal this string diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/java/security/KeyStore/PKCS12/ReadP12Test.java --- a/jdk/test/java/security/KeyStore/PKCS12/ReadP12Test.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/java/security/KeyStore/PKCS12/ReadP12Test.java Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2003,2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -65,8 +65,7 @@ public class ReadP12Test { - private final static String IN_KETYSTORE_TYPE = "pkcs12"; - private final static String IN_KEYSTORE_PRV = "SunJSSE"; + private final static String IN_KEYSTORE_TYPE = "pkcs12"; private final static String IN_STORE_PASS = "pass"; public static void main(String args[]) throws Exception { @@ -124,8 +123,7 @@ String dir = System.getProperty("test.src", "."); String keystorePath = dir + File.separator + "certs" + File.separator + "readP12"; - inputKeyStore = KeyStore - .getInstance(IN_KETYSTORE_TYPE, IN_KEYSTORE_PRV); + inputKeyStore = KeyStore.getInstance(IN_KEYSTORE_TYPE); // KeyStore have encoded by Base64.getMimeEncoder().encode(),need decode // first. byte[] input = Files.readAllBytes(Paths.get(keystorePath, inKeyStore)); diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/java/security/KeyStore/ProbeKeystores.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/jdk/test/java/security/KeyStore/ProbeKeystores.java Tue Dec 23 16:30:57 2014 +0000 @@ -0,0 +1,287 @@ +/* + * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8044445 + * @summary test new methods from JEP-229: Create PKCS12 Keystores by Default + */ + +import java.io.*; +import java.security.*; +import java.security.KeyStore.*; +import java.security.cert.*; +import javax.crypto.*; +import javax.security.auth.callback.*; + +public class ProbeKeystores { + private static final char[] PASSWORD = "changeit".toCharArray(); + private static final char[] BAD_PASSWORD = "badpasword".toCharArray(); + private static final String DIR = System.getProperty("test.src", "."); + private static final String CERT_FILE = "trusted.pem"; + + public static final void main(String[] args) throws Exception { + try { + test(); + } finally { + cleanup(); + } + } + + private static final void test() throws Exception { + cleanup(); + + // Testing empty keystores + + init("empty.jks", "JKS"); + init("empty.jceks", "JCEKS"); + init("empty.p12", "PKCS12"); + + load("empty.jks", "JKS"); + load("empty.jceks", "JCEKS"); + load("empty.p12", "PKCS12"); + load("empty.jks", "PKCS12"); // test compatibility mode + load("empty.p12", "JKS"); // test compatibility mode + load("empty.jks", "PKCS12", true); // test without compatibility mode + load("empty.jks", "JKS", false); // test without compatibility mode + load("empty.p12", "JKS", true); // test without compatibility mode + load("empty.p12", "PKCS12", false); // test without compatibility mode + + probe("empty.jks", "JKS"); + probe("empty.jceks", "JCEKS"); + probe("empty.p12", "PKCS12"); + + build("empty.jks", "JKS", true); + build("empty.jks", "JKS", false); + build("empty.jceks", "JCEKS", true); + build("empty.jceks", "JCEKS", false); + build("empty.p12", "PKCS12", true); + build("empty.p12", "PKCS12", false); + + // Testing keystores containing an X.509 certificate + + X509Certificate cert = loadCertificate(CERT_FILE); + init("onecert.jks", "JKS", cert); + init("onecert.jceks", "JCEKS", cert); + init("onecert.p12", "PKCS12", cert); + + load("onecert.jks", "JKS"); + load("onecert.jceks", "JCEKS"); + load("onecert.p12", "PKCS12"); + load("onecert.jks", "PKCS12"); // test compatibility mode + load("onecert.p12", "JKS"); // test compatibility mode + load("onecert.jks", "PKCS12", true); // test without compatibility mode + load("onecert.jks", "JKS", false); // test without compatibility mode + load("onecert.p12", "JKS", true); // test without compatibility mode + load("onecert.p12", "PKCS12", false); // test without compatibility mode + + probe("onecert.jks", "JKS"); + probe("onecert.jceks", "JCEKS"); + probe("onecert.p12", "PKCS12"); + + build("onecert.jks", "JKS", true); + build("onecert.jks", "JKS", false); + build("onecert.jceks", "JCEKS", true); + build("onecert.jceks", "JCEKS", false); + build("onecert.p12", "PKCS12", true); + build("onecert.p12", "PKCS12", false); + + // Testing keystores containing a secret key + + SecretKey key = generateSecretKey("AES", 128); + init("onekey.jceks", "JCEKS", key); + init("onekey.p12", "PKCS12", key); + + load("onekey.jceks", "JCEKS"); + load("onekey.p12", "PKCS12"); + load("onekey.p12", "JKS"); // test compatibility mode + load("onekey.p12", "JKS", true); // test without compatibility mode + load("onekey.p12", "PKCS12", false); // test without compatibility mode + + probe("onekey.jceks", "JCEKS"); + probe("onekey.p12", "PKCS12"); + + build("onekey.jceks", "JCEKS", true); + build("onekey.jceks", "JCEKS", false); + build("onekey.p12", "PKCS12", true); + build("onekey.p12", "PKCS12", false); + + System.out.println("OK."); + } + + private static void cleanup() { + new File("empty.jks").delete(); + new File("empty.jceks").delete(); + new File("empty.p12").delete(); + new File("onecert.jks").delete(); + new File("onecert.jceks").delete(); + new File("onecert.p12").delete(); + new File("onekey.jceks").delete(); + new File("onekey.p12").delete(); + } + + // Instantiate an empty keystore using the supplied keystore type + private static void init(String file, String type) throws Exception { + KeyStore ks = KeyStore.getInstance(type); + ks.load(null, null); + try (OutputStream stream = new FileOutputStream(DIR + "/" + file)) { + ks.store(stream, PASSWORD); + } + System.out.println("Created a " + type + " keystore named '" + file + "'"); + } + + // Instantiate a keystore using the supplied keystore type & create an entry + private static void init(String file, String type, X509Certificate cert) + throws Exception { + KeyStore ks = KeyStore.getInstance(type); + ks.load(null, null); + ks.setEntry("mycert", new KeyStore.TrustedCertificateEntry(cert), null); + try (OutputStream stream = new FileOutputStream(DIR + "/" + file)) { + ks.store(stream, PASSWORD); + } + System.out.println("Created a " + type + " keystore named '" + file + "'"); + } + + // Instantiate a keystore using the supplied keystore type & create an entry + private static void init(String file, String type, SecretKey key) + throws Exception { + KeyStore ks = KeyStore.getInstance(type); + ks.load(null, null); + ks.setEntry("mykey", new KeyStore.SecretKeyEntry(key), + new PasswordProtection(PASSWORD)); + try (OutputStream stream = new FileOutputStream(DIR + "/" + file)) { + ks.store(stream, PASSWORD); + } + System.out.println("Created a " + type + " keystore named '" + file + "'"); + } + + // Instantiate a keystore by probing the supplied file for the keystore type + private static void probe(String file, String type) throws Exception { + // First try with the correct password + KeyStore ks = KeyStore.getInstance(new File(DIR, file), PASSWORD); + if (!type.equalsIgnoreCase(ks.getType())) { + throw new Exception("ERROR: expected a " + type + " keystore, " + + "got a " + ks.getType() + " keystore instead"); + } else { + System.out.println("Probed a " + type + " keystore named '" + file + "'"); + } + + // Next try with an incorrect password + try { + ks = KeyStore.getInstance(new File(DIR, file), BAD_PASSWORD); + throw new Exception("ERROR: expected an exception but got success"); + } catch (IOException e) { + System.out.println("Failed to load a " + type + " keystore named '" + file + "' (as expected)"); + } + } + + // Instantiate a keystore by probing the supplied file for the keystore type + private static void build(String file, String type, boolean usePassword) + throws Exception { + + Builder builder; + if (usePassword) { + builder = Builder.newInstance(new File(DIR, file), + new PasswordProtection(PASSWORD)); + } else { + builder = Builder.newInstance(new File(DIR, file), + new CallbackHandlerProtection(new DummyHandler())); + } + KeyStore ks = builder.getKeyStore(); + if (!type.equalsIgnoreCase(ks.getType())) { + throw new Exception("ERROR: expected a " + type + " keystore, " + + "got a " + ks.getType() + " keystore instead"); + } else { + System.out.println("Built a " + type + " keystore named '" + file + "'"); + } + } + + // Load the keystore entries + private static void load(String file, String type) throws Exception { + KeyStore ks = KeyStore.getInstance(type); + try (InputStream stream = new FileInputStream(DIR + "/" + file)) { + ks.load(stream, PASSWORD); + } + if (!type.equalsIgnoreCase(ks.getType())) { + throw new Exception("ERROR: expected a " + type + " keystore, " + + "got a " + ks.getType() + " keystore instead"); + } else { + System.out.println("Loaded a " + type + " keystore named '" + file + "'"); + } + } + + // Load the keystore entries (with compatibility mode disabled) + private static void load(String file, String type, boolean expectFailure) + throws Exception { + Security.setProperty("keystore.type.compat", "false"); + try { + load(file, type); + if (expectFailure) { + throw new Exception("ERROR: expected load to fail but it didn't"); + } + } catch (IOException e) { + if (expectFailure) { + System.out.println("Failed to load a " + type + " keystore named '" + file + "' (as expected)"); + } else { + throw e; + } + } finally { + Security.setProperty("keystore.type.compat", "true"); + } + } + + // Read an X.509 certificate from the supplied file + private static X509Certificate loadCertificate(String certFile) + throws Exception { + X509Certificate cert = null; + try (FileInputStream certStream = + new FileInputStream(DIR + "/" + certFile)) { + CertificateFactory factory = + CertificateFactory.getInstance("X.509"); + return (X509Certificate) factory.generateCertificate(certStream); + } + } + + // Generate a secret key using the supplied algorithm name and key size + private static SecretKey generateSecretKey(String algorithm, int size) + throws NoSuchAlgorithmException { + KeyGenerator generator = KeyGenerator.getInstance(algorithm); + generator.init(size); + return generator.generateKey(); + } + + private static class DummyHandler implements CallbackHandler { + public void handle(Callback[] callbacks) + throws IOException, UnsupportedCallbackException { + System.out.println("** Callbackhandler invoked"); + for (int i = 0; i < callbacks.length; i++) { + Callback cb = callbacks[i]; + if (cb instanceof PasswordCallback) { + PasswordCallback pcb = (PasswordCallback)cb; + pcb.setPassword(PASSWORD); + break; + } + } + } + } +} diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/java/security/KeyStore/trusted.pem --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/jdk/test/java/security/KeyStore/trusted.pem Tue Dec 23 16:30:57 2014 +0000 @@ -0,0 +1,29 @@ +-----BEGIN CERTIFICATE----- +MIIF5DCCBMygAwIBAgIQGVCD3zqdD1ZMZZ/zLAPnQzANBgkqhkiG9w0BAQUFADCBvDELMAkGA1UE +BhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMR8wHQYDVQQLExZWZXJpU2lnbiBUcnVzdCBO +ZXR3b3JrMTswOQYDVQQLEzJUZXJtcyBvZiB1c2UgYXQgaHR0cHM6Ly93d3cudmVyaXNpZ24uY29t +L3JwYSAoYykxMDE2MDQGA1UEAxMtVmVyaVNpZ24gQ2xhc3MgMyBJbnRlcm5hdGlvbmFsIFNlcnZl +ciBDQSAtIEczMB4XDTEyMDcxMDAwMDAwMFoXDTEzMDczMTIzNTk1OVowgbgxCzAJBgNVBAYTAlVT +MRMwEQYDVQQIEwpDYWxpZm9ybmlhMRcwFQYDVQQHFA5SZWR3b29kIFNob3JlczEbMBkGA1UEChQS +T3JhY2xlIENvcnBvcmF0aW9uMRIwEAYDVQQLFAlHbG9iYWwgSVQxMzAxBgNVBAsUKlRlcm1zIG9m +IHVzZSBhdCB3d3cudmVyaXNpZ24uY29tL3JwYSAoYykwNTEVMBMGA1UEAxQMKi5vcmFjbGUuY29t +MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAz/dOCGrWzPj62q0ZkF59Oj9Fli4wHAuX +U4/S0yBXF8j6K7TKWFTQkGZt3+08KUhmLm1CE1DbbyRJT292YNXYXunNaKdABob8kaBO/NESUOEJ +0SZh7fd0xCSJAAPiwOMrM5jLeb/dEpU6nP74Afrhu5ffvKdcvTRGguj9H2oVsisTK8Z1HsiiwcJG +JXcrjvdCZoPU4FHvK03XZPAqPHKNSaJOrux6kRIWYjQMlmL+qDOb0nNHa6gBdi+VqqJHJHeAM677 +dcUd0jn2m2OWtUnrM3MJZQof7/z27RTdX5J8np0ChkUgm63biDgRZO7uZP0DARQ0I6lZMlrarT8/ +sct3twIDAQABo4IB4jCCAd4wFwYDVR0RBBAwDoIMKi5vcmFjbGUuY29tMAkGA1UdEwQCMAAwCwYD +VR0PBAQDAgWgMEQGA1UdIAQ9MDswOQYLYIZIAYb4RQEHFwMwKjAoBggrBgEFBQcCARYcaHR0cHM6 +Ly93d3cudmVyaXNpZ24uY29tL3JwYTAdBgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwbgYI +KwYBBQUHAQwEYjBgoV6gXDBaMFgwVhYJaW1hZ2UvZ2lmMCEwHzAHBgUrDgMCGgQUS2u5KJYGDLvQ +UjibKaxLB4shBRgwJhYkaHR0cDovL2xvZ28udmVyaXNpZ24uY29tL3ZzbG9nbzEuZ2lmMHIGCCsG +AQUFBwEBBGYwZDAkBggrBgEFBQcwAYYYaHR0cDovL29jc3AudmVyaXNpZ24uY29tMDwGCCsGAQUF +BzAChjBodHRwOi8vc3ZyaW50bC1nMy1haWEudmVyaXNpZ24uY29tL1NWUkludGxHMy5jZXIwQQYD +VR0fBDowODA2oDSgMoYwaHR0cDovL3N2cmludGwtZzMtY3JsLnZlcmlzaWduLmNvbS9TVlJJbnRs +RzMuY3JsMB8GA1UdIwQYMBaAFNebfNgioBX33a1fzimbWMO8RgC1MA0GCSqGSIb3DQEBBQUAA4IB +AQAITRBlEo+qXLwCL53Db2BGnhDgnSomjne8aCmU7Yt4Kp91tzJdhNuaC/wwDuzD2dPJqzemae3s +wKiOXrmDQZDj9NNTdkrXHnCvDR4TpOynWe3zBa0bwKnV2cIRKcv482yV53u0kALyFZbagYPwOOz3 +YJA/2SqdcDn9Ztc/ABQ1SkyXyA5j4LJdf2g7BtYrFxjy0RG6We2iM781WSB/9MCNKyHgiwd3KpLf +urdSKLzy1elNAyt1P3UHwBIIvZ6sJIr/eeELc54Lxt6PtQCXx8qwxYTYXWPXbLgKBHdebgrmAbPK +TfD69wysvjk6vwSHjmvaqB4R4WRcgkuT+1gxx+ve +-----END CERTIFICATE----- diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/jarsigner/DefaultSigalg.java --- a/jdk/test/sun/security/tools/jarsigner/DefaultSigalg.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/jarsigner/DefaultSigalg.java Tue Dec 23 16:30:57 2014 +0000 @@ -74,7 +74,7 @@ KeyStore ks = KeyStore.getInstance("JKS"); try (FileInputStream jks = new FileInputStream("jks"); JarFile jf = new JarFile("a.jar")) { - ks.load(jks, null); + ks.load(jks, "changeit".toCharArray()); for (int i = 0; i A1.java echo class A2 {} > A2.java @@ -73,9 +74,9 @@ # a.jar includes 8 unsigned, 2 signed by a1 and a2, 2 signed by a3 $JAR cvf a.jar A1.class A2.class -$JARSIGNER -keystore js.jks -storepass changeit a.jar a1 +$JARSIGNER -keystore $KS -storepass changeit a.jar a1 $JAR uvf a.jar A3.class A4.class -$JARSIGNER -keystore js.jks -storepass changeit a.jar a2 +$JARSIGNER -keystore $KS -storepass changeit a.jar a2 $JAR uvf a.jar A5.class A6.class # Verify OK @@ -87,15 +88,15 @@ [ $? = 20 ] || exit $LINENO # 16(hasUnsignedEntry) -$JARSIGNER -verify a.jar -strict -keystore js.jks +$JARSIGNER -verify a.jar -strict -keystore $KS -storepass changeit [ $? = 16 ] || exit $LINENO # 16(hasUnsignedEntry)+32(notSignedByAlias) -$JARSIGNER -verify a.jar a1 -strict -keystore js.jks +$JARSIGNER -verify a.jar a1 -strict -keystore $KS -storepass changeit [ $? = 48 ] || exit $LINENO # 16(hasUnsignedEntry) -$JARSIGNER -verify a.jar a1 a2 -strict -keystore js.jks +$JARSIGNER -verify a.jar a1 a2 -strict -keystore $KS -storepass changeit [ $? = 16 ] || exit $LINENO # 12 entries all together @@ -153,25 +154,25 @@ $KT -importcert -alias badchain $KT -delete -alias ca -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar expired +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar expired [ $? = 4 ] || exit $LINENO -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar notyetvalid +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar notyetvalid [ $? = 4 ] || exit $LINENO -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar badku +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar badku [ $? = 8 ] || exit $LINENO -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar badeku +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar badeku [ $? = 8 ] || exit $LINENO -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar goodku +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar goodku [ $? = 0 ] || exit $LINENO -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar goodeku +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar goodeku [ $? = 0 ] || exit $LINENO -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar badchain +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar badchain [ $? = 4 ] || exit $LINENO $JARSIGNER -verify a.jar @@ -189,11 +190,11 @@ $KT -delete -alias ca2 # Now altchain is still self-signed -$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar altchain +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar altchain [ $? = 0 ] || exit $LINENO # If -certchain is used, then it's bad -$JARSIGNER -strict -keystore js.jks -storepass changeit -certchain certchain a.jar altchain +$JARSIGNER -strict -keystore $KS -storepass changeit -certchain certchain a.jar altchain [ $? = 4 ] || exit $LINENO $JARSIGNER -verify a.jar diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/jarsigner/emptymanifest.sh --- a/jdk/test/sun/security/tools/jarsigner/emptymanifest.sh Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/jarsigner/emptymanifest.sh Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ # -# Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved. +# Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved. # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. # # This code is free software; you can redistribute it and/or modify it @@ -44,14 +44,14 @@ ;; esac -KS=emptymanifest.jks +KS=emptymanifest.ks JFILE=em.jar KT="$TESTJAVA${FS}bin${FS}keytool ${TESTTOOLVMOPTS} -storepass changeit -keypass changeit -keystore $KS" JAR="$TESTJAVA${FS}bin${FS}jar ${TESTTOOLVMOPTS}" JAVA="$TESTJAVA${FS}bin${FS}java ${TESTVMOPTS}" JAVAC="$TESTJAVA${FS}bin${FS}javac ${TESTTOOLVMOPTS} ${TESTJAVACOPTS}" -JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner ${TESTTOOLVMOPTS}" +JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner ${TESTTOOLVMOPTS} -keystore $KS -storepass changeit" rm $KS $JFILE echo A > A @@ -70,7 +70,7 @@ $KT -alias a -dname CN=a -keyalg rsa -genkey -validity 300 -$JARSIGNER -keystore $KS -storepass changeit $JFILE a || exit 1 -$JARSIGNER -keystore $KS -verify -debug -strict $JFILE || exit 2 +$JARSIGNER $JFILE a || exit 1 +$JARSIGNER -verify -debug -strict $JFILE || exit 2 exit 0 diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/jarsigner/nameclash.sh --- a/jdk/test/sun/security/tools/jarsigner/nameclash.sh Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/jarsigner/nameclash.sh Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ # -# Copyright (c) 2009, Oracle and/or its affiliates. All rights reserved. +# Copyright (c) 2009, 2014 Oracle and/or its affiliates. All rights reserved. # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. # # This code is free software; you can redistribute it and/or modify it @@ -42,12 +42,12 @@ ;; esac -KS=nc.jks +KS=nc.ks JFILE=nc.jar KT="$TESTJAVA${FS}bin${FS}keytool ${TESTTOOLVMOPTS} -storepass changeit -keypass changeit -keystore $KS" JAR="$TESTJAVA${FS}bin${FS}jar ${TESTTOOLVMOPTS}" -JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner ${TESTTOOLVMOPTS}" +JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner ${TESTTOOLVMOPTS} -keystore $KS -storepass changeit" rm $KS $JFILE @@ -57,10 +57,10 @@ echo A > A $JAR cvf $JFILE A -$JARSIGNER -keystore $KS -storepass changeit $JFILE a -digestalg SHA1 || exit 1 -$JARSIGNER -keystore $KS -storepass changeit $JFILE b -digestalg SHA-1 || exit 2 +$JARSIGNER $JFILE a -digestalg SHA1 || exit 1 +$JARSIGNER $JFILE b -digestalg SHA-1 || exit 2 -$JARSIGNER -keystore $KS -verify -debug -strict $JFILE || exit 3 +$JARSIGNER -verify -debug -strict $JFILE || exit 3 exit 0 diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/jarsigner/passtype.sh --- a/jdk/test/sun/security/tools/jarsigner/passtype.sh Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/jarsigner/passtype.sh Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ # -# Copyright (c) 2009, 2013, Oracle and/or its affiliates. All rights reserved. +# Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved. # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. # # This code is free software; you can redistribute it and/or modify it @@ -42,7 +42,7 @@ ;; esac -KS=pt.jks +KS=pt.ks JFILE=pt.jar KT="$TESTJAVA${FS}bin${FS}keytool ${TESTTOOLVMOPTS} -keystore $KS -validity 300 -keyalg rsa" @@ -62,11 +62,15 @@ echo A > A $JAR cvf $JFILE A +# Sign $JARSIGNER -keystore $KS -storepass test12 $JFILE a || exit 4 PASSENV=test12 $JARSIGNER -keystore $KS -storepass:env PASSENV $JFILE b || exit 5 $JARSIGNER -keystore $KS -storepass:file passfile $JFILE b || exit 6 -$JARSIGNER -keystore $KS -verify -debug -strict $JFILE || exit 7 +# Verify +$JARSIGNER -keystore $KS -storepass test12 -verify -debug -strict $JFILE || exit 7 +PASSENV=test12 $JARSIGNER -keystore $KS -storepass:env PASSENV -verify -debug -strict $JFILE || exit 8 +$JARSIGNER -keystore $KS -storepass:file passfile -verify -debug -strict $JFILE || exit 9 exit 0 diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/keytool/KeyToolTest.java --- a/jdk/test/sun/security/tools/keytool/KeyToolTest.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/keytool/KeyToolTest.java Tue Dec 23 16:30:57 2014 +0000 @@ -328,15 +328,15 @@ // name changes: genkeypair, importcert, exportcert remove("x.jks"); remove("x.jks.p1.cert"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -alias p1 -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -exportcert -alias p1 -file x.jks.p1.cert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -alias p1 -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -exportcert -alias p1 -file x.jks.p1.cert"); ks = loadStore("x.jks", "changeit", "JKS"); assertTrue(ks.getKey("p1", "changeit".toCharArray()) != null, "key not DSA"); assertTrue(new File("x.jks.p1.cert").exists(), "p1 export err"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias p1"); - testOK("y\n", "-keystore x.jks -storepass changeit -importcert -alias c1 -file x.jks.p1.cert"); // importcert, prompt for Yes/No - testOK("", "-keystore x.jks -storepass changeit -importcert -alias c2 -file x.jks.p1.cert -noprompt"); // importcert, -noprompt + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias p1"); + testOK("y\n", "-keystore x.jks -storetype JKS -storepass changeit -importcert -alias c1 -file x.jks.p1.cert"); // importcert, prompt for Yes/No + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -importcert -alias c2 -file x.jks.p1.cert -noprompt"); // importcert, -noprompt ks = loadStore("x.jks", "changeit", "JKS"); assertTrue(ks.getCertificate("c1") != null, "import c1 err"); @@ -346,10 +346,10 @@ assertTrue(certImpl.getVersion() == 3, "Version is not 3"); // changealias and keyclone - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -alias p1 -dname CN=olala"); - testOK("changeit\n", "-keystore x.jks -changealias -alias p1 -destalias p11"); - testOK("changeit\n", "-keystore x.jks -changealias -alias c1 -destalias c11"); - testOK("changeit\n\n", "-keystore x.jks -keyclone -alias p11 -destalias p111"); // press ENTER when prompt for p111's keypass + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -alias p1 -dname CN=olala"); + testOK("changeit\n", "-keystore x.jks -storetype JKS -changealias -alias p1 -destalias p11"); + testOK("changeit\n", "-keystore x.jks -storetype JKS -changealias -alias c1 -destalias c11"); + testOK("changeit\n\n", "-keystore x.jks -storetype JKS -keyclone -alias p11 -destalias p111"); // press ENTER when prompt for p111's keypass ks = loadStore("x.jks", "changeit", "JKS"); assertTrue(!ks.containsAlias("p1"), "there is no p1"); assertTrue(!ks.containsAlias("c1"), "there is no c1"); @@ -382,7 +382,7 @@ assertTrue(!ks.containsAlias("s7"), "s7 not created"); // maybe we needn't test this, one day JKS will support SecretKey - //testFail("changeit\nchangeit\n", "-keystore x.jks -genseckey -keyalg AES -alias s3 -keysize 128"); + //testFail("changeit\nchangeit\n", "-keystore x.jks -storetype JKS -genseckey -keyalg AES -alias s3 -keysize 128"); // importKeyStore remove("x.jks"); @@ -479,9 +479,9 @@ // pkcs12 remove("x.jks"); - testFail("changeit\nchangeit\n", "-keystore x.jks -genkeypair -alias p1 -dname CN=olala"); // JKS prompt for keypass + testFail("changeit\nchangeit\n", "-keystore x.jks -storetype JKS -genkeypair -alias p1 -dname CN=olala"); // JKS prompt for keypass remove("x.jks"); - testOK("changeit\nchangeit\n\n", "-keystore x.jks -genkeypair -alias p1 -dname CN=olala"); // just type ENTER means keypass=storepass + testOK("changeit\nchangeit\n\n", "-keystore x.jks -storetype JKS -genkeypair -alias p1 -dname CN=olala"); // just type ENTER means keypass=storepass remove("x.p12"); testOK("", "-keystore x.p12 -storetype PKCS12 -storepass changeit -genkeypair -alias p0 -dname CN=olala"); // PKCS12 only need storepass testOK("changeit\n", "-keystore x.p12 -storetype PKCS12 -genkeypair -alias p1 -dname CN=olala"); @@ -616,84 +616,84 @@ void sqeImportTest() throws Exception { KeyStore ks; remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert"); - /* deleted */ testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); - /* deleted */ testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("yes\n", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -exportcert -file x.jks.p1.cert"); + /* deleted */ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); + /* deleted */ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("yes\n", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert"); ks = loadStore("x.jks", "changeit", "JKS"); assertTrue(ks.containsAlias("mykey"), "imported"); - /* deleted */ testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("\n", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert"); + /* deleted */ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("\n", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert"); ks = loadStore("x.jks", "changeit", "JKS"); assertTrue(!ks.containsAlias("mykey"), "imported"); - testOK("no\n", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert"); + testOK("no\n", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert"); ks = loadStore("x.jks", "changeit", "JKS"); assertTrue(!ks.containsAlias("mykey"), "imported"); - testFail("no\n", "-keystore x.jks -storepass changeit -importcert -file nonexist"); - testFail("no\n", "-keystore x.jks -storepass changeit -importcert -file x.jks"); + testFail("no\n", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file nonexist"); + testFail("no\n", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks"); remove("x.jks"); } // keyclone: exist. nonexist err, cert err, dest exist, misc void sqeKeyclonetest() throws Exception { remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -new newpass -keyclone -dest p0"); // new pass - testOK("\n", "-keystore x.jks -storepass changeit -keypass changeit -keyclone -dest p1"); // new pass - testOK("\n", "-keystore x.jks -storepass changeit -keyclone -dest p2"); - testFail("\n", "-keystore x.jks -storepass changeit -keyclone -dest p2"); - testFail("\n", "-keystore x.jks -storepass changeit -keyclone -dest p3 -alias noexist"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -new newpass -keyclone -dest p0"); // new pass + testOK("\n", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -keyclone -dest p1"); // new pass + testOK("\n", "-keystore x.jks -storetype JKS -storepass changeit -keyclone -dest p2"); + testFail("\n", "-keystore x.jks -storetype JKS -storepass changeit -keyclone -dest p2"); + testFail("\n", "-keystore x.jks -storetype JKS -storepass changeit -keyclone -dest p3 -alias noexist"); // no cert - testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -new newpass -keyclone -dest p0"); // new pass + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -exportcert -file x.jks.p1.cert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -new newpass -keyclone -dest p0"); // new pass remove("x.jks"); } // keypasswd: exist, short, nonexist err, cert err, misc void sqeKeypasswdTest() throws Exception { remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd -new newpass"); - /*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit"); - testOK("newpass\nnewpass\n", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd"); - /*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit"); - testOK("new\nnew\nnewpass\nnewpass\n", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd"); - /*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit"); - testOK("", "-keystore x.jks -storepass changeit -keypasswd -new newpass"); - /*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit"); - testOK("changeit\n", "-keystore x.jks -keypasswd -new newpass"); - /*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit"); - testFail("", "-keystore x.jks -storepass badpass -keypass changeit -keypasswd -new newpass"); - testFail("", "-keystore x.jks -storepass changeit -keypass bad -keypasswd -new newpass"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -keypasswd -new newpass"); + /*change back*/ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass newpass -keypasswd -new changeit"); + testOK("newpass\nnewpass\n", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -keypasswd"); + /*change back*/ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass newpass -keypasswd -new changeit"); + testOK("new\nnew\nnewpass\nnewpass\n", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -keypasswd"); + /*change back*/ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass newpass -keypasswd -new changeit"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypasswd -new newpass"); + /*change back*/ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass newpass -keypasswd -new changeit"); + testOK("changeit\n", "-keystore x.jks -storetype JKS -keypasswd -new newpass"); + /*change back*/ testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass newpass -keypasswd -new changeit"); + testFail("", "-keystore x.jks -storetype JKS -storepass badpass -keypass changeit -keypasswd -new newpass"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass bad -keypasswd -new newpass"); // no cert - testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd -new newpass"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -exportcert -file x.jks.p1.cert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -keypasswd -new newpass"); // diff pass - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -keypass keypass -genkeypair -dname CN=olala"); - testFail("", "-keystore x.jks -storepass changeit -keypasswd -new newpass"); - testOK("keypass\n", "-keystore x.jks -storepass changeit -keypasswd -new newpass"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass keypass -genkeypair -dname CN=olala"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypasswd -new newpass"); + testOK("keypass\n", "-keystore x.jks -storetype JKS -storepass changeit -keypasswd -new newpass"); // i hate those misc test remove("x.jks"); } // list: -f -alias, exist, nonexist err; otherwise, check all shows, -rfc shows more, and misc void sqeListTest() throws Exception { remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -list"); - testOK("", "-keystore x.jks -storepass changeit -list -alias mykey"); - testFail("", "-keystore x.jks -storepass changeit -list -alias notexist"); - testFail("", "-keystore x.jks -storepass badpass -list -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -keypass badpass -list -alias mykey"); // keypass ignore - testOK("\n", "-keystore x.jks -list"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -list"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -list -alias mykey"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -list -alias notexist"); + testFail("", "-keystore x.jks -storetype JKS -storepass badpass -list -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass badpass -list -alias mykey"); // keypass ignore + testOK("\n", "-keystore x.jks -storetype JKS -list"); assertTrue(err.indexOf("WARNING") != -1, "no storepass"); - testOK("changeit\n", "-keystore x.jks -list"); + testOK("changeit\n", "-keystore x.jks -storetype JKS -list"); assertTrue(err.indexOf("WARNING") == -1, "has storepass"); - testFail("badpass\n", "-keystore x.jks -list"); + testFail("badpass\n", "-keystore x.jks -storetype JKS -list"); // misc testFail("", "-keystore aa\\bb//cc -storepass changeit -list"); testFail("", "-keystore nonexisting -storepass changeit -list"); @@ -703,45 +703,45 @@ // selfcert: exist, non-exist err, cert err, sig..., dname, wrong keypass, misc void sqeSelfCertTest() throws Exception { remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -selfcert"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert -alias nonexisting"); // not exist - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert -dname CN=NewName"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert -sigalg MD5withRSA"); // sig not compatible - testFail("", "-keystore x.jks -storepass wrong -keypass changeit -selfcert"); // bad pass - testFail("", "-keystore x.jks -storepass changeit -keypass wrong -selfcert"); // bad pass + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -selfcert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -selfcert"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -selfcert -alias nonexisting"); // not exist + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -selfcert -dname CN=NewName"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -selfcert -sigalg MD5withRSA"); // sig not compatible + testFail("", "-keystore x.jks -storetype JKS -storepass wrong -keypass changeit -selfcert"); // bad pass + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass wrong -selfcert"); // bad pass //misc testFail("", "-keystore nonexist -storepass changeit -keypass changeit -selfcert"); testFail("", "-keystore aa//dd\\gg -storepass changeit -keypass changeit -selfcert"); // diff pass remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass keypass -genkeypair -dname CN=olala"); - testFail("", "-keystore x.jks -storepass changeit -selfcert"); - testOK("keypass\n", "-keystore x.jks -storepass changeit -selfcert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass keypass -genkeypair -dname CN=olala"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -selfcert"); + testOK("keypass\n", "-keystore x.jks -storetype JKS -storepass changeit -selfcert"); - testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); - testFail("", "-keystore x.jks -storepass changeit -selfcert"); // certentry cannot do selfcert + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -exportcert -file x.jks.p1.cert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -selfcert"); // certentry cannot do selfcert remove("x.jks"); } // storepass: bad old, short new, misc void sqeStorepassTest() throws Exception { remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-storepasswd -keystore x.jks -storepass changeit -new newstore"); // all in arg - /* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit"); - testOK("changeit\nnewstore\nnewstore\n", "-storepasswd -keystore x.jks"); // all not in arg, new twice - /* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit"); - testOK("changeit\n", "-storepasswd -keystore x.jks -new newstore"); // new in arg - /* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit"); - testOK("newstore\nnewstore\n", "-storepasswd -keystore x.jks -storepass changeit"); // old in arg - /* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit"); - testOK("new\nnew\nnewstore\nnewstore\n", "-storepasswd -keystore x.jks -storepass changeit"); // old in arg - /* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit"); - testFail("", "-storepasswd -keystore x.jks -storepass badold -new newstore"); // bad old - testFail("", "-storepasswd -keystore x.jks -storepass changeit -new new"); // short new + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-storepasswd -keystore x.jks -storetype JKS -storepass changeit -new newstore"); // all in arg + /* Change back */ testOK("", "-storepasswd -keystore x.jks -storetype JKS -storepass newstore -new changeit"); + testOK("changeit\nnewstore\nnewstore\n", "-storepasswd -keystore x.jks -storetype JKS"); // all not in arg, new twice + /* Change back */ testOK("", "-storepasswd -keystore x.jks -storetype JKS -storepass newstore -new changeit"); + testOK("changeit\n", "-storepasswd -keystore x.jks -storetype JKS -new newstore"); // new in arg + /* Change back */ testOK("", "-storepasswd -keystore x.jks -storetype JKS -storepass newstore -new changeit"); + testOK("newstore\nnewstore\n", "-storepasswd -keystore x.jks -storetype JKS -storepass changeit"); // old in arg + /* Change back */ testOK("", "-storepasswd -keystore x.jks -storetype JKS -storepass newstore -new changeit"); + testOK("new\nnew\nnewstore\nnewstore\n", "-storepasswd -keystore x.jks -storetype JKS -storepass changeit"); // old in arg + /* Change back */ testOK("", "-storepasswd -keystore x.jks -storetype JKS -storepass newstore -new changeit"); + testFail("", "-storepasswd -keystore x.jks -storetype JKS -storepass badold -new newstore"); // bad old + testFail("", "-storepasswd -keystore x.jks -storetype JKS -storepass changeit -new new"); // short new // misc testFail("", "-storepasswd -keystore nonexist -storepass changeit -new newstore"); // non exist testFail("", "-storepasswd -keystore badkeystore -storepass changeit -new newstore"); // bad file @@ -752,40 +752,40 @@ void sqeGenkeyTest() throws Exception { remove("x.jks"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias newentry"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias newentry"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg DSA -alias n1"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -alias n2"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg NoSuchAlg -alias n3"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 56 -alias n4"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 999 -alias n5"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 512 -alias n6"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 1024 -alias n7"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -sigalg NoSuchAlg -alias n8"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg MD2withRSA -alias n9"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg MD5withRSA -alias n10"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg SHA1withRSA -alias n11"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias newentry"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias newentry"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg DSA -alias n1"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -alias n2"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg NoSuchAlg -alias n3"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 56 -alias n4"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 999 -alias n5"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 512 -alias n6"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 1024 -alias n7"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -sigalg NoSuchAlg -alias n8"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg MD2withRSA -alias n9"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg MD5withRSA -alias n10"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg SHA1withRSA -alias n11"); testFail("", "-keystore aa\\bb//cc\\dd -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg NoSuchAlg -alias n12"); testFail("", "-keystore badkeystore -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias n14"); - testFail("", "-keystore x.jks -storepass badpass -keypass changeit -genkeypair -dname CN=olala -alias n16"); - testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CNN=olala -alias n17"); + testFail("", "-keystore x.jks -storetype JKS -storepass badpass -keypass changeit -genkeypair -dname CN=olala -alias n16"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CNN=olala -alias n17"); remove("x.jks"); } void sqeExportTest() throws Exception { remove("x.jks"); - testFail("", "-keystore x.jks -storepass changeit -export -file mykey.cert -alias mykey"); // nonexist - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -export -file mykey.cert -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -import -file mykey.cert -noprompt -alias c1"); - testOK("", "-keystore x.jks -storepass changeit -export -file mykey.cert2 -alias c1"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -export -file mykey.cert -alias mykey"); // nonexist + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -export -file mykey.cert -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -import -file mykey.cert -noprompt -alias c1"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -export -file mykey.cert2 -alias c1"); testFail("", "-keystore aa\\bb//cc\\dd -storepass changeit -export -file mykey.cert2 -alias c1"); testFail("", "-keystore nonexistkeystore -storepass changeit -export -file mykey.cert2 -alias c1"); testFail("", "-keystore badkeystore -storepass changeit -export -file mykey.cert2 -alias c1"); - testFail("", "-keystore x.jks -storepass badpass -export -file mykey.cert2 -alias c1"); + testFail("", "-keystore x.jks -storetype JKS -storepass badpass -export -file mykey.cert2 -alias c1"); remove("mykey.cert"); remove("mykey.cert2"); remove("x.jks"); @@ -793,14 +793,14 @@ void sqeDeleteTest() throws Exception { remove("x.jks"); - testFail("", "-keystore x.jks -storepass changeit -delete -alias mykey"); // nonexist - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); // nonexist + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); testFail("", "-keystore aa\\bb//cc\\dd -storepass changeit -delete -alias mykey"); // keystore name illegal testFail("", "-keystore nonexistkeystore -storepass changeit -delete -alias mykey"); // keystore not exist testFail("", "-keystore badkeystore -storepass changeit -delete -alias mykey"); // keystore invalid - testFail("", "-keystore x.jks -storepass xxxxxxxx -delete -alias mykey"); // wrong pass + testFail("", "-keystore x.jks -storetype JKS -storepass xxxxxxxx -delete -alias mykey"); // wrong pass remove("x.jks"); } @@ -809,31 +809,31 @@ remove("x.jks.p1.cert"); remove("csr1"); // PrivateKeyEntry can do certreq - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 1024"); - testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1"); - testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg SHA1withDSA"); - testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg MD5withRSA"); // unmatched sigalg + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 1024"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -sigalg SHA1withDSA"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -sigalg MD5withRSA"); // unmatched sigalg // misc test - testFail("", "-keystore x.jks -storepass badstorepass -certreq -file csr1"); // bad storepass - testOK("changeit\n", "-keystore x.jks -certreq -file csr1"); // storepass from terminal - testFail("\n", "-keystore x.jks -certreq -file csr1"); // must provide storepass - testFail("", "-keystore x.jks -storepass changeit -keypass badkeypass -certreq -file csr1"); // bad keypass - testFail("", "-keystore x.jks -storepass changeit -certreq -file aa\\bb//cc\\dd"); // bad filepath + testFail("", "-keystore x.jks -storetype JKS -storepass badstorepass -certreq -file csr1"); // bad storepass + testOK("changeit\n", "-keystore x.jks -storetype JKS -certreq -file csr1"); // storepass from terminal + testFail("\n", "-keystore x.jks -storetype JKS -certreq -file csr1"); // must provide storepass + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -keypass badkeypass -certreq -file csr1"); // bad keypass + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file aa\\bb//cc\\dd"); // bad filepath testFail("", "-keystore noexistks -storepass changeit -certreq -file csr1"); // non-existing keystore // Try the RSA private key - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA"); - testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1"); - testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg SHA1withDSA"); // unmatched sigalg - testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg MD5withRSA"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -sigalg SHA1withDSA"); // unmatched sigalg + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -sigalg MD5withRSA"); // TrustedCertificateEntry cannot do certreq - testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert"); - testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey"); - testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); - testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1 -alias mykey"); - testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -exportcert -file x.jks.p1.cert"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -delete -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -importcert -file x.jks.p1.cert -noprompt"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1 -alias mykey"); + testFail("", "-keystore x.jks -storetype JKS -storepass changeit -certreq -file csr1"); remove("x.jks"); remove("x.jks.p1.cert"); remove("csr1"); @@ -842,8 +842,8 @@ void sqePrintcertTest() throws Exception { remove("x.jks"); remove("mykey.cert"); - testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); - testOK("", "-keystore x.jks -storepass changeit -export -file mykey.cert -alias mykey"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -genkeypair -dname CN=olala"); + testOK("", "-keystore x.jks -storetype JKS -storepass changeit -export -file mykey.cert -alias mykey"); testFail("", "-printcert -file badkeystore"); testFail("", "-printcert -file a/b/c/d"); testOK("", "-printcert -file mykey.cert"); @@ -857,7 +857,7 @@ void v3extTest(String keyAlg) throws Exception { KeyStore ks; remove("x.jks"); - String simple = "-keystore x.jks -storepass changeit -keypass changeit -noprompt -keyalg " + keyAlg + " "; + String simple = "-keystore x.jks -storetype JKS -storepass changeit -keypass changeit -noprompt -keyalg " + keyAlg + " "; String pre = simple + "-genkeypair -dname CN=Olala -alias "; // Version and SKID @@ -1195,39 +1195,39 @@ testOK("", "-help"); // 2. keytool -genkey -v -keysize 512 Enter "a" for the keystore password. Check error (password too short). Enter "password" for the keystore password. Hit 'return' for "first and last name", "organizational unit", "City", "State", and "Country Code". Type "yes" when they ask you if everything is correct. Type 'return' for new key password. - testOK("a\npassword\npassword\nMe\nHere\nNow\nPlace\nPlace\nUS\nyes\n\n", "-genkey -v -keysize 512 -keystore x.jks"); + testOK("a\npassword\npassword\nMe\nHere\nNow\nPlace\nPlace\nUS\nyes\n\n", "-genkey -v -keysize 512 -keystore x.jks -storetype JKS"); // 3. keytool -list -v -storepass password - testOK("", "-list -v -storepass password -keystore x.jks"); + testOK("", "-list -v -storepass password -keystore x.jks -storetype JKS"); // 4. keytool -list -v Type "a" for the keystore password. Check error (wrong keystore password). - testFail("a\n", "-list -v -keystore x.jks"); + testFail("a\n", "-list -v -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("password was incorrect") != -1); // 5. keytool -genkey -v -keysize 512 Enter "password" as the password. Check error (alias 'mykey' already exists). - testFail("password\n", "-genkey -v -keysize 512 -keystore x.jks"); + testFail("password\n", "-genkey -v -keysize 512 -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("alias already exists") != -1); // 6. keytool -genkey -v -keysize 512 -alias mykey2 -storepass password Hit 'return' for "first and last name", "organizational unit", "City", "State", and "Country Code". Type "yes" when they ask you if everything is correct. Type 'return' for new key password. - testOK("\n\n\n\n\n\nyes\n\n", "-genkey -v -keysize 512 -alias mykey2 -storepass password -keystore x.jks"); + testOK("\n\n\n\n\n\nyes\n\n", "-genkey -v -keysize 512 -alias mykey2 -storepass password -keystore x.jks -storetype JKS"); // 7. keytool -list -v Type 'password' for the store password. - testOK("password\n", "-list -v -keystore x.jks"); + testOK("password\n", "-list -v -keystore x.jks -storetype JKS"); // 8. keytool -keypasswd -v -alias mykey2 -storepass password Type "a" for the new key password. Type "aaaaaa" for the new key password. Type "bbbbbb" when re-entering the new key password. Type "a" for the new key password. Check Error (too many failures). - testFail("a\naaaaaa\nbbbbbb\na\n", "-keypasswd -v -alias mykey2 -storepass password -keystore x.jks"); + testFail("a\naaaaaa\nbbbbbb\na\n", "-keypasswd -v -alias mykey2 -storepass password -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("Too many failures - try later") != -1); // 9. keytool -keypasswd -v -alias mykey2 -storepass password Type "aaaaaa" for the new key password. Type "aaaaaa" when re-entering the new key password. - testOK("aaaaaa\naaaaaa\n", "-keypasswd -v -alias mykey2 -storepass password -keystore x.jks"); + testOK("aaaaaa\naaaaaa\n", "-keypasswd -v -alias mykey2 -storepass password -keystore x.jks -storetype JKS"); // 10. keytool -selfcert -v -alias mykey -storepass password - testOK("", "-selfcert -v -alias mykey -storepass password -keystore x.jks"); + testOK("", "-selfcert -v -alias mykey -storepass password -keystore x.jks -storetype JKS"); // 11. keytool -list -v -storepass password - testOK("", "-list -v -storepass password -keystore x.jks"); + testOK("", "-list -v -storepass password -keystore x.jks -storetype JKS"); // 12. keytool -export -v -alias mykey -file cert -storepass password remove("cert"); - testOK("", "-export -v -alias mykey -file cert -storepass password -keystore x.jks"); + testOK("", "-export -v -alias mykey -file cert -storepass password -keystore x.jks -storetype JKS"); // 13. keytool -import -v -file cert -storepass password Check error (Certificate reply and cert are the same) - testFail("", "-import -v -file cert -storepass password -keystore x.jks"); + testFail("", "-import -v -file cert -storepass password -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("Certificate reply and certificate in keystore are identical") != -1); // 14. keytool -printcert -file cert - testOK("", "-printcert -file cert -keystore x.jks"); + testOK("", "-printcert -file cert -keystore x.jks -storetype JKS"); remove("cert"); // 15. keytool -list -storepass password -provider sun.security.provider.Sun - testOK("", "-list -storepass password -provider sun.security.provider.Sun -keystore x.jks"); + testOK("", "-list -storepass password -provider sun.security.provider.Sun -keystore x.jks -storetype JKS"); //Error tests @@ -1245,13 +1245,13 @@ testFail("", "-keypasswd -storetype PKCS11 -keystore NONE"); assertTrue(ex.indexOf("UnsupportedOperationException") != -1); // 5. keytool -list -protected -storepass password Check error (password can not be specified with -protected) - testFail("", "-list -protected -storepass password -keystore x.jks"); + testFail("", "-list -protected -storepass password -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("if -protected is specified, then") != -1); // 6. keytool -keypasswd -protected -keypass password Check error (password can not be specified with -protected) - testFail("", "-keypasswd -protected -keypass password -keystore x.jks"); + testFail("", "-keypasswd -protected -keypass password -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("if -protected is specified, then") != -1); // 7. keytool -keypasswd -protected -new password Check error (password can not be specified with -protected) - testFail("", "-keypasswd -protected -new password -keystore x.jks"); + testFail("", "-keypasswd -protected -new password -keystore x.jks -storetype JKS"); assertTrue(ex.indexOf("if -protected is specified, then") != -1); remove("x.jks"); } diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/keytool/NewSize7.java --- a/jdk/test/sun/security/tools/keytool/NewSize7.java Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/keytool/NewSize7.java Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -47,7 +47,7 @@ " -keypass changeit -keyalg rsa").split(" ")); KeyStore ks = KeyStore.getInstance("JKS"); try (FileInputStream fin = new FileInputStream(FILE)) { - ks.load(fin, null); + ks.load(fin, "changeit".toCharArray()); } Files.delete(Paths.get(FILE)); RSAPublicKey r = (RSAPublicKey)ks.getCertificate("a").getPublicKey(); diff -r 0cbef7c46996 -r 47080f9ae750 jdk/test/sun/security/tools/keytool/selfissued.sh --- a/jdk/test/sun/security/tools/keytool/selfissued.sh Tue Dec 23 15:10:15 2014 +0000 +++ b/jdk/test/sun/security/tools/keytool/selfissued.sh Tue Dec 23 16:30:57 2014 +0000 @@ -1,5 +1,5 @@ # -# Copyright (c) 2009, 2013, Oracle and/or its affiliates. All rights reserved. +# Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved. # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. # # This code is free software; you can redistribute it and/or modify it @@ -44,14 +44,14 @@ ;; esac -KS=selfsigned.jks +KS=selfsigned.ks KT="$TESTJAVA${FS}bin${FS}keytool ${TESTTOOLVMOPTS} -storepass changeit -keypass changeit -keystore $KS -keyalg rsa" rm $KS $KT -alias ca -dname CN=CA -genkeypair -$KT -alias ca1 -dname CN=CA -genkeypair -$KT -alias ca2 -dname CN=CA -genkeypair +$KT -alias ca1 -dname CN=CA1 -genkeypair +$KT -alias ca2 -dname CN=CA2 -genkeypair $KT -alias e1 -dname CN=E1 -genkeypair # ca signs ca1, ca1 signs ca2, all self-issued