blob: 6673ec6f641eab482d0d9aa1c6639e84dd7deb89 [file] [log] [blame]
[email protected]a2006ece2010-04-23 16:44:021// Copyright (c) 2010 The Chromium Authors. All rights reserved.
license.botbf09a502008-08-24 00:55:552// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commit586acc5fe2008-07-26 22:42:524
[email protected]f7984fc62009-06-22 23:26:445#include "net/socket/ssl_client_socket.h"
6
initial.commit586acc5fe2008-07-26 22:42:527#include "net/base/address_list.h"
initial.commit586acc5fe2008-07-26 22:42:528#include "net/base/host_resolver.h"
[email protected]597cf6e2009-05-29 09:43:269#include "net/base/io_buffer.h"
[email protected]9e743cd2010-03-16 07:03:5310#include "net/base/net_log.h"
11#include "net/base/net_log_unittest.h"
[email protected]7b822b2b2008-08-05 00:15:4512#include "net/base/net_errors.h"
[email protected]aaead502008-10-15 00:20:1113#include "net/base/ssl_config_service.h"
initial.commit586acc5fe2008-07-26 22:42:5214#include "net/base/test_completion_callback.h"
[email protected]f7984fc62009-06-22 23:26:4415#include "net/socket/client_socket_factory.h"
[email protected]39afe642010-04-29 14:55:1816#include "net/socket/socket_test_util.h"
[email protected]f7984fc62009-06-22 23:26:4417#include "net/socket/tcp_client_socket.h"
[email protected]1b9565c2010-07-21 01:19:3118#include "net/test/test_server.h"
initial.commit586acc5fe2008-07-26 22:42:5219#include "testing/gtest/include/gtest/gtest.h"
[email protected]23887f04f2008-12-02 19:20:1520#include "testing/platform_test.h"
initial.commit586acc5fe2008-07-26 22:42:5221
22//-----------------------------------------------------------------------------
23
[email protected]aaead502008-10-15 00:20:1124const net::SSLConfig kDefaultSSLConfig;
[email protected]c5949a32008-10-08 17:28:2325
[email protected]b75523f2008-10-17 14:49:0726class SSLClientSocketTest : public PlatformTest {
[email protected]aaead502008-10-15 00:20:1127 public:
28 SSLClientSocketTest()
[email protected]962b98212010-07-17 03:37:5129 : resolver_(net::CreateSystemHostResolver(
30 net::HostResolver::kDefaultParallelism)),
[email protected]b59ff372009-07-15 22:04:3231 socket_factory_(net::ClientSocketFactory::GetDefaultFactory()) {
[email protected]73e0bba2009-02-19 22:57:0932 }
33
[email protected]aaead502008-10-15 00:20:1134 protected:
[email protected]b59ff372009-07-15 22:04:3235 scoped_refptr<net::HostResolver> resolver_;
[email protected]aaead502008-10-15 00:20:1136 net::ClientSocketFactory* socket_factory_;
initial.commit586acc5fe2008-07-26 22:42:5237};
38
initial.commit586acc5fe2008-07-26 22:42:5239//-----------------------------------------------------------------------------
40
[email protected]010e27e2009-08-27 17:49:4141TEST_F(SSLClientSocketTest, Connect) {
[email protected]95409e12010-08-17 20:07:1142 net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath());
43 ASSERT_TRUE(test_server.Start());
[email protected]73e0bba2009-02-19 22:57:0944
initial.commit586acc5fe2008-07-26 22:42:5245 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:1146 ASSERT_TRUE(test_server.GetAddressList(&addr));
47
initial.commit586acc5fe2008-07-26 22:42:5248 TestCompletionCallback callback;
[email protected]a2006ece2010-04-23 16:44:0249 net::CapturingNetLog log(net::CapturingNetLog::kUnbounded);
50 net::ClientSocket* transport = new net::TCPClientSocket(addr, &log);
[email protected]95409e12010-08-17 20:07:1151 int rv = transport->Connect(&callback);
[email protected]bacff652009-03-31 17:50:3352 if (rv == net::ERR_IO_PENDING)
53 rv = callback.WaitForResult();
54 EXPECT_EQ(net::OK, rv);
55
[email protected]aaead502008-10-15 00:20:1156 scoped_ptr<net::SSLClientSocket> sock(
[email protected]bacff652009-03-31 17:50:3357 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:1158 test_server.host_port_pair().host(), kDefaultSSLConfig));
initial.commit586acc5fe2008-07-26 22:42:5259
[email protected]aaead502008-10-15 00:20:1160 EXPECT_FALSE(sock->IsConnected());
initial.commit586acc5fe2008-07-26 22:42:5261
[email protected]a2006ece2010-04-23 16:44:0262 rv = sock->Connect(&callback);
[email protected]eb8605c2010-05-21 22:17:4763 EXPECT_TRUE(net::LogContainsBeginEvent(
[email protected]06650c52010-06-03 00:49:1764 log.entries(), 5, net::NetLog::TYPE_SSL_CONNECT));
[email protected]7b822b2b2008-08-05 00:15:4565 if (rv != net::OK) {
66 ASSERT_EQ(net::ERR_IO_PENDING, rv);
[email protected]73e0bba2009-02-19 22:57:0967 EXPECT_FALSE(sock->IsConnected());
[email protected]e9002a92010-01-29 07:10:4668 EXPECT_FALSE(net::LogContainsEndEvent(
[email protected]9e743cd2010-03-16 07:03:5369 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
initial.commit586acc5fe2008-07-26 22:42:5270
[email protected]7b822b2b2008-08-05 00:15:4571 rv = callback.WaitForResult();
72 EXPECT_EQ(net::OK, rv);
73 }
initial.commit586acc5fe2008-07-26 22:42:5274
[email protected]aaead502008-10-15 00:20:1175 EXPECT_TRUE(sock->IsConnected());
[email protected]e9002a92010-01-29 07:10:4676 EXPECT_TRUE(net::LogContainsEndEvent(
[email protected]9e743cd2010-03-16 07:03:5377 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
initial.commit586acc5fe2008-07-26 22:42:5278
[email protected]aaead502008-10-15 00:20:1179 sock->Disconnect();
80 EXPECT_FALSE(sock->IsConnected());
initial.commit586acc5fe2008-07-26 22:42:5281}
82
[email protected]010e27e2009-08-27 17:49:4183TEST_F(SSLClientSocketTest, ConnectExpired) {
[email protected]95409e12010-08-17 20:07:1184 net::TestServer test_server(net::TestServer::TYPE_HTTPS_EXPIRED_CERTIFICATE,
85 FilePath());
86 ASSERT_TRUE(test_server.Start());
[email protected]73e0bba2009-02-19 22:57:0987
initial.commit586acc5fe2008-07-26 22:42:5288 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:1189 ASSERT_TRUE(test_server.GetAddressList(&addr));
90
initial.commit586acc5fe2008-07-26 22:42:5291 TestCompletionCallback callback;
[email protected]a2006ece2010-04-23 16:44:0292 net::CapturingNetLog log(net::CapturingNetLog::kUnbounded);
93 net::ClientSocket* transport = new net::TCPClientSocket(addr, &log);
[email protected]95409e12010-08-17 20:07:1194 int rv = transport->Connect(&callback);
[email protected]bacff652009-03-31 17:50:3395 if (rv == net::ERR_IO_PENDING)
96 rv = callback.WaitForResult();
97 EXPECT_EQ(net::OK, rv);
98
[email protected]73e0bba2009-02-19 22:57:0999 scoped_ptr<net::SSLClientSocket> sock(
[email protected]bacff652009-03-31 17:50:33100 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11101 test_server.host_port_pair().host(), kDefaultSSLConfig));
[email protected]73e0bba2009-02-19 22:57:09102
103 EXPECT_FALSE(sock->IsConnected());
104
[email protected]a2006ece2010-04-23 16:44:02105 rv = sock->Connect(&callback);
[email protected]eb8605c2010-05-21 22:17:47106 EXPECT_TRUE(net::LogContainsBeginEvent(
[email protected]06650c52010-06-03 00:49:17107 log.entries(), 5, net::NetLog::TYPE_SSL_CONNECT));
[email protected]73e0bba2009-02-19 22:57:09108 if (rv != net::OK) {
109 ASSERT_EQ(net::ERR_IO_PENDING, rv);
110 EXPECT_FALSE(sock->IsConnected());
[email protected]e9002a92010-01-29 07:10:46111 EXPECT_FALSE(net::LogContainsEndEvent(
[email protected]9e743cd2010-03-16 07:03:53112 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
[email protected]73e0bba2009-02-19 22:57:09113
114 rv = callback.WaitForResult();
115 EXPECT_EQ(net::ERR_CERT_DATE_INVALID, rv);
116 }
117
[email protected]bacff652009-03-31 17:50:33118 // We cannot test sock->IsConnected(), as the NSS implementation disconnects
119 // the socket when it encounters an error, whereas other implementations
120 // leave it connected.
[email protected]5a05c47a2009-11-02 23:25:19121
[email protected]e9002a92010-01-29 07:10:46122 EXPECT_TRUE(net::LogContainsEndEvent(
[email protected]9e743cd2010-03-16 07:03:53123 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
[email protected]73e0bba2009-02-19 22:57:09124}
125
[email protected]010e27e2009-08-27 17:49:41126TEST_F(SSLClientSocketTest, ConnectMismatched) {
[email protected]95409e12010-08-17 20:07:11127 net::TestServer test_server(net::TestServer::TYPE_HTTPS_MISMATCHED_HOSTNAME,
128 FilePath());
129 ASSERT_TRUE(test_server.Start());
[email protected]73e0bba2009-02-19 22:57:09130
131 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:11132 ASSERT_TRUE(test_server.GetAddressList(&addr));
133
[email protected]73e0bba2009-02-19 22:57:09134 TestCompletionCallback callback;
[email protected]a2006ece2010-04-23 16:44:02135 net::CapturingNetLog log(net::CapturingNetLog::kUnbounded);
136 net::ClientSocket* transport = new net::TCPClientSocket(addr, &log);
[email protected]95409e12010-08-17 20:07:11137 int rv = transport->Connect(&callback);
[email protected]bacff652009-03-31 17:50:33138 if (rv == net::ERR_IO_PENDING)
139 rv = callback.WaitForResult();
140 EXPECT_EQ(net::OK, rv);
141
[email protected]73e0bba2009-02-19 22:57:09142 scoped_ptr<net::SSLClientSocket> sock(
[email protected]bacff652009-03-31 17:50:33143 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11144 test_server.host_port_pair().host(), kDefaultSSLConfig));
[email protected]73e0bba2009-02-19 22:57:09145
146 EXPECT_FALSE(sock->IsConnected());
147
[email protected]a2006ece2010-04-23 16:44:02148 rv = sock->Connect(&callback);
[email protected]4b32be92010-05-20 03:21:42149
[email protected]eb8605c2010-05-21 22:17:47150 EXPECT_TRUE(net::LogContainsBeginEvent(
[email protected]06650c52010-06-03 00:49:17151 log.entries(), 5, net::NetLog::TYPE_SSL_CONNECT));
[email protected]73e0bba2009-02-19 22:57:09152 if (rv != net::ERR_CERT_COMMON_NAME_INVALID) {
153 ASSERT_EQ(net::ERR_IO_PENDING, rv);
154 EXPECT_FALSE(sock->IsConnected());
[email protected]e9002a92010-01-29 07:10:46155 EXPECT_FALSE(net::LogContainsEndEvent(
[email protected]9e743cd2010-03-16 07:03:53156 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
[email protected]73e0bba2009-02-19 22:57:09157
158 rv = callback.WaitForResult();
159 EXPECT_EQ(net::ERR_CERT_COMMON_NAME_INVALID, rv);
160 }
161
[email protected]bacff652009-03-31 17:50:33162 // We cannot test sock->IsConnected(), as the NSS implementation disconnects
163 // the socket when it encounters an error, whereas other implementations
164 // leave it connected.
[email protected]5a05c47a2009-11-02 23:25:19165
[email protected]e9002a92010-01-29 07:10:46166 EXPECT_TRUE(net::LogContainsEndEvent(
[email protected]9e743cd2010-03-16 07:03:53167 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
[email protected]73e0bba2009-02-19 22:57:09168}
169
[email protected]8df162a2010-08-07 01:10:02170// TODO(davidben): Also test providing a certificate.
171TEST_F(SSLClientSocketTest, ConnectClientAuthNoCert) {
[email protected]95409e12010-08-17 20:07:11172 net::TestServer test_server(net::TestServer::TYPE_HTTPS_CLIENT_AUTH,
173 FilePath());
174 ASSERT_TRUE(test_server.Start());
[email protected]8df162a2010-08-07 01:10:02175
176 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:11177 ASSERT_TRUE(test_server.GetAddressList(&addr));
178
[email protected]8df162a2010-08-07 01:10:02179 TestCompletionCallback callback;
[email protected]8df162a2010-08-07 01:10:02180 net::CapturingNetLog log(net::CapturingNetLog::kUnbounded);
181 net::ClientSocket* transport = new net::TCPClientSocket(addr, &log);
[email protected]95409e12010-08-17 20:07:11182 int rv = transport->Connect(&callback);
[email protected]8df162a2010-08-07 01:10:02183 if (rv == net::ERR_IO_PENDING)
184 rv = callback.WaitForResult();
185 EXPECT_EQ(net::OK, rv);
186
187 scoped_ptr<net::SSLClientSocket> sock(
188 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11189 test_server.host_port_pair().host(), kDefaultSSLConfig));
[email protected]8df162a2010-08-07 01:10:02190
191 EXPECT_FALSE(sock->IsConnected());
192
193 rv = sock->Connect(&callback);
194 EXPECT_TRUE(net::LogContainsBeginEvent(
195 log.entries(), 5, net::NetLog::TYPE_SSL_CONNECT));
196 if (rv != net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED) {
197 ASSERT_EQ(net::ERR_IO_PENDING, rv);
198 EXPECT_FALSE(sock->IsConnected());
199 EXPECT_FALSE(net::LogContainsEndEvent(
200 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
201
202 rv = callback.WaitForResult();
203 EXPECT_EQ(net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED, rv);
204 }
205
206 // We cannot test sock->IsConnected(), as the NSS implementation disconnects
207 // the socket when it encounters an error, whereas other implementations
208 // leave it connected.
209
210 EXPECT_TRUE(net::LogContainsEndEvent(
211 log.entries(), -1, net::NetLog::TYPE_SSL_CONNECT));
212}
213
[email protected]b2197852009-02-19 23:27:33214// TODO(wtc): Add unit tests for IsConnectedAndIdle:
215// - Server closes an SSL connection (with a close_notify alert message).
216// - Server closes the underlying TCP connection directly.
217// - Server sends data unexpectedly.
218
[email protected]010e27e2009-08-27 17:49:41219TEST_F(SSLClientSocketTest, Read) {
[email protected]95409e12010-08-17 20:07:11220 net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath());
221 ASSERT_TRUE(test_server.Start());
[email protected]73e0bba2009-02-19 22:57:09222
223 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:11224 ASSERT_TRUE(test_server.GetAddressList(&addr));
225
[email protected]73e0bba2009-02-19 22:57:09226 TestCompletionCallback callback;
[email protected]a2006ece2010-04-23 16:44:02227 net::ClientSocket* transport = new net::TCPClientSocket(addr, NULL);
[email protected]95409e12010-08-17 20:07:11228 int rv = transport->Connect(&callback);
[email protected]bacff652009-03-31 17:50:33229 if (rv == net::ERR_IO_PENDING)
230 rv = callback.WaitForResult();
231 EXPECT_EQ(net::OK, rv);
232
[email protected]aaead502008-10-15 00:20:11233 scoped_ptr<net::SSLClientSocket> sock(
[email protected]bacff652009-03-31 17:50:33234 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11235 test_server.host_port_pair().host(),
[email protected]73e0bba2009-02-19 22:57:09236 kDefaultSSLConfig));
initial.commit586acc5fe2008-07-26 22:42:52237
[email protected]a2006ece2010-04-23 16:44:02238 rv = sock->Connect(&callback);
[email protected]7b822b2b2008-08-05 00:15:45239 if (rv != net::OK) {
[email protected]b75523f2008-10-17 14:49:07240 ASSERT_EQ(net::ERR_IO_PENDING, rv);
initial.commit586acc5fe2008-07-26 22:42:52241
[email protected]7b822b2b2008-08-05 00:15:45242 rv = callback.WaitForResult();
[email protected]b75523f2008-10-17 14:49:07243 EXPECT_EQ(net::OK, rv);
[email protected]7b822b2b2008-08-05 00:15:45244 }
[email protected]b43c97c2008-10-22 19:50:58245 EXPECT_TRUE(sock->IsConnected());
initial.commit586acc5fe2008-07-26 22:42:52246
247 const char request_text[] = "GET / HTTP/1.0\r\n\r\n";
[email protected]ffeb0882009-04-30 21:51:25248 scoped_refptr<net::IOBuffer> request_buffer =
249 new net::IOBuffer(arraysize(request_text) - 1);
250 memcpy(request_buffer->data(), request_text, arraysize(request_text) - 1);
251
252 rv = sock->Write(request_buffer, arraysize(request_text) - 1, &callback);
initial.commit586acc5fe2008-07-26 22:42:52253 EXPECT_TRUE(rv >= 0 || rv == net::ERR_IO_PENDING);
254
[email protected]914286d62009-12-10 23:06:44255 if (rv == net::ERR_IO_PENDING)
initial.commit586acc5fe2008-07-26 22:42:52256 rv = callback.WaitForResult();
[email protected]914286d62009-12-10 23:06:44257 EXPECT_EQ(static_cast<int>(arraysize(request_text) - 1), rv);
initial.commit586acc5fe2008-07-26 22:42:52258
[email protected]ffeb0882009-04-30 21:51:25259 scoped_refptr<net::IOBuffer> buf = new net::IOBuffer(4096);
initial.commit586acc5fe2008-07-26 22:42:52260 for (;;) {
[email protected]ffeb0882009-04-30 21:51:25261 rv = sock->Read(buf, 4096, &callback);
initial.commit586acc5fe2008-07-26 22:42:52262 EXPECT_TRUE(rv >= 0 || rv == net::ERR_IO_PENDING);
263
264 if (rv == net::ERR_IO_PENDING)
265 rv = callback.WaitForResult();
266
[email protected]7b822b2b2008-08-05 00:15:45267 EXPECT_GE(rv, 0);
268 if (rv <= 0)
initial.commit586acc5fe2008-07-26 22:42:52269 break;
270 }
271}
272
[email protected]914286d62009-12-10 23:06:44273// Test the full duplex mode, with Read and Write pending at the same time.
274// This test also serves as a regression test for http://crbug.com/29815.
275TEST_F(SSLClientSocketTest, Read_FullDuplex) {
[email protected]95409e12010-08-17 20:07:11276 net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath());
277 ASSERT_TRUE(test_server.Start());
[email protected]914286d62009-12-10 23:06:44278
279 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:11280 ASSERT_TRUE(test_server.GetAddressList(&addr));
281
[email protected]914286d62009-12-10 23:06:44282 TestCompletionCallback callback; // Used for everything except Write.
283 TestCompletionCallback callback2; // Used for Write only.
284
[email protected]a2006ece2010-04-23 16:44:02285 net::ClientSocket* transport = new net::TCPClientSocket(addr, NULL);
[email protected]95409e12010-08-17 20:07:11286 int rv = transport->Connect(&callback);
[email protected]914286d62009-12-10 23:06:44287 if (rv == net::ERR_IO_PENDING)
288 rv = callback.WaitForResult();
289 EXPECT_EQ(net::OK, rv);
290
291 scoped_ptr<net::SSLClientSocket> sock(
292 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11293 test_server.host_port_pair().host(),
[email protected]914286d62009-12-10 23:06:44294 kDefaultSSLConfig));
295
[email protected]a2006ece2010-04-23 16:44:02296 rv = sock->Connect(&callback);
[email protected]914286d62009-12-10 23:06:44297 if (rv != net::OK) {
298 ASSERT_EQ(net::ERR_IO_PENDING, rv);
299
300 rv = callback.WaitForResult();
301 EXPECT_EQ(net::OK, rv);
302 }
303 EXPECT_TRUE(sock->IsConnected());
304
305 // Issue a "hanging" Read first.
306 scoped_refptr<net::IOBuffer> buf = new net::IOBuffer(4096);
307 rv = sock->Read(buf, 4096, &callback);
308 // We haven't written the request, so there should be no response yet.
309 ASSERT_EQ(net::ERR_IO_PENDING, rv);
310
311 // Write the request.
312 // The request is padded with a User-Agent header to a size that causes the
313 // memio circular buffer (4k bytes) in SSLClientSocketNSS to wrap around.
314 // This tests the fix for http://crbug.com/29815.
315 std::string request_text = "GET / HTTP/1.1\r\nUser-Agent: long browser name ";
316 for (int i = 0; i < 3800; ++i)
317 request_text.push_back('*');
318 request_text.append("\r\n\r\n");
319 scoped_refptr<net::IOBuffer> request_buffer =
320 new net::StringIOBuffer(request_text);
321
322 rv = sock->Write(request_buffer, request_text.size(), &callback2);
323 EXPECT_TRUE(rv >= 0 || rv == net::ERR_IO_PENDING);
324
325 if (rv == net::ERR_IO_PENDING)
326 rv = callback2.WaitForResult();
327 EXPECT_EQ(static_cast<int>(request_text.size()), rv);
328
329 // Now get the Read result.
330 rv = callback.WaitForResult();
331 EXPECT_GT(rv, 0);
332}
333
[email protected]010e27e2009-08-27 17:49:41334TEST_F(SSLClientSocketTest, Read_SmallChunks) {
[email protected]95409e12010-08-17 20:07:11335 net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath());
336 ASSERT_TRUE(test_server.Start());
[email protected]73e0bba2009-02-19 22:57:09337
initial.commit586acc5fe2008-07-26 22:42:52338 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:11339 ASSERT_TRUE(test_server.GetAddressList(&addr));
340
initial.commit586acc5fe2008-07-26 22:42:52341 TestCompletionCallback callback;
[email protected]a2006ece2010-04-23 16:44:02342 net::ClientSocket* transport = new net::TCPClientSocket(addr, NULL);
[email protected]95409e12010-08-17 20:07:11343 int rv = transport->Connect(&callback);
[email protected]bacff652009-03-31 17:50:33344 if (rv == net::ERR_IO_PENDING)
345 rv = callback.WaitForResult();
346 EXPECT_EQ(net::OK, rv);
347
[email protected]aaead502008-10-15 00:20:11348 scoped_ptr<net::SSLClientSocket> sock(
[email protected]bacff652009-03-31 17:50:33349 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11350 test_server.host_port_pair().host(), kDefaultSSLConfig));
initial.commit586acc5fe2008-07-26 22:42:52351
[email protected]a2006ece2010-04-23 16:44:02352 rv = sock->Connect(&callback);
[email protected]7b822b2b2008-08-05 00:15:45353 if (rv != net::OK) {
[email protected]b75523f2008-10-17 14:49:07354 ASSERT_EQ(net::ERR_IO_PENDING, rv);
initial.commit586acc5fe2008-07-26 22:42:52355
[email protected]7b822b2b2008-08-05 00:15:45356 rv = callback.WaitForResult();
[email protected]b75523f2008-10-17 14:49:07357 EXPECT_EQ(net::OK, rv);
[email protected]7b822b2b2008-08-05 00:15:45358 }
initial.commit586acc5fe2008-07-26 22:42:52359
360 const char request_text[] = "GET / HTTP/1.0\r\n\r\n";
[email protected]ffeb0882009-04-30 21:51:25361 scoped_refptr<net::IOBuffer> request_buffer =
362 new net::IOBuffer(arraysize(request_text) - 1);
363 memcpy(request_buffer->data(), request_text, arraysize(request_text) - 1);
364
365 rv = sock->Write(request_buffer, arraysize(request_text) - 1, &callback);
initial.commit586acc5fe2008-07-26 22:42:52366 EXPECT_TRUE(rv >= 0 || rv == net::ERR_IO_PENDING);
367
[email protected]914286d62009-12-10 23:06:44368 if (rv == net::ERR_IO_PENDING)
initial.commit586acc5fe2008-07-26 22:42:52369 rv = callback.WaitForResult();
[email protected]914286d62009-12-10 23:06:44370 EXPECT_EQ(static_cast<int>(arraysize(request_text) - 1), rv);
initial.commit586acc5fe2008-07-26 22:42:52371
[email protected]ffeb0882009-04-30 21:51:25372 scoped_refptr<net::IOBuffer> buf = new net::IOBuffer(1);
initial.commit586acc5fe2008-07-26 22:42:52373 for (;;) {
[email protected]ffeb0882009-04-30 21:51:25374 rv = sock->Read(buf, 1, &callback);
initial.commit586acc5fe2008-07-26 22:42:52375 EXPECT_TRUE(rv >= 0 || rv == net::ERR_IO_PENDING);
376
377 if (rv == net::ERR_IO_PENDING)
378 rv = callback.WaitForResult();
379
[email protected]7b822b2b2008-08-05 00:15:45380 EXPECT_GE(rv, 0);
381 if (rv <= 0)
initial.commit586acc5fe2008-07-26 22:42:52382 break;
383 }
384}
385
[email protected]010e27e2009-08-27 17:49:41386TEST_F(SSLClientSocketTest, Read_Interrupted) {
[email protected]95409e12010-08-17 20:07:11387 net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath());
388 ASSERT_TRUE(test_server.Start());
[email protected]73e0bba2009-02-19 22:57:09389
initial.commit586acc5fe2008-07-26 22:42:52390 net::AddressList addr;
[email protected]95409e12010-08-17 20:07:11391 ASSERT_TRUE(test_server.GetAddressList(&addr));
392
initial.commit586acc5fe2008-07-26 22:42:52393 TestCompletionCallback callback;
[email protected]a2006ece2010-04-23 16:44:02394 net::ClientSocket* transport = new net::TCPClientSocket(addr, NULL);
[email protected]95409e12010-08-17 20:07:11395 int rv = transport->Connect(&callback);
[email protected]bacff652009-03-31 17:50:33396 if (rv == net::ERR_IO_PENDING)
397 rv = callback.WaitForResult();
398 EXPECT_EQ(net::OK, rv);
399
[email protected]aaead502008-10-15 00:20:11400 scoped_ptr<net::SSLClientSocket> sock(
[email protected]bacff652009-03-31 17:50:33401 socket_factory_->CreateSSLClientSocket(transport,
[email protected]95409e12010-08-17 20:07:11402 test_server.host_port_pair().host(), kDefaultSSLConfig));
initial.commit586acc5fe2008-07-26 22:42:52403
[email protected]a2006ece2010-04-23 16:44:02404 rv = sock->Connect(&callback);
[email protected]7b822b2b2008-08-05 00:15:45405 if (rv != net::OK) {
[email protected]b75523f2008-10-17 14:49:07406 ASSERT_EQ(net::ERR_IO_PENDING, rv);
initial.commit586acc5fe2008-07-26 22:42:52407
[email protected]7b822b2b2008-08-05 00:15:45408 rv = callback.WaitForResult();
[email protected]b75523f2008-10-17 14:49:07409 EXPECT_EQ(net::OK, rv);
[email protected]7b822b2b2008-08-05 00:15:45410 }
initial.commit586acc5fe2008-07-26 22:42:52411
412 const char request_text[] = "GET / HTTP/1.0\r\n\r\n";
[email protected]ffeb0882009-04-30 21:51:25413 scoped_refptr<net::IOBuffer> request_buffer =
414 new net::IOBuffer(arraysize(request_text) - 1);
415 memcpy(request_buffer->data(), request_text, arraysize(request_text) - 1);
416
417 rv = sock->Write(request_buffer, arraysize(request_text) - 1, &callback);
initial.commit586acc5fe2008-07-26 22:42:52418 EXPECT_TRUE(rv >= 0 || rv == net::ERR_IO_PENDING);
419
[email protected]914286d62009-12-10 23:06:44420 if (rv == net::ERR_IO_PENDING)
initial.commit586acc5fe2008-07-26 22:42:52421 rv = callback.WaitForResult();
[email protected]914286d62009-12-10 23:06:44422 EXPECT_EQ(static_cast<int>(arraysize(request_text) - 1), rv);
initial.commit586acc5fe2008-07-26 22:42:52423
424 // Do a partial read and then exit. This test should not crash!
[email protected]ffeb0882009-04-30 21:51:25425 scoped_refptr<net::IOBuffer> buf = new net::IOBuffer(512);
426 rv = sock->Read(buf, 512, &callback);
[email protected]914286d62009-12-10 23:06:44427 EXPECT_TRUE(rv > 0 || rv == net::ERR_IO_PENDING);
initial.commit586acc5fe2008-07-26 22:42:52428
429 if (rv == net::ERR_IO_PENDING)
430 rv = callback.WaitForResult();
431
[email protected]914286d62009-12-10 23:06:44432 EXPECT_GT(rv, 0);
initial.commit586acc5fe2008-07-26 22:42:52433}
[email protected]39afe642010-04-29 14:55:18434
[email protected]39afe642010-04-29 14:55:18435// Regression test for http://crbug.com/42538
436TEST_F(SSLClientSocketTest, PrematureApplicationData) {
[email protected]95409e12010-08-17 20:07:11437 net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath());
438 ASSERT_TRUE(test_server.Start());
439
[email protected]39afe642010-04-29 14:55:18440 net::AddressList addr;
441 TestCompletionCallback callback;
442
443 static const unsigned char application_data[] = {
444 0x17, 0x03, 0x01, 0x00, 0x4a, 0x02, 0x00, 0x00, 0x46, 0x03, 0x01, 0x4b,
445 0xc2, 0xf8, 0xb2, 0xc1, 0x56, 0x42, 0xb9, 0x57, 0x7f, 0xde, 0x87, 0x46,
446 0xf7, 0xa3, 0x52, 0x42, 0x21, 0xf0, 0x13, 0x1c, 0x9c, 0x83, 0x88, 0xd6,
447 0x93, 0x0c, 0xf6, 0x36, 0x30, 0x05, 0x7e, 0x20, 0xb5, 0xb5, 0x73, 0x36,
448 0x53, 0x83, 0x0a, 0xfc, 0x17, 0x63, 0xbf, 0xa0, 0xe4, 0x42, 0x90, 0x0d,
449 0x2f, 0x18, 0x6d, 0x20, 0xd8, 0x36, 0x3f, 0xfc, 0xe6, 0x01, 0xfa, 0x0f,
450 0xa5, 0x75, 0x7f, 0x09, 0x00, 0x04, 0x00, 0x16, 0x03, 0x01, 0x11, 0x57,
451 0x0b, 0x00, 0x11, 0x53, 0x00, 0x11, 0x50, 0x00, 0x06, 0x22, 0x30, 0x82,
452 0x06, 0x1e, 0x30, 0x82, 0x05, 0x06, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02,
453 0x0a
454 };
455
456 // All reads and writes complete synchronously (async=false).
457 net::MockRead data_reads[] = {
458 net::MockRead(false, reinterpret_cast<const char*>(application_data),
459 arraysize(application_data)),
460 net::MockRead(false, net::OK),
461 };
462
463 net::StaticSocketDataProvider data(data_reads, arraysize(data_reads),
464 NULL, 0);
465
466 net::ClientSocket* transport =
467 new net::MockTCPClientSocket(addr, NULL, &data);
468 int rv = transport->Connect(&callback);
469 if (rv == net::ERR_IO_PENDING)
470 rv = callback.WaitForResult();
471 EXPECT_EQ(net::OK, rv);
472
473 scoped_ptr<net::SSLClientSocket> sock(
474 socket_factory_->CreateSSLClientSocket(
[email protected]95409e12010-08-17 20:07:11475 transport, test_server.host_port_pair().host(), kDefaultSSLConfig));
[email protected]39afe642010-04-29 14:55:18476
477 rv = sock->Connect(&callback);
478 EXPECT_EQ(net::ERR_SSL_PROTOCOL_ERROR, rv);
479}