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

Unified Diff: net/spdy/spdy_session.cc

Issue 14311002: [SPDY] Avoid leaking bytes from the session flow control receive window (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 7 years, 8 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 side-by-side diff with in-line comments
Download patch
Index: net/spdy/spdy_session.cc
diff --git a/net/spdy/spdy_session.cc b/net/spdy/spdy_session.cc
index c80f5236f2555ec236cb48e7c84f08efb4bddf99..4a4be676266fc5737e09482f7431a64028c35b25 100644
--- a/net/spdy/spdy_session.cc
+++ b/net/spdy/spdy_session.cc
@@ -1402,14 +1402,17 @@ void SpdySession::OnStreamFrameData(SpdyStreamId stream_id,
if (it == active_streams_.end())
return;
- // Only decrease the window size for data for active streams.
- if (flow_control_state_ == FLOW_CONTROL_STREAM_AND_SESSION && len > 0)
- DecreaseRecvWindowSize(static_cast<int32>(len));
-
scoped_ptr<SpdyBuffer> buffer;
if (data) {
DCHECK_GT(len, 0u);
buffer.reset(new SpdyBuffer(data, len));
+
+ if (flow_control_state_ == FLOW_CONTROL_STREAM_AND_SESSION) {
+ DecreaseRecvWindowSize(static_cast<int32>(len));
+ buffer->AddConsumeCallback(
+ base::Bind(&SpdySession::IncreaseRecvWindowSize,
+ weak_factory_.GetWeakPtr()));
+ }
} else {
DCHECK_EQ(len, 0u);
}
@@ -1805,31 +1808,6 @@ void SpdySession::SendStreamWindowUpdate(SpdyStreamId stream_id,
SendWindowUpdateFrame(stream_id, delta_window_size, stream->priority());
}
-void SpdySession::IncreaseRecvWindowSize(int32 delta_window_size) {
- if (flow_control_state_ < FLOW_CONTROL_STREAM_AND_SESSION)
- return;
-
- DCHECK_GE(session_unacked_recv_window_bytes_, 0);
- DCHECK_GE(session_recv_window_size_, session_unacked_recv_window_bytes_);
- DCHECK_GE(delta_window_size, 1);
- // Check for overflow.
- DCHECK_LE(delta_window_size, kint32max - session_recv_window_size_);
-
- session_recv_window_size_ += delta_window_size;
- net_log_.AddEvent(
- NetLog::TYPE_SPDY_STREAM_UPDATE_RECV_WINDOW,
- base::Bind(&NetLogSpdySessionWindowUpdateCallback,
- delta_window_size, session_recv_window_size_));
-
- session_unacked_recv_window_bytes_ += delta_window_size;
- if (session_unacked_recv_window_bytes_ > kSpdySessionInitialWindowSize / 2) {
- SendWindowUpdateFrame(kSessionFlowControlStreamId,
- session_unacked_recv_window_bytes_,
- HIGHEST);
- session_unacked_recv_window_bytes_ = 0;
- }
-}
-
// Given a cwnd that we would have sent to the server, modify it based on the
// field trial policy.
uint32 ApplyCwndFieldTrialPolicy(int cwnd) {
@@ -2280,6 +2258,32 @@ void SpdySession::DecreaseSendWindowSize(int32 delta_window_size) {
-delta_window_size, session_send_window_size_));
}
+void SpdySession::IncreaseRecvWindowSize(size_t delta_window_size) {
+ if (flow_control_state_ < FLOW_CONTROL_STREAM_AND_SESSION)
+ return;
+
+ DCHECK_GE(session_unacked_recv_window_bytes_, 0);
+ DCHECK_GE(session_recv_window_size_, session_unacked_recv_window_bytes_);
+ DCHECK_GE(delta_window_size, 1u);
+ // Check for overflow.
+ DCHECK_LE(delta_window_size,
+ static_cast<size_t>(kint32max - session_recv_window_size_));
+
+ session_recv_window_size_ += delta_window_size;
+ net_log_.AddEvent(
+ NetLog::TYPE_SPDY_STREAM_UPDATE_RECV_WINDOW,
+ base::Bind(&NetLogSpdySessionWindowUpdateCallback,
+ delta_window_size, session_recv_window_size_));
+
+ session_unacked_recv_window_bytes_ += delta_window_size;
+ if (session_unacked_recv_window_bytes_ > kSpdySessionInitialWindowSize / 2) {
+ SendWindowUpdateFrame(kSessionFlowControlStreamId,
+ session_unacked_recv_window_bytes_,
+ HIGHEST);
+ session_unacked_recv_window_bytes_ = 0;
+ }
+}
+
void SpdySession::DecreaseRecvWindowSize(int32 delta_window_size) {
DCHECK_EQ(flow_control_state_, FLOW_CONTROL_STREAM_AND_SESSION);
DCHECK_GE(delta_window_size, 1);

Powered by Google App Engine
This is Rietveld 408576698