| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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_simple_server_session.h" | 5 #include "net/tools/quic/quic_simple_server_session.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "base/macros.h" | 9 #include "base/macros.h" |
| 10 #include "base/strings/string_number_conversions.h" | 10 #include "base/strings/string_number_conversions.h" |
| (...skipping 13 matching lines...) Expand all Loading... |
| 24 #include "net/quic/test_tools/quic_sustained_bandwidth_recorder_peer.h" | 24 #include "net/quic/test_tools/quic_sustained_bandwidth_recorder_peer.h" |
| 25 #include "net/quic/test_tools/quic_test_utils.h" | 25 #include "net/quic/test_tools/quic_test_utils.h" |
| 26 #include "net/test/gtest_util.h" | 26 #include "net/test/gtest_util.h" |
| 27 #include "net/tools/quic/quic_simple_server_stream.h" | 27 #include "net/tools/quic/quic_simple_server_stream.h" |
| 28 #include "net/tools/quic/test_tools/mock_quic_server_session_visitor.h" | 28 #include "net/tools/quic/test_tools/mock_quic_server_session_visitor.h" |
| 29 #include "net/tools/quic/test_tools/quic_in_memory_cache_peer.h" | 29 #include "net/tools/quic/test_tools/quic_in_memory_cache_peer.h" |
| 30 #include "testing/gmock/include/gmock/gmock.h" | 30 #include "testing/gmock/include/gmock/gmock.h" |
| 31 #include "testing/gtest/include/gtest/gtest.h" | 31 #include "testing/gtest/include/gtest/gtest.h" |
| 32 | 32 |
| 33 using net::test::CryptoTestUtils; | 33 using net::test::CryptoTestUtils; |
| 34 using net::test::GenerateBody; |
| 34 using net::test::MockConnection; | 35 using net::test::MockConnection; |
| 35 using net::test::MockConnectionHelper; | 36 using net::test::MockConnectionHelper; |
| 36 using net::test::QuicConfigPeer; | 37 using net::test::QuicConfigPeer; |
| 37 using net::test::QuicConnectionPeer; | 38 using net::test::QuicConnectionPeer; |
| 38 using net::test::QuicSpdyStreamPeer; | 39 using net::test::QuicSpdyStreamPeer; |
| 39 using net::test::QuicSentPacketManagerPeer; | 40 using net::test::QuicSentPacketManagerPeer; |
| 40 using net::test::QuicSessionPeer; | 41 using net::test::QuicSessionPeer; |
| 41 using net::test::QuicSpdySessionPeer; | 42 using net::test::QuicSpdySessionPeer; |
| 42 using net::test::QuicSustainedBandwidthRecorderPeer; | 43 using net::test::QuicSustainedBandwidthRecorderPeer; |
| 43 using net::test::SupportedVersions; | 44 using net::test::SupportedVersions; |
| (...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 169 QuicRandom::GetInstance(), &clock, | 170 QuicRandom::GetInstance(), &clock, |
| 170 QuicCryptoServerConfig::ConfigOptions())); | 171 QuicCryptoServerConfig::ConfigOptions())); |
| 171 session_->Initialize(); | 172 session_->Initialize(); |
| 172 visitor_ = QuicConnectionPeer::GetVisitor(connection_); | 173 visitor_ = QuicConnectionPeer::GetVisitor(connection_); |
| 173 headers_stream_ = new MockQuicHeadersStream(session_.get()); | 174 headers_stream_ = new MockQuicHeadersStream(session_.get()); |
| 174 QuicSpdySessionPeer::SetHeadersStream(session_.get(), headers_stream_); | 175 QuicSpdySessionPeer::SetHeadersStream(session_.get(), headers_stream_); |
| 175 // TODO(jri): Remove this line once tests pass. | 176 // TODO(jri): Remove this line once tests pass. |
| 176 FLAGS_quic_cede_correctly = false; | 177 FLAGS_quic_cede_correctly = false; |
| 177 } | 178 } |
| 178 | 179 |
| 179 // Given |num_resources|, create this number of fake push resources and push | |
| 180 // them by sending PUSH_PROMISE for all and sending push responses for as much | |
| 181 // as possible(limited by kMaxStreamsForTest). | |
| 182 // If |num_resources| > kMaxStreamsForTest, the left over will be queued. | |
| 183 void PromisePushResources(size_t num_resources) { | |
| 184 // Assume encryption already established. | |
| 185 MockQuicCryptoServerStream* crypto_stream = | |
| 186 new MockQuicCryptoServerStream(&crypto_config_, session_.get()); | |
| 187 crypto_stream->set_encryption_established(true); | |
| 188 QuicSimpleServerSessionPeer::SetCryptoStream(session_.get(), crypto_stream); | |
| 189 | |
| 190 QuicInMemoryCachePeer::ResetForTests(); | |
| 191 | |
| 192 string request_url = "mail.google.com/"; | |
| 193 SpdyHeaderBlock request_headers; | |
| 194 string resource_host = "www.google.com"; | |
| 195 string partial_push_resource_path = "/server_push_src"; | |
| 196 string partial_push_response_body = | |
| 197 "Push resource body " + partial_push_resource_path; | |
| 198 list<QuicInMemoryCache::ServerPushInfo> push_resources; | |
| 199 string scheme = "http"; | |
| 200 for (unsigned int i = 1; i <= num_resources; ++i) { | |
| 201 string path = partial_push_resource_path + base::UintToString(i); | |
| 202 string url = scheme + "://" + resource_host + path; | |
| 203 GURL resource_url = GURL(url); | |
| 204 string body = partial_push_response_body + base::UintToString(i); | |
| 205 SpdyHeaderBlock response_headers; | |
| 206 QuicInMemoryCache::GetInstance()->AddSimpleResponse(resource_host, path, | |
| 207 200, body); | |
| 208 push_resources.push_back(QuicInMemoryCache::ServerPushInfo( | |
| 209 resource_url, response_headers, kDefaultPriority, body)); | |
| 210 // PUSH_PROMISED are sent for all the resources. | |
| 211 EXPECT_CALL(*headers_stream_, | |
| 212 WritePushPromise(kClientDataStreamId1, i * 2, _, nullptr)); | |
| 213 if (i <= kMaxStreamsForTest) { | |
| 214 // |kMaxStreamsForTest| promised responses should be sent. | |
| 215 EXPECT_CALL(*headers_stream_, | |
| 216 WriteHeaders(i * 2, _, false, kDefaultPriority, nullptr)); | |
| 217 // Mock that SendStreamData() returns less than supposed to send to keep | |
| 218 // the stream open. | |
| 219 EXPECT_CALL(*connection_, SendStreamData(i * 2, _, 0, true, _, nullptr)) | |
| 220 .WillOnce(Return(QuicConsumedData(0, false))); | |
| 221 } | |
| 222 } | |
| 223 session_->PromisePushResources(request_url, push_resources, | |
| 224 kClientDataStreamId1, request_headers); | |
| 225 } | |
| 226 | |
| 227 StrictMock<MockQuicServerSessionVisitor> owner_; | 180 StrictMock<MockQuicServerSessionVisitor> owner_; |
| 228 MockConnectionHelper helper_; | 181 MockConnectionHelper helper_; |
| 229 StrictMock<MockConnectionWithSendStreamData>* connection_; | 182 StrictMock<MockConnectionWithSendStreamData>* connection_; |
| 230 QuicConfig config_; | 183 QuicConfig config_; |
| 231 QuicCryptoServerConfig crypto_config_; | 184 QuicCryptoServerConfig crypto_config_; |
| 232 scoped_ptr<QuicSimpleServerSession> session_; | 185 scoped_ptr<QuicSimpleServerSession> session_; |
| 233 scoped_ptr<CryptoHandshakeMessage> handshake_message_; | 186 scoped_ptr<CryptoHandshakeMessage> handshake_message_; |
| 234 QuicConnectionVisitorInterface* visitor_; | 187 QuicConnectionVisitorInterface* visitor_; |
| 235 MockQuicHeadersStream* headers_stream_; | 188 MockQuicHeadersStream* headers_stream_; |
| 236 }; | 189 }; |
| (...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 396 } | 349 } |
| 397 | 350 |
| 398 TEST_P(QuicSimpleServerSessionTest, OnStreamFrameWithEvenStreamId) { | 351 TEST_P(QuicSimpleServerSessionTest, OnStreamFrameWithEvenStreamId) { |
| 399 QuicStreamFrame frame(2, false, 0, StringPiece()); | 352 QuicStreamFrame frame(2, false, 0, StringPiece()); |
| 400 EXPECT_CALL(*connection_, SendConnectionCloseWithDetails( | 353 EXPECT_CALL(*connection_, SendConnectionCloseWithDetails( |
| 401 QUIC_INVALID_STREAM_ID, | 354 QUIC_INVALID_STREAM_ID, |
| 402 "Client sent data on server push stream")); | 355 "Client sent data on server push stream")); |
| 403 session_->OnStreamFrame(frame); | 356 session_->OnStreamFrame(frame); |
| 404 } | 357 } |
| 405 | 358 |
| 406 TEST_P(QuicSimpleServerSessionTest, TestPromisePushResources) { | 359 TEST_P(QuicSimpleServerSessionTest, GetEvenIncomingError) { |
| 360 // Tests that calling GetOrCreateDynamicStream() on an outgoing stream not |
| 361 // promised yet should result close connection. |
| 362 EXPECT_CALL(*connection_, |
| 363 SendConnectionCloseWithDetails(QUIC_INVALID_STREAM_ID, |
| 364 "Data for nonexistent stream")); |
| 365 EXPECT_EQ(nullptr, |
| 366 QuicSessionPeer::GetOrCreateDynamicStream(session_.get(), 4)); |
| 367 } |
| 368 |
| 369 // In order to test the case where server push stream creation goes beyond |
| 370 // limit, server push streams need to be hanging there instead of |
| 371 // immediately closing after sending back response. |
| 372 // To achieve this goal, this class resets flow control windows so that large |
| 373 // responses will not be sent fully in order to prevent push streams from being |
| 374 // closed immediately. |
| 375 // Also adjust connection-level flow control window to ensure a large response |
| 376 // can cause stream-level flow control blocked but not connection-level. |
| 377 class QuicSimpleServerSessionServerPushTest |
| 378 : public QuicSimpleServerSessionTest { |
| 379 protected: |
| 380 const size_t kStreamFlowControlWindowSize = 32 * 1024; // 32KB. |
| 381 |
| 382 QuicSimpleServerSessionServerPushTest() : QuicSimpleServerSessionTest() { |
| 383 // This flag has to be true for negotiation of max number of outgoing |
| 384 // streams to work correctly. |
| 385 FLAGS_quic_different_max_num_open_streams = true; |
| 386 |
| 387 config_.SetMaxStreamsPerConnection(kMaxStreamsForTest, kMaxStreamsForTest); |
| 388 |
| 389 // Reset stream level flow control window to be 32KB. |
| 390 QuicConfigPeer::SetReceivedInitialStreamFlowControlWindow( |
| 391 &config_, kStreamFlowControlWindowSize); |
| 392 // Reset connection level flow control window to be 1.5 MB which is large |
| 393 // enough that it won't block any stream to write before stream level flow |
| 394 // control blocks it. |
| 395 QuicConfigPeer::SetReceivedInitialSessionFlowControlWindow( |
| 396 &config_, kInitialSessionFlowControlWindowForTest); |
| 397 |
| 398 connection_ = new StrictMock<MockConnectionWithSendStreamData>( |
| 399 &helper_, Perspective::IS_SERVER, SupportedVersions(GetParam())); |
| 400 session_.reset(new QuicSimpleServerSession(config_, connection_, &owner_, |
| 401 &crypto_config_)); |
| 402 session_->Initialize(); |
| 403 // Needed to make new session flow control window work. |
| 404 session_->OnConfigNegotiated(); |
| 405 |
| 406 visitor_ = QuicConnectionPeer::GetVisitor(connection_); |
| 407 headers_stream_ = new MockQuicHeadersStream(session_.get()); |
| 408 QuicSpdySessionPeer::SetHeadersStream(session_.get(), headers_stream_); |
| 409 |
| 410 // Assume encryption already established. |
| 411 MockQuicCryptoServerStream* crypto_stream = |
| 412 new MockQuicCryptoServerStream(&crypto_config_, session_.get()); |
| 413 crypto_stream->set_encryption_established(true); |
| 414 QuicSimpleServerSessionPeer::SetCryptoStream(session_.get(), crypto_stream); |
| 415 } |
| 416 |
| 417 // Given |num_resources|, create this number of fake push resources and push |
| 418 // them by sending PUSH_PROMISE for all and sending push responses for as much |
| 419 // as possible(limited by kMaxStreamsForTest). |
| 420 // If |num_resources| > kMaxStreamsForTest, the left over will be queued. |
| 421 void PromisePushResources(size_t num_resources) { |
| 422 // To prevent push streams from being closed the response need to be larger |
| 423 // than stream flow control window so stream won't send the full body. |
| 424 size_t body_size = 2 * kStreamFlowControlWindowSize; // 64KB. |
| 425 |
| 426 config_.SetMaxStreamsPerConnection(kMaxStreamsForTest, kMaxStreamsForTest); |
| 427 |
| 428 QuicInMemoryCachePeer::ResetForTests(); |
| 429 |
| 430 string request_url = "mail.google.com/"; |
| 431 SpdyHeaderBlock request_headers; |
| 432 string resource_host = "www.google.com"; |
| 433 string partial_push_resource_path = "/server_push_src"; |
| 434 list<QuicInMemoryCache::ServerPushInfo> push_resources; |
| 435 string scheme = "http"; |
| 436 for (unsigned int i = 1; i <= num_resources; ++i) { |
| 437 QuicStreamId stream_id = i * 2; |
| 438 string path = partial_push_resource_path + base::UintToString(i); |
| 439 string url = scheme + "://" + resource_host + path; |
| 440 GURL resource_url = GURL(url); |
| 441 string body; |
| 442 GenerateBody(&body, body_size); |
| 443 SpdyHeaderBlock response_headers; |
| 444 QuicInMemoryCache::GetInstance()->AddSimpleResponse(resource_host, path, |
| 445 200, body); |
| 446 push_resources.push_back(QuicInMemoryCache::ServerPushInfo( |
| 447 resource_url, response_headers, kDefaultPriority, body)); |
| 448 // PUSH_PROMISED are sent for all the resources. |
| 449 EXPECT_CALL(*headers_stream_, WritePushPromise(kClientDataStreamId1, |
| 450 stream_id, _, nullptr)); |
| 451 if (i <= kMaxStreamsForTest) { |
| 452 // |kMaxStreamsForTest| promised responses should be sent. |
| 453 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_id, _, false, |
| 454 kDefaultPriority, nullptr)); |
| 455 // Since flow control window is smaller than response body, not the |
| 456 // whole body will be sent. |
| 457 EXPECT_CALL(*connection_, |
| 458 SendStreamData(stream_id, _, 0, false, _, nullptr)) |
| 459 .WillOnce( |
| 460 Return(QuicConsumedData(kStreamFlowControlWindowSize, false))); |
| 461 EXPECT_CALL(*connection_, SendBlocked(stream_id)); |
| 462 } |
| 463 } |
| 464 session_->PromisePushResources(request_url, push_resources, |
| 465 kClientDataStreamId1, request_headers); |
| 466 } |
| 467 }; |
| 468 |
| 469 INSTANTIATE_TEST_CASE_P(Tests, |
| 470 QuicSimpleServerSessionServerPushTest, |
| 471 ::testing::ValuesIn(QuicSupportedVersions())); |
| 472 |
| 473 TEST_P(QuicSimpleServerSessionServerPushTest, TestPromisePushResources) { |
| 407 // Tests that given more than kMaxOpenStreamForTest resources, all their | 474 // Tests that given more than kMaxOpenStreamForTest resources, all their |
| 408 // PUSH_PROMISE's will be sent out and only |kMaxOpenStreamForTest| streams | 475 // PUSH_PROMISE's will be sent out and only |kMaxOpenStreamForTest| streams |
| 409 // will be opened and send push response. | 476 // will be opened and send push response. |
| 410 size_t num_resources = kMaxStreamsForTest + 5; | 477 size_t num_resources = kMaxStreamsForTest + 5; |
| 411 PromisePushResources(num_resources); | 478 PromisePushResources(num_resources); |
| 412 EXPECT_EQ(kMaxStreamsForTest, session_->GetNumOpenOutgoingStreams()); | 479 EXPECT_EQ(kMaxStreamsForTest, session_->GetNumOpenOutgoingStreams()); |
| 413 } | 480 } |
| 414 | 481 |
| 415 TEST_P(QuicSimpleServerSessionTest, | 482 TEST_P(QuicSimpleServerSessionServerPushTest, |
| 416 HandlePromisedPushRequestsAfterStreamDraining) { | 483 HandlePromisedPushRequestsAfterStreamDraining) { |
| 417 // Tests that after promised stream queued up, when an opened stream is marked | 484 // Tests that after promised stream queued up, when an opened stream is marked |
| 418 // draining, a queued promised stream will become open and send push response. | 485 // draining, a queued promised stream will become open and send push response. |
| 419 size_t num_resources = kMaxStreamsForTest + 1; | 486 size_t num_resources = kMaxStreamsForTest + 1; |
| 420 PromisePushResources(num_resources); | 487 PromisePushResources(num_resources); |
| 421 QuicStreamId next_out_going_stream_id = num_resources * 2; | 488 QuicStreamId next_out_going_stream_id = num_resources * 2; |
| 422 | 489 |
| 423 // After an open stream is marked draining, a new stream is expected to be | 490 // After an open stream is marked draining, a new stream is expected to be |
| 424 // created and a response sent on the stream. | 491 // created and a response sent on the stream. |
| 425 EXPECT_CALL(*headers_stream_, WriteHeaders(next_out_going_stream_id, _, false, | 492 EXPECT_CALL(*headers_stream_, WriteHeaders(next_out_going_stream_id, _, false, |
| 426 kDefaultPriority, nullptr)); | 493 kDefaultPriority, nullptr)); |
| 427 EXPECT_CALL(*connection_, | 494 EXPECT_CALL(*connection_, |
| 428 SendStreamData(next_out_going_stream_id, _, 0, true, _, nullptr)) | 495 SendStreamData(next_out_going_stream_id, _, 0, false, _, nullptr)) |
| 429 .WillOnce(Return(QuicConsumedData(0, false))); | 496 .WillOnce(Return(QuicConsumedData(kStreamFlowControlWindowSize, false))); |
| 497 EXPECT_CALL(*connection_, SendBlocked(next_out_going_stream_id)); |
| 430 session_->StreamDraining(2); | 498 session_->StreamDraining(2); |
| 431 // Number of open outgoing streams should still be the same, because a new | 499 // Number of open outgoing streams should still be the same, because a new |
| 432 // stream is opened. And the queue should be empty. | 500 // stream is opened. And the queue should be empty. |
| 433 EXPECT_EQ(kMaxStreamsForTest, session_->GetNumOpenOutgoingStreams()); | 501 EXPECT_EQ(kMaxStreamsForTest, session_->GetNumOpenOutgoingStreams()); |
| 434 } | 502 } |
| 435 | 503 |
| 436 TEST_P(QuicSimpleServerSessionTest, GetEvenIncomingError) { | 504 TEST_P(QuicSimpleServerSessionServerPushTest, |
| 437 // Tests that calling GetOrCreateDynamicStream() on an outgoing stream not | 505 ResetPromisedStreamToCancelServerPush) { |
| 438 // promised yet should result close connection. | |
| 439 EXPECT_CALL(*connection_, | |
| 440 SendConnectionCloseWithDetails(QUIC_INVALID_STREAM_ID, | |
| 441 "Data for nonexistent stream")); | |
| 442 EXPECT_EQ(nullptr, | |
| 443 QuicSessionPeer::GetOrCreateDynamicStream(session_.get(), 4)); | |
| 444 } | |
| 445 | |
| 446 TEST_P(QuicSimpleServerSessionTest, ResetPromisedStreamToCancelServerPush) { | |
| 447 // Tests that after all resources are promised, a RST frame from client can | 506 // Tests that after all resources are promised, a RST frame from client can |
| 448 // prevent a promised resource to be send out. | 507 // prevent a promised resource to be send out. |
| 449 | 508 |
| 450 // Having two extra resources to be send later. One of them will be reset, so | 509 // Having two extra resources to be send later. One of them will be reset, so |
| 451 // when opened stream become close, only one will become open. | 510 // when opened stream become close, only one will become open. |
| 452 size_t num_resources = kMaxStreamsForTest + 2; | 511 size_t num_resources = kMaxStreamsForTest + 2; |
| 453 PromisePushResources(num_resources); | 512 PromisePushResources(num_resources); |
| 454 | 513 |
| 455 // Reset the last stream in the queue. It should be marked cancelled. | 514 // Reset the last stream in the queue. It should be marked cancelled. |
| 456 QuicStreamId stream_got_reset = num_resources * 2; | 515 QuicStreamId stream_got_reset = num_resources * 2; |
| 457 QuicRstStreamFrame rst(stream_got_reset, QUIC_STREAM_CANCELLED, 0); | 516 QuicRstStreamFrame rst(stream_got_reset, QUIC_STREAM_CANCELLED, 0); |
| 458 EXPECT_CALL(*connection_, | 517 EXPECT_CALL(*connection_, |
| 459 SendRstStream(stream_got_reset, QUIC_RST_ACKNOWLEDGEMENT, 0)); | 518 SendRstStream(stream_got_reset, QUIC_RST_ACKNOWLEDGEMENT, 0)); |
| 460 visitor_->OnRstStream(rst); | 519 visitor_->OnRstStream(rst); |
| 461 | 520 |
| 462 // When the first 2 streams becomes draining, the two queued up stream could | 521 // When the first 2 streams becomes draining, the two queued up stream could |
| 463 // be created. But since one of them was marked cancelled due to RST frame, | 522 // be created. But since one of them was marked cancelled due to RST frame, |
| 464 // only one queued resource will be sent out. | 523 // only one queued resource will be sent out. |
| 465 QuicStreamId stream_not_reset = (kMaxStreamsForTest + 1) * 2; | 524 QuicStreamId stream_not_reset = (kMaxStreamsForTest + 1) * 2; |
| 466 InSequence s; | 525 InSequence s; |
| 467 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_not_reset, _, false, | 526 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_not_reset, _, false, |
| 468 kDefaultPriority, nullptr)); | 527 kDefaultPriority, nullptr)); |
| 469 EXPECT_CALL(*connection_, | 528 EXPECT_CALL(*connection_, |
| 470 SendStreamData(stream_not_reset, _, 0, true, _, nullptr)) | 529 SendStreamData(stream_not_reset, _, 0, false, _, nullptr)) |
| 471 .WillOnce(Return(QuicConsumedData(0, false))); | 530 .WillOnce(Return(QuicConsumedData(kStreamFlowControlWindowSize, false))); |
| 531 EXPECT_CALL(*connection_, SendBlocked(stream_not_reset)); |
| 472 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_got_reset, _, false, | 532 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_got_reset, _, false, |
| 473 kDefaultPriority, nullptr)) | 533 kDefaultPriority, nullptr)) |
| 474 .Times(0); | 534 .Times(0); |
| 475 | 535 |
| 476 session_->StreamDraining(2); | 536 session_->StreamDraining(2); |
| 477 session_->StreamDraining(4); | 537 session_->StreamDraining(4); |
| 478 } | 538 } |
| 479 | 539 |
| 480 TEST_P(QuicSimpleServerSessionTest, CloseStreamToHandleMorePromisedStream) { | 540 TEST_P(QuicSimpleServerSessionServerPushTest, |
| 541 CloseStreamToHandleMorePromisedStream) { |
| 481 // Tests that closing a open outgoing stream can trigger a promised resource | 542 // Tests that closing a open outgoing stream can trigger a promised resource |
| 482 // in the queue to be send out. | 543 // in the queue to be send out. |
| 483 size_t num_resources = kMaxStreamsForTest + 1; | 544 size_t num_resources = kMaxStreamsForTest + 1; |
| 484 PromisePushResources(num_resources); | 545 PromisePushResources(num_resources); |
| 485 QuicStreamId stream_to_open = num_resources * 2; | 546 QuicStreamId stream_to_open = num_resources * 2; |
| 486 | 547 |
| 487 // Resetting 1st open stream will close the stream and give space for extra | 548 // Resetting 1st open stream will close the stream and give space for extra |
| 488 // stream to be opened. | 549 // stream to be opened. |
| 489 QuicStreamId stream_got_reset = 2; | 550 QuicStreamId stream_got_reset = 2; |
| 490 EXPECT_CALL(*connection_, | 551 EXPECT_CALL(*connection_, |
| 491 SendRstStream(stream_got_reset, QUIC_RST_ACKNOWLEDGEMENT, _)); | 552 SendRstStream(stream_got_reset, QUIC_RST_ACKNOWLEDGEMENT, _)); |
| 492 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_to_open, _, false, | 553 EXPECT_CALL(*headers_stream_, WriteHeaders(stream_to_open, _, false, |
| 493 kDefaultPriority, nullptr)); | 554 kDefaultPriority, nullptr)); |
| 494 EXPECT_CALL(*connection_, | 555 EXPECT_CALL(*connection_, |
| 495 SendStreamData(stream_to_open, _, 0, true, _, nullptr)) | 556 SendStreamData(stream_to_open, _, 0, false, _, nullptr)) |
| 496 .WillOnce(Return(QuicConsumedData(0, false))); | 557 .WillOnce(Return(QuicConsumedData(kStreamFlowControlWindowSize, false))); |
| 497 | 558 |
| 559 EXPECT_CALL(*connection_, SendBlocked(stream_to_open)); |
| 498 QuicRstStreamFrame rst(stream_got_reset, QUIC_STREAM_CANCELLED, 0); | 560 QuicRstStreamFrame rst(stream_got_reset, QUIC_STREAM_CANCELLED, 0); |
| 499 visitor_->OnRstStream(rst); | 561 visitor_->OnRstStream(rst); |
| 500 } | 562 } |
| 501 | 563 |
| 502 } // namespace | 564 } // namespace |
| 503 } // namespace test | 565 } // namespace test |
| 504 } // namespace net | 566 } // namespace net |
| OLD | NEW |