| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "net/quic/quic_crypto_client_stream.h" | 5 #include "net/quic/quic_crypto_client_stream.h" |
| 6 | 6 |
| 7 #include "net/quic/crypto/crypto_protocol.h" | 7 #include "net/quic/crypto/crypto_protocol.h" |
| 8 #include "net/quic/crypto/crypto_utils.h" | 8 #include "net/quic/crypto/crypto_utils.h" |
| 9 #include "net/quic/crypto/null_encrypter.h" | 9 #include "net/quic/crypto/null_encrypter.h" |
| 10 #include "net/quic/crypto/proof_verifier.h" | 10 #include "net/quic/crypto/proof_verifier.h" |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 51 | 51 |
| 52 void QuicCryptoClientStream::DoHandshakeLoop( | 52 void QuicCryptoClientStream::DoHandshakeLoop( |
| 53 const CryptoHandshakeMessage* in) { | 53 const CryptoHandshakeMessage* in) { |
| 54 CryptoHandshakeMessage out; | 54 CryptoHandshakeMessage out; |
| 55 QuicErrorCode error; | 55 QuicErrorCode error; |
| 56 string error_details; | 56 string error_details; |
| 57 QuicCryptoClientConfig::CachedState* cached = | 57 QuicCryptoClientConfig::CachedState* cached = |
| 58 crypto_config_->LookupOrCreate(server_hostname_); | 58 crypto_config_->LookupOrCreate(server_hostname_); |
| 59 | 59 |
| 60 if (in != NULL) { | 60 if (in != NULL) { |
| 61 DLOG(INFO) << "Client received: " << in->DebugString(); | 61 DVLOG(1) << "Client received: " << in->DebugString(); |
| 62 } | 62 } |
| 63 | 63 |
| 64 for (;;) { | 64 for (;;) { |
| 65 const State state = next_state_; | 65 const State state = next_state_; |
| 66 next_state_ = STATE_IDLE; | 66 next_state_ = STATE_IDLE; |
| 67 switch (state) { | 67 switch (state) { |
| 68 case STATE_SEND_CHLO: { | 68 case STATE_SEND_CHLO: { |
| 69 if (num_client_hellos_ > kMaxClientHellos) { | 69 if (num_client_hellos_ > kMaxClientHellos) { |
| 70 CloseConnection(QUIC_CRYPTO_TOO_MANY_REJECTS); | 70 CloseConnection(QUIC_CRYPTO_TOO_MANY_REJECTS); |
| 71 return; | 71 return; |
| 72 } | 72 } |
| 73 num_client_hellos_++; | 73 num_client_hellos_++; |
| 74 | 74 |
| 75 if (!cached->is_complete()) { | 75 if (!cached->IsComplete(session()->connection()->clock()->WallNow())) { |
| 76 crypto_config_->FillInchoateClientHello( | 76 crypto_config_->FillInchoateClientHello( |
| 77 server_hostname_, cached, &crypto_negotiated_params_, &out); | 77 server_hostname_, cached, &crypto_negotiated_params_, &out); |
| 78 next_state_ = STATE_RECV_REJ; | 78 next_state_ = STATE_RECV_REJ; |
| 79 DLOG(INFO) << "Client Sending: " << out.DebugString(); | 79 DVLOG(1) << "Client Sending: " << out.DebugString(); |
| 80 SendHandshakeMessage(out); | 80 SendHandshakeMessage(out); |
| 81 return; | 81 return; |
| 82 } | 82 } |
| 83 session()->config()->ToHandshakeMessage(&out); | 83 session()->config()->ToHandshakeMessage(&out); |
| 84 error = crypto_config_->FillClientHello( | 84 error = crypto_config_->FillClientHello( |
| 85 server_hostname_, | 85 server_hostname_, |
| 86 session()->connection()->guid(), | 86 session()->connection()->guid(), |
| 87 cached, | 87 cached, |
| 88 session()->connection()->clock()->WallNow(), | 88 session()->connection()->clock()->WallNow(), |
| 89 session()->connection()->random_generator(), | 89 session()->connection()->random_generator(), |
| 90 &crypto_negotiated_params_, | 90 &crypto_negotiated_params_, |
| 91 &out, | 91 &out, |
| 92 &error_details); | 92 &error_details); |
| 93 if (error != QUIC_NO_ERROR) { | 93 if (error != QUIC_NO_ERROR) { |
| 94 // Flush the cached config so that, if it's bad, the server has a |
| 95 // chance to send us another in the future. |
| 96 cached->InvalidateServerConfig(); |
| 94 CloseConnectionWithDetails(error, error_details); | 97 CloseConnectionWithDetails(error, error_details); |
| 95 return; | 98 return; |
| 96 } | 99 } |
| 97 next_state_ = STATE_RECV_SHLO; | 100 next_state_ = STATE_RECV_SHLO; |
| 98 DLOG(INFO) << "Client Sending: " << out.DebugString(); | 101 DVLOG(1) << "Client Sending: " << out.DebugString(); |
| 99 SendHandshakeMessage(out); | 102 SendHandshakeMessage(out); |
| 100 // Be prepared to decrypt with the new server write key. | 103 // Be prepared to decrypt with the new server write key. |
| 101 session()->connection()->SetAlternativeDecrypter( | 104 session()->connection()->SetAlternativeDecrypter( |
| 102 crypto_negotiated_params_.initial_crypters.decrypter.release(), | 105 crypto_negotiated_params_.initial_crypters.decrypter.release(), |
| 103 true /* latch once used */); | 106 true /* latch once used */); |
| 104 // Send subsequent packets under encryption on the assumption that the | 107 // Send subsequent packets under encryption on the assumption that the |
| 105 // server will accept the handshake. | 108 // server will accept the handshake. |
| 106 session()->connection()->SetEncrypter( | 109 session()->connection()->SetEncrypter( |
| 107 ENCRYPTION_INITIAL, | 110 ENCRYPTION_INITIAL, |
| 108 crypto_negotiated_params_.initial_crypters.encrypter.release()); | 111 crypto_negotiated_params_.initial_crypters.encrypter.release()); |
| (...skipping 18 matching lines...) Expand all Loading... |
| 127 case STATE_RECV_REJ: | 130 case STATE_RECV_REJ: |
| 128 // We sent a dummy CHLO because we didn't have enough information to | 131 // We sent a dummy CHLO because we didn't have enough information to |
| 129 // perform a handshake, or we sent a full hello that the server | 132 // perform a handshake, or we sent a full hello that the server |
| 130 // rejected. Here we hope to have a REJ that contains the information | 133 // rejected. Here we hope to have a REJ that contains the information |
| 131 // that we need. | 134 // that we need. |
| 132 if (in->tag() != kREJ) { | 135 if (in->tag() != kREJ) { |
| 133 CloseConnectionWithDetails(QUIC_INVALID_CRYPTO_MESSAGE_TYPE, | 136 CloseConnectionWithDetails(QUIC_INVALID_CRYPTO_MESSAGE_TYPE, |
| 134 "Expected REJ"); | 137 "Expected REJ"); |
| 135 return; | 138 return; |
| 136 } | 139 } |
| 137 error = crypto_config_->ProcessRejection(cached, *in, | 140 error = crypto_config_->ProcessRejection( |
| 138 &crypto_negotiated_params_, | 141 cached, *in, session()->connection()->clock()->WallNow(), |
| 139 &error_details); | 142 &crypto_negotiated_params_, &error_details); |
| 140 if (error != QUIC_NO_ERROR) { | 143 if (error != QUIC_NO_ERROR) { |
| 141 CloseConnectionWithDetails(error, error_details); | 144 CloseConnectionWithDetails(error, error_details); |
| 142 return; | 145 return; |
| 143 } | 146 } |
| 144 if (!cached->proof_valid()) { | 147 if (!cached->proof_valid()) { |
| 145 const ProofVerifier* verifier = crypto_config_->proof_verifier(); | 148 const ProofVerifier* verifier = crypto_config_->proof_verifier(); |
| 146 if (!verifier) { | 149 if (!verifier) { |
| 147 // If no verifier is set then we don't check the certificates. | 150 // If no verifier is set then we don't check the certificates. |
| 148 cached->SetProofValid(); | 151 cached->SetProofValid(); |
| 149 } else if (!cached->signature().empty()) { | 152 } else if (!cached->signature().empty()) { |
| (...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 235 } | 238 } |
| 236 case STATE_IDLE: | 239 case STATE_IDLE: |
| 237 // This means that the peer sent us a message that we weren't expecting. | 240 // This means that the peer sent us a message that we weren't expecting. |
| 238 CloseConnection(QUIC_INVALID_CRYPTO_MESSAGE_TYPE); | 241 CloseConnection(QUIC_INVALID_CRYPTO_MESSAGE_TYPE); |
| 239 return; | 242 return; |
| 240 } | 243 } |
| 241 } | 244 } |
| 242 } | 245 } |
| 243 | 246 |
| 244 } // namespace net | 247 } // namespace net |
| OLD | NEW |