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_session.h" | 5 #include "net/quic/quic_session.h" |
6 | 6 |
7 #include <set> | 7 #include <set> |
8 | 8 |
9 #include "base/basictypes.h" | 9 #include "base/basictypes.h" |
10 #include "base/containers/hash_tables.h" | 10 #include "base/containers/hash_tables.h" |
11 #include "base/rand_util.h" | 11 #include "base/rand_util.h" |
12 #include "base/stl_util.h" | 12 #include "base/stl_util.h" |
13 #include "base/strings/string_number_conversions.h" | 13 #include "base/strings/string_number_conversions.h" |
14 #include "net/quic/crypto/crypto_protocol.h" | 14 #include "net/quic/crypto/crypto_protocol.h" |
15 #include "net/quic/quic_crypto_stream.h" | 15 #include "net/quic/quic_crypto_stream.h" |
16 #include "net/quic/quic_flags.h" | 16 #include "net/quic/quic_flags.h" |
17 #include "net/quic/quic_protocol.h" | 17 #include "net/quic/quic_protocol.h" |
18 #include "net/quic/quic_utils.h" | 18 #include "net/quic/quic_utils.h" |
19 #include "net/quic/reliable_quic_stream.h" | 19 #include "net/quic/reliable_quic_stream.h" |
20 #include "net/quic/test_tools/quic_config_peer.h" | 20 #include "net/quic/test_tools/quic_config_peer.h" |
21 #include "net/quic/test_tools/quic_connection_peer.h" | 21 #include "net/quic/test_tools/quic_connection_peer.h" |
22 #include "net/quic/test_tools/quic_data_stream_peer.h" | 22 #include "net/quic/test_tools/quic_data_stream_peer.h" |
23 #include "net/quic/test_tools/quic_flow_controller_peer.h" | 23 #include "net/quic/test_tools/quic_flow_controller_peer.h" |
24 #include "net/quic/test_tools/quic_session_peer.h" | 24 #include "net/quic/test_tools/quic_session_peer.h" |
| 25 #include "net/quic/test_tools/quic_spdy_session_peer.h" |
25 #include "net/quic/test_tools/quic_test_utils.h" | 26 #include "net/quic/test_tools/quic_test_utils.h" |
26 #include "net/quic/test_tools/reliable_quic_stream_peer.h" | 27 #include "net/quic/test_tools/reliable_quic_stream_peer.h" |
27 #include "net/spdy/spdy_framer.h" | 28 #include "net/spdy/spdy_framer.h" |
28 #include "net/test/gtest_util.h" | 29 #include "net/test/gtest_util.h" |
29 #include "testing/gmock/include/gmock/gmock.h" | 30 #include "testing/gmock/include/gmock/gmock.h" |
30 #include "testing/gmock_mutant.h" | 31 #include "testing/gmock_mutant.h" |
31 #include "testing/gtest/include/gtest/gtest.h" | 32 #include "testing/gtest/include/gtest/gtest.h" |
32 | 33 |
33 using base::hash_map; | 34 using base::hash_map; |
34 using std::set; | 35 using std::set; |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
69 EXPECT_EQ(QUIC_NO_ERROR, error); | 70 EXPECT_EQ(QUIC_NO_ERROR, error); |
70 session()->OnConfigNegotiated(); | 71 session()->OnConfigNegotiated(); |
71 session()->OnCryptoHandshakeEvent(QuicSession::HANDSHAKE_CONFIRMED); | 72 session()->OnCryptoHandshakeEvent(QuicSession::HANDSHAKE_CONFIRMED); |
72 } | 73 } |
73 | 74 |
74 MOCK_METHOD0(OnCanWrite, void()); | 75 MOCK_METHOD0(OnCanWrite, void()); |
75 }; | 76 }; |
76 | 77 |
77 class TestHeadersStream : public QuicHeadersStream { | 78 class TestHeadersStream : public QuicHeadersStream { |
78 public: | 79 public: |
79 explicit TestHeadersStream(QuicSession* session) | 80 explicit TestHeadersStream(QuicSpdySession* session) |
80 : QuicHeadersStream(session) { | 81 : QuicHeadersStream(session) {} |
81 } | |
82 | 82 |
83 MOCK_METHOD0(OnCanWrite, void()); | 83 MOCK_METHOD0(OnCanWrite, void()); |
84 }; | 84 }; |
85 | 85 |
86 class TestStream : public QuicDataStream { | 86 class TestStream : public QuicDataStream { |
87 public: | 87 public: |
88 TestStream(QuicStreamId id, QuicSession* session) | 88 TestStream(QuicStreamId id, QuicSpdySession* session) |
89 : QuicDataStream(id, session) { | 89 : QuicDataStream(id, session) {} |
90 } | |
91 | 90 |
92 using ReliableQuicStream::CloseWriteSide; | 91 using ReliableQuicStream::CloseWriteSide; |
93 | 92 |
94 uint32 ProcessData(const char* data, uint32 data_len) override { | 93 uint32 ProcessData(const char* data, uint32 data_len) override { |
95 return data_len; | 94 return data_len; |
96 } | 95 } |
97 | 96 |
98 void SendBody(const string& data, bool fin) { | 97 void SendBody(const string& data, bool fin) { |
99 WriteOrBufferData(data, fin, nullptr); | 98 WriteOrBufferData(data, fin, nullptr); |
100 } | 99 } |
(...skipping 11 matching lines...) Expand all Loading... |
112 | 111 |
113 void MarkWriteBlocked() { | 112 void MarkWriteBlocked() { |
114 session_->MarkWriteBlocked(stream_id_, kSomeMiddlePriority); | 113 session_->MarkWriteBlocked(stream_id_, kSomeMiddlePriority); |
115 } | 114 } |
116 | 115 |
117 private: | 116 private: |
118 QuicSession* const session_; | 117 QuicSession* const session_; |
119 const QuicStreamId stream_id_; | 118 const QuicStreamId stream_id_; |
120 }; | 119 }; |
121 | 120 |
122 class TestSession : public QuicSession { | 121 class TestSession : public QuicSpdySession { |
123 public: | 122 public: |
124 explicit TestSession(QuicConnection* connection) | 123 explicit TestSession(QuicConnection* connection) |
125 : QuicSession(connection, DefaultQuicConfig()), | 124 : QuicSpdySession(connection, DefaultQuicConfig()), |
126 crypto_stream_(this), | 125 crypto_stream_(this), |
127 writev_consumes_all_data_(false) { | 126 writev_consumes_all_data_(false) { |
128 Initialize(); | 127 Initialize(); |
129 } | 128 } |
130 | 129 |
131 TestCryptoStream* GetCryptoStream() override { return &crypto_stream_; } | 130 TestCryptoStream* GetCryptoStream() override { return &crypto_stream_; } |
132 | 131 |
133 TestStream* CreateOutgoingDataStream() override { | 132 TestStream* CreateOutgoingDynamicStream() override { |
134 TestStream* stream = new TestStream(GetNextStreamId(), this); | 133 TestStream* stream = new TestStream(GetNextStreamId(), this); |
135 ActivateStream(stream); | 134 ActivateStream(stream); |
136 return stream; | 135 return stream; |
137 } | 136 } |
138 | 137 |
139 TestStream* CreateIncomingDataStream(QuicStreamId id) override { | 138 TestStream* CreateIncomingDynamicStream(QuicStreamId id) override { |
140 return new TestStream(id, this); | 139 return new TestStream(id, this); |
141 } | 140 } |
142 | 141 |
143 bool IsClosedStream(QuicStreamId id) { | 142 bool IsClosedStream(QuicStreamId id) { |
144 return QuicSession::IsClosedStream(id); | 143 return QuicSession::IsClosedStream(id); |
145 } | 144 } |
146 | 145 |
147 QuicDataStream* GetIncomingDataStream(QuicStreamId stream_id) { | 146 ReliableQuicStream* GetIncomingDynamicStream(QuicStreamId stream_id) { |
148 return QuicSession::GetIncomingDataStream(stream_id); | 147 return QuicSpdySession::GetIncomingDynamicStream(stream_id); |
149 } | 148 } |
150 | 149 |
151 QuicConsumedData WritevData( | 150 QuicConsumedData WritevData( |
152 QuicStreamId id, | 151 QuicStreamId id, |
153 const IOVector& data, | 152 const IOVector& data, |
154 QuicStreamOffset offset, | 153 QuicStreamOffset offset, |
155 bool fin, | 154 bool fin, |
156 FecProtection fec_protection, | 155 FecProtection fec_protection, |
157 QuicAckNotifier::DelegateInterface* ack_notifier_delegate) override { | 156 QuicAckNotifier::DelegateInterface* ack_notifier_delegate) override { |
158 // Always consumes everything. | 157 // Always consumes everything. |
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
267 } | 266 } |
268 | 267 |
269 TEST_P(QuicSessionTestServer, IsClosedStreamDefault) { | 268 TEST_P(QuicSessionTestServer, IsClosedStreamDefault) { |
270 // Ensure that no streams are initially closed. | 269 // Ensure that no streams are initially closed. |
271 for (int i = kCryptoStreamId; i < 100; i++) { | 270 for (int i = kCryptoStreamId; i < 100; i++) { |
272 EXPECT_FALSE(session_.IsClosedStream(i)) << "stream id: " << i; | 271 EXPECT_FALSE(session_.IsClosedStream(i)) << "stream id: " << i; |
273 } | 272 } |
274 } | 273 } |
275 | 274 |
276 TEST_P(QuicSessionTestServer, ImplicitlyCreatedStreams) { | 275 TEST_P(QuicSessionTestServer, ImplicitlyCreatedStreams) { |
277 ASSERT_TRUE(session_.GetIncomingDataStream(9) != nullptr); | 276 ASSERT_TRUE(session_.GetIncomingDynamicStream(9) != nullptr); |
278 // Both 5 and 7 should be implicitly created. | 277 // Both 5 and 7 should be implicitly created. |
279 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 5)); | 278 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 5)); |
280 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 7)); | 279 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 7)); |
281 ASSERT_TRUE(session_.GetIncomingDataStream(7) != nullptr); | 280 ASSERT_TRUE(session_.GetIncomingDynamicStream(7) != nullptr); |
282 ASSERT_TRUE(session_.GetIncomingDataStream(5) != nullptr); | 281 ASSERT_TRUE(session_.GetIncomingDynamicStream(5) != nullptr); |
283 } | 282 } |
284 | 283 |
285 TEST_P(QuicSessionTestServer, IsClosedStreamLocallyCreated) { | 284 TEST_P(QuicSessionTestServer, IsClosedStreamLocallyCreated) { |
286 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 285 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
287 EXPECT_EQ(2u, stream2->id()); | 286 EXPECT_EQ(2u, stream2->id()); |
288 TestStream* stream4 = session_.CreateOutgoingDataStream(); | 287 TestStream* stream4 = session_.CreateOutgoingDynamicStream(); |
289 EXPECT_EQ(4u, stream4->id()); | 288 EXPECT_EQ(4u, stream4->id()); |
290 | 289 |
291 CheckClosedStreams(); | 290 CheckClosedStreams(); |
292 CloseStream(4); | 291 CloseStream(4); |
293 CheckClosedStreams(); | 292 CheckClosedStreams(); |
294 CloseStream(2); | 293 CloseStream(2); |
295 CheckClosedStreams(); | 294 CheckClosedStreams(); |
296 } | 295 } |
297 | 296 |
298 TEST_P(QuicSessionTestServer, IsClosedStreamPeerCreated) { | 297 TEST_P(QuicSessionTestServer, IsClosedStreamPeerCreated) { |
299 QuicStreamId stream_id1 = kClientDataStreamId1; | 298 QuicStreamId stream_id1 = kClientDataStreamId1; |
300 QuicStreamId stream_id2 = kClientDataStreamId2; | 299 QuicStreamId stream_id2 = kClientDataStreamId2; |
301 QuicDataStream* stream1 = session_.GetIncomingDataStream(stream_id1); | 300 session_.GetIncomingDynamicStream(stream_id1); |
302 QuicDataStreamPeer::SetHeadersDecompressed(stream1, true); | 301 session_.GetIncomingDynamicStream(stream_id2); |
303 QuicDataStream* stream2 = session_.GetIncomingDataStream(stream_id2); | |
304 QuicDataStreamPeer::SetHeadersDecompressed(stream2, true); | |
305 | 302 |
306 CheckClosedStreams(); | 303 CheckClosedStreams(); |
307 CloseStream(stream_id1); | 304 CloseStream(stream_id1); |
308 CheckClosedStreams(); | 305 CheckClosedStreams(); |
309 CloseStream(stream_id2); | 306 CloseStream(stream_id2); |
310 // Create a stream explicitly, and another implicitly. | 307 // Create a stream explicitly, and another implicitly. |
311 QuicDataStream* stream3 = session_.GetIncomingDataStream(stream_id2 + 4); | 308 ReliableQuicStream* stream3 = |
312 QuicDataStreamPeer::SetHeadersDecompressed(stream3, true); | 309 session_.GetIncomingDynamicStream(stream_id2 + 4); |
313 CheckClosedStreams(); | 310 CheckClosedStreams(); |
314 // Close one, but make sure the other is still not closed | 311 // Close one, but make sure the other is still not closed |
315 CloseStream(stream3->id()); | 312 CloseStream(stream3->id()); |
316 CheckClosedStreams(); | 313 CheckClosedStreams(); |
317 } | 314 } |
318 | 315 |
319 TEST_P(QuicSessionTestServer, StreamIdTooLarge) { | 316 TEST_P(QuicSessionTestServer, StreamIdTooLarge) { |
320 QuicStreamId stream_id = kClientDataStreamId1; | 317 QuicStreamId stream_id = kClientDataStreamId1; |
321 session_.GetIncomingDataStream(stream_id); | 318 session_.GetIncomingDynamicStream(stream_id); |
322 EXPECT_CALL(*connection_, SendConnectionClose(QUIC_INVALID_STREAM_ID)); | 319 EXPECT_CALL(*connection_, SendConnectionClose(QUIC_INVALID_STREAM_ID)); |
323 session_.GetIncomingDataStream(stream_id + kMaxStreamIdDelta + 2); | 320 session_.GetIncomingDynamicStream(stream_id + kMaxStreamIdDelta + 2); |
324 } | 321 } |
325 | 322 |
326 TEST_P(QuicSessionTestServer, DebugDFatalIfMarkingClosedStreamWriteBlocked) { | 323 TEST_P(QuicSessionTestServer, DebugDFatalIfMarkingClosedStreamWriteBlocked) { |
327 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 324 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
328 QuicStreamId kClosedStreamId = stream2->id(); | 325 QuicStreamId kClosedStreamId = stream2->id(); |
329 // Close the stream. | 326 // Close the stream. |
330 EXPECT_CALL(*connection_, SendRstStream(kClosedStreamId, _, _)); | 327 EXPECT_CALL(*connection_, SendRstStream(kClosedStreamId, _, _)); |
331 stream2->Reset(QUIC_BAD_APPLICATION_PAYLOAD); | 328 stream2->Reset(QUIC_BAD_APPLICATION_PAYLOAD); |
332 EXPECT_DEBUG_DFATAL( | 329 EXPECT_DEBUG_DFATAL( |
333 session_.MarkWriteBlocked(kClosedStreamId, kSomeMiddlePriority), | 330 session_.MarkWriteBlocked(kClosedStreamId, kSomeMiddlePriority), |
334 "Marking unknown stream 2 blocked."); | 331 "Marking unknown stream 2 blocked."); |
335 } | 332 } |
336 | 333 |
337 TEST_P(QuicSessionTestServer, | 334 TEST_P(QuicSessionTestServer, |
338 DebugDFatalIfMarkWriteBlockedCalledWithWrongPriority) { | 335 DebugDFatalIfMarkWriteBlockedCalledWithWrongPriority) { |
339 const QuicPriority kDifferentPriority = 0; | 336 const QuicPriority kDifferentPriority = 0; |
340 | 337 |
341 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 338 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
342 EXPECT_NE(kDifferentPriority, stream2->EffectivePriority()); | 339 EXPECT_NE(kDifferentPriority, stream2->EffectivePriority()); |
343 EXPECT_DEBUG_DFATAL( | 340 EXPECT_DEBUG_DFATAL( |
344 session_.MarkWriteBlocked(stream2->id(), kDifferentPriority), | 341 session_.MarkWriteBlocked(stream2->id(), kDifferentPriority), |
345 "Priorities do not match. Got: 0 Expected: 3"); | 342 "Priorities do not match. Got: 0 Expected: 3"); |
346 } | 343 } |
347 | 344 |
348 TEST_P(QuicSessionTestServer, OnCanWrite) { | 345 TEST_P(QuicSessionTestServer, OnCanWrite) { |
349 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 346 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
350 TestStream* stream4 = session_.CreateOutgoingDataStream(); | 347 TestStream* stream4 = session_.CreateOutgoingDynamicStream(); |
351 TestStream* stream6 = session_.CreateOutgoingDataStream(); | 348 TestStream* stream6 = session_.CreateOutgoingDynamicStream(); |
352 | 349 |
353 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); | 350 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); |
354 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); | 351 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); |
355 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); | 352 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); |
356 | 353 |
357 InSequence s; | 354 InSequence s; |
358 StreamBlocker stream2_blocker(&session_, stream2->id()); | 355 StreamBlocker stream2_blocker(&session_, stream2->id()); |
359 // Reregister, to test the loop limit. | 356 // Reregister, to test the loop limit. |
360 EXPECT_CALL(*stream2, OnCanWrite()) | 357 EXPECT_CALL(*stream2, OnCanWrite()) |
361 .WillOnce(Invoke(&stream2_blocker, &StreamBlocker::MarkWriteBlocked)); | 358 .WillOnce(Invoke(&stream2_blocker, &StreamBlocker::MarkWriteBlocked)); |
362 EXPECT_CALL(*stream6, OnCanWrite()); | 359 EXPECT_CALL(*stream6, OnCanWrite()); |
363 EXPECT_CALL(*stream4, OnCanWrite()); | 360 EXPECT_CALL(*stream4, OnCanWrite()); |
364 session_.OnCanWrite(); | 361 session_.OnCanWrite(); |
365 EXPECT_TRUE(session_.WillingAndAbleToWrite()); | 362 EXPECT_TRUE(session_.WillingAndAbleToWrite()); |
366 } | 363 } |
367 | 364 |
368 TEST_P(QuicSessionTestServer, OnCanWriteBundlesStreams) { | 365 TEST_P(QuicSessionTestServer, OnCanWriteBundlesStreams) { |
369 // Drive congestion control manually. | 366 // Drive congestion control manually. |
370 MockSendAlgorithm* send_algorithm = new StrictMock<MockSendAlgorithm>; | 367 MockSendAlgorithm* send_algorithm = new StrictMock<MockSendAlgorithm>; |
371 QuicConnectionPeer::SetSendAlgorithm(session_.connection(), send_algorithm); | 368 QuicConnectionPeer::SetSendAlgorithm(session_.connection(), send_algorithm); |
372 | 369 |
373 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 370 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
374 TestStream* stream4 = session_.CreateOutgoingDataStream(); | 371 TestStream* stream4 = session_.CreateOutgoingDynamicStream(); |
375 TestStream* stream6 = session_.CreateOutgoingDataStream(); | 372 TestStream* stream6 = session_.CreateOutgoingDynamicStream(); |
376 | 373 |
377 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); | 374 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); |
378 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); | 375 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); |
379 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); | 376 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); |
380 | 377 |
381 EXPECT_CALL(*send_algorithm, TimeUntilSend(_, _, _)).WillRepeatedly( | 378 EXPECT_CALL(*send_algorithm, TimeUntilSend(_, _, _)).WillRepeatedly( |
382 Return(QuicTime::Delta::Zero())); | 379 Return(QuicTime::Delta::Zero())); |
383 EXPECT_CALL(*send_algorithm, GetCongestionWindow()) | 380 EXPECT_CALL(*send_algorithm, GetCongestionWindow()) |
384 .WillRepeatedly(Return(kMaxPacketSize * 10)); | 381 .WillRepeatedly(Return(kMaxPacketSize * 10)); |
385 EXPECT_CALL(*stream2, OnCanWrite()) | 382 EXPECT_CALL(*stream2, OnCanWrite()) |
(...skipping 18 matching lines...) Expand all Loading... |
404 EXPECT_FALSE(session_.WillingAndAbleToWrite()); | 401 EXPECT_FALSE(session_.WillingAndAbleToWrite()); |
405 } | 402 } |
406 | 403 |
407 TEST_P(QuicSessionTestServer, OnCanWriteCongestionControlBlocks) { | 404 TEST_P(QuicSessionTestServer, OnCanWriteCongestionControlBlocks) { |
408 InSequence s; | 405 InSequence s; |
409 | 406 |
410 // Drive congestion control manually. | 407 // Drive congestion control manually. |
411 MockSendAlgorithm* send_algorithm = new StrictMock<MockSendAlgorithm>; | 408 MockSendAlgorithm* send_algorithm = new StrictMock<MockSendAlgorithm>; |
412 QuicConnectionPeer::SetSendAlgorithm(session_.connection(), send_algorithm); | 409 QuicConnectionPeer::SetSendAlgorithm(session_.connection(), send_algorithm); |
413 | 410 |
414 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 411 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
415 TestStream* stream4 = session_.CreateOutgoingDataStream(); | 412 TestStream* stream4 = session_.CreateOutgoingDynamicStream(); |
416 TestStream* stream6 = session_.CreateOutgoingDataStream(); | 413 TestStream* stream6 = session_.CreateOutgoingDynamicStream(); |
417 | 414 |
418 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); | 415 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); |
419 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); | 416 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); |
420 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); | 417 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); |
421 | 418 |
422 StreamBlocker stream2_blocker(&session_, stream2->id()); | 419 StreamBlocker stream2_blocker(&session_, stream2->id()); |
423 EXPECT_CALL(*send_algorithm, TimeUntilSend(_, _, _)).WillOnce(Return( | 420 EXPECT_CALL(*send_algorithm, TimeUntilSend(_, _, _)).WillOnce(Return( |
424 QuicTime::Delta::Zero())); | 421 QuicTime::Delta::Zero())); |
425 EXPECT_CALL(*stream2, OnCanWrite()); | 422 EXPECT_CALL(*stream2, OnCanWrite()); |
426 EXPECT_CALL(*send_algorithm, TimeUntilSend(_, _, _)).WillOnce(Return( | 423 EXPECT_CALL(*send_algorithm, TimeUntilSend(_, _, _)).WillOnce(Return( |
(...skipping 18 matching lines...) Expand all Loading... |
445 QuicTime::Delta::Zero())); | 442 QuicTime::Delta::Zero())); |
446 EXPECT_CALL(*stream4, OnCanWrite()); | 443 EXPECT_CALL(*stream4, OnCanWrite()); |
447 session_.OnCanWrite(); | 444 session_.OnCanWrite(); |
448 EXPECT_FALSE(session_.WillingAndAbleToWrite()); | 445 EXPECT_FALSE(session_.WillingAndAbleToWrite()); |
449 } | 446 } |
450 | 447 |
451 TEST_P(QuicSessionTestServer, BufferedHandshake) { | 448 TEST_P(QuicSessionTestServer, BufferedHandshake) { |
452 EXPECT_FALSE(session_.HasPendingHandshake()); // Default value. | 449 EXPECT_FALSE(session_.HasPendingHandshake()); // Default value. |
453 | 450 |
454 // Test that blocking other streams does not change our status. | 451 // Test that blocking other streams does not change our status. |
455 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 452 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
456 StreamBlocker stream2_blocker(&session_, stream2->id()); | 453 StreamBlocker stream2_blocker(&session_, stream2->id()); |
457 stream2_blocker.MarkWriteBlocked(); | 454 stream2_blocker.MarkWriteBlocked(); |
458 EXPECT_FALSE(session_.HasPendingHandshake()); | 455 EXPECT_FALSE(session_.HasPendingHandshake()); |
459 | 456 |
460 TestStream* stream3 = session_.CreateOutgoingDataStream(); | 457 TestStream* stream3 = session_.CreateOutgoingDynamicStream(); |
461 StreamBlocker stream3_blocker(&session_, stream3->id()); | 458 StreamBlocker stream3_blocker(&session_, stream3->id()); |
462 stream3_blocker.MarkWriteBlocked(); | 459 stream3_blocker.MarkWriteBlocked(); |
463 EXPECT_FALSE(session_.HasPendingHandshake()); | 460 EXPECT_FALSE(session_.HasPendingHandshake()); |
464 | 461 |
465 // Blocking (due to buffering of) the Crypto stream is detected. | 462 // Blocking (due to buffering of) the Crypto stream is detected. |
466 session_.MarkWriteBlocked(kCryptoStreamId, kHighestPriority); | 463 session_.MarkWriteBlocked(kCryptoStreamId, kHighestPriority); |
467 EXPECT_TRUE(session_.HasPendingHandshake()); | 464 EXPECT_TRUE(session_.HasPendingHandshake()); |
468 | 465 |
469 TestStream* stream4 = session_.CreateOutgoingDataStream(); | 466 TestStream* stream4 = session_.CreateOutgoingDynamicStream(); |
470 StreamBlocker stream4_blocker(&session_, stream4->id()); | 467 StreamBlocker stream4_blocker(&session_, stream4->id()); |
471 stream4_blocker.MarkWriteBlocked(); | 468 stream4_blocker.MarkWriteBlocked(); |
472 EXPECT_TRUE(session_.HasPendingHandshake()); | 469 EXPECT_TRUE(session_.HasPendingHandshake()); |
473 | 470 |
474 InSequence s; | 471 InSequence s; |
475 // Force most streams to re-register, which is common scenario when we block | 472 // Force most streams to re-register, which is common scenario when we block |
476 // the Crypto stream, and only the crypto stream can "really" write. | 473 // the Crypto stream, and only the crypto stream can "really" write. |
477 | 474 |
478 // Due to prioritization, we *should* be asked to write the crypto stream | 475 // Due to prioritization, we *should* be asked to write the crypto stream |
479 // first. | 476 // first. |
480 // Don't re-register the crypto stream (which signals complete writing). | 477 // Don't re-register the crypto stream (which signals complete writing). |
481 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); | 478 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); |
482 EXPECT_CALL(*crypto_stream, OnCanWrite()); | 479 EXPECT_CALL(*crypto_stream, OnCanWrite()); |
483 | 480 |
484 // Re-register all other streams, to show they weren't able to proceed. | 481 // Re-register all other streams, to show they weren't able to proceed. |
485 EXPECT_CALL(*stream2, OnCanWrite()) | 482 EXPECT_CALL(*stream2, OnCanWrite()) |
486 .WillOnce(Invoke(&stream2_blocker, &StreamBlocker::MarkWriteBlocked)); | 483 .WillOnce(Invoke(&stream2_blocker, &StreamBlocker::MarkWriteBlocked)); |
487 EXPECT_CALL(*stream3, OnCanWrite()) | 484 EXPECT_CALL(*stream3, OnCanWrite()) |
488 .WillOnce(Invoke(&stream3_blocker, &StreamBlocker::MarkWriteBlocked)); | 485 .WillOnce(Invoke(&stream3_blocker, &StreamBlocker::MarkWriteBlocked)); |
489 EXPECT_CALL(*stream4, OnCanWrite()) | 486 EXPECT_CALL(*stream4, OnCanWrite()) |
490 .WillOnce(Invoke(&stream4_blocker, &StreamBlocker::MarkWriteBlocked)); | 487 .WillOnce(Invoke(&stream4_blocker, &StreamBlocker::MarkWriteBlocked)); |
491 | 488 |
492 session_.OnCanWrite(); | 489 session_.OnCanWrite(); |
493 EXPECT_TRUE(session_.WillingAndAbleToWrite()); | 490 EXPECT_TRUE(session_.WillingAndAbleToWrite()); |
494 EXPECT_FALSE(session_.HasPendingHandshake()); // Crypto stream wrote. | 491 EXPECT_FALSE(session_.HasPendingHandshake()); // Crypto stream wrote. |
495 } | 492 } |
496 | 493 |
497 TEST_P(QuicSessionTestServer, OnCanWriteWithClosedStream) { | 494 TEST_P(QuicSessionTestServer, OnCanWriteWithClosedStream) { |
498 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 495 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
499 TestStream* stream4 = session_.CreateOutgoingDataStream(); | 496 TestStream* stream4 = session_.CreateOutgoingDynamicStream(); |
500 TestStream* stream6 = session_.CreateOutgoingDataStream(); | 497 TestStream* stream6 = session_.CreateOutgoingDynamicStream(); |
501 | 498 |
502 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); | 499 session_.MarkWriteBlocked(stream2->id(), kSomeMiddlePriority); |
503 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); | 500 session_.MarkWriteBlocked(stream6->id(), kSomeMiddlePriority); |
504 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); | 501 session_.MarkWriteBlocked(stream4->id(), kSomeMiddlePriority); |
505 CloseStream(stream6->id()); | 502 CloseStream(stream6->id()); |
506 | 503 |
507 InSequence s; | 504 InSequence s; |
508 EXPECT_CALL(*stream2, OnCanWrite()); | 505 EXPECT_CALL(*stream2, OnCanWrite()); |
509 EXPECT_CALL(*stream4, OnCanWrite()); | 506 EXPECT_CALL(*stream4, OnCanWrite()); |
510 session_.OnCanWrite(); | 507 session_.OnCanWrite(); |
511 EXPECT_FALSE(session_.WillingAndAbleToWrite()); | 508 EXPECT_FALSE(session_.WillingAndAbleToWrite()); |
512 } | 509 } |
513 | 510 |
514 TEST_P(QuicSessionTestServer, OnCanWriteLimitsNumWritesIfFlowControlBlocked) { | 511 TEST_P(QuicSessionTestServer, OnCanWriteLimitsNumWritesIfFlowControlBlocked) { |
515 // Ensure connection level flow control blockage. | 512 // Ensure connection level flow control blockage. |
516 QuicFlowControllerPeer::SetSendWindowOffset(session_.flow_controller(), 0); | 513 QuicFlowControllerPeer::SetSendWindowOffset(session_.flow_controller(), 0); |
517 EXPECT_TRUE(session_.flow_controller()->IsBlocked()); | 514 EXPECT_TRUE(session_.flow_controller()->IsBlocked()); |
518 EXPECT_TRUE(session_.IsConnectionFlowControlBlocked()); | 515 EXPECT_TRUE(session_.IsConnectionFlowControlBlocked()); |
519 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 516 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
520 | 517 |
521 // Mark the crypto and headers streams as write blocked, we expect them to be | 518 // Mark the crypto and headers streams as write blocked, we expect them to be |
522 // allowed to write later. | 519 // allowed to write later. |
523 session_.MarkWriteBlocked(kCryptoStreamId, kHighestPriority); | 520 session_.MarkWriteBlocked(kCryptoStreamId, kHighestPriority); |
524 session_.MarkWriteBlocked(kHeadersStreamId, kHighestPriority); | 521 session_.MarkWriteBlocked(kHeadersStreamId, kHighestPriority); |
525 | 522 |
526 // Create a data stream, and although it is write blocked we never expect it | 523 // Create a data stream, and although it is write blocked we never expect it |
527 // to be allowed to write as we are connection level flow control blocked. | 524 // to be allowed to write as we are connection level flow control blocked. |
528 TestStream* stream = session_.CreateOutgoingDataStream(); | 525 TestStream* stream = session_.CreateOutgoingDynamicStream(); |
529 session_.MarkWriteBlocked(stream->id(), kSomeMiddlePriority); | 526 session_.MarkWriteBlocked(stream->id(), kSomeMiddlePriority); |
530 EXPECT_CALL(*stream, OnCanWrite()).Times(0); | 527 EXPECT_CALL(*stream, OnCanWrite()).Times(0); |
531 | 528 |
532 // The crypto and headers streams should be called even though we are | 529 // The crypto and headers streams should be called even though we are |
533 // connection flow control blocked. | 530 // connection flow control blocked. |
534 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); | 531 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); |
535 EXPECT_CALL(*crypto_stream, OnCanWrite()).Times(1); | 532 EXPECT_CALL(*crypto_stream, OnCanWrite()).Times(1); |
536 TestHeadersStream* headers_stream = new TestHeadersStream(&session_); | 533 TestHeadersStream* headers_stream = new TestHeadersStream(&session_); |
537 QuicSessionPeer::SetHeadersStream(&session_, headers_stream); | 534 QuicSpdySessionPeer::SetHeadersStream(&session_, headers_stream); |
538 EXPECT_CALL(*headers_stream, OnCanWrite()).Times(1); | 535 EXPECT_CALL(*headers_stream, OnCanWrite()).Times(1); |
539 | 536 |
540 session_.OnCanWrite(); | 537 session_.OnCanWrite(); |
541 EXPECT_FALSE(session_.WillingAndAbleToWrite()); | 538 EXPECT_FALSE(session_.WillingAndAbleToWrite()); |
542 } | 539 } |
543 | 540 |
544 TEST_P(QuicSessionTestServer, SendGoAway) { | 541 TEST_P(QuicSessionTestServer, SendGoAway) { |
545 EXPECT_CALL(*connection_, | 542 EXPECT_CALL(*connection_, |
546 SendGoAway(QUIC_PEER_GOING_AWAY, 0u, "Going Away.")); | 543 SendGoAway(QUIC_PEER_GOING_AWAY, 3u, "Going Away.")); |
547 session_.SendGoAway(QUIC_PEER_GOING_AWAY, "Going Away."); | 544 session_.SendGoAway(QUIC_PEER_GOING_AWAY, "Going Away."); |
548 EXPECT_TRUE(session_.goaway_sent()); | 545 EXPECT_TRUE(session_.goaway_sent()); |
549 | 546 |
550 EXPECT_CALL(*connection_, | 547 EXPECT_CALL(*connection_, |
551 SendRstStream(3u, QUIC_STREAM_PEER_GOING_AWAY, 0)).Times(0); | 548 SendRstStream(3u, QUIC_STREAM_PEER_GOING_AWAY, 0)).Times(0); |
552 EXPECT_TRUE(session_.GetIncomingDataStream(3u)); | 549 EXPECT_TRUE(session_.GetIncomingDynamicStream(3u)); |
553 } | 550 } |
554 | 551 |
555 TEST_P(QuicSessionTestServer, DoNotSendGoAwayTwice) { | 552 TEST_P(QuicSessionTestServer, DoNotSendGoAwayTwice) { |
556 EXPECT_CALL(*connection_, | 553 EXPECT_CALL(*connection_, SendGoAway(QUIC_PEER_GOING_AWAY, 3u, "Going Away.")) |
557 SendGoAway(QUIC_PEER_GOING_AWAY, 0u, "Going Away.")).Times(1); | 554 .Times(1); |
558 session_.SendGoAway(QUIC_PEER_GOING_AWAY, "Going Away."); | 555 session_.SendGoAway(QUIC_PEER_GOING_AWAY, "Going Away."); |
559 EXPECT_TRUE(session_.goaway_sent()); | 556 EXPECT_TRUE(session_.goaway_sent()); |
560 session_.SendGoAway(QUIC_PEER_GOING_AWAY, "Going Away."); | 557 session_.SendGoAway(QUIC_PEER_GOING_AWAY, "Going Away."); |
561 } | 558 } |
562 | 559 |
563 TEST_P(QuicSessionTestServer, IncreasedTimeoutAfterCryptoHandshake) { | 560 TEST_P(QuicSessionTestServer, IncreasedTimeoutAfterCryptoHandshake) { |
564 EXPECT_EQ(kInitialIdleTimeoutSecs + 3, | 561 EXPECT_EQ(kInitialIdleTimeoutSecs + 3, |
565 QuicConnectionPeer::GetNetworkTimeout(connection_).ToSeconds()); | 562 QuicConnectionPeer::GetNetworkTimeout(connection_).ToSeconds()); |
566 CryptoHandshakeMessage msg; | 563 CryptoHandshakeMessage msg; |
567 session_.GetCryptoStream()->OnHandshakeMessage(msg); | 564 session_.GetCryptoStream()->OnHandshakeMessage(msg); |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
614 | 611 |
615 TEST_P(QuicSessionTestServer, HandshakeUnblocksFlowControlBlockedStream) { | 612 TEST_P(QuicSessionTestServer, HandshakeUnblocksFlowControlBlockedStream) { |
616 // Test that if a stream is flow control blocked, then on receipt of the SHLO | 613 // Test that if a stream is flow control blocked, then on receipt of the SHLO |
617 // containing a suitable send window offset, the stream becomes unblocked. | 614 // containing a suitable send window offset, the stream becomes unblocked. |
618 | 615 |
619 // Ensure that Writev consumes all the data it is given (simulate no socket | 616 // Ensure that Writev consumes all the data it is given (simulate no socket |
620 // blocking). | 617 // blocking). |
621 session_.set_writev_consumes_all_data(true); | 618 session_.set_writev_consumes_all_data(true); |
622 | 619 |
623 // Create a stream, and send enough data to make it flow control blocked. | 620 // Create a stream, and send enough data to make it flow control blocked. |
624 TestStream* stream2 = session_.CreateOutgoingDataStream(); | 621 TestStream* stream2 = session_.CreateOutgoingDynamicStream(); |
625 string body(kMinimumFlowControlSendWindow, '.'); | 622 string body(kMinimumFlowControlSendWindow, '.'); |
626 EXPECT_FALSE(stream2->flow_controller()->IsBlocked()); | 623 EXPECT_FALSE(stream2->flow_controller()->IsBlocked()); |
627 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 624 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
628 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 625 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
629 EXPECT_CALL(*connection_, SendBlocked(stream2->id())); | 626 EXPECT_CALL(*connection_, SendBlocked(stream2->id())); |
630 EXPECT_CALL(*connection_, SendBlocked(0)); | 627 EXPECT_CALL(*connection_, SendBlocked(0)); |
631 stream2->SendBody(body, false); | 628 stream2->SendBody(body, false); |
632 EXPECT_TRUE(stream2->flow_controller()->IsBlocked()); | 629 EXPECT_TRUE(stream2->flow_controller()->IsBlocked()); |
633 EXPECT_TRUE(session_.IsConnectionFlowControlBlocked()); | 630 EXPECT_TRUE(session_.IsConnectionFlowControlBlocked()); |
634 EXPECT_TRUE(session_.IsStreamFlowControlBlocked()); | 631 EXPECT_TRUE(session_.IsStreamFlowControlBlocked()); |
(...skipping 14 matching lines...) Expand all Loading... |
649 | 646 |
650 TEST_P(QuicSessionTestServer, HandshakeUnblocksFlowControlBlockedCryptoStream) { | 647 TEST_P(QuicSessionTestServer, HandshakeUnblocksFlowControlBlockedCryptoStream) { |
651 // Test that if the crypto stream is flow control blocked, then if the SHLO | 648 // Test that if the crypto stream is flow control blocked, then if the SHLO |
652 // contains a larger send window offset, the stream becomes unblocked. | 649 // contains a larger send window offset, the stream becomes unblocked. |
653 session_.set_writev_consumes_all_data(true); | 650 session_.set_writev_consumes_all_data(true); |
654 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); | 651 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); |
655 EXPECT_FALSE(crypto_stream->flow_controller()->IsBlocked()); | 652 EXPECT_FALSE(crypto_stream->flow_controller()->IsBlocked()); |
656 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 653 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
657 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 654 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
658 QuicHeadersStream* headers_stream = | 655 QuicHeadersStream* headers_stream = |
659 QuicSessionPeer::GetHeadersStream(&session_); | 656 QuicSpdySessionPeer::GetHeadersStream(&session_); |
660 EXPECT_FALSE(headers_stream->flow_controller()->IsBlocked()); | 657 EXPECT_FALSE(headers_stream->flow_controller()->IsBlocked()); |
661 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 658 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
662 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 659 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
663 // Write until the crypto stream is flow control blocked. | 660 // Write until the crypto stream is flow control blocked. |
664 EXPECT_CALL(*connection_, SendBlocked(kCryptoStreamId)); | 661 EXPECT_CALL(*connection_, SendBlocked(kCryptoStreamId)); |
665 int i = 0; | 662 int i = 0; |
666 while (!crypto_stream->flow_controller()->IsBlocked() && i < 1000) { | 663 while (!crypto_stream->flow_controller()->IsBlocked() && i < 1000) { |
667 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 664 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
668 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 665 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
669 QuicConfig config; | 666 QuicConfig config; |
(...skipping 26 matching lines...) Expand all Loading... |
696 TEST_P(QuicSessionTestServer, | 693 TEST_P(QuicSessionTestServer, |
697 HandshakeUnblocksFlowControlBlockedHeadersStream) { | 694 HandshakeUnblocksFlowControlBlockedHeadersStream) { |
698 // Test that if the header stream is flow control blocked, then if the SHLO | 695 // Test that if the header stream is flow control blocked, then if the SHLO |
699 // contains a larger send window offset, the stream becomes unblocked. | 696 // contains a larger send window offset, the stream becomes unblocked. |
700 session_.set_writev_consumes_all_data(true); | 697 session_.set_writev_consumes_all_data(true); |
701 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); | 698 TestCryptoStream* crypto_stream = session_.GetCryptoStream(); |
702 EXPECT_FALSE(crypto_stream->flow_controller()->IsBlocked()); | 699 EXPECT_FALSE(crypto_stream->flow_controller()->IsBlocked()); |
703 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 700 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
704 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 701 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
705 QuicHeadersStream* headers_stream = | 702 QuicHeadersStream* headers_stream = |
706 QuicSessionPeer::GetHeadersStream(&session_); | 703 QuicSpdySessionPeer::GetHeadersStream(&session_); |
707 EXPECT_FALSE(headers_stream->flow_controller()->IsBlocked()); | 704 EXPECT_FALSE(headers_stream->flow_controller()->IsBlocked()); |
708 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 705 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
709 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 706 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
710 QuicStreamId stream_id = 5; | 707 QuicStreamId stream_id = 5; |
711 // Write until the header stream is flow control blocked. | 708 // Write until the header stream is flow control blocked. |
712 EXPECT_CALL(*connection_, SendBlocked(kHeadersStreamId)); | 709 EXPECT_CALL(*connection_, SendBlocked(kHeadersStreamId)); |
713 SpdyHeaderBlock headers; | 710 SpdyHeaderBlock headers; |
714 while (!headers_stream->flow_controller()->IsBlocked() && stream_id < 2000) { | 711 while (!headers_stream->flow_controller()->IsBlocked() && stream_id < 2000) { |
715 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 712 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
716 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 713 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
(...skipping 24 matching lines...) Expand all Loading... |
741 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 738 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
742 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); | 739 EXPECT_FALSE(session_.IsStreamFlowControlBlocked()); |
743 EXPECT_FALSE(headers_stream->HasBufferedData()); | 740 EXPECT_FALSE(headers_stream->HasBufferedData()); |
744 } | 741 } |
745 | 742 |
746 TEST_P(QuicSessionTestServer, ConnectionFlowControlAccountingRstOutOfOrder) { | 743 TEST_P(QuicSessionTestServer, ConnectionFlowControlAccountingRstOutOfOrder) { |
747 // Test that when we receive an out of order stream RST we correctly adjust | 744 // Test that when we receive an out of order stream RST we correctly adjust |
748 // our connection level flow control receive window. | 745 // our connection level flow control receive window. |
749 // On close, the stream should mark as consumed all bytes between the highest | 746 // On close, the stream should mark as consumed all bytes between the highest |
750 // byte consumed so far and the final byte offset from the RST frame. | 747 // byte consumed so far and the final byte offset from the RST frame. |
751 TestStream* stream = session_.CreateOutgoingDataStream(); | 748 TestStream* stream = session_.CreateOutgoingDynamicStream(); |
752 | 749 |
753 const QuicStreamOffset kByteOffset = | 750 const QuicStreamOffset kByteOffset = |
754 1 + kInitialSessionFlowControlWindowForTest / 2; | 751 1 + kInitialSessionFlowControlWindowForTest / 2; |
755 | 752 |
756 // Expect no stream WINDOW_UPDATE frames, as stream read side closed. | 753 // Expect no stream WINDOW_UPDATE frames, as stream read side closed. |
757 EXPECT_CALL(*connection_, SendWindowUpdate(stream->id(), _)).Times(0); | 754 EXPECT_CALL(*connection_, SendWindowUpdate(stream->id(), _)).Times(0); |
758 // We do expect a connection level WINDOW_UPDATE when the stream is reset. | 755 // We do expect a connection level WINDOW_UPDATE when the stream is reset. |
759 EXPECT_CALL(*connection_, | 756 EXPECT_CALL(*connection_, |
760 SendWindowUpdate(0, kInitialSessionFlowControlWindowForTest + | 757 SendWindowUpdate(0, kInitialSessionFlowControlWindowForTest + |
761 kByteOffset)).Times(1); | 758 kByteOffset)).Times(1); |
762 | 759 |
763 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); | 760 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); |
764 QuicRstStreamFrame rst_frame(stream->id(), QUIC_STREAM_CANCELLED, | 761 QuicRstStreamFrame rst_frame(stream->id(), QUIC_STREAM_CANCELLED, |
765 kByteOffset); | 762 kByteOffset); |
766 session_.OnRstStream(rst_frame); | 763 session_.OnRstStream(rst_frame); |
767 session_.PostProcessAfterData(); | 764 session_.PostProcessAfterData(); |
768 EXPECT_EQ(kByteOffset, session_.flow_controller()->bytes_consumed()); | 765 EXPECT_EQ(kByteOffset, session_.flow_controller()->bytes_consumed()); |
769 } | 766 } |
770 | 767 |
771 TEST_P(QuicSessionTestServer, ConnectionFlowControlAccountingFinAndLocalReset) { | 768 TEST_P(QuicSessionTestServer, ConnectionFlowControlAccountingFinAndLocalReset) { |
772 // Test the situation where we receive a FIN on a stream, and before we fully | 769 // Test the situation where we receive a FIN on a stream, and before we fully |
773 // consume all the data from the sequencer buffer we locally RST the stream. | 770 // consume all the data from the sequencer buffer we locally RST the stream. |
774 // The bytes between highest consumed byte, and the final byte offset that we | 771 // The bytes between highest consumed byte, and the final byte offset that we |
775 // determined when the FIN arrived, should be marked as consumed at the | 772 // determined when the FIN arrived, should be marked as consumed at the |
776 // connection level flow controller when the stream is reset. | 773 // connection level flow controller when the stream is reset. |
777 TestStream* stream = session_.CreateOutgoingDataStream(); | 774 TestStream* stream = session_.CreateOutgoingDynamicStream(); |
778 | 775 |
779 const QuicStreamOffset kByteOffset = | 776 const QuicStreamOffset kByteOffset = |
780 kInitialSessionFlowControlWindowForTest / 2; | 777 kInitialSessionFlowControlWindowForTest / 2; |
781 QuicStreamFrame frame(stream->id(), true, kByteOffset, StringPiece()); | 778 QuicStreamFrame frame(stream->id(), true, kByteOffset, StringPiece()); |
782 vector<QuicStreamFrame> frames; | 779 vector<QuicStreamFrame> frames; |
783 frames.push_back(frame); | 780 frames.push_back(frame); |
784 session_.OnStreamFrames(frames); | 781 session_.OnStreamFrames(frames); |
785 session_.PostProcessAfterData(); | 782 session_.PostProcessAfterData(); |
786 EXPECT_TRUE(connection_->connected()); | 783 EXPECT_TRUE(connection_->connected()); |
787 | 784 |
(...skipping 16 matching lines...) Expand all Loading... |
804 // due to other active streams. | 801 // due to other active streams. |
805 const uint64 kInitialConnectionBytesConsumed = 567; | 802 const uint64 kInitialConnectionBytesConsumed = 567; |
806 const uint64 kInitialConnectionHighestReceivedOffset = 1234; | 803 const uint64 kInitialConnectionHighestReceivedOffset = 1234; |
807 EXPECT_LT(kInitialConnectionBytesConsumed, | 804 EXPECT_LT(kInitialConnectionBytesConsumed, |
808 kInitialConnectionHighestReceivedOffset); | 805 kInitialConnectionHighestReceivedOffset); |
809 session_.flow_controller()->UpdateHighestReceivedOffset( | 806 session_.flow_controller()->UpdateHighestReceivedOffset( |
810 kInitialConnectionHighestReceivedOffset); | 807 kInitialConnectionHighestReceivedOffset); |
811 session_.flow_controller()->AddBytesConsumed(kInitialConnectionBytesConsumed); | 808 session_.flow_controller()->AddBytesConsumed(kInitialConnectionBytesConsumed); |
812 | 809 |
813 // Reset our stream: this results in the stream being closed locally. | 810 // Reset our stream: this results in the stream being closed locally. |
814 TestStream* stream = session_.CreateOutgoingDataStream(); | 811 TestStream* stream = session_.CreateOutgoingDynamicStream(); |
815 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); | 812 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); |
816 stream->Reset(QUIC_STREAM_CANCELLED); | 813 stream->Reset(QUIC_STREAM_CANCELLED); |
817 | 814 |
818 // Now receive a response from the peer with a FIN. We should handle this by | 815 // Now receive a response from the peer with a FIN. We should handle this by |
819 // adjusting the connection level flow control receive window to take into | 816 // adjusting the connection level flow control receive window to take into |
820 // account the total number of bytes sent by the peer. | 817 // account the total number of bytes sent by the peer. |
821 const QuicStreamOffset kByteOffset = 5678; | 818 const QuicStreamOffset kByteOffset = 5678; |
822 string body = "hello"; | 819 string body = "hello"; |
823 QuicStreamFrame frame(stream->id(), true, kByteOffset, StringPiece(body)); | 820 QuicStreamFrame frame(stream->id(), true, kByteOffset, StringPiece(body)); |
824 vector<QuicStreamFrame> frames; | 821 vector<QuicStreamFrame> frames; |
(...skipping 18 matching lines...) Expand all Loading... |
843 // due to other active streams. | 840 // due to other active streams. |
844 const uint64 kInitialConnectionBytesConsumed = 567; | 841 const uint64 kInitialConnectionBytesConsumed = 567; |
845 const uint64 kInitialConnectionHighestReceivedOffset = 1234; | 842 const uint64 kInitialConnectionHighestReceivedOffset = 1234; |
846 EXPECT_LT(kInitialConnectionBytesConsumed, | 843 EXPECT_LT(kInitialConnectionBytesConsumed, |
847 kInitialConnectionHighestReceivedOffset); | 844 kInitialConnectionHighestReceivedOffset); |
848 session_.flow_controller()->UpdateHighestReceivedOffset( | 845 session_.flow_controller()->UpdateHighestReceivedOffset( |
849 kInitialConnectionHighestReceivedOffset); | 846 kInitialConnectionHighestReceivedOffset); |
850 session_.flow_controller()->AddBytesConsumed(kInitialConnectionBytesConsumed); | 847 session_.flow_controller()->AddBytesConsumed(kInitialConnectionBytesConsumed); |
851 | 848 |
852 // Reset our stream: this results in the stream being closed locally. | 849 // Reset our stream: this results in the stream being closed locally. |
853 TestStream* stream = session_.CreateOutgoingDataStream(); | 850 TestStream* stream = session_.CreateOutgoingDynamicStream(); |
854 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); | 851 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); |
855 stream->Reset(QUIC_STREAM_CANCELLED); | 852 stream->Reset(QUIC_STREAM_CANCELLED); |
856 | 853 |
857 // Now receive a RST from the peer. We should handle this by adjusting the | 854 // Now receive a RST from the peer. We should handle this by adjusting the |
858 // connection level flow control receive window to take into account the total | 855 // connection level flow control receive window to take into account the total |
859 // number of bytes sent by the peer. | 856 // number of bytes sent by the peer. |
860 const QuicStreamOffset kByteOffset = 5678; | 857 const QuicStreamOffset kByteOffset = 5678; |
861 QuicRstStreamFrame rst_frame(stream->id(), QUIC_STREAM_CANCELLED, | 858 QuicRstStreamFrame rst_frame(stream->id(), QUIC_STREAM_CANCELLED, |
862 kByteOffset); | 859 kByteOffset); |
863 session_.OnRstStream(rst_frame); | 860 session_.OnRstStream(rst_frame); |
(...skipping 30 matching lines...) Expand all Loading... |
894 | 891 |
895 TEST_P(QuicSessionTestServer, FlowControlWithInvalidFinalOffset) { | 892 TEST_P(QuicSessionTestServer, FlowControlWithInvalidFinalOffset) { |
896 // Test that if we receive a stream RST with a highest byte offset that | 893 // Test that if we receive a stream RST with a highest byte offset that |
897 // violates flow control, that we close the connection. | 894 // violates flow control, that we close the connection. |
898 const uint64 kLargeOffset = kInitialSessionFlowControlWindowForTest + 1; | 895 const uint64 kLargeOffset = kInitialSessionFlowControlWindowForTest + 1; |
899 EXPECT_CALL(*connection_, | 896 EXPECT_CALL(*connection_, |
900 SendConnectionClose(QUIC_FLOW_CONTROL_RECEIVED_TOO_MUCH_DATA)) | 897 SendConnectionClose(QUIC_FLOW_CONTROL_RECEIVED_TOO_MUCH_DATA)) |
901 .Times(2); | 898 .Times(2); |
902 | 899 |
903 // Check that stream frame + FIN results in connection close. | 900 // Check that stream frame + FIN results in connection close. |
904 TestStream* stream = session_.CreateOutgoingDataStream(); | 901 TestStream* stream = session_.CreateOutgoingDynamicStream(); |
905 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); | 902 EXPECT_CALL(*connection_, SendRstStream(stream->id(), _, _)); |
906 stream->Reset(QUIC_STREAM_CANCELLED); | 903 stream->Reset(QUIC_STREAM_CANCELLED); |
907 QuicStreamFrame frame(stream->id(), true, kLargeOffset, StringPiece()); | 904 QuicStreamFrame frame(stream->id(), true, kLargeOffset, StringPiece()); |
908 vector<QuicStreamFrame> frames; | 905 vector<QuicStreamFrame> frames; |
909 frames.push_back(frame); | 906 frames.push_back(frame); |
910 session_.OnStreamFrames(frames); | 907 session_.OnStreamFrames(frames); |
911 | 908 |
912 // Check that RST results in connection close. | 909 // Check that RST results in connection close. |
913 QuicRstStreamFrame rst_frame(stream->id(), QUIC_STREAM_CANCELLED, | 910 QuicRstStreamFrame rst_frame(stream->id(), QUIC_STREAM_CANCELLED, |
914 kLargeOffset); | 911 kLargeOffset); |
915 session_.OnRstStream(rst_frame); | 912 session_.OnRstStream(rst_frame); |
916 } | 913 } |
917 | 914 |
918 TEST_P(QuicSessionTestServer, WindowUpdateUnblocksHeadersStream) { | 915 TEST_P(QuicSessionTestServer, WindowUpdateUnblocksHeadersStream) { |
919 // Test that a flow control blocked headers stream gets unblocked on recipt of | 916 // Test that a flow control blocked headers stream gets unblocked on recipt of |
920 // a WINDOW_UPDATE frame. | 917 // a WINDOW_UPDATE frame. |
921 | 918 |
922 // Set the headers stream to be flow control blocked. | 919 // Set the headers stream to be flow control blocked. |
923 QuicHeadersStream* headers_stream = | 920 QuicHeadersStream* headers_stream = |
924 QuicSessionPeer::GetHeadersStream(&session_); | 921 QuicSpdySessionPeer::GetHeadersStream(&session_); |
925 QuicFlowControllerPeer::SetSendWindowOffset(headers_stream->flow_controller(), | 922 QuicFlowControllerPeer::SetSendWindowOffset(headers_stream->flow_controller(), |
926 0); | 923 0); |
927 EXPECT_TRUE(headers_stream->flow_controller()->IsBlocked()); | 924 EXPECT_TRUE(headers_stream->flow_controller()->IsBlocked()); |
928 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); | 925 EXPECT_FALSE(session_.IsConnectionFlowControlBlocked()); |
929 EXPECT_TRUE(session_.IsStreamFlowControlBlocked()); | 926 EXPECT_TRUE(session_.IsStreamFlowControlBlocked()); |
930 | 927 |
931 // Unblock the headers stream by supplying a WINDOW_UPDATE. | 928 // Unblock the headers stream by supplying a WINDOW_UPDATE. |
932 QuicWindowUpdateFrame window_update_frame(headers_stream->id(), | 929 QuicWindowUpdateFrame window_update_frame(headers_stream->id(), |
933 2 * kMinimumFlowControlSendWindow); | 930 2 * kMinimumFlowControlSendWindow); |
934 vector<QuicWindowUpdateFrame> frames; | 931 vector<QuicWindowUpdateFrame> frames; |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
970 class QuicSessionTestClient : public QuicSessionTestBase { | 967 class QuicSessionTestClient : public QuicSessionTestBase { |
971 protected: | 968 protected: |
972 QuicSessionTestClient() : QuicSessionTestBase(Perspective::IS_CLIENT) {} | 969 QuicSessionTestClient() : QuicSessionTestBase(Perspective::IS_CLIENT) {} |
973 }; | 970 }; |
974 | 971 |
975 INSTANTIATE_TEST_CASE_P(Tests, | 972 INSTANTIATE_TEST_CASE_P(Tests, |
976 QuicSessionTestClient, | 973 QuicSessionTestClient, |
977 ::testing::ValuesIn(QuicSupportedVersions())); | 974 ::testing::ValuesIn(QuicSupportedVersions())); |
978 | 975 |
979 TEST_P(QuicSessionTestClient, ImplicitlyCreatedStreamsClient) { | 976 TEST_P(QuicSessionTestClient, ImplicitlyCreatedStreamsClient) { |
980 ASSERT_TRUE(session_.GetIncomingDataStream(6) != nullptr); | 977 ASSERT_TRUE(session_.GetIncomingDynamicStream(6) != nullptr); |
981 // Both 2 and 4 should be implicitly created. | 978 // Both 2 and 4 should be implicitly created. |
982 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 2)); | 979 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 2)); |
983 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 4)); | 980 EXPECT_TRUE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 4)); |
984 ASSERT_TRUE(session_.GetIncomingDataStream(2) != nullptr); | 981 ASSERT_TRUE(session_.GetIncomingDynamicStream(2) != nullptr); |
985 ASSERT_TRUE(session_.GetIncomingDataStream(4) != nullptr); | 982 ASSERT_TRUE(session_.GetIncomingDynamicStream(4) != nullptr); |
986 // And 5 should be not implicitly created. | 983 // And 5 should be not implicitly created. |
987 EXPECT_FALSE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 5)); | 984 EXPECT_FALSE(QuicSessionPeer::IsStreamImplicitlyCreated(&session_, 5)); |
988 } | 985 } |
989 | 986 |
990 } // namespace | 987 } // namespace |
991 } // namespace test | 988 } // namespace test |
992 } // namespace net | 989 } // namespace net |
OLD | NEW |