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/spdy/spdy_http_stream.h" | 5 #include "net/spdy/spdy_http_stream.h" |
6 | 6 |
7 #include <stdint.h> | 7 #include <stdint.h> |
8 | 8 |
9 #include <memory> | 9 #include <memory> |
10 | 10 |
11 #include "base/run_loop.h" | 11 #include "base/run_loop.h" |
12 #include "base/stl_util.h" | 12 #include "base/stl_util.h" |
13 #include "crypto/ec_private_key.h" | 13 #include "crypto/ec_private_key.h" |
14 #include "crypto/ec_signature_creator.h" | 14 #include "crypto/ec_signature_creator.h" |
15 #include "crypto/signature_creator.h" | 15 #include "crypto/signature_creator.h" |
16 #include "net/base/chunked_upload_data_stream.h" | 16 #include "net/base/chunked_upload_data_stream.h" |
17 #include "net/base/load_timing_info.h" | 17 #include "net/base/load_timing_info.h" |
18 #include "net/base/load_timing_info_test_util.h" | 18 #include "net/base/load_timing_info_test_util.h" |
19 #include "net/base/test_completion_callback.h" | 19 #include "net/base/test_completion_callback.h" |
20 #include "net/cert/asn1_util.h" | 20 #include "net/cert/asn1_util.h" |
21 #include "net/http/http_request_info.h" | 21 #include "net/http/http_request_info.h" |
22 #include "net/http/http_response_headers.h" | 22 #include "net/http/http_response_headers.h" |
23 #include "net/http/http_response_info.h" | 23 #include "net/http/http_response_info.h" |
24 #include "net/log/test_net_log.h" | 24 #include "net/log/test_net_log.h" |
25 #include "net/socket/next_proto.h" | |
26 #include "net/socket/socket_test_util.h" | 25 #include "net/socket/socket_test_util.h" |
27 #include "net/spdy/spdy_http_utils.h" | 26 #include "net/spdy/spdy_http_utils.h" |
28 #include "net/spdy/spdy_session.h" | 27 #include "net/spdy/spdy_session.h" |
29 #include "net/spdy/spdy_test_util_common.h" | 28 #include "net/spdy/spdy_test_util_common.h" |
30 #include "net/ssl/default_channel_id_store.h" | 29 #include "net/ssl/default_channel_id_store.h" |
31 #include "net/test/gtest_util.h" | 30 #include "net/test/gtest_util.h" |
32 #include "testing/gmock/include/gmock/gmock.h" | 31 #include "testing/gmock/include/gmock/gmock.h" |
33 #include "testing/gtest/include/gtest/gtest.h" | 32 #include "testing/gtest/include/gtest/gtest.h" |
34 | 33 |
35 using net::test::IsError; | 34 using net::test::IsError; |
(...skipping 304 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
340 // Stream 2 still has queued body data. | 339 // Stream 2 still has queued body data. |
341 TestLoadTimingReused(*http_stream2); | 340 TestLoadTimingReused(*http_stream2); |
342 | 341 |
343 EXPECT_EQ(static_cast<int64_t>(req2->size()), | 342 EXPECT_EQ(static_cast<int64_t>(req2->size()), |
344 http_stream2->GetTotalSentBytes()); | 343 http_stream2->GetTotalSentBytes()); |
345 EXPECT_EQ(static_cast<int64_t>(resp2->size() + body2->size()), | 344 EXPECT_EQ(static_cast<int64_t>(resp2->size() + body2->size()), |
346 http_stream2->GetTotalReceivedBytes()); | 345 http_stream2->GetTotalReceivedBytes()); |
347 } | 346 } |
348 | 347 |
349 TEST_P(SpdyHttpStreamTest, SendChunkedPost) { | 348 TEST_P(SpdyHttpStreamTest, SendChunkedPost) { |
350 BufferedSpdyFramer framer(HTTP2); | 349 BufferedSpdyFramer framer; |
351 | 350 |
352 std::unique_ptr<SpdySerializedFrame> req( | 351 std::unique_ptr<SpdySerializedFrame> req( |
353 spdy_util_.ConstructChunkedSpdyPost(nullptr, 0)); | 352 spdy_util_.ConstructChunkedSpdyPost(nullptr, 0)); |
354 std::unique_ptr<SpdySerializedFrame> body( | 353 std::unique_ptr<SpdySerializedFrame> body( |
355 framer.CreateDataFrame(1, kUploadData, kUploadDataSize, DATA_FLAG_FIN)); | 354 framer.CreateDataFrame(1, kUploadData, kUploadDataSize, DATA_FLAG_FIN)); |
356 MockWrite writes[] = { | 355 MockWrite writes[] = { |
357 CreateMockWrite(*req, 0), // request | 356 CreateMockWrite(*req, 0), // request |
358 CreateMockWrite(*body, 1) // POST upload frame | 357 CreateMockWrite(*body, 1) // POST upload frame |
359 }; | 358 }; |
360 | 359 |
361 std::unique_ptr<SpdySerializedFrame> resp( | 360 std::unique_ptr<SpdySerializedFrame> resp( |
362 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); | 361 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); |
363 MockRead reads[] = { | 362 MockRead reads[] = { |
364 CreateMockRead(*resp, 2), | 363 CreateMockRead(*resp, 2), |
365 CreateMockRead(*body, 3), | 364 CreateMockRead(*body, 3), |
366 MockRead(SYNCHRONOUS, 0, 4) // EOF | 365 MockRead(SYNCHRONOUS, 0, 4) // EOF |
367 }; | 366 }; |
368 | 367 |
369 InitSession(reads, arraysize(reads), writes, arraysize(writes)); | 368 InitSession(reads, arraysize(reads), writes, arraysize(writes)); |
370 EXPECT_EQ(HTTP2, session_->GetProtocolVersion()); | |
371 | 369 |
372 ChunkedUploadDataStream upload_stream(0); | 370 ChunkedUploadDataStream upload_stream(0); |
373 const int kFirstChunkSize = kUploadDataSize/2; | 371 const int kFirstChunkSize = kUploadDataSize/2; |
374 upload_stream.AppendData(kUploadData, kFirstChunkSize, false); | 372 upload_stream.AppendData(kUploadData, kFirstChunkSize, false); |
375 upload_stream.AppendData(kUploadData + kFirstChunkSize, | 373 upload_stream.AppendData(kUploadData + kFirstChunkSize, |
376 kUploadDataSize - kFirstChunkSize, true); | 374 kUploadDataSize - kFirstChunkSize, true); |
377 | 375 |
378 HttpRequestInfo request; | 376 HttpRequestInfo request; |
379 request.method = "POST"; | 377 request.method = "POST"; |
380 request.url = GURL("http://www.example.org/"); | 378 request.url = GURL("http://www.example.org/"); |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
421 | 419 |
422 std::unique_ptr<SpdySerializedFrame> resp( | 420 std::unique_ptr<SpdySerializedFrame> resp( |
423 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); | 421 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); |
424 MockRead reads[] = { | 422 MockRead reads[] = { |
425 CreateMockRead(*resp, 2), | 423 CreateMockRead(*resp, 2), |
426 CreateMockRead(*chunk, 3), | 424 CreateMockRead(*chunk, 3), |
427 MockRead(SYNCHRONOUS, 0, 4) // EOF | 425 MockRead(SYNCHRONOUS, 0, 4) // EOF |
428 }; | 426 }; |
429 | 427 |
430 InitSession(reads, arraysize(reads), writes, arraysize(writes)); | 428 InitSession(reads, arraysize(reads), writes, arraysize(writes)); |
431 EXPECT_EQ(HTTP2, session_->GetProtocolVersion()); | |
432 | 429 |
433 ChunkedUploadDataStream upload_stream(0); | 430 ChunkedUploadDataStream upload_stream(0); |
434 upload_stream.AppendData(nullptr, 0, true); | 431 upload_stream.AppendData(nullptr, 0, true); |
435 | 432 |
436 HttpRequestInfo request; | 433 HttpRequestInfo request; |
437 request.method = "POST"; | 434 request.method = "POST"; |
438 request.url = GURL("http://www.example.org/"); | 435 request.url = GURL("http://www.example.org/"); |
439 request.upload_data_stream = &upload_stream; | 436 request.upload_data_stream = &upload_stream; |
440 | 437 |
441 ASSERT_THAT(upload_stream.Init(TestCompletionCallback().callback()), IsOk()); | 438 ASSERT_THAT(upload_stream.Init(TestCompletionCallback().callback()), IsOk()); |
(...skipping 15 matching lines...) Expand all Loading... |
457 http_stream.GetTotalSentBytes()); | 454 http_stream.GetTotalSentBytes()); |
458 EXPECT_EQ(static_cast<int64_t>(resp->size() + chunk->size()), | 455 EXPECT_EQ(static_cast<int64_t>(resp->size() + chunk->size()), |
459 http_stream.GetTotalReceivedBytes()); | 456 http_stream.GetTotalReceivedBytes()); |
460 | 457 |
461 // Because the server closed the connection, there shouldn't be a session | 458 // Because the server closed the connection, there shouldn't be a session |
462 // in the pool anymore. | 459 // in the pool anymore. |
463 EXPECT_FALSE(HasSpdySession(http_session_->spdy_session_pool(), key_)); | 460 EXPECT_FALSE(HasSpdySession(http_session_->spdy_session_pool(), key_)); |
464 } | 461 } |
465 | 462 |
466 TEST_P(SpdyHttpStreamTest, ConnectionClosedDuringChunkedPost) { | 463 TEST_P(SpdyHttpStreamTest, ConnectionClosedDuringChunkedPost) { |
467 BufferedSpdyFramer framer(HTTP2); | 464 BufferedSpdyFramer framer; |
468 | 465 |
469 std::unique_ptr<SpdySerializedFrame> req( | 466 std::unique_ptr<SpdySerializedFrame> req( |
470 spdy_util_.ConstructChunkedSpdyPost(nullptr, 0)); | 467 spdy_util_.ConstructChunkedSpdyPost(nullptr, 0)); |
471 std::unique_ptr<SpdySerializedFrame> body( | 468 std::unique_ptr<SpdySerializedFrame> body( |
472 framer.CreateDataFrame(1, kUploadData, kUploadDataSize, DATA_FLAG_NONE)); | 469 framer.CreateDataFrame(1, kUploadData, kUploadDataSize, DATA_FLAG_NONE)); |
473 MockWrite writes[] = { | 470 MockWrite writes[] = { |
474 CreateMockWrite(*req, 0), // Request | 471 CreateMockWrite(*req, 0), // Request |
475 CreateMockWrite(*body, 1) // First POST upload frame | 472 CreateMockWrite(*body, 1) // First POST upload frame |
476 }; | 473 }; |
477 | 474 |
478 std::unique_ptr<SpdySerializedFrame> resp( | 475 std::unique_ptr<SpdySerializedFrame> resp( |
479 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); | 476 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); |
480 MockRead reads[] = { | 477 MockRead reads[] = { |
481 MockRead(ASYNC, ERR_CONNECTION_CLOSED, 2) // Server hangs up early. | 478 MockRead(ASYNC, ERR_CONNECTION_CLOSED, 2) // Server hangs up early. |
482 }; | 479 }; |
483 | 480 |
484 InitSession(reads, arraysize(reads), writes, arraysize(writes)); | 481 InitSession(reads, arraysize(reads), writes, arraysize(writes)); |
485 EXPECT_EQ(HTTP2, session_->GetProtocolVersion()); | |
486 | 482 |
487 ChunkedUploadDataStream upload_stream(0); | 483 ChunkedUploadDataStream upload_stream(0); |
488 // Append first chunk. | 484 // Append first chunk. |
489 upload_stream.AppendData(kUploadData, kUploadDataSize, false); | 485 upload_stream.AppendData(kUploadData, kUploadDataSize, false); |
490 | 486 |
491 HttpRequestInfo request; | 487 HttpRequestInfo request; |
492 request.method = "POST"; | 488 request.method = "POST"; |
493 request.url = GURL("http://www.example.org/"); | 489 request.url = GURL("http://www.example.org/"); |
494 request.upload_data_stream = &upload_stream; | 490 request.upload_data_stream = &upload_stream; |
495 | 491 |
(...skipping 401 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
897 http_stream->GetTotalSentBytes()); | 893 http_stream->GetTotalSentBytes()); |
898 EXPECT_EQ(0, http_stream->GetTotalReceivedBytes()); | 894 EXPECT_EQ(0, http_stream->GetTotalReceivedBytes()); |
899 | 895 |
900 upload_stream.AppendData(kUploadData, kUploadDataSize, true); | 896 upload_stream.AppendData(kUploadData, kUploadDataSize, true); |
901 | 897 |
902 ASSERT_TRUE(callback.have_result()); | 898 ASSERT_TRUE(callback.have_result()); |
903 EXPECT_THAT(callback.WaitForResult(), IsOk()); | 899 EXPECT_THAT(callback.WaitForResult(), IsOk()); |
904 | 900 |
905 // Verify that the window size has decreased. | 901 // Verify that the window size has decreased. |
906 ASSERT_TRUE(http_stream->stream() != nullptr); | 902 ASSERT_TRUE(http_stream->stream() != nullptr); |
907 EXPECT_NE(static_cast<int>( | 903 EXPECT_NE(static_cast<int>(kDefaultInitialWindowSize), |
908 SpdySession::GetDefaultInitialWindowSize(session_->protocol())), | |
909 http_stream->stream()->send_window_size()); | 904 http_stream->stream()->send_window_size()); |
910 | 905 |
911 // Read window update. | 906 // Read window update. |
912 base::RunLoop().RunUntilIdle(); | 907 base::RunLoop().RunUntilIdle(); |
913 | 908 |
914 EXPECT_EQ(static_cast<int64_t>(req->size() + chunk1->size()), | 909 EXPECT_EQ(static_cast<int64_t>(req->size() + chunk1->size()), |
915 http_stream->GetTotalSentBytes()); | 910 http_stream->GetTotalSentBytes()); |
916 // The window update is not counted in the total received bytes. | 911 // The window update is not counted in the total received bytes. |
917 EXPECT_EQ(0, http_stream->GetTotalReceivedBytes()); | 912 EXPECT_EQ(0, http_stream->GetTotalReceivedBytes()); |
918 | 913 |
919 // Verify the window update. | 914 // Verify the window update. |
920 ASSERT_TRUE(http_stream->stream() != nullptr); | 915 ASSERT_TRUE(http_stream->stream() != nullptr); |
921 EXPECT_EQ(static_cast<int>( | 916 EXPECT_EQ(static_cast<int>(kDefaultInitialWindowSize), |
922 SpdySession::GetDefaultInitialWindowSize(session_->protocol())), | |
923 http_stream->stream()->send_window_size()); | 917 http_stream->stream()->send_window_size()); |
924 | 918 |
925 // Read rest of data. | 919 // Read rest of data. |
926 sequenced_data_->Resume(); | 920 sequenced_data_->Resume(); |
927 base::RunLoop().RunUntilIdle(); | 921 base::RunLoop().RunUntilIdle(); |
928 | 922 |
929 EXPECT_EQ(static_cast<int64_t>(req->size() + chunk1->size()), | 923 EXPECT_EQ(static_cast<int64_t>(req->size() + chunk1->size()), |
930 http_stream->GetTotalSentBytes()); | 924 http_stream->GetTotalSentBytes()); |
931 EXPECT_EQ(static_cast<int64_t>(resp->size() + chunk1->size()), | 925 EXPECT_EQ(static_cast<int64_t>(resp->size() + chunk1->size()), |
932 http_stream->GetTotalReceivedBytes()); | 926 http_stream->GetTotalReceivedBytes()); |
(...skipping 28 matching lines...) Expand all Loading... |
961 }; | 955 }; |
962 | 956 |
963 std::unique_ptr<SpdySerializedFrame> resp( | 957 std::unique_ptr<SpdySerializedFrame> resp( |
964 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); | 958 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); |
965 | 959 |
966 MockRead reads[] = { | 960 MockRead reads[] = { |
967 CreateMockRead(*resp, 2), MockRead(SYNCHRONOUS, 0, 3), | 961 CreateMockRead(*resp, 2), MockRead(SYNCHRONOUS, 0, 3), |
968 }; | 962 }; |
969 | 963 |
970 InitSession(reads, arraysize(reads), writes, arraysize(writes)); | 964 InitSession(reads, arraysize(reads), writes, arraysize(writes)); |
971 EXPECT_EQ(HTTP2, session_->GetProtocolVersion()); | |
972 | 965 |
973 ReadErrorUploadDataStream upload_data_stream( | 966 ReadErrorUploadDataStream upload_data_stream( |
974 ReadErrorUploadDataStream::FailureMode::SYNC); | 967 ReadErrorUploadDataStream::FailureMode::SYNC); |
975 ASSERT_THAT(upload_data_stream.Init(TestCompletionCallback().callback()), | 968 ASSERT_THAT(upload_data_stream.Init(TestCompletionCallback().callback()), |
976 IsOk()); | 969 IsOk()); |
977 | 970 |
978 HttpRequestInfo request; | 971 HttpRequestInfo request; |
979 request.method = "POST"; | 972 request.method = "POST"; |
980 request.url = GURL("http://www.example.org/"); | 973 request.url = GURL("http://www.example.org/"); |
981 request.upload_data_stream = &upload_data_stream; | 974 request.upload_data_stream = &upload_data_stream; |
(...skipping 30 matching lines...) Expand all Loading... |
1012 }; | 1005 }; |
1013 | 1006 |
1014 std::unique_ptr<SpdySerializedFrame> resp( | 1007 std::unique_ptr<SpdySerializedFrame> resp( |
1015 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); | 1008 spdy_util_.ConstructSpdyPostSynReply(nullptr, 0)); |
1016 | 1009 |
1017 MockRead reads[] = { | 1010 MockRead reads[] = { |
1018 MockRead(ASYNC, 0, 2), | 1011 MockRead(ASYNC, 0, 2), |
1019 }; | 1012 }; |
1020 | 1013 |
1021 InitSession(reads, arraysize(reads), writes, arraysize(writes)); | 1014 InitSession(reads, arraysize(reads), writes, arraysize(writes)); |
1022 EXPECT_EQ(HTTP2, session_->GetProtocolVersion()); | |
1023 | 1015 |
1024 ReadErrorUploadDataStream upload_data_stream( | 1016 ReadErrorUploadDataStream upload_data_stream( |
1025 ReadErrorUploadDataStream::FailureMode::ASYNC); | 1017 ReadErrorUploadDataStream::FailureMode::ASYNC); |
1026 ASSERT_THAT(upload_data_stream.Init(TestCompletionCallback().callback()), | 1018 ASSERT_THAT(upload_data_stream.Init(TestCompletionCallback().callback()), |
1027 IsOk()); | 1019 IsOk()); |
1028 | 1020 |
1029 HttpRequestInfo request; | 1021 HttpRequestInfo request; |
1030 request.method = "POST"; | 1022 request.method = "POST"; |
1031 request.url = GURL("http://www.example.org/"); | 1023 request.url = GURL("http://www.example.org/"); |
1032 request.upload_data_stream = &upload_data_stream; | 1024 request.upload_data_stream = &upload_data_stream; |
(...skipping 12 matching lines...) Expand all Loading... |
1045 | 1037 |
1046 // Because the server has closed the connection, there shouldn't be a session | 1038 // Because the server has closed the connection, there shouldn't be a session |
1047 // in the pool anymore. | 1039 // in the pool anymore. |
1048 EXPECT_FALSE(HasSpdySession(http_session_->spdy_session_pool(), key_)); | 1040 EXPECT_FALSE(HasSpdySession(http_session_->spdy_session_pool(), key_)); |
1049 } | 1041 } |
1050 | 1042 |
1051 // TODO(willchan): Write a longer test for SpdyStream that exercises all | 1043 // TODO(willchan): Write a longer test for SpdyStream that exercises all |
1052 // methods. | 1044 // methods. |
1053 | 1045 |
1054 } // namespace net | 1046 } // namespace net |
OLD | NEW |