1/*
2 * Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24import java.io.PrintStream;
25import java.security.NoSuchAlgorithmException;
26import java.security.Provider;
27import java.security.Security;
28import javax.crypto.Cipher;
29import javax.crypto.NoSuchPaddingException;
30
31/**
32 * @test
33 * @bug 8041787
34 * @summary Verify that for PBEWithMD5AndDES cipher, only CBC mode and
35 * PKCS#5Padding is allowed
36 * @author Yun Ke
37 * @author Bill Situ
38 * @author Yu-Ching (Valerie) PENG
39 */
40public class TestCipherPBECons {
41
42    private static final String[] PBEAlgorithms = {"pbeWithMD5ANDdes",
43        "PBEWithMD5AndTripleDES"};
44    private static final String[] cipherModes = {"ECb", "cbC", "cFB", "Cfb32",
45        "OfB", "oFb64", "pCbC"};
46    private static final String[] cipherPaddings = {"Pkcs5Padding", "NoPaDDing"};
47
48    public static void main(String[] args) {
49        TestCipherPBECons test = new TestCipherPBECons();
50        Provider sunjce = Security.getProvider("SunJCE");
51
52        if (!test.runAll(sunjce, System.out)) {
53            throw new RuntimeException("One or more tests have failed....");
54        }
55    }
56
57    public boolean runAll(Provider p, PrintStream out) {
58        boolean finalResult = true;
59
60        for (String algorithm : PBEAlgorithms) {
61            for (String mode : cipherModes) {
62                for (String padding : cipherPaddings) {
63                    out.println("Running test with " + algorithm
64                            + "/" + mode + "/" + padding);
65                    try {
66                        if (!runTest(p, algorithm, mode, padding, out)) {
67                            finalResult = false;
68                            out.println("STATUS: Failed");
69                        } else {
70                            out.println("STATUS: Passed");
71                        }
72                    } catch (Exception ex) {
73                        finalResult = false;
74                        ex.printStackTrace(out);
75                        out.println("STATUS:Failed");
76                    }
77                }
78            }
79        }
80
81        return finalResult;
82    }
83
84    public boolean runTest(Provider p, String algo, String mo, String pad,
85            PrintStream out) throws Exception {
86        try {
87            // Initialization
88            Cipher ci = Cipher.getInstance(algo + "/" + mo + "/" + pad, p);
89
90            // No exception thrown, must be of the right mode and right
91            // padding scheme
92            return (mo.equalsIgnoreCase("CBC"))
93                    && (pad.equalsIgnoreCase("PKCS5Padding"));
94        } catch (NoSuchAlgorithmException ex) {
95            if (p.getName().compareTo("SunJCE") == 0) {
96                if (!(mo.equalsIgnoreCase("CBC")
97                        && pad.equalsIgnoreCase("PKCS5Padding"))) {
98                    out.println("NoSuchAlgorithmException is as expected");
99                    return true;
100                }
101            }
102
103            out.println("Caught exception: " + ex.getMessage());
104            throw ex;
105        } catch (NoSuchPaddingException ex) {
106            if (mo.equalsIgnoreCase("CBC")
107                    && pad.equalsIgnoreCase("NoPadding")) {
108                out.println("NoSuchPaddingException is as expected");
109                return true;
110            } else {
111                out.println("Caught unexpected exception: " + ex.getMessage());
112                return false;
113            }
114        }
115    }
116}
117