blob: f0b611a3eaceca99f4851deee0183b5aa60dcbac [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"
8#include "base/string_util.h"
9#include "net/base/mock_host_resolver.h"
10#include "net/http/http_response_headers.h"
11#include "net/http/http_response_info.h"
12#include "net/http/http_util.h"
13#include "net/quic/quic_http_stream.h"
14#include "net/quic/test_tools/mock_clock.h"
[email protected]9558c5d32012-12-22 00:08:1415#include "net/quic/test_tools/mock_random.h"
[email protected]e13201d82012-12-12 05:00:3216#include "net/quic/test_tools/quic_test_utils.h"
17#include "net/socket/socket_test_util.h"
18#include "testing/gtest/include/gtest/gtest.h"
19
20namespace net {
[email protected]e13201d82012-12-12 05:00:3221namespace test {
22
23class QuicStreamFactoryTest : public ::testing::Test {
24 protected:
25 QuicStreamFactoryTest()
26 : factory_(&host_resolver_, &socket_factory_,
[email protected]9558c5d32012-12-22 00:08:1427 &random_generator_,
[email protected]f1e97e92012-12-16 04:53:2528 new MockClock()),
[email protected]e13201d82012-12-12 05:00:3229 host_port_proxy_pair_(HostPortPair("www.google.com", 443),
30 ProxyServer::Direct()) {
31 }
32
33 scoped_ptr<QuicEncryptedPacket> ConstructChlo() {
34 scoped_ptr<QuicPacket> chlo(ConstructHandshakePacket(0xDEADBEEF, kCHLO));
35 QuicFramer framer(QuicDecrypter::Create(kNULL),
36 QuicEncrypter::Create(kNULL));
37 return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(*chlo));
38 }
39
40 scoped_ptr<QuicEncryptedPacket> ConstructShlo() {
41 scoped_ptr<QuicPacket> shlo(ConstructHandshakePacket(0xDEADBEEF, kSHLO));
42 QuicFramer framer(QuicDecrypter::Create(kNULL),
43 QuicEncrypter::Create(kNULL));
44 return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(*shlo));
45 }
46
47 scoped_ptr<QuicEncryptedPacket> ConstructRstPacket(
48 QuicPacketSequenceNumber num,
49 QuicStreamId stream_id) {
50 QuicPacketHeader header;
51 header.guid = 0xDEADBEEF;
52 header.packet_sequence_number = num;
53 header.flags = PACKET_FLAGS_NONE;
54 header.fec_group = 0;
55
56 QuicRstStreamFrame rst(stream_id, 0, QUIC_NO_ERROR);
57 return scoped_ptr<QuicEncryptedPacket>(
58 ConstructPacket(header, QuicFrame(&rst)));
59 }
60
61 scoped_ptr<QuicEncryptedPacket> ConstructAckPacket(
62 QuicPacketSequenceNumber largest_received,
63 QuicPacketSequenceNumber least_unacked) {
64 QuicPacketHeader header;
65 header.guid = 0xDEADBEEF;
66 header.packet_sequence_number = 2;
67 header.flags = PACKET_FLAGS_NONE;
68 header.fec_group = 0;
69
[email protected]7884ecad2012-12-14 22:55:1570 QuicAckFrame ack(largest_received, least_unacked);
[email protected]e13201d82012-12-12 05:00:3271
72 return scoped_ptr<QuicEncryptedPacket>(
73 ConstructPacket(header, QuicFrame(&ack)));
74 }
75
[email protected]26f3f8e2012-12-13 21:07:1976 // Returns a newly created packet to send congestion feedback data.
77 scoped_ptr<QuicEncryptedPacket> ConstructFeedbackPacket(
78 QuicPacketSequenceNumber sequence_number) {
79 QuicPacketHeader header;
80 header.guid = 0xDEADBEEF;
81 header.packet_sequence_number = sequence_number;
82 header.flags = PACKET_FLAGS_NONE;
83 header.fec_group = 0;
84
85 QuicCongestionFeedbackFrame frame;
86 frame.type = kTCP;
87 frame.tcp.accumulated_number_of_lost_packets = 0;
88 frame.tcp.receive_window = 16000;
89
90 return scoped_ptr<QuicEncryptedPacket>(
91 ConstructPacket(header, QuicFrame(&frame)));
92 }
93
[email protected]e13201d82012-12-12 05:00:3294 scoped_ptr<QuicEncryptedPacket> ConstructPacket(
95 const QuicPacketHeader& header,
96 const QuicFrame& frame) {
97 QuicFramer framer(QuicDecrypter::Create(kNULL),
98 QuicEncrypter::Create(kNULL));
99 QuicFrames frames;
100 frames.push_back(frame);
[email protected]610a7e942012-12-18 00:21:39101 scoped_ptr<QuicPacket> packet(
102 framer.ConstructFrameDataPacket(header, frames));
103 return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(*packet));
[email protected]e13201d82012-12-12 05:00:32104 }
105
106 MockHostResolver host_resolver_;
107 MockClientSocketFactory socket_factory_;
[email protected]9558c5d32012-12-22 00:08:14108 MockRandom random_generator_;
[email protected]e13201d82012-12-12 05:00:32109 QuicStreamFactory factory_;
110 HostPortProxyPair host_port_proxy_pair_;
111 BoundNetLog net_log_;
112 TestCompletionCallback callback_;
[email protected]e13201d82012-12-12 05:00:32113};
114
115TEST_F(QuicStreamFactoryTest, CreateIfSessionExists) {
116 EXPECT_EQ(NULL, factory_.CreateIfSessionExists(host_port_proxy_pair_,
117 net_log_).get());
118}
119
120TEST_F(QuicStreamFactoryTest, Create) {
121 scoped_ptr<QuicEncryptedPacket> chlo(ConstructChlo());
122 scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 1));
[email protected]26f3f8e2012-12-13 21:07:19123 scoped_ptr<QuicEncryptedPacket> feedback(ConstructFeedbackPacket(3));
124 scoped_ptr<QuicEncryptedPacket> rst3(ConstructRstPacket(4, 3));
125 scoped_ptr<QuicEncryptedPacket> rst5(ConstructRstPacket(5, 5));
126 scoped_ptr<QuicEncryptedPacket> rst7(ConstructRstPacket(6, 7));
[email protected]e13201d82012-12-12 05:00:32127 MockWrite writes[] = {
128 MockWrite(SYNCHRONOUS, chlo->data(), chlo->length()),
129 MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
[email protected]26f3f8e2012-12-13 21:07:19130 MockWrite(SYNCHRONOUS, feedback->data(), feedback->length()),
[email protected]e13201d82012-12-12 05:00:32131 MockWrite(SYNCHRONOUS, rst3->data(), rst3->length()),
132 MockWrite(SYNCHRONOUS, rst5->data(), rst5->length()),
133 MockWrite(SYNCHRONOUS, rst7->data(), rst7->length()),
134 };
135 scoped_ptr<QuicEncryptedPacket> shlo(ConstructShlo());
136 scoped_ptr<QuicEncryptedPacket> ack2(ConstructAckPacket(2, 0));
137 MockRead reads[] = {
138 MockRead(SYNCHRONOUS, shlo->data(), shlo->length()),
139 MockRead(SYNCHRONOUS, ack2->data(), ack2->length()),
140 MockRead(ASYNC, OK), // EOF
141 };
142 StaticSocketDataProvider socket_data(reads, arraysize(reads),
143 writes, arraysize(writes));
144 socket_factory_.AddSocketDataProvider(&socket_data);
145
146 QuicStreamRequest request(&factory_);
147 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, net_log_,
148 callback_.callback()));
149
150 EXPECT_EQ(OK, callback_.WaitForResult());
151 scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
152
153 // Will reset stream 3.
154 stream = factory_.CreateIfSessionExists(host_port_proxy_pair_, net_log_);
155 EXPECT_TRUE(stream.get());
156
157 QuicStreamRequest request2(&factory_);
158 EXPECT_EQ(OK, request2.Request(host_port_proxy_pair_, net_log_,
159 callback_.callback()));
160 stream = request2.ReleaseStream(); // Will reset stream 5.
161 stream.reset(); // Will reset stream 7.
162
163 EXPECT_TRUE(socket_data.at_read_eof());
164 EXPECT_TRUE(socket_data.at_write_eof());
165}
166
167TEST_F(QuicStreamFactoryTest, CreateError) {
168 StaticSocketDataProvider socket_data(NULL, 0, NULL, 0);
169 socket_factory_.AddSocketDataProvider(&socket_data);
170
171 host_resolver_.rules()->AddSimulatedFailure("www.google.com");
172
173 QuicStreamRequest request(&factory_);
174 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, net_log_,
175 callback_.callback()));
176
177 EXPECT_EQ(ERR_NAME_NOT_RESOLVED, callback_.WaitForResult());
178
179 EXPECT_TRUE(socket_data.at_read_eof());
180 EXPECT_TRUE(socket_data.at_write_eof());
181}
182
183TEST_F(QuicStreamFactoryTest, CancelCreate) {
184 scoped_ptr<QuicEncryptedPacket> chlo(ConstructChlo());
185 scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 1));
[email protected]26f3f8e2012-12-13 21:07:19186 scoped_ptr<QuicEncryptedPacket> feedback(ConstructFeedbackPacket(3));
187 scoped_ptr<QuicEncryptedPacket> rst3(ConstructRstPacket(4, 3));
[email protected]e13201d82012-12-12 05:00:32188
189 MockWrite writes[] = {
190 MockWrite(SYNCHRONOUS, chlo->data(), chlo->length()),
191 MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
[email protected]26f3f8e2012-12-13 21:07:19192 MockWrite(SYNCHRONOUS, feedback->data(), feedback->length()),
[email protected]e13201d82012-12-12 05:00:32193 MockWrite(SYNCHRONOUS, rst3->data(), rst3->length()),
194 };
195 scoped_ptr<QuicEncryptedPacket> shlo(ConstructShlo());
196 scoped_ptr<QuicEncryptedPacket> ack2(ConstructAckPacket(2, 0));
197 MockRead reads[] = {
198 MockRead(SYNCHRONOUS, shlo->data(), shlo->length()),
199 MockRead(SYNCHRONOUS, ack2->data(), ack2->length()),
200 MockRead(ASYNC, OK), // EOF
201 };
202 StaticSocketDataProvider socket_data(reads, arraysize(reads),
203 writes, arraysize(writes));
204 socket_factory_.AddSocketDataProvider(&socket_data);
205 {
206 QuicStreamRequest request(&factory_);
207 EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, net_log_,
208 callback_.callback()));
209 }
210
211 base::RunLoop run_loop;
212 run_loop.RunUntilIdle();
213
214 scoped_ptr<QuicHttpStream> stream(
215 factory_.CreateIfSessionExists(host_port_proxy_pair_, net_log_));
216 EXPECT_TRUE(stream.get());
217 stream.reset();
218
219 EXPECT_TRUE(socket_data.at_read_eof());
220 EXPECT_TRUE(socket_data.at_write_eof());
221}
222
223} // namespace test
[email protected]e13201d82012-12-12 05:00:32224} // namespace net