blob: a55f273e235089808a2c357e8d0882abf897912c [file] [log] [blame]
[email protected]e13201d82012-12-12 05:00:321// 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
3// found in the LICENSE file.
4
5#include "net/quic/quic_stream_factory.h"
6
[email protected]e13201d82012-12-12 05:00:327#include "base/run_loop.h"
[email protected]fc9be5802013-06-11 10:56:518#include "base/strings/string_util.h"
[email protected]6d1b4ed2013-07-10 03:57:549#include "net/cert/cert_verifier.h"
[email protected]f2cb3cf2013-03-21 01:40:5310#include "net/dns/mock_host_resolver.h"
[email protected]e13201d82012-12-12 05:00:3211#include "net/http/http_response_headers.h"
12#include "net/http/http_response_info.h"
13#include "net/http/http_util.h"
[email protected]c49ff182013-09-28 08:33:2614#include "net/quic/crypto/crypto_handshake.h"
[email protected]4df69842013-02-27 06:32:1615#include "net/quic/crypto/quic_decrypter.h"
16#include "net/quic/crypto/quic_encrypter.h"
[email protected]e13201d82012-12-12 05:00:3217#include "net/quic/quic_http_stream.h"
18#include "net/quic/test_tools/mock_clock.h"
[email protected]e8ff26842013-03-22 21:02:0519#include "net/quic/test_tools/mock_crypto_client_stream_factory.h"
[email protected]9558c5d32012-12-22 00:08:1420#include "net/quic/test_tools/mock_random.h"
[email protected]e13201d82012-12-12 05:00:3221#include "net/quic/test_tools/quic_test_utils.h"
22#include "net/socket/socket_test_util.h"
23#include "testing/gtest/include/gtest/gtest.h"
24
[email protected]6e12d702013-11-13 00:17:1725using base::StringPiece;
26using std::string;
27using std::vector;
28
[email protected]e13201d82012-12-12 05:00:3229namespace net {
[email protected]e13201d82012-12-12 05:00:3230namespace test {
31
[email protected]c49ff182013-09-28 08:33:2632class QuicStreamFactoryPeer {
33 public:
34 static QuicCryptoClientConfig* GetOrCreateCryptoConfig(
35 QuicStreamFactory* factory,
36 const HostPortProxyPair& host_port_proxy_pair) {
37 return factory->GetOrCreateCryptoConfig(host_port_proxy_pair);
38 }
[email protected]4d283b32013-10-17 12:57:2739
40 static bool HasActiveSession(QuicStreamFactory* factory,
41 const HostPortProxyPair& host_port_proxy_pair) {
42 return factory->HasActiveSession(host_port_proxy_pair);
43 }
44
45 static QuicClientSession* GetActiveSession(
46 QuicStreamFactory* factory,
47 const HostPortProxyPair& host_port_proxy_pair) {
48 DCHECK(factory->HasActiveSession(host_port_proxy_pair));
49 return factory->active_sessions_[host_port_proxy_pair];
50 }
51
52 static bool IsLiveSession(QuicStreamFactory* factory,
53 QuicClientSession* session) {
54 for (QuicStreamFactory::SessionSet::iterator it =
55 factory->all_sessions_.begin();
56 it != factory->all_sessions_.end(); ++it) {
57 if (*it == session)
58 return true;
59 }
60 return false;
61 }
[email protected]c49ff182013-09-28 08:33:2662};
63
[email protected]e13201d82012-12-12 05:00:3264class QuicStreamFactoryTest : public ::testing::Test {
65 protected:
66 QuicStreamFactoryTest()
[email protected]872edd9e2013-01-16 08:51:1567 : clock_(new MockClock()),
68 factory_(&host_resolver_, &socket_factory_,
[email protected]77c6c162013-08-17 02:57:4569 base::WeakPtr<HttpServerProperties>(),
[email protected]e8ff26842013-03-22 21:02:0570 &crypto_client_stream_factory_,
[email protected]9d9e7932013-02-25 18:31:0571 &random_generator_, clock_),
[email protected]e13201d82012-12-12 05:00:3272 host_port_proxy_pair_(HostPortPair("www.google.com", 443),
[email protected]6d1b4ed2013-07-10 03:57:5473 ProxyServer::Direct()),
74 is_https_(false),
75 cert_verifier_(CertVerifier::CreateDefault()) {
[email protected]11c05872013-08-20 02:04:1276 factory_.set_require_confirmation(false);
[email protected]e13201d82012-12-12 05:00:3277 }
78
[email protected]e13201d82012-12-12 05:00:3279 scoped_ptr<QuicEncryptedPacket> ConstructRstPacket(
80 QuicPacketSequenceNumber num,
81 QuicStreamId stream_id) {
82 QuicPacketHeader header;
[email protected]c995c572013-01-18 05:43:2083 header.public_header.guid = 0xDEADBEEF;
[email protected]9db443912013-02-25 05:27:0384 header.public_header.reset_flag = false;
[email protected]e8ff26842013-03-22 21:02:0585 header.public_header.version_flag = true;
[email protected]e13201d82012-12-12 05:00:3286 header.packet_sequence_number = num;
[email protected]06ff5152013-08-29 01:03:0587 header.public_header.sequence_number_length = PACKET_1BYTE_SEQUENCE_NUMBER;
[email protected]9db443912013-02-25 05:27:0388 header.entropy_flag = false;
[email protected]9db443912013-02-25 05:27:0389 header.fec_flag = false;
[email protected]e13201d82012-12-12 05:00:3290 header.fec_group = 0;
91
[email protected]6548b662013-10-23 01:38:5392 QuicRstStreamFrame rst(stream_id, QUIC_STREAM_CANCELLED);
[email protected]e13201d82012-12-12 05:00:3293 return scoped_ptr<QuicEncryptedPacket>(
94 ConstructPacket(header, QuicFrame(&rst)));
95 }
96
97 scoped_ptr<QuicEncryptedPacket> ConstructAckPacket(
98 QuicPacketSequenceNumber largest_received,
99 QuicPacketSequenceNumber least_unacked) {
100 QuicPacketHeader header;
[email protected]c995c572013-01-18 05:43:20101 header.public_header.guid = 0xDEADBEEF;
[email protected]9db443912013-02-25 05:27:03102 header.public_header.reset_flag = false;
103 header.public_header.version_flag = false;
[email protected]e13201d82012-12-12 05:00:32104 header.packet_sequence_number = 2;
[email protected]9db443912013-02-25 05:27:03105 header.entropy_flag = false;
[email protected]9db443912013-02-25 05:27:03106 header.fec_flag = false;
[email protected]e13201d82012-12-12 05:00:32107 header.fec_group = 0;
108
[email protected]14e8106c2013-03-14 16:25:33109 QuicAckFrame ack(largest_received, QuicTime::Zero(), least_unacked);
[email protected]dda3e9b2012-12-22 21:49:25110 QuicCongestionFeedbackFrame feedback;
111 feedback.type = kTCP;
112 feedback.tcp.accumulated_number_of_lost_packets = 0;
113 feedback.tcp.receive_window = 16000;
114
[email protected]b007e632013-10-28 08:39:25115 QuicFramer framer(QuicSupportedVersions(), QuicTime::Zero(), false);
[email protected]dda3e9b2012-12-22 21:49:25116 QuicFrames frames;
117 frames.push_back(QuicFrame(&ack));
118 frames.push_back(QuicFrame(&feedback));
119 scoped_ptr<QuicPacket> packet(
[email protected]3e60db82013-08-05 19:43:06120 framer.BuildUnsizedDataPacket(header, frames).packet);
[email protected]8ba81212013-05-03 13:11:48121 return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(
122 ENCRYPTION_NONE, header.packet_sequence_number, *packet));
[email protected]e13201d82012-12-12 05:00:32123 }
124
[email protected]26f3f8e2012-12-13 21:07:19125 // Returns a newly created packet to send congestion feedback data.
126 scoped_ptr<QuicEncryptedPacket> ConstructFeedbackPacket(
127 QuicPacketSequenceNumber sequence_number) {
128 QuicPacketHeader header;
[email protected]c995c572013-01-18 05:43:20129 header.public_header.guid = 0xDEADBEEF;
[email protected]9db443912013-02-25 05:27:03130 header.public_header.reset_flag = false;
131 header.public_header.version_flag = false;
[email protected]26f3f8e2012-12-13 21:07:19132 header.packet_sequence_number = sequence_number;
[email protected]9db443912013-02-25 05:27:03133 header.entropy_flag = false;
[email protected]9db443912013-02-25 05:27:03134 header.fec_flag = false;
[email protected]26f3f8e2012-12-13 21:07:19135 header.fec_group = 0;
136
137 QuicCongestionFeedbackFrame frame;
138 frame.type = kTCP;
139 frame.tcp.accumulated_number_of_lost_packets = 0;
140 frame.tcp.receive_window = 16000;
141
142 return scoped_ptr<QuicEncryptedPacket>(
143 ConstructPacket(header, QuicFrame(&frame)));
144 }
145
[email protected]e13201d82012-12-12 05:00:32146 scoped_ptr<QuicEncryptedPacket> ConstructPacket(
147 const QuicPacketHeader& header,
148 const QuicFrame& frame) {
[email protected]b007e632013-10-28 08:39:25149 QuicFramer framer(QuicSupportedVersions(), QuicTime::Zero(), false);
[email protected]e13201d82012-12-12 05:00:32150 QuicFrames frames;
151 frames.push_back(frame);
[email protected]610a7e942012-12-18 00:21:39152 scoped_ptr<QuicPacket> packet(
[email protected]3e60db82013-08-05 19:43:06153 framer.BuildUnsizedDataPacket(header, frames).packet);
[email protected]8ba81212013-05-03 13:11:48154 return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(
155 ENCRYPTION_NONE, header.packet_sequence_number, *packet));
[email protected]e13201d82012-12-12 05:00:32156 }
157
158 MockHostResolver host_resolver_;
[email protected]0edce6a2013-05-08 18:02:40159 DeterministicMockClientSocketFactory socket_factory_;
[email protected]e8ff26842013-03-22 21:02:05160 MockCryptoClientStreamFactory crypto_client_stream_factory_;
[email protected]9558c5d32012-12-22 00:08:14161 MockRandom random_generator_;
[email protected]872edd9e2013-01-16 08:51:15162 MockClock* clock_; // Owned by factory_.
[email protected]e13201d82012-12-12 05:00:32163 QuicStreamFactory factory_;
164 HostPortProxyPair host_port_proxy_pair_;
[email protected]6d1b4ed2013-07-10 03:57:54165 bool is_https_;
[email protected]ce542d52013-07-11 01:08:39166 scoped_ptr<CertVerifier> cert_verifier_;
[email protected]e13201d82012-12-12 05:00:32167 BoundNetLog net_log_;
168 TestCompletionCallback callback_;
[email protected]e13201d82012-12-12 05:00:32169};
170
171TEST_F(QuicStreamFactoryTest, CreateIfSessionExists) {
172 EXPECT_EQ(NULL, factory_.CreateIfSessionExists(host_port_proxy_pair_,
173 net_log_).get());
174}
175
176TEST_F(QuicStreamFactoryTest, Create) {
[email protected]69dfd1b2013-06-04 22:20:12177 MockRead reads[] = {
[email protected]25c31dc2013-06-05 17:56:04178 MockRead(ASYNC, OK, 0) // EOF
[email protected]69dfd1b2013-06-04 22:20:12179 };
[email protected]25c31dc2013-06-05 17:56:04180 DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
[email protected]e13201d82012-12-12 05:00:32181 socket_factory_.AddSocketDataProvider(&socket_data);
[email protected]25c31dc2013-06-05 17:56:04182 socket_data.StopAfter(1);
[email protected]e13201d82012-12-12 05:00:32183
184 QuicStreamRequest request(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54185 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39186 cert_verifier_.get(), net_log_,
[email protected]e13201d82012-12-12 05:00:32187 callback_.callback()));
188
189 EXPECT_EQ(OK, callback_.WaitForResult());
190 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
[email protected]0edce6a2013-05-08 18:02:40191 EXPECT_TRUE(stream.get());
[email protected]e13201d82012-12-12 05:00:32192
193 // Will reset stream 3.
194 stream = factory_.CreateIfSessionExists(host_port_proxy_pair_, net_log_);
195 EXPECT_TRUE(stream.get());
196
[email protected]6d1b4ed2013-07-10 03:57:54197 // TODO(rtenneti): We should probably have a tests that HTTP and HTTPS result
198 // in streams on different sessions.
[email protected]e13201d82012-12-12 05:00:32199 QuicStreamRequest request2(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54200 EXPECT_EQ(OK, request2.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39201 cert_verifier_.get(), net_log_,
[email protected]e13201d82012-12-12 05:00:32202 callback_.callback()));
203 stream = request2.ReleaseStream(); // Will reset stream 5.
204 stream.reset(); // Will reset stream 7.
205
206 EXPECT_TRUE(socket_data.at_read_eof());
207 EXPECT_TRUE(socket_data.at_write_eof());
208}
209
[email protected]4d283b32013-10-17 12:57:27210TEST_F(QuicStreamFactoryTest, Goaway) {
211 MockRead reads[] = {
212 MockRead(ASYNC, OK, 0) // EOF
213 };
214 DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
215 socket_data.StopAfter(1);
216 socket_factory_.AddSocketDataProvider(&socket_data);
217 DeterministicSocketData socket_data2(reads, arraysize(reads), NULL, 0);
218 socket_data2.StopAfter(1);
219 socket_factory_.AddSocketDataProvider(&socket_data2);
220
221 QuicStreamRequest request(&factory_);
222 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
223 cert_verifier_.get(), net_log_,
224 callback_.callback()));
225
226 EXPECT_EQ(OK, callback_.WaitForResult());
227 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
228 EXPECT_TRUE(stream.get());
229
230 // Mark the session as going away. Ensure that while it is still alive
231 // that it is no longer active.
232 QuicClientSession* session = QuicStreamFactoryPeer::GetActiveSession(
233 &factory_, host_port_proxy_pair_);
234 factory_.OnSessionGoingAway(session);
235 EXPECT_EQ(true, QuicStreamFactoryPeer::IsLiveSession(&factory_, session));
236 EXPECT_FALSE(QuicStreamFactoryPeer::HasActiveSession(&factory_,
237 host_port_proxy_pair_));
238 EXPECT_EQ(NULL, factory_.CreateIfSessionExists(host_port_proxy_pair_,
239 net_log_).get());
240
241 // Create a new request for the same destination and verify that a
242 // new session is created.
243 QuicStreamRequest request2(&factory_);
244 EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
245 cert_verifier_.get(), net_log_,
246 callback_.callback()));
247 EXPECT_EQ(OK, callback_.WaitForResult());
248 scoped_ptr<QuicHttpStream> stream2 = request2.ReleaseStream();
249 EXPECT_TRUE(stream2.get());
250
251 EXPECT_TRUE(QuicStreamFactoryPeer::HasActiveSession(&factory_,
252 host_port_proxy_pair_));
253 EXPECT_NE(session,
254 QuicStreamFactoryPeer::GetActiveSession(
255 &factory_, host_port_proxy_pair_));
256 EXPECT_EQ(true, QuicStreamFactoryPeer::IsLiveSession(&factory_, session));
257
258 stream2.reset();
259 stream.reset();
260
261 EXPECT_TRUE(socket_data.at_read_eof());
262 EXPECT_TRUE(socket_data.at_write_eof());
263}
264
[email protected]0b2294d32013-08-02 00:46:36265TEST_F(QuicStreamFactoryTest, MaxOpenStream) {
266 MockRead reads[] = {
267 MockRead(ASYNC, OK, 0) // EOF
268 };
[email protected]06ff5152013-08-29 01:03:05269 scoped_ptr<QuicEncryptedPacket> rst(ConstructRstPacket(1, 3));
270 MockWrite writes[] = {
271 MockWrite(ASYNC, rst->data(), rst->length(), 1),
272 };
273 DeterministicSocketData socket_data(reads, arraysize(reads),
274 writes, arraysize(writes));
[email protected]0b2294d32013-08-02 00:46:36275 socket_factory_.AddSocketDataProvider(&socket_data);
276 socket_data.StopAfter(1);
277
278 HttpRequestInfo request_info;
279 std::vector<QuicHttpStream*> streams;
280 // The MockCryptoClientStream sets max_open_streams to be
281 // 2 * kDefaultMaxStreamsPerConnection.
282 for (size_t i = 0; i < 2 * kDefaultMaxStreamsPerConnection; i++) {
283 QuicStreamRequest request(&factory_);
284 int rv = request.Request(host_port_proxy_pair_, is_https_,
285 cert_verifier_.get(), net_log_,
286 callback_.callback());
287 if (i == 0) {
288 EXPECT_EQ(ERR_IO_PENDING, rv);
289 EXPECT_EQ(OK, callback_.WaitForResult());
290 } else {
291 EXPECT_EQ(OK, rv);
292 }
293 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
294 EXPECT_TRUE(stream);
295 EXPECT_EQ(OK, stream->InitializeStream(
296 &request_info, DEFAULT_PRIORITY, net_log_, CompletionCallback()));
297 streams.push_back(stream.release());
298 }
299
300 QuicStreamRequest request(&factory_);
301 EXPECT_EQ(OK, request.Request(host_port_proxy_pair_, is_https_,
302 cert_verifier_.get(), net_log_,
303 CompletionCallback()));
304 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
305 EXPECT_TRUE(stream);
306 EXPECT_EQ(ERR_IO_PENDING, stream->InitializeStream(
307 &request_info, DEFAULT_PRIORITY, net_log_, callback_.callback()));
308
309 // Close the first stream.
310 streams.front()->Close(false);
311
312 ASSERT_TRUE(callback_.have_result());
313
314 EXPECT_EQ(OK, callback_.WaitForResult());
315
316 EXPECT_TRUE(socket_data.at_read_eof());
317 EXPECT_TRUE(socket_data.at_write_eof());
318 STLDeleteElements(&streams);
319}
320
[email protected]e13201d82012-12-12 05:00:32321TEST_F(QuicStreamFactoryTest, CreateError) {
[email protected]0edce6a2013-05-08 18:02:40322 DeterministicSocketData socket_data(NULL, 0, NULL, 0);
[email protected]e13201d82012-12-12 05:00:32323 socket_factory_.AddSocketDataProvider(&socket_data);
324
325 host_resolver_.rules()->AddSimulatedFailure("www.google.com");
326
327 QuicStreamRequest request(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54328 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39329 cert_verifier_.get(), net_log_,
[email protected]e13201d82012-12-12 05:00:32330 callback_.callback()));
331
332 EXPECT_EQ(ERR_NAME_NOT_RESOLVED, callback_.WaitForResult());
333
334 EXPECT_TRUE(socket_data.at_read_eof());
335 EXPECT_TRUE(socket_data.at_write_eof());
336}
337
338TEST_F(QuicStreamFactoryTest, CancelCreate) {
[email protected]69dfd1b2013-06-04 22:20:12339 MockRead reads[] = {
[email protected]25c31dc2013-06-05 17:56:04340 MockRead(ASYNC, OK, 0) // EOF
[email protected]69dfd1b2013-06-04 22:20:12341 };
[email protected]25c31dc2013-06-05 17:56:04342 DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
[email protected]e13201d82012-12-12 05:00:32343 socket_factory_.AddSocketDataProvider(&socket_data);
344 {
345 QuicStreamRequest request(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54346 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39347 cert_verifier_.get(), net_log_,
[email protected]e13201d82012-12-12 05:00:32348 callback_.callback()));
349 }
350
[email protected]25c31dc2013-06-05 17:56:04351 socket_data.StopAfter(1);
[email protected]e13201d82012-12-12 05:00:32352 base::RunLoop run_loop;
353 run_loop.RunUntilIdle();
354
355 scoped_ptr<QuicHttpStream> stream(
356 factory_.CreateIfSessionExists(host_port_proxy_pair_, net_log_));
357 EXPECT_TRUE(stream.get());
358 stream.reset();
359
360 EXPECT_TRUE(socket_data.at_read_eof());
361 EXPECT_TRUE(socket_data.at_write_eof());
362}
363
[email protected]56dfb902013-01-03 23:17:55364TEST_F(QuicStreamFactoryTest, CloseAllSessions) {
[email protected]56dfb902013-01-03 23:17:55365 MockRead reads[] = {
[email protected]0edce6a2013-05-08 18:02:40366 MockRead(ASYNC, 0, 0) // EOF
[email protected]56dfb902013-01-03 23:17:55367 };
[email protected]25c31dc2013-06-05 17:56:04368 DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
[email protected]56dfb902013-01-03 23:17:55369 socket_factory_.AddSocketDataProvider(&socket_data);
[email protected]0edce6a2013-05-08 18:02:40370 socket_data.StopAfter(1);
[email protected]56dfb902013-01-03 23:17:55371
[email protected]69dfd1b2013-06-04 22:20:12372 MockRead reads2[] = {
[email protected]25c31dc2013-06-05 17:56:04373 MockRead(ASYNC, 0, 0) // EOF
[email protected]69dfd1b2013-06-04 22:20:12374 };
[email protected]25c31dc2013-06-05 17:56:04375 DeterministicSocketData socket_data2(reads2, arraysize(reads2), NULL, 0);
[email protected]56dfb902013-01-03 23:17:55376 socket_factory_.AddSocketDataProvider(&socket_data2);
[email protected]0edce6a2013-05-08 18:02:40377 socket_data2.StopAfter(1);
[email protected]56dfb902013-01-03 23:17:55378
379 QuicStreamRequest request(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54380 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39381 cert_verifier_.get(), net_log_,
[email protected]56dfb902013-01-03 23:17:55382 callback_.callback()));
383
384 EXPECT_EQ(OK, callback_.WaitForResult());
385 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
[email protected]0b2294d32013-08-02 00:46:36386 HttpRequestInfo request_info;
387 EXPECT_EQ(OK, stream->InitializeStream(&request_info,
388 DEFAULT_PRIORITY,
389 net_log_, CompletionCallback()));
[email protected]56dfb902013-01-03 23:17:55390
391 // Close the session and verify that stream saw the error.
392 factory_.CloseAllSessions(ERR_INTERNET_DISCONNECTED);
393 EXPECT_EQ(ERR_INTERNET_DISCONNECTED,
394 stream->ReadResponseHeaders(callback_.callback()));
395
396 // Now attempting to request a stream to the same origin should create
397 // a new session.
398
399 QuicStreamRequest request2(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54400 EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39401 cert_verifier_.get(), net_log_,
[email protected]56dfb902013-01-03 23:17:55402 callback_.callback()));
403
404 EXPECT_EQ(OK, callback_.WaitForResult());
405 stream = request2.ReleaseStream();
406 stream.reset(); // Will reset stream 3.
407
408 EXPECT_TRUE(socket_data.at_read_eof());
409 EXPECT_TRUE(socket_data.at_write_eof());
410 EXPECT_TRUE(socket_data2.at_read_eof());
411 EXPECT_TRUE(socket_data2.at_write_eof());
412}
413
[email protected]f698a012013-05-06 20:18:59414TEST_F(QuicStreamFactoryTest, OnIPAddressChanged) {
[email protected]f698a012013-05-06 20:18:59415 MockRead reads[] = {
[email protected]0edce6a2013-05-08 18:02:40416 MockRead(ASYNC, 0, 0) // EOF
[email protected]f698a012013-05-06 20:18:59417 };
[email protected]25c31dc2013-06-05 17:56:04418 DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
[email protected]f698a012013-05-06 20:18:59419 socket_factory_.AddSocketDataProvider(&socket_data);
[email protected]0edce6a2013-05-08 18:02:40420 socket_data.StopAfter(1);
[email protected]f698a012013-05-06 20:18:59421
[email protected]69dfd1b2013-06-04 22:20:12422 MockRead reads2[] = {
[email protected]25c31dc2013-06-05 17:56:04423 MockRead(ASYNC, 0, 0) // EOF
[email protected]69dfd1b2013-06-04 22:20:12424 };
[email protected]25c31dc2013-06-05 17:56:04425 DeterministicSocketData socket_data2(reads2, arraysize(reads2), NULL, 0);
[email protected]f698a012013-05-06 20:18:59426 socket_factory_.AddSocketDataProvider(&socket_data2);
[email protected]0edce6a2013-05-08 18:02:40427 socket_data2.StopAfter(1);
[email protected]f698a012013-05-06 20:18:59428
429 QuicStreamRequest request(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54430 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39431 cert_verifier_.get(), net_log_,
[email protected]f698a012013-05-06 20:18:59432 callback_.callback()));
433
434 EXPECT_EQ(OK, callback_.WaitForResult());
435 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
[email protected]0b2294d32013-08-02 00:46:36436 HttpRequestInfo request_info;
437 EXPECT_EQ(OK, stream->InitializeStream(&request_info,
438 DEFAULT_PRIORITY,
439 net_log_, CompletionCallback()));
[email protected]f698a012013-05-06 20:18:59440
441 // Change the IP address and verify that stream saw the error.
442 factory_.OnIPAddressChanged();
443 EXPECT_EQ(ERR_NETWORK_CHANGED,
444 stream->ReadResponseHeaders(callback_.callback()));
[email protected]11c05872013-08-20 02:04:12445 EXPECT_TRUE(factory_.require_confirmation());
[email protected]f698a012013-05-06 20:18:59446
447 // Now attempting to request a stream to the same origin should create
448 // a new session.
449
450 QuicStreamRequest request2(&factory_);
[email protected]6d1b4ed2013-07-10 03:57:54451 EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
[email protected]ce542d52013-07-11 01:08:39452 cert_verifier_.get(), net_log_,
[email protected]f698a012013-05-06 20:18:59453 callback_.callback()));
454
455 EXPECT_EQ(OK, callback_.WaitForResult());
456 stream = request2.ReleaseStream();
457 stream.reset(); // Will reset stream 3.
458
459 EXPECT_TRUE(socket_data.at_read_eof());
460 EXPECT_TRUE(socket_data.at_write_eof());
461 EXPECT_TRUE(socket_data2.at_read_eof());
462 EXPECT_TRUE(socket_data2.at_write_eof());
463}
464
[email protected]b70fdb792013-10-25 19:04:14465TEST_F(QuicStreamFactoryTest, SharedCryptoConfig) {
[email protected]6e12d702013-11-13 00:17:17466 vector<string> cannoncial_suffixes;
467 cannoncial_suffixes.push_back(string(".c.youtube.com"));
468 cannoncial_suffixes.push_back(string(".googlevideo.com"));
[email protected]c49ff182013-09-28 08:33:26469
[email protected]6e12d702013-11-13 00:17:17470 for (unsigned i = 0; i < cannoncial_suffixes.size(); ++i) {
471 string r1_host_name("r1");
472 string r2_host_name("r2");
473 r1_host_name.append(cannoncial_suffixes[i]);
474 r2_host_name.append(cannoncial_suffixes[i]);
[email protected]b70fdb792013-10-25 19:04:14475
[email protected]6e12d702013-11-13 00:17:17476 HostPortProxyPair host_port_proxy_pair1(HostPortPair(r1_host_name, 80),
477 ProxyServer::Direct());
[email protected]c49ff182013-09-28 08:33:26478
[email protected]6e12d702013-11-13 00:17:17479 QuicCryptoClientConfig* crypto_config1 =
480 QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
481 host_port_proxy_pair1);
482 DCHECK(crypto_config1);
483 QuicCryptoClientConfig::CachedState* cached1 =
484 crypto_config1->LookupOrCreate(host_port_proxy_pair1.first.host());
485 EXPECT_FALSE(cached1->proof_valid());
486 EXPECT_TRUE(cached1->source_address_token().empty());
487
488 // Mutate the cached1 to have different data.
489 // TODO(rtenneti): mutate other members of CachedState.
490 cached1->set_source_address_token(r1_host_name);
491 cached1->SetProofValid();
492
493 HostPortProxyPair host_port_proxy_pair2(HostPortPair(r2_host_name, 80),
494 ProxyServer::Direct());
495 QuicCryptoClientConfig* crypto_config2 =
496 QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
497 host_port_proxy_pair2);
498 DCHECK(crypto_config2);
499 QuicCryptoClientConfig::CachedState* cached2 =
500 crypto_config2->LookupOrCreate(host_port_proxy_pair2.first.host());
501 EXPECT_EQ(cached1->source_address_token(), cached2->source_address_token());
502 EXPECT_TRUE(cached2->proof_valid());
503 }
[email protected]b70fdb792013-10-25 19:04:14504}
505
506TEST_F(QuicStreamFactoryTest, CryptoConfigWhenProofIsInvalid) {
[email protected]6e12d702013-11-13 00:17:17507 vector<string> cannoncial_suffixes;
508 cannoncial_suffixes.push_back(string(".c.youtube.com"));
509 cannoncial_suffixes.push_back(string(".googlevideo.com"));
[email protected]b70fdb792013-10-25 19:04:14510
[email protected]6e12d702013-11-13 00:17:17511 for (unsigned i = 0; i < cannoncial_suffixes.size(); ++i) {
512 string r3_host_name("r3");
513 string r4_host_name("r4");
514 r3_host_name.append(cannoncial_suffixes[i]);
515 r4_host_name.append(cannoncial_suffixes[i]);
[email protected]b70fdb792013-10-25 19:04:14516
[email protected]6e12d702013-11-13 00:17:17517 HostPortProxyPair host_port_proxy_pair1(HostPortPair(r3_host_name, 80),
518 ProxyServer::Direct());
[email protected]b70fdb792013-10-25 19:04:14519
[email protected]6e12d702013-11-13 00:17:17520 QuicCryptoClientConfig* crypto_config1 =
521 QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
522 host_port_proxy_pair1);
523 DCHECK(crypto_config1);
524 QuicCryptoClientConfig::CachedState* cached1 =
525 crypto_config1->LookupOrCreate(host_port_proxy_pair1.first.host());
526 EXPECT_FALSE(cached1->proof_valid());
527 EXPECT_TRUE(cached1->source_address_token().empty());
528
529 // Mutate the cached1 to have different data.
530 // TODO(rtenneti): mutate other members of CachedState.
531 cached1->set_source_address_token(r3_host_name);
532 cached1->SetProofInvalid();
533
534 HostPortProxyPair host_port_proxy_pair2(HostPortPair(r4_host_name, 80),
535 ProxyServer::Direct());
536 QuicCryptoClientConfig* crypto_config2 =
537 QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
538 host_port_proxy_pair2);
539 DCHECK(crypto_config2);
540 QuicCryptoClientConfig::CachedState* cached2 =
541 crypto_config2->LookupOrCreate(host_port_proxy_pair2.first.host());
542 EXPECT_NE(cached1->source_address_token(), cached2->source_address_token());
543 EXPECT_TRUE(cached2->source_address_token().empty());
544 EXPECT_FALSE(cached2->proof_valid());
545 }
[email protected]c49ff182013-09-28 08:33:26546}
547
[email protected]e13201d82012-12-12 05:00:32548} // namespace test
[email protected]e13201d82012-12-12 05:00:32549} // namespace net