Upstream version 10.39.225.0
[platform/framework/web/crosswalk.git] / src / net / quic / quic_end_to_end_unittest.cc
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
3 // found in the LICENSE file.
4
5 #include "base/basictypes.h"
6 #include "base/compiler_specific.h"
7 #include "base/memory/scoped_ptr.h"
8 #include "base/stl_util.h"
9 #include "base/strings/string_number_conversions.h"
10 #include "net/base/test_completion_callback.h"
11 #include "net/base/upload_bytes_element_reader.h"
12 #include "net/base/upload_data_stream.h"
13 #include "net/cert/mock_cert_verifier.h"
14 #include "net/dns/mapped_host_resolver.h"
15 #include "net/dns/mock_host_resolver.h"
16 #include "net/http/http_auth_handler_factory.h"
17 #include "net/http/http_network_session.h"
18 #include "net/http/http_network_transaction.h"
19 #include "net/http/http_server_properties_impl.h"
20 #include "net/http/http_transaction_test_util.h"
21 #include "net/http/transport_security_state.h"
22 #include "net/proxy/proxy_service.h"
23 #include "net/quic/test_tools/quic_test_utils.h"
24 #include "net/ssl/ssl_config_service_defaults.h"
25 #include "net/tools/quic/quic_in_memory_cache.h"
26 #include "net/tools/quic/quic_server.h"
27 #include "net/tools/quic/test_tools/quic_in_memory_cache_peer.h"
28 #include "net/tools/quic/test_tools/server_thread.h"
29 #include "testing/gtest/include/gtest/gtest.h"
30 #include "testing/platform_test.h"
31
32 using base::StringPiece;
33 using net::tools::QuicInMemoryCache;
34 using net::tools::QuicServer;
35 using net::tools::test::QuicInMemoryCachePeer;
36 using net::tools::test::ServerThread;
37
38 namespace net {
39 namespace test {
40
41 namespace {
42
43 const char kResponseBody[] = "some arbitrary response body";
44
45 // Factory for creating HttpTransactions, used by TestTransactionConsumer.
46 class TestTransactionFactory : public HttpTransactionFactory {
47  public:
48   TestTransactionFactory(const HttpNetworkSession::Params& params)
49       : session_(new HttpNetworkSession(params)) {}
50
51   virtual ~TestTransactionFactory() {
52   }
53
54   // HttpTransactionFactory methods
55   virtual int CreateTransaction(RequestPriority priority,
56                                 scoped_ptr<HttpTransaction>* trans) OVERRIDE {
57     trans->reset(new HttpNetworkTransaction(priority, session_.get()));
58     return OK;
59   }
60
61   virtual HttpCache* GetCache() OVERRIDE {
62     return NULL;
63   }
64
65   virtual HttpNetworkSession* GetSession() OVERRIDE { return session_.get(); };
66
67  private:
68   scoped_refptr<HttpNetworkSession> session_;
69 };
70
71 }  // namespace
72
73 class QuicEndToEndTest : public PlatformTest {
74  protected:
75   QuicEndToEndTest()
76       : host_resolver_impl_(CreateResolverImpl()),
77         host_resolver_(host_resolver_impl_.PassAs<HostResolver>()),
78         ssl_config_service_(new SSLConfigServiceDefaults),
79         proxy_service_(ProxyService::CreateDirect()),
80         auth_handler_factory_(
81             HttpAuthHandlerFactory::CreateDefault(&host_resolver_)),
82         strike_register_no_startup_period_(false) {
83     request_.method = "GET";
84     request_.url = GURL("http://www.google.com/");
85     request_.load_flags = 0;
86
87     params_.enable_quic = true;
88     params_.quic_clock = NULL;
89     params_.quic_random = NULL;
90     params_.host_resolver = &host_resolver_;
91     params_.cert_verifier = &cert_verifier_;
92     params_.transport_security_state = &transport_security_state_;
93     params_.proxy_service = proxy_service_.get();
94     params_.ssl_config_service = ssl_config_service_.get();
95     params_.http_auth_handler_factory = auth_handler_factory_.get();
96     params_.http_server_properties = http_server_properties.GetWeakPtr();
97   }
98
99   // Creates a mock host resolver in which www.google.com
100   // resolves to localhost.
101   static MockHostResolver* CreateResolverImpl() {
102     MockHostResolver* resolver = new MockHostResolver();
103     resolver->rules()->AddRule("www.google.com", "127.0.0.1");
104     return resolver;
105   }
106
107   virtual void SetUp() {
108     QuicInMemoryCachePeer::ResetForTests();
109     StartServer();
110
111     // Use a mapped host resolver so that request for www.google.com (port 80)
112     // reach the server running on localhost.
113     std::string map_rule = "MAP www.google.com www.google.com:" +
114         base::IntToString(server_thread_->GetPort());
115     EXPECT_TRUE(host_resolver_.AddRuleFromString(map_rule));
116
117     // To simplify the test, and avoid the race with the HTTP request, we force
118     // QUIC for these requests.
119     params_.origin_to_force_quic_on =
120         HostPortPair::FromString("www.google.com:80");
121
122     transaction_factory_.reset(new TestTransactionFactory(params_));
123   }
124
125   virtual void TearDown() {
126     StopServer();
127     QuicInMemoryCachePeer::ResetForTests();
128   }
129
130   // Starts the QUIC server listening on a random port.
131   void StartServer() {
132     net::IPAddressNumber ip;
133     CHECK(net::ParseIPLiteralToNumber("127.0.0.1", &ip));
134     server_address_ = IPEndPoint(ip, 0);
135     server_config_.SetDefaults();
136     server_config_.SetInitialFlowControlWindowToSend(
137         kInitialSessionFlowControlWindowForTest);
138     server_config_.SetInitialStreamFlowControlWindowToSend(
139         kInitialStreamFlowControlWindowForTest);
140     server_config_.SetInitialSessionFlowControlWindowToSend(
141         kInitialSessionFlowControlWindowForTest);
142     server_thread_.reset(new ServerThread(
143          new QuicServer(server_config_, QuicSupportedVersions()),
144          server_address_,
145          strike_register_no_startup_period_));
146     server_thread_->Initialize();
147     server_address_ = IPEndPoint(server_address_.address(),
148                                  server_thread_->GetPort());
149     server_thread_->Start();
150     server_started_ = true;
151   }
152
153   // Stops the QUIC server.
154   void StopServer() {
155     if (!server_started_) {
156       return;
157     }
158     if (server_thread_.get()) {
159       server_thread_->Quit();
160       server_thread_->Join();
161     }
162   }
163
164   // Adds an entry to the cache used by the QUIC server to serve
165   // responses.
166   void AddToCache(const StringPiece& method,
167                   const StringPiece& path,
168                   const StringPiece& version,
169                   const StringPiece& response_code,
170                   const StringPiece& response_detail,
171                   const StringPiece& body) {
172     QuicInMemoryCache::GetInstance()->AddSimpleResponse(
173         method, path, version, response_code, response_detail, body);
174   }
175
176   // Populates |request_body_| with |length_| ASCII bytes.
177   void GenerateBody(size_t length) {
178     request_body_.clear();
179     request_body_.reserve(length);
180     for (size_t i = 0; i < length; ++i) {
181       request_body_.append(1, static_cast<char>(32 + i % (126 - 32)));
182     }
183   }
184
185   // Initializes |request_| for a post of |length| bytes.
186   void InitializePostRequest(size_t length) {
187     GenerateBody(length);
188     ScopedVector<UploadElementReader> element_readers;
189     element_readers.push_back(
190         new UploadBytesElementReader(request_body_.data(),
191                                      request_body_.length()));
192     upload_data_stream_.reset(new UploadDataStream(element_readers.Pass(), 0));
193     request_.method = "POST";
194     request_.url = GURL("http://www.google.com/");
195     request_.upload_data_stream = upload_data_stream_.get();
196     ASSERT_EQ(OK, request_.upload_data_stream->Init(CompletionCallback()));
197   }
198
199   // Checks that |consumer| completed and received |status_line| and |body|.
200   void CheckResponse(const TestTransactionConsumer& consumer,
201                      const std::string& status_line,
202                      const std::string& body) {
203     ASSERT_TRUE(consumer.is_done());
204     EXPECT_EQ(OK, consumer.error());
205     EXPECT_EQ(status_line,
206               consumer.response_info()->headers->GetStatusLine());
207     EXPECT_EQ(body, consumer.content());
208   }
209
210   scoped_ptr<MockHostResolver> host_resolver_impl_;
211   MappedHostResolver host_resolver_;
212   MockCertVerifier cert_verifier_;
213   TransportSecurityState transport_security_state_;
214   scoped_refptr<SSLConfigServiceDefaults> ssl_config_service_;
215   scoped_ptr<ProxyService> proxy_service_;
216   scoped_ptr<HttpAuthHandlerFactory> auth_handler_factory_;
217   HttpServerPropertiesImpl http_server_properties;
218   HttpNetworkSession::Params params_;
219   scoped_ptr<TestTransactionFactory> transaction_factory_;
220   HttpRequestInfo request_;
221   std::string request_body_;
222   scoped_ptr<UploadDataStream> upload_data_stream_;
223   scoped_ptr<ServerThread> server_thread_;
224   IPEndPoint server_address_;
225   std::string server_hostname_;
226   QuicConfig server_config_;
227   bool server_started_;
228   bool strike_register_no_startup_period_;
229 };
230
231 TEST_F(QuicEndToEndTest, LargeGetWithNoPacketLoss) {
232   std::string response(10 * 1024, 'x');
233
234   AddToCache("GET", request_.url.spec(),
235              "HTTP/1.1", "200", "OK",
236              response);
237
238   TestTransactionConsumer consumer(DEFAULT_PRIORITY,
239                                    transaction_factory_.get());
240   consumer.Start(&request_, BoundNetLog());
241
242   // Will terminate when the last consumer completes.
243   base::MessageLoop::current()->Run();
244
245   CheckResponse(consumer, "HTTP/1.1 200 OK", response);
246 }
247
248 // http://crbug.com/307284
249 TEST_F(QuicEndToEndTest, DISABLED_LargePostWithNoPacketLoss) {
250   InitializePostRequest(10 * 1024 * 1024);
251
252   AddToCache("POST", request_.url.spec(),
253              "HTTP/1.1", "200", "OK",
254              kResponseBody);
255
256   TestTransactionConsumer consumer(DEFAULT_PRIORITY,
257                                    transaction_factory_.get());
258   consumer.Start(&request_, BoundNetLog());
259
260   // Will terminate when the last consumer completes.
261   base::MessageLoop::current()->Run();
262
263   CheckResponse(consumer, "HTTP/1.1 200 OK", kResponseBody);
264 }
265
266 TEST_F(QuicEndToEndTest, LargePostWithPacketLoss) {
267   // FLAGS_fake_packet_loss_percentage = 30;
268   InitializePostRequest(1024 * 1024);
269
270   const char kResponseBody[] = "some really big response body";
271   AddToCache("POST", request_.url.spec(),
272              "HTTP/1.1", "200", "OK",
273              kResponseBody);
274
275   TestTransactionConsumer consumer(DEFAULT_PRIORITY,
276                                    transaction_factory_.get());
277   consumer.Start(&request_, BoundNetLog());
278
279   // Will terminate when the last consumer completes.
280   base::MessageLoop::current()->Run();
281
282   CheckResponse(consumer, "HTTP/1.1 200 OK", kResponseBody);
283 }
284
285 TEST_F(QuicEndToEndTest, UberTest) {
286   // FLAGS_fake_packet_loss_percentage = 30;
287
288   const char kResponseBody[] = "some really big response body";
289   AddToCache("GET", request_.url.spec(),
290              "HTTP/1.1", "200", "OK",
291              kResponseBody);
292
293   std::vector<TestTransactionConsumer*> consumers;
294   size_t num_requests = 100;
295   for (size_t i = 0; i < num_requests; ++i) {
296       TestTransactionConsumer* consumer =
297           new TestTransactionConsumer(DEFAULT_PRIORITY,
298                                       transaction_factory_.get());
299       consumers.push_back(consumer);
300       consumer->Start(&request_, BoundNetLog());
301   }
302
303   // Will terminate when the last consumer completes.
304   base::MessageLoop::current()->Run();
305
306   for (size_t i = 0; i < num_requests; ++i) {
307     CheckResponse(*consumers[i], "HTTP/1.1 200 OK", kResponseBody);
308   }
309   STLDeleteElements(&consumers);
310 }
311
312 }  // namespace test
313 }  // namespace net