Path: blob/aarch64-shenandoah-jdk8u272-b10/jdk/test/sun/security/tools/keytool/KeyToolTest.java
38853 views
/*1* Copyright (c) 2005, 2017, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223/*24*25*26* @summary Testing keytool27* @author weijun.wang28*29* Run through autotest.sh and manualtest.sh30*31* Testing non-PKCS11 keystores:32* echo | java -Dfile KeyToolTest33*34* Testing NSS PKCS11 keystores:35* # testing NSS36* # make sure the NSS db files are in current directory and writable37* echo | java -Dnss -Dnss.lib=/path/to/libsoftokn3.so KeyToolTest38*39* Testing Solaris Cryptography Framework PKCS11 keystores:40* # make sure you've already run pktool and set test12 as pin41* echo | java -Dsolaris KeyToolTest42*43* ATTENTION:44* Exception in thread "main" java.security.ProviderException: sun.security.pkcs11.wrapper.PKCS11Exception: CKR_KEY_SIZE_RANGE45* at sun.security.pkcs11.P11Signature.engineSign(P11Signature.java:420)46* ...47* Caused by: sun.security.pkcs11.wrapper.PKCS11Exception: CKR_KEY_SIZE_RANGE48* at sun.security.pkcs11.wrapper.PKCS11.C_SignFinal(Native Method)49* at sun.security.pkcs11.P11Signature.engineSign(P11Signature.java:391)50* ...51* been observed. Possibly a Solaris bug52*53* ATTENTION:54* NSS PKCS11 config file are changed, DSA not supported now.55*/5657import java.nio.file.Files;58import java.nio.file.Paths;59import java.security.KeyStore;60import sun.security.x509.*;61import java.io.*;62import java.security.KeyPairGenerator;63import java.security.NoSuchAlgorithmException;64import java.util.*;65import java.security.cert.X509Certificate;66import sun.security.util.ObjectIdentifier;6768public class KeyToolTest {6970// The stdout and stderr outputs after a keytool run71String out;72String err;7374// the output of println() in KeyTool.run75String ex;7677String lastInput = "", lastCommand = "";78private static final boolean debug =79System.getProperty("debug") != null;8081static final String NSS_P11_ARG =82"-keystore NONE -storetype PKCS11 -providerName SunPKCS11-nss -providerClass sun.security.pkcs11.SunPKCS11 -providerArg p11-nss.txt ";83static final String NSS_SRC_P11_ARG =84"-srckeystore NONE -srcstoretype PKCS11 -srcproviderName SunPKCS11-nss -providerClass sun.security.pkcs11.SunPKCS11 -providerArg p11-nss.txt ";85static final String NZZ_P11_ARG =86"-keystore NONE -storetype PKCS11 -providerName SunPKCS11-nzz -providerClass sun.security.pkcs11.SunPKCS11 -providerArg p11-nzz.txt ";87static final String NZZ_SRC_P11_ARG =88"-srckeystore NONE -srcstoretype PKCS11 -srcproviderName SunPKCS11-nzz -providerClass sun.security.pkcs11.SunPKCS11 -providerArg p11-nzz.txt ";89static final String SUN_P11_ARG = "-keystore NONE -storetype PKCS11 ";90static final String SUN_SRC_P11_ARG = "-srckeystore NONE -srcstoretype PKCS11 ";9192String p11Arg, srcP11Arg;9394/** Creates a new instance of KeyToolTest */95KeyToolTest() {96// so that there is "Warning" and not translated into other language97Locale.setDefault(Locale.US);98}99100/**101* Helper, removes a file102*/103void remove(String filename) {104if (debug) {105System.err.println("Removing " + filename);106}107new File(filename).delete();108if (new File(filename).exists()) {109throw new RuntimeException("Error deleting " + filename);110}111}112113/**114* Run a set of keytool command with given terminal input.115* @param input the terminal inputs, the characters typed by human116* if <code>cmd</code> is running on a terminal117* @param cmd the argument of a keytool command line118* @throws if keytool goes wrong in some place119*/120void test(String input, String cmd) throws Exception {121lastInput = input;122lastCommand = cmd;123124// "X" is appended so that we can precisely test how input is consumed125HumanInputStream in = new HumanInputStream(input+"X");126test(in, cmd);127// make sure the input string is no more no less128if(in.read() != 'X' || in.read() != -1)129throw new Exception("Input not consumed exactly");130}131132void test(InputStream in, String cmd) throws Exception {133134// save the original 3 streams135if (debug) {136System.err.println(cmd);137} else {138System.err.print(".");139}140PrintStream p1 = System.out;141PrintStream p2 = System.err;142InputStream i1 = System.in;143144ByteArrayOutputStream b1 = new ByteArrayOutputStream();145ByteArrayOutputStream b2 = new ByteArrayOutputStream();146147try {148System.setIn(in);149System.setOut(new PrintStream(b1));150System.setErr(new PrintStream(b2));151152// since System.in is overrided, the153// sun.security.tools.keytool.Main.main() method will154// never block at user input155156// use -debug so that main() will throw an Exception157// instead of calling System.exit()158sun.security.tools.keytool.Main.main(("-debug "+cmd).split("\\s+"));159} finally {160out = b1.toString();161err = b2.toString();162ex = out; // now it goes to System.out163System.setIn(i1);164System.setOut(p1);165System.setErr(p2);166}167}168169/**170* Call this method if you expect test(input, cmd) should go OK171*/172void testOK(String input, String cmd) throws Exception {173try {174// Workaround for "8057810: Make SHA256withDSA the default175// jarsigner and keytool algorithm for DSA keys". Unfortunately176// SunPKCS11-NSS does not support SHA256withDSA yet.177if (cmd.contains("p11-nss.txt") && cmd.contains("-genkey")178&& !cmd.contains("-keyalg")) {179cmd += " -sigalg SHA1withDSA -keysize 1024";180}181test(input, cmd);182} catch(Exception e) {183afterFail(input, cmd, "OK");184throw e;185}186}187188/**189* Call this method if you expect test(input, cmd) should fail and throw190* an exception191*/192void testFail(String input, String cmd) throws Exception {193boolean ok;194try {195test(input, cmd);196ok = true;197} catch(Exception e) {198if (e instanceof MissingResourceException) {199ok = true;200} else {201ok = false;202}203}204if(ok) {205afterFail(input, cmd, "FAIL");206throw new RuntimeException();207}208}209210/**211* Call this method if you expect test(input, cmd) should go OK212*/213void testOK(InputStream is, String cmd) throws Exception {214try {215test(is, cmd);216} catch(Exception e) {217afterFail("", cmd, "OK");218throw e;219}220}221222/**223* Call this method if you expect test(input, cmd) should fail and throw224* an exception225*/226void testFail(InputStream is, String cmd) throws Exception {227boolean ok;228try {229test(is, cmd);230ok = true;231} catch(Exception e) {232ok = false;233}234if(ok) {235afterFail("", cmd, "FAIL");236throw new RuntimeException();237}238}239240/**241* Call this method if you just want to run the command and does242* not care if it succeeds or fails.243*/244void testAnyway(String input, String cmd) {245try {246test(input, cmd);247} catch(Exception e) {248;249}250}251252/**253* Helper method, print some output after a test does not do as expected254*/255void afterFail(String input, String cmd, String should) {256if (cmd.contains("p11-nss.txt")) {257cmd = "-J-Dnss.lib=" + System.getProperty("nss.lib") + " " + cmd;258}259System.err.println("\nTest fails for the command ---\n" +260"keytool " + cmd + "\nOr its debug version ---\n" +261"keytool -debug " + cmd);262263System.err.println("The command result should be " + should +264", but it's not. Try run the command manually and type" +265" these input into it: ");266char[] inputChars = input.toCharArray();267268for (int i=0; i<inputChars.length; i++) {269char ch = inputChars[i];270if (ch == '\n') System.err.print("ENTER ");271else if (ch == ' ') System.err.print("SPACE ");272else System.err.print(ch + " ");273}274System.err.println("");275276System.err.println("ERR is:\n"+err);277System.err.println("OUT is:\n"+out);278}279280void assertTrue(boolean bool, String msg) {281if (debug) {282System.err.println("If not " + bool + ", " + msg);283} else {284System.err.print("v");285}286if(!bool) {287afterFail(lastInput, lastCommand, "TRUE");288System.err.println(msg);289throw new RuntimeException(msg);290}291}292293void assertTrue(boolean bool) {294assertTrue(bool, "well...");295}296/**297* Helper method, load a keystore298* @param file file for keystore, null or "NONE" for PKCS11299* @pass password for the keystore300* @type keystore type301* @returns the KeyStore object302* @exception Exception if anything goes wrong303*/304KeyStore loadStore(String file, String pass, String type) throws Exception {305KeyStore ks = KeyStore.getInstance(type);306FileInputStream is = null;307if (file != null && !file.equals("NONE")) {308is = new FileInputStream(file);309}310ks.load(is, pass.toCharArray());311is.close();312return ks;313}314315/**316* The test suite.317* Maybe it's better to put this outside the KeyToolTest class318*/319void testAll() throws Exception {320KeyStore ks;321322remove("x.jks");323remove("x.jceks");324remove("x.p12");325remove("x2.jceks");326remove("x2.jks");327remove("x.jks.p1.cert");328329// name changes: genkeypair, importcert, exportcert330remove("x.jks");331remove("x.jks.p1.cert");332testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -alias p1 -dname CN=olala");333testOK("", "-keystore x.jks -storepass changeit -exportcert -alias p1 -file x.jks.p1.cert");334ks = loadStore("x.jks", "changeit", "JKS");335assertTrue(ks.getKey("p1", "changeit".toCharArray()) != null,336"key not DSA");337assertTrue(new File("x.jks.p1.cert").exists(), "p1 export err");338testOK("", "-keystore x.jks -storepass changeit -delete -alias p1");339testOK("y\n", "-keystore x.jks -storepass changeit -importcert -alias c1 -file x.jks.p1.cert"); // importcert, prompt for Yes/No340testOK("", "-keystore x.jks -storepass changeit -importcert -alias c2 -file x.jks.p1.cert -noprompt"); // importcert, -noprompt341ks = loadStore("x.jks", "changeit", "JKS");342assertTrue(ks.getCertificate("c1") != null, "import c1 err");343344// v3345byte[] encoded = ks.getCertificate("c1").getEncoded();346X509CertImpl certImpl = new X509CertImpl(encoded);347assertTrue(certImpl.getVersion() == 3, "Version is not 3");348349// changealias and keyclone350testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -alias p1 -dname CN=olala");351testOK("changeit\n", "-keystore x.jks -changealias -alias p1 -destalias p11");352testOK("changeit\n", "-keystore x.jks -changealias -alias c1 -destalias c11");353testOK("changeit\n\n", "-keystore x.jks -keyclone -alias p11 -destalias p111"); // press ENTER when prompt for p111's keypass354ks = loadStore("x.jks", "changeit", "JKS");355assertTrue(!ks.containsAlias("p1"), "there is no p1");356assertTrue(!ks.containsAlias("c1"), "there is no c1");357assertTrue(ks.containsAlias("p11"), "there is p11");358assertTrue(ks.containsAlias("c11"), "there is c11");359assertTrue(ks.containsAlias("p111"), "there is p111");360361// genSecKey362remove("x.jceks");363testOK("changeit\nchangeit\n\n", "-keystore x.jceks -storetype JCEKS -genseckey -alias s1"); // DES, no need keysize364testFail("changeit\n\n", "-keystore x.jceks -storetype JCEKS -genseckey -alias s11 -keysize 128"); // DES, keysize cannot be 128365testOK("changeit\n\n", "-keystore x.jceks -storetype JCEKS -genseckey -keyalg DESede -alias s2"); // DESede. no need keysize366testFail("changeit\n\n", "-keystore x.jceks -storetype AES -genseckey -keyalg Rijndael -alias s3"); // AES, need keysize367testOK("changeit\n\n", "-keystore x.jceks -storetype JCEKS -genseckey -keyalg AES -alias s3 -keysize 128");368// about keypass369testOK("\n", "-keystore x.jceks -storetype JCEKS -storepass changeit -genseckey -alias s4"); // can accept storepass370testOK("keypass\nkeypass\n", "-keystore x.jceks -storetype JCEKS -storepass changeit -genseckey -alias s5"); // or a new one371testOK("bad\n\bad\nkeypass\nkeypass\n", "-keystore x.jceks -storetype JCEKS -storepass changeit -genseckey -alias s6"); // keypass must be valid (prompt 3 times)372testFail("bad\n\bad\nbad\n", "-keystore x.jceks -storetype JCEKS -storepass changeit -genseckey -alias s7"); // keypass must be valid (prompt 3 times)373testFail("bad\n\bad\nbad\nkeypass\n", "-keystore x.jceks -storetype JCEKS -storepass changeit -genseckey -alias s7"); // keypass must be valid (prompt 3 times)374ks = loadStore("x.jceks", "changeit", "JCEKS");375assertTrue(ks.getKey("s1", "changeit".toCharArray()).getAlgorithm().equalsIgnoreCase("DES"), "s1 is DES");376assertTrue(ks.getKey("s1", "changeit".toCharArray()).getEncoded().length == 8, "DES is 56");377assertTrue(ks.getKey("s2", "changeit".toCharArray()).getEncoded().length == 24, "DESede is 168");378assertTrue(ks.getKey("s2", "changeit".toCharArray()).getAlgorithm().equalsIgnoreCase("DESede"), "s2 is DESede");379assertTrue(ks.getKey("s3", "changeit".toCharArray()).getAlgorithm().equalsIgnoreCase("AES"), "s3 is AES");380assertTrue(ks.getKey("s4", "changeit".toCharArray()).getAlgorithm().equalsIgnoreCase("DES"), "s4 is DES");381assertTrue(ks.getKey("s5", "keypass".toCharArray()).getAlgorithm().equalsIgnoreCase("DES"), "s5 is DES");382assertTrue(ks.getKey("s6", "keypass".toCharArray()).getAlgorithm().equalsIgnoreCase("DES"), "s6 is DES");383assertTrue(!ks.containsAlias("s7"), "s7 not created");384385// maybe we needn't test this, one day JKS will support SecretKey386//testFail("changeit\nchangeit\n", "-keystore x.jks -genseckey -keyalg AES -alias s3 -keysize 128");387388// importKeyStore389remove("x.jks");390remove("x.jceks");391testOK("changeit\nchangeit\n\n", "-keystore x.jceks -storetype JCEKS -genkeypair -alias p1 -dname CN=Olala"); // create 2 entries...392testOK("", "-keystore x.jceks -storetype JCEKS -storepass changeit -importcert -alias c1 -file x.jks.p1.cert -noprompt"); // ...393ks = loadStore("x.jceks", "changeit", "JCEKS");394assertTrue(ks.size() == 2, "2 entries in JCEKS");395// import, shouldn't mention destalias/srckeypass/destkeypass if srcalias is no given396testFail("changeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -destalias pp");397testFail("changeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srckeypass changeit");398testFail("changeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -destkeypass changeit");399// normal import400testOK("changeit\nchangeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS");401ks = loadStore("x.jks", "changeit", "JKS");402assertTrue(ks.size() == 2, "2 entries in JKS");403// import again, type yes to overwrite old entries404testOK("changeit\nchangeit\ny\ny\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS");405ks = loadStore("x.jks", "changeit", "JKS");406// import again, specify -nopromt407testOK("changeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -noprompt");408assertTrue(err.indexOf("Warning") != -1, "noprompt will warn");409ks = loadStore("x.jks", "changeit", "JKS");410assertTrue(ks.size() == 2, "2 entries in JKS");411// import again, type into new aliases when prompted412testOK("changeit\nchangeit\n\ns1\n\ns2\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS");413ks = loadStore("x.jks", "changeit", "JKS");414assertTrue(ks.size() == 4, "4 entries in JKS");415416// importkeystore single417remove("x.jks");418testOK("changeit\nchangeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p1"); // normal419ks = loadStore("x.jks", "changeit", "JKS");420assertTrue(ks.size() == 1, "1 entries in JKS");421testOK("changeit\nchangeit\ny\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p1"); // overwrite422ks = loadStore("x.jks", "changeit", "JKS");423assertTrue(ks.size() == 1, "1 entries in JKS");424testOK("changeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p1 -noprompt"); // noprompt425ks = loadStore("x.jks", "changeit", "JKS");426assertTrue(ks.size() == 1, "1 entries in JKS");427testOK("changeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p1 -destalias p2"); // rename428ks = loadStore("x.jks", "changeit", "JKS");429assertTrue(ks.size() == 2, "2 entries in JKS");430testOK("changeit\nchangeit\n\nnewalias\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p1"); // another rename431ks = loadStore("x.jks", "changeit", "JKS");432assertTrue(ks.size() == 3, "3 entries in JKS");433434// importkeystore single, different keypass435remove("x.jks");436testOK("changeit\nkeypass\nkeypass\n", "-keystore x.jceks -storetype JCEKS -genkeypair -alias p2 -dname CN=Olala"); // generate entry with different keypass437testOK("changeit\nchangeit\nchangeit\nkeypass\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p2"); // prompt438ks = loadStore("x.jks", "changeit", "JKS");439assertTrue(ks.size() == 1, "1 entries in JKS");440testOK("changeit\nchangeit\nkeypass\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias p2 -destalias p3 -destkeypass keypass2"); // diff destkeypass441ks = loadStore("x.jks", "changeit", "JKS");442assertTrue(ks.size() == 2, "2 entries in JKS");443assertTrue(ks.getKey("p2", "keypass".toCharArray()) != null, "p2 has old password");444assertTrue(ks.getKey("p3", "keypass2".toCharArray()) != null, "p3 has new password");445446// importkeystore single, cert447remove("x.jks");448testOK("changeit\nchangeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias c1"); // normal449testOK("changeit\n\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias c1 -destalias c2"); // in fact srcstorepass can be ignored450assertTrue(err.indexOf("WARNING") != -1, "But will warn");451testOK("changeit\n\ny\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias c1 -destalias c2"); // 2nd import, press y to overwrite ...452testOK("changeit\n\n\nc3\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias c1 -destalias c2"); // ... or rename453ks = loadStore("x.jks", "changeit", "JKS");454assertTrue(ks.size() == 3, "3 entries in JKS"); // c1, c2, c3455456// importkeystore, secretkey457remove("x.jks");458testOK("changeit\n\n", "-keystore x.jceks -storetype JCEKS -genseckey -alias s1"); // create SecretKeyEntry459testOK("changeit\n\n", "-keystore x.jceks -storetype JCEKS -genseckey -alias s2"); // create SecretKeyEntry460testOK("changeit\n", "-keystore x.jceks -storetype JCEKS -delete -alias p2"); // remove the keypass!=storepass one461ks = loadStore("x.jceks", "changeit", "JCEKS");462assertTrue(ks.size() == 4, "4 entries in JCEKS"); // p1, c1, s1, s2463testOK("changeit\nchangeit\nchangeit\n", "-importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS -srcalias s1"); // normal464assertTrue(err.indexOf("not imported") != -1, "Not imported");465assertTrue(err.indexOf("Cannot store non-PrivateKeys") != -1, "Not imported");466467// Importing a JCEKS keystore to a JKS one. Will warn for the 2 SecretKey entries468469remove("x.jks");470// Two "no" answers to bypass warnings471testOK("\n\n", "-srcstorepass changeit -deststorepass changeit -importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS"); // normal472assertTrue(err.indexOf("s1 not") != -1, "s1 not");473assertTrue(err.indexOf("s2 not") != -1, "s2 not");474assertTrue(err.indexOf("c1 success") != -1, "c1 success");475assertTrue(err.indexOf("p1 success") != -1, "p1 success");476remove("x.jks");477// One "yes" to stop478testOK("yes\n", "-srcstorepass changeit -deststorepass changeit -importkeystore -srckeystore x.jceks -srcstoretype JCEKS -destkeystore x.jks -deststoretype JKS"); // normal479// maybe c1 or p1 has been imported before s1 or s2 is touched, anyway we know yesNo is only asked once.480481// pkcs12482remove("x.jks");483testFail("changeit\nchangeit\n", "-keystore x.jks -genkeypair -alias p1 -dname CN=olala"); // JKS prompt for keypass484remove("x.jks");485testOK("changeit\nchangeit\n\n", "-keystore x.jks -genkeypair -alias p1 -dname CN=olala"); // just type ENTER means keypass=storepass486remove("x.p12");487testOK("", "-keystore x.p12 -storetype PKCS12 -storepass changeit -genkeypair -alias p0 -dname CN=olala"); // PKCS12 only need storepass488testOK("changeit\n", "-keystore x.p12 -storetype PKCS12 -genkeypair -alias p1 -dname CN=olala");489testOK("changeit\n", "-keystore x.p12 -keypass changeit -storetype PKCS12 -genkeypair -alias p3 -dname CN=olala"); // when specify keypass, make sure keypass==storepass...490assertTrue(err.indexOf("Warning") == -1, "PKCS12 silent when keypass == storepass");491testOK("changeit\n", "-keystore x.p12 -keypass another -storetype PKCS12 -genkeypair -alias p2 -dname CN=olala"); // otherwise, print a warning492assertTrue(err.indexOf("Warning") != -1, "PKCS12 warning when keypass != storepass");493testFail("", "-keystore x.p12 -storepass changeit -storetype PKCS12 -keypasswd -new changeit -alias p3"); // no -keypasswd for PKCS12494testOK("", "-keystore x.p12 -storepass changeit -storetype PKCS12 -changealias -alias p3 -destalias p33");495testOK("", "-keystore x.p12 -storepass changeit -storetype PKCS12 -keyclone -alias p33 -destalias p3");496497// pkcs12498remove("x.p12");499testOK("", "-keystore x.p12 -storetype PKCS12 -storepass changeit -genkeypair -alias p0 -dname CN=olala"); // PKCS12 only need storepass500testOK("", "-storepass changeit -keystore x.p12 -storetype PKCS12 -genkeypair -alias p1 -dname CN=olala");501testOK("", "-storepass changeit -keystore x.p12 -keypass changeit -storetype PKCS12 -genkeypair -alias p3 -dname CN=olala"); // when specify keypass, make sure keypass==storepass...502assertTrue(err.indexOf("Warning") == -1, "PKCS12 silent when keypass == storepass");503testOK("", "-storepass changeit -keystore x.p12 -keypass another -storetype PKCS12 -genkeypair -alias p2 -dname CN=olala"); // otherwise, print a warning504assertTrue(err.indexOf("Warning") != -1, "PKCS12 warning when keypass != storepass");505506remove("x.jks");507remove("x.jceks");508remove("x.p12");509remove("x2.jceks");510remove("x2.jks");511remove("x.jks.p1.cert");512}513514void testPKCS11() throws Exception {515KeyStore ks;516// pkcs11, the password maybe different and maybe PKCS11 is not supported517518// in case last test is not executed successfully519testAnyway("", p11Arg + "-storepass test12 -delete -alias p1");520testAnyway("", p11Arg + "-storepass test12 -delete -alias p2");521testAnyway("", p11Arg + "-storepass test12 -delete -alias p3");522testAnyway("", p11Arg + "-storepass test12 -delete -alias nss");523524testOK("", p11Arg + "-storepass test12 -list");525assertTrue(out.indexOf("Your keystore contains 0 entries") != -1, "*** MAKE SURE YOU HAVE NO ENTRIES IN YOUR PKCS11 KEYSTORE BEFORE THIS TEST ***");526527testOK("", p11Arg + "-storepass test12 -genkeypair -alias p1 -dname CN=olala");528testOK("test12\n", p11Arg + "-genkeypair -alias p2 -dname CN=olala2");529testFail("test12\n", p11Arg + "-keypass test12 -genkeypair -alias p3 -dname CN=olala3"); // cannot provide keypass for PKCS11530testFail("test12\n", p11Arg + "-keypass nonsense -genkeypair -alias p3 -dname CN=olala3"); // cannot provide keypass for PKCS11531532testOK("", p11Arg + "-storepass test12 -list");533assertTrue(out.indexOf("Your keystore contains 2 entries") != -1, "2 entries in p11");534535testOK("test12\n", p11Arg + "-alias p1 -changealias -destalias p3");536testOK("", p11Arg + "-storepass test12 -list -alias p3");537testFail("", p11Arg + "-storepass test12 -list -alias p1");538539testOK("test12\n", p11Arg + "-alias p3 -keyclone -destalias p1");540testFail("", p11Arg + "-storepass test12 -list -alias p3"); // in PKCS11, keyclone will delete old541testOK("", p11Arg + "-storepass test12 -list -alias p1");542543testFail("test12\n", p11Arg + "-alias p1 -keypasswd -new another"); // cannot change password for PKCS11544545testOK("", p11Arg + "-storepass test12 -list");546assertTrue(out.indexOf("Your keystore contains 2 entries") != -1, "2 entries in p11");547548testOK("", p11Arg + "-storepass test12 -delete -alias p1");549testOK("", p11Arg + "-storepass test12 -delete -alias p2");550551testOK("", p11Arg + "-storepass test12 -list");552assertTrue(out.indexOf("Your keystore contains 0 entries") != -1, "*** MAKE SURE YOU HAVE NO ENTRIES IN YOUR PKCS11 KEYSTORE BEFORE THIS TEST ***");553}554555void testPKCS11ImportKeyStore() throws Exception {556557KeyStore ks;558testOK("", p11Arg + "-storepass test12 -genkeypair -alias p1 -dname CN=olala");559testOK("test12\n", p11Arg + "-genkeypair -alias p2 -dname CN=olala2");560// test importkeystore for pkcs11561562remove("x.jks");563// pkcs11 -> jks564testOK("changeit\nchangeit\ntest12\n", srcP11Arg + "-importkeystore -destkeystore x.jks -deststoretype JKS -srcalias p1");565assertTrue(err.indexOf("not imported") != -1, "cannot import key without destkeypass");566ks = loadStore("x.jks", "changeit", "JKS");567assertTrue(!ks.containsAlias("p1"), "p1 is not imported");568569testOK("changeit\ntest12\n", srcP11Arg + "-importkeystore -destkeystore x.jks -deststoretype JKS -srcalias p1 -destkeypass changeit");570testOK("changeit\ntest12\n", srcP11Arg + "-importkeystore -destkeystore x.jks -deststoretype JKS -srcalias p2 -destkeypass changeit");571ks = loadStore("x.jks", "changeit", "JKS");572assertTrue(ks.containsAlias("p1"), "p1 is imported");573assertTrue(ks.containsAlias("p2"), "p2 is imported");574// jks -> pkcs11575testOK("", p11Arg + "-storepass test12 -delete -alias p1");576testOK("", p11Arg + "-storepass test12 -delete -alias p2");577testOK("test12\nchangeit\n", p11Arg + "-importkeystore -srckeystore x.jks -srcstoretype JKS");578testOK("", p11Arg + "-storepass test12 -list -alias p1");579testOK("", p11Arg + "-storepass test12 -list -alias p2");580testOK("", p11Arg + "-storepass test12 -list");581assertTrue(out.indexOf("Your keystore contains 2 entries") != -1, "2 entries in p11");582// clean up583testOK("", p11Arg + "-storepass test12 -delete -alias p1");584testOK("", p11Arg + "-storepass test12 -delete -alias p2");585testOK("", p11Arg + "-storepass test12 -list");586assertTrue(out.indexOf("Your keystore contains 0 entries") != -1, "empty p11");587588remove("x.jks");589}590591// The sqeTest reflects the test suggested by judy.gao and bill.situ at592// /net/sqesvr-nfs/global/nfs/sec/ws_6.0_int/security/src/SecurityTools/Keytool593//594void sqeTest() throws Exception {595FileOutputStream fos = new FileOutputStream("badkeystore");596for (int i=0; i<100; i++) {597fos.write(i);598}599fos.close();600601sqeCsrTest();602sqePrintcertTest();603sqeDeleteTest();604sqeExportTest();605sqeGenkeyTest();606sqeImportTest();607sqeKeyclonetest();608sqeKeypasswdTest();609sqeListTest();610sqeSelfCertTest();611sqeStorepassTest();612613remove("badkeystore");614}615616// Import: cacert, prompt, trusted, non-trusted, bad chain, not match617void sqeImportTest() throws Exception {618KeyStore ks;619remove("x.jks");620testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");621testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert");622/* deleted */ testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");623testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt");624/* deleted */ testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");625testOK("yes\n", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert");626ks = loadStore("x.jks", "changeit", "JKS");627assertTrue(ks.containsAlias("mykey"), "imported");628/* deleted */ testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");629testOK("\n", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert");630ks = loadStore("x.jks", "changeit", "JKS");631assertTrue(!ks.containsAlias("mykey"), "imported");632testOK("no\n", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert");633ks = loadStore("x.jks", "changeit", "JKS");634assertTrue(!ks.containsAlias("mykey"), "imported");635testFail("no\n", "-keystore x.jks -storepass changeit -importcert -file nonexist");636testFail("no\n", "-keystore x.jks -storepass changeit -importcert -file x.jks");637remove("x.jks");638}639// keyclone: exist. nonexist err, cert err, dest exist, misc640void sqeKeyclonetest() throws Exception {641remove("x.jks");642testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");643testOK("", "-keystore x.jks -storepass changeit -keypass changeit -new newpass -keyclone -dest p0"); // new pass644testOK("\n", "-keystore x.jks -storepass changeit -keypass changeit -keyclone -dest p1"); // new pass645testOK("\n", "-keystore x.jks -storepass changeit -keyclone -dest p2");646testFail("\n", "-keystore x.jks -storepass changeit -keyclone -dest p2");647testFail("\n", "-keystore x.jks -storepass changeit -keyclone -dest p3 -alias noexist");648// no cert649testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert");650testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");651testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt");652testFail("", "-keystore x.jks -storepass changeit -keypass changeit -new newpass -keyclone -dest p0"); // new pass653remove("x.jks");654}655// keypasswd: exist, short, nonexist err, cert err, misc656void sqeKeypasswdTest() throws Exception {657remove("x.jks");658testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");659testOK("", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd -new newpass");660/*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit");661testOK("newpass\nnewpass\n", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd");662/*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit");663testOK("new\nnew\nnewpass\nnewpass\n", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd");664/*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit");665testOK("", "-keystore x.jks -storepass changeit -keypasswd -new newpass");666/*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit");667testOK("changeit\n", "-keystore x.jks -keypasswd -new newpass");668/*change back*/ testOK("", "-keystore x.jks -storepass changeit -keypass newpass -keypasswd -new changeit");669testFail("", "-keystore x.jks -storepass badpass -keypass changeit -keypasswd -new newpass");670testFail("", "-keystore x.jks -storepass changeit -keypass bad -keypasswd -new newpass");671// no cert672testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert");673testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");674testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt");675testFail("", "-keystore x.jks -storepass changeit -keypass changeit -keypasswd -new newpass");676// diff pass677testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");678testOK("", "-keystore x.jks -storepass changeit -keypass keypass -genkeypair -dname CN=olala");679testFail("", "-keystore x.jks -storepass changeit -keypasswd -new newpass");680testOK("keypass\n", "-keystore x.jks -storepass changeit -keypasswd -new newpass");681// i hate those misc test682remove("x.jks");683}684// list: -f -alias, exist, nonexist err; otherwise, check all shows, -rfc shows more, and misc685void sqeListTest() throws Exception {686remove("x.jks");687testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");688testOK("", "-keystore x.jks -storepass changeit -list");689testOK("", "-keystore x.jks -storepass changeit -list -alias mykey");690testFail("", "-keystore x.jks -storepass changeit -list -alias notexist");691testFail("", "-keystore x.jks -storepass badpass -list -alias mykey");692testOK("", "-keystore x.jks -storepass changeit -keypass badpass -list -alias mykey"); // keypass ignore693testOK("\n", "-keystore x.jks -list");694assertTrue(err.indexOf("WARNING") != -1, "no storepass");695testOK("changeit\n", "-keystore x.jks -list");696assertTrue(err.indexOf("WARNING") == -1, "has storepass");697testFail("badpass\n", "-keystore x.jks -list");698// misc699testFail("", "-keystore aa\\bb//cc -storepass changeit -list");700testFail("", "-keystore nonexisting -storepass changeit -list");701testFail("", "-keystore badkeystore -storepass changeit -list");702remove("x.jks");703}704// selfcert: exist, non-exist err, cert err, sig..., dname, wrong keypass, misc705void sqeSelfCertTest() throws Exception {706remove("x.jks");707testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");708testOK("", "-keystore x.jks -storepass changeit -selfcert");709testOK("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert");710testFail("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert -alias nonexisting"); // not exist711testOK("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert -dname CN=NewName");712testFail("", "-keystore x.jks -storepass changeit -keypass changeit -selfcert -sigalg MD5withRSA"); // sig not compatible713testFail("", "-keystore x.jks -storepass wrong -keypass changeit -selfcert"); // bad pass714testFail("", "-keystore x.jks -storepass changeit -keypass wrong -selfcert"); // bad pass715//misc716testFail("", "-keystore nonexist -storepass changeit -keypass changeit -selfcert");717testFail("", "-keystore aa//dd\\gg -storepass changeit -keypass changeit -selfcert");718// diff pass719remove("x.jks");720testOK("", "-keystore x.jks -storepass changeit -keypass keypass -genkeypair -dname CN=olala");721testFail("", "-keystore x.jks -storepass changeit -selfcert");722testOK("keypass\n", "-keystore x.jks -storepass changeit -selfcert");723724testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert");725testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");726testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt");727testFail("", "-keystore x.jks -storepass changeit -selfcert"); // certentry cannot do selfcert728remove("x.jks");729}730// storepass: bad old, short new, misc731void sqeStorepassTest() throws Exception {732remove("x.jks");733testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");734testOK("", "-storepasswd -keystore x.jks -storepass changeit -new newstore"); // all in arg735/* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit");736testOK("changeit\nnewstore\nnewstore\n", "-storepasswd -keystore x.jks"); // all not in arg, new twice737/* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit");738testOK("changeit\n", "-storepasswd -keystore x.jks -new newstore"); // new in arg739/* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit");740testOK("newstore\nnewstore\n", "-storepasswd -keystore x.jks -storepass changeit"); // old in arg741/* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit");742testOK("new\nnew\nnewstore\nnewstore\n", "-storepasswd -keystore x.jks -storepass changeit"); // old in arg743/* Change back */ testOK("", "-storepasswd -keystore x.jks -storepass newstore -new changeit");744testFail("", "-storepasswd -keystore x.jks -storepass badold -new newstore"); // bad old745testFail("", "-storepasswd -keystore x.jks -storepass changeit -new new"); // short new746// misc747testFail("", "-storepasswd -keystore nonexist -storepass changeit -new newstore"); // non exist748testFail("", "-storepasswd -keystore badkeystore -storepass changeit -new newstore"); // bad file749testFail("", "-storepasswd -keystore aa\\bb//cc//dd -storepass changeit -new newstore"); // bad file750remove("x.jks");751}752753void sqeGenkeyTest() throws Exception {754755remove("x.jks");756testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");757testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");758testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias newentry");759testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias newentry");760testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg DSA -alias n1");761testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -alias n2");762testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg NoSuchAlg -alias n3");763testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 56 -alias n4");764testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 999 -alias n5");765testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 512 -alias n6");766testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 1024 -alias n7");767testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -sigalg NoSuchAlg -alias n8");768testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg MD2withRSA -alias n9");769testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg MD5withRSA -alias n10");770testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg SHA1withRSA -alias n11");771testFail("", "-keystore aa\\bb//cc\\dd -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA -sigalg NoSuchAlg -alias n12");772testFail("", "-keystore badkeystore -storepass changeit -keypass changeit -genkeypair -dname CN=olala -alias n14");773testFail("", "-keystore x.jks -storepass badpass -keypass changeit -genkeypair -dname CN=olala -alias n16");774testFail("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CNN=olala -alias n17");775remove("x.jks");776}777778void sqeExportTest() throws Exception {779remove("x.jks");780testFail("", "-keystore x.jks -storepass changeit -export -file mykey.cert -alias mykey"); // nonexist781testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");782testOK("", "-keystore x.jks -storepass changeit -export -file mykey.cert -alias mykey");783testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");784testOK("", "-keystore x.jks -storepass changeit -import -file mykey.cert -noprompt -alias c1");785testOK("", "-keystore x.jks -storepass changeit -export -file mykey.cert2 -alias c1");786testFail("", "-keystore aa\\bb//cc\\dd -storepass changeit -export -file mykey.cert2 -alias c1");787testFail("", "-keystore nonexistkeystore -storepass changeit -export -file mykey.cert2 -alias c1");788testFail("", "-keystore badkeystore -storepass changeit -export -file mykey.cert2 -alias c1");789testFail("", "-keystore x.jks -storepass badpass -export -file mykey.cert2 -alias c1");790remove("mykey.cert");791remove("mykey.cert2");792remove("x.jks");793}794795void sqeDeleteTest() throws Exception {796remove("x.jks");797testFail("", "-keystore x.jks -storepass changeit -delete -alias mykey"); // nonexist798testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");799testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");800testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");801testFail("", "-keystore aa\\bb//cc\\dd -storepass changeit -delete -alias mykey"); // keystore name illegal802testFail("", "-keystore nonexistkeystore -storepass changeit -delete -alias mykey"); // keystore not exist803testFail("", "-keystore badkeystore -storepass changeit -delete -alias mykey"); // keystore invalid804testFail("", "-keystore x.jks -storepass xxxxxxxx -delete -alias mykey"); // wrong pass805remove("x.jks");806}807808void sqeCsrTest() throws Exception {809remove("x.jks");810remove("x.jks.p1.cert");811remove("csr1");812// PrivateKeyEntry can do certreq813testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keysize 1024");814testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -alias mykey");815testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1");816testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg SHA1withDSA");817testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg MD5withRSA"); // unmatched sigalg818// misc test819testFail("", "-keystore x.jks -storepass badstorepass -certreq -file csr1"); // bad storepass820testOK("changeit\n", "-keystore x.jks -certreq -file csr1"); // storepass from terminal821testFail("\n", "-keystore x.jks -certreq -file csr1"); // must provide storepass822testFail("", "-keystore x.jks -storepass changeit -keypass badkeypass -certreq -file csr1"); // bad keypass823testFail("", "-keystore x.jks -storepass changeit -certreq -file aa\\bb//cc\\dd"); // bad filepath824testFail("", "-keystore noexistks -storepass changeit -certreq -file csr1"); // non-existing keystore825// Try the RSA private key826testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");827testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala -keyalg RSA");828testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -alias mykey");829testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1");830testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg SHA1withDSA"); // unmatched sigalg831testOK("", "-keystore x.jks -storepass changeit -certreq -file csr1 -sigalg MD5withRSA");832// TrustedCertificateEntry cannot do certreq833testOK("", "-keystore x.jks -storepass changeit -exportcert -file x.jks.p1.cert");834testOK("", "-keystore x.jks -storepass changeit -delete -alias mykey");835testOK("", "-keystore x.jks -storepass changeit -importcert -file x.jks.p1.cert -noprompt");836testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1 -alias mykey");837testFail("", "-keystore x.jks -storepass changeit -certreq -file csr1");838remove("x.jks");839remove("x.jks.p1.cert");840remove("csr1");841}842843void sqePrintcertTest() throws Exception {844remove("x.jks");845remove("mykey.cert");846testOK("", "-keystore x.jks -storepass changeit -keypass changeit -genkeypair -dname CN=olala");847testOK("", "-keystore x.jks -storepass changeit -export -file mykey.cert -alias mykey");848testFail("", "-printcert -file badkeystore");849testFail("", "-printcert -file a/b/c/d");850testOK("", "-printcert -file mykey.cert");851FileInputStream fin = new FileInputStream("mykey.cert");852testOK(fin, "-printcert");853fin.close();854remove("x.jks");855remove("mykey.cert");856}857858// 8074935: jdk8 keytool doesn't validate pem files for RFC 1421 correctness859static void checkPem(String file) throws Exception {860boolean maybeLast = false;861for (String s: Files.readAllLines(Paths.get(file))) {862if (s.isEmpty()) continue;863if (s.startsWith("---")) continue;864if (maybeLast) {865throw new Exception("Last line already seen");866}867if (s.length() > 64) {868throw new Exception(s);869}870if (s.length() < 64) {871maybeLast = true;872}873}874}875876void v3extTest(String keyAlg) throws Exception {877KeyStore ks;878remove("x.jks");879String simple = "-keystore x.jks -storepass changeit -keypass changeit -noprompt -keyalg " + keyAlg + " ";880String pre = simple + "-genkeypair -dname CN=Olala -alias ";881882// Version and SKID883testOK("", pre + "o1");884885ks = loadStore("x.jks", "changeit", "JKS");886assertTrue(((X509Certificate)ks.getCertificate("o1")).getVersion() == 3);887assertTrue(((X509CertImpl)ks.getCertificate("o1")).getSubjectKeyIdentifierExtension() != null);888889// BC890testOK("", pre + "b1 -ext BC:critical");891testOK("", pre + "b2 -ext BC");892testOK("", pre + "b3 -ext bc");893testOK("", pre + "b4 -ext BasicConstraints");894testOK("", pre + "b5 -ext basicconstraints");895testOK("", pre + "b6 -ext BC=ca:true,pathlen:12");896testOK("", pre + "b7 -ext BC=ca:false");897testOK("", pre + "b8 -ext BC:critical=ca:false");898testOK("", pre + "b9 -ext BC=12");899900ks = loadStore("x.jks", "changeit", "JKS");901assertTrue(((X509CertImpl)ks.getCertificate("b1")).getBasicConstraintsExtension().isCritical());902assertTrue(!((X509CertImpl)ks.getCertificate("b2")).getBasicConstraintsExtension().isCritical());903assertTrue(((X509CertImpl)ks.getCertificate("b8")).getBasicConstraintsExtension().isCritical());904assertTrue(((X509Certificate)ks.getCertificate("b1")).getBasicConstraints() == Integer.MAX_VALUE);905assertTrue(((X509Certificate)ks.getCertificate("b2")).getBasicConstraints() == Integer.MAX_VALUE);906assertTrue(((X509Certificate)ks.getCertificate("b3")).getBasicConstraints() == Integer.MAX_VALUE);907assertTrue(((X509Certificate)ks.getCertificate("b4")).getBasicConstraints() == Integer.MAX_VALUE);908assertTrue(((X509Certificate)ks.getCertificate("b5")).getBasicConstraints() == Integer.MAX_VALUE);909assertTrue(((X509Certificate)ks.getCertificate("b6")).getBasicConstraints() == 12);910assertTrue(((X509Certificate)ks.getCertificate("b7")).getBasicConstraints() == -1);911assertTrue(((X509Certificate)ks.getCertificate("b9")).getBasicConstraints() == 12);912913// KU914testOK("", pre + "ku1 -ext KeyUsage:critical=digitalsignature");915testOK("", pre + "ku2 -ext KU=digitalSignature");916testOK("", pre + "ku3 -ext KU=ds");917testOK("", pre + "ku4 -ext KU=dig");918testFail("", pre + "ku5 -ext KU=d"); // ambigous value919testFail("", pre + "ku6 -ext KU=cs"); // cRLSign cannot be cs920testOK("", pre + "ku11 -ext KU=nr");921testFail("", pre + "ku12 -ext KU=ke"); // ke also means keyAgreement922testOK("", pre + "ku12 -ext KU=keyE");923testFail("", pre + "ku13 -ext KU=de"); // de also means decipherOnly924testOK("", pre + "ku13 -ext KU=dataE");925testOK("", pre + "ku14 -ext KU=ka");926testOK("", pre + "ku15 -ext KU=kcs");927testOK("", pre + "ku16 -ext KU=crls");928testOK("", pre + "ku17 -ext KU=eo");929testOK("", pre + "ku18 -ext KU=do");930testOK("", pre + "ku19 -ext KU=cc");931932testOK("", pre + "ku017 -ext KU=ds,cc,eo");933testOK("", pre + "ku135 -ext KU=nr,dataEncipherment,keyCertSign");934testOK("", pre + "ku246 -ext KU=keyEnc,cRL,keyA");935testOK("", pre + "ku1234 -ext KU=ka,da,keyE,nonR");936937ks = loadStore("x.jks", "changeit", "JKS");938class CheckKU {939void check(KeyStore ks, String alias, int... pos) throws Exception {940System.err.print("x");941boolean[] bs = ((X509Certificate)ks.getCertificate(alias)).getKeyUsage();942bs = Arrays.copyOf(bs, 9);943for (int i=0; i<bs.length; i++) {944boolean found = false;945for (int p: pos) {946if (p == i) found = true;947}948if (!found ^ bs[i]) {949// OK950} else {951throw new RuntimeException("KU not match at " + i +952": " + found + " vs " + bs[i]);953}954}955}956}957CheckKU c = new CheckKU();958assertTrue(((X509CertImpl)ks.getCertificate("ku1")).getExtension(PKIXExtensions.KeyUsage_Id).isCritical());959assertTrue(!((X509CertImpl)ks.getCertificate("ku2")).getExtension(PKIXExtensions.KeyUsage_Id).isCritical());960c.check(ks, "ku1", 0);961c.check(ks, "ku2", 0);962c.check(ks, "ku3", 0);963c.check(ks, "ku4", 0);964c.check(ks, "ku11", 1);965c.check(ks, "ku12", 2);966c.check(ks, "ku13", 3);967c.check(ks, "ku14", 4);968c.check(ks, "ku15", 5);969c.check(ks, "ku16", 6);970c.check(ks, "ku17", 7);971c.check(ks, "ku18", 8);972c.check(ks, "ku19", 1);973c.check(ks, "ku11", 1);974c.check(ks, "ku11", 1);975c.check(ks, "ku11", 1);976c.check(ks, "ku017", 0, 1, 7);977c.check(ks, "ku135", 1, 3, 5);978c.check(ks, "ku246", 6, 2, 4);979c.check(ks, "ku1234", 1, 2, 3, 4);980981// EKU982testOK("", pre + "eku1 -ext EKU:critical=sa");983testOK("", pre + "eku2 -ext ExtendedKeyUsage=ca");984testOK("", pre + "eku3 -ext EKU=cs");985testOK("", pre + "eku4 -ext EKU=ep");986testOK("", pre + "eku8 -ext EKU=ts");987testFail("", pre + "eku9 -ext EKU=os");988testOK("", pre + "eku9 -ext EKU=ocsps");989testOK("", pre + "eku10 -ext EKU=any");990testOK("", pre + "eku11 -ext EKU=1.2.3.4,1.3.5.7,ep");991testFail("", pre + "eku12 -ext EKU=c");992testFail("", pre + "eku12 -ext EKU=nothing");993994ks = loadStore("x.jks", "changeit", "JKS");995class CheckEKU {996void check(KeyStore ks, String alias, String... pos) throws Exception {997System.err.print("x");998List<String> bs = ((X509Certificate)ks.getCertificate(alias)).getExtendedKeyUsage();999int found = 0;1000for (String p: pos) {1001if (bs.contains(p)) {1002found++;1003} else {1004throw new RuntimeException("EKU: not included " + p);1005}1006}1007if (found != bs.size()) {1008throw new RuntimeException("EKU: more items than expected");1009}1010}1011}1012CheckEKU cx = new CheckEKU();1013assertTrue(((X509CertImpl)ks.getCertificate("eku1")).getExtension(PKIXExtensions.ExtendedKeyUsage_Id).isCritical());1014assertTrue(!((X509CertImpl)ks.getCertificate("eku2")).getExtension(PKIXExtensions.ExtendedKeyUsage_Id).isCritical());1015cx.check(ks, "eku1", "1.3.6.1.5.5.7.3.1");1016cx.check(ks, "eku2", "1.3.6.1.5.5.7.3.2");1017cx.check(ks, "eku3", "1.3.6.1.5.5.7.3.3");1018cx.check(ks, "eku4", "1.3.6.1.5.5.7.3.4");1019cx.check(ks, "eku8", "1.3.6.1.5.5.7.3.8");1020cx.check(ks, "eku9", "1.3.6.1.5.5.7.3.9");1021cx.check(ks, "eku10", "2.5.29.37.0");1022cx.check(ks, "eku11", "1.3.6.1.5.5.7.3.4", "1.2.3.4", "1.3.5.7");10231024// SAN1025testOK("", pre+"san1 -ext san:critical=email:[email protected]");1026testOK("", pre+"san2 -ext san=uri:http://me.org");1027testOK("", pre+"san3 -ext san=dns:me.org");1028testOK("", pre+"san4 -ext san=ip:192.168.0.1");1029testOK("", pre+"san5 -ext san=oid:1.2.3.4");1030testOK("", pre+"san6 -ext san=dns:1abc.com"); //begin with digit1031testOK("", pre+"san235 -ext san=uri:http://me.org,dns:me.org,oid:1.2.3.4");10321033ks = loadStore("x.jks", "changeit", "JKS");1034class CheckSAN {1035// Please sort items with name type1036void check(KeyStore ks, String alias, int type, Object... items) throws Exception {1037int pos = 0;1038System.err.print("x");1039Object[] names = null;1040if (type == 0) names = ((X509Certificate)ks.getCertificate(alias)).getSubjectAlternativeNames().toArray();1041else names = ((X509Certificate)ks.getCertificate(alias)).getIssuerAlternativeNames().toArray();1042Arrays.sort(names, new Comparator() {1043public int compare(Object o1, Object o2) {1044int i1 = (Integer)((List)o1).get(0);1045int i2 = (Integer)((List)o2).get(0);1046return i1 - i2;1047}1048});1049for (Object o: names) {1050List l = (List)o;1051for (Object o2: l) {1052if (!items[pos++].equals(o2)) {1053throw new RuntimeException("Not equals at " + pos1054+ ": " + items[pos-1] + " vs " + o2);1055}1056}1057}1058if (pos != items.length) {1059throw new RuntimeException("Extra items, pos is " + pos);1060}1061}1062}1063CheckSAN csan = new CheckSAN();1064assertTrue(((X509CertImpl)ks.getCertificate("san1")).getSubjectAlternativeNameExtension().isCritical());1065assertTrue(!((X509CertImpl)ks.getCertificate("san2")).getSubjectAlternativeNameExtension().isCritical());1066csan.check(ks, "san1", 0, 1, "[email protected]");1067csan.check(ks, "san2", 0, 6, "http://me.org");1068csan.check(ks, "san3", 0, 2, "me.org");1069csan.check(ks, "san4", 0, 7, "192.168.0.1");1070csan.check(ks, "san5", 0, 8, "1.2.3.4");1071csan.check(ks, "san235", 0, 2, "me.org", 6, "http://me.org", 8, "1.2.3.4");10721073// IAN1074testOK("", pre+"ian1 -ext ian:critical=email:[email protected]");1075testOK("", pre+"ian2 -ext ian=uri:http://me.org");1076testOK("", pre+"ian3 -ext ian=dns:me.org");1077testOK("", pre+"ian4 -ext ian=ip:192.168.0.1");1078testOK("", pre+"ian5 -ext ian=oid:1.2.3.4");1079testOK("", pre+"ian235 -ext ian=uri:http://me.org,dns:me.org,oid:1.2.3.4");10801081ks = loadStore("x.jks", "changeit", "JKS");1082assertTrue(((X509CertImpl)ks.getCertificate("ian1")).getIssuerAlternativeNameExtension().isCritical());1083assertTrue(!((X509CertImpl)ks.getCertificate("ian2")).getIssuerAlternativeNameExtension().isCritical());1084csan.check(ks, "ian1", 1, 1, "[email protected]");1085csan.check(ks, "ian2", 1, 6, "http://me.org");1086csan.check(ks, "ian3", 1, 2, "me.org");1087csan.check(ks, "ian4", 1, 7, "192.168.0.1");1088csan.check(ks, "ian5", 1, 8, "1.2.3.4");1089csan.check(ks, "ian235", 1, 2, "me.org", 6, "http://me.org", 8, "1.2.3.4");10901091// SIA1092testOK("", pre+"sia1 -ext sia=care:uri:ldap://ca.com/cn=CA");1093testOK("", pre+"sia2 -ext sia=ts:email:[email protected]");1094testFail("SIA never critical", pre+"sia3 -ext sia:critical=ts:email:[email protected]");10951096ks = loadStore("x.jks", "changeit", "JKS");1097class CheckSia {1098void check(KeyStore ks, String alias, int type, Object... items) throws Exception {1099int pos = 0;1100System.err.print("x");1101AccessDescription[] ads = null;1102if (type == 0) {1103SubjectInfoAccessExtension siae = (SubjectInfoAccessExtension)((X509CertImpl)ks.getCertificate(alias)).getExtension(PKIXExtensions.SubjectInfoAccess_Id);1104ads = siae.getAccessDescriptions().toArray(new AccessDescription[0]);1105} else {1106AuthorityInfoAccessExtension aiae = (AuthorityInfoAccessExtension)((X509CertImpl)ks.getCertificate(alias)).getExtension(PKIXExtensions.AuthInfoAccess_Id);1107ads = aiae.getAccessDescriptions().toArray(new AccessDescription[0]);1108}1109Arrays.sort(ads, new Comparator<AccessDescription>() {1110@Override1111public int compare(AccessDescription o1, AccessDescription o2) {1112return o1.getAccessMethod().toString().compareTo(o2.getAccessMethod().toString());1113}1114});1115for (AccessDescription ad: ads) {1116if (!ad.getAccessMethod().equals(items[pos++]) ||1117!new Integer(ad.getAccessLocation().getType()).equals(items[pos++])) {1118throw new RuntimeException("Not same type at " + pos);1119}1120String name = null;1121switch (ad.getAccessLocation().getType()) {1122case 1:1123name = ((RFC822Name)ad.getAccessLocation().getName()).getName();1124break;1125case 6:1126name = ((URIName)ad.getAccessLocation().getName()).getURI().toString();1127break;1128default:1129throw new RuntimeException("Not implemented: " + ad);1130}1131if (!name.equals(items[pos++])) {1132throw new Exception("Name not same for " + ad + " at pos " + pos);1133}1134}1135}1136}1137CheckSia csia = new CheckSia();1138assertTrue(!((X509CertImpl)ks.getCertificate("sia1")).getExtension(PKIXExtensions.SubjectInfoAccess_Id).isCritical());1139csia.check(ks, "sia1", 0, AccessDescription.Ad_CAREPOSITORY_Id, 6, "ldap://ca.com/cn=CA");1140csia.check(ks, "sia2", 0, AccessDescription.Ad_TIMESTAMPING_Id, 1, "[email protected]");11411142// AIA1143testOK("", pre+"aia1 -ext aia=cai:uri:ldap://ca.com/cn=CA");1144testOK("", pre+"aia2 -ext aia=ocsp:email:[email protected]");1145testFail("AIA never critical", pre+"aia3 -ext aia:critical=ts:email:[email protected]");11461147ks = loadStore("x.jks", "changeit", "JKS");1148assertTrue(!((X509CertImpl)ks.getCertificate("aia1")).getExtension(PKIXExtensions.AuthInfoAccess_Id).isCritical());1149csia.check(ks, "aia1", 1, AccessDescription.Ad_CAISSUERS_Id, 6, "ldap://ca.com/cn=CA");1150csia.check(ks, "aia2", 1, AccessDescription.Ad_OCSP_Id, 1, "[email protected]");11511152// OID1153testOK("", pre+"oid1 -ext 1.2.3:critical=0102");1154testOK("", pre+"oid2 -ext 1.2.3");1155testOK("", pre+"oid12 -ext 1.2.3 -ext 1.2.4=01:02:03");11561157ks = loadStore("x.jks", "changeit", "JKS");1158class CheckOid {1159void check(KeyStore ks, String alias, String oid, byte[] value) throws Exception {1160int pos = 0;1161System.err.print("x");1162Extension ex = ((X509CertImpl)ks.getCertificate(alias)).getExtension(new ObjectIdentifier(oid));1163if (!Arrays.equals(value, ex.getValue())) {1164throw new RuntimeException("Not same content in " + alias + " for " + oid);1165}1166}1167}1168CheckOid coid = new CheckOid();1169assertTrue(((X509CertImpl)ks.getCertificate("oid1")).getExtension(new ObjectIdentifier("1.2.3")).isCritical());1170assertTrue(!((X509CertImpl)ks.getCertificate("oid2")).getExtension(new ObjectIdentifier("1.2.3")).isCritical());1171coid.check(ks, "oid1", "1.2.3", new byte[]{1,2});1172coid.check(ks, "oid2", "1.2.3", new byte[]{});1173coid.check(ks, "oid12", "1.2.3", new byte[]{});1174coid.check(ks, "oid12", "1.2.4", new byte[]{1,2,3});11751176// honored1177testOK("", pre+"ca");1178testOK("", pre+"a");1179// request: BC,KU,1.2.3,1.2.4,1.2.51180testOK("", simple+"-alias a -certreq " +1181"-ext BC=1 -ext KU=crl " +1182"-ext 1.2.3=01 -ext 1.2.4:critical=0102 -ext 1.2.5=010203 " +1183"-rfc -file test.req");1184// printcertreq1185testOK("", "-printcertreq -file test.req");1186checkPem("test.req");1187// issue: deny KU, change criticality of 1.2.3 and 1.2.4,1188// change content of BC, add 2.3.41189testOK("", simple+"-gencert -alias ca -infile test.req -ext " +1190"honored=all,-KU,1.2.3:critical,1.2.4:non-critical " +1191"-ext BC=2 -ext 2.3.4=01020304 " +1192"-debug -rfc -outfile test.cert");1193checkPem("test.cert");1194testOK("", simple+"-importcert -file test.cert -alias a");1195ks = loadStore("x.jks", "changeit", "JKS");1196X509CertImpl a = (X509CertImpl)ks.getCertificate("a");1197assertTrue(a.getAuthorityKeyIdentifierExtension() != null);1198assertTrue(a.getSubjectKeyIdentifierExtension() != null);1199assertTrue(a.getKeyUsage() == null);1200assertTrue(a.getExtension(new ObjectIdentifier("1.2.3")).isCritical());1201assertTrue(!a.getExtension(new ObjectIdentifier("1.2.4")).isCritical());1202assertTrue(!a.getExtension(new ObjectIdentifier("1.2.5")).isCritical());1203assertTrue(a.getExtensionValue("1.2.3").length == 3);1204assertTrue(a.getExtensionValue("1.2.4").length == 4);1205assertTrue(a.getExtensionValue("1.2.5").length == 5);1206assertTrue(a.getBasicConstraints() == 2);1207assertTrue(!a.getExtension(new ObjectIdentifier("2.3.4")).isCritical());1208assertTrue(a.getExtensionValue("2.3.4").length == 6);12091210remove("x.jks");1211remove("test.req");1212remove("test.cert");1213}12141215void i18nTest() throws Exception {1216// 1. keytool -help1217remove("x.jks");1218testOK("", "-help");12191220// 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.1221testOK("a\npassword\npassword\nMe\nHere\nNow\nPlace\nPlace\nUS\nyes\n\n", "-genkey -v -keysize 512 -keystore x.jks");1222// 3. keytool -list -v -storepass password1223testOK("", "-list -v -storepass password -keystore x.jks");1224// 4. keytool -list -v Type "a" for the keystore password. Check error (wrong keystore password).1225testFail("a\n", "-list -v -keystore x.jks");1226assertTrue(ex.indexOf("password was incorrect") != -1);1227// 5. keytool -genkey -v -keysize 512 Enter "password" as the password. Check error (alias 'mykey' already exists).1228testFail("password\n", "-genkey -v -keysize 512 -keystore x.jks");1229assertTrue(ex.indexOf("alias <mykey> already exists") != -1);1230// 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.1231testOK("\n\n\n\n\n\nyes\n\n", "-genkey -v -keysize 512 -alias mykey2 -storepass password -keystore x.jks");1232// 7. keytool -list -v Type 'password' for the store password.1233testOK("password\n", "-list -v -keystore x.jks");1234// 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).1235testFail("a\naaaaaa\nbbbbbb\na\n", "-keypasswd -v -alias mykey2 -storepass password -keystore x.jks");1236assertTrue(ex.indexOf("Too many failures - try later") != -1);1237// 9. keytool -keypasswd -v -alias mykey2 -storepass password Type "aaaaaa" for the new key password. Type "aaaaaa" when re-entering the new key password.1238testOK("aaaaaa\naaaaaa\n", "-keypasswd -v -alias mykey2 -storepass password -keystore x.jks");1239// 10. keytool -selfcert -v -alias mykey -storepass password1240testOK("", "-selfcert -v -alias mykey -storepass password -keystore x.jks");1241// 11. keytool -list -v -storepass password1242testOK("", "-list -v -storepass password -keystore x.jks");1243// 12. keytool -export -v -alias mykey -file cert -storepass password1244remove("cert");1245testOK("", "-export -v -alias mykey -file cert -storepass password -keystore x.jks");1246// 13. keytool -import -v -file cert -storepass password Check error (Certificate reply and cert are the same)1247testFail("", "-import -v -file cert -storepass password -keystore x.jks");1248assertTrue(ex.indexOf("Certificate reply and certificate in keystore are identical") != -1);1249// 14. keytool -printcert -file cert1250testOK("", "-printcert -file cert -keystore x.jks");1251remove("cert");1252// 15. keytool -list -storepass password -provider sun.security.provider.Sun1253testOK("", "-list -storepass password -provider sun.security.provider.Sun -keystore x.jks");12541255//Error tests12561257// 1. keytool -storepasswd -storepass password -new abc Check error (password too short)1258testFail("", "-storepasswd -storepass password -new abc");1259assertTrue(ex.indexOf("New password must be at least 6 characters") != -1);1260// Changed, no NONE needed now1261// 2. keytool -list -storetype PKCS11 Check error (-keystore must be NONE)1262//testFail("", "-list -storetype PKCS11");1263//assertTrue(err.indexOf("keystore must be NONE") != -1);1264// 3. keytool -storepasswd -storetype PKCS11 -keystore NONE Check error (unsupported operation)1265testFail("", "-storepasswd -storetype PKCS11 -keystore NONE");1266assertTrue(ex.indexOf("UnsupportedOperationException") != -1);1267// 4. keytool -keypasswd -storetype PKCS11 -keystore NONE Check error (unsupported operation)1268testFail("", "-keypasswd -storetype PKCS11 -keystore NONE");1269assertTrue(ex.indexOf("UnsupportedOperationException") != -1);1270// 5. keytool -list -protected -storepass password Check error (password can not be specified with -protected)1271testFail("", "-list -protected -storepass password -keystore x.jks");1272assertTrue(ex.indexOf("if -protected is specified, then") != -1);1273// 6. keytool -keypasswd -protected -keypass password Check error (password can not be specified with -protected)1274testFail("", "-keypasswd -protected -keypass password -keystore x.jks");1275assertTrue(ex.indexOf("if -protected is specified, then") != -1);1276// 7. keytool -keypasswd -protected -new password Check error (password can not be specified with -protected)1277testFail("", "-keypasswd -protected -new password -keystore x.jks");1278assertTrue(ex.indexOf("if -protected is specified, then") != -1);1279remove("x.jks");1280}12811282void i18nPKCS11Test() throws Exception {1283//PKCS#11 tests12841285// 1. sccs edit cert8.db key3.db1286//Runtime.getRuntime().exec("/usr/ccs/bin/sccs edit cert8.db key3.db");1287testOK("", p11Arg + "-storepass test12 -genkey -alias genkey -dname cn=genkey -keysize 512 -keyalg rsa");1288testOK("", p11Arg + "-storepass test12 -list");1289testOK("", p11Arg + "-storepass test12 -list -alias genkey");1290testOK("", p11Arg + "-storepass test12 -certreq -alias genkey -file genkey.certreq");1291testOK("", p11Arg + "-storepass test12 -export -alias genkey -file genkey.cert");1292testOK("", "-printcert -file genkey.cert");1293testOK("", p11Arg + "-storepass test12 -selfcert -alias genkey -dname cn=selfCert");1294testOK("", p11Arg + "-storepass test12 -list -alias genkey -v");1295assertTrue(out.indexOf("Owner: CN=selfCert") != -1);1296//(check that cert subject DN is [cn=selfCert])1297testOK("", p11Arg + "-storepass test12 -delete -alias genkey");1298testOK("", p11Arg + "-storepass test12 -list");1299assertTrue(out.indexOf("Your keystore contains 0 entries") != -1);1300//(check for empty database listing)1301//Runtime.getRuntime().exec("/usr/ccs/bin/sccs unedit cert8.db key3.db");1302remove("genkey.cert");1303remove("genkey.certreq");1304// 12. sccs unedit cert8.db key3.db1305}13061307// tesing new option -srcProviderName1308void sszzTest() throws Exception {1309testAnyway("", NSS_P11_ARG+"-delete -alias nss -storepass test12");1310testAnyway("", NZZ_P11_ARG+"-delete -alias nss -storepass test12");1311testOK("", NSS_P11_ARG+"-genkeypair -dname CN=NSS -alias nss -storepass test12");1312testOK("", NSS_SRC_P11_ARG + NZZ_P11_ARG +1313"-importkeystore -srcstorepass test12 -deststorepass test12");1314testAnyway("", NSS_P11_ARG+"-delete -alias nss -storepass test12");1315testAnyway("", NZZ_P11_ARG+"-delete -alias nss -storepass test12");1316}13171318public static void main(String[] args) throws Exception {1319Locale reservedLocale = Locale.getDefault();1320try {1321// first test if HumanInputStream really acts like a human being1322HumanInputStream.test();1323KeyToolTest t = new KeyToolTest();13241325if (System.getProperty("file") != null) {1326t.sqeTest();1327t.testAll();1328t.i18nTest();1329t.v3extTest("RSA");1330t.v3extTest("DSA");1331boolean testEC = true;1332try {1333KeyPairGenerator.getInstance("EC");1334} catch (NoSuchAlgorithmException nae) {1335testEC = false;1336}1337if (testEC) t.v3extTest("EC");1338}13391340if (System.getProperty("nss") != null) {1341t.srcP11Arg = NSS_SRC_P11_ARG;1342t.p11Arg = NSS_P11_ARG;13431344t.testPKCS11();13451346// FAIL:1347// 1. we still don't have srcprovidername yet1348// 2. cannot store privatekey into NSS keystore1349// java.security.KeyStoreException: sun.security.pkcs11.wrapper.PKCS11Exception: CKR_TEMPLATE_INCOMPLETE.1350//t.testPKCS11ImportKeyStore();13511352t.i18nPKCS11Test();1353//FAIL: currently PKCS11-NSS does not support 2 NSS KeyStores to be loaded at the same time1354//t.sszzTest();1355}13561357if (System.getProperty("solaris") != null) {1358// For Solaris Cryptography Framework1359t.srcP11Arg = SUN_SRC_P11_ARG;1360t.p11Arg = SUN_P11_ARG;1361t.testPKCS11();1362t.testPKCS11ImportKeyStore();1363t.i18nPKCS11Test();1364}13651366System.out.println("Test pass!!!");1367} finally {1368// restore the reserved locale1369Locale.setDefault(reservedLocale);1370}1371}1372}13731374class TestException extends Exception {1375public TestException(String e) {1376super(e);1377}1378}13791380/**1381* HumanInputStream tries to act like a human sitting in front of a computer1382* terminal typing on the keyboard while the keytool program is running.1383*1384* keytool has called InputStream.read() and BufferedReader.readLine() in1385* various places. a call to B.readLine() will try to buffer as much input as1386* possible. Thus, a trivial InputStream will find it impossible to feed1387* anything to I.read() after a B.readLine() call.1388*1389* This is why i create HumanInputStream, which will only send a single line1390* to B.readLine(), no more, no less, and the next I.read() can have a chance1391* to read the exact character right after "\n".1392*1393* I don't know why HumanInputStream works.1394*/1395class HumanInputStream extends InputStream {1396byte[] src;1397int pos;1398int length;1399boolean inLine;1400int stopIt;14011402public HumanInputStream(String input) {1403src = input.getBytes();1404pos = 0;1405length = src.length;1406stopIt = 0;1407inLine = false;1408}14091410// the trick: when called through read(byte[], int, int),1411// return -1 twice after "\n"14121413@Override public int read() throws IOException {1414int re;1415if(pos < length) {1416re = src[pos];1417if(inLine) {1418if(stopIt > 0) {1419stopIt--;1420re = -1;1421} else {1422if(re == '\n') {1423stopIt = 2;1424}1425pos++;1426}1427} else {1428pos++;1429}1430} else {1431re = -1;//throw new IOException("NO MORE TO READ");1432}1433//if (re < 32) System.err.printf("[%02d]", re);1434//else System.err.printf("[%c]", (char)re);1435return re;1436}1437@Override public int read(byte[] buffer, int offset, int len) {1438inLine = true;1439try {1440int re = super.read(buffer, offset, len);1441return re;1442} catch(Exception e) {1443throw new RuntimeException("HumanInputStream error");1444} finally {1445inLine = false;1446}1447}1448@Override public int available() {1449if(pos < length) return 1;1450return 0;1451}14521453// test part1454static void assertTrue(boolean bool) {1455if(!bool)1456throw new RuntimeException();1457}14581459public static void test() throws Exception {14601461class Tester {1462HumanInputStream is;1463BufferedReader reader;1464Tester(String s) {1465is = new HumanInputStream(s);1466reader = new BufferedReader(new InputStreamReader(is));1467}14681469// three kinds of test method1470// 1. read byte by byte from InputStream1471void testStreamReadOnce(int expection) throws Exception {1472assertTrue(is.read() == expection);1473}1474void testStreamReadMany(String expection) throws Exception {1475char[] keys = expection.toCharArray();1476for(int i=0; i<keys.length; i++) {1477assertTrue(is.read() == keys[i]);1478}1479}1480// 2. read a line with a newly created Reader1481void testReaderReadline(String expection) throws Exception {1482String s = new BufferedReader(new InputStreamReader(is)).readLine();1483if(s == null) assertTrue(expection == null);1484else assertTrue(s.equals(expection));1485}1486// 3. read a line with the old Reader1487void testReaderReadline2(String expection) throws Exception {1488String s = reader.readLine();1489if(s == null) assertTrue(expection == null);1490else assertTrue(s.equals(expection));1491}1492}14931494Tester test;14951496test = new Tester("111\n222\n\n444\n\n");1497test.testReaderReadline("111");1498test.testReaderReadline("222");1499test.testReaderReadline("");1500test.testReaderReadline("444");1501test.testReaderReadline("");1502test.testReaderReadline(null);15031504test = new Tester("111\n222\n\n444\n\n");1505test.testReaderReadline2("111");1506test.testReaderReadline2("222");1507test.testReaderReadline2("");1508test.testReaderReadline2("444");1509test.testReaderReadline2("");1510test.testReaderReadline2(null);15111512test = new Tester("111\n222\n\n444\n\n");1513test.testReaderReadline2("111");1514test.testReaderReadline("222");1515test.testReaderReadline2("");1516test.testReaderReadline2("444");1517test.testReaderReadline("");1518test.testReaderReadline2(null);15191520test = new Tester("1\n2");1521test.testStreamReadMany("1\n2");1522test.testStreamReadOnce(-1);15231524test = new Tester("12\n234");1525test.testStreamReadOnce('1');1526test.testReaderReadline("2");1527test.testStreamReadOnce('2');1528test.testReaderReadline2("34");1529test.testReaderReadline2(null);15301531test = new Tester("changeit\n");1532test.testStreamReadMany("changeit\n");1533test.testReaderReadline(null);15341535test = new Tester("changeit\nName\nCountry\nYes\n");1536test.testStreamReadMany("changeit\n");1537test.testReaderReadline("Name");1538test.testReaderReadline("Country");1539test.testReaderReadline("Yes");1540test.testReaderReadline(null);15411542test = new Tester("Me\nHere\n");1543test.testReaderReadline2("Me");1544test.testReaderReadline2("Here");1545}1546}154715481549