| 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/core/quic_session.h" | 5 #include "net/quic/core/quic_session.h" |
| 6 | 6 |
| 7 #include <cstdint> | 7 #include <cstdint> |
| 8 #include <utility> | 8 #include <utility> |
| 9 | 9 |
| 10 #include "net/quic/core/quic_connection.h" | 10 #include "net/quic/core/quic_connection.h" |
| (...skipping 27 matching lines...) Expand all Loading... |
| 38 num_locally_closed_incoming_streams_highest_offset_(0), | 38 num_locally_closed_incoming_streams_highest_offset_(0), |
| 39 error_(QUIC_NO_ERROR), | 39 error_(QUIC_NO_ERROR), |
| 40 flow_controller_(connection_, | 40 flow_controller_(connection_, |
| 41 0, | 41 0, |
| 42 perspective(), | 42 perspective(), |
| 43 kMinimumFlowControlSendWindow, | 43 kMinimumFlowControlSendWindow, |
| 44 config_.GetInitialSessionFlowControlWindowToSend(), | 44 config_.GetInitialSessionFlowControlWindowToSend(), |
| 45 perspective() == Perspective::IS_SERVER, | 45 perspective() == Perspective::IS_SERVER, |
| 46 nullptr), | 46 nullptr), |
| 47 currently_writing_stream_id_(0), | 47 currently_writing_stream_id_(0), |
| 48 respect_goaway_(true) {} | 48 respect_goaway_(true), |
| 49 use_stream_notifier_( |
| 50 FLAGS_quic_reloadable_flag_quic_use_stream_notifier) {} |
| 49 | 51 |
| 50 void QuicSession::Initialize() { | 52 void QuicSession::Initialize() { |
| 51 connection_->set_visitor(this); | 53 connection_->set_visitor(this); |
| 54 if (use_stream_notifier_) { |
| 55 connection_->SetStreamNotifier(this); |
| 56 } |
| 52 connection_->SetFromConfig(config_); | 57 connection_->SetFromConfig(config_); |
| 53 | 58 |
| 54 DCHECK_EQ(kCryptoStreamId, GetMutableCryptoStream()->id()); | 59 DCHECK_EQ(kCryptoStreamId, GetMutableCryptoStream()->id()); |
| 55 static_stream_map_[kCryptoStreamId] = GetMutableCryptoStream(); | 60 static_stream_map_[kCryptoStreamId] = GetMutableCryptoStream(); |
| 56 } | 61 } |
| 57 | 62 |
| 58 QuicSession::~QuicSession() { | 63 QuicSession::~QuicSession() { |
| 59 QUIC_LOG_IF(WARNING, num_locally_closed_incoming_streams_highest_offset() > | 64 QUIC_LOG_IF(WARNING, num_locally_closed_incoming_streams_highest_offset() > |
| 60 max_open_incoming_streams_) | 65 max_open_incoming_streams_) |
| 61 << "Surprisingly high number of locally closed peer initiated streams" | 66 << "Surprisingly high number of locally closed peer initiated streams" |
| 62 "still waiting for final byte offset: " | 67 "still waiting for final byte offset: " |
| 63 << num_locally_closed_incoming_streams_highest_offset(); | 68 << num_locally_closed_incoming_streams_highest_offset(); |
| 64 QUIC_LOG_IF(WARNING, GetNumLocallyClosedOutgoingStreamsHighestOffset() > | 69 QUIC_LOG_IF(WARNING, GetNumLocallyClosedOutgoingStreamsHighestOffset() > |
| 65 max_open_outgoing_streams_) | 70 max_open_outgoing_streams_) |
| 66 << "Surprisingly high number of locally closed self initiated streams" | 71 << "Surprisingly high number of locally closed self initiated streams" |
| 67 "still waiting for final byte offset: " | 72 "still waiting for final byte offset: " |
| 68 << GetNumLocallyClosedOutgoingStreamsHighestOffset(); | 73 << GetNumLocallyClosedOutgoingStreamsHighestOffset(); |
| 74 QUIC_LOG_IF(WARNING, !zombie_streams_.empty()) << "Still have zombie streams"; |
| 69 } | 75 } |
| 70 | 76 |
| 71 void QuicSession::OnStreamFrame(const QuicStreamFrame& frame) { | 77 void QuicSession::OnStreamFrame(const QuicStreamFrame& frame) { |
| 72 // TODO(rch) deal with the error case of stream id 0. | 78 // TODO(rch) deal with the error case of stream id 0. |
| 73 QuicStreamId stream_id = frame.stream_id; | 79 QuicStreamId stream_id = frame.stream_id; |
| 74 QuicStream* stream = GetOrCreateStream(stream_id); | 80 QuicStream* stream = GetOrCreateStream(stream_id); |
| 75 if (!stream) { | 81 if (!stream) { |
| 76 // The stream no longer exists, but we may still be interested in the | 82 // The stream no longer exists, but we may still be interested in the |
| 77 // final stream byte offset sent by the peer. A frame with a FIN can give | 83 // final stream byte offset sent by the peer. A frame with a FIN can give |
| 78 // us this offset. | 84 // us this offset. |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 122 DynamicStreamMap::iterator it = dynamic_stream_map_.begin(); | 128 DynamicStreamMap::iterator it = dynamic_stream_map_.begin(); |
| 123 QuicStreamId id = it->first; | 129 QuicStreamId id = it->first; |
| 124 it->second->OnConnectionClosed(error, source); | 130 it->second->OnConnectionClosed(error, source); |
| 125 // The stream should call CloseStream as part of OnConnectionClosed. | 131 // The stream should call CloseStream as part of OnConnectionClosed. |
| 126 if (dynamic_stream_map_.find(id) != dynamic_stream_map_.end()) { | 132 if (dynamic_stream_map_.find(id) != dynamic_stream_map_.end()) { |
| 127 QUIC_BUG << ENDPOINT << "Stream failed to close under OnConnectionClosed"; | 133 QUIC_BUG << ENDPOINT << "Stream failed to close under OnConnectionClosed"; |
| 128 CloseStream(id); | 134 CloseStream(id); |
| 129 } | 135 } |
| 130 } | 136 } |
| 131 | 137 |
| 138 // Cleanup zombie stream map on connection close. |
| 139 while (!zombie_streams_.empty()) { |
| 140 ZombieStreamMap::iterator it = zombie_streams_.begin(); |
| 141 closed_streams_.push_back(std::move(it->second)); |
| 142 zombie_streams_.erase(it); |
| 143 } |
| 144 |
| 132 if (visitor_) { | 145 if (visitor_) { |
| 133 visitor_->OnConnectionClosed(connection_->connection_id(), error, | 146 visitor_->OnConnectionClosed(connection_->connection_id(), error, |
| 134 error_details); | 147 error_details); |
| 135 } | 148 } |
| 136 } | 149 } |
| 137 | 150 |
| 138 void QuicSession::OnWriteBlocked() { | 151 void QuicSession::OnWriteBlocked() { |
| 139 if (visitor_) { | 152 if (visitor_) { |
| 140 visitor_->OnWriteBlocked(connection_); | 153 visitor_->OnWriteBlocked(connection_); |
| 141 } | 154 } |
| (...skipping 220 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 362 QUIC_DLOG(INFO) << ENDPOINT << "Stream is already closed: " << stream_id; | 375 QUIC_DLOG(INFO) << ENDPOINT << "Stream is already closed: " << stream_id; |
| 363 return; | 376 return; |
| 364 } | 377 } |
| 365 QuicStream* stream = it->second.get(); | 378 QuicStream* stream = it->second.get(); |
| 366 | 379 |
| 367 // Tell the stream that a RST has been sent. | 380 // Tell the stream that a RST has been sent. |
| 368 if (locally_reset) { | 381 if (locally_reset) { |
| 369 stream->set_rst_sent(true); | 382 stream->set_rst_sent(true); |
| 370 } | 383 } |
| 371 | 384 |
| 372 closed_streams_.push_back(std::move(it->second)); | 385 if (stream->IsWaitingForAcks()) { |
| 386 zombie_streams_[stream->id()] = std::move(it->second); |
| 387 } else { |
| 388 closed_streams_.push_back(std::move(it->second)); |
| 389 } |
| 373 | 390 |
| 374 // If we haven't received a FIN or RST for this stream, we need to keep track | 391 // If we haven't received a FIN or RST for this stream, we need to keep track |
| 375 // of the how many bytes the stream's flow controller believes it has | 392 // of the how many bytes the stream's flow controller believes it has |
| 376 // received, for accurate connection level flow control accounting. | 393 // received, for accurate connection level flow control accounting. |
| 377 if (!stream->HasFinalReceivedByteOffset()) { | 394 if (!stream->HasFinalReceivedByteOffset()) { |
| 378 InsertLocallyClosedStreamsHighestOffset( | 395 InsertLocallyClosedStreamsHighestOffset( |
| 379 stream_id, stream->flow_controller()->highest_received_byte_offset()); | 396 stream_id, stream->flow_controller()->highest_received_byte_offset()); |
| 380 } | 397 } |
| 381 | 398 |
| 382 dynamic_stream_map_.erase(it); | 399 dynamic_stream_map_.erase(it); |
| (...skipping 554 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 937 return CreateAndActivateStream(GetNextOutgoingStreamId()); | 954 return CreateAndActivateStream(GetNextOutgoingStreamId()); |
| 938 } | 955 } |
| 939 | 956 |
| 940 QuicStream* QuicSession::CreateAndActivateStream(QuicStreamId id) { | 957 QuicStream* QuicSession::CreateAndActivateStream(QuicStreamId id) { |
| 941 std::unique_ptr<QuicStream> stream = CreateStream(id); | 958 std::unique_ptr<QuicStream> stream = CreateStream(id); |
| 942 QuicStream* stream_ptr = stream.get(); | 959 QuicStream* stream_ptr = stream.get(); |
| 943 ActivateStream(std::move(stream)); | 960 ActivateStream(std::move(stream)); |
| 944 return stream_ptr; | 961 return stream_ptr; |
| 945 } | 962 } |
| 946 | 963 |
| 964 void QuicSession::OnStreamDoneWaitingForAcks(QuicStreamId id) { |
| 965 auto it = zombie_streams_.find(id); |
| 966 if (it == zombie_streams_.end()) { |
| 967 return; |
| 968 } |
| 969 |
| 970 closed_streams_.push_back(std::move(it->second)); |
| 971 zombie_streams_.erase(it); |
| 972 } |
| 973 |
| 974 QuicStream* QuicSession::GetStream(QuicStreamId id) const { |
| 975 auto static_stream = static_stream_map_.find(id); |
| 976 if (static_stream != static_stream_map_.end()) { |
| 977 return static_stream->second; |
| 978 } |
| 979 auto active_stream = dynamic_stream_map_.find(id); |
| 980 if (active_stream != dynamic_stream_map_.end()) { |
| 981 return active_stream->second.get(); |
| 982 } |
| 983 auto zombie_stream = zombie_streams_.find(id); |
| 984 if (zombie_stream != zombie_streams_.end()) { |
| 985 return zombie_stream->second.get(); |
| 986 } |
| 987 return nullptr; |
| 988 } |
| 989 |
| 990 void QuicSession::OnStreamFrameAcked(const QuicStreamFrame& frame, |
| 991 QuicTime::Delta ack_delay_time) { |
| 992 QuicStream* stream = GetStream(frame.stream_id); |
| 993 if (stream != nullptr) { |
| 994 stream->OnStreamFrameAcked(frame, ack_delay_time); |
| 995 } |
| 996 } |
| 997 |
| 998 void QuicSession::OnStreamFrameRetransmitted(const QuicStreamFrame& frame) { |
| 999 QuicStream* stream = GetStream(frame.stream_id); |
| 1000 if (stream != nullptr) { |
| 1001 stream->OnStreamFrameRetransmitted(frame); |
| 1002 } |
| 1003 } |
| 1004 |
| 947 } // namespace net | 1005 } // namespace net |
| OLD | NEW |