blob: 7874273b29ac0fe5ce7f2b9256ce8d4aa4516db0 [file] [log] [blame]
[email protected]dd3fd0e2012-11-04 05:14:401// 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_client_session.h"
6
7#include <vector>
8
[email protected]4d283b32013-10-17 12:57:279#include "base/rand_util.h"
[email protected]0d10b592013-02-14 16:09:2610#include "net/base/capturing_net_log.h"
[email protected]8ee611b2012-11-20 01:48:1211#include "net/base/test_completion_callback.h"
[email protected]0bbeb6972013-05-23 04:10:2112#include "net/quic/crypto/aes_128_gcm_12_encrypter.h"
[email protected]dd3fd0e2012-11-04 05:14:4013#include "net/quic/crypto/crypto_protocol.h"
[email protected]4df69842013-02-27 06:32:1614#include "net/quic/crypto/quic_decrypter.h"
15#include "net/quic/crypto/quic_encrypter.h"
[email protected]cbd731e2013-10-24 00:20:3916#include "net/quic/quic_default_packet_writer.h"
[email protected]ed3fc15d2013-03-08 18:37:4417#include "net/quic/test_tools/crypto_test_utils.h"
[email protected]899951652013-05-16 12:52:3918#include "net/quic/test_tools/quic_client_session_peer.h"
[email protected]dd3fd0e2012-11-04 05:14:4019#include "net/quic/test_tools/quic_test_utils.h"
[email protected]4d283b32013-10-17 12:57:2720#include "net/socket/socket_test_util.h"
[email protected]18ccfdb2013-08-15 00:13:4421#include "net/udp/datagram_client_socket.h"
[email protected]dd3fd0e2012-11-04 05:14:4022
23using testing::_;
24
25namespace net {
26namespace test {
27namespace {
28
[email protected]41d6b172013-01-29 16:10:5729const char kServerHostname[] = "www.example.com";
30
[email protected]cbd731e2013-10-24 00:20:3931class TestPacketWriter : public QuicDefaultPacketWriter {
32 public:
33 TestPacketWriter() {
34 }
35
36 // QuicPacketWriter
37 virtual WriteResult WritePacket(
38 const char* buffer, size_t buf_len,
39 const IPAddressNumber& self_address,
40 const IPEndPoint& peer_address,
41 QuicBlockedWriterInterface* blocked_writer) OVERRIDE {
42 QuicFramer framer(QuicVersionMax(), QuicTime::Zero(), true);
43 FramerVisitorCapturingFrames visitor;
44 framer.set_visitor(&visitor);
45 QuicEncryptedPacket packet(buffer, buf_len);
46 EXPECT_TRUE(framer.ProcessPacket(packet));
47 header_ = *visitor.header();
48 return WriteResult(WRITE_STATUS_OK, packet.length());
49 }
50
51 virtual bool IsWriteBlockedDataBuffered() const OVERRIDE {
52 // Chrome sockets' Write() methods buffer the data until the Write is
53 // permitted.
54 return true;
55 }
56
57 // Returns the header from the last packet written.
58 const QuicPacketHeader& header() { return header_; }
59
60 private:
61 QuicPacketHeader header_;
62};
63
[email protected]dd3fd0e2012-11-04 05:14:4064class QuicClientSessionTest : public ::testing::Test {
65 protected:
66 QuicClientSessionTest()
67 : guid_(1),
[email protected]cbd731e2013-10-24 00:20:3968 writer_(new TestPacketWriter()),
[email protected]14e8106c2013-03-14 16:25:3369 connection_(new PacketSavingConnection(guid_, IPEndPoint(), false)),
[email protected]cbd731e2013-10-24 00:20:3970 session_(connection_, GetSocket().Pass(), writer_.Pass(), NULL, NULL,
71 kServerHostname, DefaultQuicConfig(), &crypto_config_,
[email protected]18ccfdb2013-08-15 00:13:4472 &net_log_) {
[email protected]47a71542013-05-17 07:58:5473 session_.config()->SetDefaults();
[email protected]ef95114d2013-04-17 17:57:0174 crypto_config_.SetDefaults();
[email protected]dd3fd0e2012-11-04 05:14:4075 }
76
[email protected]4d283b32013-10-17 12:57:2777 virtual void TearDown() OVERRIDE {
78 session_.CloseSessionOnError(ERR_ABORTED);
79 }
80
81 scoped_ptr<DatagramClientSocket> GetSocket() {
82 socket_factory_.AddSocketDataProvider(&socket_data_);
83 return socket_factory_.CreateDatagramClientSocket(
84 DatagramSocket::DEFAULT_BIND, base::Bind(&base::RandInt),
85 &net_log_, NetLog::Source());
86 }
87
[email protected]ed3fc15d2013-03-08 18:37:4488 void CompleteCryptoHandshake() {
89 ASSERT_EQ(ERR_IO_PENDING,
[email protected]11c05872013-08-20 02:04:1290 session_.CryptoConnect(false, callback_.callback()));
[email protected]e8ff26842013-03-22 21:02:0591 CryptoTestUtils::HandshakeWithFakeServer(
92 connection_, session_.GetCryptoStream());
[email protected]ed3fc15d2013-03-08 18:37:4493 ASSERT_EQ(OK, callback_.WaitForResult());
[email protected]ed3fc15d2013-03-08 18:37:4494 }
95
[email protected]dd3fd0e2012-11-04 05:14:4096 QuicGuid guid_;
[email protected]cbd731e2013-10-24 00:20:3997 scoped_ptr<QuicDefaultPacketWriter> writer_;
[email protected]dd3fd0e2012-11-04 05:14:4098 PacketSavingConnection* connection_;
[email protected]ed3fc15d2013-03-08 18:37:4499 CapturingNetLog net_log_;
[email protected]4d283b32013-10-17 12:57:27100 MockClientSocketFactory socket_factory_;
101 StaticSocketDataProvider socket_data_;
[email protected]dd3fd0e2012-11-04 05:14:40102 QuicClientSession session_;
[email protected]ed3fc15d2013-03-08 18:37:44103 MockClock clock_;
104 MockRandom random_;
[email protected]dd3fd0e2012-11-04 05:14:40105 QuicConnectionVisitorInterface* visitor_;
[email protected]8ee611b2012-11-20 01:48:12106 TestCompletionCallback callback_;
[email protected]ef95114d2013-04-17 17:57:01107 QuicCryptoClientConfig crypto_config_;
[email protected]dd3fd0e2012-11-04 05:14:40108};
109
[email protected]ed3fc15d2013-03-08 18:37:44110TEST_F(QuicClientSessionTest, CryptoConnect) {
[email protected]0bbeb6972013-05-23 04:10:21111 if (!Aes128Gcm12Encrypter::IsSupported()) {
[email protected]74bda142013-03-31 02:49:11112 LOG(INFO) << "AES GCM not supported. Test skipped.";
113 return;
114 }
115
[email protected]ed3fc15d2013-03-08 18:37:44116 CompleteCryptoHandshake();
[email protected]8ee611b2012-11-20 01:48:12117}
118
[email protected]67efa082013-07-21 19:51:19119TEST_F(QuicClientSessionTest, MaxNumStreams) {
[email protected]0bbeb6972013-05-23 04:10:21120 if (!Aes128Gcm12Encrypter::IsSupported()) {
[email protected]74bda142013-03-31 02:49:11121 LOG(INFO) << "AES GCM not supported. Test skipped.";
122 return;
123 }
124
[email protected]ed3fc15d2013-03-08 18:37:44125 CompleteCryptoHandshake();
[email protected]dd3fd0e2012-11-04 05:14:40126
127 std::vector<QuicReliableClientStream*> streams;
128 for (size_t i = 0; i < kDefaultMaxStreamsPerConnection; i++) {
129 QuicReliableClientStream* stream = session_.CreateOutgoingReliableStream();
[email protected]dd3fd0e2012-11-04 05:14:40130 EXPECT_TRUE(stream);
[email protected]f702d572012-12-04 15:56:20131 streams.push_back(stream);
[email protected]dd3fd0e2012-11-04 05:14:40132 }
133 EXPECT_FALSE(session_.CreateOutgoingReliableStream());
134
135 // Close a stream and ensure I can now open a new one.
136 session_.CloseStream(streams[0]->id());
[email protected]f702d572012-12-04 15:56:20137 EXPECT_TRUE(session_.CreateOutgoingReliableStream());
[email protected]dd3fd0e2012-11-04 05:14:40138}
139
[email protected]0b2294d32013-08-02 00:46:36140TEST_F(QuicClientSessionTest, MaxNumStreamsViaRequest) {
141 if (!Aes128Gcm12Encrypter::IsSupported()) {
142 LOG(INFO) << "AES GCM not supported. Test skipped.";
143 return;
144 }
145
146 CompleteCryptoHandshake();
147
148 std::vector<QuicReliableClientStream*> streams;
149 for (size_t i = 0; i < kDefaultMaxStreamsPerConnection; i++) {
150 QuicReliableClientStream* stream = session_.CreateOutgoingReliableStream();
151 EXPECT_TRUE(stream);
152 streams.push_back(stream);
153 }
154
155 QuicReliableClientStream* stream;
156 QuicClientSession::StreamRequest stream_request;
157 TestCompletionCallback callback;
158 ASSERT_EQ(ERR_IO_PENDING,
159 stream_request.StartRequest(session_.GetWeakPtr(), &stream,
160 callback.callback()));
161
162 // Close a stream and ensure I can now open a new one.
163 session_.CloseStream(streams[0]->id());
164 ASSERT_TRUE(callback.have_result());
165 EXPECT_EQ(OK, callback.WaitForResult());
166 EXPECT_TRUE(stream != NULL);
167}
168
[email protected]9db443912013-02-25 05:27:03169TEST_F(QuicClientSessionTest, GoAwayReceived) {
[email protected]0bbeb6972013-05-23 04:10:21170 if (!Aes128Gcm12Encrypter::IsSupported()) {
[email protected]8ba81212013-05-03 13:11:48171 LOG(INFO) << "AES GCM not supported. Test skipped.";
172 return;
173 }
174
175 CompleteCryptoHandshake();
[email protected]9db443912013-02-25 05:27:03176
177 // After receiving a GoAway, I should no longer be able to create outgoing
178 // streams.
179 session_.OnGoAway(QuicGoAwayFrame(QUIC_PEER_GOING_AWAY, 1u, "Going away."));
180 EXPECT_EQ(NULL, session_.CreateOutgoingReliableStream());
181}
182
[email protected]dd3fd0e2012-11-04 05:14:40183} // namespace
184} // namespace test
185} // namespace net