1 /*
   2  * Copyright (c) 2010, 2016, 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 under
   6  * the terms of the GNU General Public License version 2 only, as published by
   7  * the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT ANY
  10  * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
  11  * A PARTICULAR PURPOSE. See the GNU General Public License version 2 for more
  12  * details (a copy is included in the LICENSE file that accompanied this code).
  13  *
  14  * You should have received a copy of the GNU General Public License version 2
  15  * along with this work; if not, write to the Free Software Foundation, Inc., 51
  16  * Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  17  *
  18  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA or
  19  * visit www.oracle.com if you need additional information or have any
  20  * questions.
  21  */
  22 
  23 import java.io.InputStream;
  24 import java.io.OutputStream;
  25 import java.security.cert.Certificate;
  26 import javax.net.ssl.KeyManager;
  27 import javax.net.ssl.SSLContext;
  28 import javax.net.ssl.SSLSession;
  29 import javax.net.ssl.SSLSocket;
  30 import javax.net.ssl.SSLSocketFactory;
  31 import javax.net.ssl.TrustManager;
  32 
  33 class JSSEClient extends CipherTestUtils.Client {
  34 
  35     private static final String DEFAULT = "DEFAULT";
  36     private static final String TLS = "TLS";
  37 
  38     private final SSLContext context;
  39     private final MyX509KeyManager keyManager;
  40     private final int port;
  41     private final String host;
  42     private final String protocol;
  43 
  44     JSSEClient(CipherTestUtils cipherTest, String host, int port,
  45             String protocols, String ciphersuite) throws Exception {
  46         super(cipherTest, ciphersuite);
  47         this.host = host;
  48         this.port = port;
  49         this.protocol = protocols;
  50         this.keyManager = new MyX509KeyManager(
  51                                     cipherTest.getClientKeyManager());
  52         context = SSLContext.getInstance(TLS);
  53     }
  54 
  55     @Override
  56     void runTest(CipherTestUtils.TestParameters params) throws Exception {
  57         keyManager.setAuthType(params.clientAuth);
  58         context.init(
  59                 new KeyManager[]{ keyManager },
  60                 new TrustManager[]{ cipherTest.getClientTrustManager() },
  61                 CipherTestUtils.secureRandom);
  62         SSLSocketFactory factory = (SSLSocketFactory)context.getSocketFactory();
  63 
  64         System.out.println("Connecting to server...");
  65         try (SSLSocket socket = (SSLSocket) factory.createSocket(host, port)) {
  66             socket.setSoTimeout(CipherTestUtils.TIMEOUT);
  67             socket.setEnabledCipherSuites(params.cipherSuite.split(","));
  68             if (params.protocol != null && !params.protocol.trim().isEmpty()
  69                     && !params.protocol.trim().equals(DEFAULT)) {
  70                 socket.setEnabledProtocols(params.protocol.split(","));
  71             }
  72             CipherTestUtils.printInfo(socket);
  73             InputStream in = socket.getInputStream();
  74             OutputStream out = socket.getOutputStream();
  75             sendRequest(in, out);
  76             SSLSession session = socket.getSession();
  77             session.invalidate();
  78             String cipherSuite = session.getCipherSuite();
  79             if (params.cipherSuite.equals(cipherSuite) == false) {
  80                 throw new RuntimeException("Negotiated ciphersuite mismatch: "
  81                         + cipherSuite + " != " + params.cipherSuite);
  82             }
  83             String protocol = session.getProtocol();
  84             if (!DEFAULT.equals(params.protocol)
  85                     && !params.protocol.contains(protocol)) {
  86                 throw new RuntimeException("Negotiated protocol mismatch: "
  87                         + protocol + " != " + params.protocol);
  88             }
  89             if (!cipherSuite.contains("DH_anon")) {
  90                 session.getPeerCertificates();
  91             }
  92             Certificate[] certificates = session.getLocalCertificates();
  93             if (params.clientAuth == null) {
  94                 if (certificates != null) {
  95                     throw new RuntimeException("Local certificates "
  96                             + "should be null");
  97                 }
  98             } else {
  99                 if ((certificates == null) || (certificates.length == 0)) {
 100                     throw new RuntimeException("Certificates missing");
 101                 }
 102                 String keyAlg = certificates[0].getPublicKey().getAlgorithm();
 103                 if ("EC".equals(keyAlg)) {
 104                     keyAlg = "ECDSA";
 105                 }
 106                 if (!params.clientAuth.equals(keyAlg)) {
 107                     throw new RuntimeException("Certificate type mismatch: "
 108                             + keyAlg + " != " + params.clientAuth);
 109                 }
 110             }
 111         }
 112     }
 113 }