116116import javax .net .ssl .SSLSocketFactory ;
117117import javax .net .ssl .TrustManager ;
118118import javax .net .ssl .TrustManagerFactory ;
119+ import javax .net .ssl .X509ExtendedTrustManager ;
119120import okio .Buffer ;
120121import okio .BufferedSink ;
121122import okio .BufferedSource ;
@@ -135,7 +136,6 @@ class OkHttpClientTransport implements ConnectionClientTransport, TransportExcep
135136 "GRPC_ENABLE_PER_RPC_AUTHORITY_CHECK" ;
136137 static boolean enablePerRpcAuthorityCheck =
137138 GrpcUtil .getFlag (GRPC_ENABLE_PER_RPC_AUTHORITY_CHECK , false );
138- private final ChannelCredentials channelCredentials ;
139139 private Socket sock ;
140140 private SSLSession sslSession ;
141141
@@ -249,7 +249,7 @@ private static Map<ErrorCode, Status> buildErrorCodeToStatusMap() {
249249 private final boolean useGetForSafeMethods ;
250250 @ GuardedBy ("lock" )
251251 private final TransportTracer transportTracer ;
252- private final TrustManager x509ExtendedTrustManager ;
252+ private final TrustManager x509TrustManager ;
253253
254254 @ SuppressWarnings ("serial" )
255255 private static class LruCache <T > extends LinkedHashMap <String , T > {
@@ -354,23 +354,22 @@ private OkHttpClientTransport(
354354 this .attributes = Attributes .newBuilder ()
355355 .set (GrpcAttributes .ATTR_CLIENT_EAG_ATTRS , eagAttrs ).build ();
356356 this .useGetForSafeMethods = transportFactory .useGetForSafeMethods ;
357- this .channelCredentials = channelCredentials ;
358357 initTransportTracer ();
359- TrustManager tempX509ExtendedTrustManager ;
358+ TrustManager tempX509TrustManager ;
360359 if (channelCredentials instanceof TlsChannelCredentials
361360 && x509ExtendedTrustManagerClass != null ) {
362361 try {
363- tempX509ExtendedTrustManager = getX509ExtendedTrustManager (
362+ tempX509TrustManager = getTrustManager (
364363 (TlsChannelCredentials ) channelCredentials );
365364 } catch (GeneralSecurityException e ) {
366- tempX509ExtendedTrustManager = null ;
365+ tempX509TrustManager = null ;
367366 log .log (Level .WARNING , "Obtaining X509ExtendedTrustManager for the transport failed."
368367 + "Per-rpc authority overrides will be disallowed." , e );
369368 }
370369 } else {
371- tempX509ExtendedTrustManager = null ;
370+ tempX509TrustManager = null ;
372371 }
373- x509ExtendedTrustManager = tempX509ExtendedTrustManager ;
372+ x509TrustManager = tempX509TrustManager ;
374373 }
375374
376375 /**
@@ -497,7 +496,7 @@ public OkHttpClientStream newStream(
497496 }
498497 }
499498
500- private TrustManager getX509ExtendedTrustManager (TlsChannelCredentials tlsCreds )
499+ private TrustManager getTrustManager (TlsChannelCredentials tlsCreds )
501500 throws GeneralSecurityException {
502501 TrustManager [] tm ;
503502 // Using the same way of creating TrustManager from OkHttpChannelBuilder.sslSocketFactoryFrom()
@@ -511,12 +510,7 @@ private TrustManager getX509ExtendedTrustManager(TlsChannelCredentials tlsCreds)
511510 tmf .init ((KeyStore ) null );
512511 tm = tmf .getTrustManagers ();
513512 }
514- for (TrustManager trustManager : tm ) {
515- if (x509ExtendedTrustManagerClass .isInstance (trustManager )) {
516- return trustManager ;
517- }
518- }
519- return null ;
513+ return tm [0 ];
520514 }
521515
522516 @ GuardedBy ("lock" )
@@ -529,79 +523,76 @@ void streamReadyToStart(OkHttpClientStream clientStream, String authority) {
529523 setInUse (clientStream );
530524 } else {
531525 if (!authority .equals (defaultAuthority )) {
532- if (hostnameVerifier != null && socket instanceof SSLSocket ) {
533- Boolean hostnameVerificationResult ;
534- if (hostnameVerificationResults .containsKey (authority )) {
535- hostnameVerificationResult = hostnameVerificationResults .get (authority );
536- } else {
537- hostnameVerificationResult = hostnameVerifier .verify (
538- authority , ((SSLSocket ) socket ).getSession ());
539- hostnameVerificationResults .put (authority , hostnameVerificationResult );
540- if (!hostnameVerificationResult && !enablePerRpcAuthorityCheck ) {
541- log .log (Level .WARNING , String .format ("HostNameVerifier verification failed for "
542- + "authority '%s'. This will be an error in the future." ,
543- authority ));
544- }
526+ Boolean hostnameVerificationResult ;
527+ if (hostnameVerificationResults .containsKey (authority )) {
528+ hostnameVerificationResult = hostnameVerificationResults .get (authority );
529+ } else {
530+ hostnameVerificationResult = hostnameVerifier .verify (
531+ authority , ((SSLSocket ) socket ).getSession ());
532+ hostnameVerificationResults .put (authority , hostnameVerificationResult );
533+ if (!hostnameVerificationResult && !enablePerRpcAuthorityCheck ) {
534+ log .log (Level .WARNING , String .format ("HostNameVerifier verification failed for "
535+ + "authority '%s'. This will be an error in the future." ,
536+ authority ));
545537 }
546- if (! hostnameVerificationResult ) {
547- if (enablePerRpcAuthorityCheck ) {
548- clientStream . transportState (). transportReportStatus (
549- Status . UNAVAILABLE . withDescription ( String . format (
550- "HostNameVerifier verification failed for authority '%s'" ,
551- authority )) ,
552- RpcProgress . PROCESSED , true , new Metadata ());
553- return ;
554- }
538+ }
539+ if (! hostnameVerificationResult ) {
540+ if ( enablePerRpcAuthorityCheck ) {
541+ clientStream . transportState (). transportReportStatus (
542+ Status . UNAVAILABLE . withDescription ( String . format (
543+ "HostNameVerifier verification failed for authority '%s'" ,
544+ authority )),
545+ RpcProgress . PROCESSED , true , new Metadata ()) ;
546+ return ;
555547 }
556548 }
557- if (socket instanceof SSLSocket
558- && (channelCredentials != null
559- && channelCredentials instanceof TlsChannelCredentials )
560- || sslSocketFactory != null ) {
561- Status peerVerificationStatus ;
562- if (peerVerificationResults .containsKey (authority )) {
563- peerVerificationStatus = peerVerificationResults .get (authority );
564- } else {
565- if (x509ExtendedTrustManager == null ) {
566- peerVerificationStatus = Status .UNAVAILABLE .withDescription (
567- String .format ("Could not verify authority '%s' for the rpc with no "
568- + "X509ExtendedTrustManager available" ,
569- authority ));
570- } else {
571- try {
572- Certificate [] peerCertificates = sslSession .getPeerCertificates ();
573- X509Certificate [] x509PeerCertificates =
574- new X509Certificate [peerCertificates .length ];
575- for (int i = 0 ; i < peerCertificates .length ; i ++) {
576- x509PeerCertificates [i ] = (X509Certificate ) peerCertificates [i ];
577- }
578- checkServerTrustedMethod .invoke (x509ExtendedTrustManager , x509PeerCertificates ,
579- "RSA" , new SslSocketWrapper ((SSLSocket ) socket , authority ));
580- peerVerificationStatus = Status .OK ;
581- } catch (SSLPeerUnverifiedException | InvocationTargetException
582- | IllegalAccessException e ) {
583- peerVerificationStatus = Status .UNAVAILABLE .withCause (e ).withDescription (
584- "Peer verification failed" );
585- }
586- if (peerVerificationStatus != null ) {
587- peerVerificationResults .put (authority , peerVerificationStatus );
549+ Status peerVerificationStatus = null ;
550+ if (peerVerificationResults .containsKey (authority )) {
551+ peerVerificationStatus = peerVerificationResults .get (authority );
552+ } else {
553+ // The status is trivially assigned in this case, but we are still making use of the
554+ // cache to keep track that a warning log had been logged for the authority when
555+ // enablePerRpcAuthorityCheck is false. When we permanently enable the feature, the
556+ // status won't need to be cached for case of x509TrustManager == null.
557+ if (x509TrustManager == null ) {
558+ peerVerificationStatus = Status .UNAVAILABLE .withDescription (
559+ String .format ("Could not verify authority '%s' for the rpc with no "
560+ + "X509TrustManager available" ,
561+ authority ));
562+ } else if (x509ExtendedTrustManagerClass .isInstance (x509TrustManager )) {
563+ try {
564+ Certificate [] peerCertificates = sslSession .getPeerCertificates ();
565+ X509Certificate [] x509PeerCertificates =
566+ new X509Certificate [peerCertificates .length ];
567+ for (int i = 0 ; i < peerCertificates .length ; i ++) {
568+ x509PeerCertificates [i ] = (X509Certificate ) peerCertificates [i ];
588569 }
570+ checkServerTrustedMethod .invoke (x509TrustManager , x509PeerCertificates ,
571+ "RSA" , new SslSocketWrapper ((SSLSocket ) socket , authority ));
572+ peerVerificationStatus = Status .OK ;
573+ } catch (SSLPeerUnverifiedException | InvocationTargetException
574+ | IllegalAccessException e ) {
575+ peerVerificationStatus = Status .UNAVAILABLE .withCause (e ).withDescription (
576+ "Peer verification failed" );
577+ }
578+ if (peerVerificationStatus != null ) {
579+ peerVerificationResults .put (authority , peerVerificationStatus );
589580 }
590581 }
591- if (peerVerificationStatus != null && !peerVerificationStatus .isOk ()) {
592- if (enablePerRpcAuthorityCheck ) {
593- clientStream .transportState ().transportReportStatus (
594- peerVerificationStatus , RpcProgress .PROCESSED , true , new Metadata ());
595- return ;
582+ }
583+ if (peerVerificationStatus != null && !peerVerificationStatus .isOk ()) {
584+ if (enablePerRpcAuthorityCheck ) {
585+ clientStream .transportState ().transportReportStatus (
586+ peerVerificationStatus , RpcProgress .PROCESSED , true , new Metadata ());
587+ return ;
588+ } else {
589+ if (peerVerificationStatus .getCause () != null ) {
590+ log .log (Level .WARNING , peerVerificationStatus .getDescription ()
591+ + ". This will be an error in the future." ,
592+ peerVerificationStatus .getCause ());
596593 } else {
597- if (peerVerificationStatus .getCause () != null ) {
598- log .log (Level .WARNING , peerVerificationStatus .getDescription ()
599- + ". This will be an error in the future." ,
600- peerVerificationStatus .getCause ());
601- } else {
602- log .log (Level .WARNING , peerVerificationStatus .getDescription ()
603- + ". This will be an error in the future." );
604- }
594+ log .log (Level .WARNING , peerVerificationStatus .getDescription ()
595+ + ". This will be an error in the future." );
605596 }
606597 }
607598 }
0 commit comments