jdk/test/javax/net/ssl/SSLEngine/ExtendedKeyEngine.java
changeset 23052 241885315119
parent 5506 202f599c92aa
equal deleted inserted replaced
23051:501d8479f798 23052:241885315119
       
     1 /*
       
     2  * Copyright (c) 2004, 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 
       
    24 /*
       
    25  * @test
       
    26  * @bug 4981697
       
    27  * @summary Rework the X509KeyManager to avoid incompatibility issues
       
    28  * @author Brad R. Wetmore
       
    29  */
       
    30 
       
    31 import javax.net.ssl.*;
       
    32 import javax.net.ssl.SSLEngineResult.*;
       
    33 import java.io.*;
       
    34 import java.security.*;
       
    35 import java.nio.*;
       
    36 
       
    37 public class ExtendedKeyEngine {
       
    38 
       
    39     private static boolean debug = false;
       
    40 
       
    41     private SSLContext sslc;
       
    42     private SSLEngine ssle1;    // client
       
    43     private SSLEngine ssle2;    // server
       
    44 
       
    45     private static String pathToStores = "../etc";
       
    46     private static String keyStoreFile = "keystore";
       
    47     private static String trustStoreFile = "truststore";
       
    48     private static String passwd = "passphrase";
       
    49 
       
    50     private static String keyFilename =
       
    51             System.getProperty("test.src", "./") + "/" + pathToStores +
       
    52                 "/" + keyStoreFile;
       
    53     private static String trustFilename =
       
    54             System.getProperty("test.src", "./") + "/" + pathToStores +
       
    55                 "/" + trustStoreFile;
       
    56 
       
    57     private ByteBuffer appOut1;         // write side of ssle1
       
    58     private ByteBuffer appIn1;          // read side of ssle1
       
    59     private ByteBuffer appOut2;         // write side of ssle2
       
    60     private ByteBuffer appIn2;          // read side of ssle2
       
    61 
       
    62     private ByteBuffer oneToTwo;        // "reliable" transport ssle1->ssle2
       
    63     private ByteBuffer twoToOne;        // "reliable" transport ssle2->ssle1
       
    64 
       
    65     /*
       
    66      * Majority of the test case is here, setup is done below.
       
    67      */
       
    68     private void createSSLEngines() throws Exception {
       
    69         ssle1 = sslc.createSSLEngine("client", 1);
       
    70         ssle1.setUseClientMode(true);
       
    71 
       
    72         ssle2 = sslc.createSSLEngine();
       
    73         ssle2.setUseClientMode(false);
       
    74         ssle2.setNeedClientAuth(true);
       
    75     }
       
    76 
       
    77     private void runTest() throws Exception {
       
    78         boolean dataDone = false;
       
    79 
       
    80         createSSLEngines();
       
    81         createBuffers();
       
    82 
       
    83         SSLEngineResult result1;        // ssle1's results from last operation
       
    84         SSLEngineResult result2;        // ssle2's results from last operation
       
    85 
       
    86         while (!isEngineClosed(ssle1) || !isEngineClosed(ssle2)) {
       
    87 
       
    88             log("================");
       
    89 
       
    90             result1 = ssle1.wrap(appOut1, oneToTwo);
       
    91             result2 = ssle2.wrap(appOut2, twoToOne);
       
    92 
       
    93             log("wrap1:  " + result1);
       
    94             log("oneToTwo  = " + oneToTwo);
       
    95             log("");
       
    96 
       
    97             log("wrap2:  " + result2);
       
    98             log("twoToOne  = " + twoToOne);
       
    99 
       
   100             runDelegatedTasks(result1, ssle1);
       
   101             runDelegatedTasks(result2, ssle2);
       
   102 
       
   103             oneToTwo.flip();
       
   104             twoToOne.flip();
       
   105 
       
   106             log("----");
       
   107 
       
   108             result1 = ssle1.unwrap(twoToOne, appIn1);
       
   109             result2 = ssle2.unwrap(oneToTwo, appIn2);
       
   110 
       
   111             log("unwrap1: " + result1);
       
   112             log("twoToOne  = " + twoToOne);
       
   113             log("");
       
   114 
       
   115             log("unwrap2: " + result2);
       
   116             log("oneToTwo  = " + oneToTwo);
       
   117 
       
   118             runDelegatedTasks(result1, ssle1);
       
   119             runDelegatedTasks(result2, ssle2);
       
   120 
       
   121             oneToTwo.compact();
       
   122             twoToOne.compact();
       
   123 
       
   124             /*
       
   125              * If we've transfered all the data between app1 and app2,
       
   126              * we try to close and see what that gets us.
       
   127              */
       
   128             if (!dataDone && (appOut1.limit() == appIn2.position()) &&
       
   129                     (appOut2.limit() == appIn1.position())) {
       
   130 
       
   131                 checkTransfer(appOut1, appIn2);
       
   132                 checkTransfer(appOut2, appIn1);
       
   133 
       
   134                 log("Closing ssle1's *OUTBOUND*...");
       
   135                 ssle1.closeOutbound();
       
   136                 dataDone = true;
       
   137             }
       
   138         }
       
   139     }
       
   140 
       
   141     public static void main(String args[]) throws Exception {
       
   142 
       
   143         ExtendedKeyEngine test;
       
   144 
       
   145         System.out.println("This test should run to completion");
       
   146         test = new ExtendedKeyEngine(true);
       
   147         test.createSSLEngines();
       
   148         test.runTest();
       
   149         System.out.println("Done!");
       
   150 
       
   151         System.out.println("This test should fail with a Handshake Error");
       
   152         test = new ExtendedKeyEngine(false);
       
   153         test.createSSLEngines();
       
   154 
       
   155         try {
       
   156             test.runTest();
       
   157         } catch (SSLHandshakeException e) {
       
   158             System.out.println(
       
   159                 "Caught proper exception, should be 'no suites in common'");
       
   160             e.printStackTrace();
       
   161         }
       
   162 
       
   163         System.out.println("Test Passed.");
       
   164     }
       
   165 
       
   166     /*
       
   167      * **********************************************************
       
   168      * Majority of the test case is above, below is just setup stuff
       
   169      * **********************************************************
       
   170      */
       
   171 
       
   172     public ExtendedKeyEngine(boolean abs) throws Exception {
       
   173         sslc = getSSLContext(keyFilename, trustFilename, abs);
       
   174     }
       
   175 
       
   176     /*
       
   177      * Create an initialized SSLContext to use for this test.
       
   178      */
       
   179     private SSLContext getSSLContext(String keyFile, String trustFile,
       
   180             boolean abs) throws Exception {
       
   181 
       
   182         KeyStore ks = KeyStore.getInstance("JKS");
       
   183         KeyStore ts = KeyStore.getInstance("JKS");
       
   184 
       
   185         char[] passphrase = "passphrase".toCharArray();
       
   186 
       
   187         ks.load(new FileInputStream(keyFile), passphrase);
       
   188         ts.load(new FileInputStream(trustFile), passphrase);
       
   189 
       
   190         KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
       
   191         kmf.init(ks, passphrase);
       
   192 
       
   193         KeyManager [] kms = kmf.getKeyManagers();
       
   194         if (abs) {
       
   195             kms = new KeyManager [] {
       
   196                 new MyX509ExtendedKeyManager((X509ExtendedKeyManager)kms[0])
       
   197             };
       
   198         } else {
       
   199             kms = new KeyManager [] {
       
   200                 new MyX509KeyManager((X509KeyManager)kms[0])
       
   201             };
       
   202         }
       
   203 
       
   204         TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509");
       
   205         tmf.init(ts);
       
   206         TrustManager [] tms = tmf.getTrustManagers();
       
   207 
       
   208         SSLContext sslCtx = SSLContext.getInstance("TLS");
       
   209 
       
   210         sslCtx.init(kms, tms, null);
       
   211 
       
   212         return sslCtx;
       
   213     }
       
   214 
       
   215     private void createBuffers() {
       
   216         // Size the buffers as appropriate.
       
   217 
       
   218         SSLSession session = ssle1.getSession();
       
   219         int appBufferMax = session.getApplicationBufferSize();
       
   220         int netBufferMax = session.getPacketBufferSize();
       
   221 
       
   222         appIn1 = ByteBuffer.allocateDirect(appBufferMax + 50);
       
   223         appIn2 = ByteBuffer.allocateDirect(appBufferMax + 50);
       
   224 
       
   225         oneToTwo = ByteBuffer.allocateDirect(netBufferMax);
       
   226         twoToOne = ByteBuffer.allocateDirect(netBufferMax);
       
   227 
       
   228         appOut1 = ByteBuffer.wrap("Hi Engine2, I'm SSLEngine1".getBytes());
       
   229         appOut2 = ByteBuffer.wrap("Hello Engine1, I'm SSLEngine2".getBytes());
       
   230 
       
   231         log("AppOut1 = " + appOut1);
       
   232         log("AppOut2 = " + appOut2);
       
   233         log("");
       
   234     }
       
   235 
       
   236     private static void runDelegatedTasks(SSLEngineResult result,
       
   237             SSLEngine engine) throws Exception {
       
   238 
       
   239         if (result.getHandshakeStatus() == HandshakeStatus.NEED_TASK) {
       
   240             Runnable runnable;
       
   241             while ((runnable = engine.getDelegatedTask()) != null) {
       
   242                 log("running delegated task...");
       
   243                 runnable.run();
       
   244             }
       
   245         }
       
   246     }
       
   247 
       
   248     private static boolean isEngineClosed(SSLEngine engine) {
       
   249         return (engine.isOutboundDone() && engine.isInboundDone());
       
   250     }
       
   251 
       
   252     private static void checkTransfer(ByteBuffer a, ByteBuffer b)
       
   253             throws Exception {
       
   254         a.flip();
       
   255         b.flip();
       
   256 
       
   257         if (!a.equals(b)) {
       
   258             throw new Exception("Data didn't transfer cleanly");
       
   259         } else {
       
   260             log("Data transferred cleanly");
       
   261         }
       
   262 
       
   263         a.position(a.limit());
       
   264         b.position(b.limit());
       
   265         a.limit(a.capacity());
       
   266         b.limit(b.capacity());
       
   267     }
       
   268 
       
   269     private static void log(String str) {
       
   270         if (debug) {
       
   271             System.out.println(str);
       
   272         }
       
   273     }
       
   274 }