Home | History | Annotate | Download | only in ssl
      1 /*
      2  * Copyright (c) 1996, 2012, 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.  Oracle designates this
      8  * particular file as subject to the "Classpath" exception as provided
      9  * by Oracle in the LICENSE file that accompanied this code.
     10  *
     11  * This code is distributed in the hope that it will be useful, but WITHOUT
     12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
     13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
     14  * version 2 for more details (a copy is included in the LICENSE file that
     15  * accompanied this code).
     16  *
     17  * You should have received a copy of the GNU General Public License version
     18  * 2 along with this work; if not, write to the Free Software Foundation,
     19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
     20  *
     21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
     22  * or visit www.oracle.com if you need additional information or have any
     23  * questions.
     24  */
     25 
     26 package sun.security.ssl;
     27 
     28 import java.io.*;
     29 import java.math.BigInteger;
     30 import java.security.*;
     31 import java.util.*;
     32 
     33 import java.security.interfaces.ECPublicKey;
     34 import java.security.interfaces.RSAPublicKey;
     35 import java.security.spec.ECParameterSpec;
     36 
     37 import java.security.cert.X509Certificate;
     38 import java.security.cert.CertificateException;
     39 
     40 import javax.crypto.SecretKey;
     41 import javax.crypto.spec.SecretKeySpec;
     42 
     43 import javax.net.ssl.*;
     44 
     45 import javax.security.auth.Subject;
     46 
     47 import sun.security.ssl.HandshakeMessage.*;
     48 import sun.security.ssl.CipherSuite.*;
     49 import static sun.security.ssl.CipherSuite.KeyExchange.*;
     50 
     51 import sun.net.util.IPAddressUtil;
     52 
     53 /**
     54  * ClientHandshaker does the protocol handshaking from the point
     55  * of view of a client.  It is driven asychronously by handshake messages
     56  * as delivered by the parent Handshaker class, and also uses
     57  * common functionality (e.g. key generation) that is provided there.
     58  *
     59  * @author David Brownell
     60  */
     61 final class ClientHandshaker extends Handshaker {
     62 
     63     // the server's public key from its certificate.
     64     private PublicKey serverKey;
     65 
     66     // the server's ephemeral public key from the server key exchange message
     67     // for ECDHE/ECDH_anon and RSA_EXPORT.
     68     private PublicKey ephemeralServerKey;
     69 
     70     // server's ephemeral public value for DHE/DH_anon key exchanges
     71     private BigInteger          serverDH;
     72 
     73     private DHCrypt             dh;
     74 
     75     private ECDHCrypt ecdh;
     76 
     77     private CertificateRequest  certRequest;
     78 
     79     private boolean serverKeyExchangeReceived;
     80 
     81     /*
     82      * The RSA PreMasterSecret needs to know the version of
     83      * ClientHello that was used on this handshake.  This represents
     84      * the "max version" this client is supporting.  In the
     85      * case of an initial handshake, it's the max version enabled,
     86      * but in the case of a resumption attempt, it's the version
     87      * of the session we're trying to resume.
     88      */
     89     private ProtocolVersion maxProtocolVersion;
     90 
     91     // To switch off the SNI extension.
     92     private final static boolean enableSNIExtension =
     93             Debug.getBooleanProperty("jsse.enableSNIExtension", true);
     94 
     95     /*
     96      * Constructors
     97      */
     98     ClientHandshaker(SSLSocketImpl socket, SSLContextImpl context,
     99             ProtocolList enabledProtocols,
    100             ProtocolVersion activeProtocolVersion,
    101             boolean isInitialHandshake, boolean secureRenegotiation,
    102             byte[] clientVerifyData, byte[] serverVerifyData) {
    103 
    104         super(socket, context, enabledProtocols, true, true,
    105             activeProtocolVersion, isInitialHandshake, secureRenegotiation,
    106             clientVerifyData, serverVerifyData);
    107     }
    108 
    109     ClientHandshaker(SSLEngineImpl engine, SSLContextImpl context,
    110             ProtocolList enabledProtocols,
    111             ProtocolVersion activeProtocolVersion,
    112             boolean isInitialHandshake, boolean secureRenegotiation,
    113             byte[] clientVerifyData, byte[] serverVerifyData) {
    114 
    115         super(engine, context, enabledProtocols, true, true,
    116             activeProtocolVersion, isInitialHandshake, secureRenegotiation,
    117             clientVerifyData, serverVerifyData);
    118     }
    119 
    120     /*
    121      * This routine handles all the client side handshake messages, one at
    122      * a time.  Given the message type (and in some cases the pending cipher
    123      * spec) it parses the type-specific message.  Then it calls a function
    124      * that handles that specific message.
    125      *
    126      * It updates the state machine (need to verify it) as each message
    127      * is processed, and writes responses as needed using the connection
    128      * in the constructor.
    129      */
    130     void processMessage(byte type, int messageLen) throws IOException {
    131         if (state >= type
    132                 && (type != HandshakeMessage.ht_hello_request)) {
    133             throw new SSLProtocolException(
    134                     "Handshake message sequence violation, " + type);
    135         }
    136 
    137         switch (type) {
    138         case HandshakeMessage.ht_hello_request:
    139             this.serverHelloRequest(new HelloRequest(input));
    140             break;
    141 
    142         case HandshakeMessage.ht_server_hello:
    143             this.serverHello(new ServerHello(input, messageLen));
    144             break;
    145 
    146         case HandshakeMessage.ht_certificate:
    147             if (keyExchange == K_DH_ANON || keyExchange == K_ECDH_ANON
    148                     || keyExchange == K_KRB5 || keyExchange == K_KRB5_EXPORT) {
    149                 fatalSE(Alerts.alert_unexpected_message,
    150                     "unexpected server cert chain");
    151                 // NOTREACHED
    152             }
    153             this.serverCertificate(new CertificateMsg(input));
    154             serverKey =
    155                 session.getPeerCertificates()[0].getPublicKey();
    156             break;
    157 
    158         case HandshakeMessage.ht_server_key_exchange:
    159             serverKeyExchangeReceived = true;
    160             switch (keyExchange) {
    161             case K_RSA_EXPORT:
    162                 /**
    163                  * The server key exchange message is sent by the server only
    164                  * when the server certificate message does not contain the
    165                  * proper amount of data to allow the client to exchange a
    166                  * premaster secret, such as when RSA_EXPORT is used and the
    167                  * public key in the server certificate is longer than 512 bits.
    168                  */
    169                 if (serverKey == null) {
    170                     throw new SSLProtocolException
    171                         ("Server did not send certificate message");
    172                 }
    173 
    174                 if (!(serverKey instanceof RSAPublicKey)) {
    175                     throw new SSLProtocolException("Protocol violation:" +
    176                         " the certificate type must be appropriate for the" +
    177                         " selected cipher suite's key exchange algorithm");
    178                 }
    179 
    180                 if (JsseJce.getRSAKeyLength(serverKey) <= 512) {
    181                     throw new SSLProtocolException("Protocol violation:" +
    182                         " server sent a server key exchange message for" +
    183                         " key exchange " + keyExchange +
    184                         " when the public key in the server certificate" +
    185                         " is less than or equal to 512 bits in length");
    186                 }
    187 
    188                 try {
    189                     this.serverKeyExchange(new RSA_ServerKeyExchange(input));
    190                 } catch (GeneralSecurityException e) {
    191                     throwSSLException("Server key", e);
    192                 }
    193                 break;
    194             case K_DH_ANON:
    195                 try {
    196                     this.serverKeyExchange(new DH_ServerKeyExchange(
    197                                                 input, protocolVersion));
    198                 } catch (GeneralSecurityException e) {
    199                     throwSSLException("Server key", e);
    200                 }
    201                 break;
    202             case K_DHE_DSS:
    203             case K_DHE_RSA:
    204                 try {
    205                     this.serverKeyExchange(new DH_ServerKeyExchange(
    206                         input, serverKey,
    207                         clnt_random.random_bytes, svr_random.random_bytes,
    208                         messageLen,
    209                         localSupportedSignAlgs, protocolVersion));
    210                 } catch (GeneralSecurityException e) {
    211                     throwSSLException("Server key", e);
    212                 }
    213                 break;
    214             case K_ECDHE_ECDSA:
    215             case K_ECDHE_RSA:
    216             case K_ECDH_ANON:
    217                 try {
    218                     this.serverKeyExchange(new ECDH_ServerKeyExchange
    219                         (input, serverKey, clnt_random.random_bytes,
    220                         svr_random.random_bytes,
    221                         localSupportedSignAlgs, protocolVersion));
    222                 } catch (GeneralSecurityException e) {
    223                     throwSSLException("Server key", e);
    224                 }
    225                 break;
    226             case K_RSA:
    227             case K_DH_RSA:
    228             case K_DH_DSS:
    229             case K_ECDH_ECDSA:
    230             case K_ECDH_RSA:
    231                 throw new SSLProtocolException(
    232                     "Protocol violation: server sent a server key exchange"
    233                     + "message for key exchange " + keyExchange);
    234             case K_KRB5:
    235             case K_KRB5_EXPORT:
    236                 throw new SSLProtocolException(
    237                     "unexpected receipt of server key exchange algorithm");
    238             default:
    239                 throw new SSLProtocolException(
    240                     "unsupported key exchange algorithm = "
    241                     + keyExchange);
    242             }
    243             break;
    244 
    245         case HandshakeMessage.ht_certificate_request:
    246             // save for later, it's handled by serverHelloDone
    247             if ((keyExchange == K_DH_ANON) || (keyExchange == K_ECDH_ANON)) {
    248                 throw new SSLHandshakeException(
    249                     "Client authentication requested for "+
    250                     "anonymous cipher suite.");
    251             } else if (keyExchange == K_KRB5 || keyExchange == K_KRB5_EXPORT) {
    252                 throw new SSLHandshakeException(
    253                     "Client certificate requested for "+
    254                     "kerberos cipher suite.");
    255             }
    256             certRequest = new CertificateRequest(input, protocolVersion);
    257             if (debug != null && Debug.isOn("handshake")) {
    258                 certRequest.print(System.out);
    259             }
    260 
    261             if (protocolVersion.v >= ProtocolVersion.TLS12.v) {
    262                 Collection<SignatureAndHashAlgorithm> peerSignAlgs =
    263                                         certRequest.getSignAlgorithms();
    264                 if (peerSignAlgs == null || peerSignAlgs.isEmpty()) {
    265                     throw new SSLHandshakeException(
    266                         "No peer supported signature algorithms");
    267                 }
    268 
    269                 Collection<SignatureAndHashAlgorithm> supportedPeerSignAlgs =
    270                     SignatureAndHashAlgorithm.getSupportedAlgorithms(
    271                                                             peerSignAlgs);
    272                 if (supportedPeerSignAlgs.isEmpty()) {
    273                     throw new SSLHandshakeException(
    274                         "No supported signature and hash algorithm in common");
    275                 }
    276 
    277                 setPeerSupportedSignAlgs(supportedPeerSignAlgs);
    278                 session.setPeerSupportedSignatureAlgorithms(
    279                                                 supportedPeerSignAlgs);
    280             }
    281 
    282             break;
    283 
    284         case HandshakeMessage.ht_server_hello_done:
    285             this.serverHelloDone(new ServerHelloDone(input));
    286             break;
    287 
    288         case HandshakeMessage.ht_finished:
    289             this.serverFinished(
    290                 new Finished(protocolVersion, input, cipherSuite));
    291             break;
    292 
    293         default:
    294             throw new SSLProtocolException(
    295                 "Illegal client handshake msg, " + type);
    296         }
    297 
    298         //
    299         // Move state machine forward if the message handling
    300         // code didn't already do so
    301         //
    302         if (state < type) {
    303             state = type;
    304         }
    305     }
    306 
    307     /*
    308      * Used by the server to kickstart negotiations -- this requests a
    309      * "client hello" to renegotiate current cipher specs (e.g. maybe lots
    310      * of data has been encrypted with the same keys, or the server needs
    311      * the client to present a certificate).
    312      */
    313     private void serverHelloRequest(HelloRequest mesg) throws IOException {
    314         if (debug != null && Debug.isOn("handshake")) {
    315             mesg.print(System.out);
    316         }
    317 
    318         //
    319         // Could be (e.g. at connection setup) that we already
    320         // sent the "client hello" but the server's not seen it.
    321         //
    322         if (state < HandshakeMessage.ht_client_hello) {
    323             if (!secureRenegotiation && !allowUnsafeRenegotiation) {
    324                 // renegotiation is not allowed.
    325                 if (activeProtocolVersion.v >= ProtocolVersion.TLS10.v) {
    326                     // response with a no_renegotiation warning,
    327                     warningSE(Alerts.alert_no_renegotiation);
    328 
    329                     // invalidate the handshake so that the caller can
    330                     // dispose this object.
    331                     invalidated = true;
    332 
    333                     // If there is still unread block in the handshake
    334                     // input stream, it would be truncated with the disposal
    335                     // and the next handshake message will become incomplete.
    336                     //
    337                     // However, according to SSL/TLS specifications, no more
    338                     // handshake message should immediately follow ClientHello
    339                     // or HelloRequest. So just let it be.
    340                 } else {
    341                     // For SSLv3, send the handshake_failure fatal error.
    342                     // Note that SSLv3 does not define a no_renegotiation
    343                     // alert like TLSv1. However we cannot ignore the message
    344                     // simply, otherwise the other side was waiting for a
    345                     // response that would never come.
    346                     fatalSE(Alerts.alert_handshake_failure,
    347                         "Renegotiation is not allowed");
    348                 }
    349             } else {
    350                 if (!secureRenegotiation) {
    351                     if (debug != null && Debug.isOn("handshake")) {
    352                         System.out.println(
    353                             "Warning: continue with insecure renegotiation");
    354                     }
    355                 }
    356                 kickstart();
    357             }
    358         }
    359     }
    360 
    361 
    362     /*
    363      * Server chooses session parameters given options created by the
    364      * client -- basically, cipher options, session id, and someday a
    365      * set of compression options.
    366      *
    367      * There are two branches of the state machine, decided by the
    368      * details of this message.  One is the "fast" handshake, where we
    369      * can resume the pre-existing session we asked resume.  The other
    370      * is a more expensive "full" handshake, with key exchange and
    371      * probably authentication getting done.
    372      */
    373     private void serverHello(ServerHello mesg) throws IOException {
    374         serverKeyExchangeReceived = false;
    375         if (debug != null && Debug.isOn("handshake")) {
    376             mesg.print(System.out);
    377         }
    378 
    379         // check if the server selected protocol version is OK for us
    380         ProtocolVersion mesgVersion = mesg.protocolVersion;
    381         if (!isNegotiable(mesgVersion)) {
    382             throw new SSLHandshakeException(
    383                 "Server chose " + mesgVersion +
    384                 ", but that protocol version is not enabled or not supported " +
    385                 "by the client.");
    386         }
    387 
    388         handshakeHash.protocolDetermined(mesgVersion);
    389 
    390         // Set protocolVersion and propagate to SSLSocket and the
    391         // Handshake streams
    392         setVersion(mesgVersion);
    393 
    394         // check the "renegotiation_info" extension
    395         RenegotiationInfoExtension serverHelloRI = (RenegotiationInfoExtension)
    396                     mesg.extensions.get(ExtensionType.EXT_RENEGOTIATION_INFO);
    397         if (serverHelloRI != null) {
    398             if (isInitialHandshake) {
    399                 // verify the length of the "renegotiated_connection" field
    400                 if (!serverHelloRI.isEmpty()) {
    401                     // abort the handshake with a fatal handshake_failure alert
    402                     fatalSE(Alerts.alert_handshake_failure,
    403                         "The renegotiation_info field is not empty");
    404                 }
    405 
    406                 secureRenegotiation = true;
    407             } else {
    408                 // For a legacy renegotiation, the client MUST verify that
    409                 // it does not contain the "renegotiation_info" extension.
    410                 if (!secureRenegotiation) {
    411                     fatalSE(Alerts.alert_handshake_failure,
    412                         "Unexpected renegotiation indication extension");
    413                 }
    414 
    415                 // verify the client_verify_data and server_verify_data values
    416                 byte[] verifyData =
    417                     new byte[clientVerifyData.length + serverVerifyData.length];
    418                 System.arraycopy(clientVerifyData, 0, verifyData,
    419                         0, clientVerifyData.length);
    420                 System.arraycopy(serverVerifyData, 0, verifyData,
    421                         clientVerifyData.length, serverVerifyData.length);
    422                 if (!Arrays.equals(verifyData,
    423                                 serverHelloRI.getRenegotiatedConnection())) {
    424                     fatalSE(Alerts.alert_handshake_failure,
    425                         "Incorrect verify data in ServerHello " +
    426                         "renegotiation_info message");
    427                 }
    428             }
    429         } else {
    430             // no renegotiation indication extension
    431             if (isInitialHandshake) {
    432                 if (!allowLegacyHelloMessages) {
    433                     // abort the handshake with a fatal handshake_failure alert
    434                     fatalSE(Alerts.alert_handshake_failure,
    435                         "Failed to negotiate the use of secure renegotiation");
    436                 }
    437 
    438                 secureRenegotiation = false;
    439                 if (debug != null && Debug.isOn("handshake")) {
    440                     System.out.println("Warning: No renegotiation " +
    441                                     "indication extension in ServerHello");
    442                 }
    443             } else {
    444                 // For a secure renegotiation, the client must abort the
    445                 // handshake if no "renegotiation_info" extension is present.
    446                 if (secureRenegotiation) {
    447                     fatalSE(Alerts.alert_handshake_failure,
    448                         "No renegotiation indication extension");
    449                 }
    450 
    451                 // we have already allowed unsafe renegotation before request
    452                 // the renegotiation.
    453             }
    454         }
    455 
    456         //
    457         // Save server nonce, we always use it to compute connection
    458         // keys and it's also used to create the master secret if we're
    459         // creating a new session (i.e. in the full handshake).
    460         //
    461         svr_random = mesg.svr_random;
    462 
    463         if (isNegotiable(mesg.cipherSuite) == false) {
    464             fatalSE(Alerts.alert_illegal_parameter,
    465                 "Server selected improper ciphersuite " + mesg.cipherSuite);
    466         }
    467 
    468         setCipherSuite(mesg.cipherSuite);
    469         if (protocolVersion.v >= ProtocolVersion.TLS12.v) {
    470             handshakeHash.setFinishedAlg(cipherSuite.prfAlg.getPRFHashAlg());
    471         }
    472 
    473         if (mesg.compression_method != 0) {
    474             fatalSE(Alerts.alert_illegal_parameter,
    475                 "compression type not supported, "
    476                 + mesg.compression_method);
    477             // NOTREACHED
    478         }
    479 
    480         // so far so good, let's look at the session
    481         if (session != null) {
    482             // we tried to resume, let's see what the server decided
    483             if (session.getSessionId().equals(mesg.sessionId)) {
    484                 // server resumed the session, let's make sure everything
    485                 // checks out
    486 
    487                 // Verify that the session ciphers are unchanged.
    488                 CipherSuite sessionSuite = session.getSuite();
    489                 if (cipherSuite != sessionSuite) {
    490                     throw new SSLProtocolException
    491                         ("Server returned wrong cipher suite for session");
    492                 }
    493 
    494                 // verify protocol version match
    495                 ProtocolVersion sessionVersion = session.getProtocolVersion();
    496                 if (protocolVersion != sessionVersion) {
    497                     throw new SSLProtocolException
    498                         ("Server resumed session with wrong protocol version");
    499                 }
    500 
    501                 // validate subject identity
    502                 if (sessionSuite.keyExchange == K_KRB5 ||
    503                     sessionSuite.keyExchange == K_KRB5_EXPORT) {
    504                     Principal localPrincipal = session.getLocalPrincipal();
    505 
    506                     Subject subject = null;
    507                     try {
    508                         subject = AccessController.doPrivileged(
    509                             new PrivilegedExceptionAction<Subject>() {
    510                             public Subject run() throws Exception {
    511                                 return Krb5Helper.getClientSubject(getAccSE());
    512                             }});
    513                     } catch (PrivilegedActionException e) {
    514                         subject = null;
    515                         if (debug != null && Debug.isOn("session")) {
    516                             System.out.println("Attempt to obtain" +
    517                                         " subject failed!");
    518                         }
    519                     }
    520 
    521                     if (subject != null) {
    522                         // Eliminate dependency on KerberosPrincipal
    523                         Set<Principal> principals =
    524                             subject.getPrincipals(Principal.class);
    525                         if (!principals.contains(localPrincipal)) {
    526                             throw new SSLProtocolException("Server resumed" +
    527                                 " session with wrong subject identity");
    528                         } else {
    529                             if (debug != null && Debug.isOn("session"))
    530                                 System.out.println("Subject identity is same");
    531                         }
    532                     } else {
    533                         if (debug != null && Debug.isOn("session"))
    534                             System.out.println("Kerberos credentials are not" +
    535                                 " present in the current Subject; check if " +
    536                                 " javax.security.auth.useSubjectAsCreds" +
    537                                 " system property has been set to false");
    538                         throw new SSLProtocolException
    539                             ("Server resumed session with no subject");
    540                     }
    541                 }
    542 
    543                 // looks fine; resume it, and update the state machine.
    544                 resumingSession = true;
    545                 state = HandshakeMessage.ht_finished - 1;
    546                 calculateConnectionKeys(session.getMasterSecret());
    547                 if (debug != null && Debug.isOn("session")) {
    548                     System.out.println("%% Server resumed " + session);
    549                 }
    550             } else {
    551                 // we wanted to resume, but the server refused
    552                 session = null;
    553                 if (!enableNewSession) {
    554                     throw new SSLException
    555                         ("New session creation is disabled");
    556                 }
    557             }
    558         }
    559 
    560         if (resumingSession && session != null) {
    561             if (protocolVersion.v >= ProtocolVersion.TLS12.v) {
    562                 handshakeHash.setCertificateVerifyAlg(null);
    563             }
    564 
    565             setHandshakeSessionSE(session);
    566             return;
    567         }
    568 
    569         // check extensions
    570         for (HelloExtension ext : mesg.extensions.list()) {
    571             ExtensionType type = ext.type;
    572             if ((type != ExtensionType.EXT_ELLIPTIC_CURVES)
    573                     && (type != ExtensionType.EXT_EC_POINT_FORMATS)
    574                     && (type != ExtensionType.EXT_SERVER_NAME)
    575                     && (type != ExtensionType.EXT_RENEGOTIATION_INFO)) {
    576                 fatalSE(Alerts.alert_unsupported_extension,
    577                     "Server sent an unsupported extension: " + type);
    578             }
    579         }
    580 
    581         // Create a new session, we need to do the full handshake
    582         session = new SSLSessionImpl(protocolVersion, cipherSuite,
    583                             getLocalSupportedSignAlgs(),
    584                             mesg.sessionId, getHostSE(), getPortSE());
    585         setHandshakeSessionSE(session);
    586         if (debug != null && Debug.isOn("handshake")) {
    587             System.out.println("** " + cipherSuite);
    588         }
    589     }
    590 
    591     /*
    592      * Server's own key was either a signing-only key, or was too
    593      * large for export rules ... this message holds an ephemeral
    594      * RSA key to use for key exchange.
    595      */
    596     private void serverKeyExchange(RSA_ServerKeyExchange mesg)
    597             throws IOException, GeneralSecurityException {
    598         if (debug != null && Debug.isOn("handshake")) {
    599             mesg.print(System.out);
    600         }
    601         if (!mesg.verify(serverKey, clnt_random, svr_random)) {
    602             fatalSE(Alerts.alert_handshake_failure,
    603                 "server key exchange invalid");
    604             // NOTREACHED
    605         }
    606         ephemeralServerKey = mesg.getPublicKey();
    607     }
    608 
    609 
    610     /*
    611      * Diffie-Hellman key exchange.  We save the server public key and
    612      * our own D-H algorithm object so we can defer key calculations
    613      * until after we've sent the client key exchange message (which
    614      * gives client and server some useful parallelism).
    615      */
    616     private void serverKeyExchange(DH_ServerKeyExchange mesg)
    617             throws IOException {
    618         if (debug != null && Debug.isOn("handshake")) {
    619             mesg.print(System.out);
    620         }
    621         dh = new DHCrypt(mesg.getModulus(), mesg.getBase(),
    622                                             sslContext.getSecureRandom());
    623         serverDH = mesg.getServerPublicKey();
    624     }
    625 
    626     private void serverKeyExchange(ECDH_ServerKeyExchange mesg)
    627             throws IOException {
    628         if (debug != null && Debug.isOn("handshake")) {
    629             mesg.print(System.out);
    630         }
    631         ECPublicKey key = mesg.getPublicKey();
    632         ecdh = new ECDHCrypt(key.getParams(), sslContext.getSecureRandom());
    633         ephemeralServerKey = key;
    634     }
    635 
    636     /*
    637      * The server's "Hello Done" message is the client's sign that
    638      * it's time to do all the hard work.
    639      */
    640     private void serverHelloDone(ServerHelloDone mesg) throws IOException {
    641         if (debug != null && Debug.isOn("handshake")) {
    642             mesg.print(System.out);
    643         }
    644         /*
    645          * Always make sure the input has been digested before we
    646          * start emitting data, to ensure the hashes are correctly
    647          * computed for the Finished and CertificateVerify messages
    648          * which we send (here).
    649          */
    650         input.digestNow();
    651 
    652         /*
    653          * FIRST ... if requested, send an appropriate Certificate chain
    654          * to authenticate the client, and remember the associated private
    655          * key to sign the CertificateVerify message.
    656          */
    657         PrivateKey signingKey = null;
    658 
    659         if (certRequest != null) {
    660             X509ExtendedKeyManager km = sslContext.getX509KeyManager();
    661 
    662             ArrayList<String> keytypesTmp = new ArrayList<>(4);
    663 
    664             for (int i = 0; i < certRequest.types.length; i++) {
    665                 String typeName;
    666 
    667                 switch (certRequest.types[i]) {
    668                 case CertificateRequest.cct_rsa_sign:
    669                     typeName = "RSA";
    670                     break;
    671 
    672                 case CertificateRequest.cct_dss_sign:
    673                     typeName = "DSA";
    674                     break;
    675 
    676                 case CertificateRequest.cct_ecdsa_sign:
    677                     // ignore if we do not have EC crypto available
    678                     typeName = JsseJce.isEcAvailable() ? "EC" : null;
    679                     break;
    680 
    681                 // Fixed DH/ECDH client authentication not supported
    682                 case CertificateRequest.cct_rsa_fixed_dh:
    683                 case CertificateRequest.cct_dss_fixed_dh:
    684                 case CertificateRequest.cct_rsa_fixed_ecdh:
    685                 case CertificateRequest.cct_ecdsa_fixed_ecdh:
    686                 // Any other values (currently not used in TLS)
    687                 case CertificateRequest.cct_rsa_ephemeral_dh:
    688                 case CertificateRequest.cct_dss_ephemeral_dh:
    689                 default:
    690                     typeName = null;
    691                     break;
    692                 }
    693 
    694                 if ((typeName != null) && (!keytypesTmp.contains(typeName))) {
    695                     keytypesTmp.add(typeName);
    696                 }
    697             }
    698 
    699             String alias = null;
    700             int keytypesTmpSize = keytypesTmp.size();
    701             if (keytypesTmpSize != 0) {
    702                 String keytypes[] =
    703                         keytypesTmp.toArray(new String[keytypesTmpSize]);
    704 
    705                 if (conn != null) {
    706                     alias = km.chooseClientAlias(keytypes,
    707                         certRequest.getAuthorities(), conn);
    708                 } else {
    709                     alias = km.chooseEngineClientAlias(keytypes,
    710                         certRequest.getAuthorities(), engine);
    711                 }
    712             }
    713 
    714             CertificateMsg m1 = null;
    715             if (alias != null) {
    716                 X509Certificate[] certs = km.getCertificateChain(alias);
    717                 if ((certs != null) && (certs.length != 0)) {
    718                     PublicKey publicKey = certs[0].getPublicKey();
    719                     // for EC, make sure we use a supported named curve
    720                     if (publicKey instanceof ECPublicKey) {
    721                         ECParameterSpec params =
    722                             ((ECPublicKey)publicKey).getParams();
    723                         int index =
    724                             SupportedEllipticCurvesExtension.getCurveIndex(
    725                                 params);
    726                         if (!SupportedEllipticCurvesExtension.isSupported(
    727                                 index)) {
    728                             publicKey = null;
    729                         }
    730                     }
    731                     if (publicKey != null) {
    732                         m1 = new CertificateMsg(certs);
    733                         signingKey = km.getPrivateKey(alias);
    734                         session.setLocalPrivateKey(signingKey);
    735                         session.setLocalCertificates(certs);
    736                     }
    737                 }
    738             }
    739             if (m1 == null) {
    740                 //
    741                 // No appropriate cert was found ... report this to the
    742                 // server.  For SSLv3, send the no_certificate alert;
    743                 // TLS uses an empty cert chain instead.
    744                 //
    745                 if (protocolVersion.v >= ProtocolVersion.TLS10.v) {
    746                     m1 = new CertificateMsg(new X509Certificate [0]);
    747                 } else {
    748                     warningSE(Alerts.alert_no_certificate);
    749                 }
    750             }
    751 
    752             //
    753             // At last ... send any client certificate chain.
    754             //
    755             if (m1 != null) {
    756                 if (debug != null && Debug.isOn("handshake")) {
    757                     m1.print(System.out);
    758                 }
    759                 m1.write(output);
    760             }
    761         }
    762 
    763         /*
    764          * SECOND ... send the client key exchange message.  The
    765          * procedure used is a function of the cipher suite selected;
    766          * one is always needed.
    767          */
    768         HandshakeMessage m2;
    769 
    770         switch (keyExchange) {
    771 
    772         case K_RSA:
    773         case K_RSA_EXPORT:
    774             if (serverKey == null) {
    775                 throw new SSLProtocolException
    776                         ("Server did not send certificate message");
    777             }
    778 
    779             if (!(serverKey instanceof RSAPublicKey)) {
    780                 throw new SSLProtocolException
    781                         ("Server certificate does not include an RSA key");
    782             }
    783 
    784             /*
    785              * For RSA key exchange, we randomly generate a new
    786              * pre-master secret and encrypt it with the server's
    787              * public key.  Then we save that pre-master secret
    788              * so that we can calculate the keying data later;
    789              * it's a performance speedup not to do that until
    790              * the client's waiting for the server response, but
    791              * more of a speedup for the D-H case.
    792              *
    793              * If the RSA_EXPORT scheme is active, when the public
    794              * key in the server certificate is less than or equal
    795              * to 512 bits in length, use the cert's public key,
    796              * otherwise, the ephemeral one.
    797              */
    798             PublicKey key;
    799             if (keyExchange == K_RSA) {
    800                 key = serverKey;
    801             } else {    // K_RSA_EXPORT
    802                 if (JsseJce.getRSAKeyLength(serverKey) <= 512) {
    803                     // extraneous ephemeralServerKey check done
    804                     // above in processMessage()
    805                     key = serverKey;
    806                 } else {
    807                     if (ephemeralServerKey == null) {
    808                         throw new SSLProtocolException("Server did not send" +
    809                             " a RSA_EXPORT Server Key Exchange message");
    810                     }
    811                     key = ephemeralServerKey;
    812                 }
    813             }
    814 
    815             m2 = new RSAClientKeyExchange(protocolVersion, maxProtocolVersion,
    816                                 sslContext.getSecureRandom(), key);
    817             break;
    818         case K_DH_RSA:
    819         case K_DH_DSS:
    820             /*
    821              * For DH Key exchange, we only need to make sure the server
    822              * knows our public key, so we calculate the same pre-master
    823              * secret.
    824              *
    825              * For certs that had DH keys in them, we send an empty
    826              * handshake message (no key) ... we flag this case by
    827              * passing a null "dhPublic" value.
    828              *
    829              * Otherwise we send ephemeral DH keys, unsigned.
    830              */
    831             // if (useDH_RSA || useDH_DSS)
    832             m2 = new DHClientKeyExchange();
    833             break;
    834         case K_DHE_RSA:
    835         case K_DHE_DSS:
    836         case K_DH_ANON:
    837             if (dh == null) {
    838                 throw new SSLProtocolException
    839                     ("Server did not send a DH Server Key Exchange message");
    840             }
    841             m2 = new DHClientKeyExchange(dh.getPublicKey());
    842             break;
    843         case K_ECDHE_RSA:
    844         case K_ECDHE_ECDSA:
    845         case K_ECDH_ANON:
    846             if (ecdh == null) {
    847                 throw new SSLProtocolException
    848                     ("Server did not send a ECDH Server Key Exchange message");
    849             }
    850             m2 = new ECDHClientKeyExchange(ecdh.getPublicKey());
    851             break;
    852         case K_ECDH_RSA:
    853         case K_ECDH_ECDSA:
    854             if (serverKey == null) {
    855                 throw new SSLProtocolException
    856                         ("Server did not send certificate message");
    857             }
    858             if (serverKey instanceof ECPublicKey == false) {
    859                 throw new SSLProtocolException
    860                         ("Server certificate does not include an EC key");
    861             }
    862             ECParameterSpec params = ((ECPublicKey)serverKey).getParams();
    863             ecdh = new ECDHCrypt(params, sslContext.getSecureRandom());
    864             m2 = new ECDHClientKeyExchange(ecdh.getPublicKey());
    865             break;
    866         case K_KRB5:
    867         case K_KRB5_EXPORT:
    868             String hostname = getHostSE();
    869             if (hostname == null) {
    870                 throw new IOException("Hostname is required" +
    871                                 " to use Kerberos cipher suites");
    872             }
    873             KerberosClientKeyExchange kerberosMsg =
    874                 new KerberosClientKeyExchange(
    875                     hostname, isLoopbackSE(), getAccSE(), protocolVersion,
    876                 sslContext.getSecureRandom());
    877             // Record the principals involved in exchange
    878             session.setPeerPrincipal(kerberosMsg.getPeerPrincipal());
    879             session.setLocalPrincipal(kerberosMsg.getLocalPrincipal());
    880             m2 = kerberosMsg;
    881             break;
    882         default:
    883             // somethings very wrong
    884             throw new RuntimeException
    885                                 ("Unsupported key exchange: " + keyExchange);
    886         }
    887         if (debug != null && Debug.isOn("handshake")) {
    888             m2.print(System.out);
    889         }
    890         m2.write(output);
    891 
    892 
    893         /*
    894          * THIRD, send a "change_cipher_spec" record followed by the
    895          * "Finished" message.  We flush the messages we've queued up, to
    896          * get concurrency between client and server.  The concurrency is
    897          * useful as we calculate the master secret, which is needed both
    898          * to compute the "Finished" message, and to compute the keys used
    899          * to protect all records following the change_cipher_spec.
    900          */
    901 
    902         output.doHashes();
    903         output.flush();
    904 
    905         /*
    906          * We deferred calculating the master secret and this connection's
    907          * keying data; we do it now.  Deferring this calculation is good
    908          * from a performance point of view, since it lets us do it during
    909          * some time that network delays and the server's own calculations
    910          * would otherwise cause to be "dead" in the critical path.
    911          */
    912         SecretKey preMasterSecret;
    913         switch (keyExchange) {
    914         case K_RSA:
    915         case K_RSA_EXPORT:
    916             preMasterSecret = ((RSAClientKeyExchange)m2).preMaster;
    917             break;
    918         case K_KRB5:
    919         case K_KRB5_EXPORT:
    920             byte[] secretBytes =
    921                 ((KerberosClientKeyExchange)m2).getUnencryptedPreMasterSecret();
    922             preMasterSecret = new SecretKeySpec(secretBytes,
    923                 "TlsPremasterSecret");
    924             break;
    925         case K_DHE_RSA:
    926         case K_DHE_DSS:
    927         case K_DH_ANON:
    928             preMasterSecret = dh.getAgreedSecret(serverDH, true);
    929             break;
    930         case K_ECDHE_RSA:
    931         case K_ECDHE_ECDSA:
    932         case K_ECDH_ANON:
    933             preMasterSecret = ecdh.getAgreedSecret(ephemeralServerKey);
    934             break;
    935         case K_ECDH_RSA:
    936         case K_ECDH_ECDSA:
    937             preMasterSecret = ecdh.getAgreedSecret(serverKey);
    938             break;
    939         default:
    940             throw new IOException("Internal error: unknown key exchange "
    941                 + keyExchange);
    942         }
    943 
    944         calculateKeys(preMasterSecret, null);
    945 
    946         /*
    947          * FOURTH, if we sent a Certificate, we need to send a signed
    948          * CertificateVerify (unless the key in the client's certificate
    949          * was a Diffie-Hellman key).).
    950          *
    951          * This uses a hash of the previous handshake messages ... either
    952          * a nonfinal one (if the particular implementation supports it)
    953          * or else using the third element in the arrays of hashes being
    954          * computed.
    955          */
    956         if (signingKey != null) {
    957             CertificateVerify m3;
    958             try {
    959                 SignatureAndHashAlgorithm preferableSignatureAlgorithm = null;
    960                 if (protocolVersion.v >= ProtocolVersion.TLS12.v) {
    961                     preferableSignatureAlgorithm =
    962                         SignatureAndHashAlgorithm.getPreferableAlgorithm(
    963                             peerSupportedSignAlgs, signingKey.getAlgorithm(),
    964                             signingKey);
    965 
    966                     if (preferableSignatureAlgorithm == null) {
    967                         throw new SSLHandshakeException(
    968                             "No supported signature algorithm");
    969                     }
    970 
    971                     String hashAlg =
    972                         SignatureAndHashAlgorithm.getHashAlgorithmName(
    973                                 preferableSignatureAlgorithm);
    974                     if (hashAlg == null || hashAlg.length() == 0) {
    975                         throw new SSLHandshakeException(
    976                                 "No supported hash algorithm");
    977                     }
    978 
    979                     handshakeHash.setCertificateVerifyAlg(hashAlg);
    980                 }
    981 
    982                 m3 = new CertificateVerify(protocolVersion, handshakeHash,
    983                     signingKey, session.getMasterSecret(),
    984                     sslContext.getSecureRandom(),
    985                     preferableSignatureAlgorithm);
    986             } catch (GeneralSecurityException e) {
    987                 fatalSE(Alerts.alert_handshake_failure,
    988                     "Error signing certificate verify", e);
    989                 // NOTREACHED, make compiler happy
    990                 m3 = null;
    991             }
    992             if (debug != null && Debug.isOn("handshake")) {
    993                 m3.print(System.out);
    994             }
    995             m3.write(output);
    996             output.doHashes();
    997         } else {
    998             if (protocolVersion.v >= ProtocolVersion.TLS12.v) {
    999                 handshakeHash.setCertificateVerifyAlg(null);
   1000             }
   1001         }
   1002 
   1003         /*
   1004          * OK, that's that!
   1005          */
   1006         sendChangeCipherAndFinish(false);
   1007     }
   1008 
   1009 
   1010     /*
   1011      * "Finished" is the last handshake message sent.  If we got this
   1012      * far, the MAC has been validated post-decryption.  We validate
   1013      * the two hashes here as an additional sanity check, protecting
   1014      * the handshake against various active attacks.
   1015      */
   1016     private void serverFinished(Finished mesg) throws IOException {
   1017         if (debug != null && Debug.isOn("handshake")) {
   1018             mesg.print(System.out);
   1019         }
   1020 
   1021         boolean verified = mesg.verify(handshakeHash, Finished.SERVER,
   1022             session.getMasterSecret());
   1023 
   1024         if (!verified) {
   1025             fatalSE(Alerts.alert_illegal_parameter,
   1026                        "server 'finished' message doesn't verify");
   1027             // NOTREACHED
   1028         }
   1029 
   1030         /*
   1031          * save server verify data for secure renegotiation
   1032          */
   1033         if (secureRenegotiation) {
   1034             serverVerifyData = mesg.getVerifyData();
   1035         }
   1036 
   1037         /*
   1038          * OK, it verified.  If we're doing the fast handshake, add that
   1039          * "Finished" message to the hash of handshake messages, then send
   1040          * our own change_cipher_spec and Finished message for the server
   1041          * to verify in turn.  These are the last handshake messages.
   1042          *
   1043          * In any case, update the session cache.  We're done handshaking,
   1044          * so there are no threats any more associated with partially
   1045          * completed handshakes.
   1046          */
   1047         if (resumingSession) {
   1048             input.digestNow();
   1049             sendChangeCipherAndFinish(true);
   1050         }
   1051         session.setLastAccessedTime(System.currentTimeMillis());
   1052 
   1053         if (!resumingSession) {
   1054             if (session.isRejoinable()) {
   1055                 ((SSLSessionContextImpl) sslContext
   1056                         .engineGetClientSessionContext())
   1057                         .put(session);
   1058                 if (debug != null && Debug.isOn("session")) {
   1059                     System.out.println("%% Cached client session: " + session);
   1060                 }
   1061             } else if (debug != null && Debug.isOn("session")) {
   1062                 System.out.println(
   1063                     "%% Didn't cache non-resumable client session: "
   1064                     + session);
   1065             }
   1066         }
   1067     }
   1068 
   1069 
   1070     /*
   1071      * Send my change-cipher-spec and Finished message ... done as the
   1072      * last handshake act in either the short or long sequences.  In
   1073      * the short one, we've already seen the server's Finished; in the
   1074      * long one, we wait for it now.
   1075      */
   1076     private void sendChangeCipherAndFinish(boolean finishedTag)
   1077             throws IOException {
   1078         Finished mesg = new Finished(protocolVersion, handshakeHash,
   1079             Finished.CLIENT, session.getMasterSecret(), cipherSuite);
   1080 
   1081         /*
   1082          * Send the change_cipher_spec message, then the Finished message
   1083          * which we just calculated (and protected using the keys we just
   1084          * calculated).  Server responds with its Finished message, except
   1085          * in the "fast handshake" (resume session) case.
   1086          */
   1087         sendChangeCipherSpec(mesg, finishedTag);
   1088 
   1089         /*
   1090          * save client verify data for secure renegotiation
   1091          */
   1092         if (secureRenegotiation) {
   1093             clientVerifyData = mesg.getVerifyData();
   1094         }
   1095 
   1096         /*
   1097          * Update state machine so server MUST send 'finished' next.
   1098          * (In "long" handshake case; in short case, we're responding
   1099          * to its message.)
   1100          */
   1101         state = HandshakeMessage.ht_finished - 1;
   1102     }
   1103 
   1104 
   1105     /*
   1106      * Returns a ClientHello message to kickstart renegotiations
   1107      */
   1108     HandshakeMessage getKickstartMessage() throws SSLException {
   1109         // session ID of the ClientHello message
   1110         SessionId sessionId = SSLSessionImpl.nullSession.getSessionId();
   1111 
   1112         // a list of cipher suites sent by the client
   1113         CipherSuiteList cipherSuites = getActiveCipherSuites();
   1114 
   1115         // set the max protocol version this client is supporting.
   1116         maxProtocolVersion = protocolVersion;
   1117 
   1118         //
   1119         // Try to resume an existing session.  This might be mandatory,
   1120         // given certain API options.
   1121         //
   1122         session = ((SSLSessionContextImpl)sslContext
   1123                         .engineGetClientSessionContext())
   1124                         .get(getHostSE(), getPortSE());
   1125         if (debug != null && Debug.isOn("session")) {
   1126             if (session != null) {
   1127                 System.out.println("%% Client cached "
   1128                     + session
   1129                     + (session.isRejoinable() ? "" : " (not rejoinable)"));
   1130             } else {
   1131                 System.out.println("%% No cached client session");
   1132             }
   1133         }
   1134         if ((session != null) && (session.isRejoinable() == false)) {
   1135             session = null;
   1136         }
   1137 
   1138         if (session != null) {
   1139             CipherSuite sessionSuite = session.getSuite();
   1140             ProtocolVersion sessionVersion = session.getProtocolVersion();
   1141             if (isNegotiable(sessionSuite) == false) {
   1142                 if (debug != null && Debug.isOn("session")) {
   1143                     System.out.println("%% can't resume, unavailable cipher");
   1144                 }
   1145                 session = null;
   1146             }
   1147 
   1148             if ((session != null) && !isNegotiable(sessionVersion)) {
   1149                 if (debug != null && Debug.isOn("session")) {
   1150                     System.out.println("%% can't resume, protocol disabled");
   1151                 }
   1152                 session = null;
   1153             }
   1154 
   1155             if (session != null) {
   1156                 if (debug != null) {
   1157                     if (Debug.isOn("handshake") || Debug.isOn("session")) {
   1158                         System.out.println("%% Try resuming " + session
   1159                             + " from port " + getLocalPortSE());
   1160                     }
   1161                 }
   1162 
   1163                 sessionId = session.getSessionId();
   1164                 maxProtocolVersion = sessionVersion;
   1165 
   1166                 // Update SSL version number in underlying SSL socket and
   1167                 // handshake output stream, so that the output records (at the
   1168                 // record layer) have the correct version
   1169                 setVersion(sessionVersion);
   1170             }
   1171 
   1172             /*
   1173              * Force use of the previous session ciphersuite, and
   1174              * add the SCSV if enabled.
   1175              */
   1176             if (!enableNewSession) {
   1177                 if (session == null) {
   1178                     throw new SSLHandshakeException(
   1179                         "Can't reuse existing SSL client session");
   1180                 }
   1181 
   1182                 Collection<CipherSuite> cipherList = new ArrayList<>(2);
   1183                 cipherList.add(sessionSuite);
   1184                 if (!secureRenegotiation &&
   1185                         cipherSuites.contains(CipherSuite.C_SCSV)) {
   1186                     cipherList.add(CipherSuite.C_SCSV);
   1187                 }   // otherwise, renegotiation_info extension will be used
   1188 
   1189                 cipherSuites = new CipherSuiteList(cipherList);
   1190             }
   1191         }
   1192 
   1193         if (session == null && !enableNewSession) {
   1194             throw new SSLHandshakeException("No existing session to resume");
   1195         }
   1196 
   1197         // exclude SCSV for secure renegotiation
   1198         if (secureRenegotiation && cipherSuites.contains(CipherSuite.C_SCSV)) {
   1199             Collection<CipherSuite> cipherList =
   1200                         new ArrayList<>(cipherSuites.size() - 1);
   1201             for (CipherSuite suite : cipherSuites.collection()) {
   1202                 if (suite != CipherSuite.C_SCSV) {
   1203                     cipherList.add(suite);
   1204                 }
   1205             }
   1206 
   1207             cipherSuites = new CipherSuiteList(cipherList);
   1208         }
   1209 
   1210         // make sure there is a negotiable cipher suite.
   1211         boolean negotiable = false;
   1212         for (CipherSuite suite : cipherSuites.collection()) {
   1213             if (isNegotiable(suite)) {
   1214                 negotiable = true;
   1215                 break;
   1216             }
   1217         }
   1218 
   1219         if (!negotiable) {
   1220             throw new SSLHandshakeException("No negotiable cipher suite");
   1221         }
   1222 
   1223         // Not a TLS1.2+ handshake
   1224         // For SSLv2Hello, HandshakeHash.reset() will be called, so we
   1225         // cannot call HandshakeHash.protocolDetermined() here. As it does
   1226         // not follow the spec that HandshakeHash.reset() can be only be
   1227         // called before protocolDetermined.
   1228         // if (maxProtocolVersion.v < ProtocolVersion.TLS12.v) {
   1229         //     handshakeHash.protocolDetermined(maxProtocolVersion);
   1230         // }
   1231 
   1232         // create the ClientHello message
   1233         ClientHello clientHelloMessage = new ClientHello(
   1234                 sslContext.getSecureRandom(), maxProtocolVersion,
   1235                 sessionId, cipherSuites);
   1236 
   1237         // add signature_algorithm extension
   1238         if (maxProtocolVersion.v >= ProtocolVersion.TLS12.v) {
   1239             // we will always send the signature_algorithm extension
   1240             Collection<SignatureAndHashAlgorithm> localSignAlgs =
   1241                                                 getLocalSupportedSignAlgs();
   1242             if (localSignAlgs.isEmpty()) {
   1243                 throw new SSLHandshakeException(
   1244                             "No supported signature algorithm");
   1245             }
   1246 
   1247             clientHelloMessage.addSignatureAlgorithmsExtension(localSignAlgs);
   1248         }
   1249 
   1250         // add server_name extension
   1251         if (enableSNIExtension) {
   1252             // We cannot use the hostname resolved from name services.  For
   1253             // virtual hosting, multiple hostnames may be bound to the same IP
   1254             // address, so the hostname resolved from name services is not
   1255             // reliable.
   1256             String hostname = getRawHostnameSE();
   1257 
   1258             // we only allow FQDN
   1259             if (hostname != null && hostname.indexOf('.') > 0 &&
   1260                     !IPAddressUtil.isIPv4LiteralAddress(hostname) &&
   1261                     !IPAddressUtil.isIPv6LiteralAddress(hostname)) {
   1262                 clientHelloMessage.addServerNameIndicationExtension(hostname);
   1263             }
   1264         }
   1265 
   1266         // reset the client random cookie
   1267         clnt_random = clientHelloMessage.clnt_random;
   1268 
   1269         /*
   1270          * need to set the renegotiation_info extension for:
   1271          * 1: secure renegotiation
   1272          * 2: initial handshake and no SCSV in the ClientHello
   1273          * 3: insecure renegotiation and no SCSV in the ClientHello
   1274          */
   1275         if (secureRenegotiation ||
   1276                 !cipherSuites.contains(CipherSuite.C_SCSV)) {
   1277             clientHelloMessage.addRenegotiationInfoExtension(clientVerifyData);
   1278         }
   1279 
   1280         return clientHelloMessage;
   1281     }
   1282 
   1283     /*
   1284      * Fault detected during handshake.
   1285      */
   1286     void handshakeAlert(byte description) throws SSLProtocolException {
   1287         String message = Alerts.alertDescription(description);
   1288 
   1289         if (debug != null && Debug.isOn("handshake")) {
   1290             System.out.println("SSL - handshake alert: " + message);
   1291         }
   1292         throw new SSLProtocolException("handshake alert:  " + message);
   1293     }
   1294 
   1295     /*
   1296      * Unless we are using an anonymous ciphersuite, the server always
   1297      * sends a certificate message (for the CipherSuites we currently
   1298      * support). The trust manager verifies the chain for us.
   1299      */
   1300     private void serverCertificate(CertificateMsg mesg) throws IOException {
   1301         if (debug != null && Debug.isOn("handshake")) {
   1302             mesg.print(System.out);
   1303         }
   1304         X509Certificate[] peerCerts = mesg.getCertificateChain();
   1305         if (peerCerts.length == 0) {
   1306             fatalSE(Alerts.alert_bad_certificate,
   1307                 "empty certificate chain");
   1308         }
   1309         // ask the trust manager to verify the chain
   1310         X509TrustManager tm = sslContext.getX509TrustManager();
   1311         try {
   1312             // find out the key exchange algorithm used
   1313             // use "RSA" for non-ephemeral "RSA_EXPORT"
   1314             String keyExchangeString;
   1315             if (keyExchange == K_RSA_EXPORT && !serverKeyExchangeReceived) {
   1316                 keyExchangeString = K_RSA.name;
   1317             } else {
   1318                 keyExchangeString = keyExchange.name;
   1319             }
   1320 
   1321             if (tm instanceof X509ExtendedTrustManager) {
   1322                 if (conn != null) {
   1323                     ((X509ExtendedTrustManager)tm).checkServerTrusted(
   1324                         peerCerts.clone(),
   1325                         keyExchangeString,
   1326                         conn);
   1327                 } else {
   1328                     ((X509ExtendedTrustManager)tm).checkServerTrusted(
   1329                         peerCerts.clone(),
   1330                         keyExchangeString,
   1331                         engine);
   1332                 }
   1333             } else {
   1334                 // Unlikely to happen, because we have wrapped the old
   1335                 // X509TrustManager with the new X509ExtendedTrustManager.
   1336                 throw new CertificateException(
   1337                     "Improper X509TrustManager implementation");
   1338             }
   1339         } catch (CertificateException e) {
   1340             // This will throw an exception, so include the original error.
   1341             fatalSE(Alerts.alert_certificate_unknown, e);
   1342         }
   1343         session.setPeerCertificates(peerCerts);
   1344     }
   1345 }
   1346