Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(86)

Side by Side Diff: net/tools/quic/quic_dispatcher.cc

Issue 1128103007: Protected by FLAGS_enable_quic_stateless_reject_support. Add support (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@Added_support_for_stateless_time_wait_93412303
Patch Set: Created 5 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « net/tools/quic/quic_dispatcher.h ('k') | net/tools/quic/quic_dispatcher_test.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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/tools/quic/quic_dispatcher.h" 5 #include "net/tools/quic/quic_dispatcher.h"
6 6
7 #include <utility> 7 #include <utility>
8 8
9 #include "base/debug/stack_trace.h" 9 #include "base/debug/stack_trace.h"
10 #include "base/logging.h" 10 #include "base/logging.h"
11 #include "base/stl_util.h" 11 #include "base/stl_util.h"
12 #include "net/quic/quic_flags.h"
12 #include "net/quic/quic_utils.h" 13 #include "net/quic/quic_utils.h"
13 #include "net/tools/quic/quic_per_connection_packet_writer.h" 14 #include "net/tools/quic/quic_per_connection_packet_writer.h"
14 #include "net/tools/quic/quic_time_wait_list_manager.h" 15 #include "net/tools/quic/quic_time_wait_list_manager.h"
15 16
16 namespace net { 17 namespace net {
17 18
18 namespace tools { 19 namespace tools {
19 20
20 using std::make_pair; 21 using std::make_pair;
21 using base::StringPiece; 22 using base::StringPiece;
22 23
24 // The threshold size for the session map, over which the dispatcher will start
25 // sending stateless rejects (SREJ), rather than stateful rejects (REJ) to
26 // clients who support them. If -1, stateless rejects will not be sent. If 0,
27 // the server will only send stateless rejects to clients who support them.
28 int32 FLAGS_quic_session_map_threshold_for_stateless_rejects = -1;
29
23 namespace { 30 namespace {
24 31
25 // An alarm that informs the QuicDispatcher to delete old sessions. 32 // An alarm that informs the QuicDispatcher to delete old sessions.
26 class DeleteSessionsAlarm : public QuicAlarm::Delegate { 33 class DeleteSessionsAlarm : public QuicAlarm::Delegate {
27 public: 34 public:
28 explicit DeleteSessionsAlarm(QuicDispatcher* dispatcher) 35 explicit DeleteSessionsAlarm(QuicDispatcher* dispatcher)
29 : dispatcher_(dispatcher) { 36 : dispatcher_(dispatcher) {
30 } 37 }
31 38
32 QuicTime OnAlarm() override { 39 QuicTime OnAlarm() override {
(...skipping 250 matching lines...) Expand 10 before | Expand all | Expand 10 after
283 QuicPacketFate fate = ValidityChecks(header); 290 QuicPacketFate fate = ValidityChecks(header);
284 switch (fate) { 291 switch (fate) {
285 case kFateProcess: { 292 case kFateProcess: {
286 // Create a session and process the packet. 293 // Create a session and process the packet.
287 QuicServerSession* session = CreateQuicSession( 294 QuicServerSession* session = CreateQuicSession(
288 connection_id, current_server_address_, current_client_address_); 295 connection_id, current_server_address_, current_client_address_);
289 DVLOG(1) << "Created new session for " << connection_id; 296 DVLOG(1) << "Created new session for " << connection_id;
290 session_map_.insert(make_pair(connection_id, session)); 297 session_map_.insert(make_pair(connection_id, session));
291 session->connection()->ProcessUdpPacket( 298 session->connection()->ProcessUdpPacket(
292 current_server_address_, current_client_address_, *current_packet_); 299 current_server_address_, current_client_address_, *current_packet_);
300
301 if (FLAGS_enable_quic_stateless_reject_support &&
302 session->UsingStatelessRejectsIfPeerSupported() &&
303 session->PeerSupportsStatelessRejects() &&
304 !session->IsCryptoHandshakeConfirmed()) {
305 DVLOG(1) << "Removing new session for " << connection_id
306 << " because the session is in stateless reject mode and"
307 << " encryption has not been established.";
308 session->connection()->CloseConnection(
309 QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT, /* from_peer */ false);
310 }
293 break; 311 break;
294 } 312 }
295 case kFateTimeWait: 313 case kFateTimeWait:
296 // Add this connection_id to the time-wait state, to safely reject 314 // Add this connection_id to the time-wait state, to safely reject
297 // future packets. 315 // future packets.
298 DVLOG(1) << "Adding connection ID " << connection_id 316 DVLOG(1) << "Adding connection ID " << connection_id
299 << "to time-wait list."; 317 << "to time-wait list.";
300 time_wait_list_manager_->AddConnectionIdToTimeWait( 318 time_wait_list_manager_->AddConnectionIdToTimeWait(
301 connection_id, framer_.version(), 319 connection_id, framer_.version(),
302 /*connection_rejected_statelessly=*/false, nullptr); 320 /*connection_rejected_statelessly=*/false, nullptr);
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
337 // Check that the sequence numer is within the range that the client is 355 // Check that the sequence numer is within the range that the client is
338 // expected to send before receiving a response from the server. 356 // expected to send before receiving a response from the server.
339 if (header.packet_sequence_number == kInvalidPacketSequenceNumber || 357 if (header.packet_sequence_number == kInvalidPacketSequenceNumber ||
340 header.packet_sequence_number > kMaxReasonableInitialSequenceNumber) { 358 header.packet_sequence_number > kMaxReasonableInitialSequenceNumber) {
341 return kFateTimeWait; 359 return kFateTimeWait;
342 } 360 }
343 361
344 return kFateProcess; 362 return kFateProcess;
345 } 363 }
346 364
347 void QuicDispatcher::CleanUpSession(SessionMap::iterator it) { 365 void QuicDispatcher::CleanUpSession(SessionMap::iterator it,
366 bool should_close_statelessly) {
348 QuicConnection* connection = it->second->connection(); 367 QuicConnection* connection = it->second->connection();
349 QuicEncryptedPacket* connection_close_packet = 368 QuicEncryptedPacket* connection_close_packet =
350 connection->ReleaseConnectionClosePacket(); 369 connection->ReleaseConnectionClosePacket();
351 write_blocked_list_.erase(connection); 370 write_blocked_list_.erase(connection);
371 DCHECK(!should_close_statelessly || !connection_close_packet);
352 time_wait_list_manager_->AddConnectionIdToTimeWait( 372 time_wait_list_manager_->AddConnectionIdToTimeWait(
353 it->first, connection->version(), 373 it->first, connection->version(), should_close_statelessly,
354 /*connection_rejected_statelessly=*/false, connection_close_packet); 374 connection_close_packet);
355 session_map_.erase(it); 375 session_map_.erase(it);
356 } 376 }
357 377
358 void QuicDispatcher::DeleteSessions() { 378 void QuicDispatcher::DeleteSessions() {
359 STLDeleteElements(&closed_session_list_); 379 STLDeleteElements(&closed_session_list_);
360 } 380 }
361 381
362 void QuicDispatcher::OnCanWrite() { 382 void QuicDispatcher::OnCanWrite() {
363 // The socket is now writable. 383 // The socket is now writable.
364 writer_->SetWritable(); 384 writer_->SetWritable();
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
401 DVLOG_IF(1, error != QUIC_NO_ERROR) << "Closing connection (" 421 DVLOG_IF(1, error != QUIC_NO_ERROR) << "Closing connection ("
402 << connection_id 422 << connection_id
403 << ") due to error: " 423 << ") due to error: "
404 << QuicUtils::ErrorToString(error); 424 << QuicUtils::ErrorToString(error);
405 425
406 if (closed_session_list_.empty()) { 426 if (closed_session_list_.empty()) {
407 delete_sessions_alarm_->Cancel(); 427 delete_sessions_alarm_->Cancel();
408 delete_sessions_alarm_->Set(helper()->GetClock()->ApproximateNow()); 428 delete_sessions_alarm_->Set(helper()->GetClock()->ApproximateNow());
409 } 429 }
410 closed_session_list_.push_back(it->second); 430 closed_session_list_.push_back(it->second);
411 CleanUpSession(it); 431 const bool should_close_statelessly =
432 (error == QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT);
433 CleanUpSession(it, should_close_statelessly);
412 } 434 }
413 435
414 void QuicDispatcher::OnWriteBlocked( 436 void QuicDispatcher::OnWriteBlocked(
415 QuicBlockedWriterInterface* blocked_writer) { 437 QuicBlockedWriterInterface* blocked_writer) {
416 if (!writer_->IsWriteBlocked()) { 438 if (!writer_->IsWriteBlocked()) {
417 LOG(DFATAL) << 439 LOG(DFATAL) <<
418 "QuicDispatcher::OnWriteBlocked called when the writer is not blocked."; 440 "QuicDispatcher::OnWriteBlocked called when the writer is not blocked.";
419 // Return without adding the connection to the blocked list, to avoid 441 // Return without adding the connection to the blocked list, to avoid
420 // infinite loops in OnCanWrite. 442 // infinite loops in OnCanWrite.
421 return; 443 return;
(...skipping 16 matching lines...) Expand all
438 const IPEndPoint& server_address, 460 const IPEndPoint& server_address,
439 const IPEndPoint& client_address) { 461 const IPEndPoint& client_address) {
440 // The QuicServerSession takes ownership of |connection| below. 462 // The QuicServerSession takes ownership of |connection| below.
441 QuicConnection* connection = new QuicConnection( 463 QuicConnection* connection = new QuicConnection(
442 connection_id, client_address, helper_.get(), connection_writer_factory_, 464 connection_id, client_address, helper_.get(), connection_writer_factory_,
443 /* owns_writer= */ true, Perspective::IS_SERVER, 465 /* owns_writer= */ true, Perspective::IS_SERVER,
444 crypto_config_->HasProofSource(), supported_versions_); 466 crypto_config_->HasProofSource(), supported_versions_);
445 467
446 QuicServerSession* session = new QuicServerSession(config_, connection, this); 468 QuicServerSession* session = new QuicServerSession(config_, connection, this);
447 session->InitializeSession(crypto_config_); 469 session->InitializeSession(crypto_config_);
470 if (FLAGS_quic_session_map_threshold_for_stateless_rejects != -1 &&
471 session_map_.size() >=
472 static_cast<size_t>(
473 FLAGS_quic_session_map_threshold_for_stateless_rejects)) {
474 session->set_use_stateless_rejects_if_peer_supported(true);
475 }
448 return session; 476 return session;
449 } 477 }
450 478
451 QuicTimeWaitListManager* QuicDispatcher::CreateQuicTimeWaitListManager() { 479 QuicTimeWaitListManager* QuicDispatcher::CreateQuicTimeWaitListManager() {
452 return new QuicTimeWaitListManager( 480 return new QuicTimeWaitListManager(
453 writer_.get(), this, helper_.get(), supported_versions()); 481 writer_.get(), this, helper_.get(), supported_versions());
454 } 482 }
455 483
456 bool QuicDispatcher::HandlePacketForTimeWait( 484 bool QuicDispatcher::HandlePacketForTimeWait(
457 const QuicPacketPublicHeader& header) { 485 const QuicPacketPublicHeader& header) {
458 if (header.reset_flag) { 486 if (header.reset_flag) {
459 // Public reset packets do not have sequence numbers, so ignore the packet. 487 // Public reset packets do not have sequence numbers, so ignore the packet.
460 return false; 488 return false;
461 } 489 }
462 490
463 // Switch the framer to the correct version, so that the sequence number can 491 // Switch the framer to the correct version, so that the sequence number can
464 // be parsed correctly. 492 // be parsed correctly.
465 framer_.set_version(time_wait_list_manager_->GetQuicVersionFromConnectionId( 493 framer_.set_version(time_wait_list_manager_->GetQuicVersionFromConnectionId(
466 header.connection_id)); 494 header.connection_id));
467 495
468 // Continue parsing the packet to extract the sequence number. Then 496 // Continue parsing the packet to extract the sequence number. Then
469 // send it to the time wait manager in OnUnathenticatedHeader. 497 // send it to the time wait manager in OnUnathenticatedHeader.
470 return true; 498 return true;
471 } 499 }
472 500
473 } // namespace tools 501 } // namespace tools
474 } // namespace net 502 } // namespace net
OLDNEW
« no previous file with comments | « net/tools/quic/quic_dispatcher.h ('k') | net/tools/quic/quic_dispatcher_test.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698