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

Side by Side Diff: net/url_request/url_fetcher_impl_unittest.cc

Issue 1732493002: Prevent URLFetcher::AppendChunkedData from dereferencing NULL pointers. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Remove unused variable Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « net/url_request/url_fetcher_core.cc ('k') | net/url_request/url_request.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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/url_request/url_fetcher_impl.h" 5 #include "net/url_request/url_fetcher_impl.h"
6 6
7 #include <stdint.h> 7 #include <stdint.h>
8 #include <string.h> 8 #include <string.h>
9 9
10 #include <algorithm> 10 #include <algorithm>
11 #include <limits> 11 #include <limits>
12 #include <string> 12 #include <string>
13 13
14 #include "base/bind.h" 14 #include "base/bind.h"
15 #include "base/files/file_path.h" 15 #include "base/files/file_path.h"
16 #include "base/files/file_util.h" 16 #include "base/files/file_util.h"
17 #include "base/files/scoped_temp_dir.h" 17 #include "base/files/scoped_temp_dir.h"
18 #include "base/location.h" 18 #include "base/location.h"
19 #include "base/macros.h" 19 #include "base/macros.h"
20 #include "base/memory/scoped_ptr.h" 20 #include "base/memory/scoped_ptr.h"
21 #include "base/path_service.h" 21 #include "base/path_service.h"
22 #include "base/run_loop.h" 22 #include "base/run_loop.h"
23 #include "base/single_thread_task_runner.h" 23 #include "base/single_thread_task_runner.h"
24 #include "base/strings/string_util.h" 24 #include "base/strings/string_util.h"
25 #include "base/strings/stringprintf.h" 25 #include "base/strings/stringprintf.h"
26 #include "base/synchronization/waitable_event.h" 26 #include "base/synchronization/waitable_event.h"
27 #include "base/test/test_timeouts.h"
27 #include "base/thread_task_runner_handle.h" 28 #include "base/thread_task_runner_handle.h"
29 #include "base/threading/platform_thread.h"
28 #include "base/threading/thread.h" 30 #include "base/threading/thread.h"
29 #include "build/build_config.h" 31 #include "build/build_config.h"
30 #include "crypto/nss_util.h" 32 #include "crypto/nss_util.h"
31 #include "net/base/elements_upload_data_stream.h" 33 #include "net/base/elements_upload_data_stream.h"
32 #include "net/base/network_change_notifier.h" 34 #include "net/base/network_change_notifier.h"
33 #include "net/base/upload_bytes_element_reader.h" 35 #include "net/base/upload_bytes_element_reader.h"
34 #include "net/base/upload_element_reader.h" 36 #include "net/base/upload_element_reader.h"
35 #include "net/base/upload_file_element_reader.h" 37 #include "net/base/upload_file_element_reader.h"
36 #include "net/dns/mock_host_resolver.h" 38 #include "net/dns/mock_host_resolver.h"
37 #include "net/http/http_response_headers.h" 39 #include "net/http/http_response_headers.h"
(...skipping 730 matching lines...) Expand 10 before | Expand all | Expand 10 after
768 delegate.StartFetcherAndWait(); 770 delegate.StartFetcherAndWait();
769 771
770 EXPECT_TRUE(delegate.fetcher()->GetStatus().is_success()); 772 EXPECT_TRUE(delegate.fetcher()->GetStatus().is_success());
771 EXPECT_EQ(500, delegate.fetcher()->GetResponseCode()); 773 EXPECT_EQ(500, delegate.fetcher()->GetResponseCode());
772 std::string data; 774 std::string data;
773 ASSERT_TRUE(delegate.fetcher()->GetResponseAsString(&data)); 775 ASSERT_TRUE(delegate.fetcher()->GetResponseAsString(&data));
774 EXPECT_EQ(kCreateUploadStreamBody, data); 776 EXPECT_EQ(kCreateUploadStreamBody, data);
775 EXPECT_EQ(2u, num_upload_streams_created()); 777 EXPECT_EQ(2u, num_upload_streams_created());
776 } 778 }
777 779
780 // Tests simple chunked POST case.
781 TEST_F(URLFetcherTest, PostChunked) {
782 scoped_refptr<FetcherTestURLRequestContextGetter> context_getter(
783 CreateCrossThreadContextGetter());
784
785 WaitingURLFetcherDelegate delegate;
786 delegate.CreateFetcher(test_server_->GetURL("/echo"), URLFetcher::POST,
787 CreateCrossThreadContextGetter());
788
789 delegate.fetcher()->SetChunkedUpload("text/plain");
790
791 // This posts a task to start the fetcher.
792 delegate.fetcher()->Start();
793
794 delegate.fetcher()->AppendChunkToUpload(kCreateUploadStreamBody, false);
795 delegate.fetcher()->AppendChunkToUpload(kCreateUploadStreamBody, true);
796
797 delegate.WaitForComplete();
798
799 EXPECT_TRUE(delegate.fetcher()->GetStatus().is_success());
800 EXPECT_EQ(200, delegate.fetcher()->GetResponseCode());
801 std::string data;
802 ASSERT_TRUE(delegate.fetcher()->GetResponseAsString(&data));
803 EXPECT_EQ(std::string(kCreateUploadStreamBody) +
804 std::string(kCreateUploadStreamBody),
805 data);
806 }
807
808 // Tests that data can be appended to a request after it fails. This is needed
809 // because the consumer may try to append data to a request after it failed, but
810 // before the consumer learns that it failed.
811 TEST_F(URLFetcherTest, PostAppendChunkAfterError) {
812 scoped_refptr<FetcherTestURLRequestContextGetter> context_getter(
813 CreateCrossThreadContextGetter());
814
815 WaitingURLFetcherDelegate delegate;
816 // Request that will fail almost immediately after being started, due to using
817 // a reserved port.
818 delegate.CreateFetcher(GURL("http://127.0.0.1:7"), URLFetcher::POST,
819 context_getter);
820
821 delegate.fetcher()->SetChunkedUpload("text/plain");
822
823 // This posts a task to start the fetcher.
824 delegate.fetcher()->Start();
825
826 // Give the request a chance to fail, and inform the fetcher of the failure,
827 // while blocking the current thread so the error doesn't reach the delegate.
828 base::PlatformThread::Sleep(TestTimeouts::tiny_timeout());
829
830 // Try to append data.
831 delegate.fetcher()->AppendChunkToUpload("kCreateUploadStreamBody", false);
832 delegate.fetcher()->AppendChunkToUpload("kCreateUploadStreamBody", true);
833
834 delegate.WaitForComplete();
835
836 // Make sure the request failed, as expected.
837 EXPECT_FALSE(delegate.fetcher()->GetStatus().is_success());
838 EXPECT_EQ(ERR_UNSAFE_PORT, delegate.fetcher()->GetStatus().error());
839 }
840
778 // Checks that upload progress increases over time, never exceeds what's already 841 // Checks that upload progress increases over time, never exceeds what's already
779 // been sent, and adds a chunk whenever all previously appended chunks have 842 // been sent, and adds a chunk whenever all previously appended chunks have
780 // been uploaded. 843 // been uploaded.
781 class CheckUploadProgressDelegate : public WaitingURLFetcherDelegate { 844 class CheckUploadProgressDelegate : public WaitingURLFetcherDelegate {
782 public: 845 public:
783 CheckUploadProgressDelegate() 846 CheckUploadProgressDelegate()
784 : chunk_(1 << 16, 'a'), num_chunks_appended_(0), last_seen_progress_(0) {} 847 : chunk_(1 << 16, 'a'), num_chunks_appended_(0), last_seen_progress_(0) {}
785 ~CheckUploadProgressDelegate() override {} 848 ~CheckUploadProgressDelegate() override {}
786 849
787 void OnURLFetchUploadProgress(const URLFetcher* source, 850 void OnURLFetchUploadProgress(const URLFetcher* source,
(...skipping 248 matching lines...) Expand 10 before | Expand all | Expand 10 after
1036 1099
1037 EXPECT_TRUE(delegate.fetcher()->GetStatus().is_success()); 1100 EXPECT_TRUE(delegate.fetcher()->GetStatus().is_success());
1038 EXPECT_EQ(200, delegate.fetcher()->GetResponseCode()); 1101 EXPECT_EQ(200, delegate.fetcher()->GetResponseCode());
1039 } 1102 }
1040 1103
1041 // 20 requests were sent. Due to throttling, they should have collectively 1104 // 20 requests were sent. Due to throttling, they should have collectively
1042 // taken over 1 second. 1105 // taken over 1 second.
1043 EXPECT_GE(Time::Now() - start_time, base::TimeDelta::FromSeconds(1)); 1106 EXPECT_GE(Time::Now() - start_time, base::TimeDelta::FromSeconds(1));
1044 } 1107 }
1045 1108
1109 // If throttling kicks in for a chunked upload, there should be no crash.
1110 TEST_F(URLFetcherTest, ThrottleChunkedUpload) {
1111 GURL url(test_server_->GetURL("/echo"));
1112
1113 scoped_refptr<FetcherTestURLRequestContextGetter> context_getter(
1114 CreateSameThreadContextGetter());
1115
1116 // Registers an entry for test url. It only allows 3 requests to be sent
1117 // in 200 milliseconds.
1118 context_getter->AddThrottlerEntry(
1119 url, std::string() /* url_id */, 200 /* sliding_window_period_ms */,
1120 3 /* max_send_threshold */, 1 /* initial_backoff_ms */,
1121 2.0 /* multiply_factor */, 0.0 /* jitter_factor */,
1122 256 /* maximum_backoff_ms */,
1123 false /* reserve_sending_time_for_next_request*/);
1124
1125 for (int i = 0; i < 20; ++i) {
1126 WaitingURLFetcherDelegate delegate;
1127 delegate.CreateFetcher(url, URLFetcher::POST, context_getter);
1128 delegate.fetcher()->SetChunkedUpload("text/plain");
1129 delegate.fetcher()->Start();
1130 delegate.fetcher()->AppendChunkToUpload(kCreateUploadStreamBody, true);
1131 delegate.WaitForComplete();
1132
1133 EXPECT_TRUE(delegate.fetcher()->GetStatus().is_success());
1134 EXPECT_EQ(200, delegate.fetcher()->GetResponseCode());
1135 std::string data;
1136 ASSERT_TRUE(delegate.fetcher()->GetResponseAsString(&data));
1137 EXPECT_EQ(kCreateUploadStreamBody, data);
1138 }
1139 }
1140
1046 TEST_F(URLFetcherTest, ThrottleOn5xxRetries) { 1141 TEST_F(URLFetcherTest, ThrottleOn5xxRetries) {
1047 base::Time start_time = Time::Now(); 1142 base::Time start_time = Time::Now();
1048 GURL url(test_server_->GetURL("/server-unavailable.html")); 1143 GURL url(test_server_->GetURL("/server-unavailable.html"));
1049 1144
1050 scoped_refptr<FetcherTestURLRequestContextGetter> context_getter( 1145 scoped_refptr<FetcherTestURLRequestContextGetter> context_getter(
1051 CreateSameThreadContextGetter()); 1146 CreateSameThreadContextGetter());
1052 1147
1053 // Registers an entry for test url. The backoff time is calculated by: 1148 // Registers an entry for test url. The backoff time is calculated by:
1054 // new_backoff = 2.0 * old_backoff + 0 1149 // new_backoff = 2.0 * old_backoff + 0
1055 // and maximum backoff time is 256 milliseconds. 1150 // and maximum backoff time is 256 milliseconds.
(...skipping 371 matching lines...) Expand 10 before | Expand all | Expand 10 after
1427 EXPECT_EQ(-1, delegate.fetcher()->GetResponseCode()); 1522 EXPECT_EQ(-1, delegate.fetcher()->GetResponseCode());
1428 EXPECT_TRUE(delegate.fetcher()->GetCookies().empty()); 1523 EXPECT_TRUE(delegate.fetcher()->GetCookies().empty());
1429 std::string data; 1524 std::string data;
1430 EXPECT_TRUE(delegate.fetcher()->GetResponseAsString(&data)); 1525 EXPECT_TRUE(delegate.fetcher()->GetResponseAsString(&data));
1431 EXPECT_TRUE(data.empty()); 1526 EXPECT_TRUE(data.empty());
1432 } 1527 }
1433 1528
1434 } // namespace 1529 } // namespace
1435 1530
1436 } // namespace net 1531 } // namespace net
OLDNEW
« no previous file with comments | « net/url_request/url_fetcher_core.cc ('k') | net/url_request/url_request.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698