src/java.base/share/classes/sun/security/ssl/SSLContextImpl.java
branchJDK-8145252-TLS13-branch
changeset 56542 56aaa6cb3693
parent 47216 71c04702a3d5
child 56611 f8f7e604e1f8
equal deleted inserted replaced
56541:92cbbfc996f3 56542:56aaa6cb3693
     1 /*
     1 /*
     2  * Copyright (c) 1999, 2017, Oracle and/or its affiliates. All rights reserved.
     2  * Copyright (c) 1999, 2018, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     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
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.  Oracle designates this
     7  * published by the Free Software Foundation.  Oracle designates this
    23  * questions.
    23  * questions.
    24  */
    24  */
    25 
    25 
    26 package sun.security.ssl;
    26 package sun.security.ssl;
    27 
    27 
       
    28 import java.io.*;
    28 import java.net.Socket;
    29 import java.net.Socket;
    29 
       
    30 import java.io.*;
       
    31 import java.util.*;
       
    32 import java.security.*;
    30 import java.security.*;
    33 import java.security.cert.*;
    31 import java.security.cert.*;
    34 import java.security.cert.Certificate;
    32 import java.util.*;
    35 
       
    36 import javax.net.ssl.*;
    33 import javax.net.ssl.*;
    37 
    34 import sun.security.action.GetPropertyAction;
    38 import sun.security.provider.certpath.AlgorithmChecker;
    35 import sun.security.provider.certpath.AlgorithmChecker;
    39 import sun.security.action.GetPropertyAction;
       
    40 import sun.security.validator.Validator;
    36 import sun.security.validator.Validator;
    41 
    37 
       
    38 /**
       
    39  * Implementation of an SSLContext.
       
    40  *
       
    41  * Instances of this class are immutable after the context is initialized.
       
    42  */
       
    43 
    42 public abstract class SSLContextImpl extends SSLContextSpi {
    44 public abstract class SSLContextImpl extends SSLContextSpi {
    43 
       
    44     private static final Debug debug = Debug.getInstance("ssl");
       
    45 
    45 
    46     private final EphemeralKeyManager ephemeralKeyManager;
    46     private final EphemeralKeyManager ephemeralKeyManager;
    47     private final SSLSessionContextImpl clientCache;
    47     private final SSLSessionContextImpl clientCache;
    48     private final SSLSessionContextImpl serverCache;
    48     private final SSLSessionContextImpl serverCache;
    49 
    49 
    54     private SecureRandom secureRandom;
    54     private SecureRandom secureRandom;
    55 
    55 
    56     // DTLS cookie exchange manager
    56     // DTLS cookie exchange manager
    57     private volatile HelloCookieManager helloCookieManager;
    57     private volatile HelloCookieManager helloCookieManager;
    58 
    58 
    59     private final boolean clientEnableStapling = Debug.getBooleanProperty(
    59     private final boolean clientEnableStapling = Utilities.getBooleanProperty(
    60             "jdk.tls.client.enableStatusRequestExtension", true);
    60             "jdk.tls.client.enableStatusRequestExtension", true);
    61     private final boolean serverEnableStapling = Debug.getBooleanProperty(
    61     private final boolean serverEnableStapling = Utilities.getBooleanProperty(
    62             "jdk.tls.server.enableStatusRequestExtension", false);
    62             "jdk.tls.server.enableStatusRequestExtension", false);
    63     private final static Collection<CipherSuite> clientCustomizedCipherSuites =
    63     private static final Collection<CipherSuite> clientCustomizedCipherSuites =
    64             getCustomizedCipherSuites("jdk.tls.client.cipherSuites");
    64             getCustomizedCipherSuites("jdk.tls.client.cipherSuites");
    65     private final static Collection<CipherSuite> serverCustomizedCipherSuites =
    65     private static final Collection<CipherSuite> serverCustomizedCipherSuites =
    66             getCustomizedCipherSuites("jdk.tls.server.cipherSuites");
    66             getCustomizedCipherSuites("jdk.tls.server.cipherSuites");
    67 
    67 
    68     private volatile StatusResponseManager statusResponseManager;
    68     private volatile StatusResponseManager statusResponseManager;
    69 
    69 
    70     SSLContextImpl() {
    70     SSLContextImpl() {
   107          * The initial delay of seeding the random number generator
   107          * The initial delay of seeding the random number generator
   108          * could be long enough to cause the initial handshake on our
   108          * could be long enough to cause the initial handshake on our
   109          * first connection to timeout and fail. Make sure it is
   109          * first connection to timeout and fail. Make sure it is
   110          * primed and ready by getting some initial output from it.
   110          * primed and ready by getting some initial output from it.
   111          */
   111          */
   112         if (debug != null && Debug.isOn("sslctx")) {
   112         if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   113             System.out.println("trigger seeding of SecureRandom");
   113             SSLLogger.finest("trigger seeding of SecureRandom");
   114         }
   114         }
   115         secureRandom.nextInt();
   115         secureRandom.nextInt();
   116         if (debug != null && Debug.isOn("sslctx")) {
   116         if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   117             System.out.println("done seeding SecureRandom");
   117             SSLLogger.finest("done seeding of SecureRandom");
   118         }
   118         }
   119 
   119 
   120         isInitialized = true;
   120         isInitialized = true;
   121     }
   121     }
   122 
   122 
   166                 }
   166                 }
   167             }
   167             }
   168             if (km instanceof X509ExtendedKeyManager) {
   168             if (km instanceof X509ExtendedKeyManager) {
   169                 return (X509ExtendedKeyManager)km;
   169                 return (X509ExtendedKeyManager)km;
   170             }
   170             }
   171             if (debug != null && Debug.isOn("sslctx")) {
   171 
   172                 System.out.println(
   172             if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   173                     "X509KeyManager passed to " +
   173                 SSLLogger.warning(
   174                     "SSLContext.init():  need an " +
   174                     "X509KeyManager passed to SSLContext.init():  need an " +
   175                     "X509ExtendedKeyManager for SSLEngine use");
   175                     "X509ExtendedKeyManager for SSLEngine use");
   176             }
   176             }
   177             return new AbstractKeyManagerWrapper((X509KeyManager)km);
   177             return new AbstractKeyManagerWrapper((X509KeyManager)km);
   178         }
   178         }
   179 
   179 
   240 
   240 
   241     EphemeralKeyManager getEphemeralKeyManager() {
   241     EphemeralKeyManager getEphemeralKeyManager() {
   242         return ephemeralKeyManager;
   242         return ephemeralKeyManager;
   243     }
   243     }
   244 
   244 
   245     // Used for DTLS in server mode only, see ServerHandshaker.
   245     // Used for DTLS in server mode only.
   246     HelloCookieManager getHelloCookieManager() {
   246     HelloCookieManager getHelloCookieManager(ProtocolVersion protocolVersion) {
   247         if (!isInitialized) {
       
   248             throw new IllegalStateException("SSLContext is not initialized");
       
   249         }
       
   250 
       
   251         if (helloCookieManager != null) {
   247         if (helloCookieManager != null) {
   252             return helloCookieManager;
   248             return helloCookieManager.valueOf(protocolVersion);
   253         }
   249         }
   254 
   250 
   255         synchronized (this) {
   251         synchronized (this) {
   256             if (helloCookieManager == null) {
   252             if (helloCookieManager == null) {
   257                 helloCookieManager = getHelloCookieManager(secureRandom);
   253                 helloCookieManager = new HelloCookieManager(secureRandom);
   258             }
   254             }
   259         }
   255         }
   260 
   256 
   261         return helloCookieManager;
   257         return helloCookieManager.valueOf(protocolVersion);
   262     }
       
   263 
       
   264     HelloCookieManager getHelloCookieManager(SecureRandom secureRandom) {
       
   265         throw new UnsupportedOperationException(
       
   266                 "Cookie exchange applies to DTLS only");
       
   267     }
   258     }
   268 
   259 
   269     StatusResponseManager getStatusResponseManager() {
   260     StatusResponseManager getStatusResponseManager() {
   270         if (serverEnableStapling && statusResponseManager == null) {
   261         if (serverEnableStapling && statusResponseManager == null) {
   271             synchronized (this) {
   262             synchronized (this) {
   272                 if (statusResponseManager == null) {
   263                 if (statusResponseManager == null) {
   273                     if (debug != null && Debug.isOn("sslctx")) {
   264                     if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   274                         System.out.println(
   265                         SSLLogger.finest(
   275                                 "Initializing StatusResponseManager");
   266                                 "Initializing StatusResponseManager");
   276                     }
   267                     }
   277                     statusResponseManager = new StatusResponseManager();
   268                     statusResponseManager = new StatusResponseManager();
   278                 }
   269                 }
   279             }
   270             }
   280         }
   271         }
   281 
   272 
   282         return statusResponseManager;
   273         return statusResponseManager;
   283     }
   274     }
   284 
   275 
   285     // Get supported ProtocolList.
   276     // Get supported protocols.
   286     abstract ProtocolList getSuportedProtocolList();
   277     abstract List<ProtocolVersion> getSuportedProtocolVersions();
   287 
   278 
   288     // Get default ProtocolList for server mode.
   279     // Get default protocols for server mode.
   289     abstract ProtocolList getServerDefaultProtocolList();
   280     abstract List<ProtocolVersion> getServerDefaultProtocolVersions();
   290 
   281 
   291     // Get default ProtocolList for client mode.
   282     // Get default protocols for client mode.
   292     abstract ProtocolList getClientDefaultProtocolList();
   283     abstract List<ProtocolVersion> getClientDefaultProtocolVersions();
   293 
   284 
   294     // Get supported CipherSuiteList.
   285     // Get supported CipherSuite list.
   295     abstract CipherSuiteList getSupportedCipherSuiteList();
   286     abstract List<CipherSuite> getSupportedCipherSuites();
   296 
   287 
   297     // Get default CipherSuiteList for server mode.
   288     // Get default CipherSuite list for server mode.
   298     abstract CipherSuiteList getServerDefaultCipherSuiteList();
   289     abstract List<CipherSuite> getServerDefaultCipherSuites();
   299 
   290 
   300     // Get default CipherSuiteList for client mode.
   291     // Get default CipherSuite list for client mode.
   301     abstract CipherSuiteList getClientDefaultCipherSuiteList();
   292     abstract List<CipherSuite> getClientDefaultCipherSuites();
   302 
   293 
   303     // Get default ProtocolList.
   294     // Is the context for DTLS protocols?
   304     ProtocolList getDefaultProtocolList(boolean roleIsServer) {
   295     abstract boolean isDTLS();
   305         return roleIsServer ? getServerDefaultProtocolList()
   296 
   306                             : getClientDefaultProtocolList();
   297     // Get default protocols.
   307     }
   298     List<ProtocolVersion> getDefaultProtocolVersions(boolean roleIsServer) {
   308 
   299         return roleIsServer ? getServerDefaultProtocolVersions()
   309     // Get default CipherSuiteList.
   300                             : getClientDefaultProtocolVersions();
   310     CipherSuiteList getDefaultCipherSuiteList(boolean roleIsServer) {
   301     }
   311         return roleIsServer ? getServerDefaultCipherSuiteList()
   302 
   312                             : getClientDefaultCipherSuiteList();
   303     // Get default CipherSuite list.
       
   304     List<CipherSuite> getDefaultCipherSuites(boolean roleIsServer) {
       
   305         return roleIsServer ? getServerDefaultCipherSuites()
       
   306                             : getClientDefaultCipherSuites();
   313     }
   307     }
   314 
   308 
   315     /**
   309     /**
   316      * Return whether a protocol list is the original default enabled
   310      * Return whether a protocol list is the original default enabled
   317      * protocols.  See: SSLSocket/SSLEngine.setEnabledProtocols()
   311      * protocols.  See: SSLSocket/SSLEngine.setEnabledProtocols()
   318      */
   312      */
   319     boolean isDefaultProtocolList(ProtocolList protocols) {
   313     boolean isDefaultProtocolVesions(List<ProtocolVersion> protocols) {
   320         return (protocols == getServerDefaultProtocolList()) ||
   314         return (protocols == getServerDefaultProtocolVersions()) ||
   321                (protocols == getClientDefaultProtocolList());
   315                (protocols == getClientDefaultProtocolVersions());
   322     }
   316     }
   323 
   317 
   324     /**
   318     /**
   325      * Return whether a protocol list is the original default enabled
   319      * Return whether a protocol list is the original default enabled
   326      * protocols.  See: SSLSocket/SSLEngine.setEnabledProtocols()
   320      * protocols.  See: SSLSocket/SSLEngine.setEnabledProtocols()
   327      */
   321      */
   328     boolean isDefaultCipherSuiteList(CipherSuiteList cipherSuites) {
   322     boolean isDefaultCipherSuiteList(List<CipherSuite> cipherSuites) {
   329         return (cipherSuites == getServerDefaultCipherSuiteList()) ||
   323         return (cipherSuites == getServerDefaultCipherSuites()) ||
   330                (cipherSuites == getClientDefaultCipherSuiteList());
   324                (cipherSuites == getClientDefaultCipherSuites());
   331     }
   325     }
   332 
   326 
   333     /**
   327     /**
   334      * Return whether client or server side stapling has been enabled
   328      * Return whether client or server side stapling has been enabled
   335      * for this SSLContextImpl
   329      * for this SSLContextImpl
   340      */
   334      */
   341     boolean isStaplingEnabled(boolean isClient) {
   335     boolean isStaplingEnabled(boolean isClient) {
   342         return isClient ? clientEnableStapling : serverEnableStapling;
   336         return isClient ? clientEnableStapling : serverEnableStapling;
   343     }
   337     }
   344 
   338 
   345 
       
   346     /*
   339     /*
   347      * Return the list of all available CipherSuites that are supported
   340      * Return the list of all available CipherSuites that are supported
   348      * using currently installed providers.
   341      * using currently installed providers.
   349      */
   342      */
   350     private static CipherSuiteList getApplicableSupportedCipherSuiteList(
   343     private static List<CipherSuite> getApplicableSupportedCipherSuites(
   351             ProtocolList protocols) {
   344             List<ProtocolVersion> protocols) {
   352 
   345 
   353         return getApplicableCipherSuiteList(
   346         return getApplicableCipherSuites(
   354                 CipherSuite.allowedCipherSuites(),
   347                 CipherSuite.allowedCipherSuites(), protocols);
   355                 protocols, CipherSuite.SUPPORTED_SUITES_PRIORITY);
       
   356     }
   348     }
   357 
   349 
   358     /*
   350     /*
   359      * Return the list of all available CipherSuites that are default enabled
   351      * Return the list of all available CipherSuites that are default enabled
   360      * in client or server side.
   352      * in client or server side.
   361      */
   353      */
   362     private static CipherSuiteList getApplicableEnabledCipherSuiteList(
   354     private static List<CipherSuite> getApplicableEnabledCipherSuites(
   363             ProtocolList protocols, boolean isClient) {
   355             List<ProtocolVersion> protocols, boolean isClient) {
   364 
   356 
   365         if (isClient) {
   357         if (isClient) {
   366             if (!clientCustomizedCipherSuites.isEmpty()) {
   358             if (!clientCustomizedCipherSuites.isEmpty()) {
   367                 return getApplicableCipherSuiteList(
   359                 return getApplicableCipherSuites(
   368                         clientCustomizedCipherSuites,
   360                         clientCustomizedCipherSuites, protocols);
   369                         protocols, CipherSuite.SUPPORTED_SUITES_PRIORITY);
       
   370             }
   361             }
   371         } else {
   362         } else {
   372             if (!serverCustomizedCipherSuites.isEmpty()) {
   363             if (!serverCustomizedCipherSuites.isEmpty()) {
   373                 return getApplicableCipherSuiteList(
   364                 return getApplicableCipherSuites(
   374                         serverCustomizedCipherSuites,
   365                         serverCustomizedCipherSuites, protocols);
   375                         protocols, CipherSuite.SUPPORTED_SUITES_PRIORITY);
   366             }
   376             }
   367         }
   377         }
   368 
   378 
   369         return getApplicableCipherSuites(
   379         return getApplicableCipherSuiteList(
   370                 CipherSuite.defaultCipherSuites(), protocols);
   380                 CipherSuite.allowedCipherSuites(),
       
   381                 protocols, CipherSuite.DEFAULT_SUITES_PRIORITY);
       
   382     }
   371     }
   383 
   372 
   384     /*
   373     /*
   385      * Return the list of available CipherSuites which are applicable to
   374      * Return the list of available CipherSuites which are applicable to
   386      * the specified protocols.
   375      * the specified protocols.
   387      */
   376      */
   388     private static CipherSuiteList getApplicableCipherSuiteList(
   377     private static List<CipherSuite> getApplicableCipherSuites(
   389             Collection<CipherSuite> allowedCipherSuites,
   378             Collection<CipherSuite> allowedCipherSuites,
   390             ProtocolList protocols, int minPriority) {
   379             List<ProtocolVersion> protocols) {
   391 
       
   392         TreeSet<CipherSuite> suites = new TreeSet<>();
   380         TreeSet<CipherSuite> suites = new TreeSet<>();
   393         if (!(protocols.collection().isEmpty()) &&
   381         if (protocols != null && (!protocols.isEmpty())) {
   394                 protocols.min.v != ProtocolVersion.NONE.v) {
       
   395             for (CipherSuite suite : allowedCipherSuites) {
   382             for (CipherSuite suite : allowedCipherSuites) {
   396                 if (!suite.allowed || suite.priority < minPriority) {
   383                 if (!suite.isAvailable()) {
   397                     continue;
   384                     continue;
   398                 }
   385                 }
   399 
   386 
   400                 if (suite.isAvailable() &&
   387                 boolean isSupported = false;
   401                         !protocols.min.obsoletes(suite) &&
   388                 for (ProtocolVersion protocol : protocols) {
   402                         protocols.max.supports(suite)) {
   389                     if (!suite.supports(protocol)) {
       
   390                         continue;
       
   391                     }
       
   392 
   403                     if (SSLAlgorithmConstraints.DEFAULT.permits(
   393                     if (SSLAlgorithmConstraints.DEFAULT.permits(
   404                             EnumSet.of(CryptoPrimitive.KEY_AGREEMENT),
   394                             EnumSet.of(CryptoPrimitive.KEY_AGREEMENT),
   405                             suite.name, null)) {
   395                             suite.name, null)) {
   406                         suites.add(suite);
   396                         suites.add(suite);
   407                     } else {
   397                         isSupported = true;
   408                         if (debug != null && Debug.isOn("sslctx") &&
   398                     } else if (SSLLogger.isOn &&
   409                                 Debug.isOn("verbose")) {
   399                             SSLLogger.isOn("ssl,sslctx,verbose")) {
   410                             System.out.println(
   400                         SSLLogger.fine(
   411                                     "Ignoring disabled cipher suite: " +
   401                                 "Ignore disabled cipher suite: " + suite.name);
   412                                             suite.name);
       
   413                         }
       
   414                     }
   402                     }
   415                 } else if (debug != null &&
   403 
   416                         Debug.isOn("sslctx") && Debug.isOn("verbose")) {
   404                     break;
   417                     if (protocols.min.obsoletes(suite)) {
   405                 }
   418                         System.out.println(
   406 
   419                             "Ignoring obsoleted cipher suite: " + suite);
   407                 if (!isSupported && SSLLogger.isOn &&
   420                     } else if (!protocols.max.supports(suite)) {
   408                         SSLLogger.isOn("ssl,sslctx,verbose")) {
   421                         System.out.println(
   409                     SSLLogger.finest(
   422                             "Ignoring unsupported cipher suite: " + suite);
   410                             "Ignore unsupported cipher suite: " + suite);
   423                     } else {
   411                 }
   424                         System.out.println(
   412             }
   425                             "Ignoring unavailable cipher suite: " + suite);
   413         }
   426                     }
   414 
   427                 }
   415         return Arrays.asList(suites.toArray(new CipherSuite[0]));
   428             }
       
   429         }
       
   430 
       
   431         return new CipherSuiteList(suites);
       
   432     }
   416     }
   433 
   417 
   434     /*
   418     /*
   435      * Get the customized cipher suites specified by the given system property.
   419      * Get the customized cipher suites specified by the given system property.
   436      */
   420      */
   437     private static Collection<CipherSuite> getCustomizedCipherSuites(
   421     private static Collection<CipherSuite> getCustomizedCipherSuites(
   438             String propertyName) {
   422             String propertyName) {
   439 
   423 
   440         String property = GetPropertyAction.privilegedGetProperty(propertyName);
   424         String property = GetPropertyAction.privilegedGetProperty(propertyName);
   441         if (debug != null && Debug.isOn("sslctx")) {
   425         if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   442             System.out.println(
   426             SSLLogger.fine(
   443                     "System property " + propertyName + " is set to '" +
   427                     "System property " + propertyName + " is set to '" +
   444                     property + "'");
   428                     property + "'");
   445         }
   429         }
   446         if (property != null && property.length() != 0) {
   430         if (property != null && property.length() != 0) {
   447             // remove double quote marks from beginning/end of the property
   431             // remove double quote marks from beginning/end of the property
   461                     continue;
   445                     continue;
   462                 }
   446                 }
   463 
   447 
   464                 CipherSuite suite;
   448                 CipherSuite suite;
   465                 try {
   449                 try {
   466                     suite = CipherSuite.valueOf(cipherSuiteNames[i]);
   450                     suite = CipherSuite.nameOf(cipherSuiteNames[i]);
   467                 } catch (IllegalArgumentException iae) {
   451                 } catch (IllegalArgumentException iae) {
   468                     if (debug != null && Debug.isOn("sslctx")) {
   452                     if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   469                         System.out.println(
   453                         SSLLogger.fine(
   470                                 "Unknown or unsupported cipher suite name: " +
   454                                 "Unknown or unsupported cipher suite name: " +
   471                                 cipherSuiteNames[i]);
   455                                 cipherSuiteNames[i]);
   472                     }
   456                     }
   473 
   457 
   474                     continue;
   458                     continue;
   475                 }
   459                 }
   476 
   460 
   477                 if (suite.isAvailable()) {
   461                 if (suite != null && suite.isAvailable()) {
   478                     cipherSuites.add(suite);
   462                     cipherSuites.add(suite);
   479                 } else {
   463                 } else {
   480                     if (debug != null && Debug.isOn("sslctx")) {
   464                     if (SSLLogger.isOn && SSLLogger.isOn("ssl,sslctx")) {
   481                         System.out.println(
   465                         SSLLogger.fine(
   482                                 "The current installed providers do not " +
   466                                 "The current installed providers do not " +
   483                                 "support cipher suite: " + cipherSuiteNames[i]);
   467                                 "support cipher suite: " + cipherSuiteNames[i]);
   484                     }
   468                     }
   485                 }
   469                 }
   486             }
   470             }
   490 
   474 
   491         return Collections.emptyList();
   475         return Collections.emptyList();
   492     }
   476     }
   493 
   477 
   494 
   478 
   495     private static String[] getAvailableProtocols(
   479     private static List<ProtocolVersion> getAvailableProtocols(
   496             ProtocolVersion[] protocolCandidates) {
   480             ProtocolVersion[] protocolCandidates) {
   497 
   481 
   498         List<String> availableProtocols = Collections.<String>emptyList();
   482         List<ProtocolVersion> availableProtocols =
       
   483                 Collections.<ProtocolVersion>emptyList();
   499         if (protocolCandidates !=  null && protocolCandidates.length != 0) {
   484         if (protocolCandidates !=  null && protocolCandidates.length != 0) {
   500             availableProtocols = new ArrayList<>(protocolCandidates.length);
   485             availableProtocols = new ArrayList<>(protocolCandidates.length);
   501             for (ProtocolVersion p : protocolCandidates) {
   486             for (ProtocolVersion p : protocolCandidates) {
   502                 if (ProtocolVersion.availableProtocols.contains(p)) {
   487                 if (p.isAvailable) {
   503                     availableProtocols.add(p.name);
   488                     availableProtocols.add(p);
   504                 }
   489                 }
   505             }
   490             }
   506         }
   491         }
   507 
   492 
   508         return availableProtocols.toArray(new String[0]);
   493         return availableProtocols;
   509     }
   494     }
   510 
       
   511 
   495 
   512     /*
   496     /*
   513      * The SSLContext implementation for SSL/(D)TLS algorithm
   497      * The SSLContext implementation for SSL/(D)TLS algorithm
   514      *
   498      *
   515      * SSL/TLS protocols specify the forward compatibility and version
   499      * SSL/TLS protocols specify the forward compatibility and version
   546      * SSL/TLS parameters.
   530      * SSL/TLS parameters.
   547      *
   531      *
   548      * @see SSLContext
   532      * @see SSLContext
   549      */
   533      */
   550     private abstract static class AbstractTLSContext extends SSLContextImpl {
   534     private abstract static class AbstractTLSContext extends SSLContextImpl {
   551         private static final ProtocolList supportedProtocolList;
   535         private static final List<ProtocolVersion> supportedProtocols;
   552         private static final ProtocolList serverDefaultProtocolList;
   536         private static final List<ProtocolVersion> serverDefaultProtocols;
   553 
   537 
   554         private static final CipherSuiteList supportedCipherSuiteList;
   538         private static final List<CipherSuite> supportedCipherSuites;
   555         private static final CipherSuiteList serverDefaultCipherSuiteList;
   539         private static final List<CipherSuite> serverDefaultCipherSuites;
   556 
   540 
   557         static {
   541         static {
   558             if (SunJSSE.isFIPS()) {
   542             if (SunJSSE.isFIPS()) {
   559                 supportedProtocolList = new ProtocolList(new String[] {
   543                 supportedProtocols = Arrays.asList(
   560                     ProtocolVersion.TLS10.name,
   544                     ProtocolVersion.TLS13,
   561                     ProtocolVersion.TLS11.name,
   545                     ProtocolVersion.TLS12,
   562                     ProtocolVersion.TLS12.name
   546                     ProtocolVersion.TLS11,
       
   547                     ProtocolVersion.TLS10
       
   548                 );
       
   549 
       
   550                 serverDefaultProtocols = getAvailableProtocols(
       
   551                         new ProtocolVersion[] {
       
   552                     ProtocolVersion.TLS13,
       
   553                     ProtocolVersion.TLS12,
       
   554                     ProtocolVersion.TLS11,
       
   555                     ProtocolVersion.TLS10
   563                 });
   556                 });
   564 
   557             } else {
   565                 serverDefaultProtocolList = new ProtocolList(
   558                 supportedProtocols = Arrays.asList(
   566                         getAvailableProtocols(new ProtocolVersion[] {
   559                     ProtocolVersion.TLS13,
       
   560                     ProtocolVersion.TLS12,
       
   561                     ProtocolVersion.TLS11,
   567                     ProtocolVersion.TLS10,
   562                     ProtocolVersion.TLS10,
       
   563                     ProtocolVersion.SSL30,
       
   564                     ProtocolVersion.SSL20Hello
       
   565                 );
       
   566 
       
   567                 serverDefaultProtocols = getAvailableProtocols(
       
   568                         new ProtocolVersion[] {
       
   569                     ProtocolVersion.TLS13,
       
   570                     ProtocolVersion.TLS12,
   568                     ProtocolVersion.TLS11,
   571                     ProtocolVersion.TLS11,
   569                     ProtocolVersion.TLS12
   572                     ProtocolVersion.TLS10,
   570                 }));
   573                     ProtocolVersion.SSL30,
   571             } else {
   574                     ProtocolVersion.SSL20Hello
   572                 supportedProtocolList = new ProtocolList(new String[] {
       
   573                     ProtocolVersion.SSL20Hello.name,
       
   574                     ProtocolVersion.SSL30.name,
       
   575                     ProtocolVersion.TLS10.name,
       
   576                     ProtocolVersion.TLS11.name,
       
   577                     ProtocolVersion.TLS12.name
       
   578                 });
   575                 });
   579 
   576             }
   580                 serverDefaultProtocolList = new ProtocolList(
   577 
   581                         getAvailableProtocols(new ProtocolVersion[] {
   578             supportedCipherSuites = getApplicableSupportedCipherSuites(
   582                     ProtocolVersion.SSL20Hello,
   579                     supportedProtocols);
   583                     ProtocolVersion.SSL30,
   580             serverDefaultCipherSuites = getApplicableEnabledCipherSuites(
   584                     ProtocolVersion.TLS10,
   581                     serverDefaultProtocols, false);
   585                     ProtocolVersion.TLS11,
   582         }
   586                     ProtocolVersion.TLS12
   583 
   587                 }));
   584         @Override
   588             }
   585         List<ProtocolVersion> getSuportedProtocolVersions() {
   589 
   586             return supportedProtocols;
   590             supportedCipherSuiteList = getApplicableSupportedCipherSuiteList(
   587         }
   591                     supportedProtocolList);
   588 
   592             serverDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
   589         @Override
   593                     serverDefaultProtocolList, false);
   590         List<CipherSuite> getSupportedCipherSuites() {
   594         }
   591             return supportedCipherSuites;
   595 
   592         }
   596         @Override
   593 
   597         ProtocolList getSuportedProtocolList() {
   594         @Override
   598             return supportedProtocolList;
   595         List<ProtocolVersion> getServerDefaultProtocolVersions() {
   599         }
   596             return serverDefaultProtocols;
   600 
   597         }
   601         @Override
   598 
   602         CipherSuiteList getSupportedCipherSuiteList() {
   599         @Override
   603             return supportedCipherSuiteList;
   600         List<CipherSuite> getServerDefaultCipherSuites() {
   604         }
   601             return serverDefaultCipherSuites;
   605 
       
   606         @Override
       
   607         ProtocolList getServerDefaultProtocolList() {
       
   608             return serverDefaultProtocolList;
       
   609         }
       
   610 
       
   611         @Override
       
   612         CipherSuiteList getServerDefaultCipherSuiteList() {
       
   613             return serverDefaultCipherSuiteList;
       
   614         }
   602         }
   615 
   603 
   616         @Override
   604         @Override
   617         SSLEngine createSSLEngineImpl() {
   605         SSLEngine createSSLEngineImpl() {
   618             return new SSLEngineImpl(this, false);
   606             return new SSLEngineImpl(this);
   619         }
   607         }
   620 
   608 
   621         @Override
   609         @Override
   622         SSLEngine createSSLEngineImpl(String host, int port) {
   610         SSLEngine createSSLEngineImpl(String host, int port) {
   623             return new SSLEngineImpl(this, host, port, false);
   611             return new SSLEngineImpl(this, host, port);
       
   612         }
       
   613 
       
   614         @Override
       
   615         boolean isDTLS() {
       
   616             return false;
   624         }
   617         }
   625     }
   618     }
   626 
   619 
   627     /*
   620     /*
   628      * The SSLContext implementation for SSLv3 and TLS10 algorithm
   621      * The SSLContext implementation for SSLv3 and TLS10 algorithm
   629      *
   622      *
   630      * @see SSLContext
   623      * @see SSLContext
   631      */
   624      */
   632     public static final class TLS10Context extends AbstractTLSContext {
   625     public static final class TLS10Context extends AbstractTLSContext {
   633         private static final ProtocolList clientDefaultProtocolList;
   626         private static final List<ProtocolVersion> clientDefaultProtocols;
   634         private static final CipherSuiteList clientDefaultCipherSuiteList;
   627         private static final List<CipherSuite> clientDefaultCipherSuites;
   635 
   628 
   636         static {
   629         static {
   637             if (SunJSSE.isFIPS()) {
   630             if (SunJSSE.isFIPS()) {
   638                 clientDefaultProtocolList = new ProtocolList(
   631                 clientDefaultProtocols = getAvailableProtocols(
   639                         getAvailableProtocols(new ProtocolVersion[] {
   632                         new ProtocolVersion[] {
   640                     ProtocolVersion.TLS10
   633                     ProtocolVersion.TLS10
   641                 }));
   634                 });
   642             } else {
   635             } else {
   643                 clientDefaultProtocolList = new ProtocolList(
   636                 clientDefaultProtocols = getAvailableProtocols(
   644                         getAvailableProtocols(new ProtocolVersion[] {
   637                         new ProtocolVersion[] {
   645                     ProtocolVersion.SSL30,
   638                     ProtocolVersion.TLS10,
   646                     ProtocolVersion.TLS10
   639                     ProtocolVersion.SSL30
   647                 }));
   640                 });
   648             }
   641             }
   649 
   642 
   650             clientDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
   643             clientDefaultCipherSuites = getApplicableEnabledCipherSuites(
   651                     clientDefaultProtocolList, true);
   644                     clientDefaultProtocols, true);
   652         }
   645         }
   653 
   646 
   654         @Override
   647         @Override
   655         ProtocolList getClientDefaultProtocolList() {
   648         List<ProtocolVersion> getClientDefaultProtocolVersions() {
   656             return clientDefaultProtocolList;
   649             return clientDefaultProtocols;
   657         }
   650         }
   658 
   651 
   659         @Override
   652         @Override
   660         CipherSuiteList getClientDefaultCipherSuiteList() {
   653         List<CipherSuite> getClientDefaultCipherSuites() {
   661             return clientDefaultCipherSuiteList;
   654             return clientDefaultCipherSuites;
   662         }
   655         }
   663     }
   656     }
   664 
   657 
   665     /*
   658     /*
   666      * The SSLContext implementation for TLS11 algorithm
   659      * The SSLContext implementation for TLS11 algorithm
   667      *
   660      *
   668      * @see SSLContext
   661      * @see SSLContext
   669      */
   662      */
   670     public static final class TLS11Context extends AbstractTLSContext {
   663     public static final class TLS11Context extends AbstractTLSContext {
   671         private static final ProtocolList clientDefaultProtocolList;
   664         private static final List<ProtocolVersion> clientDefaultProtocols;
   672         private static final CipherSuiteList clientDefaultCipherSuiteList;
   665         private static final List<CipherSuite> clientDefaultCipherSuites;
   673 
   666 
   674         static {
   667         static {
   675             if (SunJSSE.isFIPS()) {
   668             if (SunJSSE.isFIPS()) {
   676                 clientDefaultProtocolList = new ProtocolList(
   669                 clientDefaultProtocols = getAvailableProtocols(
   677                         getAvailableProtocols(new ProtocolVersion[] {
   670                         new ProtocolVersion[] {
       
   671                     ProtocolVersion.TLS11,
       
   672                     ProtocolVersion.TLS10
       
   673                 });
       
   674             } else {
       
   675                 clientDefaultProtocols = getAvailableProtocols(
       
   676                         new ProtocolVersion[] {
       
   677                     ProtocolVersion.TLS11,
   678                     ProtocolVersion.TLS10,
   678                     ProtocolVersion.TLS10,
   679                     ProtocolVersion.TLS11
   679                     ProtocolVersion.SSL30
   680                 }));
   680                 });
   681             } else {
   681             }
   682                 clientDefaultProtocolList = new ProtocolList(
   682 
   683                         getAvailableProtocols(new ProtocolVersion[] {
   683             clientDefaultCipherSuites = getApplicableEnabledCipherSuites(
   684                     ProtocolVersion.SSL30,
   684                     clientDefaultProtocols, true);
   685                     ProtocolVersion.TLS10,
   685 
   686                     ProtocolVersion.TLS11
   686         }
   687                 }));
   687 
   688             }
   688         @Override
   689 
   689         List<ProtocolVersion> getClientDefaultProtocolVersions() {
   690             clientDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
   690             return clientDefaultProtocols;
   691                     clientDefaultProtocolList, true);
   691         }
   692 
   692 
   693         }
   693         @Override
   694 
   694         List<CipherSuite> getClientDefaultCipherSuites() {
   695         @Override
   695             return clientDefaultCipherSuites;
   696         ProtocolList getClientDefaultProtocolList() {
       
   697             return clientDefaultProtocolList;
       
   698         }
       
   699 
       
   700         @Override
       
   701         CipherSuiteList getClientDefaultCipherSuiteList() {
       
   702             return clientDefaultCipherSuiteList;
       
   703         }
   696         }
   704     }
   697     }
   705 
   698 
   706     /*
   699     /*
   707      * The SSLContext implementation for TLS12 algorithm
   700      * The SSLContext implementation for TLS12 algorithm
   708      *
   701      *
   709      * @see SSLContext
   702      * @see SSLContext
   710      */
   703      */
   711     public static final class TLS12Context extends AbstractTLSContext {
   704     public static final class TLS12Context extends AbstractTLSContext {
   712         private static final ProtocolList clientDefaultProtocolList;
   705         private static final List<ProtocolVersion> clientDefaultProtocols;
   713         private static final CipherSuiteList clientDefaultCipherSuiteList;
   706         private static final List<CipherSuite> clientDefaultCipherSuites;
   714 
   707 
   715         static {
   708         static {
   716             if (SunJSSE.isFIPS()) {
   709             if (SunJSSE.isFIPS()) {
   717                 clientDefaultProtocolList = new ProtocolList(
   710                 clientDefaultProtocols = getAvailableProtocols(
   718                         getAvailableProtocols(new ProtocolVersion[] {
   711                         new ProtocolVersion[] {
       
   712                     ProtocolVersion.TLS12,
       
   713                     ProtocolVersion.TLS11,
       
   714                     ProtocolVersion.TLS10
       
   715                 });
       
   716             } else {
       
   717                 clientDefaultProtocols = getAvailableProtocols(
       
   718                         new ProtocolVersion[] {
       
   719                     ProtocolVersion.TLS12,
       
   720                     ProtocolVersion.TLS11,
   719                     ProtocolVersion.TLS10,
   721                     ProtocolVersion.TLS10,
       
   722                     ProtocolVersion.SSL30
       
   723                 });
       
   724             }
       
   725 
       
   726             clientDefaultCipherSuites = getApplicableEnabledCipherSuites(
       
   727                     clientDefaultProtocols, true);
       
   728         }
       
   729 
       
   730         @Override
       
   731         List<ProtocolVersion> getClientDefaultProtocolVersions() {
       
   732             return clientDefaultProtocols;
       
   733         }
       
   734 
       
   735         @Override
       
   736         List<CipherSuite> getClientDefaultCipherSuites() {
       
   737             return clientDefaultCipherSuites;
       
   738         }
       
   739     }
       
   740 
       
   741     /*
       
   742      * The SSLContext implementation for TLS1.3 algorithm
       
   743      *
       
   744      * @see SSLContext
       
   745      */
       
   746     public static final class TLS13Context extends AbstractTLSContext {
       
   747         private static final List<ProtocolVersion> clientDefaultProtocols;
       
   748         private static final List<CipherSuite> clientDefaultCipherSuites;
       
   749 
       
   750         static {
       
   751             if (SunJSSE.isFIPS()) {
       
   752                 clientDefaultProtocols = getAvailableProtocols(
       
   753                         new ProtocolVersion[] {
       
   754                     ProtocolVersion.TLS13,
       
   755                     ProtocolVersion.TLS12,
   720                     ProtocolVersion.TLS11,
   756                     ProtocolVersion.TLS11,
   721                     ProtocolVersion.TLS12
   757                     ProtocolVersion.TLS10
   722                 }));
   758                 });
   723             } else {
   759             } else {
   724                 clientDefaultProtocolList = new ProtocolList(
   760                 clientDefaultProtocols = getAvailableProtocols(
   725                         getAvailableProtocols(new ProtocolVersion[] {
   761                         new ProtocolVersion[] {
   726                     ProtocolVersion.SSL30,
   762                     ProtocolVersion.TLS13,
       
   763                     ProtocolVersion.TLS12,
       
   764                     ProtocolVersion.TLS11,
   727                     ProtocolVersion.TLS10,
   765                     ProtocolVersion.TLS10,
   728                     ProtocolVersion.TLS11,
   766                     ProtocolVersion.SSL30
   729                     ProtocolVersion.TLS12
   767                 });
   730                 }));
   768             }
   731             }
   769 
   732 
   770             clientDefaultCipherSuites = getApplicableEnabledCipherSuites(
   733             clientDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
   771                     clientDefaultProtocols, true);
   734                     clientDefaultProtocolList, true);
   772         }
   735         }
   773 
   736 
   774         @Override
   737         @Override
   775         List<ProtocolVersion> getClientDefaultProtocolVersions() {
   738         ProtocolList getClientDefaultProtocolList() {
   776             return clientDefaultProtocols;
   739             return clientDefaultProtocolList;
   777         }
   740         }
   778 
   741 
   779         @Override
   742         @Override
   780         List<CipherSuite> getClientDefaultCipherSuites() {
   743         CipherSuiteList getClientDefaultCipherSuiteList() {
   781             return clientDefaultCipherSuites;
   744             return clientDefaultCipherSuiteList;
       
   745         }
   782         }
   746     }
   783     }
   747 
   784 
   748     /*
   785     /*
   749      * The interface for the customized SSL/(D)TLS SSLContext.
   786      * The interface for the customized SSL/(D)TLS SSLContext.
   751      * @see SSLContext
   788      * @see SSLContext
   752      */
   789      */
   753     private static class CustomizedSSLProtocols {
   790     private static class CustomizedSSLProtocols {
   754         private static final String PROPERTY_NAME = "jdk.tls.client.protocols";
   791         private static final String PROPERTY_NAME = "jdk.tls.client.protocols";
   755         static IllegalArgumentException reservedException = null;
   792         static IllegalArgumentException reservedException = null;
   756         static ArrayList<ProtocolVersion>
   793         static final ArrayList<ProtocolVersion>
   757                                 customizedProtocols = new ArrayList<>();
   794                                 customizedProtocols = new ArrayList<>();
   758 
   795 
   759         // Don't want a java.lang.LinkageError for illegal system property.
   796         // Don't want a java.lang.LinkageError for illegal system property.
   760         //
   797         //
   761         // Please don't throw exception in this static block.  Otherwise,
   798         // Please don't throw exception in this static block.  Otherwise,
   776             if (property != null && property.length() != 0) {
   813             if (property != null && property.length() != 0) {
   777                 String[] protocols = property.split(",");
   814                 String[] protocols = property.split(",");
   778                 for (int i = 0; i < protocols.length; i++) {
   815                 for (int i = 0; i < protocols.length; i++) {
   779                     protocols[i] = protocols[i].trim();
   816                     protocols[i] = protocols[i].trim();
   780                     // Is it a supported protocol name?
   817                     // Is it a supported protocol name?
   781                     try {
   818                     ProtocolVersion pv =
   782                         ProtocolVersion pro =
   819                             ProtocolVersion.nameOf(protocols[i]);
   783                                 ProtocolVersion.valueOf(protocols[i]);
   820                     if (pv == null) {
   784 
       
   785                         if (SunJSSE.isFIPS() &&
       
   786                                 ((pro.v == ProtocolVersion.SSL30.v) ||
       
   787                                  (pro.v == ProtocolVersion.SSL20Hello.v))) {
       
   788                             reservedException = new IllegalArgumentException(
       
   789                                     PROPERTY_NAME + ": " + pro +
       
   790                                     " is not FIPS compliant");
       
   791 
       
   792                             break;
       
   793                         }
       
   794 
       
   795                         // ignore duplicated protocols
       
   796                         if (!customizedProtocols.contains(pro)) {
       
   797                             customizedProtocols.add(pro);
       
   798                         }
       
   799                     } catch (IllegalArgumentException iae) {
       
   800                         reservedException = new IllegalArgumentException(
   821                         reservedException = new IllegalArgumentException(
   801                                 PROPERTY_NAME + ": " + protocols[i] +
   822                             PROPERTY_NAME + ": " + protocols[i] +
   802                                 " is not a standard SSL protocol name", iae);
   823                             " is not a supported SSL protocol name");
   803                     }
   824                     }
       
   825 
       
   826                     if (SunJSSE.isFIPS() &&
       
   827                             ((pv == ProtocolVersion.SSL30) ||
       
   828                              (pv == ProtocolVersion.SSL20Hello))) {
       
   829                         reservedException = new IllegalArgumentException(
       
   830                                 PROPERTY_NAME + ": " + pv +
       
   831                                 " is not FIPS compliant");
       
   832 
       
   833                         break;
       
   834                     }
       
   835 
       
   836                     // ignore duplicated protocols
       
   837                     if (!customizedProtocols.contains(pv)) {
       
   838                         customizedProtocols.add(pv);
       
   839                     }
   804                 }
   840                 }
   805             }
   841             }
   806         }
   842         }
   807     }
   843     }
   808 
   844 
   811      *
   847      *
   812      * @see SSLContext
   848      * @see SSLContext
   813      */
   849      */
   814     private static class CustomizedTLSContext extends AbstractTLSContext {
   850     private static class CustomizedTLSContext extends AbstractTLSContext {
   815 
   851 
   816         private static final ProtocolList clientDefaultProtocolList;
   852         private static final List<ProtocolVersion> clientDefaultProtocols;
   817         private static final CipherSuiteList clientDefaultCipherSuiteList;
   853         private static final List<CipherSuite> clientDefaultCipherSuites;
   818 
   854         private static final IllegalArgumentException reservedException;
   819         private static IllegalArgumentException reservedException = null;
       
   820 
   855 
   821         // Don't want a java.lang.LinkageError for illegal system property.
   856         // Don't want a java.lang.LinkageError for illegal system property.
   822         //
   857         //
   823         // Please don't throw exception in this static block.  Otherwise,
   858         // Please don't throw exception in this static block.  Otherwise,
   824         // java.lang.LinkageError may be thrown during the instantiation of
   859         // java.lang.LinkageError may be thrown during the instantiation of
   829             if (reservedException == null) {
   864             if (reservedException == null) {
   830                 ArrayList<ProtocolVersion>
   865                 ArrayList<ProtocolVersion>
   831                         customizedTLSProtocols = new ArrayList<>();
   866                         customizedTLSProtocols = new ArrayList<>();
   832                 for (ProtocolVersion protocol :
   867                 for (ProtocolVersion protocol :
   833                         CustomizedSSLProtocols.customizedProtocols) {
   868                         CustomizedSSLProtocols.customizedProtocols) {
   834                     if (!protocol.isDTLSProtocol()) {
   869                     if (!protocol.isDTLS) {
   835                         customizedTLSProtocols.add(protocol);
   870                         customizedTLSProtocols.add(protocol);
   836                     }
   871                     }
   837                 }
   872                 }
   838 
   873 
   839                 // candidates for available protocols
   874                 // candidates for available protocols
   841                 if (customizedTLSProtocols.isEmpty()) {
   876                 if (customizedTLSProtocols.isEmpty()) {
   842                     // Use the default enabled client protocols if no
   877                     // Use the default enabled client protocols if no
   843                     // customized TLS protocols.
   878                     // customized TLS protocols.
   844                     if (SunJSSE.isFIPS()) {
   879                     if (SunJSSE.isFIPS()) {
   845                         candidates = new ProtocolVersion[] {
   880                         candidates = new ProtocolVersion[] {
   846                             ProtocolVersion.TLS10,
   881                             ProtocolVersion.TLS13,
       
   882                             ProtocolVersion.TLS12,
   847                             ProtocolVersion.TLS11,
   883                             ProtocolVersion.TLS11,
   848                             ProtocolVersion.TLS12
   884                             ProtocolVersion.TLS10
   849                         };
   885                         };
   850                     } else {
   886                     } else {
   851                         candidates = new ProtocolVersion[] {
   887                         candidates = new ProtocolVersion[] {
   852                             ProtocolVersion.SSL30,
   888                             ProtocolVersion.TLS13,
       
   889                             ProtocolVersion.TLS12,
       
   890                             ProtocolVersion.TLS11,
   853                             ProtocolVersion.TLS10,
   891                             ProtocolVersion.TLS10,
   854                             ProtocolVersion.TLS11,
   892                             ProtocolVersion.SSL30
   855                             ProtocolVersion.TLS12
       
   856                         };
   893                         };
   857                     }
   894                     }
   858                 } else {
   895                 } else {
   859                     // Use the customized TLS protocols.
   896                     // Use the customized TLS protocols.
   860                     candidates =
   897                     candidates =
   861                             new ProtocolVersion[customizedTLSProtocols.size()];
   898                             new ProtocolVersion[customizedTLSProtocols.size()];
   862                     candidates = customizedTLSProtocols.toArray(candidates);
   899                     candidates = customizedTLSProtocols.toArray(candidates);
   863                 }
   900                 }
   864 
   901 
   865                 clientDefaultProtocolList = new ProtocolList(
   902                 clientDefaultProtocols = getAvailableProtocols(candidates);
   866                         getAvailableProtocols(candidates));
   903                 clientDefaultCipherSuites =
   867                 clientDefaultCipherSuiteList =
   904                         getApplicableEnabledCipherSuites(
   868                         getApplicableEnabledCipherSuiteList(
   905                                 clientDefaultProtocols, true);
   869                                 clientDefaultProtocolList, true);
       
   870             } else {
   906             } else {
   871                 clientDefaultProtocolList = null;       // unlikely to be used
   907                 clientDefaultProtocols = null;       // unlikely to be used
   872                 clientDefaultCipherSuiteList = null;    // unlikely to be used
   908                 clientDefaultCipherSuites = null;    // unlikely to be used
   873             }
   909             }
   874         }
   910         }
   875 
   911 
   876         protected CustomizedTLSContext() {
   912         protected CustomizedTLSContext() {
   877             if (reservedException != null) {
   913             if (reservedException != null) {
   878                 throw reservedException;
   914                 throw reservedException;
   879             }
   915             }
   880         }
   916         }
   881 
   917 
   882         @Override
   918         @Override
   883         ProtocolList getClientDefaultProtocolList() {
   919         List<ProtocolVersion> getClientDefaultProtocolVersions() {
   884             return clientDefaultProtocolList;
   920             return clientDefaultProtocols;
   885         }
   921         }
   886 
   922 
   887         @Override
   923         @Override
   888         CipherSuiteList getClientDefaultCipherSuiteList() {
   924         List<CipherSuite> getClientDefaultCipherSuites() {
   889             return clientDefaultCipherSuiteList;
   925             return clientDefaultCipherSuites;
   890         }
   926         }
   891     }
   927     }
   892 
   928 
   893     /*
   929     /*
   894      * The SSLContext implementation for default "TLS" algorithm
   930      * The SSLContext implementation for default "TLS" algorithm
   907         private static final String P11KEYSTORE = "PKCS11";
   943         private static final String P11KEYSTORE = "PKCS11";
   908 
   944 
   909         private static final TrustManager[] trustManagers;
   945         private static final TrustManager[] trustManagers;
   910         private static final KeyManager[] keyManagers;
   946         private static final KeyManager[] keyManagers;
   911 
   947 
   912         static Exception reservedException = null;
   948         private static final Exception reservedException;
   913 
   949 
   914         static {
   950         static {
       
   951             Exception reserved = null;
   915             TrustManager[] tmMediator;
   952             TrustManager[] tmMediator;
   916             try {
   953             try {
   917                 tmMediator = getTrustManagers();
   954                 tmMediator = getTrustManagers();
   918             } catch (Exception e) {
   955             } catch (Exception e) {
   919                 reservedException = e;
   956                 reserved = e;
   920                 tmMediator = new TrustManager[0];
   957                 tmMediator = new TrustManager[0];
   921             }
   958             }
   922             trustManagers = tmMediator;
   959             trustManagers = tmMediator;
   923 
   960 
   924             if (reservedException == null) {
   961             if (reserved == null) {
   925                 KeyManager[] kmMediator;
   962                 KeyManager[] kmMediator;
   926                 try {
   963                 try {
   927                     kmMediator = getKeyManagers();
   964                     kmMediator = getKeyManagers();
   928                 } catch (Exception e) {
   965                 } catch (Exception e) {
   929                     reservedException = e;
   966                     reserved = e;
   930                     kmMediator = new KeyManager[0];
   967                     kmMediator = new KeyManager[0];
   931                 }
   968                 }
   932                 keyManagers = kmMediator;
   969                 keyManagers = kmMediator;
   933             } else {
   970             } else {
   934                 keyManagers = new KeyManager[0];
   971                 keyManagers = new KeyManager[0];
   935             }
   972             }
       
   973 
       
   974             reservedException = reserved;
   936         }
   975         }
   937 
   976 
   938         private static TrustManager[] getTrustManagers() throws Exception {
   977         private static TrustManager[] getTrustManagers() throws Exception {
   939             TrustManagerFactory tmf = TrustManagerFactory.getInstance(
   978             TrustManagerFactory tmf = TrustManagerFactory.getInstance(
   940                     TrustManagerFactory.getDefaultAlgorithm());
   979                     TrustManagerFactory.getDefaultAlgorithm());
   974             });
  1013             });
   975 
  1014 
   976             final String defaultKeyStore = props.get("keyStore");
  1015             final String defaultKeyStore = props.get("keyStore");
   977             String defaultKeyStoreType = props.get("keyStoreType");
  1016             String defaultKeyStoreType = props.get("keyStoreType");
   978             String defaultKeyStoreProvider = props.get("keyStoreProvider");
  1017             String defaultKeyStoreProvider = props.get("keyStoreProvider");
   979             if (debug != null && Debug.isOn("defaultctx")) {
  1018             if (SSLLogger.isOn && SSLLogger.isOn("ssl,defaultctx")) {
   980                 System.out.println("keyStore is : " + defaultKeyStore);
  1019                 SSLLogger.fine("keyStore is : " + defaultKeyStore);
   981                 System.out.println("keyStore type is : " +
  1020                 SSLLogger.fine("keyStore type is : " +
   982                                         defaultKeyStoreType);
  1021                                         defaultKeyStoreType);
   983                 System.out.println("keyStore provider is : " +
  1022                 SSLLogger.fine("keyStore provider is : " +
   984                                         defaultKeyStoreProvider);
  1023                                         defaultKeyStoreProvider);
   985             }
  1024             }
   986 
  1025 
   987             if (P11KEYSTORE.equals(defaultKeyStoreType) &&
  1026             if (P11KEYSTORE.equals(defaultKeyStoreType) &&
   988                     !NONE.equals(defaultKeyStore)) {
  1027                     !NONE.equals(defaultKeyStore)) {
  1012 
  1051 
  1013                 /**
  1052                 /**
  1014                  * Try to initialize key store.
  1053                  * Try to initialize key store.
  1015                  */
  1054                  */
  1016                 if ((defaultKeyStoreType.length()) != 0) {
  1055                 if ((defaultKeyStoreType.length()) != 0) {
  1017                     if (debug != null && Debug.isOn("defaultctx")) {
  1056                     if (SSLLogger.isOn && SSLLogger.isOn("ssl,defaultctx")) {
  1018                         System.out.println("init keystore");
  1057                         SSLLogger.finest("init keystore");
  1019                     }
  1058                     }
  1020                     if (defaultKeyStoreProvider.length() == 0) {
  1059                     if (defaultKeyStoreProvider.length() == 0) {
  1021                         ks = KeyStore.getInstance(defaultKeyStoreType);
  1060                         ks = KeyStore.getInstance(defaultKeyStoreType);
  1022                     } else {
  1061                     } else {
  1023                         ks = KeyStore.getInstance(defaultKeyStoreType,
  1062                         ks = KeyStore.getInstance(defaultKeyStoreType,
  1035             }
  1074             }
  1036 
  1075 
  1037             /*
  1076             /*
  1038              * Try to initialize key manager.
  1077              * Try to initialize key manager.
  1039              */
  1078              */
  1040             if (debug != null && Debug.isOn("defaultctx")) {
  1079             if (SSLLogger.isOn && SSLLogger.isOn("ssl,defaultctx")) {
  1041                 System.out.println("init keymanager of type " +
  1080                 SSLLogger.fine("init keymanager of type " +
  1042                     KeyManagerFactory.getDefaultAlgorithm());
  1081                     KeyManagerFactory.getDefaultAlgorithm());
  1043             }
  1082             }
  1044             KeyManagerFactory kmf = KeyManagerFactory.getInstance(
  1083             KeyManagerFactory kmf = KeyManagerFactory.getInstance(
  1045                 KeyManagerFactory.getDefaultAlgorithm());
  1084                 KeyManagerFactory.getDefaultAlgorithm());
  1046 
  1085 
  1093 
  1132 
  1094             try {
  1133             try {
  1095                 super.engineInit(DefaultManagersHolder.keyManagers,
  1134                 super.engineInit(DefaultManagersHolder.keyManagers,
  1096                         DefaultManagersHolder.trustManagers, null);
  1135                         DefaultManagersHolder.trustManagers, null);
  1097             } catch (Exception e) {
  1136             } catch (Exception e) {
  1098                 if (debug != null && Debug.isOn("defaultctx")) {
  1137                 if (SSLLogger.isOn && SSLLogger.isOn("ssl,defaultctx")) {
  1099                     System.out.println("default context init failed: " + e);
  1138                     SSLLogger.fine("default context init failed: ", e);
  1100                 }
  1139                 }
  1101                 throw e;
  1140                 throw e;
  1102             }
  1141             }
  1103         }
  1142         }
  1104 
  1143 
  1126      * parameters.
  1165      * parameters.
  1127      *
  1166      *
  1128      * @see SSLContext
  1167      * @see SSLContext
  1129      */
  1168      */
  1130     private abstract static class AbstractDTLSContext extends SSLContextImpl {
  1169     private abstract static class AbstractDTLSContext extends SSLContextImpl {
  1131         private static final ProtocolList supportedProtocolList;
  1170         private static final List<ProtocolVersion> supportedProtocols;
  1132         private static final ProtocolList serverDefaultProtocolList;
  1171         private static final List<ProtocolVersion> serverDefaultProtocols;
  1133 
  1172 
  1134         private static final CipherSuiteList supportedCipherSuiteList;
  1173         private static final List<CipherSuite> supportedCipherSuites;
  1135         private static final CipherSuiteList serverDefaultCipherSuiteList;
  1174         private static final List<CipherSuite> serverDefaultCipherSuites;
  1136 
  1175 
  1137         static {
  1176         static {
  1138             // Both DTLSv1.0 and DTLSv1.2 can be used in FIPS mode.
  1177             // Both DTLSv1.0 and DTLSv1.2 can be used in FIPS mode.
  1139             supportedProtocolList = new ProtocolList(new String[] {
  1178             supportedProtocols = Arrays.asList(
  1140                 ProtocolVersion.DTLS10.name,
  1179                 ProtocolVersion.DTLS12,
  1141                 ProtocolVersion.DTLS12.name
  1180                 ProtocolVersion.DTLS10
       
  1181             );
       
  1182 
       
  1183             // available protocols for server mode
       
  1184             serverDefaultProtocols = getAvailableProtocols(
       
  1185                     new ProtocolVersion[] {
       
  1186                 ProtocolVersion.DTLS12,
       
  1187                 ProtocolVersion.DTLS10
  1142             });
  1188             });
  1143 
  1189 
  1144             // available protocols for server mode
  1190             supportedCipherSuites = getApplicableSupportedCipherSuites(
  1145             serverDefaultProtocolList = new ProtocolList(
  1191                     supportedProtocols);
  1146                     getAvailableProtocols(new ProtocolVersion[] {
  1192             serverDefaultCipherSuites = getApplicableEnabledCipherSuites(
  1147                 ProtocolVersion.DTLS10,
  1193                     serverDefaultProtocols, false);
  1148                 ProtocolVersion.DTLS12
  1194         }
  1149             }));
  1195 
  1150 
  1196         @Override
  1151             supportedCipherSuiteList = getApplicableSupportedCipherSuiteList(
  1197         List<ProtocolVersion> getSuportedProtocolVersions() {
  1152                     supportedProtocolList);
  1198             return supportedProtocols;
  1153             serverDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
  1199         }
  1154                     serverDefaultProtocolList, false);
  1200 
  1155         }
  1201         @Override
  1156 
  1202         List<CipherSuite> getSupportedCipherSuites() {
  1157         @Override
  1203             return supportedCipherSuites;
  1158         ProtocolList getSuportedProtocolList() {
  1204         }
  1159             return supportedProtocolList;
  1205 
  1160         }
  1206         @Override
  1161 
  1207         List<ProtocolVersion> getServerDefaultProtocolVersions() {
  1162         @Override
  1208             return serverDefaultProtocols;
  1163         CipherSuiteList getSupportedCipherSuiteList() {
  1209         }
  1164             return supportedCipherSuiteList;
  1210 
  1165         }
  1211         @Override
  1166 
  1212         List<CipherSuite> getServerDefaultCipherSuites() {
  1167         @Override
  1213             return serverDefaultCipherSuites;
  1168         ProtocolList getServerDefaultProtocolList() {
       
  1169             return serverDefaultProtocolList;
       
  1170         }
       
  1171 
       
  1172         @Override
       
  1173         CipherSuiteList getServerDefaultCipherSuiteList() {
       
  1174             return serverDefaultCipherSuiteList;
       
  1175         }
  1214         }
  1176 
  1215 
  1177         @Override
  1216         @Override
  1178         SSLEngine createSSLEngineImpl() {
  1217         SSLEngine createSSLEngineImpl() {
  1179             return new SSLEngineImpl(this, true);
  1218             return new SSLEngineImpl(this);
  1180         }
  1219         }
  1181 
  1220 
  1182         @Override
  1221         @Override
  1183         SSLEngine createSSLEngineImpl(String host, int port) {
  1222         SSLEngine createSSLEngineImpl(String host, int port) {
  1184             return new SSLEngineImpl(this, host, port, true);
  1223             return new SSLEngineImpl(this, host, port);
  1185         }
  1224         }
  1186 
  1225 
  1187         @Override
  1226         @Override
  1188         HelloCookieManager getHelloCookieManager(SecureRandom secureRandom) {
  1227         boolean isDTLS() {
  1189             return new HelloCookieManager(secureRandom);
  1228             return true;
  1190         }
  1229         }
  1191     }
  1230     }
  1192 
  1231 
  1193     /*
  1232     /*
  1194      * The SSLContext implementation for DTLSv1.0 algorithm.
  1233      * The SSLContext implementation for DTLSv1.0 algorithm.
  1195      *
  1234      *
  1196      * @see SSLContext
  1235      * @see SSLContext
  1197      */
  1236      */
  1198     public static final class DTLS10Context extends AbstractDTLSContext {
  1237     public static final class DTLS10Context extends AbstractDTLSContext {
  1199         private static final ProtocolList clientDefaultProtocolList;
  1238         private static final List<ProtocolVersion> clientDefaultProtocols;
  1200         private static final CipherSuiteList clientDefaultCipherSuiteList;
  1239         private static final List<CipherSuite> clientDefaultCipherSuites;
  1201 
  1240 
  1202         static {
  1241         static {
  1203             // available protocols for client mode
  1242             // available protocols for client mode
  1204             clientDefaultProtocolList = new ProtocolList(
  1243             clientDefaultProtocols = getAvailableProtocols(
  1205                     getAvailableProtocols(new ProtocolVersion[] {
  1244                     new ProtocolVersion[] {
  1206                 ProtocolVersion.DTLS10
  1245                 ProtocolVersion.DTLS10
  1207             }));
  1246             });
  1208 
  1247 
  1209             clientDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
  1248             clientDefaultCipherSuites = getApplicableEnabledCipherSuites(
  1210                     clientDefaultProtocolList, true);
  1249                     clientDefaultProtocols, true);
  1211         }
  1250         }
  1212 
  1251 
  1213         @Override
  1252         @Override
  1214         ProtocolList getClientDefaultProtocolList() {
  1253         List<ProtocolVersion> getClientDefaultProtocolVersions() {
  1215             return clientDefaultProtocolList;
  1254             return clientDefaultProtocols;
  1216         }
  1255         }
  1217 
  1256 
  1218         @Override
  1257         @Override
  1219         CipherSuiteList getClientDefaultCipherSuiteList() {
  1258         List<CipherSuite> getClientDefaultCipherSuites() {
  1220             return clientDefaultCipherSuiteList;
  1259             return clientDefaultCipherSuites;
  1221         }
  1260         }
  1222     }
  1261     }
  1223 
  1262 
  1224     /*
  1263     /*
  1225      * The SSLContext implementation for DTLSv1.2 algorithm.
  1264      * The SSLContext implementation for DTLSv1.2 algorithm.
  1226      *
  1265      *
  1227      * @see SSLContext
  1266      * @see SSLContext
  1228      */
  1267      */
  1229     public static final class DTLS12Context extends AbstractDTLSContext {
  1268     public static final class DTLS12Context extends AbstractDTLSContext {
  1230         private static final ProtocolList clientDefaultProtocolList;
  1269         private static final List<ProtocolVersion> clientDefaultProtocols;
  1231         private static final CipherSuiteList clientDefaultCipherSuiteList;
  1270         private static final List<CipherSuite> clientDefaultCipherSuites;
  1232 
  1271 
  1233         static {
  1272         static {
  1234             // available protocols for client mode
  1273             // available protocols for client mode
  1235             clientDefaultProtocolList = new ProtocolList(
  1274             clientDefaultProtocols = getAvailableProtocols(
  1236                     getAvailableProtocols(new ProtocolVersion[] {
  1275                     new ProtocolVersion[] {
  1237                 ProtocolVersion.DTLS10,
  1276                 ProtocolVersion.DTLS12,
  1238                 ProtocolVersion.DTLS12
  1277                 ProtocolVersion.DTLS10
  1239             }));
  1278             });
  1240 
  1279 
  1241             clientDefaultCipherSuiteList = getApplicableEnabledCipherSuiteList(
  1280             clientDefaultCipherSuites = getApplicableEnabledCipherSuites(
  1242                     clientDefaultProtocolList, true);
  1281                     clientDefaultProtocols, true);
  1243         }
  1282         }
  1244 
  1283 
  1245         @Override
  1284         @Override
  1246         ProtocolList getClientDefaultProtocolList() {
  1285         List<ProtocolVersion> getClientDefaultProtocolVersions() {
  1247             return clientDefaultProtocolList;
  1286             return clientDefaultProtocols;
  1248         }
  1287         }
  1249 
  1288 
  1250         @Override
  1289         @Override
  1251         CipherSuiteList getClientDefaultCipherSuiteList() {
  1290         List<CipherSuite> getClientDefaultCipherSuites() {
  1252             return clientDefaultCipherSuiteList;
  1291             return clientDefaultCipherSuites;
  1253         }
  1292         }
  1254     }
  1293     }
  1255 
  1294 
  1256     /*
  1295     /*
  1257      * The SSLContext implementation for customized TLS protocols
  1296      * The SSLContext implementation for customized TLS protocols
  1258      *
  1297      *
  1259      * @see SSLContext
  1298      * @see SSLContext
  1260      */
  1299      */
  1261     private static class CustomizedDTLSContext extends AbstractDTLSContext {
  1300     private static class CustomizedDTLSContext extends AbstractDTLSContext {
  1262         private static final ProtocolList clientDefaultProtocolList;
  1301         private static final List<ProtocolVersion> clientDefaultProtocols;
  1263         private static final CipherSuiteList clientDefaultCipherSuiteList;
  1302         private static final List<CipherSuite> clientDefaultCipherSuites;
  1264 
  1303 
  1265         private static IllegalArgumentException reservedException = null;
  1304         private static IllegalArgumentException reservedException = null;
  1266 
  1305 
  1267         // Don't want a java.lang.LinkageError for illegal system property.
  1306         // Don't want a java.lang.LinkageError for illegal system property.
  1268         //
  1307         //
  1275             if (reservedException == null) {
  1314             if (reservedException == null) {
  1276                 ArrayList<ProtocolVersion>
  1315                 ArrayList<ProtocolVersion>
  1277                         customizedDTLSProtocols = new ArrayList<>();
  1316                         customizedDTLSProtocols = new ArrayList<>();
  1278                 for (ProtocolVersion protocol :
  1317                 for (ProtocolVersion protocol :
  1279                         CustomizedSSLProtocols.customizedProtocols) {
  1318                         CustomizedSSLProtocols.customizedProtocols) {
  1280                     if (protocol.isDTLSProtocol()) {
  1319                     if (protocol.isDTLS) {
  1281                         customizedDTLSProtocols.add(protocol);
  1320                         customizedDTLSProtocols.add(protocol);
  1282                     }
  1321                     }
  1283                 }
  1322                 }
  1284 
  1323 
  1285                 // candidates for available protocols
  1324                 // candidates for available protocols
  1288                     // Use the default enabled client protocols if no
  1327                     // Use the default enabled client protocols if no
  1289                     // customized TLS protocols.
  1328                     // customized TLS protocols.
  1290                     //
  1329                     //
  1291                     // Both DTLSv1.0 and DTLSv1.2 can be used in FIPS mode.
  1330                     // Both DTLSv1.0 and DTLSv1.2 can be used in FIPS mode.
  1292                     candidates = new ProtocolVersion[] {
  1331                     candidates = new ProtocolVersion[] {
  1293                         ProtocolVersion.DTLS10,
  1332                         ProtocolVersion.DTLS12,
  1294                         ProtocolVersion.DTLS12
  1333                         ProtocolVersion.DTLS10
  1295                     };
  1334                     };
  1296 
  1335 
  1297                 } else {
  1336                 } else {
  1298                     // Use the customized TLS protocols.
  1337                     // Use the customized TLS protocols.
  1299                     candidates =
  1338                     candidates =
  1300                             new ProtocolVersion[customizedDTLSProtocols.size()];
  1339                             new ProtocolVersion[customizedDTLSProtocols.size()];
  1301                     candidates = customizedDTLSProtocols.toArray(candidates);
  1340                     candidates = customizedDTLSProtocols.toArray(candidates);
  1302                 }
  1341                 }
  1303 
  1342 
  1304                 clientDefaultProtocolList = new ProtocolList(
  1343                 clientDefaultProtocols = getAvailableProtocols(candidates);
  1305                         getAvailableProtocols(candidates));
  1344                 clientDefaultCipherSuites =
  1306                 clientDefaultCipherSuiteList =
  1345                         getApplicableEnabledCipherSuites(
  1307                         getApplicableEnabledCipherSuiteList(
  1346                                 clientDefaultProtocols, true);
  1308                                 clientDefaultProtocolList, true);
       
  1309             } else {
  1347             } else {
  1310                 clientDefaultProtocolList = null;       // unlikely to be used
  1348                 clientDefaultProtocols = null;       // unlikely to be used
  1311                 clientDefaultCipherSuiteList = null;    // unlikely to be used
  1349                 clientDefaultCipherSuites = null;    // unlikely to be used
  1312             }
  1350             }
  1313         }
  1351         }
  1314 
  1352 
  1315         protected CustomizedDTLSContext() {
  1353         protected CustomizedDTLSContext() {
  1316             if (reservedException != null) {
  1354             if (reservedException != null) {
  1317                 throw reservedException;
  1355                 throw reservedException;
  1318             }
  1356             }
  1319         }
  1357         }
  1320 
  1358 
  1321         @Override
  1359         @Override
  1322         ProtocolList getClientDefaultProtocolList() {
  1360         List<ProtocolVersion> getClientDefaultProtocolVersions() {
  1323             return clientDefaultProtocolList;
  1361             return clientDefaultProtocols;
  1324         }
  1362         }
  1325 
  1363 
  1326         @Override
  1364         @Override
  1327         CipherSuiteList getClientDefaultCipherSuiteList() {
  1365         List<CipherSuite> getClientDefaultCipherSuites() {
  1328             return clientDefaultCipherSuiteList;
  1366             return clientDefaultCipherSuites;
  1329         }
  1367         }
  1330     }
  1368     }
  1331 
  1369 
  1332     /*
  1370     /*
  1333      * The SSLContext implementation for default "DTLS" algorithm
  1371      * The SSLContext implementation for default "DTLS" algorithm
  1337     public static final class DTLSContext extends CustomizedDTLSContext {
  1375     public static final class DTLSContext extends CustomizedDTLSContext {
  1338         // use the default constructor and methods
  1376         // use the default constructor and methods
  1339     }
  1377     }
  1340 
  1378 
  1341 }
  1379 }
  1342 
       
  1343 
  1380 
  1344 final class AbstractTrustManagerWrapper extends X509ExtendedTrustManager
  1381 final class AbstractTrustManagerWrapper extends X509ExtendedTrustManager
  1345             implements X509TrustManager {
  1382             implements X509TrustManager {
  1346 
  1383 
  1347     // the delegated trust manager
  1384     // the delegated trust manager
  1415                 X509TrustManagerImpl.checkIdentity(
  1452                 X509TrustManagerImpl.checkIdentity(
  1416                                     hostname, chain[0], identityAlg);
  1453                                     hostname, chain[0], identityAlg);
  1417             }
  1454             }
  1418 
  1455 
  1419             // try the best to check the algorithm constraints
  1456             // try the best to check the algorithm constraints
  1420             ProtocolVersion protocolVersion =
  1457             AlgorithmConstraints constraints;
  1421                 ProtocolVersion.valueOf(session.getProtocol());
  1458             if (ProtocolVersion.useTLS12PlusSpec(session.getProtocol())) {
  1422             AlgorithmConstraints constraints = null;
       
  1423             if (protocolVersion.useTLS12PlusSpec()) {
       
  1424                 if (session instanceof ExtendedSSLSession) {
  1459                 if (session instanceof ExtendedSSLSession) {
  1425                     ExtendedSSLSession extSession =
  1460                     ExtendedSSLSession extSession =
  1426                                     (ExtendedSSLSession)session;
  1461                                     (ExtendedSSLSession)session;
  1427                     String[] peerSupportedSignAlgs =
  1462                     String[] peerSupportedSignAlgs =
  1428                             extSession.getLocalSupportedSignatureAlgorithms();
  1463                             extSession.getLocalSupportedSignatureAlgorithms();
  1457                 X509TrustManagerImpl.checkIdentity(
  1492                 X509TrustManagerImpl.checkIdentity(
  1458                                     hostname, chain[0], identityAlg);
  1493                                     hostname, chain[0], identityAlg);
  1459             }
  1494             }
  1460 
  1495 
  1461             // try the best to check the algorithm constraints
  1496             // try the best to check the algorithm constraints
  1462             ProtocolVersion protocolVersion =
  1497             AlgorithmConstraints constraints;
  1463                 ProtocolVersion.valueOf(session.getProtocol());
  1498             if (ProtocolVersion.useTLS12PlusSpec(session.getProtocol())) {
  1464             AlgorithmConstraints constraints = null;
       
  1465             if (protocolVersion.useTLS12PlusSpec()) {
       
  1466                 if (session instanceof ExtendedSSLSession) {
  1499                 if (session instanceof ExtendedSSLSession) {
  1467                     ExtendedSSLSession extSession =
  1500                     ExtendedSSLSession extSession =
  1468                                     (ExtendedSSLSession)session;
  1501                                     (ExtendedSSLSession)session;
  1469                     String[] peerSupportedSignAlgs =
  1502                     String[] peerSupportedSignAlgs =
  1470                             extSession.getLocalSupportedSignatureAlgorithms();
  1503                             extSession.getLocalSupportedSignatureAlgorithms();
  1482             checkAlgorithmConstraints(chain, constraints, isClient);
  1515             checkAlgorithmConstraints(chain, constraints, isClient);
  1483         }
  1516         }
  1484     }
  1517     }
  1485 
  1518 
  1486     private void checkAlgorithmConstraints(X509Certificate[] chain,
  1519     private void checkAlgorithmConstraints(X509Certificate[] chain,
  1487             AlgorithmConstraints constraints, boolean isClient) throws CertificateException {
  1520             AlgorithmConstraints constraints,
  1488 
  1521             boolean isClient) throws CertificateException {
  1489         try {
  1522         try {
  1490             // Does the certificate chain end with a trusted certificate?
  1523             // Does the certificate chain end with a trusted certificate?
  1491             int checkedLength = chain.length - 1;
  1524             int checkedLength = chain.length - 1;
  1492 
  1525 
  1493             Collection<X509Certificate> trustedCerts = new HashSet<>();
  1526             Collection<X509Certificate> trustedCerts = new HashSet<>();
  1501             }
  1534             }
  1502 
  1535 
  1503             // A forward checker, need to check from trust to target
  1536             // A forward checker, need to check from trust to target
  1504             if (checkedLength >= 0) {
  1537             if (checkedLength >= 0) {
  1505                 AlgorithmChecker checker =
  1538                 AlgorithmChecker checker =
  1506                         new AlgorithmChecker(constraints, null,
  1539                     new AlgorithmChecker(constraints, null,
  1507                                 (isClient ? Validator.VAR_TLS_CLIENT : Validator.VAR_TLS_SERVER));
  1540                             (isClient ? Validator.VAR_TLS_CLIENT :
       
  1541                                         Validator.VAR_TLS_SERVER));
  1508                 checker.init(false);
  1542                 checker.init(false);
  1509                 for (int i = checkedLength; i >= 0; i--) {
  1543                 for (int i = checkedLength; i >= 0; i--) {
  1510                     Certificate cert = chain[i];
  1544                     X509Certificate cert = chain[i];
  1511                     // We don't care about the unresolved critical extensions.
  1545                     // We don't care about the unresolved critical extensions.
  1512                     checker.check(cert, Collections.<String>emptySet());
  1546                     checker.check(cert, Collections.<String>emptySet());
  1513                 }
  1547                 }
  1514             }
  1548             }
  1515         } catch (CertPathValidatorException cpve) {
  1549         } catch (CertPathValidatorException cpve) {