Add GetSslInfo() interface in QuicCryptoStream to expose SSL object in BoringSSL. The interface will be used in Envoy.

PiperOrigin-RevId: 400774065
diff --git a/quic/core/http/quic_spdy_session_test.cc b/quic/core/http/quic_spdy_session_test.cc
index 89beb70..48f488d 100644
--- a/quic/core/http/quic_spdy_session_test.cc
+++ b/quic/core/http/quic_spdy_session_test.cc
@@ -186,6 +186,7 @@
 
   void OnConnectionClosed(QuicErrorCode /*error*/,
                           ConnectionCloseSource /*source*/) override {}
+  SSL* GetSsl() const override { return nullptr; }
 
  private:
   using QuicCryptoStream::session;
diff --git a/quic/core/http/quic_spdy_stream_test.cc b/quic/core/http/quic_spdy_stream_test.cc
index 04343e0..37ed187 100644
--- a/quic/core/http/quic_spdy_stream_test.cc
+++ b/quic/core/http/quic_spdy_stream_test.cc
@@ -168,6 +168,8 @@
 
   MOCK_METHOD(bool, HasPendingRetransmission, (), (const, override));
 
+  SSL* GetSsl() const override { return nullptr; }
+
  private:
   using QuicCryptoStream::session;
 
diff --git a/quic/core/quic_crypto_client_stream.cc b/quic/core/quic_crypto_client_stream.cc
index 78d2f10..27de0b8 100644
--- a/quic/core/quic_crypto_client_stream.cc
+++ b/quic/core/quic_crypto_client_stream.cc
@@ -43,11 +43,14 @@
           server_id, this, session, std::move(verify_context), crypto_config,
           proof_handler);
       break;
-    case PROTOCOL_TLS1_3:
-      handshaker_ = std::make_unique<TlsClientHandshaker>(
+    case PROTOCOL_TLS1_3: {
+      auto handshaker = std::make_unique<TlsClientHandshaker>(
           server_id, this, session, std::move(verify_context), crypto_config,
           proof_handler, has_application_state);
+      tls_handshaker_ = handshaker.get();
+      handshaker_ = std::move(handshaker);
       break;
+    }
     case PROTOCOL_UNSUPPORTED:
       QUIC_BUG(quic_bug_10296_1)
           << "Attempting to create QuicCryptoClientStream for unknown "
@@ -167,4 +170,8 @@
       std::move(application_state));
 }
 
+SSL* QuicCryptoClientStream::GetSsl() const {
+  return tls_handshaker_ == nullptr ? nullptr : tls_handshaker_->ssl();
+}
+
 }  // namespace quic
diff --git a/quic/core/quic_crypto_client_stream.h b/quic/core/quic_crypto_client_stream.h
index b3d3c2b..e539165 100644
--- a/quic/core/quic_crypto_client_stream.h
+++ b/quic/core/quic_crypto_client_stream.h
@@ -25,6 +25,8 @@
 class QuicCryptoClientStreamPeer;
 }  // namespace test
 
+class TlsClientHandshaker;
+
 class QUIC_EXPORT_PRIVATE QuicCryptoClientStreamBase : public QuicCryptoStream {
  public:
   explicit QuicCryptoClientStreamBase(QuicSession* session);
@@ -250,6 +252,7 @@
   std::unique_ptr<QuicDecrypter> AdvanceKeysAndCreateCurrentOneRttDecrypter()
       override;
   std::unique_ptr<QuicEncrypter> CreateCurrentOneRttEncrypter() override;
+  SSL* GetSsl() const override;
 
   std::string chlo_hash() const;
 
@@ -261,6 +264,10 @@
  private:
   friend class test::QuicCryptoClientStreamPeer;
   std::unique_ptr<HandshakerInterface> handshaker_;
+  // Points to |handshaker_| if it uses TLS1.3. Otherwise, nullptr.
+  // TODO(danzh) change the type of |handshaker_| to TlsClientHandshaker after
+  // deprecating Google QUIC.
+  TlsClientHandshaker* tls_handshaker_{nullptr};
 };
 
 }  // namespace quic
diff --git a/quic/core/quic_crypto_server_stream.cc b/quic/core/quic_crypto_server_stream.cc
index 461c58f..de6cb75 100644
--- a/quic/core/quic_crypto_server_stream.cc
+++ b/quic/core/quic_crypto_server_stream.cc
@@ -511,4 +511,6 @@
   return session()->connection()->peer_address();
 }
 
+SSL* QuicCryptoServerStream::GetSsl() const { return nullptr; }
+
 }  // namespace quic
diff --git a/quic/core/quic_crypto_server_stream.h b/quic/core/quic_crypto_server_stream.h
index 690e872..bf6f3e5 100644
--- a/quic/core/quic_crypto_server_stream.h
+++ b/quic/core/quic_crypto_server_stream.h
@@ -69,6 +69,7 @@
   std::unique_ptr<QuicDecrypter> AdvanceKeysAndCreateCurrentOneRttDecrypter()
       override;
   std::unique_ptr<QuicEncrypter> CreateCurrentOneRttEncrypter() override;
+  SSL* GetSsl() const override;
 
   // From QuicCryptoHandshaker
   void OnHandshakeMessage(const CryptoHandshakeMessage& message) override;
diff --git a/quic/core/quic_crypto_stream.h b/quic/core/quic_crypto_stream.h
index 2a86a72..37edc87 100644
--- a/quic/core/quic_crypto_stream.h
+++ b/quic/core/quic_crypto_stream.h
@@ -147,6 +147,11 @@
   // decrypter returned by AdvanceKeysAndCreateCurrentOneRttDecrypter().
   virtual std::unique_ptr<QuicEncrypter> CreateCurrentOneRttEncrypter() = 0;
 
+  // Return the SSL struct object created by BoringSSL if the stream is using
+  // TLS1.3. Otherwise, return nullptr.
+  // This method is used in Envoy.
+  virtual SSL* GetSsl() const = 0;
+
   // Called to cancel retransmission of unencrypted crypto stream data.
   void NeuterUnencryptedStreamData();
 
diff --git a/quic/core/quic_crypto_stream_test.cc b/quic/core/quic_crypto_stream_test.cc
index 545fdd8..6624a95 100644
--- a/quic/core/quic_crypto_stream_test.cc
+++ b/quic/core/quic_crypto_stream_test.cc
@@ -79,6 +79,7 @@
   std::unique_ptr<QuicEncrypter> CreateCurrentOneRttEncrypter() override {
     return nullptr;
   }
+  SSL* GetSsl() const override { return nullptr; }
 
  private:
   QuicReferenceCountedPointer<QuicCryptoNegotiatedParameters> params_;
diff --git a/quic/core/quic_session_test.cc b/quic/core/quic_session_test.cc
index 7980256..f87302f 100644
--- a/quic/core/quic_session_test.cc
+++ b/quic/core/quic_session_test.cc
@@ -168,6 +168,8 @@
   void OnConnectionClosed(QuicErrorCode /*error*/,
                           ConnectionCloseSource /*source*/) override {}
 
+  SSL* GetSsl() const override { return nullptr; }
+
  private:
   using QuicCryptoStream::session;
 
diff --git a/quic/core/tls_client_handshaker.h b/quic/core/tls_client_handshaker.h
index eb39ccf..4e0e3b6 100644
--- a/quic/core/tls_client_handshaker.h
+++ b/quic/core/tls_client_handshaker.h
@@ -81,8 +81,9 @@
 
   void AllowEmptyAlpnForTests() { allow_empty_alpn_for_tests_ = true; }
   void AllowInvalidSNIForTests() { allow_invalid_sni_for_tests_ = true; }
-  SSL* GetSslForTests() { return tls_connection_.ssl(); }
-  const SSL* GetSslForTests() const { return tls_connection_.ssl(); }
+
+  // Make the SSL object from BoringSSL publicly accessible.
+  using TlsHandshaker::ssl;
 
  protected:
   const TlsConnection* tls_connection() const override {
diff --git a/quic/core/tls_server_handshaker.cc b/quic/core/tls_server_handshaker.cc
index 7da1f23..3abf0ac 100644
--- a/quic/core/tls_server_handshaker.cc
+++ b/quic/core/tls_server_handshaker.cc
@@ -1128,4 +1128,6 @@
   return result;
 }
 
+SSL* TlsServerHandshaker::GetSsl() const { return ssl(); }
+
 }  // namespace quic
diff --git a/quic/core/tls_server_handshaker.h b/quic/core/tls_server_handshaker.h
index f105676..f2a42ad 100644
--- a/quic/core/tls_server_handshaker.h
+++ b/quic/core/tls_server_handshaker.h
@@ -64,6 +64,7 @@
   bool ShouldSendExpectCTHeader() const override;
   bool DidCertMatchSni() const override;
   const ProofSource::Details* ProofSourceDetails() const override;
+  SSL* GetSsl() const override;
 
   // From QuicCryptoServerStreamBase and TlsHandshaker
   ssl_early_data_reason_t EarlyDataReason() const override;
diff --git a/quic/test_tools/quic_test_utils.h b/quic/test_tools/quic_test_utils.h
index 7053829..6e9db90 100644
--- a/quic/test_tools/quic_test_utils.h
+++ b/quic/test_tools/quic_test_utils.h
@@ -844,6 +844,7 @@
   std::unique_ptr<QuicEncrypter> CreateCurrentOneRttEncrypter() override {
     return nullptr;
   }
+  SSL* GetSsl() const override { return nullptr; }
 
  private:
   QuicReferenceCountedPointer<QuicCryptoNegotiatedParameters> params_;