Add new methods to QuicFramer for controlling decrypters

This CL is a roll forward of cl/243273832. David had to make test-only changes to fix the broken test //third_party/quic/core:tls_handshaker_test. And the chromium patch is ready.

gfe-relnote: Protected behind QUIC_VERSION_99 and quic_supports_tls_handshake
PiperOrigin-RevId: 243344023
Change-Id: Ia845325b55557d4d8811d6641ae5b50bdf2aed45
diff --git a/quic/core/quic_crypto_client_handshaker.cc b/quic/core/quic_crypto_client_handshaker.cc
index 013ab3f..d6c9af4 100644
--- a/quic/core/quic_crypto_client_handshaker.cc
+++ b/quic/core/quic_crypto_client_handshaker.cc
@@ -375,10 +375,16 @@
       crypto_config_->pad_full_hello());
   SendHandshakeMessage(out);
   // Be prepared to decrypt with the new server write key.
-  session()->connection()->SetAlternativeDecrypter(
-      ENCRYPTION_ZERO_RTT,
-      std::move(crypto_negotiated_params_->initial_crypters.decrypter),
-      true /* latch once used */);
+  if (session()->connection()->version().KnowsWhichDecrypterToUse()) {
+    session()->connection()->InstallDecrypter(
+        ENCRYPTION_ZERO_RTT,
+        std::move(crypto_negotiated_params_->initial_crypters.decrypter));
+  } else {
+    session()->connection()->SetAlternativeDecrypter(
+        ENCRYPTION_ZERO_RTT,
+        std::move(crypto_negotiated_params_->initial_crypters.decrypter),
+        true /* latch once used */);
+  }
   // Send subsequent packets under encryption on the assumption that the
   // server will accept the handshake.
   session()->connection()->SetEncrypter(
@@ -584,10 +590,8 @@
   // to see whether the response was a reject, and if so, move on to
   // the reject-processing state.
   if ((in->tag() == kREJ) || (in->tag() == kSREJ)) {
-    // alternative_decrypter will be nullptr if the original alternative
-    // decrypter latched and became the primary decrypter. That happens
-    // if we received a message encrypted with the INITIAL key.
-    if (session()->connection()->alternative_decrypter() == nullptr) {
+    // A reject message must be sent in ENCRYPTION_INITIAL.
+    if (session()->connection()->last_decrypted_level() != ENCRYPTION_INITIAL) {
       // The rejection was sent encrypted!
       stream_->CloseConnectionWithDetails(
           QUIC_CRYPTO_ENCRYPTION_LEVEL_INCORRECT, "encrypted REJ message");
@@ -603,10 +607,7 @@
     return;
   }
 
-  // alternative_decrypter will be nullptr if the original alternative
-  // decrypter latched and became the primary decrypter. That happens
-  // if we received a message encrypted with the INITIAL key.
-  if (session()->connection()->alternative_decrypter() != nullptr) {
+  if (session()->connection()->last_decrypted_level() == ENCRYPTION_INITIAL) {
     // The server hello was sent without encryption.
     stream_->CloseConnectionWithDetails(QUIC_CRYPTO_ENCRYPTION_LEVEL_INCORRECT,
                                         "unencrypted SHLO message");
@@ -638,9 +639,14 @@
   // has been floated that the server shouldn't send packets encrypted
   // with the FORWARD_SECURE key until it receives a FORWARD_SECURE
   // packet from the client.
-  session()->connection()->SetAlternativeDecrypter(
-      ENCRYPTION_FORWARD_SECURE, std::move(crypters->decrypter),
-      false /* don't latch */);
+  if (session()->connection()->version().KnowsWhichDecrypterToUse()) {
+    session()->connection()->InstallDecrypter(ENCRYPTION_FORWARD_SECURE,
+                                              std::move(crypters->decrypter));
+  } else {
+    session()->connection()->SetAlternativeDecrypter(
+        ENCRYPTION_FORWARD_SECURE, std::move(crypters->decrypter),
+        false /* don't latch */);
+  }
   session()->connection()->SetEncrypter(ENCRYPTION_FORWARD_SECURE,
                                         std::move(crypters->encrypter));
   session()->connection()->SetDefaultEncryptionLevel(ENCRYPTION_FORWARD_SECURE);