| 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_server_stream.h" |    5 #include "net/quic/quic_crypto_server_stream.h" | 
|    6  |    6  | 
|    7 #include "base/base64.h" |    7 #include "base/base64.h" | 
|    8 #include "crypto/secure_hash.h" |    8 #include "crypto/secure_hash.h" | 
|    9 #include "net/quic/crypto/crypto_protocol.h" |    9 #include "net/quic/crypto/crypto_protocol.h" | 
|   10 #include "net/quic/crypto/crypto_utils.h" |   10 #include "net/quic/crypto/crypto_utils.h" | 
| (...skipping 14 matching lines...) Expand all  Loading... | 
|   25     QuicTime::Delta delta_largest_observed) { |   25     QuicTime::Delta delta_largest_observed) { | 
|   26   // The SHLO is sent in one packet. |   26   // The SHLO is sent in one packet. | 
|   27   server_stream_->OnServerHelloAcked(); |   27   server_stream_->OnServerHelloAcked(); | 
|   28 } |   28 } | 
|   29  |   29  | 
|   30 void ServerHelloNotifier::OnPacketRetransmitted(int /*retransmitted_bytes*/) {} |   30 void ServerHelloNotifier::OnPacketRetransmitted(int /*retransmitted_bytes*/) {} | 
|   31  |   31  | 
|   32 QuicCryptoServerStream::QuicCryptoServerStream( |   32 QuicCryptoServerStream::QuicCryptoServerStream( | 
|   33     const QuicCryptoServerConfig* crypto_config, |   33     const QuicCryptoServerConfig* crypto_config, | 
|   34     QuicSession* session) |   34     QuicSession* session) | 
|   35     : QuicCryptoStream(session), |   35     : QuicCryptoServerStreamBase(session), | 
|   36       crypto_config_(crypto_config), |   36       crypto_config_(crypto_config), | 
|   37       validate_client_hello_cb_(nullptr), |   37       validate_client_hello_cb_(nullptr), | 
|   38       num_handshake_messages_(0), |   38       num_handshake_messages_(0), | 
|   39       num_handshake_messages_with_server_nonces_(0), |   39       num_handshake_messages_with_server_nonces_(0), | 
|   40       num_server_config_update_messages_sent_(0), |   40       num_server_config_update_messages_sent_(0), | 
|   41       use_stateless_rejects_if_peer_supported_( |   41       use_stateless_rejects_if_peer_supported_( | 
|   42           FLAGS_enable_quic_stateless_reject_support), |   42           FLAGS_enable_quic_stateless_reject_support), | 
|   43       peer_supports_stateless_rejects_(false) { |   43       peer_supports_stateless_rejects_(false) { | 
|   44   DCHECK_EQ(Perspective::IS_SERVER, session->connection()->perspective()); |   44   DCHECK_EQ(Perspective::IS_SERVER, session->connection()->perspective()); | 
|   45 } |   45 } | 
|   46  |   46  | 
|   47 QuicCryptoServerStream::~QuicCryptoServerStream() { |   47 QuicCryptoServerStream::~QuicCryptoServerStream() { | 
|   48   CancelOutstandingCallbacks(); |   48   CancelOutstandingCallbacks(); | 
|   49 } |   49 } | 
|   50  |   50  | 
|   51 void QuicCryptoServerStream::CancelOutstandingCallbacks() { |   51 void QuicCryptoServerStream::CancelOutstandingCallbacks() { | 
|   52   // Detach from the validation callback.  Calling this multiple times is safe. |   52   // Detach from the validation callback.  Calling this multiple times is safe. | 
|   53   if (validate_client_hello_cb_ != nullptr) { |   53   if (validate_client_hello_cb_ != nullptr) { | 
|   54     validate_client_hello_cb_->Cancel(); |   54     validate_client_hello_cb_->Cancel(); | 
|   55   } |   55   } | 
|   56 } |   56 } | 
|   57  |   57  | 
|   58 void QuicCryptoServerStream::OnHandshakeMessage( |   58 void QuicCryptoServerStream::OnHandshakeMessage( | 
|   59     const CryptoHandshakeMessage& message) { |   59     const CryptoHandshakeMessage& message) { | 
|   60   QuicCryptoStream::OnHandshakeMessage(message); |   60   QuicCryptoServerStreamBase::OnHandshakeMessage(message); | 
|   61   ++num_handshake_messages_; |   61   ++num_handshake_messages_; | 
|   62  |   62  | 
|   63   // Do not process handshake messages after the handshake is confirmed. |   63   // Do not process handshake messages after the handshake is confirmed. | 
|   64   if (handshake_confirmed_) { |   64   if (handshake_confirmed_) { | 
|   65     CloseConnection(QUIC_CRYPTO_MESSAGE_AFTER_HANDSHAKE_COMPLETE); |   65     CloseConnection(QUIC_CRYPTO_MESSAGE_AFTER_HANDSHAKE_COMPLETE); | 
|   66     return; |   66     return; | 
|   67   } |   67   } | 
|   68  |   68  | 
|   69   if (message.tag() != kCHLO) { |   69   if (message.tag() != kCHLO) { | 
|   70     CloseConnection(QUIC_INVALID_CRYPTO_MESSAGE_TYPE); |   70     CloseConnection(QUIC_INVALID_CRYPTO_MESSAGE_TYPE); | 
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  103   QuicErrorCode error = |  103   QuicErrorCode error = | 
|  104       ProcessClientHello(message, result, &reply, &error_details); |  104       ProcessClientHello(message, result, &reply, &error_details); | 
|  105  |  105  | 
|  106   if (error != QUIC_NO_ERROR) { |  106   if (error != QUIC_NO_ERROR) { | 
|  107     CloseConnectionWithDetails(error, error_details); |  107     CloseConnectionWithDetails(error, error_details); | 
|  108     return; |  108     return; | 
|  109   } |  109   } | 
|  110  |  110  | 
|  111   if (reply.tag() != kSHLO) { |  111   if (reply.tag() != kSHLO) { | 
|  112     if (reply.tag() == kSREJ) { |  112     if (reply.tag() == kSREJ) { | 
|  113       DCHECK(use_stateless_rejects_if_peer_supported()); |  113       DCHECK(use_stateless_rejects_if_peer_supported_); | 
|  114       DCHECK(peer_supports_stateless_rejects()); |  114       DCHECK(peer_supports_stateless_rejects_); | 
|  115       // Before sending the SREJ, cause the connection to save crypto packets |  115       // Before sending the SREJ, cause the connection to save crypto packets | 
|  116       // so that they can be added to the time wait list manager and |  116       // so that they can be added to the time wait list manager and | 
|  117       // retransmitted. |  117       // retransmitted. | 
|  118       session()->connection()->EnableSavingCryptoPackets(); |  118       session()->connection()->EnableSavingCryptoPackets(); | 
|  119     } |  119     } | 
|  120     SendHandshakeMessage(reply); |  120     SendHandshakeMessage(reply); | 
|  121  |  121  | 
|  122     if (reply.tag() == kSREJ) { |  122     if (reply.tag() == kSREJ) { | 
|  123       DCHECK(use_stateless_rejects_if_peer_supported()); |  123       DCHECK(use_stateless_rejects_if_peer_supported_); | 
|  124       DCHECK(peer_supports_stateless_rejects()); |  124       DCHECK(peer_supports_stateless_rejects_); | 
|  125       DCHECK(!handshake_confirmed()); |  125       DCHECK(!handshake_confirmed()); | 
|  126       DVLOG(1) << "Closing connection " |  126       DVLOG(1) << "Closing connection " | 
|  127                << session()->connection()->connection_id() |  127                << session()->connection()->connection_id() | 
|  128                << " because of a stateless reject."; |  128                << " because of a stateless reject."; | 
|  129       session()->connection()->CloseConnection( |  129       session()->connection()->CloseConnection( | 
|  130           QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT, /* from_peer */ false); |  130           QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT, /* from_peer */ false); | 
|  131     } |  131     } | 
|  132     return; |  132     return; | 
|  133   } |  133   } | 
|  134  |  134  | 
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  205   const QuicData& data = server_config_update_message.GetSerialized(); |  205   const QuicData& data = server_config_update_message.GetSerialized(); | 
|  206   WriteOrBufferData(string(data.data(), data.length()), false, nullptr); |  206   WriteOrBufferData(string(data.data(), data.length()), false, nullptr); | 
|  207  |  207  | 
|  208   ++num_server_config_update_messages_sent_; |  208   ++num_server_config_update_messages_sent_; | 
|  209 } |  209 } | 
|  210  |  210  | 
|  211 void QuicCryptoServerStream::OnServerHelloAcked() { |  211 void QuicCryptoServerStream::OnServerHelloAcked() { | 
|  212   session()->connection()->OnHandshakeComplete(); |  212   session()->connection()->OnHandshakeComplete(); | 
|  213 } |  213 } | 
|  214  |  214  | 
|  215 void QuicCryptoServerStream::set_previous_cached_network_params( |  215 uint8 QuicCryptoServerStream::NumHandshakeMessages() const { | 
 |  216   return num_handshake_messages_; | 
 |  217 } | 
 |  218  | 
 |  219 uint8 QuicCryptoServerStream::NumHandshakeMessagesWithServerNonces() const { | 
 |  220   return num_handshake_messages_with_server_nonces_; | 
 |  221 } | 
 |  222  | 
 |  223 int QuicCryptoServerStream::NumServerConfigUpdateMessagesSent() const { | 
 |  224   return num_server_config_update_messages_sent_; | 
 |  225 } | 
 |  226  | 
 |  227 const CachedNetworkParameters* | 
 |  228 QuicCryptoServerStream::PreviousCachedNetworkParams() const { | 
 |  229   return previous_cached_network_params_.get(); | 
 |  230 } | 
 |  231  | 
 |  232 bool QuicCryptoServerStream::UseStatelessRejectsIfPeerSupported() const { | 
 |  233   return use_stateless_rejects_if_peer_supported_; | 
 |  234 } | 
 |  235  | 
 |  236 bool QuicCryptoServerStream::PeerSupportsStatelessRejects() const { | 
 |  237   return peer_supports_stateless_rejects_; | 
 |  238 } | 
 |  239  | 
 |  240 void QuicCryptoServerStream::SetPeerSupportsStatelessRejects( | 
 |  241     bool peer_supports_stateless_rejects) { | 
 |  242   peer_supports_stateless_rejects_ = peer_supports_stateless_rejects; | 
 |  243 } | 
 |  244  | 
 |  245 void QuicCryptoServerStream::SetPreviousCachedNetworkParams( | 
|  216     CachedNetworkParameters cached_network_params) { |  246     CachedNetworkParameters cached_network_params) { | 
|  217   previous_cached_network_params_.reset( |  247   previous_cached_network_params_.reset( | 
|  218       new CachedNetworkParameters(cached_network_params)); |  248       new CachedNetworkParameters(cached_network_params)); | 
|  219 } |  249 } | 
|  220  |  250  | 
|  221 bool QuicCryptoServerStream::GetBase64SHA256ClientChannelID( |  251 bool QuicCryptoServerStream::GetBase64SHA256ClientChannelID( | 
|  222     string* output) const { |  252     string* output) const { | 
|  223   if (!encryption_established_ || |  253   if (!encryption_established_ || | 
|  224       crypto_negotiated_params_.channel_id.empty()) { |  254       crypto_negotiated_params_.channel_id.empty()) { | 
|  225     return false; |  255     return false; | 
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  275       result, connection->connection_id(), connection->self_address().address(), |  305       result, connection->connection_id(), connection->self_address().address(), | 
|  276       connection->peer_address(), version(), connection->supported_versions(), |  306       connection->peer_address(), version(), connection->supported_versions(), | 
|  277       use_stateless_rejects_in_crypto_config, server_designated_connection_id, |  307       use_stateless_rejects_in_crypto_config, server_designated_connection_id, | 
|  278       connection->clock(), connection->random_generator(), |  308       connection->clock(), connection->random_generator(), | 
|  279       &crypto_negotiated_params_, &crypto_proof_, reply, error_details); |  309       &crypto_negotiated_params_, &crypto_proof_, reply, error_details); | 
|  280 } |  310 } | 
|  281  |  311  | 
|  282 void QuicCryptoServerStream::OverrideQuicConfigDefaults(QuicConfig* config) { |  312 void QuicCryptoServerStream::OverrideQuicConfigDefaults(QuicConfig* config) { | 
|  283 } |  313 } | 
|  284  |  314  | 
|  285 const CachedNetworkParameters* |  | 
|  286 QuicCryptoServerStream::previous_cached_network_params() const { |  | 
|  287   return previous_cached_network_params_.get(); |  | 
|  288 } |  | 
|  289  |  | 
|  290 QuicCryptoServerStream::ValidateCallback::ValidateCallback( |  315 QuicCryptoServerStream::ValidateCallback::ValidateCallback( | 
|  291     QuicCryptoServerStream* parent) : parent_(parent) { |  316     QuicCryptoServerStream* parent) : parent_(parent) { | 
|  292 } |  317 } | 
|  293  |  318  | 
|  294 void QuicCryptoServerStream::ValidateCallback::Cancel() { parent_ = nullptr; } |  319 void QuicCryptoServerStream::ValidateCallback::Cancel() { parent_ = nullptr; } | 
|  295  |  320  | 
|  296 void QuicCryptoServerStream::ValidateCallback::RunImpl( |  321 void QuicCryptoServerStream::ValidateCallback::RunImpl( | 
|  297     const CryptoHandshakeMessage& client_hello, |  322     const CryptoHandshakeMessage& client_hello, | 
|  298     const Result& result) { |  323     const Result& result) { | 
|  299   if (parent_ != nullptr) { |  324   if (parent_ != nullptr) { | 
| (...skipping 20 matching lines...) Expand all  Loading... | 
|  320   } |  345   } | 
|  321   for (size_t i = 0; i < received_tags_length; ++i) { |  346   for (size_t i = 0; i < received_tags_length; ++i) { | 
|  322     if (received_tags[i] == kSREJ) { |  347     if (received_tags[i] == kSREJ) { | 
|  323       return true; |  348       return true; | 
|  324     } |  349     } | 
|  325   } |  350   } | 
|  326   return false; |  351   return false; | 
|  327 } |  352 } | 
|  328  |  353  | 
|  329 }  // namespace net |  354 }  // namespace net | 
| OLD | NEW |