Home | History | Annotate | Download | only in http
      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 "net/http/http_network_transaction.h"
      6 
      7 #include <math.h>  // ceil
      8 #include <stdarg.h>
      9 #include <string>
     10 #include <vector>
     11 
     12 #include "base/basictypes.h"
     13 #include "base/compiler_specific.h"
     14 #include "base/file_util.h"
     15 #include "base/files/file_path.h"
     16 #include "base/json/json_writer.h"
     17 #include "base/memory/scoped_ptr.h"
     18 #include "base/memory/weak_ptr.h"
     19 #include "base/run_loop.h"
     20 #include "base/strings/string_util.h"
     21 #include "base/strings/utf_string_conversions.h"
     22 #include "base/test/test_file_util.h"
     23 #include "net/base/auth.h"
     24 #include "net/base/capturing_net_log.h"
     25 #include "net/base/completion_callback.h"
     26 #include "net/base/load_timing_info.h"
     27 #include "net/base/load_timing_info_test_util.h"
     28 #include "net/base/net_log.h"
     29 #include "net/base/net_log_unittest.h"
     30 #include "net/base/request_priority.h"
     31 #include "net/base/test_completion_callback.h"
     32 #include "net/base/test_data_directory.h"
     33 #include "net/base/upload_bytes_element_reader.h"
     34 #include "net/base/upload_data_stream.h"
     35 #include "net/base/upload_file_element_reader.h"
     36 #include "net/cert/mock_cert_verifier.h"
     37 #include "net/dns/host_cache.h"
     38 #include "net/dns/mock_host_resolver.h"
     39 #include "net/http/http_auth_challenge_tokenizer.h"
     40 #include "net/http/http_auth_handler_digest.h"
     41 #include "net/http/http_auth_handler_mock.h"
     42 #include "net/http/http_auth_handler_ntlm.h"
     43 #include "net/http/http_basic_stream.h"
     44 #include "net/http/http_network_session.h"
     45 #include "net/http/http_network_session_peer.h"
     46 #include "net/http/http_server_properties_impl.h"
     47 #include "net/http/http_stream.h"
     48 #include "net/http/http_stream_factory.h"
     49 #include "net/http/http_transaction_test_util.h"
     50 #include "net/proxy/proxy_config_service_fixed.h"
     51 #include "net/proxy/proxy_info.h"
     52 #include "net/proxy/proxy_resolver.h"
     53 #include "net/proxy/proxy_service.h"
     54 #include "net/socket/client_socket_factory.h"
     55 #include "net/socket/client_socket_pool_manager.h"
     56 #include "net/socket/mock_client_socket_pool_manager.h"
     57 #include "net/socket/next_proto.h"
     58 #include "net/socket/socket_test_util.h"
     59 #include "net/socket/ssl_client_socket.h"
     60 #include "net/spdy/spdy_framer.h"
     61 #include "net/spdy/spdy_session.h"
     62 #include "net/spdy/spdy_session_pool.h"
     63 #include "net/spdy/spdy_test_util_common.h"
     64 #include "net/ssl/ssl_cert_request_info.h"
     65 #include "net/ssl/ssl_config_service.h"
     66 #include "net/ssl/ssl_config_service_defaults.h"
     67 #include "net/ssl/ssl_info.h"
     68 #include "net/test/cert_test_util.h"
     69 #include "net/websockets/websocket_handshake_stream_base.h"
     70 #include "testing/gtest/include/gtest/gtest.h"
     71 #include "testing/platform_test.h"
     72 #include "url/gurl.h"
     73 
     74 using base::ASCIIToUTF16;
     75 
     76 //-----------------------------------------------------------------------------
     77 
     78 namespace {
     79 
     80 const base::string16 kBar(ASCIIToUTF16("bar"));
     81 const base::string16 kBar2(ASCIIToUTF16("bar2"));
     82 const base::string16 kBar3(ASCIIToUTF16("bar3"));
     83 const base::string16 kBaz(ASCIIToUTF16("baz"));
     84 const base::string16 kFirst(ASCIIToUTF16("first"));
     85 const base::string16 kFoo(ASCIIToUTF16("foo"));
     86 const base::string16 kFoo2(ASCIIToUTF16("foo2"));
     87 const base::string16 kFoo3(ASCIIToUTF16("foo3"));
     88 const base::string16 kFou(ASCIIToUTF16("fou"));
     89 const base::string16 kSecond(ASCIIToUTF16("second"));
     90 const base::string16 kTestingNTLM(ASCIIToUTF16("testing-ntlm"));
     91 const base::string16 kWrongPassword(ASCIIToUTF16("wrongpassword"));
     92 
     93 int GetIdleSocketCountInTransportSocketPool(net::HttpNetworkSession* session) {
     94   return session->GetTransportSocketPool(
     95       net::HttpNetworkSession::NORMAL_SOCKET_POOL)->IdleSocketCount();
     96 }
     97 
     98 int GetIdleSocketCountInSSLSocketPool(net::HttpNetworkSession* session) {
     99   return session->GetSSLSocketPool(
    100       net::HttpNetworkSession::NORMAL_SOCKET_POOL)->IdleSocketCount();
    101 }
    102 
    103 bool IsTransportSocketPoolStalled(net::HttpNetworkSession* session) {
    104   return session->GetTransportSocketPool(
    105       net::HttpNetworkSession::NORMAL_SOCKET_POOL)->IsStalled();
    106 }
    107 
    108 // Takes in a Value created from a NetLogHttpResponseParameter, and returns
    109 // a JSONified list of headers as a single string.  Uses single quotes instead
    110 // of double quotes for easier comparison.  Returns false on failure.
    111 bool GetHeaders(base::DictionaryValue* params, std::string* headers) {
    112   if (!params)
    113     return false;
    114   base::ListValue* header_list;
    115   if (!params->GetList("headers", &header_list))
    116     return false;
    117   std::string double_quote_headers;
    118   base::JSONWriter::Write(header_list, &double_quote_headers);
    119   base::ReplaceChars(double_quote_headers, "\"", "'", headers);
    120   return true;
    121 }
    122 
    123 // Tests LoadTimingInfo in the case a socket is reused and no PAC script is
    124 // used.
    125 void TestLoadTimingReused(const net::LoadTimingInfo& load_timing_info) {
    126   EXPECT_TRUE(load_timing_info.socket_reused);
    127   EXPECT_NE(net::NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
    128 
    129   EXPECT_TRUE(load_timing_info.proxy_resolve_start.is_null());
    130   EXPECT_TRUE(load_timing_info.proxy_resolve_end.is_null());
    131 
    132   net::ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
    133   EXPECT_FALSE(load_timing_info.send_start.is_null());
    134 
    135   EXPECT_LE(load_timing_info.send_start, load_timing_info.send_end);
    136 
    137   // Set at a higher level.
    138   EXPECT_TRUE(load_timing_info.request_start_time.is_null());
    139   EXPECT_TRUE(load_timing_info.request_start.is_null());
    140   EXPECT_TRUE(load_timing_info.receive_headers_end.is_null());
    141 }
    142 
    143 // Tests LoadTimingInfo in the case a new socket is used and no PAC script is
    144 // used.
    145 void TestLoadTimingNotReused(const net::LoadTimingInfo& load_timing_info,
    146                              int connect_timing_flags) {
    147   EXPECT_FALSE(load_timing_info.socket_reused);
    148   EXPECT_NE(net::NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
    149 
    150   EXPECT_TRUE(load_timing_info.proxy_resolve_start.is_null());
    151   EXPECT_TRUE(load_timing_info.proxy_resolve_end.is_null());
    152 
    153   net::ExpectConnectTimingHasTimes(load_timing_info.connect_timing,
    154                                    connect_timing_flags);
    155   EXPECT_LE(load_timing_info.connect_timing.connect_end,
    156             load_timing_info.send_start);
    157 
    158   EXPECT_LE(load_timing_info.send_start, load_timing_info.send_end);
    159 
    160   // Set at a higher level.
    161   EXPECT_TRUE(load_timing_info.request_start_time.is_null());
    162   EXPECT_TRUE(load_timing_info.request_start.is_null());
    163   EXPECT_TRUE(load_timing_info.receive_headers_end.is_null());
    164 }
    165 
    166 // Tests LoadTimingInfo in the case a socket is reused and a PAC script is
    167 // used.
    168 void TestLoadTimingReusedWithPac(const net::LoadTimingInfo& load_timing_info) {
    169   EXPECT_TRUE(load_timing_info.socket_reused);
    170   EXPECT_NE(net::NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
    171 
    172   net::ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
    173 
    174   EXPECT_FALSE(load_timing_info.proxy_resolve_start.is_null());
    175   EXPECT_LE(load_timing_info.proxy_resolve_start,
    176             load_timing_info.proxy_resolve_end);
    177   EXPECT_LE(load_timing_info.proxy_resolve_end,
    178             load_timing_info.send_start);
    179   EXPECT_LE(load_timing_info.send_start, load_timing_info.send_end);
    180 
    181   // Set at a higher level.
    182   EXPECT_TRUE(load_timing_info.request_start_time.is_null());
    183   EXPECT_TRUE(load_timing_info.request_start.is_null());
    184   EXPECT_TRUE(load_timing_info.receive_headers_end.is_null());
    185 }
    186 
    187 // Tests LoadTimingInfo in the case a new socket is used and a PAC script is
    188 // used.
    189 void TestLoadTimingNotReusedWithPac(const net::LoadTimingInfo& load_timing_info,
    190                                     int connect_timing_flags) {
    191   EXPECT_FALSE(load_timing_info.socket_reused);
    192   EXPECT_NE(net::NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
    193 
    194   EXPECT_FALSE(load_timing_info.proxy_resolve_start.is_null());
    195   EXPECT_LE(load_timing_info.proxy_resolve_start,
    196             load_timing_info.proxy_resolve_end);
    197   EXPECT_LE(load_timing_info.proxy_resolve_end,
    198             load_timing_info.connect_timing.connect_start);
    199   net::ExpectConnectTimingHasTimes(load_timing_info.connect_timing,
    200                                    connect_timing_flags);
    201   EXPECT_LE(load_timing_info.connect_timing.connect_end,
    202             load_timing_info.send_start);
    203 
    204   EXPECT_LE(load_timing_info.send_start, load_timing_info.send_end);
    205 
    206   // Set at a higher level.
    207   EXPECT_TRUE(load_timing_info.request_start_time.is_null());
    208   EXPECT_TRUE(load_timing_info.request_start.is_null());
    209   EXPECT_TRUE(load_timing_info.receive_headers_end.is_null());
    210 }
    211 
    212 }  // namespace
    213 
    214 namespace net {
    215 
    216 namespace {
    217 
    218 HttpNetworkSession* CreateSession(SpdySessionDependencies* session_deps) {
    219   return SpdySessionDependencies::SpdyCreateSession(session_deps);
    220 }
    221 
    222 }  // namespace
    223 
    224 class HttpNetworkTransactionTest
    225     : public PlatformTest,
    226       public ::testing::WithParamInterface<NextProto> {
    227  public:
    228   virtual ~HttpNetworkTransactionTest() {
    229     // Important to restore the per-pool limit first, since the pool limit must
    230     // always be greater than group limit, and the tests reduce both limits.
    231     ClientSocketPoolManager::set_max_sockets_per_pool(
    232         HttpNetworkSession::NORMAL_SOCKET_POOL, old_max_pool_sockets_);
    233     ClientSocketPoolManager::set_max_sockets_per_group(
    234         HttpNetworkSession::NORMAL_SOCKET_POOL, old_max_group_sockets_);
    235   }
    236 
    237  protected:
    238   HttpNetworkTransactionTest()
    239       : spdy_util_(GetParam()),
    240         session_deps_(GetParam()),
    241         old_max_group_sockets_(ClientSocketPoolManager::max_sockets_per_group(
    242             HttpNetworkSession::NORMAL_SOCKET_POOL)),
    243         old_max_pool_sockets_(ClientSocketPoolManager::max_sockets_per_pool(
    244             HttpNetworkSession::NORMAL_SOCKET_POOL)) {
    245   }
    246 
    247   struct SimpleGetHelperResult {
    248     int rv;
    249     std::string status_line;
    250     std::string response_data;
    251     int64 totalReceivedBytes;
    252     LoadTimingInfo load_timing_info;
    253   };
    254 
    255   virtual void SetUp() {
    256     NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
    257     base::MessageLoop::current()->RunUntilIdle();
    258   }
    259 
    260   virtual void TearDown() {
    261     NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
    262     base::MessageLoop::current()->RunUntilIdle();
    263     // Empty the current queue.
    264     base::MessageLoop::current()->RunUntilIdle();
    265     PlatformTest::TearDown();
    266     NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
    267     base::MessageLoop::current()->RunUntilIdle();
    268   }
    269 
    270   // This is the expected return from a current server advertising SPDY.
    271   std::string GetAlternateProtocolHttpHeader() {
    272     return
    273         std::string("Alternate-Protocol: 443:") +
    274         AlternateProtocolToString(AlternateProtocolFromNextProto(GetParam())) +
    275         "\r\n\r\n";
    276   }
    277 
    278   // Either |write_failure| specifies a write failure or |read_failure|
    279   // specifies a read failure when using a reused socket.  In either case, the
    280   // failure should cause the network transaction to resend the request, and the
    281   // other argument should be NULL.
    282   void KeepAliveConnectionResendRequestTest(const MockWrite* write_failure,
    283                                             const MockRead* read_failure);
    284 
    285   // Either |write_failure| specifies a write failure or |read_failure|
    286   // specifies a read failure when using a reused socket.  In either case, the
    287   // failure should cause the network transaction to resend the request, and the
    288   // other argument should be NULL.
    289   void PreconnectErrorResendRequestTest(const MockWrite* write_failure,
    290                                         const MockRead* read_failure,
    291                                         bool use_spdy);
    292 
    293   SimpleGetHelperResult SimpleGetHelperForData(StaticSocketDataProvider* data[],
    294                                                size_t data_count) {
    295     SimpleGetHelperResult out;
    296 
    297     HttpRequestInfo request;
    298     request.method = "GET";
    299     request.url = GURL("http://www.google.com/");
    300     request.load_flags = 0;
    301 
    302     CapturingBoundNetLog log;
    303     session_deps_.net_log = log.bound().net_log();
    304     scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
    305     scoped_ptr<HttpTransaction> trans(
    306         new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
    307 
    308     for (size_t i = 0; i < data_count; ++i) {
    309       session_deps_.socket_factory->AddSocketDataProvider(data[i]);
    310     }
    311 
    312     TestCompletionCallback callback;
    313 
    314     EXPECT_TRUE(log.bound().IsLogging());
    315     int rv = trans->Start(&request, callback.callback(), log.bound());
    316     EXPECT_EQ(ERR_IO_PENDING, rv);
    317 
    318     out.rv = callback.WaitForResult();
    319 
    320     // Even in the failure cases that use this function, connections are always
    321     // successfully established before the error.
    322     EXPECT_TRUE(trans->GetLoadTimingInfo(&out.load_timing_info));
    323     TestLoadTimingNotReused(out.load_timing_info, CONNECT_TIMING_HAS_DNS_TIMES);
    324 
    325     if (out.rv != OK)
    326       return out;
    327 
    328     const HttpResponseInfo* response = trans->GetResponseInfo();
    329     // Can't use ASSERT_* inside helper functions like this, so
    330     // return an error.
    331     if (response == NULL || response->headers.get() == NULL) {
    332       out.rv = ERR_UNEXPECTED;
    333       return out;
    334     }
    335     out.status_line = response->headers->GetStatusLine();
    336 
    337     EXPECT_EQ("127.0.0.1", response->socket_address.host());
    338     EXPECT_EQ(80, response->socket_address.port());
    339 
    340     rv = ReadTransaction(trans.get(), &out.response_data);
    341     EXPECT_EQ(OK, rv);
    342 
    343     net::CapturingNetLog::CapturedEntryList entries;
    344     log.GetEntries(&entries);
    345     size_t pos = ExpectLogContainsSomewhere(
    346         entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_REQUEST_HEADERS,
    347         NetLog::PHASE_NONE);
    348     ExpectLogContainsSomewhere(
    349         entries, pos,
    350         NetLog::TYPE_HTTP_TRANSACTION_READ_RESPONSE_HEADERS,
    351         NetLog::PHASE_NONE);
    352 
    353     std::string line;
    354     EXPECT_TRUE(entries[pos].GetStringValue("line", &line));
    355     EXPECT_EQ("GET / HTTP/1.1\r\n", line);
    356 
    357     HttpRequestHeaders request_headers;
    358     EXPECT_TRUE(trans->GetFullRequestHeaders(&request_headers));
    359     std::string value;
    360     EXPECT_TRUE(request_headers.GetHeader("Host", &value));
    361     EXPECT_EQ("www.google.com", value);
    362     EXPECT_TRUE(request_headers.GetHeader("Connection", &value));
    363     EXPECT_EQ("keep-alive", value);
    364 
    365     std::string response_headers;
    366     EXPECT_TRUE(GetHeaders(entries[pos].params.get(), &response_headers));
    367     EXPECT_EQ("['Host: www.google.com','Connection: keep-alive']",
    368               response_headers);
    369 
    370     out.totalReceivedBytes = trans->GetTotalReceivedBytes();
    371     return out;
    372   }
    373 
    374   SimpleGetHelperResult SimpleGetHelper(MockRead data_reads[],
    375                                         size_t reads_count) {
    376     StaticSocketDataProvider reads(data_reads, reads_count, NULL, 0);
    377     StaticSocketDataProvider* data[] = { &reads };
    378     return SimpleGetHelperForData(data, 1);
    379   }
    380 
    381   int64 ReadsSize(MockRead data_reads[], size_t reads_count) {
    382     int64 size = 0;
    383     for (size_t i = 0; i < reads_count; ++i)
    384       size += data_reads[i].data_len;
    385     return size;
    386   }
    387 
    388   void ConnectStatusHelperWithExpectedStatus(const MockRead& status,
    389                                              int expected_status);
    390 
    391   void ConnectStatusHelper(const MockRead& status);
    392 
    393   void BypassHostCacheOnRefreshHelper(int load_flags);
    394 
    395   void CheckErrorIsPassedBack(int error, IoMode mode);
    396 
    397   SpdyTestUtil spdy_util_;
    398   SpdySessionDependencies session_deps_;
    399 
    400   // Original socket limits.  Some tests set these.  Safest to always restore
    401   // them once each test has been run.
    402   int old_max_group_sockets_;
    403   int old_max_pool_sockets_;
    404 };
    405 
    406 INSTANTIATE_TEST_CASE_P(
    407     NextProto,
    408     HttpNetworkTransactionTest,
    409     testing::Values(kProtoDeprecatedSPDY2,
    410                     kProtoSPDY3, kProtoSPDY31, kProtoSPDY4));
    411 
    412 namespace {
    413 
    414 class BeforeNetworkStartHandler {
    415  public:
    416   explicit BeforeNetworkStartHandler(bool defer)
    417       : defer_on_before_network_start_(defer),
    418         observed_before_network_start_(false) {}
    419 
    420   void OnBeforeNetworkStart(bool* defer) {
    421     *defer = defer_on_before_network_start_;
    422     observed_before_network_start_ = true;
    423   }
    424 
    425   bool observed_before_network_start() const {
    426     return observed_before_network_start_;
    427   }
    428 
    429  private:
    430   const bool defer_on_before_network_start_;
    431   bool observed_before_network_start_;
    432 
    433   DISALLOW_COPY_AND_ASSIGN(BeforeNetworkStartHandler);
    434 };
    435 
    436 // Fill |str| with a long header list that consumes >= |size| bytes.
    437 void FillLargeHeadersString(std::string* str, int size) {
    438   const char* row =
    439       "SomeHeaderName: xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx\r\n";
    440   const int sizeof_row = strlen(row);
    441   const int num_rows = static_cast<int>(
    442       ceil(static_cast<float>(size) / sizeof_row));
    443   const int sizeof_data = num_rows * sizeof_row;
    444   DCHECK(sizeof_data >= size);
    445   str->reserve(sizeof_data);
    446 
    447   for (int i = 0; i < num_rows; ++i)
    448     str->append(row, sizeof_row);
    449 }
    450 
    451 // Alternative functions that eliminate randomness and dependency on the local
    452 // host name so that the generated NTLM messages are reproducible.
    453 void MockGenerateRandom1(uint8* output, size_t n) {
    454   static const uint8 bytes[] = {
    455     0x55, 0x29, 0x66, 0x26, 0x6b, 0x9c, 0x73, 0x54
    456   };
    457   static size_t current_byte = 0;
    458   for (size_t i = 0; i < n; ++i) {
    459     output[i] = bytes[current_byte++];
    460     current_byte %= arraysize(bytes);
    461   }
    462 }
    463 
    464 void MockGenerateRandom2(uint8* output, size_t n) {
    465   static const uint8 bytes[] = {
    466     0x96, 0x79, 0x85, 0xe7, 0x49, 0x93, 0x70, 0xa1,
    467     0x4e, 0xe7, 0x87, 0x45, 0x31, 0x5b, 0xd3, 0x1f
    468   };
    469   static size_t current_byte = 0;
    470   for (size_t i = 0; i < n; ++i) {
    471     output[i] = bytes[current_byte++];
    472     current_byte %= arraysize(bytes);
    473   }
    474 }
    475 
    476 std::string MockGetHostName() {
    477   return "WTC-WIN7";
    478 }
    479 
    480 template<typename ParentPool>
    481 class CaptureGroupNameSocketPool : public ParentPool {
    482  public:
    483   CaptureGroupNameSocketPool(HostResolver* host_resolver,
    484                              CertVerifier* cert_verifier);
    485 
    486   const std::string last_group_name_received() const {
    487     return last_group_name_;
    488   }
    489 
    490   virtual int RequestSocket(const std::string& group_name,
    491                             const void* socket_params,
    492                             RequestPriority priority,
    493                             ClientSocketHandle* handle,
    494                             const CompletionCallback& callback,
    495                             const BoundNetLog& net_log) {
    496     last_group_name_ = group_name;
    497     return ERR_IO_PENDING;
    498   }
    499   virtual void CancelRequest(const std::string& group_name,
    500                              ClientSocketHandle* handle) {}
    501   virtual void ReleaseSocket(const std::string& group_name,
    502                              scoped_ptr<StreamSocket> socket,
    503                              int id) {}
    504   virtual void CloseIdleSockets() {}
    505   virtual int IdleSocketCount() const {
    506     return 0;
    507   }
    508   virtual int IdleSocketCountInGroup(const std::string& group_name) const {
    509     return 0;
    510   }
    511   virtual LoadState GetLoadState(const std::string& group_name,
    512                                  const ClientSocketHandle* handle) const {
    513     return LOAD_STATE_IDLE;
    514   }
    515   virtual base::TimeDelta ConnectionTimeout() const {
    516     return base::TimeDelta();
    517   }
    518 
    519  private:
    520   std::string last_group_name_;
    521 };
    522 
    523 typedef CaptureGroupNameSocketPool<TransportClientSocketPool>
    524 CaptureGroupNameTransportSocketPool;
    525 typedef CaptureGroupNameSocketPool<HttpProxyClientSocketPool>
    526 CaptureGroupNameHttpProxySocketPool;
    527 typedef CaptureGroupNameSocketPool<SOCKSClientSocketPool>
    528 CaptureGroupNameSOCKSSocketPool;
    529 typedef CaptureGroupNameSocketPool<SSLClientSocketPool>
    530 CaptureGroupNameSSLSocketPool;
    531 
    532 template<typename ParentPool>
    533 CaptureGroupNameSocketPool<ParentPool>::CaptureGroupNameSocketPool(
    534     HostResolver* host_resolver,
    535     CertVerifier* /* cert_verifier */)
    536     : ParentPool(0, 0, NULL, host_resolver, NULL, NULL) {}
    537 
    538 template<>
    539 CaptureGroupNameHttpProxySocketPool::CaptureGroupNameSocketPool(
    540     HostResolver* host_resolver,
    541     CertVerifier* /* cert_verifier */)
    542     : HttpProxyClientSocketPool(0, 0, NULL, host_resolver, NULL, NULL, NULL) {}
    543 
    544 template <>
    545 CaptureGroupNameSSLSocketPool::CaptureGroupNameSocketPool(
    546     HostResolver* host_resolver,
    547     CertVerifier* cert_verifier)
    548     : SSLClientSocketPool(0,
    549                           0,
    550                           NULL,
    551                           host_resolver,
    552                           cert_verifier,
    553                           NULL,
    554                           NULL,
    555                           NULL,
    556                           std::string(),
    557                           NULL,
    558                           NULL,
    559                           NULL,
    560                           NULL,
    561                           NULL,
    562                           NULL) {}
    563 
    564 //-----------------------------------------------------------------------------
    565 
    566 // Helper functions for validating that AuthChallengeInfo's are correctly
    567 // configured for common cases.
    568 bool CheckBasicServerAuth(const AuthChallengeInfo* auth_challenge) {
    569   if (!auth_challenge)
    570     return false;
    571   EXPECT_FALSE(auth_challenge->is_proxy);
    572   EXPECT_EQ("www.google.com:80", auth_challenge->challenger.ToString());
    573   EXPECT_EQ("MyRealm1", auth_challenge->realm);
    574   EXPECT_EQ("basic", auth_challenge->scheme);
    575   return true;
    576 }
    577 
    578 bool CheckBasicProxyAuth(const AuthChallengeInfo* auth_challenge) {
    579   if (!auth_challenge)
    580     return false;
    581   EXPECT_TRUE(auth_challenge->is_proxy);
    582   EXPECT_EQ("myproxy:70", auth_challenge->challenger.ToString());
    583   EXPECT_EQ("MyRealm1", auth_challenge->realm);
    584   EXPECT_EQ("basic", auth_challenge->scheme);
    585   return true;
    586 }
    587 
    588 bool CheckDigestServerAuth(const AuthChallengeInfo* auth_challenge) {
    589   if (!auth_challenge)
    590     return false;
    591   EXPECT_FALSE(auth_challenge->is_proxy);
    592   EXPECT_EQ("www.google.com:80", auth_challenge->challenger.ToString());
    593   EXPECT_EQ("digestive", auth_challenge->realm);
    594   EXPECT_EQ("digest", auth_challenge->scheme);
    595   return true;
    596 }
    597 
    598 bool CheckNTLMServerAuth(const AuthChallengeInfo* auth_challenge) {
    599   if (!auth_challenge)
    600     return false;
    601   EXPECT_FALSE(auth_challenge->is_proxy);
    602   EXPECT_EQ("172.22.68.17:80", auth_challenge->challenger.ToString());
    603   EXPECT_EQ(std::string(), auth_challenge->realm);
    604   EXPECT_EQ("ntlm", auth_challenge->scheme);
    605   return true;
    606 }
    607 
    608 }  // namespace
    609 
    610 TEST_P(HttpNetworkTransactionTest, Basic) {
    611   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
    612   scoped_ptr<HttpTransaction> trans(
    613       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
    614 }
    615 
    616 TEST_P(HttpNetworkTransactionTest, SimpleGET) {
    617   MockRead data_reads[] = {
    618     MockRead("HTTP/1.0 200 OK\r\n\r\n"),
    619     MockRead("hello world"),
    620     MockRead(SYNCHRONOUS, OK),
    621   };
    622   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    623                                               arraysize(data_reads));
    624   EXPECT_EQ(OK, out.rv);
    625   EXPECT_EQ("HTTP/1.0 200 OK", out.status_line);
    626   EXPECT_EQ("hello world", out.response_data);
    627   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    628   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    629 }
    630 
    631 // Response with no status line.
    632 TEST_P(HttpNetworkTransactionTest, SimpleGETNoHeaders) {
    633   MockRead data_reads[] = {
    634     MockRead("hello world"),
    635     MockRead(SYNCHRONOUS, OK),
    636   };
    637   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    638                                               arraysize(data_reads));
    639   EXPECT_EQ(OK, out.rv);
    640   EXPECT_EQ("HTTP/0.9 200 OK", out.status_line);
    641   EXPECT_EQ("hello world", out.response_data);
    642   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    643   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    644 }
    645 
    646 // Allow up to 4 bytes of junk to precede status line.
    647 TEST_P(HttpNetworkTransactionTest, StatusLineJunk3Bytes) {
    648   MockRead data_reads[] = {
    649     MockRead("xxxHTTP/1.0 404 Not Found\nServer: blah\n\nDATA"),
    650     MockRead(SYNCHRONOUS, OK),
    651   };
    652   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    653                                               arraysize(data_reads));
    654   EXPECT_EQ(OK, out.rv);
    655   EXPECT_EQ("HTTP/1.0 404 Not Found", out.status_line);
    656   EXPECT_EQ("DATA", out.response_data);
    657   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    658   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    659 }
    660 
    661 // Allow up to 4 bytes of junk to precede status line.
    662 TEST_P(HttpNetworkTransactionTest, StatusLineJunk4Bytes) {
    663   MockRead data_reads[] = {
    664     MockRead("\n\nQJHTTP/1.0 404 Not Found\nServer: blah\n\nDATA"),
    665     MockRead(SYNCHRONOUS, OK),
    666   };
    667   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    668                                               arraysize(data_reads));
    669   EXPECT_EQ(OK, out.rv);
    670   EXPECT_EQ("HTTP/1.0 404 Not Found", out.status_line);
    671   EXPECT_EQ("DATA", out.response_data);
    672   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    673   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    674 }
    675 
    676 // Beyond 4 bytes of slop and it should fail to find a status line.
    677 TEST_P(HttpNetworkTransactionTest, StatusLineJunk5Bytes) {
    678   MockRead data_reads[] = {
    679     MockRead("xxxxxHTTP/1.1 404 Not Found\nServer: blah"),
    680     MockRead(SYNCHRONOUS, OK),
    681   };
    682   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    683                                               arraysize(data_reads));
    684   EXPECT_EQ(OK, out.rv);
    685   EXPECT_EQ("HTTP/0.9 200 OK", out.status_line);
    686   EXPECT_EQ("xxxxxHTTP/1.1 404 Not Found\nServer: blah", out.response_data);
    687   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    688   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    689 }
    690 
    691 // Same as StatusLineJunk4Bytes, except the read chunks are smaller.
    692 TEST_P(HttpNetworkTransactionTest, StatusLineJunk4Bytes_Slow) {
    693   MockRead data_reads[] = {
    694     MockRead("\n"),
    695     MockRead("\n"),
    696     MockRead("Q"),
    697     MockRead("J"),
    698     MockRead("HTTP/1.0 404 Not Found\nServer: blah\n\nDATA"),
    699     MockRead(SYNCHRONOUS, OK),
    700   };
    701   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    702                                               arraysize(data_reads));
    703   EXPECT_EQ(OK, out.rv);
    704   EXPECT_EQ("HTTP/1.0 404 Not Found", out.status_line);
    705   EXPECT_EQ("DATA", out.response_data);
    706   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    707   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    708 }
    709 
    710 // Close the connection before enough bytes to have a status line.
    711 TEST_P(HttpNetworkTransactionTest, StatusLinePartial) {
    712   MockRead data_reads[] = {
    713     MockRead("HTT"),
    714     MockRead(SYNCHRONOUS, OK),
    715   };
    716   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    717                                               arraysize(data_reads));
    718   EXPECT_EQ(OK, out.rv);
    719   EXPECT_EQ("HTTP/0.9 200 OK", out.status_line);
    720   EXPECT_EQ("HTT", out.response_data);
    721   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    722   EXPECT_EQ(reads_size, out.totalReceivedBytes);
    723 }
    724 
    725 // Simulate a 204 response, lacking a Content-Length header, sent over a
    726 // persistent connection.  The response should still terminate since a 204
    727 // cannot have a response body.
    728 TEST_P(HttpNetworkTransactionTest, StopsReading204) {
    729   char junk[] = "junk";
    730   MockRead data_reads[] = {
    731     MockRead("HTTP/1.1 204 No Content\r\n\r\n"),
    732     MockRead(junk),  // Should not be read!!
    733     MockRead(SYNCHRONOUS, OK),
    734   };
    735   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    736                                               arraysize(data_reads));
    737   EXPECT_EQ(OK, out.rv);
    738   EXPECT_EQ("HTTP/1.1 204 No Content", out.status_line);
    739   EXPECT_EQ("", out.response_data);
    740   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    741   int64 response_size = reads_size - strlen(junk);
    742   EXPECT_EQ(response_size, out.totalReceivedBytes);
    743 }
    744 
    745 // A simple request using chunked encoding with some extra data after.
    746 TEST_P(HttpNetworkTransactionTest, ChunkedEncoding) {
    747   std::string final_chunk = "0\r\n\r\n";
    748   std::string extra_data = "HTTP/1.1 200 OK\r\n";
    749   std::string last_read = final_chunk + extra_data;
    750   MockRead data_reads[] = {
    751     MockRead("HTTP/1.1 200 OK\r\nTransfer-Encoding: chunked\r\n\r\n"),
    752     MockRead("5\r\nHello\r\n"),
    753     MockRead("1\r\n"),
    754     MockRead(" \r\n"),
    755     MockRead("5\r\nworld\r\n"),
    756     MockRead(last_read.data()),
    757     MockRead(SYNCHRONOUS, OK),
    758   };
    759   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    760                                               arraysize(data_reads));
    761   EXPECT_EQ(OK, out.rv);
    762   EXPECT_EQ("HTTP/1.1 200 OK", out.status_line);
    763   EXPECT_EQ("Hello world", out.response_data);
    764   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
    765   int64 response_size = reads_size - extra_data.size();
    766   EXPECT_EQ(response_size, out.totalReceivedBytes);
    767 }
    768 
    769 // Next tests deal with http://crbug.com/56344.
    770 
    771 TEST_P(HttpNetworkTransactionTest,
    772        MultipleContentLengthHeadersNoTransferEncoding) {
    773   MockRead data_reads[] = {
    774     MockRead("HTTP/1.1 200 OK\r\n"),
    775     MockRead("Content-Length: 10\r\n"),
    776     MockRead("Content-Length: 5\r\n\r\n"),
    777   };
    778   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    779                                               arraysize(data_reads));
    780   EXPECT_EQ(ERR_RESPONSE_HEADERS_MULTIPLE_CONTENT_LENGTH, out.rv);
    781 }
    782 
    783 TEST_P(HttpNetworkTransactionTest,
    784        DuplicateContentLengthHeadersNoTransferEncoding) {
    785   MockRead data_reads[] = {
    786     MockRead("HTTP/1.1 200 OK\r\n"),
    787     MockRead("Content-Length: 5\r\n"),
    788     MockRead("Content-Length: 5\r\n\r\n"),
    789     MockRead("Hello"),
    790   };
    791   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    792                                               arraysize(data_reads));
    793   EXPECT_EQ(OK, out.rv);
    794   EXPECT_EQ("HTTP/1.1 200 OK", out.status_line);
    795   EXPECT_EQ("Hello", out.response_data);
    796 }
    797 
    798 TEST_P(HttpNetworkTransactionTest,
    799        ComplexContentLengthHeadersNoTransferEncoding) {
    800   // More than 2 dupes.
    801   {
    802     MockRead data_reads[] = {
    803       MockRead("HTTP/1.1 200 OK\r\n"),
    804       MockRead("Content-Length: 5\r\n"),
    805       MockRead("Content-Length: 5\r\n"),
    806       MockRead("Content-Length: 5\r\n\r\n"),
    807       MockRead("Hello"),
    808     };
    809     SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    810                                                 arraysize(data_reads));
    811     EXPECT_EQ(OK, out.rv);
    812     EXPECT_EQ("HTTP/1.1 200 OK", out.status_line);
    813     EXPECT_EQ("Hello", out.response_data);
    814   }
    815   // HTTP/1.0
    816   {
    817     MockRead data_reads[] = {
    818       MockRead("HTTP/1.0 200 OK\r\n"),
    819       MockRead("Content-Length: 5\r\n"),
    820       MockRead("Content-Length: 5\r\n"),
    821       MockRead("Content-Length: 5\r\n\r\n"),
    822       MockRead("Hello"),
    823     };
    824     SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    825                                                 arraysize(data_reads));
    826     EXPECT_EQ(OK, out.rv);
    827     EXPECT_EQ("HTTP/1.0 200 OK", out.status_line);
    828     EXPECT_EQ("Hello", out.response_data);
    829   }
    830   // 2 dupes and one mismatched.
    831   {
    832     MockRead data_reads[] = {
    833       MockRead("HTTP/1.1 200 OK\r\n"),
    834       MockRead("Content-Length: 10\r\n"),
    835       MockRead("Content-Length: 10\r\n"),
    836       MockRead("Content-Length: 5\r\n\r\n"),
    837     };
    838     SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    839                                                 arraysize(data_reads));
    840     EXPECT_EQ(ERR_RESPONSE_HEADERS_MULTIPLE_CONTENT_LENGTH, out.rv);
    841   }
    842 }
    843 
    844 TEST_P(HttpNetworkTransactionTest,
    845        MultipleContentLengthHeadersTransferEncoding) {
    846   MockRead data_reads[] = {
    847     MockRead("HTTP/1.1 200 OK\r\n"),
    848     MockRead("Content-Length: 666\r\n"),
    849     MockRead("Content-Length: 1337\r\n"),
    850     MockRead("Transfer-Encoding: chunked\r\n\r\n"),
    851     MockRead("5\r\nHello\r\n"),
    852     MockRead("1\r\n"),
    853     MockRead(" \r\n"),
    854     MockRead("5\r\nworld\r\n"),
    855     MockRead("0\r\n\r\nHTTP/1.1 200 OK\r\n"),
    856     MockRead(SYNCHRONOUS, OK),
    857   };
    858   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    859                                               arraysize(data_reads));
    860   EXPECT_EQ(OK, out.rv);
    861   EXPECT_EQ("HTTP/1.1 200 OK", out.status_line);
    862   EXPECT_EQ("Hello world", out.response_data);
    863 }
    864 
    865 // Next tests deal with http://crbug.com/98895.
    866 
    867 // Checks that a single Content-Disposition header results in no error.
    868 TEST_P(HttpNetworkTransactionTest, SingleContentDispositionHeader) {
    869   MockRead data_reads[] = {
    870     MockRead("HTTP/1.1 200 OK\r\n"),
    871     MockRead("Content-Disposition: attachment;filename=\"salutations.txt\"r\n"),
    872     MockRead("Content-Length: 5\r\n\r\n"),
    873     MockRead("Hello"),
    874   };
    875   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    876                                               arraysize(data_reads));
    877   EXPECT_EQ(OK, out.rv);
    878   EXPECT_EQ("HTTP/1.1 200 OK", out.status_line);
    879   EXPECT_EQ("Hello", out.response_data);
    880 }
    881 
    882 // Checks that two identical Content-Disposition headers result in no error.
    883 TEST_P(HttpNetworkTransactionTest,
    884        TwoIdenticalContentDispositionHeaders) {
    885   MockRead data_reads[] = {
    886     MockRead("HTTP/1.1 200 OK\r\n"),
    887     MockRead("Content-Disposition: attachment;filename=\"greetings.txt\"r\n"),
    888     MockRead("Content-Disposition: attachment;filename=\"greetings.txt\"r\n"),
    889     MockRead("Content-Length: 5\r\n\r\n"),
    890     MockRead("Hello"),
    891   };
    892   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    893                                               arraysize(data_reads));
    894   EXPECT_EQ(OK, out.rv);
    895   EXPECT_EQ("HTTP/1.1 200 OK", out.status_line);
    896   EXPECT_EQ("Hello", out.response_data);
    897 }
    898 
    899 // Checks that two distinct Content-Disposition headers result in an error.
    900 TEST_P(HttpNetworkTransactionTest, TwoDistinctContentDispositionHeaders) {
    901   MockRead data_reads[] = {
    902     MockRead("HTTP/1.1 200 OK\r\n"),
    903     MockRead("Content-Disposition: attachment;filename=\"greetings.txt\"r\n"),
    904     MockRead("Content-Disposition: attachment;filename=\"hi.txt\"r\n"),
    905     MockRead("Content-Length: 5\r\n\r\n"),
    906     MockRead("Hello"),
    907   };
    908   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    909                                               arraysize(data_reads));
    910   EXPECT_EQ(ERR_RESPONSE_HEADERS_MULTIPLE_CONTENT_DISPOSITION, out.rv);
    911 }
    912 
    913 // Checks that two identical Location headers result in no error.
    914 // Also tests Location header behavior.
    915 TEST_P(HttpNetworkTransactionTest, TwoIdenticalLocationHeaders) {
    916   MockRead data_reads[] = {
    917     MockRead("HTTP/1.1 302 Redirect\r\n"),
    918     MockRead("Location: http://good.com/\r\n"),
    919     MockRead("Location: http://good.com/\r\n"),
    920     MockRead("Content-Length: 0\r\n\r\n"),
    921     MockRead(SYNCHRONOUS, OK),
    922   };
    923 
    924   HttpRequestInfo request;
    925   request.method = "GET";
    926   request.url = GURL("http://redirect.com/");
    927   request.load_flags = 0;
    928 
    929   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
    930   scoped_ptr<HttpTransaction> trans(
    931       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
    932 
    933   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
    934   session_deps_.socket_factory->AddSocketDataProvider(&data);
    935 
    936   TestCompletionCallback callback;
    937 
    938   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
    939   EXPECT_EQ(ERR_IO_PENDING, rv);
    940 
    941   EXPECT_EQ(OK, callback.WaitForResult());
    942 
    943   const HttpResponseInfo* response = trans->GetResponseInfo();
    944   ASSERT_TRUE(response != NULL && response->headers.get() != NULL);
    945   EXPECT_EQ("HTTP/1.1 302 Redirect", response->headers->GetStatusLine());
    946   std::string url;
    947   EXPECT_TRUE(response->headers->IsRedirect(&url));
    948   EXPECT_EQ("http://good.com/", url);
    949   EXPECT_TRUE(response->proxy_server.IsEmpty());
    950 }
    951 
    952 // Checks that two distinct Location headers result in an error.
    953 TEST_P(HttpNetworkTransactionTest, TwoDistinctLocationHeaders) {
    954   MockRead data_reads[] = {
    955     MockRead("HTTP/1.1 302 Redirect\r\n"),
    956     MockRead("Location: http://good.com/\r\n"),
    957     MockRead("Location: http://evil.com/\r\n"),
    958     MockRead("Content-Length: 0\r\n\r\n"),
    959     MockRead(SYNCHRONOUS, OK),
    960   };
    961   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
    962                                               arraysize(data_reads));
    963   EXPECT_EQ(ERR_RESPONSE_HEADERS_MULTIPLE_LOCATION, out.rv);
    964 }
    965 
    966 // Do a request using the HEAD method. Verify that we don't try to read the
    967 // message body (since HEAD has none).
    968 TEST_P(HttpNetworkTransactionTest, Head) {
    969   HttpRequestInfo request;
    970   request.method = "HEAD";
    971   request.url = GURL("http://www.google.com/");
    972   request.load_flags = 0;
    973 
    974   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
    975   scoped_ptr<HttpTransaction> trans(
    976       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
    977 
    978   MockWrite data_writes1[] = {
    979     MockWrite("HEAD / HTTP/1.1\r\n"
    980               "Host: www.google.com\r\n"
    981               "Connection: keep-alive\r\n"
    982               "Content-Length: 0\r\n\r\n"),
    983   };
    984   MockRead data_reads1[] = {
    985     MockRead("HTTP/1.1 404 Not Found\r\n"),
    986     MockRead("Server: Blah\r\n"),
    987     MockRead("Content-Length: 1234\r\n\r\n"),
    988 
    989     // No response body because the test stops reading here.
    990     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
    991   };
    992 
    993   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
    994                                  data_writes1, arraysize(data_writes1));
    995   session_deps_.socket_factory->AddSocketDataProvider(&data1);
    996 
    997   TestCompletionCallback callback1;
    998 
    999   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   1000   EXPECT_EQ(ERR_IO_PENDING, rv);
   1001 
   1002   rv = callback1.WaitForResult();
   1003   EXPECT_EQ(OK, rv);
   1004 
   1005   const HttpResponseInfo* response = trans->GetResponseInfo();
   1006   ASSERT_TRUE(response != NULL);
   1007 
   1008   // Check that the headers got parsed.
   1009   EXPECT_TRUE(response->headers.get() != NULL);
   1010   EXPECT_EQ(1234, response->headers->GetContentLength());
   1011   EXPECT_EQ("HTTP/1.1 404 Not Found", response->headers->GetStatusLine());
   1012   EXPECT_TRUE(response->proxy_server.IsEmpty());
   1013 
   1014   std::string server_header;
   1015   void* iter = NULL;
   1016   bool has_server_header = response->headers->EnumerateHeader(
   1017       &iter, "Server", &server_header);
   1018   EXPECT_TRUE(has_server_header);
   1019   EXPECT_EQ("Blah", server_header);
   1020 
   1021   // Reading should give EOF right away, since there is no message body
   1022   // (despite non-zero content-length).
   1023   std::string response_data;
   1024   rv = ReadTransaction(trans.get(), &response_data);
   1025   EXPECT_EQ(OK, rv);
   1026   EXPECT_EQ("", response_data);
   1027 }
   1028 
   1029 TEST_P(HttpNetworkTransactionTest, ReuseConnection) {
   1030   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1031 
   1032   MockRead data_reads[] = {
   1033     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n"),
   1034     MockRead("hello"),
   1035     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n"),
   1036     MockRead("world"),
   1037     MockRead(SYNCHRONOUS, OK),
   1038   };
   1039   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1040   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1041 
   1042   const char* const kExpectedResponseData[] = {
   1043     "hello", "world"
   1044   };
   1045 
   1046   for (int i = 0; i < 2; ++i) {
   1047     HttpRequestInfo request;
   1048     request.method = "GET";
   1049     request.url = GURL("http://www.google.com/");
   1050     request.load_flags = 0;
   1051 
   1052     scoped_ptr<HttpTransaction> trans(
   1053         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1054 
   1055     TestCompletionCallback callback;
   1056 
   1057     int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1058     EXPECT_EQ(ERR_IO_PENDING, rv);
   1059 
   1060     rv = callback.WaitForResult();
   1061     EXPECT_EQ(OK, rv);
   1062 
   1063     const HttpResponseInfo* response = trans->GetResponseInfo();
   1064     ASSERT_TRUE(response != NULL);
   1065 
   1066     EXPECT_TRUE(response->headers.get() != NULL);
   1067     EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   1068     EXPECT_TRUE(response->proxy_server.IsEmpty());
   1069 
   1070     std::string response_data;
   1071     rv = ReadTransaction(trans.get(), &response_data);
   1072     EXPECT_EQ(OK, rv);
   1073     EXPECT_EQ(kExpectedResponseData[i], response_data);
   1074   }
   1075 }
   1076 
   1077 TEST_P(HttpNetworkTransactionTest, Ignores100) {
   1078   ScopedVector<UploadElementReader> element_readers;
   1079   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   1080   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   1081 
   1082   HttpRequestInfo request;
   1083   request.method = "POST";
   1084   request.url = GURL("http://www.foo.com/");
   1085   request.upload_data_stream = &upload_data_stream;
   1086   request.load_flags = 0;
   1087 
   1088   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1089   scoped_ptr<HttpTransaction> trans(
   1090       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1091 
   1092   MockRead data_reads[] = {
   1093     MockRead("HTTP/1.0 100 Continue\r\n\r\n"),
   1094     MockRead("HTTP/1.0 200 OK\r\n\r\n"),
   1095     MockRead("hello world"),
   1096     MockRead(SYNCHRONOUS, OK),
   1097   };
   1098   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1099   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1100 
   1101   TestCompletionCallback callback;
   1102 
   1103   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1104   EXPECT_EQ(ERR_IO_PENDING, rv);
   1105 
   1106   rv = callback.WaitForResult();
   1107   EXPECT_EQ(OK, rv);
   1108 
   1109   const HttpResponseInfo* response = trans->GetResponseInfo();
   1110   ASSERT_TRUE(response != NULL);
   1111 
   1112   EXPECT_TRUE(response->headers.get() != NULL);
   1113   EXPECT_EQ("HTTP/1.0 200 OK", response->headers->GetStatusLine());
   1114 
   1115   std::string response_data;
   1116   rv = ReadTransaction(trans.get(), &response_data);
   1117   EXPECT_EQ(OK, rv);
   1118   EXPECT_EQ("hello world", response_data);
   1119 }
   1120 
   1121 // This test is almost the same as Ignores100 above, but the response contains
   1122 // a 102 instead of a 100. Also, instead of HTTP/1.0 the response is
   1123 // HTTP/1.1 and the two status headers are read in one read.
   1124 TEST_P(HttpNetworkTransactionTest, Ignores1xx) {
   1125   HttpRequestInfo request;
   1126   request.method = "GET";
   1127   request.url = GURL("http://www.foo.com/");
   1128   request.load_flags = 0;
   1129 
   1130   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1131   scoped_ptr<HttpTransaction> trans(
   1132       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1133 
   1134   MockRead data_reads[] = {
   1135     MockRead("HTTP/1.1 102 Unspecified status code\r\n\r\n"
   1136              "HTTP/1.1 200 OK\r\n\r\n"),
   1137     MockRead("hello world"),
   1138     MockRead(SYNCHRONOUS, OK),
   1139   };
   1140   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1141   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1142 
   1143   TestCompletionCallback callback;
   1144 
   1145   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1146   EXPECT_EQ(ERR_IO_PENDING, rv);
   1147 
   1148   rv = callback.WaitForResult();
   1149   EXPECT_EQ(OK, rv);
   1150 
   1151   const HttpResponseInfo* response = trans->GetResponseInfo();
   1152   ASSERT_TRUE(response != NULL);
   1153 
   1154   EXPECT_TRUE(response->headers.get() != NULL);
   1155   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   1156 
   1157   std::string response_data;
   1158   rv = ReadTransaction(trans.get(), &response_data);
   1159   EXPECT_EQ(OK, rv);
   1160   EXPECT_EQ("hello world", response_data);
   1161 }
   1162 
   1163 TEST_P(HttpNetworkTransactionTest, Incomplete100ThenEOF) {
   1164   HttpRequestInfo request;
   1165   request.method = "POST";
   1166   request.url = GURL("http://www.foo.com/");
   1167   request.load_flags = 0;
   1168 
   1169   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1170   scoped_ptr<HttpTransaction> trans(
   1171       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1172 
   1173   MockRead data_reads[] = {
   1174     MockRead(SYNCHRONOUS, "HTTP/1.0 100 Continue\r\n"),
   1175     MockRead(ASYNC, 0),
   1176   };
   1177   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1178   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1179 
   1180   TestCompletionCallback callback;
   1181 
   1182   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1183   EXPECT_EQ(ERR_IO_PENDING, rv);
   1184 
   1185   rv = callback.WaitForResult();
   1186   EXPECT_EQ(OK, rv);
   1187 
   1188   std::string response_data;
   1189   rv = ReadTransaction(trans.get(), &response_data);
   1190   EXPECT_EQ(OK, rv);
   1191   EXPECT_EQ("", response_data);
   1192 }
   1193 
   1194 TEST_P(HttpNetworkTransactionTest, EmptyResponse) {
   1195   HttpRequestInfo request;
   1196   request.method = "POST";
   1197   request.url = GURL("http://www.foo.com/");
   1198   request.load_flags = 0;
   1199 
   1200   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1201   scoped_ptr<HttpTransaction> trans(
   1202       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1203 
   1204 
   1205   MockRead data_reads[] = {
   1206     MockRead(ASYNC, 0),
   1207   };
   1208   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1209   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1210 
   1211   TestCompletionCallback callback;
   1212 
   1213   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1214   EXPECT_EQ(ERR_IO_PENDING, rv);
   1215 
   1216   rv = callback.WaitForResult();
   1217   EXPECT_EQ(ERR_EMPTY_RESPONSE, rv);
   1218 }
   1219 
   1220 void HttpNetworkTransactionTest::KeepAliveConnectionResendRequestTest(
   1221     const MockWrite* write_failure,
   1222     const MockRead* read_failure) {
   1223   HttpRequestInfo request;
   1224   request.method = "GET";
   1225   request.url = GURL("http://www.foo.com/");
   1226   request.load_flags = 0;
   1227 
   1228   CapturingNetLog net_log;
   1229   session_deps_.net_log = &net_log;
   1230   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1231 
   1232   // Written data for successfully sending both requests.
   1233   MockWrite data1_writes[] = {
   1234     MockWrite("GET / HTTP/1.1\r\n"
   1235               "Host: www.foo.com\r\n"
   1236               "Connection: keep-alive\r\n\r\n"),
   1237     MockWrite("GET / HTTP/1.1\r\n"
   1238               "Host: www.foo.com\r\n"
   1239               "Connection: keep-alive\r\n\r\n")
   1240   };
   1241 
   1242   // Read results for the first request.
   1243   MockRead data1_reads[] = {
   1244     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n"),
   1245     MockRead("hello"),
   1246     MockRead(ASYNC, OK),
   1247   };
   1248 
   1249   if (write_failure) {
   1250     ASSERT_FALSE(read_failure);
   1251     data1_writes[1] = *write_failure;
   1252   } else {
   1253     ASSERT_TRUE(read_failure);
   1254     data1_reads[2] = *read_failure;
   1255   }
   1256 
   1257   StaticSocketDataProvider data1(data1_reads, arraysize(data1_reads),
   1258                                  data1_writes, arraysize(data1_writes));
   1259   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   1260 
   1261   MockRead data2_reads[] = {
   1262     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n"),
   1263     MockRead("world"),
   1264     MockRead(ASYNC, OK),
   1265   };
   1266   StaticSocketDataProvider data2(data2_reads, arraysize(data2_reads), NULL, 0);
   1267   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   1268 
   1269   const char* kExpectedResponseData[] = {
   1270     "hello", "world"
   1271   };
   1272 
   1273   uint32 first_socket_log_id = NetLog::Source::kInvalidId;
   1274   for (int i = 0; i < 2; ++i) {
   1275     TestCompletionCallback callback;
   1276 
   1277     scoped_ptr<HttpTransaction> trans(
   1278         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1279 
   1280     int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1281     EXPECT_EQ(ERR_IO_PENDING, rv);
   1282 
   1283     rv = callback.WaitForResult();
   1284     EXPECT_EQ(OK, rv);
   1285 
   1286     LoadTimingInfo load_timing_info;
   1287     EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   1288     TestLoadTimingNotReused(load_timing_info, CONNECT_TIMING_HAS_DNS_TIMES);
   1289     if (i == 0) {
   1290       first_socket_log_id = load_timing_info.socket_log_id;
   1291     } else {
   1292       // The second request should be using a new socket.
   1293       EXPECT_NE(first_socket_log_id, load_timing_info.socket_log_id);
   1294     }
   1295 
   1296     const HttpResponseInfo* response = trans->GetResponseInfo();
   1297     ASSERT_TRUE(response != NULL);
   1298 
   1299     EXPECT_TRUE(response->headers.get() != NULL);
   1300     EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   1301 
   1302     std::string response_data;
   1303     rv = ReadTransaction(trans.get(), &response_data);
   1304     EXPECT_EQ(OK, rv);
   1305     EXPECT_EQ(kExpectedResponseData[i], response_data);
   1306   }
   1307 }
   1308 
   1309 void HttpNetworkTransactionTest::PreconnectErrorResendRequestTest(
   1310     const MockWrite* write_failure,
   1311     const MockRead* read_failure,
   1312     bool use_spdy) {
   1313   HttpRequestInfo request;
   1314   request.method = "GET";
   1315   request.url = GURL("https://www.foo.com/");
   1316   request.load_flags = 0;
   1317 
   1318   CapturingNetLog net_log;
   1319   session_deps_.net_log = &net_log;
   1320   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1321 
   1322   SSLSocketDataProvider ssl1(ASYNC, OK);
   1323   SSLSocketDataProvider ssl2(ASYNC, OK);
   1324   if (use_spdy) {
   1325     ssl1.SetNextProto(GetParam());
   1326     ssl2.SetNextProto(GetParam());
   1327   }
   1328   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl1);
   1329   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl2);
   1330 
   1331   // SPDY versions of the request and response.
   1332   scoped_ptr<SpdyFrame> spdy_request(spdy_util_.ConstructSpdyGet(
   1333       request.url.spec().c_str(), false, 1, DEFAULT_PRIORITY));
   1334   scoped_ptr<SpdyFrame> spdy_response(
   1335       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   1336   scoped_ptr<SpdyFrame> spdy_data(
   1337       spdy_util_.ConstructSpdyBodyFrame(1, "hello", 5, true));
   1338 
   1339   // HTTP/1.1 versions of the request and response.
   1340   const char kHttpRequest[] = "GET / HTTP/1.1\r\n"
   1341       "Host: www.foo.com\r\n"
   1342       "Connection: keep-alive\r\n\r\n";
   1343   const char kHttpResponse[] = "HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n";
   1344   const char kHttpData[] = "hello";
   1345 
   1346   std::vector<MockRead> data1_reads;
   1347   std::vector<MockWrite> data1_writes;
   1348   if (write_failure) {
   1349     ASSERT_FALSE(read_failure);
   1350     data1_writes.push_back(*write_failure);
   1351     data1_reads.push_back(MockRead(ASYNC, OK));
   1352   } else {
   1353     ASSERT_TRUE(read_failure);
   1354     if (use_spdy) {
   1355       data1_writes.push_back(CreateMockWrite(*spdy_request));
   1356     } else {
   1357       data1_writes.push_back(MockWrite(kHttpRequest));
   1358     }
   1359     data1_reads.push_back(*read_failure);
   1360   }
   1361 
   1362   StaticSocketDataProvider data1(&data1_reads[0], data1_reads.size(),
   1363                                  &data1_writes[0], data1_writes.size());
   1364   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   1365 
   1366   std::vector<MockRead> data2_reads;
   1367   std::vector<MockWrite> data2_writes;
   1368 
   1369   if (use_spdy) {
   1370     data2_writes.push_back(CreateMockWrite(*spdy_request, 0, ASYNC));
   1371 
   1372     data2_reads.push_back(CreateMockRead(*spdy_response, 1, ASYNC));
   1373     data2_reads.push_back(CreateMockRead(*spdy_data, 2, ASYNC));
   1374     data2_reads.push_back(MockRead(ASYNC, OK, 3));
   1375   } else {
   1376     data2_writes.push_back(
   1377         MockWrite(ASYNC, kHttpRequest, strlen(kHttpRequest), 0));
   1378 
   1379     data2_reads.push_back(
   1380         MockRead(ASYNC, kHttpResponse, strlen(kHttpResponse), 1));
   1381     data2_reads.push_back(MockRead(ASYNC, kHttpData, strlen(kHttpData), 2));
   1382     data2_reads.push_back(MockRead(ASYNC, OK, 3));
   1383   }
   1384   OrderedSocketData data2(&data2_reads[0], data2_reads.size(),
   1385                           &data2_writes[0], data2_writes.size());
   1386   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   1387 
   1388   // Preconnect a socket.
   1389   net::SSLConfig ssl_config;
   1390   session->ssl_config_service()->GetSSLConfig(&ssl_config);
   1391   session->GetNextProtos(&ssl_config.next_protos);
   1392   session->http_stream_factory()->PreconnectStreams(
   1393       1, request, DEFAULT_PRIORITY, ssl_config, ssl_config);
   1394   // Wait for the preconnect to complete.
   1395   // TODO(davidben): Some way to wait for an idle socket count might be handy.
   1396   base::RunLoop().RunUntilIdle();
   1397   EXPECT_EQ(1, GetIdleSocketCountInSSLSocketPool(session.get()));
   1398 
   1399   // Make the request.
   1400   TestCompletionCallback callback;
   1401 
   1402   scoped_ptr<HttpTransaction> trans(
   1403       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1404 
   1405   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1406   EXPECT_EQ(ERR_IO_PENDING, rv);
   1407 
   1408   rv = callback.WaitForResult();
   1409   EXPECT_EQ(OK, rv);
   1410 
   1411   LoadTimingInfo load_timing_info;
   1412   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   1413   TestLoadTimingNotReused(
   1414       load_timing_info,
   1415       CONNECT_TIMING_HAS_DNS_TIMES|CONNECT_TIMING_HAS_SSL_TIMES);
   1416 
   1417   const HttpResponseInfo* response = trans->GetResponseInfo();
   1418   ASSERT_TRUE(response != NULL);
   1419 
   1420   EXPECT_TRUE(response->headers.get() != NULL);
   1421   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   1422 
   1423   std::string response_data;
   1424   rv = ReadTransaction(trans.get(), &response_data);
   1425   EXPECT_EQ(OK, rv);
   1426   EXPECT_EQ(kHttpData, response_data);
   1427 }
   1428 
   1429 TEST_P(HttpNetworkTransactionTest,
   1430        KeepAliveConnectionNotConnectedOnWrite) {
   1431   MockWrite write_failure(ASYNC, ERR_SOCKET_NOT_CONNECTED);
   1432   KeepAliveConnectionResendRequestTest(&write_failure, NULL);
   1433 }
   1434 
   1435 TEST_P(HttpNetworkTransactionTest, KeepAliveConnectionReset) {
   1436   MockRead read_failure(ASYNC, ERR_CONNECTION_RESET);
   1437   KeepAliveConnectionResendRequestTest(NULL, &read_failure);
   1438 }
   1439 
   1440 TEST_P(HttpNetworkTransactionTest, KeepAliveConnectionEOF) {
   1441   MockRead read_failure(SYNCHRONOUS, OK);  // EOF
   1442   KeepAliveConnectionResendRequestTest(NULL, &read_failure);
   1443 }
   1444 
   1445 // Make sure that on a 408 response (Request Timeout), the request is retried,
   1446 // if the socket was a reused keep alive socket.
   1447 TEST_P(HttpNetworkTransactionTest, KeepAlive408) {
   1448   MockRead read_failure(SYNCHRONOUS,
   1449                         "HTTP/1.1 408 Request Timeout\r\n"
   1450                         "Connection: Keep-Alive\r\n"
   1451                         "Content-Length: 6\r\n\r\n"
   1452                         "Pickle");
   1453   KeepAliveConnectionResendRequestTest(NULL, &read_failure);
   1454 }
   1455 
   1456 TEST_P(HttpNetworkTransactionTest,
   1457        PreconnectErrorNotConnectedOnWrite) {
   1458   MockWrite write_failure(ASYNC, ERR_SOCKET_NOT_CONNECTED);
   1459   PreconnectErrorResendRequestTest(&write_failure, NULL, false);
   1460 }
   1461 
   1462 TEST_P(HttpNetworkTransactionTest, PreconnectErrorReset) {
   1463   MockRead read_failure(ASYNC, ERR_CONNECTION_RESET);
   1464   PreconnectErrorResendRequestTest(NULL, &read_failure, false);
   1465 }
   1466 
   1467 TEST_P(HttpNetworkTransactionTest, PreconnectErrorEOF) {
   1468   MockRead read_failure(SYNCHRONOUS, OK);  // EOF
   1469   PreconnectErrorResendRequestTest(NULL, &read_failure, false);
   1470 }
   1471 
   1472 TEST_P(HttpNetworkTransactionTest, PreconnectErrorAsyncEOF) {
   1473   MockRead read_failure(ASYNC, OK);  // EOF
   1474   PreconnectErrorResendRequestTest(NULL, &read_failure, false);
   1475 }
   1476 
   1477 // Make sure that on a 408 response (Request Timeout), the request is retried,
   1478 // if the socket was a preconnected (UNUSED_IDLE) socket.
   1479 TEST_P(HttpNetworkTransactionTest, RetryOnIdle408) {
   1480   MockRead read_failure(SYNCHRONOUS,
   1481                         "HTTP/1.1 408 Request Timeout\r\n"
   1482                         "Connection: Keep-Alive\r\n"
   1483                         "Content-Length: 6\r\n\r\n"
   1484                         "Pickle");
   1485   KeepAliveConnectionResendRequestTest(NULL, &read_failure);
   1486   PreconnectErrorResendRequestTest(NULL, &read_failure, false);
   1487 }
   1488 
   1489 TEST_P(HttpNetworkTransactionTest,
   1490        SpdyPreconnectErrorNotConnectedOnWrite) {
   1491   MockWrite write_failure(ASYNC, ERR_SOCKET_NOT_CONNECTED);
   1492   PreconnectErrorResendRequestTest(&write_failure, NULL, true);
   1493 }
   1494 
   1495 TEST_P(HttpNetworkTransactionTest, SpdyPreconnectErrorReset) {
   1496   MockRead read_failure(ASYNC, ERR_CONNECTION_RESET);
   1497   PreconnectErrorResendRequestTest(NULL, &read_failure, true);
   1498 }
   1499 
   1500 TEST_P(HttpNetworkTransactionTest, SpdyPreconnectErrorEOF) {
   1501   MockRead read_failure(SYNCHRONOUS, OK);  // EOF
   1502   PreconnectErrorResendRequestTest(NULL, &read_failure, true);
   1503 }
   1504 
   1505 TEST_P(HttpNetworkTransactionTest, SpdyPreconnectErrorAsyncEOF) {
   1506   MockRead read_failure(ASYNC, OK);  // EOF
   1507   PreconnectErrorResendRequestTest(NULL, &read_failure, true);
   1508 }
   1509 
   1510 TEST_P(HttpNetworkTransactionTest, NonKeepAliveConnectionReset) {
   1511   HttpRequestInfo request;
   1512   request.method = "GET";
   1513   request.url = GURL("http://www.google.com/");
   1514   request.load_flags = 0;
   1515 
   1516   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1517   scoped_ptr<HttpTransaction> trans(
   1518       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1519 
   1520   MockRead data_reads[] = {
   1521     MockRead(ASYNC, ERR_CONNECTION_RESET),
   1522     MockRead("HTTP/1.0 200 OK\r\n\r\n"),  // Should not be used
   1523     MockRead("hello world"),
   1524     MockRead(SYNCHRONOUS, OK),
   1525   };
   1526   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1527   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1528 
   1529   TestCompletionCallback callback;
   1530 
   1531   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1532   EXPECT_EQ(ERR_IO_PENDING, rv);
   1533 
   1534   rv = callback.WaitForResult();
   1535   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   1536 
   1537   const HttpResponseInfo* response = trans->GetResponseInfo();
   1538   EXPECT_TRUE(response == NULL);
   1539 }
   1540 
   1541 // What do various browsers do when the server closes a non-keepalive
   1542 // connection without sending any response header or body?
   1543 //
   1544 // IE7: error page
   1545 // Safari 3.1.2 (Windows): error page
   1546 // Firefox 3.0.1: blank page
   1547 // Opera 9.52: after five attempts, blank page
   1548 // Us with WinHTTP: error page (ERR_INVALID_RESPONSE)
   1549 // Us: error page (EMPTY_RESPONSE)
   1550 TEST_P(HttpNetworkTransactionTest, NonKeepAliveConnectionEOF) {
   1551   MockRead data_reads[] = {
   1552     MockRead(SYNCHRONOUS, OK),  // EOF
   1553     MockRead("HTTP/1.0 200 OK\r\n\r\n"),  // Should not be used
   1554     MockRead("hello world"),
   1555     MockRead(SYNCHRONOUS, OK),
   1556   };
   1557   SimpleGetHelperResult out = SimpleGetHelper(data_reads,
   1558                                               arraysize(data_reads));
   1559   EXPECT_EQ(ERR_EMPTY_RESPONSE, out.rv);
   1560 }
   1561 
   1562 // Test that network access can be deferred and resumed.
   1563 TEST_P(HttpNetworkTransactionTest, ThrottleBeforeNetworkStart) {
   1564   HttpRequestInfo request;
   1565   request.method = "GET";
   1566   request.url = GURL("http://www.google.com/");
   1567   request.load_flags = 0;
   1568 
   1569   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1570   scoped_ptr<HttpTransaction> trans(
   1571       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1572 
   1573   // Defer on OnBeforeNetworkStart.
   1574   BeforeNetworkStartHandler net_start_handler(true);  // defer
   1575   trans->SetBeforeNetworkStartCallback(
   1576       base::Bind(&BeforeNetworkStartHandler::OnBeforeNetworkStart,
   1577                  base::Unretained(&net_start_handler)));
   1578 
   1579   MockRead data_reads[] = {
   1580     MockRead("HTTP/1.0 200 OK\r\n"),
   1581     MockRead("Content-Length: 5\r\n\r\n"),
   1582     MockRead("hello"),
   1583     MockRead(SYNCHRONOUS, 0),
   1584   };
   1585   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1586   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1587 
   1588   TestCompletionCallback callback;
   1589 
   1590   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1591   EXPECT_EQ(ERR_IO_PENDING, rv);
   1592   base::MessageLoop::current()->RunUntilIdle();
   1593 
   1594   // Should have deferred for network start.
   1595   EXPECT_TRUE(net_start_handler.observed_before_network_start());
   1596   EXPECT_EQ(LOAD_STATE_WAITING_FOR_DELEGATE, trans->GetLoadState());
   1597   EXPECT_TRUE(trans->GetResponseInfo() == NULL);
   1598 
   1599   trans->ResumeNetworkStart();
   1600   rv = callback.WaitForResult();
   1601   EXPECT_EQ(OK, rv);
   1602   EXPECT_TRUE(trans->GetResponseInfo() != NULL);
   1603 
   1604   scoped_refptr<IOBufferWithSize> io_buf(new IOBufferWithSize(100));
   1605   rv = trans->Read(io_buf.get(), io_buf->size(), callback.callback());
   1606   if (rv == ERR_IO_PENDING)
   1607     rv = callback.WaitForResult();
   1608   EXPECT_EQ(5, rv);
   1609   trans.reset();
   1610 }
   1611 
   1612 // Test that network use can be deferred and canceled.
   1613 TEST_P(HttpNetworkTransactionTest, ThrottleAndCancelBeforeNetworkStart) {
   1614   HttpRequestInfo request;
   1615   request.method = "GET";
   1616   request.url = GURL("http://www.google.com/");
   1617   request.load_flags = 0;
   1618 
   1619   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1620   scoped_ptr<HttpTransaction> trans(
   1621       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1622 
   1623   // Defer on OnBeforeNetworkStart.
   1624   BeforeNetworkStartHandler net_start_handler(true);  // defer
   1625   trans->SetBeforeNetworkStartCallback(
   1626       base::Bind(&BeforeNetworkStartHandler::OnBeforeNetworkStart,
   1627                  base::Unretained(&net_start_handler)));
   1628 
   1629   TestCompletionCallback callback;
   1630 
   1631   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1632   EXPECT_EQ(ERR_IO_PENDING, rv);
   1633   base::MessageLoop::current()->RunUntilIdle();
   1634 
   1635   // Should have deferred for network start.
   1636   EXPECT_TRUE(net_start_handler.observed_before_network_start());
   1637   EXPECT_EQ(LOAD_STATE_WAITING_FOR_DELEGATE, trans->GetLoadState());
   1638   EXPECT_TRUE(trans->GetResponseInfo() == NULL);
   1639 }
   1640 
   1641 // Next 2 cases (KeepAliveEarlyClose and KeepAliveEarlyClose2) are regression
   1642 // tests. There was a bug causing HttpNetworkTransaction to hang in the
   1643 // destructor in such situations.
   1644 // See http://crbug.com/154712 and http://crbug.com/156609.
   1645 TEST_P(HttpNetworkTransactionTest, KeepAliveEarlyClose) {
   1646   HttpRequestInfo request;
   1647   request.method = "GET";
   1648   request.url = GURL("http://www.google.com/");
   1649   request.load_flags = 0;
   1650 
   1651   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1652   scoped_ptr<HttpTransaction> trans(
   1653       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1654 
   1655   MockRead data_reads[] = {
   1656     MockRead("HTTP/1.0 200 OK\r\n"),
   1657     MockRead("Connection: keep-alive\r\n"),
   1658     MockRead("Content-Length: 100\r\n\r\n"),
   1659     MockRead("hello"),
   1660     MockRead(SYNCHRONOUS, 0),
   1661   };
   1662   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1663   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1664 
   1665   TestCompletionCallback callback;
   1666 
   1667   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1668   EXPECT_EQ(ERR_IO_PENDING, rv);
   1669 
   1670   rv = callback.WaitForResult();
   1671   EXPECT_EQ(OK, rv);
   1672 
   1673   scoped_refptr<IOBufferWithSize> io_buf(new IOBufferWithSize(100));
   1674   rv = trans->Read(io_buf.get(), io_buf->size(), callback.callback());
   1675   if (rv == ERR_IO_PENDING)
   1676     rv = callback.WaitForResult();
   1677   EXPECT_EQ(5, rv);
   1678   rv = trans->Read(io_buf.get(), io_buf->size(), callback.callback());
   1679   EXPECT_EQ(ERR_CONTENT_LENGTH_MISMATCH, rv);
   1680 
   1681   trans.reset();
   1682   base::MessageLoop::current()->RunUntilIdle();
   1683   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   1684 }
   1685 
   1686 TEST_P(HttpNetworkTransactionTest, KeepAliveEarlyClose2) {
   1687   HttpRequestInfo request;
   1688   request.method = "GET";
   1689   request.url = GURL("http://www.google.com/");
   1690   request.load_flags = 0;
   1691 
   1692   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1693   scoped_ptr<HttpTransaction> trans(
   1694       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1695 
   1696   MockRead data_reads[] = {
   1697     MockRead("HTTP/1.0 200 OK\r\n"),
   1698     MockRead("Connection: keep-alive\r\n"),
   1699     MockRead("Content-Length: 100\r\n\r\n"),
   1700     MockRead(SYNCHRONOUS, 0),
   1701   };
   1702   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   1703   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1704 
   1705   TestCompletionCallback callback;
   1706 
   1707   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1708   EXPECT_EQ(ERR_IO_PENDING, rv);
   1709 
   1710   rv = callback.WaitForResult();
   1711   EXPECT_EQ(OK, rv);
   1712 
   1713   scoped_refptr<IOBufferWithSize> io_buf(new IOBufferWithSize(100));
   1714   rv = trans->Read(io_buf.get(), io_buf->size(), callback.callback());
   1715   if (rv == ERR_IO_PENDING)
   1716     rv = callback.WaitForResult();
   1717   EXPECT_EQ(ERR_CONTENT_LENGTH_MISMATCH, rv);
   1718 
   1719   trans.reset();
   1720   base::MessageLoop::current()->RunUntilIdle();
   1721   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   1722 }
   1723 
   1724 // Test that we correctly reuse a keep-alive connection after not explicitly
   1725 // reading the body.
   1726 TEST_P(HttpNetworkTransactionTest, KeepAliveAfterUnreadBody) {
   1727   HttpRequestInfo request;
   1728   request.method = "GET";
   1729   request.url = GURL("http://www.foo.com/");
   1730   request.load_flags = 0;
   1731 
   1732   CapturingNetLog net_log;
   1733   session_deps_.net_log = &net_log;
   1734   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1735 
   1736   // Note that because all these reads happen in the same
   1737   // StaticSocketDataProvider, it shows that the same socket is being reused for
   1738   // all transactions.
   1739   MockRead data1_reads[] = {
   1740     MockRead("HTTP/1.1 204 No Content\r\n\r\n"),
   1741     MockRead("HTTP/1.1 205 Reset Content\r\n\r\n"),
   1742     MockRead("HTTP/1.1 304 Not Modified\r\n\r\n"),
   1743     MockRead("HTTP/1.1 302 Found\r\n"
   1744              "Content-Length: 0\r\n\r\n"),
   1745     MockRead("HTTP/1.1 302 Found\r\n"
   1746              "Content-Length: 5\r\n\r\n"
   1747              "hello"),
   1748     MockRead("HTTP/1.1 301 Moved Permanently\r\n"
   1749              "Content-Length: 0\r\n\r\n"),
   1750     MockRead("HTTP/1.1 301 Moved Permanently\r\n"
   1751              "Content-Length: 5\r\n\r\n"
   1752              "hello"),
   1753     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n"),
   1754     MockRead("hello"),
   1755   };
   1756   StaticSocketDataProvider data1(data1_reads, arraysize(data1_reads), NULL, 0);
   1757   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   1758 
   1759   MockRead data2_reads[] = {
   1760     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   1761   };
   1762   StaticSocketDataProvider data2(data2_reads, arraysize(data2_reads), NULL, 0);
   1763   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   1764 
   1765   const int kNumUnreadBodies = arraysize(data1_reads) - 2;
   1766   std::string response_lines[kNumUnreadBodies];
   1767 
   1768   uint32 first_socket_log_id = NetLog::Source::kInvalidId;
   1769   for (size_t i = 0; i < arraysize(data1_reads) - 2; ++i) {
   1770     TestCompletionCallback callback;
   1771 
   1772     scoped_ptr<HttpTransaction> trans(
   1773         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1774 
   1775     int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1776     EXPECT_EQ(ERR_IO_PENDING, rv);
   1777 
   1778     rv = callback.WaitForResult();
   1779     EXPECT_EQ(OK, rv);
   1780 
   1781     LoadTimingInfo load_timing_info;
   1782     EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   1783     if (i == 0) {
   1784       TestLoadTimingNotReused(load_timing_info, CONNECT_TIMING_HAS_DNS_TIMES);
   1785       first_socket_log_id = load_timing_info.socket_log_id;
   1786     } else {
   1787       TestLoadTimingReused(load_timing_info);
   1788       EXPECT_EQ(first_socket_log_id, load_timing_info.socket_log_id);
   1789     }
   1790 
   1791     const HttpResponseInfo* response = trans->GetResponseInfo();
   1792     ASSERT_TRUE(response != NULL);
   1793 
   1794     ASSERT_TRUE(response->headers.get() != NULL);
   1795     response_lines[i] = response->headers->GetStatusLine();
   1796 
   1797     // We intentionally don't read the response bodies.
   1798   }
   1799 
   1800   const char* const kStatusLines[] = {
   1801     "HTTP/1.1 204 No Content",
   1802     "HTTP/1.1 205 Reset Content",
   1803     "HTTP/1.1 304 Not Modified",
   1804     "HTTP/1.1 302 Found",
   1805     "HTTP/1.1 302 Found",
   1806     "HTTP/1.1 301 Moved Permanently",
   1807     "HTTP/1.1 301 Moved Permanently",
   1808   };
   1809 
   1810   COMPILE_ASSERT(kNumUnreadBodies == arraysize(kStatusLines),
   1811                  forgot_to_update_kStatusLines);
   1812 
   1813   for (int i = 0; i < kNumUnreadBodies; ++i)
   1814     EXPECT_EQ(kStatusLines[i], response_lines[i]);
   1815 
   1816   TestCompletionCallback callback;
   1817   scoped_ptr<HttpTransaction> trans(
   1818       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   1819   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1820   EXPECT_EQ(ERR_IO_PENDING, rv);
   1821   rv = callback.WaitForResult();
   1822   EXPECT_EQ(OK, rv);
   1823   const HttpResponseInfo* response = trans->GetResponseInfo();
   1824   ASSERT_TRUE(response != NULL);
   1825   ASSERT_TRUE(response->headers.get() != NULL);
   1826   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   1827   std::string response_data;
   1828   rv = ReadTransaction(trans.get(), &response_data);
   1829   EXPECT_EQ(OK, rv);
   1830   EXPECT_EQ("hello", response_data);
   1831 }
   1832 
   1833 // Test the request-challenge-retry sequence for basic auth.
   1834 // (basic auth is the easiest to mock, because it has no randomness).
   1835 TEST_P(HttpNetworkTransactionTest, BasicAuth) {
   1836   HttpRequestInfo request;
   1837   request.method = "GET";
   1838   request.url = GURL("http://www.google.com/");
   1839   request.load_flags = 0;
   1840 
   1841   CapturingNetLog log;
   1842   session_deps_.net_log = &log;
   1843   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1844   scoped_ptr<HttpTransaction> trans(
   1845       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1846 
   1847   MockWrite data_writes1[] = {
   1848     MockWrite("GET / HTTP/1.1\r\n"
   1849               "Host: www.google.com\r\n"
   1850               "Connection: keep-alive\r\n\r\n"),
   1851   };
   1852 
   1853   MockRead data_reads1[] = {
   1854     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   1855     // Give a couple authenticate options (only the middle one is actually
   1856     // supported).
   1857     MockRead("WWW-Authenticate: Basic invalid\r\n"),  // Malformed.
   1858     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   1859     MockRead("WWW-Authenticate: UNSUPPORTED realm=\"FOO\"\r\n"),
   1860     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   1861     // Large content-length -- won't matter, as connection will be reset.
   1862     MockRead("Content-Length: 10000\r\n\r\n"),
   1863     MockRead(SYNCHRONOUS, ERR_FAILED),
   1864   };
   1865 
   1866   // After calling trans->RestartWithAuth(), this is the request we should
   1867   // be issuing -- the final header line contains the credentials.
   1868   MockWrite data_writes2[] = {
   1869     MockWrite("GET / HTTP/1.1\r\n"
   1870               "Host: www.google.com\r\n"
   1871               "Connection: keep-alive\r\n"
   1872               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   1873   };
   1874 
   1875   // Lastly, the server responds with the actual content.
   1876   MockRead data_reads2[] = {
   1877     MockRead("HTTP/1.0 200 OK\r\n"),
   1878     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   1879     MockRead("Content-Length: 100\r\n\r\n"),
   1880     MockRead(SYNCHRONOUS, OK),
   1881   };
   1882 
   1883   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   1884                                  data_writes1, arraysize(data_writes1));
   1885   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   1886                                  data_writes2, arraysize(data_writes2));
   1887   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   1888   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   1889 
   1890   TestCompletionCallback callback1;
   1891 
   1892   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   1893   EXPECT_EQ(ERR_IO_PENDING, rv);
   1894 
   1895   rv = callback1.WaitForResult();
   1896   EXPECT_EQ(OK, rv);
   1897 
   1898   LoadTimingInfo load_timing_info1;
   1899   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info1));
   1900   TestLoadTimingNotReused(load_timing_info1, CONNECT_TIMING_HAS_DNS_TIMES);
   1901 
   1902   int64 reads_size1 = ReadsSize(data_reads1, arraysize(data_reads1));
   1903   EXPECT_EQ(reads_size1, trans->GetTotalReceivedBytes());
   1904 
   1905   const HttpResponseInfo* response = trans->GetResponseInfo();
   1906   ASSERT_TRUE(response != NULL);
   1907   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   1908 
   1909   TestCompletionCallback callback2;
   1910 
   1911   rv = trans->RestartWithAuth(
   1912       AuthCredentials(kFoo, kBar), callback2.callback());
   1913   EXPECT_EQ(ERR_IO_PENDING, rv);
   1914 
   1915   rv = callback2.WaitForResult();
   1916   EXPECT_EQ(OK, rv);
   1917 
   1918   LoadTimingInfo load_timing_info2;
   1919   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info2));
   1920   TestLoadTimingNotReused(load_timing_info2, CONNECT_TIMING_HAS_DNS_TIMES);
   1921   // The load timing after restart should have a new socket ID, and times after
   1922   // those of the first load timing.
   1923   EXPECT_LE(load_timing_info1.receive_headers_end,
   1924             load_timing_info2.connect_timing.connect_start);
   1925   EXPECT_NE(load_timing_info1.socket_log_id, load_timing_info2.socket_log_id);
   1926 
   1927   int64 reads_size2 = ReadsSize(data_reads2, arraysize(data_reads2));
   1928   EXPECT_EQ(reads_size1 + reads_size2, trans->GetTotalReceivedBytes());
   1929 
   1930   response = trans->GetResponseInfo();
   1931   ASSERT_TRUE(response != NULL);
   1932   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   1933   EXPECT_EQ(100, response->headers->GetContentLength());
   1934 }
   1935 
   1936 TEST_P(HttpNetworkTransactionTest, DoNotSendAuth) {
   1937   HttpRequestInfo request;
   1938   request.method = "GET";
   1939   request.url = GURL("http://www.google.com/");
   1940   request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA;
   1941 
   1942   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1943   scoped_ptr<HttpTransaction> trans(
   1944       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   1945 
   1946   MockWrite data_writes[] = {
   1947     MockWrite("GET / HTTP/1.1\r\n"
   1948               "Host: www.google.com\r\n"
   1949               "Connection: keep-alive\r\n\r\n"),
   1950   };
   1951 
   1952   MockRead data_reads[] = {
   1953     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   1954     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   1955     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   1956     // Large content-length -- won't matter, as connection will be reset.
   1957     MockRead("Content-Length: 10000\r\n\r\n"),
   1958     MockRead(SYNCHRONOUS, ERR_FAILED),
   1959   };
   1960 
   1961   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   1962                                 data_writes, arraysize(data_writes));
   1963   session_deps_.socket_factory->AddSocketDataProvider(&data);
   1964   TestCompletionCallback callback;
   1965 
   1966   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   1967   EXPECT_EQ(ERR_IO_PENDING, rv);
   1968 
   1969   rv = callback.WaitForResult();
   1970   EXPECT_EQ(0, rv);
   1971 
   1972   int64 reads_size = ReadsSize(data_reads, arraysize(data_reads));
   1973   EXPECT_EQ(reads_size, trans->GetTotalReceivedBytes());
   1974 
   1975   const HttpResponseInfo* response = trans->GetResponseInfo();
   1976   ASSERT_TRUE(response != NULL);
   1977   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   1978 }
   1979 
   1980 // Test the request-challenge-retry sequence for basic auth, over a keep-alive
   1981 // connection.
   1982 TEST_P(HttpNetworkTransactionTest, BasicAuthKeepAlive) {
   1983   HttpRequestInfo request;
   1984   request.method = "GET";
   1985   request.url = GURL("http://www.google.com/");
   1986   request.load_flags = 0;
   1987 
   1988   CapturingNetLog log;
   1989   session_deps_.net_log = &log;
   1990   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   1991 
   1992   MockWrite data_writes1[] = {
   1993     MockWrite("GET / HTTP/1.1\r\n"
   1994               "Host: www.google.com\r\n"
   1995               "Connection: keep-alive\r\n\r\n"),
   1996 
   1997     // After calling trans->RestartWithAuth(), this is the request we should
   1998     // be issuing -- the final header line contains the credentials.
   1999     MockWrite("GET / HTTP/1.1\r\n"
   2000               "Host: www.google.com\r\n"
   2001               "Connection: keep-alive\r\n"
   2002               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   2003   };
   2004 
   2005   MockRead data_reads1[] = {
   2006     MockRead("HTTP/1.1 401 Unauthorized\r\n"),
   2007     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2008     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2009     MockRead("Content-Length: 14\r\n\r\n"),
   2010     MockRead("Unauthorized\r\n"),
   2011 
   2012     // Lastly, the server responds with the actual content.
   2013     MockRead("HTTP/1.1 200 OK\r\n"),
   2014     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2015     MockRead("Content-Length: 5\r\n\r\n"),
   2016     MockRead("Hello"),
   2017   };
   2018 
   2019   // If there is a regression where we disconnect a Keep-Alive
   2020   // connection during an auth roundtrip, we'll end up reading this.
   2021   MockRead data_reads2[] = {
   2022     MockRead(SYNCHRONOUS, ERR_FAILED),
   2023   };
   2024 
   2025   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2026                                  data_writes1, arraysize(data_writes1));
   2027   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   2028                                  NULL, 0);
   2029   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2030   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   2031 
   2032   TestCompletionCallback callback1;
   2033 
   2034   scoped_ptr<HttpTransaction> trans(
   2035       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2036   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   2037   EXPECT_EQ(ERR_IO_PENDING, rv);
   2038 
   2039   rv = callback1.WaitForResult();
   2040   EXPECT_EQ(OK, rv);
   2041 
   2042   LoadTimingInfo load_timing_info1;
   2043   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info1));
   2044   TestLoadTimingNotReused(load_timing_info1, CONNECT_TIMING_HAS_DNS_TIMES);
   2045 
   2046   const HttpResponseInfo* response = trans->GetResponseInfo();
   2047   ASSERT_TRUE(response != NULL);
   2048   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   2049 
   2050   TestCompletionCallback callback2;
   2051 
   2052   rv = trans->RestartWithAuth(
   2053       AuthCredentials(kFoo, kBar), callback2.callback());
   2054   EXPECT_EQ(ERR_IO_PENDING, rv);
   2055 
   2056   rv = callback2.WaitForResult();
   2057   EXPECT_EQ(OK, rv);
   2058 
   2059   LoadTimingInfo load_timing_info2;
   2060   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info2));
   2061   TestLoadTimingReused(load_timing_info2);
   2062   // The load timing after restart should have the same socket ID, and times
   2063   // those of the first load timing.
   2064   EXPECT_LE(load_timing_info1.receive_headers_end,
   2065             load_timing_info2.send_start);
   2066   EXPECT_EQ(load_timing_info1.socket_log_id, load_timing_info2.socket_log_id);
   2067 
   2068   response = trans->GetResponseInfo();
   2069   ASSERT_TRUE(response != NULL);
   2070   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   2071   EXPECT_EQ(5, response->headers->GetContentLength());
   2072 
   2073   std::string response_data;
   2074   rv = ReadTransaction(trans.get(), &response_data);
   2075   EXPECT_EQ(OK, rv);
   2076   int64 reads_size1 = ReadsSize(data_reads1, arraysize(data_reads1));
   2077   EXPECT_EQ(reads_size1, trans->GetTotalReceivedBytes());
   2078 }
   2079 
   2080 // Test the request-challenge-retry sequence for basic auth, over a keep-alive
   2081 // connection and with no response body to drain.
   2082 TEST_P(HttpNetworkTransactionTest, BasicAuthKeepAliveNoBody) {
   2083   HttpRequestInfo request;
   2084   request.method = "GET";
   2085   request.url = GURL("http://www.google.com/");
   2086   request.load_flags = 0;
   2087 
   2088   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2089 
   2090   MockWrite data_writes1[] = {
   2091     MockWrite("GET / HTTP/1.1\r\n"
   2092               "Host: www.google.com\r\n"
   2093               "Connection: keep-alive\r\n\r\n"),
   2094 
   2095     // After calling trans->RestartWithAuth(), this is the request we should
   2096     // be issuing -- the final header line contains the credentials.
   2097     MockWrite("GET / HTTP/1.1\r\n"
   2098               "Host: www.google.com\r\n"
   2099               "Connection: keep-alive\r\n"
   2100               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   2101   };
   2102 
   2103   MockRead data_reads1[] = {
   2104     MockRead("HTTP/1.1 401 Unauthorized\r\n"),
   2105     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2106     MockRead("Content-Length: 0\r\n\r\n"),  // No response body.
   2107 
   2108     // Lastly, the server responds with the actual content.
   2109     MockRead("HTTP/1.1 200 OK\r\n"),
   2110     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2111     MockRead("Content-Length: 5\r\n\r\n"),
   2112     MockRead("hello"),
   2113   };
   2114 
   2115   // An incorrect reconnect would cause this to be read.
   2116   MockRead data_reads2[] = {
   2117     MockRead(SYNCHRONOUS, ERR_FAILED),
   2118   };
   2119 
   2120   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2121                                  data_writes1, arraysize(data_writes1));
   2122   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   2123                                  NULL, 0);
   2124   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2125   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   2126 
   2127   TestCompletionCallback callback1;
   2128 
   2129   scoped_ptr<HttpTransaction> trans(
   2130       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2131   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   2132   EXPECT_EQ(ERR_IO_PENDING, rv);
   2133 
   2134   rv = callback1.WaitForResult();
   2135   EXPECT_EQ(OK, rv);
   2136 
   2137   const HttpResponseInfo* response = trans->GetResponseInfo();
   2138   ASSERT_TRUE(response != NULL);
   2139   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   2140 
   2141   TestCompletionCallback callback2;
   2142 
   2143   rv = trans->RestartWithAuth(
   2144       AuthCredentials(kFoo, kBar), callback2.callback());
   2145   EXPECT_EQ(ERR_IO_PENDING, rv);
   2146 
   2147   rv = callback2.WaitForResult();
   2148   EXPECT_EQ(OK, rv);
   2149 
   2150   response = trans->GetResponseInfo();
   2151   ASSERT_TRUE(response != NULL);
   2152   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   2153   EXPECT_EQ(5, response->headers->GetContentLength());
   2154 }
   2155 
   2156 // Test the request-challenge-retry sequence for basic auth, over a keep-alive
   2157 // connection and with a large response body to drain.
   2158 TEST_P(HttpNetworkTransactionTest, BasicAuthKeepAliveLargeBody) {
   2159   HttpRequestInfo request;
   2160   request.method = "GET";
   2161   request.url = GURL("http://www.google.com/");
   2162   request.load_flags = 0;
   2163 
   2164   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2165 
   2166   MockWrite data_writes1[] = {
   2167     MockWrite("GET / HTTP/1.1\r\n"
   2168               "Host: www.google.com\r\n"
   2169               "Connection: keep-alive\r\n\r\n"),
   2170 
   2171     // After calling trans->RestartWithAuth(), this is the request we should
   2172     // be issuing -- the final header line contains the credentials.
   2173     MockWrite("GET / HTTP/1.1\r\n"
   2174               "Host: www.google.com\r\n"
   2175               "Connection: keep-alive\r\n"
   2176               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   2177   };
   2178 
   2179   // Respond with 5 kb of response body.
   2180   std::string large_body_string("Unauthorized");
   2181   large_body_string.append(5 * 1024, ' ');
   2182   large_body_string.append("\r\n");
   2183 
   2184   MockRead data_reads1[] = {
   2185     MockRead("HTTP/1.1 401 Unauthorized\r\n"),
   2186     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2187     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2188     // 5134 = 12 + 5 * 1024 + 2
   2189     MockRead("Content-Length: 5134\r\n\r\n"),
   2190     MockRead(ASYNC, large_body_string.data(), large_body_string.size()),
   2191 
   2192     // Lastly, the server responds with the actual content.
   2193     MockRead("HTTP/1.1 200 OK\r\n"),
   2194     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2195     MockRead("Content-Length: 5\r\n\r\n"),
   2196     MockRead("hello"),
   2197   };
   2198 
   2199   // An incorrect reconnect would cause this to be read.
   2200   MockRead data_reads2[] = {
   2201     MockRead(SYNCHRONOUS, ERR_FAILED),
   2202   };
   2203 
   2204   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2205                                  data_writes1, arraysize(data_writes1));
   2206   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   2207                                  NULL, 0);
   2208   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2209   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   2210 
   2211   TestCompletionCallback callback1;
   2212 
   2213   scoped_ptr<HttpTransaction> trans(
   2214       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2215   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   2216   EXPECT_EQ(ERR_IO_PENDING, rv);
   2217 
   2218   rv = callback1.WaitForResult();
   2219   EXPECT_EQ(OK, rv);
   2220 
   2221   const HttpResponseInfo* response = trans->GetResponseInfo();
   2222   ASSERT_TRUE(response != NULL);
   2223   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   2224 
   2225   TestCompletionCallback callback2;
   2226 
   2227   rv = trans->RestartWithAuth(
   2228       AuthCredentials(kFoo, kBar), callback2.callback());
   2229   EXPECT_EQ(ERR_IO_PENDING, rv);
   2230 
   2231   rv = callback2.WaitForResult();
   2232   EXPECT_EQ(OK, rv);
   2233 
   2234   response = trans->GetResponseInfo();
   2235   ASSERT_TRUE(response != NULL);
   2236   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   2237   EXPECT_EQ(5, response->headers->GetContentLength());
   2238 }
   2239 
   2240 // Test the request-challenge-retry sequence for basic auth, over a keep-alive
   2241 // connection, but the server gets impatient and closes the connection.
   2242 TEST_P(HttpNetworkTransactionTest, BasicAuthKeepAliveImpatientServer) {
   2243   HttpRequestInfo request;
   2244   request.method = "GET";
   2245   request.url = GURL("http://www.google.com/");
   2246   request.load_flags = 0;
   2247 
   2248   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2249 
   2250   MockWrite data_writes1[] = {
   2251     MockWrite("GET / HTTP/1.1\r\n"
   2252               "Host: www.google.com\r\n"
   2253               "Connection: keep-alive\r\n\r\n"),
   2254     // This simulates the seemingly successful write to a closed connection
   2255     // if the bug is not fixed.
   2256     MockWrite("GET / HTTP/1.1\r\n"
   2257               "Host: www.google.com\r\n"
   2258               "Connection: keep-alive\r\n"
   2259               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   2260   };
   2261 
   2262   MockRead data_reads1[] = {
   2263     MockRead("HTTP/1.1 401 Unauthorized\r\n"),
   2264     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2265     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2266     MockRead("Content-Length: 14\r\n\r\n"),
   2267     // Tell MockTCPClientSocket to simulate the server closing the connection.
   2268     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   2269     MockRead("Unauthorized\r\n"),
   2270     MockRead(SYNCHRONOUS, OK),  // The server closes the connection.
   2271   };
   2272 
   2273   // After calling trans->RestartWithAuth(), this is the request we should
   2274   // be issuing -- the final header line contains the credentials.
   2275   MockWrite data_writes2[] = {
   2276     MockWrite("GET / HTTP/1.1\r\n"
   2277               "Host: www.google.com\r\n"
   2278               "Connection: keep-alive\r\n"
   2279               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   2280   };
   2281 
   2282   // Lastly, the server responds with the actual content.
   2283   MockRead data_reads2[] = {
   2284     MockRead("HTTP/1.1 200 OK\r\n"),
   2285     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2286     MockRead("Content-Length: 5\r\n\r\n"),
   2287     MockRead("hello"),
   2288   };
   2289 
   2290   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2291                                  data_writes1, arraysize(data_writes1));
   2292   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   2293                                  data_writes2, arraysize(data_writes2));
   2294   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2295   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   2296 
   2297   TestCompletionCallback callback1;
   2298 
   2299   scoped_ptr<HttpTransaction> trans(
   2300       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2301   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   2302   EXPECT_EQ(ERR_IO_PENDING, rv);
   2303 
   2304   rv = callback1.WaitForResult();
   2305   EXPECT_EQ(OK, rv);
   2306 
   2307   const HttpResponseInfo* response = trans->GetResponseInfo();
   2308   ASSERT_TRUE(response != NULL);
   2309   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   2310 
   2311   TestCompletionCallback callback2;
   2312 
   2313   rv = trans->RestartWithAuth(
   2314       AuthCredentials(kFoo, kBar), callback2.callback());
   2315   EXPECT_EQ(ERR_IO_PENDING, rv);
   2316 
   2317   rv = callback2.WaitForResult();
   2318   EXPECT_EQ(OK, rv);
   2319 
   2320   response = trans->GetResponseInfo();
   2321   ASSERT_TRUE(response != NULL);
   2322   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   2323   EXPECT_EQ(5, response->headers->GetContentLength());
   2324 }
   2325 
   2326 // Test the request-challenge-retry sequence for basic auth, over a connection
   2327 // that requires a restart when setting up an SSL tunnel.
   2328 TEST_P(HttpNetworkTransactionTest, BasicAuthProxyNoKeepAlive) {
   2329   HttpRequestInfo request;
   2330   request.method = "GET";
   2331   request.url = GURL("https://www.google.com/");
   2332   // when the no authentication data flag is set.
   2333   request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA;
   2334 
   2335   // Configure against proxy server "myproxy:70".
   2336   session_deps_.proxy_service.reset(
   2337       ProxyService::CreateFixedFromPacResult("PROXY myproxy:70"));
   2338   CapturingBoundNetLog log;
   2339   session_deps_.net_log = log.bound().net_log();
   2340   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2341 
   2342   // Since we have proxy, should try to establish tunnel.
   2343   MockWrite data_writes1[] = {
   2344     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2345               "Host: www.google.com\r\n"
   2346               "Proxy-Connection: keep-alive\r\n\r\n"),
   2347 
   2348     // After calling trans->RestartWithAuth(), this is the request we should
   2349     // be issuing -- the final header line contains the credentials.
   2350     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2351               "Host: www.google.com\r\n"
   2352               "Proxy-Connection: keep-alive\r\n"
   2353               "Proxy-Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   2354 
   2355     MockWrite("GET / HTTP/1.1\r\n"
   2356               "Host: www.google.com\r\n"
   2357               "Connection: keep-alive\r\n\r\n"),
   2358   };
   2359 
   2360   // The proxy responds to the connect with a 407, using a persistent
   2361   // connection.
   2362   MockRead data_reads1[] = {
   2363     // No credentials.
   2364     MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   2365     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2366     MockRead("Proxy-Connection: close\r\n\r\n"),
   2367 
   2368     MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
   2369 
   2370     MockRead("HTTP/1.1 200 OK\r\n"),
   2371     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2372     MockRead("Content-Length: 5\r\n\r\n"),
   2373     MockRead(SYNCHRONOUS, "hello"),
   2374   };
   2375 
   2376   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2377                                  data_writes1, arraysize(data_writes1));
   2378   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2379   SSLSocketDataProvider ssl(ASYNC, OK);
   2380   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   2381 
   2382   TestCompletionCallback callback1;
   2383 
   2384   scoped_ptr<HttpTransaction> trans(
   2385       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2386 
   2387   int rv = trans->Start(&request, callback1.callback(), log.bound());
   2388   EXPECT_EQ(ERR_IO_PENDING, rv);
   2389 
   2390   rv = callback1.WaitForResult();
   2391   EXPECT_EQ(OK, rv);
   2392   net::CapturingNetLog::CapturedEntryList entries;
   2393   log.GetEntries(&entries);
   2394   size_t pos = ExpectLogContainsSomewhere(
   2395       entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_TUNNEL_HEADERS,
   2396       NetLog::PHASE_NONE);
   2397   ExpectLogContainsSomewhere(
   2398       entries, pos,
   2399       NetLog::TYPE_HTTP_TRANSACTION_READ_TUNNEL_RESPONSE_HEADERS,
   2400       NetLog::PHASE_NONE);
   2401 
   2402   const HttpResponseInfo* response = trans->GetResponseInfo();
   2403   ASSERT_TRUE(response != NULL);
   2404   ASSERT_FALSE(response->headers.get() == NULL);
   2405   EXPECT_EQ(407, response->headers->response_code());
   2406   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   2407   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   2408 
   2409   LoadTimingInfo load_timing_info;
   2410   // CONNECT requests and responses are handled at the connect job level, so
   2411   // the transaction does not yet have a connection.
   2412   EXPECT_FALSE(trans->GetLoadTimingInfo(&load_timing_info));
   2413 
   2414   TestCompletionCallback callback2;
   2415 
   2416   rv = trans->RestartWithAuth(
   2417       AuthCredentials(kFoo, kBar), callback2.callback());
   2418   EXPECT_EQ(ERR_IO_PENDING, rv);
   2419 
   2420   rv = callback2.WaitForResult();
   2421   EXPECT_EQ(OK, rv);
   2422 
   2423   response = trans->GetResponseInfo();
   2424   ASSERT_TRUE(response != NULL);
   2425 
   2426   EXPECT_TRUE(response->headers->IsKeepAlive());
   2427   EXPECT_EQ(200, response->headers->response_code());
   2428   EXPECT_EQ(5, response->headers->GetContentLength());
   2429   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   2430 
   2431   // The password prompt info should not be set.
   2432   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   2433 
   2434   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   2435   TestLoadTimingNotReusedWithPac(load_timing_info,
   2436                                  CONNECT_TIMING_HAS_SSL_TIMES);
   2437 
   2438   trans.reset();
   2439   session->CloseAllConnections();
   2440 }
   2441 
   2442 // Test the request-challenge-retry sequence for basic auth, over a keep-alive
   2443 // proxy connection, when setting up an SSL tunnel.
   2444 TEST_P(HttpNetworkTransactionTest, BasicAuthProxyKeepAlive) {
   2445   HttpRequestInfo request;
   2446   request.method = "GET";
   2447   request.url = GURL("https://www.google.com/");
   2448   // Ensure that proxy authentication is attempted even
   2449   // when the no authentication data flag is set.
   2450   request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA;
   2451 
   2452   // Configure against proxy server "myproxy:70".
   2453   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   2454   CapturingBoundNetLog log;
   2455   session_deps_.net_log = log.bound().net_log();
   2456   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2457 
   2458   scoped_ptr<HttpTransaction> trans(
   2459       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2460 
   2461   // Since we have proxy, should try to establish tunnel.
   2462   MockWrite data_writes1[] = {
   2463     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2464               "Host: www.google.com\r\n"
   2465               "Proxy-Connection: keep-alive\r\n\r\n"),
   2466 
   2467     // After calling trans->RestartWithAuth(), this is the request we should
   2468     // be issuing -- the final header line contains the credentials.
   2469     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2470               "Host: www.google.com\r\n"
   2471               "Proxy-Connection: keep-alive\r\n"
   2472               "Proxy-Authorization: Basic Zm9vOmJheg==\r\n\r\n"),
   2473   };
   2474 
   2475   // The proxy responds to the connect with a 407, using a persistent
   2476   // connection.
   2477   MockRead data_reads1[] = {
   2478     // No credentials.
   2479     MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   2480     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2481     MockRead("Content-Length: 10\r\n\r\n"),
   2482     MockRead("0123456789"),
   2483 
   2484     // Wrong credentials (wrong password).
   2485     MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   2486     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2487     MockRead("Content-Length: 10\r\n\r\n"),
   2488     // No response body because the test stops reading here.
   2489     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   2490   };
   2491 
   2492   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2493                                  data_writes1, arraysize(data_writes1));
   2494   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2495 
   2496   TestCompletionCallback callback1;
   2497 
   2498   int rv = trans->Start(&request, callback1.callback(), log.bound());
   2499   EXPECT_EQ(ERR_IO_PENDING, rv);
   2500 
   2501   rv = callback1.WaitForResult();
   2502   EXPECT_EQ(OK, rv);
   2503   net::CapturingNetLog::CapturedEntryList entries;
   2504   log.GetEntries(&entries);
   2505   size_t pos = ExpectLogContainsSomewhere(
   2506       entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_TUNNEL_HEADERS,
   2507       NetLog::PHASE_NONE);
   2508   ExpectLogContainsSomewhere(
   2509       entries, pos,
   2510       NetLog::TYPE_HTTP_TRANSACTION_READ_TUNNEL_RESPONSE_HEADERS,
   2511       NetLog::PHASE_NONE);
   2512 
   2513   const HttpResponseInfo* response = trans->GetResponseInfo();
   2514   ASSERT_TRUE(response != NULL);
   2515   ASSERT_FALSE(response->headers.get() == NULL);
   2516   EXPECT_TRUE(response->headers->IsKeepAlive());
   2517   EXPECT_EQ(407, response->headers->response_code());
   2518   EXPECT_EQ(10, response->headers->GetContentLength());
   2519   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   2520   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   2521 
   2522   TestCompletionCallback callback2;
   2523 
   2524   // Wrong password (should be "bar").
   2525   rv = trans->RestartWithAuth(
   2526       AuthCredentials(kFoo, kBaz), callback2.callback());
   2527   EXPECT_EQ(ERR_IO_PENDING, rv);
   2528 
   2529   rv = callback2.WaitForResult();
   2530   EXPECT_EQ(OK, rv);
   2531 
   2532   response = trans->GetResponseInfo();
   2533   ASSERT_TRUE(response != NULL);
   2534   ASSERT_FALSE(response->headers.get() == NULL);
   2535   EXPECT_TRUE(response->headers->IsKeepAlive());
   2536   EXPECT_EQ(407, response->headers->response_code());
   2537   EXPECT_EQ(10, response->headers->GetContentLength());
   2538   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   2539   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   2540 
   2541   // Flush the idle socket before the NetLog and HttpNetworkTransaction go
   2542   // out of scope.
   2543   session->CloseAllConnections();
   2544 }
   2545 
   2546 // Test that we don't read the response body when we fail to establish a tunnel,
   2547 // even if the user cancels the proxy's auth attempt.
   2548 TEST_P(HttpNetworkTransactionTest, BasicAuthProxyCancelTunnel) {
   2549   HttpRequestInfo request;
   2550   request.method = "GET";
   2551   request.url = GURL("https://www.google.com/");
   2552   request.load_flags = 0;
   2553 
   2554   // Configure against proxy server "myproxy:70".
   2555   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   2556 
   2557   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2558 
   2559   scoped_ptr<HttpTransaction> trans(
   2560       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2561 
   2562   // Since we have proxy, should try to establish tunnel.
   2563   MockWrite data_writes[] = {
   2564     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2565               "Host: www.google.com\r\n"
   2566               "Proxy-Connection: keep-alive\r\n\r\n"),
   2567   };
   2568 
   2569   // The proxy responds to the connect with a 407.
   2570   MockRead data_reads[] = {
   2571     MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   2572     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2573     MockRead("Content-Length: 10\r\n\r\n"),
   2574     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   2575   };
   2576 
   2577   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   2578                                 data_writes, arraysize(data_writes));
   2579   session_deps_.socket_factory->AddSocketDataProvider(&data);
   2580 
   2581   TestCompletionCallback callback;
   2582 
   2583   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   2584   EXPECT_EQ(ERR_IO_PENDING, rv);
   2585 
   2586   rv = callback.WaitForResult();
   2587   EXPECT_EQ(OK, rv);
   2588 
   2589   const HttpResponseInfo* response = trans->GetResponseInfo();
   2590   ASSERT_TRUE(response != NULL);
   2591 
   2592   EXPECT_TRUE(response->headers->IsKeepAlive());
   2593   EXPECT_EQ(407, response->headers->response_code());
   2594   EXPECT_EQ(10, response->headers->GetContentLength());
   2595   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   2596 
   2597   std::string response_data;
   2598   rv = ReadTransaction(trans.get(), &response_data);
   2599   EXPECT_EQ(ERR_TUNNEL_CONNECTION_FAILED, rv);
   2600 
   2601   // Flush the idle socket before the HttpNetworkTransaction goes out of scope.
   2602   session->CloseAllConnections();
   2603 }
   2604 
   2605 // Test when a server (non-proxy) returns a 407 (proxy-authenticate).
   2606 // The request should fail with ERR_UNEXPECTED_PROXY_AUTH.
   2607 TEST_P(HttpNetworkTransactionTest, UnexpectedProxyAuth) {
   2608   HttpRequestInfo request;
   2609   request.method = "GET";
   2610   request.url = GURL("http://www.google.com/");
   2611   request.load_flags = 0;
   2612 
   2613   // We are using a DIRECT connection (i.e. no proxy) for this session.
   2614   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2615   scoped_ptr<HttpTransaction> trans(
   2616       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   2617 
   2618   MockWrite data_writes1[] = {
   2619     MockWrite("GET / HTTP/1.1\r\n"
   2620               "Host: www.google.com\r\n"
   2621               "Connection: keep-alive\r\n\r\n"),
   2622   };
   2623 
   2624   MockRead data_reads1[] = {
   2625     MockRead("HTTP/1.0 407 Proxy Auth required\r\n"),
   2626     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2627     // Large content-length -- won't matter, as connection will be reset.
   2628     MockRead("Content-Length: 10000\r\n\r\n"),
   2629     MockRead(SYNCHRONOUS, ERR_FAILED),
   2630   };
   2631 
   2632   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2633                                  data_writes1, arraysize(data_writes1));
   2634   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2635 
   2636   TestCompletionCallback callback;
   2637 
   2638   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   2639   EXPECT_EQ(ERR_IO_PENDING, rv);
   2640 
   2641   rv = callback.WaitForResult();
   2642   EXPECT_EQ(ERR_UNEXPECTED_PROXY_AUTH, rv);
   2643 }
   2644 
   2645 // Tests when an HTTPS server (non-proxy) returns a 407 (proxy-authentication)
   2646 // through a non-authenticating proxy. The request should fail with
   2647 // ERR_UNEXPECTED_PROXY_AUTH.
   2648 // Note that it is impossible to detect if an HTTP server returns a 407 through
   2649 // a non-authenticating proxy - there is nothing to indicate whether the
   2650 // response came from the proxy or the server, so it is treated as if the proxy
   2651 // issued the challenge.
   2652 TEST_P(HttpNetworkTransactionTest,
   2653        HttpsServerRequestsProxyAuthThroughProxy) {
   2654   HttpRequestInfo request;
   2655   request.method = "GET";
   2656   request.url = GURL("https://www.google.com/");
   2657 
   2658   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   2659   CapturingBoundNetLog log;
   2660   session_deps_.net_log = log.bound().net_log();
   2661   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2662 
   2663   // Since we have proxy, should try to establish tunnel.
   2664   MockWrite data_writes1[] = {
   2665     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2666               "Host: www.google.com\r\n"
   2667               "Proxy-Connection: keep-alive\r\n\r\n"),
   2668 
   2669     MockWrite("GET / HTTP/1.1\r\n"
   2670               "Host: www.google.com\r\n"
   2671               "Connection: keep-alive\r\n\r\n"),
   2672   };
   2673 
   2674   MockRead data_reads1[] = {
   2675     MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
   2676 
   2677     MockRead("HTTP/1.1 407 Unauthorized\r\n"),
   2678     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   2679     MockRead("\r\n"),
   2680     MockRead(SYNCHRONOUS, OK),
   2681   };
   2682 
   2683   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2684                                  data_writes1, arraysize(data_writes1));
   2685   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2686   SSLSocketDataProvider ssl(ASYNC, OK);
   2687   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   2688 
   2689   TestCompletionCallback callback1;
   2690 
   2691   scoped_ptr<HttpTransaction> trans(
   2692       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2693 
   2694   int rv = trans->Start(&request, callback1.callback(), log.bound());
   2695   EXPECT_EQ(ERR_IO_PENDING, rv);
   2696 
   2697   rv = callback1.WaitForResult();
   2698   EXPECT_EQ(ERR_UNEXPECTED_PROXY_AUTH, rv);
   2699   net::CapturingNetLog::CapturedEntryList entries;
   2700   log.GetEntries(&entries);
   2701   size_t pos = ExpectLogContainsSomewhere(
   2702       entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_TUNNEL_HEADERS,
   2703       NetLog::PHASE_NONE);
   2704   ExpectLogContainsSomewhere(
   2705       entries, pos,
   2706       NetLog::TYPE_HTTP_TRANSACTION_READ_TUNNEL_RESPONSE_HEADERS,
   2707       NetLog::PHASE_NONE);
   2708 }
   2709 
   2710 // Test the load timing for HTTPS requests with an HTTP proxy.
   2711 TEST_P(HttpNetworkTransactionTest, HttpProxyLoadTimingNoPacTwoRequests) {
   2712   HttpRequestInfo request1;
   2713   request1.method = "GET";
   2714   request1.url = GURL("https://www.google.com/1");
   2715 
   2716   HttpRequestInfo request2;
   2717   request2.method = "GET";
   2718   request2.url = GURL("https://www.google.com/2");
   2719 
   2720   // Configure against proxy server "myproxy:70".
   2721   session_deps_.proxy_service.reset(
   2722       ProxyService::CreateFixed("PROXY myproxy:70"));
   2723   CapturingBoundNetLog log;
   2724   session_deps_.net_log = log.bound().net_log();
   2725   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2726 
   2727   // Since we have proxy, should try to establish tunnel.
   2728   MockWrite data_writes1[] = {
   2729     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2730               "Host: www.google.com\r\n"
   2731               "Proxy-Connection: keep-alive\r\n\r\n"),
   2732 
   2733     MockWrite("GET /1 HTTP/1.1\r\n"
   2734               "Host: www.google.com\r\n"
   2735               "Connection: keep-alive\r\n\r\n"),
   2736 
   2737     MockWrite("GET /2 HTTP/1.1\r\n"
   2738               "Host: www.google.com\r\n"
   2739               "Connection: keep-alive\r\n\r\n"),
   2740   };
   2741 
   2742   // The proxy responds to the connect with a 407, using a persistent
   2743   // connection.
   2744   MockRead data_reads1[] = {
   2745     MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
   2746 
   2747     MockRead("HTTP/1.1 200 OK\r\n"),
   2748     MockRead("Content-Length: 1\r\n\r\n"),
   2749     MockRead(SYNCHRONOUS, "1"),
   2750 
   2751     MockRead("HTTP/1.1 200 OK\r\n"),
   2752     MockRead("Content-Length: 2\r\n\r\n"),
   2753     MockRead(SYNCHRONOUS, "22"),
   2754   };
   2755 
   2756   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2757                                  data_writes1, arraysize(data_writes1));
   2758   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2759   SSLSocketDataProvider ssl(ASYNC, OK);
   2760   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   2761 
   2762   TestCompletionCallback callback1;
   2763   scoped_ptr<HttpTransaction> trans1(
   2764       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2765 
   2766   int rv = trans1->Start(&request1, callback1.callback(), log.bound());
   2767   EXPECT_EQ(ERR_IO_PENDING, rv);
   2768 
   2769   rv = callback1.WaitForResult();
   2770   EXPECT_EQ(OK, rv);
   2771 
   2772   const HttpResponseInfo* response1 = trans1->GetResponseInfo();
   2773   ASSERT_TRUE(response1 != NULL);
   2774   ASSERT_TRUE(response1->headers.get() != NULL);
   2775   EXPECT_EQ(1, response1->headers->GetContentLength());
   2776 
   2777   LoadTimingInfo load_timing_info1;
   2778   EXPECT_TRUE(trans1->GetLoadTimingInfo(&load_timing_info1));
   2779   TestLoadTimingNotReused(load_timing_info1, CONNECT_TIMING_HAS_SSL_TIMES);
   2780 
   2781   trans1.reset();
   2782 
   2783   TestCompletionCallback callback2;
   2784   scoped_ptr<HttpTransaction> trans2(
   2785       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2786 
   2787   rv = trans2->Start(&request2, callback2.callback(), log.bound());
   2788   EXPECT_EQ(ERR_IO_PENDING, rv);
   2789 
   2790   rv = callback2.WaitForResult();
   2791   EXPECT_EQ(OK, rv);
   2792 
   2793   const HttpResponseInfo* response2 = trans2->GetResponseInfo();
   2794   ASSERT_TRUE(response2 != NULL);
   2795   ASSERT_TRUE(response2->headers.get() != NULL);
   2796   EXPECT_EQ(2, response2->headers->GetContentLength());
   2797 
   2798   LoadTimingInfo load_timing_info2;
   2799   EXPECT_TRUE(trans2->GetLoadTimingInfo(&load_timing_info2));
   2800   TestLoadTimingReused(load_timing_info2);
   2801 
   2802   EXPECT_EQ(load_timing_info1.socket_log_id, load_timing_info2.socket_log_id);
   2803 
   2804   trans2.reset();
   2805   session->CloseAllConnections();
   2806 }
   2807 
   2808 // Test the load timing for HTTPS requests with an HTTP proxy and a PAC script.
   2809 TEST_P(HttpNetworkTransactionTest, HttpProxyLoadTimingWithPacTwoRequests) {
   2810   HttpRequestInfo request1;
   2811   request1.method = "GET";
   2812   request1.url = GURL("https://www.google.com/1");
   2813 
   2814   HttpRequestInfo request2;
   2815   request2.method = "GET";
   2816   request2.url = GURL("https://www.google.com/2");
   2817 
   2818   // Configure against proxy server "myproxy:70".
   2819   session_deps_.proxy_service.reset(
   2820       ProxyService::CreateFixedFromPacResult("PROXY myproxy:70"));
   2821   CapturingBoundNetLog log;
   2822   session_deps_.net_log = log.bound().net_log();
   2823   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2824 
   2825   // Since we have proxy, should try to establish tunnel.
   2826   MockWrite data_writes1[] = {
   2827     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   2828               "Host: www.google.com\r\n"
   2829               "Proxy-Connection: keep-alive\r\n\r\n"),
   2830 
   2831     MockWrite("GET /1 HTTP/1.1\r\n"
   2832               "Host: www.google.com\r\n"
   2833               "Connection: keep-alive\r\n\r\n"),
   2834 
   2835     MockWrite("GET /2 HTTP/1.1\r\n"
   2836               "Host: www.google.com\r\n"
   2837               "Connection: keep-alive\r\n\r\n"),
   2838   };
   2839 
   2840   // The proxy responds to the connect with a 407, using a persistent
   2841   // connection.
   2842   MockRead data_reads1[] = {
   2843     MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
   2844 
   2845     MockRead("HTTP/1.1 200 OK\r\n"),
   2846     MockRead("Content-Length: 1\r\n\r\n"),
   2847     MockRead(SYNCHRONOUS, "1"),
   2848 
   2849     MockRead("HTTP/1.1 200 OK\r\n"),
   2850     MockRead("Content-Length: 2\r\n\r\n"),
   2851     MockRead(SYNCHRONOUS, "22"),
   2852   };
   2853 
   2854   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2855                                  data_writes1, arraysize(data_writes1));
   2856   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2857   SSLSocketDataProvider ssl(ASYNC, OK);
   2858   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   2859 
   2860   TestCompletionCallback callback1;
   2861   scoped_ptr<HttpTransaction> trans1(
   2862       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2863 
   2864   int rv = trans1->Start(&request1, callback1.callback(), log.bound());
   2865   EXPECT_EQ(ERR_IO_PENDING, rv);
   2866 
   2867   rv = callback1.WaitForResult();
   2868   EXPECT_EQ(OK, rv);
   2869 
   2870   const HttpResponseInfo* response1 = trans1->GetResponseInfo();
   2871   ASSERT_TRUE(response1 != NULL);
   2872   ASSERT_TRUE(response1->headers.get() != NULL);
   2873   EXPECT_EQ(1, response1->headers->GetContentLength());
   2874 
   2875   LoadTimingInfo load_timing_info1;
   2876   EXPECT_TRUE(trans1->GetLoadTimingInfo(&load_timing_info1));
   2877   TestLoadTimingNotReusedWithPac(load_timing_info1,
   2878                                  CONNECT_TIMING_HAS_SSL_TIMES);
   2879 
   2880   trans1.reset();
   2881 
   2882   TestCompletionCallback callback2;
   2883   scoped_ptr<HttpTransaction> trans2(
   2884       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2885 
   2886   rv = trans2->Start(&request2, callback2.callback(), log.bound());
   2887   EXPECT_EQ(ERR_IO_PENDING, rv);
   2888 
   2889   rv = callback2.WaitForResult();
   2890   EXPECT_EQ(OK, rv);
   2891 
   2892   const HttpResponseInfo* response2 = trans2->GetResponseInfo();
   2893   ASSERT_TRUE(response2 != NULL);
   2894   ASSERT_TRUE(response2->headers.get() != NULL);
   2895   EXPECT_EQ(2, response2->headers->GetContentLength());
   2896 
   2897   LoadTimingInfo load_timing_info2;
   2898   EXPECT_TRUE(trans2->GetLoadTimingInfo(&load_timing_info2));
   2899   TestLoadTimingReusedWithPac(load_timing_info2);
   2900 
   2901   EXPECT_EQ(load_timing_info1.socket_log_id, load_timing_info2.socket_log_id);
   2902 
   2903   trans2.reset();
   2904   session->CloseAllConnections();
   2905 }
   2906 
   2907 // Test a simple get through an HTTPS Proxy.
   2908 TEST_P(HttpNetworkTransactionTest, HttpsProxyGet) {
   2909   HttpRequestInfo request;
   2910   request.method = "GET";
   2911   request.url = GURL("http://www.google.com/");
   2912 
   2913   // Configure against https proxy server "proxy:70".
   2914   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   2915       "https://proxy:70"));
   2916   CapturingBoundNetLog log;
   2917   session_deps_.net_log = log.bound().net_log();
   2918   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2919 
   2920   // Since we have proxy, should use full url
   2921   MockWrite data_writes1[] = {
   2922     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   2923               "Host: www.google.com\r\n"
   2924               "Proxy-Connection: keep-alive\r\n\r\n"),
   2925   };
   2926 
   2927   MockRead data_reads1[] = {
   2928     MockRead("HTTP/1.1 200 OK\r\n"),
   2929     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   2930     MockRead("Content-Length: 100\r\n\r\n"),
   2931     MockRead(SYNCHRONOUS, OK),
   2932   };
   2933 
   2934   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   2935                                  data_writes1, arraysize(data_writes1));
   2936   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   2937   SSLSocketDataProvider ssl(ASYNC, OK);
   2938   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   2939 
   2940   TestCompletionCallback callback1;
   2941 
   2942   scoped_ptr<HttpTransaction> trans(
   2943       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   2944 
   2945   int rv = trans->Start(&request, callback1.callback(), log.bound());
   2946   EXPECT_EQ(ERR_IO_PENDING, rv);
   2947 
   2948   rv = callback1.WaitForResult();
   2949   EXPECT_EQ(OK, rv);
   2950 
   2951   LoadTimingInfo load_timing_info;
   2952   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   2953   TestLoadTimingNotReused(load_timing_info,
   2954                           CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   2955 
   2956   const HttpResponseInfo* response = trans->GetResponseInfo();
   2957   ASSERT_TRUE(response != NULL);
   2958 
   2959   EXPECT_TRUE(response->headers->IsKeepAlive());
   2960   EXPECT_EQ(200, response->headers->response_code());
   2961   EXPECT_EQ(100, response->headers->GetContentLength());
   2962   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   2963 
   2964   // The password prompt info should not be set.
   2965   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   2966 }
   2967 
   2968 // Test a SPDY get through an HTTPS Proxy.
   2969 TEST_P(HttpNetworkTransactionTest, HttpsProxySpdyGet) {
   2970   HttpRequestInfo request;
   2971   request.method = "GET";
   2972   request.url = GURL("http://www.google.com/");
   2973   request.load_flags = 0;
   2974 
   2975   // Configure against https proxy server "proxy:70".
   2976   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   2977       "https://proxy:70"));
   2978   CapturingBoundNetLog log;
   2979   session_deps_.net_log = log.bound().net_log();
   2980   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   2981 
   2982   // fetch http://www.google.com/ via SPDY
   2983   scoped_ptr<SpdyFrame> req(
   2984       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, false));
   2985   MockWrite spdy_writes[] = { CreateMockWrite(*req) };
   2986 
   2987   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   2988   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   2989   MockRead spdy_reads[] = {
   2990     CreateMockRead(*resp),
   2991     CreateMockRead(*data),
   2992     MockRead(ASYNC, 0, 0),
   2993   };
   2994 
   2995   DelayedSocketData spdy_data(
   2996       1,  // wait for one write to finish before reading.
   2997       spdy_reads, arraysize(spdy_reads),
   2998       spdy_writes, arraysize(spdy_writes));
   2999   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   3000 
   3001   SSLSocketDataProvider ssl(ASYNC, OK);
   3002   ssl.SetNextProto(GetParam());
   3003   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3004 
   3005   TestCompletionCallback callback1;
   3006 
   3007   scoped_ptr<HttpTransaction> trans(
   3008       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3009 
   3010   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3011   EXPECT_EQ(ERR_IO_PENDING, rv);
   3012 
   3013   rv = callback1.WaitForResult();
   3014   EXPECT_EQ(OK, rv);
   3015 
   3016   LoadTimingInfo load_timing_info;
   3017   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3018   TestLoadTimingNotReused(load_timing_info,
   3019                           CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   3020 
   3021   const HttpResponseInfo* response = trans->GetResponseInfo();
   3022   ASSERT_TRUE(response != NULL);
   3023   ASSERT_TRUE(response->headers.get() != NULL);
   3024   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3025 
   3026   std::string response_data;
   3027   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   3028   EXPECT_EQ(kUploadData, response_data);
   3029 }
   3030 
   3031 // Verifies that a session which races and wins against the owning transaction
   3032 // (completing prior to host resolution), doesn't fail the transaction.
   3033 // Regression test for crbug.com/334413.
   3034 TEST_P(HttpNetworkTransactionTest, HttpsProxySpdyGetWithSessionRace) {
   3035   HttpRequestInfo request;
   3036   request.method = "GET";
   3037   request.url = GURL("http://www.google.com/");
   3038   request.load_flags = 0;
   3039 
   3040   // Configure SPDY proxy server "proxy:70".
   3041   session_deps_.proxy_service.reset(
   3042       ProxyService::CreateFixed("https://proxy:70"));
   3043   CapturingBoundNetLog log;
   3044   session_deps_.net_log = log.bound().net_log();
   3045   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3046 
   3047   // Fetch http://www.google.com/ through the SPDY proxy.
   3048   scoped_ptr<SpdyFrame> req(
   3049       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, false));
   3050   MockWrite spdy_writes[] = {CreateMockWrite(*req)};
   3051 
   3052   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3053   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   3054   MockRead spdy_reads[] = {
   3055       CreateMockRead(*resp), CreateMockRead(*data), MockRead(ASYNC, 0, 0),
   3056   };
   3057 
   3058   DelayedSocketData spdy_data(
   3059       1,  // wait for one write to finish before reading.
   3060       spdy_reads,
   3061       arraysize(spdy_reads),
   3062       spdy_writes,
   3063       arraysize(spdy_writes));
   3064   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   3065 
   3066   SSLSocketDataProvider ssl(ASYNC, OK);
   3067   ssl.SetNextProto(GetParam());
   3068   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3069 
   3070   TestCompletionCallback callback1;
   3071 
   3072   scoped_ptr<HttpTransaction> trans(
   3073       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3074 
   3075   // Stall the hostname resolution begun by the transaction.
   3076   session_deps_.host_resolver->set_synchronous_mode(false);
   3077   session_deps_.host_resolver->set_ondemand_mode(true);
   3078 
   3079   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3080   EXPECT_EQ(ERR_IO_PENDING, rv);
   3081 
   3082   // Race a session to the proxy, which completes first.
   3083   session_deps_.host_resolver->set_ondemand_mode(false);
   3084   SpdySessionKey key(
   3085       HostPortPair("proxy", 70), ProxyServer::Direct(), PRIVACY_MODE_DISABLED);
   3086   base::WeakPtr<SpdySession> spdy_session =
   3087       CreateSecureSpdySession(session, key, log.bound());
   3088 
   3089   // Unstall the resolution begun by the transaction.
   3090   session_deps_.host_resolver->set_ondemand_mode(true);
   3091   session_deps_.host_resolver->ResolveAllPending();
   3092 
   3093   EXPECT_FALSE(callback1.have_result());
   3094   rv = callback1.WaitForResult();
   3095   EXPECT_EQ(OK, rv);
   3096 
   3097   const HttpResponseInfo* response = trans->GetResponseInfo();
   3098   ASSERT_TRUE(response != NULL);
   3099   ASSERT_TRUE(response->headers.get() != NULL);
   3100   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3101 
   3102   std::string response_data;
   3103   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   3104   EXPECT_EQ(kUploadData, response_data);
   3105 }
   3106 
   3107 // Test a SPDY get through an HTTPS Proxy.
   3108 TEST_P(HttpNetworkTransactionTest, HttpsProxySpdyGetWithProxyAuth) {
   3109   HttpRequestInfo request;
   3110   request.method = "GET";
   3111   request.url = GURL("http://www.google.com/");
   3112   request.load_flags = 0;
   3113 
   3114   // Configure against https proxy server "myproxy:70".
   3115   session_deps_.proxy_service.reset(
   3116       ProxyService::CreateFixed("https://myproxy:70"));
   3117   CapturingBoundNetLog log;
   3118   session_deps_.net_log = log.bound().net_log();
   3119   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3120 
   3121   // The first request will be a bare GET, the second request will be a
   3122   // GET with a Proxy-Authorization header.
   3123   scoped_ptr<SpdyFrame> req_get(
   3124       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, false));
   3125   const char* const kExtraAuthorizationHeaders[] = {
   3126     "proxy-authorization", "Basic Zm9vOmJhcg=="
   3127   };
   3128   scoped_ptr<SpdyFrame> req_get_authorization(
   3129       spdy_util_.ConstructSpdyGet(kExtraAuthorizationHeaders,
   3130                                   arraysize(kExtraAuthorizationHeaders) / 2,
   3131                                   false,
   3132                                   3,
   3133                                   LOWEST,
   3134                                   false));
   3135   MockWrite spdy_writes[] = {
   3136     CreateMockWrite(*req_get, 1),
   3137     CreateMockWrite(*req_get_authorization, 4),
   3138   };
   3139 
   3140   // The first response is a 407 proxy authentication challenge, and the second
   3141   // response will be a 200 response since the second request includes a valid
   3142   // Authorization header.
   3143   const char* const kExtraAuthenticationHeaders[] = {
   3144     "proxy-authenticate", "Basic realm=\"MyRealm1\""
   3145   };
   3146   scoped_ptr<SpdyFrame> resp_authentication(
   3147       spdy_util_.ConstructSpdySynReplyError(
   3148           "407 Proxy Authentication Required",
   3149           kExtraAuthenticationHeaders, arraysize(kExtraAuthenticationHeaders)/2,
   3150           1));
   3151   scoped_ptr<SpdyFrame> body_authentication(
   3152       spdy_util_.ConstructSpdyBodyFrame(1, true));
   3153   scoped_ptr<SpdyFrame> resp_data(
   3154       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   3155   scoped_ptr<SpdyFrame> body_data(spdy_util_.ConstructSpdyBodyFrame(3, true));
   3156   MockRead spdy_reads[] = {
   3157     CreateMockRead(*resp_authentication, 2),
   3158     CreateMockRead(*body_authentication, 3),
   3159     CreateMockRead(*resp_data, 5),
   3160     CreateMockRead(*body_data, 6),
   3161     MockRead(ASYNC, 0, 7),
   3162   };
   3163 
   3164   OrderedSocketData data(
   3165       spdy_reads, arraysize(spdy_reads),
   3166       spdy_writes, arraysize(spdy_writes));
   3167   session_deps_.socket_factory->AddSocketDataProvider(&data);
   3168 
   3169   SSLSocketDataProvider ssl(ASYNC, OK);
   3170   ssl.SetNextProto(GetParam());
   3171   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3172 
   3173   TestCompletionCallback callback1;
   3174 
   3175   scoped_ptr<HttpTransaction> trans(
   3176       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3177 
   3178   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3179   EXPECT_EQ(ERR_IO_PENDING, rv);
   3180 
   3181   rv = callback1.WaitForResult();
   3182   EXPECT_EQ(OK, rv);
   3183 
   3184   const HttpResponseInfo* const response = trans->GetResponseInfo();
   3185 
   3186   ASSERT_TRUE(response != NULL);
   3187   ASSERT_TRUE(response->headers.get() != NULL);
   3188   EXPECT_EQ(407, response->headers->response_code());
   3189   EXPECT_TRUE(response->was_fetched_via_spdy);
   3190   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   3191 
   3192   TestCompletionCallback callback2;
   3193 
   3194   rv = trans->RestartWithAuth(
   3195       AuthCredentials(kFoo, kBar), callback2.callback());
   3196   EXPECT_EQ(ERR_IO_PENDING, rv);
   3197 
   3198   rv = callback2.WaitForResult();
   3199   EXPECT_EQ(OK, rv);
   3200 
   3201   const HttpResponseInfo* const response_restart = trans->GetResponseInfo();
   3202 
   3203   ASSERT_TRUE(response_restart != NULL);
   3204   ASSERT_TRUE(response_restart->headers.get() != NULL);
   3205   EXPECT_EQ(200, response_restart->headers->response_code());
   3206   // The password prompt info should not be set.
   3207   EXPECT_TRUE(response_restart->auth_challenge.get() == NULL);
   3208 }
   3209 
   3210 // Test a SPDY CONNECT through an HTTPS Proxy to an HTTPS (non-SPDY) Server.
   3211 TEST_P(HttpNetworkTransactionTest, HttpsProxySpdyConnectHttps) {
   3212   HttpRequestInfo request;
   3213   request.method = "GET";
   3214   request.url = GURL("https://www.google.com/");
   3215   request.load_flags = 0;
   3216 
   3217   // Configure against https proxy server "proxy:70".
   3218   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   3219       "https://proxy:70"));
   3220   CapturingBoundNetLog log;
   3221   session_deps_.net_log = log.bound().net_log();
   3222   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3223 
   3224   scoped_ptr<HttpTransaction> trans(
   3225       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3226 
   3227   // CONNECT to www.google.com:443 via SPDY
   3228   scoped_ptr<SpdyFrame> connect(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   3229                                                                 LOWEST));
   3230   // fetch https://www.google.com/ via HTTP
   3231 
   3232   const char get[] = "GET / HTTP/1.1\r\n"
   3233     "Host: www.google.com\r\n"
   3234     "Connection: keep-alive\r\n\r\n";
   3235   scoped_ptr<SpdyFrame> wrapped_get(
   3236       spdy_util_.ConstructSpdyBodyFrame(1, get, strlen(get), false));
   3237   scoped_ptr<SpdyFrame> conn_resp(
   3238       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3239   const char resp[] = "HTTP/1.1 200 OK\r\n"
   3240       "Content-Length: 10\r\n\r\n";
   3241   scoped_ptr<SpdyFrame> wrapped_get_resp(
   3242       spdy_util_.ConstructSpdyBodyFrame(1, resp, strlen(resp), false));
   3243   scoped_ptr<SpdyFrame> wrapped_body(
   3244       spdy_util_.ConstructSpdyBodyFrame(1, "1234567890", 10, false));
   3245   scoped_ptr<SpdyFrame> window_update(
   3246       spdy_util_.ConstructSpdyWindowUpdate(1, wrapped_get_resp->size()));
   3247 
   3248   MockWrite spdy_writes[] = {
   3249       CreateMockWrite(*connect, 1),
   3250       CreateMockWrite(*wrapped_get, 3),
   3251       CreateMockWrite(*window_update, 5),
   3252   };
   3253 
   3254   MockRead spdy_reads[] = {
   3255     CreateMockRead(*conn_resp, 2, ASYNC),
   3256     CreateMockRead(*wrapped_get_resp, 4, ASYNC),
   3257     CreateMockRead(*wrapped_body, 6, ASYNC),
   3258     CreateMockRead(*wrapped_body, 7, ASYNC),
   3259     MockRead(ASYNC, 0, 8),
   3260   };
   3261 
   3262   OrderedSocketData spdy_data(
   3263       spdy_reads, arraysize(spdy_reads),
   3264       spdy_writes, arraysize(spdy_writes));
   3265   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   3266 
   3267   SSLSocketDataProvider ssl(ASYNC, OK);
   3268   ssl.SetNextProto(GetParam());
   3269   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3270   SSLSocketDataProvider ssl2(ASYNC, OK);
   3271   ssl2.was_npn_negotiated = false;
   3272   ssl2.protocol_negotiated = kProtoUnknown;
   3273   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl2);
   3274 
   3275   TestCompletionCallback callback1;
   3276 
   3277   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3278   EXPECT_EQ(ERR_IO_PENDING, rv);
   3279 
   3280   rv = callback1.WaitForResult();
   3281   EXPECT_EQ(OK, rv);
   3282 
   3283   LoadTimingInfo load_timing_info;
   3284   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3285   TestLoadTimingNotReused(load_timing_info, CONNECT_TIMING_HAS_SSL_TIMES);
   3286 
   3287   const HttpResponseInfo* response = trans->GetResponseInfo();
   3288   ASSERT_TRUE(response != NULL);
   3289   ASSERT_TRUE(response->headers.get() != NULL);
   3290   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3291 
   3292   std::string response_data;
   3293   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   3294   EXPECT_EQ("1234567890", response_data);
   3295 }
   3296 
   3297 // Test a SPDY CONNECT through an HTTPS Proxy to a SPDY server.
   3298 TEST_P(HttpNetworkTransactionTest, HttpsProxySpdyConnectSpdy) {
   3299   HttpRequestInfo request;
   3300   request.method = "GET";
   3301   request.url = GURL("https://www.google.com/");
   3302   request.load_flags = 0;
   3303 
   3304   // Configure against https proxy server "proxy:70".
   3305   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   3306       "https://proxy:70"));
   3307   CapturingBoundNetLog log;
   3308   session_deps_.net_log = log.bound().net_log();
   3309   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3310 
   3311   scoped_ptr<HttpTransaction> trans(
   3312       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3313 
   3314   // CONNECT to www.google.com:443 via SPDY
   3315   scoped_ptr<SpdyFrame> connect(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   3316                                                                 LOWEST));
   3317   // fetch https://www.google.com/ via SPDY
   3318   const char* const kMyUrl = "https://www.google.com/";
   3319   scoped_ptr<SpdyFrame> get(
   3320       spdy_util_.ConstructSpdyGet(kMyUrl, false, 1, LOWEST));
   3321   scoped_ptr<SpdyFrame> wrapped_get(
   3322       spdy_util_.ConstructWrappedSpdyFrame(get, 1));
   3323   scoped_ptr<SpdyFrame> conn_resp(
   3324       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3325   scoped_ptr<SpdyFrame> get_resp(
   3326       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3327   scoped_ptr<SpdyFrame> wrapped_get_resp(
   3328       spdy_util_.ConstructWrappedSpdyFrame(get_resp, 1));
   3329   scoped_ptr<SpdyFrame> body(spdy_util_.ConstructSpdyBodyFrame(1, true));
   3330   scoped_ptr<SpdyFrame> wrapped_body(
   3331       spdy_util_.ConstructWrappedSpdyFrame(body, 1));
   3332   scoped_ptr<SpdyFrame> window_update_get_resp(
   3333       spdy_util_.ConstructSpdyWindowUpdate(1, wrapped_get_resp->size()));
   3334   scoped_ptr<SpdyFrame> window_update_body(
   3335       spdy_util_.ConstructSpdyWindowUpdate(1, wrapped_body->size()));
   3336 
   3337   MockWrite spdy_writes[] = {
   3338       CreateMockWrite(*connect, 1),
   3339       CreateMockWrite(*wrapped_get, 3),
   3340       CreateMockWrite(*window_update_get_resp, 5),
   3341       CreateMockWrite(*window_update_body, 7),
   3342   };
   3343 
   3344   MockRead spdy_reads[] = {
   3345     CreateMockRead(*conn_resp, 2, ASYNC),
   3346     CreateMockRead(*wrapped_get_resp, 4, ASYNC),
   3347     CreateMockRead(*wrapped_body, 6, ASYNC),
   3348     MockRead(ASYNC, 0, 8),
   3349   };
   3350 
   3351   OrderedSocketData spdy_data(
   3352       spdy_reads, arraysize(spdy_reads),
   3353       spdy_writes, arraysize(spdy_writes));
   3354   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   3355 
   3356   SSLSocketDataProvider ssl(ASYNC, OK);
   3357   ssl.SetNextProto(GetParam());
   3358   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3359   SSLSocketDataProvider ssl2(ASYNC, OK);
   3360   ssl2.SetNextProto(GetParam());
   3361   ssl2.protocol_negotiated = GetParam();
   3362   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl2);
   3363 
   3364   TestCompletionCallback callback1;
   3365 
   3366   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3367   EXPECT_EQ(ERR_IO_PENDING, rv);
   3368 
   3369   rv = callback1.WaitForResult();
   3370   EXPECT_EQ(OK, rv);
   3371 
   3372   LoadTimingInfo load_timing_info;
   3373   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3374   TestLoadTimingNotReused(load_timing_info, CONNECT_TIMING_HAS_SSL_TIMES);
   3375 
   3376   const HttpResponseInfo* response = trans->GetResponseInfo();
   3377   ASSERT_TRUE(response != NULL);
   3378   ASSERT_TRUE(response->headers.get() != NULL);
   3379   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3380 
   3381   std::string response_data;
   3382   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   3383   EXPECT_EQ(kUploadData, response_data);
   3384 }
   3385 
   3386 // Test a SPDY CONNECT failure through an HTTPS Proxy.
   3387 TEST_P(HttpNetworkTransactionTest, HttpsProxySpdyConnectFailure) {
   3388   HttpRequestInfo request;
   3389   request.method = "GET";
   3390   request.url = GURL("https://www.google.com/");
   3391   request.load_flags = 0;
   3392 
   3393   // Configure against https proxy server "proxy:70".
   3394   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   3395       "https://proxy:70"));
   3396   CapturingBoundNetLog log;
   3397   session_deps_.net_log = log.bound().net_log();
   3398   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3399 
   3400   scoped_ptr<HttpTransaction> trans(
   3401       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3402 
   3403   // CONNECT to www.google.com:443 via SPDY
   3404   scoped_ptr<SpdyFrame> connect(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   3405                                                                 LOWEST));
   3406   scoped_ptr<SpdyFrame> get(
   3407       spdy_util_.ConstructSpdyRstStream(1, RST_STREAM_CANCEL));
   3408 
   3409   MockWrite spdy_writes[] = {
   3410       CreateMockWrite(*connect, 1),
   3411       CreateMockWrite(*get, 3),
   3412   };
   3413 
   3414   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdySynReplyError(1));
   3415   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   3416   MockRead spdy_reads[] = {
   3417     CreateMockRead(*resp, 2, ASYNC),
   3418     MockRead(ASYNC, 0, 4),
   3419   };
   3420 
   3421   OrderedSocketData spdy_data(
   3422       spdy_reads, arraysize(spdy_reads),
   3423       spdy_writes, arraysize(spdy_writes));
   3424   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   3425 
   3426   SSLSocketDataProvider ssl(ASYNC, OK);
   3427   ssl.SetNextProto(GetParam());
   3428   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3429   SSLSocketDataProvider ssl2(ASYNC, OK);
   3430   ssl2.SetNextProto(GetParam());
   3431   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl2);
   3432 
   3433   TestCompletionCallback callback1;
   3434 
   3435   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3436   EXPECT_EQ(ERR_IO_PENDING, rv);
   3437 
   3438   rv = callback1.WaitForResult();
   3439   EXPECT_EQ(ERR_TUNNEL_CONNECTION_FAILED, rv);
   3440 
   3441   // TODO(ttuttle): Anything else to check here?
   3442 }
   3443 
   3444 // Test load timing in the case of two HTTPS (non-SPDY) requests through a SPDY
   3445 // HTTPS Proxy to different servers.
   3446 TEST_P(HttpNetworkTransactionTest,
   3447        HttpsProxySpdyConnectHttpsLoadTimingTwoRequestsTwoServers) {
   3448   // Configure against https proxy server "proxy:70".
   3449   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   3450       "https://proxy:70"));
   3451   CapturingBoundNetLog log;
   3452   session_deps_.net_log = log.bound().net_log();
   3453   scoped_refptr<HttpNetworkSession> session(
   3454       SpdySessionDependencies::SpdyCreateSessionDeterministic(&session_deps_));
   3455 
   3456   HttpRequestInfo request1;
   3457   request1.method = "GET";
   3458   request1.url = GURL("https://www.google.com/");
   3459   request1.load_flags = 0;
   3460 
   3461   HttpRequestInfo request2;
   3462   request2.method = "GET";
   3463   request2.url = GURL("https://news.google.com/");
   3464   request2.load_flags = 0;
   3465 
   3466   // CONNECT to www.google.com:443 via SPDY.
   3467   scoped_ptr<SpdyFrame> connect1(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   3468                                                                  LOWEST));
   3469   scoped_ptr<SpdyFrame> conn_resp1(
   3470       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3471 
   3472   // Fetch https://www.google.com/ via HTTP.
   3473   const char get1[] = "GET / HTTP/1.1\r\n"
   3474       "Host: www.google.com\r\n"
   3475       "Connection: keep-alive\r\n\r\n";
   3476   scoped_ptr<SpdyFrame> wrapped_get1(
   3477       spdy_util_.ConstructSpdyBodyFrame(1, get1, strlen(get1), false));
   3478   const char resp1[] = "HTTP/1.1 200 OK\r\n"
   3479       "Content-Length: 1\r\n\r\n";
   3480   scoped_ptr<SpdyFrame> wrapped_get_resp1(
   3481       spdy_util_.ConstructSpdyBodyFrame(1, resp1, strlen(resp1), false));
   3482   scoped_ptr<SpdyFrame> wrapped_body1(
   3483       spdy_util_.ConstructSpdyBodyFrame(1, "1", 1, false));
   3484   scoped_ptr<SpdyFrame> window_update(
   3485       spdy_util_.ConstructSpdyWindowUpdate(1, wrapped_get_resp1->size()));
   3486 
   3487   // CONNECT to news.google.com:443 via SPDY.
   3488   SpdySynStreamIR connect2_ir(3);
   3489   spdy_util_.SetPriority(LOWEST, &connect2_ir);
   3490   connect2_ir.SetHeader(spdy_util_.GetMethodKey(), "CONNECT");
   3491   connect2_ir.SetHeader(spdy_util_.GetPathKey(), "news.google.com:443");
   3492   connect2_ir.SetHeader(spdy_util_.GetHostKey(), "news.google.com");
   3493   spdy_util_.MaybeAddVersionHeader(&connect2_ir);
   3494   scoped_ptr<SpdyFrame> connect2(
   3495       spdy_util_.CreateFramer(false)->SerializeFrame(connect2_ir));
   3496 
   3497   scoped_ptr<SpdyFrame> conn_resp2(
   3498       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   3499 
   3500   // Fetch https://news.google.com/ via HTTP.
   3501   const char get2[] = "GET / HTTP/1.1\r\n"
   3502       "Host: news.google.com\r\n"
   3503       "Connection: keep-alive\r\n\r\n";
   3504   scoped_ptr<SpdyFrame> wrapped_get2(
   3505       spdy_util_.ConstructSpdyBodyFrame(3, get2, strlen(get2), false));
   3506   const char resp2[] = "HTTP/1.1 200 OK\r\n"
   3507       "Content-Length: 2\r\n\r\n";
   3508   scoped_ptr<SpdyFrame> wrapped_get_resp2(
   3509       spdy_util_.ConstructSpdyBodyFrame(3, resp2, strlen(resp2), false));
   3510   scoped_ptr<SpdyFrame> wrapped_body2(
   3511       spdy_util_.ConstructSpdyBodyFrame(3, "22", 2, false));
   3512 
   3513   MockWrite spdy_writes[] = {
   3514       CreateMockWrite(*connect1, 0),
   3515       CreateMockWrite(*wrapped_get1, 2),
   3516       CreateMockWrite(*connect2, 5),
   3517       CreateMockWrite(*wrapped_get2, 7),
   3518   };
   3519 
   3520   MockRead spdy_reads[] = {
   3521     CreateMockRead(*conn_resp1, 1, ASYNC),
   3522     CreateMockRead(*wrapped_get_resp1, 3, ASYNC),
   3523     CreateMockRead(*wrapped_body1, 4, ASYNC),
   3524     CreateMockRead(*conn_resp2, 6, ASYNC),
   3525     CreateMockRead(*wrapped_get_resp2, 8, ASYNC),
   3526     CreateMockRead(*wrapped_body2, 9, ASYNC),
   3527     MockRead(ASYNC, 0, 10),
   3528   };
   3529 
   3530   DeterministicSocketData spdy_data(
   3531       spdy_reads, arraysize(spdy_reads),
   3532       spdy_writes, arraysize(spdy_writes));
   3533   session_deps_.deterministic_socket_factory->AddSocketDataProvider(&spdy_data);
   3534 
   3535   SSLSocketDataProvider ssl(ASYNC, OK);
   3536   ssl.SetNextProto(GetParam());
   3537   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl);
   3538   SSLSocketDataProvider ssl2(ASYNC, OK);
   3539   ssl2.was_npn_negotiated = false;
   3540   ssl2.protocol_negotiated = kProtoUnknown;
   3541   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl2);
   3542   SSLSocketDataProvider ssl3(ASYNC, OK);
   3543   ssl3.was_npn_negotiated = false;
   3544   ssl3.protocol_negotiated = kProtoUnknown;
   3545   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl3);
   3546 
   3547   TestCompletionCallback callback;
   3548 
   3549   scoped_ptr<HttpTransaction> trans(
   3550       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3551   int rv = trans->Start(&request1, callback.callback(), BoundNetLog());
   3552   EXPECT_EQ(ERR_IO_PENDING, rv);
   3553   // The first connect and request, each of their responses, and the body.
   3554   spdy_data.RunFor(5);
   3555 
   3556   rv = callback.WaitForResult();
   3557   EXPECT_EQ(OK, rv);
   3558 
   3559   LoadTimingInfo load_timing_info;
   3560   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3561   TestLoadTimingNotReused(load_timing_info, CONNECT_TIMING_HAS_SSL_TIMES);
   3562 
   3563   const HttpResponseInfo* response = trans->GetResponseInfo();
   3564   ASSERT_TRUE(response != NULL);
   3565   ASSERT_TRUE(response->headers.get() != NULL);
   3566   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3567 
   3568   std::string response_data;
   3569   scoped_refptr<net::IOBuffer> buf(new net::IOBuffer(256));
   3570   EXPECT_EQ(1, trans->Read(buf.get(), 256, callback.callback()));
   3571 
   3572   scoped_ptr<HttpTransaction> trans2(
   3573       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3574   rv = trans2->Start(&request2, callback.callback(), BoundNetLog());
   3575   EXPECT_EQ(ERR_IO_PENDING, rv);
   3576 
   3577   // The second connect and request, each of their responses, and the body.
   3578   spdy_data.RunFor(5);
   3579   rv = callback.WaitForResult();
   3580   EXPECT_EQ(OK, rv);
   3581 
   3582   LoadTimingInfo load_timing_info2;
   3583   EXPECT_TRUE(trans2->GetLoadTimingInfo(&load_timing_info2));
   3584   // Even though the SPDY connection is reused, a new tunnelled connection has
   3585   // to be created, so the socket's load timing looks like a fresh connection.
   3586   TestLoadTimingNotReused(load_timing_info2, CONNECT_TIMING_HAS_SSL_TIMES);
   3587 
   3588   // The requests should have different IDs, since they each are using their own
   3589   // separate stream.
   3590   EXPECT_NE(load_timing_info.socket_log_id, load_timing_info2.socket_log_id);
   3591 
   3592   EXPECT_EQ(2, trans2->Read(buf.get(), 256, callback.callback()));
   3593 }
   3594 
   3595 // Test load timing in the case of two HTTPS (non-SPDY) requests through a SPDY
   3596 // HTTPS Proxy to the same server.
   3597 TEST_P(HttpNetworkTransactionTest,
   3598        HttpsProxySpdyConnectHttpsLoadTimingTwoRequestsSameServer) {
   3599   // Configure against https proxy server "proxy:70".
   3600   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   3601       "https://proxy:70"));
   3602   CapturingBoundNetLog log;
   3603   session_deps_.net_log = log.bound().net_log();
   3604   scoped_refptr<HttpNetworkSession> session(
   3605       SpdySessionDependencies::SpdyCreateSessionDeterministic(&session_deps_));
   3606 
   3607   HttpRequestInfo request1;
   3608   request1.method = "GET";
   3609   request1.url = GURL("https://www.google.com/");
   3610   request1.load_flags = 0;
   3611 
   3612   HttpRequestInfo request2;
   3613   request2.method = "GET";
   3614   request2.url = GURL("https://www.google.com/2");
   3615   request2.load_flags = 0;
   3616 
   3617   // CONNECT to www.google.com:443 via SPDY.
   3618   scoped_ptr<SpdyFrame> connect1(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   3619                                                                  LOWEST));
   3620   scoped_ptr<SpdyFrame> conn_resp1(
   3621       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3622 
   3623   // Fetch https://www.google.com/ via HTTP.
   3624   const char get1[] = "GET / HTTP/1.1\r\n"
   3625       "Host: www.google.com\r\n"
   3626       "Connection: keep-alive\r\n\r\n";
   3627   scoped_ptr<SpdyFrame> wrapped_get1(
   3628       spdy_util_.ConstructSpdyBodyFrame(1, get1, strlen(get1), false));
   3629   const char resp1[] = "HTTP/1.1 200 OK\r\n"
   3630       "Content-Length: 1\r\n\r\n";
   3631   scoped_ptr<SpdyFrame> wrapped_get_resp1(
   3632       spdy_util_.ConstructSpdyBodyFrame(1, resp1, strlen(resp1), false));
   3633   scoped_ptr<SpdyFrame> wrapped_body1(
   3634       spdy_util_.ConstructSpdyBodyFrame(1, "1", 1, false));
   3635   scoped_ptr<SpdyFrame> window_update(
   3636       spdy_util_.ConstructSpdyWindowUpdate(1, wrapped_get_resp1->size()));
   3637 
   3638   // Fetch https://www.google.com/2 via HTTP.
   3639   const char get2[] = "GET /2 HTTP/1.1\r\n"
   3640       "Host: www.google.com\r\n"
   3641       "Connection: keep-alive\r\n\r\n";
   3642   scoped_ptr<SpdyFrame> wrapped_get2(
   3643       spdy_util_.ConstructSpdyBodyFrame(1, get2, strlen(get2), false));
   3644   const char resp2[] = "HTTP/1.1 200 OK\r\n"
   3645       "Content-Length: 2\r\n\r\n";
   3646   scoped_ptr<SpdyFrame> wrapped_get_resp2(
   3647       spdy_util_.ConstructSpdyBodyFrame(1, resp2, strlen(resp2), false));
   3648   scoped_ptr<SpdyFrame> wrapped_body2(
   3649       spdy_util_.ConstructSpdyBodyFrame(1, "22", 2, false));
   3650 
   3651   MockWrite spdy_writes[] = {
   3652       CreateMockWrite(*connect1, 0),
   3653       CreateMockWrite(*wrapped_get1, 2),
   3654       CreateMockWrite(*wrapped_get2, 5),
   3655   };
   3656 
   3657   MockRead spdy_reads[] = {
   3658     CreateMockRead(*conn_resp1, 1, ASYNC),
   3659     CreateMockRead(*wrapped_get_resp1, 3, ASYNC),
   3660     CreateMockRead(*wrapped_body1, 4, ASYNC),
   3661     CreateMockRead(*wrapped_get_resp2, 6, ASYNC),
   3662     CreateMockRead(*wrapped_body2, 7, ASYNC),
   3663     MockRead(ASYNC, 0, 8),
   3664   };
   3665 
   3666   DeterministicSocketData spdy_data(
   3667       spdy_reads, arraysize(spdy_reads),
   3668       spdy_writes, arraysize(spdy_writes));
   3669   session_deps_.deterministic_socket_factory->AddSocketDataProvider(&spdy_data);
   3670 
   3671   SSLSocketDataProvider ssl(ASYNC, OK);
   3672   ssl.SetNextProto(GetParam());
   3673   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl);
   3674   SSLSocketDataProvider ssl2(ASYNC, OK);
   3675   ssl2.was_npn_negotiated = false;
   3676   ssl2.protocol_negotiated = kProtoUnknown;
   3677   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl2);
   3678 
   3679   TestCompletionCallback callback;
   3680 
   3681   scoped_ptr<HttpTransaction> trans(
   3682       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3683   int rv = trans->Start(&request1, callback.callback(), BoundNetLog());
   3684   EXPECT_EQ(ERR_IO_PENDING, rv);
   3685   // The first connect and request, each of their responses, and the body.
   3686   spdy_data.RunFor(5);
   3687 
   3688   rv = callback.WaitForResult();
   3689   EXPECT_EQ(OK, rv);
   3690 
   3691   LoadTimingInfo load_timing_info;
   3692   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3693   TestLoadTimingNotReused(load_timing_info, CONNECT_TIMING_HAS_SSL_TIMES);
   3694 
   3695   const HttpResponseInfo* response = trans->GetResponseInfo();
   3696   ASSERT_TRUE(response != NULL);
   3697   ASSERT_TRUE(response->headers.get() != NULL);
   3698   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3699 
   3700   std::string response_data;
   3701   scoped_refptr<net::IOBuffer> buf(new net::IOBuffer(256));
   3702   EXPECT_EQ(1, trans->Read(buf.get(), 256, callback.callback()));
   3703   trans.reset();
   3704 
   3705   scoped_ptr<HttpTransaction> trans2(
   3706       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3707   rv = trans2->Start(&request2, callback.callback(), BoundNetLog());
   3708   EXPECT_EQ(ERR_IO_PENDING, rv);
   3709 
   3710   // The second request, response, and body.  There should not be a second
   3711   // connect.
   3712   spdy_data.RunFor(3);
   3713   rv = callback.WaitForResult();
   3714   EXPECT_EQ(OK, rv);
   3715 
   3716   LoadTimingInfo load_timing_info2;
   3717   EXPECT_TRUE(trans2->GetLoadTimingInfo(&load_timing_info2));
   3718   TestLoadTimingReused(load_timing_info2);
   3719 
   3720   // The requests should have the same ID.
   3721   EXPECT_EQ(load_timing_info.socket_log_id, load_timing_info2.socket_log_id);
   3722 
   3723   EXPECT_EQ(2, trans2->Read(buf.get(), 256, callback.callback()));
   3724 }
   3725 
   3726 // Test load timing in the case of of two HTTP requests through a SPDY HTTPS
   3727 // Proxy to different servers.
   3728 TEST_P(HttpNetworkTransactionTest,
   3729        HttpsProxySpdyLoadTimingTwoHttpRequests) {
   3730   // Configure against https proxy server "proxy:70".
   3731   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   3732       "https://proxy:70"));
   3733   CapturingBoundNetLog log;
   3734   session_deps_.net_log = log.bound().net_log();
   3735   scoped_refptr<HttpNetworkSession> session(
   3736       SpdySessionDependencies::SpdyCreateSessionDeterministic(&session_deps_));
   3737 
   3738   HttpRequestInfo request1;
   3739   request1.method = "GET";
   3740   request1.url = GURL("http://www.google.com/");
   3741   request1.load_flags = 0;
   3742 
   3743   HttpRequestInfo request2;
   3744   request2.method = "GET";
   3745   request2.url = GURL("http://news.google.com/");
   3746   request2.load_flags = 0;
   3747 
   3748   // http://www.google.com/
   3749   scoped_ptr<SpdyHeaderBlock> headers(
   3750       spdy_util_.ConstructGetHeaderBlockForProxy("http://www.google.com/"));
   3751   scoped_ptr<SpdyFrame> get1(spdy_util_.ConstructSpdyControlFrame(
   3752       headers.Pass(), false, 1, LOWEST, SYN_STREAM, CONTROL_FLAG_FIN, 0));
   3753   scoped_ptr<SpdyFrame> get_resp1(
   3754       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   3755   scoped_ptr<SpdyFrame> body1(
   3756       spdy_util_.ConstructSpdyBodyFrame(1, "1", 1, true));
   3757 
   3758   // http://news.google.com/
   3759   scoped_ptr<SpdyHeaderBlock> headers2(
   3760       spdy_util_.ConstructGetHeaderBlockForProxy("http://news.google.com/"));
   3761   scoped_ptr<SpdyFrame> get2(spdy_util_.ConstructSpdyControlFrame(
   3762       headers2.Pass(), false, 3, LOWEST, SYN_STREAM, CONTROL_FLAG_FIN, 0));
   3763   scoped_ptr<SpdyFrame> get_resp2(
   3764       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   3765   scoped_ptr<SpdyFrame> body2(
   3766       spdy_util_.ConstructSpdyBodyFrame(3, "22", 2, true));
   3767 
   3768   MockWrite spdy_writes[] = {
   3769       CreateMockWrite(*get1, 0),
   3770       CreateMockWrite(*get2, 3),
   3771   };
   3772 
   3773   MockRead spdy_reads[] = {
   3774     CreateMockRead(*get_resp1, 1, ASYNC),
   3775     CreateMockRead(*body1, 2, ASYNC),
   3776     CreateMockRead(*get_resp2, 4, ASYNC),
   3777     CreateMockRead(*body2, 5, ASYNC),
   3778     MockRead(ASYNC, 0, 6),
   3779   };
   3780 
   3781   DeterministicSocketData spdy_data(
   3782       spdy_reads, arraysize(spdy_reads),
   3783       spdy_writes, arraysize(spdy_writes));
   3784   session_deps_.deterministic_socket_factory->AddSocketDataProvider(&spdy_data);
   3785 
   3786   SSLSocketDataProvider ssl(ASYNC, OK);
   3787   ssl.SetNextProto(GetParam());
   3788   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl);
   3789 
   3790   TestCompletionCallback callback;
   3791 
   3792   scoped_ptr<HttpTransaction> trans(
   3793       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3794   int rv = trans->Start(&request1, callback.callback(), BoundNetLog());
   3795   EXPECT_EQ(ERR_IO_PENDING, rv);
   3796   spdy_data.RunFor(2);
   3797 
   3798   rv = callback.WaitForResult();
   3799   EXPECT_EQ(OK, rv);
   3800 
   3801   LoadTimingInfo load_timing_info;
   3802   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3803   TestLoadTimingNotReused(load_timing_info,
   3804                           CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   3805 
   3806   const HttpResponseInfo* response = trans->GetResponseInfo();
   3807   ASSERT_TRUE(response != NULL);
   3808   ASSERT_TRUE(response->headers.get() != NULL);
   3809   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   3810 
   3811   std::string response_data;
   3812   scoped_refptr<net::IOBuffer> buf(new net::IOBuffer(256));
   3813   EXPECT_EQ(ERR_IO_PENDING, trans->Read(buf.get(), 256, callback.callback()));
   3814   spdy_data.RunFor(1);
   3815   EXPECT_EQ(1, callback.WaitForResult());
   3816   // Delete the first request, so the second one can reuse the socket.
   3817   trans.reset();
   3818 
   3819   scoped_ptr<HttpTransaction> trans2(
   3820       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3821   rv = trans2->Start(&request2, callback.callback(), BoundNetLog());
   3822   EXPECT_EQ(ERR_IO_PENDING, rv);
   3823 
   3824   spdy_data.RunFor(2);
   3825   rv = callback.WaitForResult();
   3826   EXPECT_EQ(OK, rv);
   3827 
   3828   LoadTimingInfo load_timing_info2;
   3829   EXPECT_TRUE(trans2->GetLoadTimingInfo(&load_timing_info2));
   3830   TestLoadTimingReused(load_timing_info2);
   3831 
   3832   // The requests should have the same ID.
   3833   EXPECT_EQ(load_timing_info.socket_log_id, load_timing_info2.socket_log_id);
   3834 
   3835   EXPECT_EQ(ERR_IO_PENDING, trans2->Read(buf.get(), 256, callback.callback()));
   3836   spdy_data.RunFor(1);
   3837   EXPECT_EQ(2, callback.WaitForResult());
   3838 }
   3839 
   3840 // Test the challenge-response-retry sequence through an HTTPS Proxy
   3841 TEST_P(HttpNetworkTransactionTest, HttpsProxyAuthRetry) {
   3842   HttpRequestInfo request;
   3843   request.method = "GET";
   3844   request.url = GURL("http://www.google.com/");
   3845   // when the no authentication data flag is set.
   3846   request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA;
   3847 
   3848   // Configure against https proxy server "myproxy:70".
   3849   session_deps_.proxy_service.reset(
   3850       ProxyService::CreateFixed("https://myproxy:70"));
   3851   CapturingBoundNetLog log;
   3852   session_deps_.net_log = log.bound().net_log();
   3853   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3854 
   3855   // Since we have proxy, should use full url
   3856   MockWrite data_writes1[] = {
   3857     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   3858               "Host: www.google.com\r\n"
   3859               "Proxy-Connection: keep-alive\r\n\r\n"),
   3860 
   3861     // After calling trans->RestartWithAuth(), this is the request we should
   3862     // be issuing -- the final header line contains the credentials.
   3863     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   3864               "Host: www.google.com\r\n"
   3865               "Proxy-Connection: keep-alive\r\n"
   3866               "Proxy-Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   3867   };
   3868 
   3869   // The proxy responds to the GET with a 407, using a persistent
   3870   // connection.
   3871   MockRead data_reads1[] = {
   3872     // No credentials.
   3873     MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   3874     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   3875     MockRead("Proxy-Connection: keep-alive\r\n"),
   3876     MockRead("Content-Length: 0\r\n\r\n"),
   3877 
   3878     MockRead("HTTP/1.1 200 OK\r\n"),
   3879     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   3880     MockRead("Content-Length: 100\r\n\r\n"),
   3881     MockRead(SYNCHRONOUS, OK),
   3882   };
   3883 
   3884   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   3885                                  data_writes1, arraysize(data_writes1));
   3886   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   3887   SSLSocketDataProvider ssl(ASYNC, OK);
   3888   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   3889 
   3890   TestCompletionCallback callback1;
   3891 
   3892   scoped_ptr<HttpTransaction> trans(
   3893       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3894 
   3895   int rv = trans->Start(&request, callback1.callback(), log.bound());
   3896   EXPECT_EQ(ERR_IO_PENDING, rv);
   3897 
   3898   rv = callback1.WaitForResult();
   3899   EXPECT_EQ(OK, rv);
   3900 
   3901   LoadTimingInfo load_timing_info;
   3902   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3903   TestLoadTimingNotReused(load_timing_info,
   3904                           CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   3905 
   3906   const HttpResponseInfo* response = trans->GetResponseInfo();
   3907   ASSERT_TRUE(response != NULL);
   3908   ASSERT_FALSE(response->headers.get() == NULL);
   3909   EXPECT_EQ(407, response->headers->response_code());
   3910   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   3911   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   3912 
   3913   TestCompletionCallback callback2;
   3914 
   3915   rv = trans->RestartWithAuth(
   3916       AuthCredentials(kFoo, kBar), callback2.callback());
   3917   EXPECT_EQ(ERR_IO_PENDING, rv);
   3918 
   3919   rv = callback2.WaitForResult();
   3920   EXPECT_EQ(OK, rv);
   3921 
   3922   load_timing_info = LoadTimingInfo();
   3923   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   3924   // Retrying with HTTP AUTH is considered to be reusing a socket.
   3925   TestLoadTimingReused(load_timing_info);
   3926 
   3927   response = trans->GetResponseInfo();
   3928   ASSERT_TRUE(response != NULL);
   3929 
   3930   EXPECT_TRUE(response->headers->IsKeepAlive());
   3931   EXPECT_EQ(200, response->headers->response_code());
   3932   EXPECT_EQ(100, response->headers->GetContentLength());
   3933   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   3934 
   3935   // The password prompt info should not be set.
   3936   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   3937 }
   3938 
   3939 void HttpNetworkTransactionTest::ConnectStatusHelperWithExpectedStatus(
   3940     const MockRead& status, int expected_status) {
   3941   HttpRequestInfo request;
   3942   request.method = "GET";
   3943   request.url = GURL("https://www.google.com/");
   3944   request.load_flags = 0;
   3945 
   3946   // Configure against proxy server "myproxy:70".
   3947   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   3948   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   3949 
   3950   // Since we have proxy, should try to establish tunnel.
   3951   MockWrite data_writes[] = {
   3952     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   3953               "Host: www.google.com\r\n"
   3954               "Proxy-Connection: keep-alive\r\n\r\n"),
   3955   };
   3956 
   3957   MockRead data_reads[] = {
   3958     status,
   3959     MockRead("Content-Length: 10\r\n\r\n"),
   3960     // No response body because the test stops reading here.
   3961     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   3962   };
   3963 
   3964   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   3965                                 data_writes, arraysize(data_writes));
   3966   session_deps_.socket_factory->AddSocketDataProvider(&data);
   3967 
   3968   TestCompletionCallback callback;
   3969 
   3970   scoped_ptr<HttpTransaction> trans(
   3971       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   3972 
   3973   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   3974   EXPECT_EQ(ERR_IO_PENDING, rv);
   3975 
   3976   rv = callback.WaitForResult();
   3977   EXPECT_EQ(expected_status, rv);
   3978 }
   3979 
   3980 void HttpNetworkTransactionTest::ConnectStatusHelper(
   3981     const MockRead& status) {
   3982   ConnectStatusHelperWithExpectedStatus(
   3983       status, ERR_TUNNEL_CONNECTION_FAILED);
   3984 }
   3985 
   3986 TEST_P(HttpNetworkTransactionTest, ConnectStatus100) {
   3987   ConnectStatusHelper(MockRead("HTTP/1.1 100 Continue\r\n"));
   3988 }
   3989 
   3990 TEST_P(HttpNetworkTransactionTest, ConnectStatus101) {
   3991   ConnectStatusHelper(MockRead("HTTP/1.1 101 Switching Protocols\r\n"));
   3992 }
   3993 
   3994 TEST_P(HttpNetworkTransactionTest, ConnectStatus201) {
   3995   ConnectStatusHelper(MockRead("HTTP/1.1 201 Created\r\n"));
   3996 }
   3997 
   3998 TEST_P(HttpNetworkTransactionTest, ConnectStatus202) {
   3999   ConnectStatusHelper(MockRead("HTTP/1.1 202 Accepted\r\n"));
   4000 }
   4001 
   4002 TEST_P(HttpNetworkTransactionTest, ConnectStatus203) {
   4003   ConnectStatusHelper(
   4004       MockRead("HTTP/1.1 203 Non-Authoritative Information\r\n"));
   4005 }
   4006 
   4007 TEST_P(HttpNetworkTransactionTest, ConnectStatus204) {
   4008   ConnectStatusHelper(MockRead("HTTP/1.1 204 No Content\r\n"));
   4009 }
   4010 
   4011 TEST_P(HttpNetworkTransactionTest, ConnectStatus205) {
   4012   ConnectStatusHelper(MockRead("HTTP/1.1 205 Reset Content\r\n"));
   4013 }
   4014 
   4015 TEST_P(HttpNetworkTransactionTest, ConnectStatus206) {
   4016   ConnectStatusHelper(MockRead("HTTP/1.1 206 Partial Content\r\n"));
   4017 }
   4018 
   4019 TEST_P(HttpNetworkTransactionTest, ConnectStatus300) {
   4020   ConnectStatusHelper(MockRead("HTTP/1.1 300 Multiple Choices\r\n"));
   4021 }
   4022 
   4023 TEST_P(HttpNetworkTransactionTest, ConnectStatus301) {
   4024   ConnectStatusHelper(MockRead("HTTP/1.1 301 Moved Permanently\r\n"));
   4025 }
   4026 
   4027 TEST_P(HttpNetworkTransactionTest, ConnectStatus302) {
   4028   ConnectStatusHelper(MockRead("HTTP/1.1 302 Found\r\n"));
   4029 }
   4030 
   4031 TEST_P(HttpNetworkTransactionTest, ConnectStatus303) {
   4032   ConnectStatusHelper(MockRead("HTTP/1.1 303 See Other\r\n"));
   4033 }
   4034 
   4035 TEST_P(HttpNetworkTransactionTest, ConnectStatus304) {
   4036   ConnectStatusHelper(MockRead("HTTP/1.1 304 Not Modified\r\n"));
   4037 }
   4038 
   4039 TEST_P(HttpNetworkTransactionTest, ConnectStatus305) {
   4040   ConnectStatusHelper(MockRead("HTTP/1.1 305 Use Proxy\r\n"));
   4041 }
   4042 
   4043 TEST_P(HttpNetworkTransactionTest, ConnectStatus306) {
   4044   ConnectStatusHelper(MockRead("HTTP/1.1 306\r\n"));
   4045 }
   4046 
   4047 TEST_P(HttpNetworkTransactionTest, ConnectStatus307) {
   4048   ConnectStatusHelper(MockRead("HTTP/1.1 307 Temporary Redirect\r\n"));
   4049 }
   4050 
   4051 TEST_P(HttpNetworkTransactionTest, ConnectStatus308) {
   4052   ConnectStatusHelper(MockRead("HTTP/1.1 308 Permanent Redirect\r\n"));
   4053 }
   4054 
   4055 TEST_P(HttpNetworkTransactionTest, ConnectStatus400) {
   4056   ConnectStatusHelper(MockRead("HTTP/1.1 400 Bad Request\r\n"));
   4057 }
   4058 
   4059 TEST_P(HttpNetworkTransactionTest, ConnectStatus401) {
   4060   ConnectStatusHelper(MockRead("HTTP/1.1 401 Unauthorized\r\n"));
   4061 }
   4062 
   4063 TEST_P(HttpNetworkTransactionTest, ConnectStatus402) {
   4064   ConnectStatusHelper(MockRead("HTTP/1.1 402 Payment Required\r\n"));
   4065 }
   4066 
   4067 TEST_P(HttpNetworkTransactionTest, ConnectStatus403) {
   4068   ConnectStatusHelper(MockRead("HTTP/1.1 403 Forbidden\r\n"));
   4069 }
   4070 
   4071 TEST_P(HttpNetworkTransactionTest, ConnectStatus404) {
   4072   ConnectStatusHelper(MockRead("HTTP/1.1 404 Not Found\r\n"));
   4073 }
   4074 
   4075 TEST_P(HttpNetworkTransactionTest, ConnectStatus405) {
   4076   ConnectStatusHelper(MockRead("HTTP/1.1 405 Method Not Allowed\r\n"));
   4077 }
   4078 
   4079 TEST_P(HttpNetworkTransactionTest, ConnectStatus406) {
   4080   ConnectStatusHelper(MockRead("HTTP/1.1 406 Not Acceptable\r\n"));
   4081 }
   4082 
   4083 TEST_P(HttpNetworkTransactionTest, ConnectStatus407) {
   4084   ConnectStatusHelperWithExpectedStatus(
   4085       MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   4086       ERR_PROXY_AUTH_UNSUPPORTED);
   4087 }
   4088 
   4089 TEST_P(HttpNetworkTransactionTest, ConnectStatus408) {
   4090   ConnectStatusHelper(MockRead("HTTP/1.1 408 Request Timeout\r\n"));
   4091 }
   4092 
   4093 TEST_P(HttpNetworkTransactionTest, ConnectStatus409) {
   4094   ConnectStatusHelper(MockRead("HTTP/1.1 409 Conflict\r\n"));
   4095 }
   4096 
   4097 TEST_P(HttpNetworkTransactionTest, ConnectStatus410) {
   4098   ConnectStatusHelper(MockRead("HTTP/1.1 410 Gone\r\n"));
   4099 }
   4100 
   4101 TEST_P(HttpNetworkTransactionTest, ConnectStatus411) {
   4102   ConnectStatusHelper(MockRead("HTTP/1.1 411 Length Required\r\n"));
   4103 }
   4104 
   4105 TEST_P(HttpNetworkTransactionTest, ConnectStatus412) {
   4106   ConnectStatusHelper(MockRead("HTTP/1.1 412 Precondition Failed\r\n"));
   4107 }
   4108 
   4109 TEST_P(HttpNetworkTransactionTest, ConnectStatus413) {
   4110   ConnectStatusHelper(MockRead("HTTP/1.1 413 Request Entity Too Large\r\n"));
   4111 }
   4112 
   4113 TEST_P(HttpNetworkTransactionTest, ConnectStatus414) {
   4114   ConnectStatusHelper(MockRead("HTTP/1.1 414 Request-URI Too Long\r\n"));
   4115 }
   4116 
   4117 TEST_P(HttpNetworkTransactionTest, ConnectStatus415) {
   4118   ConnectStatusHelper(MockRead("HTTP/1.1 415 Unsupported Media Type\r\n"));
   4119 }
   4120 
   4121 TEST_P(HttpNetworkTransactionTest, ConnectStatus416) {
   4122   ConnectStatusHelper(
   4123       MockRead("HTTP/1.1 416 Requested Range Not Satisfiable\r\n"));
   4124 }
   4125 
   4126 TEST_P(HttpNetworkTransactionTest, ConnectStatus417) {
   4127   ConnectStatusHelper(MockRead("HTTP/1.1 417 Expectation Failed\r\n"));
   4128 }
   4129 
   4130 TEST_P(HttpNetworkTransactionTest, ConnectStatus500) {
   4131   ConnectStatusHelper(MockRead("HTTP/1.1 500 Internal Server Error\r\n"));
   4132 }
   4133 
   4134 TEST_P(HttpNetworkTransactionTest, ConnectStatus501) {
   4135   ConnectStatusHelper(MockRead("HTTP/1.1 501 Not Implemented\r\n"));
   4136 }
   4137 
   4138 TEST_P(HttpNetworkTransactionTest, ConnectStatus502) {
   4139   ConnectStatusHelper(MockRead("HTTP/1.1 502 Bad Gateway\r\n"));
   4140 }
   4141 
   4142 TEST_P(HttpNetworkTransactionTest, ConnectStatus503) {
   4143   ConnectStatusHelper(MockRead("HTTP/1.1 503 Service Unavailable\r\n"));
   4144 }
   4145 
   4146 TEST_P(HttpNetworkTransactionTest, ConnectStatus504) {
   4147   ConnectStatusHelper(MockRead("HTTP/1.1 504 Gateway Timeout\r\n"));
   4148 }
   4149 
   4150 TEST_P(HttpNetworkTransactionTest, ConnectStatus505) {
   4151   ConnectStatusHelper(MockRead("HTTP/1.1 505 HTTP Version Not Supported\r\n"));
   4152 }
   4153 
   4154 // Test the flow when both the proxy server AND origin server require
   4155 // authentication. Again, this uses basic auth for both since that is
   4156 // the simplest to mock.
   4157 TEST_P(HttpNetworkTransactionTest, BasicAuthProxyThenServer) {
   4158   HttpRequestInfo request;
   4159   request.method = "GET";
   4160   request.url = GURL("http://www.google.com/");
   4161   request.load_flags = 0;
   4162 
   4163   // Configure against proxy server "myproxy:70".
   4164   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   4165   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4166 
   4167   scoped_ptr<HttpTransaction> trans(
   4168       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   4169 
   4170   MockWrite data_writes1[] = {
   4171     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   4172               "Host: www.google.com\r\n"
   4173               "Proxy-Connection: keep-alive\r\n\r\n"),
   4174   };
   4175 
   4176   MockRead data_reads1[] = {
   4177     MockRead("HTTP/1.0 407 Unauthorized\r\n"),
   4178     // Give a couple authenticate options (only the middle one is actually
   4179     // supported).
   4180     MockRead("Proxy-Authenticate: Basic invalid\r\n"),  // Malformed.
   4181     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   4182     MockRead("Proxy-Authenticate: UNSUPPORTED realm=\"FOO\"\r\n"),
   4183     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   4184     // Large content-length -- won't matter, as connection will be reset.
   4185     MockRead("Content-Length: 10000\r\n\r\n"),
   4186     MockRead(SYNCHRONOUS, ERR_FAILED),
   4187   };
   4188 
   4189   // After calling trans->RestartWithAuth() the first time, this is the
   4190   // request we should be issuing -- the final header line contains the
   4191   // proxy's credentials.
   4192   MockWrite data_writes2[] = {
   4193     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   4194               "Host: www.google.com\r\n"
   4195               "Proxy-Connection: keep-alive\r\n"
   4196               "Proxy-Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   4197   };
   4198 
   4199   // Now the proxy server lets the request pass through to origin server.
   4200   // The origin server responds with a 401.
   4201   MockRead data_reads2[] = {
   4202     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   4203     // Note: We are using the same realm-name as the proxy server. This is
   4204     // completely valid, as realms are unique across hosts.
   4205     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   4206     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   4207     MockRead("Content-Length: 2000\r\n\r\n"),
   4208     MockRead(SYNCHRONOUS, ERR_FAILED),  // Won't be reached.
   4209   };
   4210 
   4211   // After calling trans->RestartWithAuth() the second time, we should send
   4212   // the credentials for both the proxy and origin server.
   4213   MockWrite data_writes3[] = {
   4214     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   4215               "Host: www.google.com\r\n"
   4216               "Proxy-Connection: keep-alive\r\n"
   4217               "Proxy-Authorization: Basic Zm9vOmJhcg==\r\n"
   4218               "Authorization: Basic Zm9vMjpiYXIy\r\n\r\n"),
   4219   };
   4220 
   4221   // Lastly we get the desired content.
   4222   MockRead data_reads3[] = {
   4223     MockRead("HTTP/1.0 200 OK\r\n"),
   4224     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   4225     MockRead("Content-Length: 100\r\n\r\n"),
   4226     MockRead(SYNCHRONOUS, OK),
   4227   };
   4228 
   4229   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   4230                                  data_writes1, arraysize(data_writes1));
   4231   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   4232                                  data_writes2, arraysize(data_writes2));
   4233   StaticSocketDataProvider data3(data_reads3, arraysize(data_reads3),
   4234                                  data_writes3, arraysize(data_writes3));
   4235   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   4236   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   4237   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   4238 
   4239   TestCompletionCallback callback1;
   4240 
   4241   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   4242   EXPECT_EQ(ERR_IO_PENDING, rv);
   4243 
   4244   rv = callback1.WaitForResult();
   4245   EXPECT_EQ(OK, rv);
   4246 
   4247   const HttpResponseInfo* response = trans->GetResponseInfo();
   4248   ASSERT_TRUE(response != NULL);
   4249   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   4250 
   4251   TestCompletionCallback callback2;
   4252 
   4253   rv = trans->RestartWithAuth(
   4254       AuthCredentials(kFoo, kBar), callback2.callback());
   4255   EXPECT_EQ(ERR_IO_PENDING, rv);
   4256 
   4257   rv = callback2.WaitForResult();
   4258   EXPECT_EQ(OK, rv);
   4259 
   4260   response = trans->GetResponseInfo();
   4261   ASSERT_TRUE(response != NULL);
   4262   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   4263 
   4264   TestCompletionCallback callback3;
   4265 
   4266   rv = trans->RestartWithAuth(
   4267       AuthCredentials(kFoo2, kBar2), callback3.callback());
   4268   EXPECT_EQ(ERR_IO_PENDING, rv);
   4269 
   4270   rv = callback3.WaitForResult();
   4271   EXPECT_EQ(OK, rv);
   4272 
   4273   response = trans->GetResponseInfo();
   4274   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   4275   EXPECT_EQ(100, response->headers->GetContentLength());
   4276 }
   4277 
   4278 // For the NTLM implementation using SSPI, we skip the NTLM tests since we
   4279 // can't hook into its internals to cause it to generate predictable NTLM
   4280 // authorization headers.
   4281 #if defined(NTLM_PORTABLE)
   4282 // The NTLM authentication unit tests were generated by capturing the HTTP
   4283 // requests and responses using Fiddler 2 and inspecting the generated random
   4284 // bytes in the debugger.
   4285 
   4286 // Enter the correct password and authenticate successfully.
   4287 TEST_P(HttpNetworkTransactionTest, NTLMAuth1) {
   4288   HttpRequestInfo request;
   4289   request.method = "GET";
   4290   request.url = GURL("http://172.22.68.17/kids/login.aspx");
   4291 
   4292   // Ensure load is not disrupted by flags which suppress behaviour specific
   4293   // to other auth schemes.
   4294   request.load_flags = LOAD_DO_NOT_USE_EMBEDDED_IDENTITY;
   4295 
   4296   HttpAuthHandlerNTLM::ScopedProcSetter proc_setter(MockGenerateRandom1,
   4297                                                     MockGetHostName);
   4298   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4299 
   4300   MockWrite data_writes1[] = {
   4301     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4302               "Host: 172.22.68.17\r\n"
   4303               "Connection: keep-alive\r\n\r\n"),
   4304   };
   4305 
   4306   MockRead data_reads1[] = {
   4307     MockRead("HTTP/1.1 401 Access Denied\r\n"),
   4308     // Negotiate and NTLM are often requested together.  However, we only want
   4309     // to test NTLM. Since Negotiate is preferred over NTLM, we have to skip
   4310     // the header that requests Negotiate for this test.
   4311     MockRead("WWW-Authenticate: NTLM\r\n"),
   4312     MockRead("Connection: close\r\n"),
   4313     MockRead("Content-Length: 42\r\n"),
   4314     MockRead("Content-Type: text/html\r\n\r\n"),
   4315     // Missing content -- won't matter, as connection will be reset.
   4316     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),
   4317   };
   4318 
   4319   MockWrite data_writes2[] = {
   4320     // After restarting with a null identity, this is the
   4321     // request we should be issuing -- the final header line contains a Type
   4322     // 1 message.
   4323     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4324               "Host: 172.22.68.17\r\n"
   4325               "Connection: keep-alive\r\n"
   4326               "Authorization: NTLM "
   4327               "TlRMTVNTUAABAAAAB4IIAAAAAAAAAAAAAAAAAAAAAAA=\r\n\r\n"),
   4328 
   4329     // After calling trans->RestartWithAuth(), we should send a Type 3 message
   4330     // (the credentials for the origin server).  The second request continues
   4331     // on the same connection.
   4332     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4333               "Host: 172.22.68.17\r\n"
   4334               "Connection: keep-alive\r\n"
   4335               "Authorization: NTLM TlRMTVNTUAADAAAAGAAYAGgAAAAYABgAgA"
   4336               "AAAAAAAABAAAAAGAAYAEAAAAAQABAAWAAAAAAAAAAAAAAABYIIAHQA"
   4337               "ZQBzAHQAaQBuAGcALQBuAHQAbABtAFcAVABDAC0AVwBJAE4ANwBVKW"
   4338               "Yma5xzVAAAAAAAAAAAAAAAAAAAAACH+gWcm+YsP9Tqb9zCR3WAeZZX"
   4339               "ahlhx5I=\r\n\r\n"),
   4340   };
   4341 
   4342   MockRead data_reads2[] = {
   4343     // The origin server responds with a Type 2 message.
   4344     MockRead("HTTP/1.1 401 Access Denied\r\n"),
   4345     MockRead("WWW-Authenticate: NTLM "
   4346              "TlRMTVNTUAACAAAADAAMADgAAAAFgokCjGpMpPGlYKkAAAAAAAAAALo"
   4347              "AugBEAAAABQEoCgAAAA9HAE8ATwBHAEwARQACAAwARwBPAE8ARwBMAE"
   4348              "UAAQAaAEEASwBFAEUAUwBBAFIAQQAtAEMATwBSAFAABAAeAGMAbwByA"
   4349              "HAALgBnAG8AbwBnAGwAZQAuAGMAbwBtAAMAQABhAGsAZQBlAHMAYQBy"
   4350              "AGEALQBjAG8AcgBwAC4AYQBkAC4AYwBvAHIAcAAuAGcAbwBvAGcAbAB"
   4351              "lAC4AYwBvAG0ABQAeAGMAbwByAHAALgBnAG8AbwBnAGwAZQAuAGMAbw"
   4352              "BtAAAAAAA=\r\n"),
   4353     MockRead("Content-Length: 42\r\n"),
   4354     MockRead("Content-Type: text/html\r\n\r\n"),
   4355     MockRead("You are not authorized to view this page\r\n"),
   4356 
   4357     // Lastly we get the desired content.
   4358     MockRead("HTTP/1.1 200 OK\r\n"),
   4359     MockRead("Content-Type: text/html; charset=utf-8\r\n"),
   4360     MockRead("Content-Length: 13\r\n\r\n"),
   4361     MockRead("Please Login\r\n"),
   4362     MockRead(SYNCHRONOUS, OK),
   4363   };
   4364 
   4365   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   4366                                  data_writes1, arraysize(data_writes1));
   4367   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   4368                                  data_writes2, arraysize(data_writes2));
   4369   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   4370   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   4371 
   4372   TestCompletionCallback callback1;
   4373 
   4374   scoped_ptr<HttpTransaction> trans(
   4375       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4376 
   4377   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   4378   EXPECT_EQ(ERR_IO_PENDING, rv);
   4379 
   4380   rv = callback1.WaitForResult();
   4381   EXPECT_EQ(OK, rv);
   4382 
   4383   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   4384 
   4385   const HttpResponseInfo* response = trans->GetResponseInfo();
   4386   ASSERT_FALSE(response == NULL);
   4387   EXPECT_TRUE(CheckNTLMServerAuth(response->auth_challenge.get()));
   4388 
   4389   TestCompletionCallback callback2;
   4390 
   4391   rv = trans->RestartWithAuth(AuthCredentials(kTestingNTLM, kTestingNTLM),
   4392                               callback2.callback());
   4393   EXPECT_EQ(ERR_IO_PENDING, rv);
   4394 
   4395   rv = callback2.WaitForResult();
   4396   EXPECT_EQ(OK, rv);
   4397 
   4398   EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   4399 
   4400   response = trans->GetResponseInfo();
   4401   ASSERT_TRUE(response != NULL);
   4402   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   4403 
   4404   TestCompletionCallback callback3;
   4405 
   4406   rv = trans->RestartWithAuth(AuthCredentials(), callback3.callback());
   4407   EXPECT_EQ(ERR_IO_PENDING, rv);
   4408 
   4409   rv = callback3.WaitForResult();
   4410   EXPECT_EQ(OK, rv);
   4411 
   4412   response = trans->GetResponseInfo();
   4413   ASSERT_TRUE(response != NULL);
   4414   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   4415   EXPECT_EQ(13, response->headers->GetContentLength());
   4416 }
   4417 
   4418 // Enter a wrong password, and then the correct one.
   4419 TEST_P(HttpNetworkTransactionTest, NTLMAuth2) {
   4420   HttpRequestInfo request;
   4421   request.method = "GET";
   4422   request.url = GURL("http://172.22.68.17/kids/login.aspx");
   4423   request.load_flags = 0;
   4424 
   4425   HttpAuthHandlerNTLM::ScopedProcSetter proc_setter(MockGenerateRandom2,
   4426                                                     MockGetHostName);
   4427   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4428 
   4429   MockWrite data_writes1[] = {
   4430     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4431               "Host: 172.22.68.17\r\n"
   4432               "Connection: keep-alive\r\n\r\n"),
   4433   };
   4434 
   4435   MockRead data_reads1[] = {
   4436     MockRead("HTTP/1.1 401 Access Denied\r\n"),
   4437     // Negotiate and NTLM are often requested together.  However, we only want
   4438     // to test NTLM. Since Negotiate is preferred over NTLM, we have to skip
   4439     // the header that requests Negotiate for this test.
   4440     MockRead("WWW-Authenticate: NTLM\r\n"),
   4441     MockRead("Connection: close\r\n"),
   4442     MockRead("Content-Length: 42\r\n"),
   4443     MockRead("Content-Type: text/html\r\n\r\n"),
   4444     // Missing content -- won't matter, as connection will be reset.
   4445     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),
   4446   };
   4447 
   4448   MockWrite data_writes2[] = {
   4449     // After restarting with a null identity, this is the
   4450     // request we should be issuing -- the final header line contains a Type
   4451     // 1 message.
   4452     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4453               "Host: 172.22.68.17\r\n"
   4454               "Connection: keep-alive\r\n"
   4455               "Authorization: NTLM "
   4456               "TlRMTVNTUAABAAAAB4IIAAAAAAAAAAAAAAAAAAAAAAA=\r\n\r\n"),
   4457 
   4458     // After calling trans->RestartWithAuth(), we should send a Type 3 message
   4459     // (the credentials for the origin server).  The second request continues
   4460     // on the same connection.
   4461     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4462               "Host: 172.22.68.17\r\n"
   4463               "Connection: keep-alive\r\n"
   4464               "Authorization: NTLM TlRMTVNTUAADAAAAGAAYAGgAAAAYABgAgA"
   4465               "AAAAAAAABAAAAAGAAYAEAAAAAQABAAWAAAAAAAAAAAAAAABYIIAHQA"
   4466               "ZQBzAHQAaQBuAGcALQBuAHQAbABtAFcAVABDAC0AVwBJAE4ANwCWeY"
   4467               "XnSZNwoQAAAAAAAAAAAAAAAAAAAADLa34/phTTKzNTWdub+uyFleOj"
   4468               "4Ww7b7E=\r\n\r\n"),
   4469   };
   4470 
   4471   MockRead data_reads2[] = {
   4472     // The origin server responds with a Type 2 message.
   4473     MockRead("HTTP/1.1 401 Access Denied\r\n"),
   4474     MockRead("WWW-Authenticate: NTLM "
   4475              "TlRMTVNTUAACAAAADAAMADgAAAAFgokCbVWUZezVGpAAAAAAAAAAALo"
   4476              "AugBEAAAABQEoCgAAAA9HAE8ATwBHAEwARQACAAwARwBPAE8ARwBMAE"
   4477              "UAAQAaAEEASwBFAEUAUwBBAFIAQQAtAEMATwBSAFAABAAeAGMAbwByA"
   4478              "HAALgBnAG8AbwBnAGwAZQAuAGMAbwBtAAMAQABhAGsAZQBlAHMAYQBy"
   4479              "AGEALQBjAG8AcgBwAC4AYQBkAC4AYwBvAHIAcAAuAGcAbwBvAGcAbAB"
   4480              "lAC4AYwBvAG0ABQAeAGMAbwByAHAALgBnAG8AbwBnAGwAZQAuAGMAbw"
   4481              "BtAAAAAAA=\r\n"),
   4482     MockRead("Content-Length: 42\r\n"),
   4483     MockRead("Content-Type: text/html\r\n\r\n"),
   4484     MockRead("You are not authorized to view this page\r\n"),
   4485 
   4486     // Wrong password.
   4487     MockRead("HTTP/1.1 401 Access Denied\r\n"),
   4488     MockRead("WWW-Authenticate: NTLM\r\n"),
   4489     MockRead("Connection: close\r\n"),
   4490     MockRead("Content-Length: 42\r\n"),
   4491     MockRead("Content-Type: text/html\r\n\r\n"),
   4492     // Missing content -- won't matter, as connection will be reset.
   4493     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),
   4494   };
   4495 
   4496   MockWrite data_writes3[] = {
   4497     // After restarting with a null identity, this is the
   4498     // request we should be issuing -- the final header line contains a Type
   4499     // 1 message.
   4500     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4501               "Host: 172.22.68.17\r\n"
   4502               "Connection: keep-alive\r\n"
   4503               "Authorization: NTLM "
   4504               "TlRMTVNTUAABAAAAB4IIAAAAAAAAAAAAAAAAAAAAAAA=\r\n\r\n"),
   4505 
   4506     // After calling trans->RestartWithAuth(), we should send a Type 3 message
   4507     // (the credentials for the origin server).  The second request continues
   4508     // on the same connection.
   4509     MockWrite("GET /kids/login.aspx HTTP/1.1\r\n"
   4510               "Host: 172.22.68.17\r\n"
   4511               "Connection: keep-alive\r\n"
   4512               "Authorization: NTLM TlRMTVNTUAADAAAAGAAYAGgAAAAYABgAgA"
   4513               "AAAAAAAABAAAAAGAAYAEAAAAAQABAAWAAAAAAAAAAAAAAABYIIAHQA"
   4514               "ZQBzAHQAaQBuAGcALQBuAHQAbABtAFcAVABDAC0AVwBJAE4ANwBO54"
   4515               "dFMVvTHwAAAAAAAAAAAAAAAAAAAACS7sT6Uzw7L0L//WUqlIaVWpbI"
   4516               "+4MUm7c=\r\n\r\n"),
   4517   };
   4518 
   4519   MockRead data_reads3[] = {
   4520     // The origin server responds with a Type 2 message.
   4521     MockRead("HTTP/1.1 401 Access Denied\r\n"),
   4522     MockRead("WWW-Authenticate: NTLM "
   4523              "TlRMTVNTUAACAAAADAAMADgAAAAFgokCL24VN8dgOR8AAAAAAAAAALo"
   4524              "AugBEAAAABQEoCgAAAA9HAE8ATwBHAEwARQACAAwARwBPAE8ARwBMAE"
   4525              "UAAQAaAEEASwBFAEUAUwBBAFIAQQAtAEMATwBSAFAABAAeAGMAbwByA"
   4526              "HAALgBnAG8AbwBnAGwAZQAuAGMAbwBtAAMAQABhAGsAZQBlAHMAYQBy"
   4527              "AGEALQBjAG8AcgBwAC4AYQBkAC4AYwBvAHIAcAAuAGcAbwBvAGcAbAB"
   4528              "lAC4AYwBvAG0ABQAeAGMAbwByAHAALgBnAG8AbwBnAGwAZQAuAGMAbw"
   4529              "BtAAAAAAA=\r\n"),
   4530     MockRead("Content-Length: 42\r\n"),
   4531     MockRead("Content-Type: text/html\r\n\r\n"),
   4532     MockRead("You are not authorized to view this page\r\n"),
   4533 
   4534     // Lastly we get the desired content.
   4535     MockRead("HTTP/1.1 200 OK\r\n"),
   4536     MockRead("Content-Type: text/html; charset=utf-8\r\n"),
   4537     MockRead("Content-Length: 13\r\n\r\n"),
   4538     MockRead("Please Login\r\n"),
   4539     MockRead(SYNCHRONOUS, OK),
   4540   };
   4541 
   4542   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   4543                                  data_writes1, arraysize(data_writes1));
   4544   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   4545                                  data_writes2, arraysize(data_writes2));
   4546   StaticSocketDataProvider data3(data_reads3, arraysize(data_reads3),
   4547                                  data_writes3, arraysize(data_writes3));
   4548   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   4549   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   4550   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   4551 
   4552   TestCompletionCallback callback1;
   4553 
   4554   scoped_ptr<HttpTransaction> trans(
   4555       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4556 
   4557   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   4558   EXPECT_EQ(ERR_IO_PENDING, rv);
   4559 
   4560   rv = callback1.WaitForResult();
   4561   EXPECT_EQ(OK, rv);
   4562 
   4563   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   4564 
   4565   const HttpResponseInfo* response = trans->GetResponseInfo();
   4566   ASSERT_TRUE(response != NULL);
   4567   EXPECT_TRUE(CheckNTLMServerAuth(response->auth_challenge.get()));
   4568 
   4569   TestCompletionCallback callback2;
   4570 
   4571   // Enter the wrong password.
   4572   rv = trans->RestartWithAuth(AuthCredentials(kTestingNTLM, kWrongPassword),
   4573                               callback2.callback());
   4574   EXPECT_EQ(ERR_IO_PENDING, rv);
   4575 
   4576   rv = callback2.WaitForResult();
   4577   EXPECT_EQ(OK, rv);
   4578 
   4579   EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   4580   TestCompletionCallback callback3;
   4581   rv = trans->RestartWithAuth(AuthCredentials(), callback3.callback());
   4582   EXPECT_EQ(ERR_IO_PENDING, rv);
   4583   rv = callback3.WaitForResult();
   4584   EXPECT_EQ(OK, rv);
   4585   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   4586 
   4587   response = trans->GetResponseInfo();
   4588   ASSERT_FALSE(response == NULL);
   4589   EXPECT_TRUE(CheckNTLMServerAuth(response->auth_challenge.get()));
   4590 
   4591   TestCompletionCallback callback4;
   4592 
   4593   // Now enter the right password.
   4594   rv = trans->RestartWithAuth(AuthCredentials(kTestingNTLM, kTestingNTLM),
   4595                               callback4.callback());
   4596   EXPECT_EQ(ERR_IO_PENDING, rv);
   4597 
   4598   rv = callback4.WaitForResult();
   4599   EXPECT_EQ(OK, rv);
   4600 
   4601   EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   4602 
   4603   TestCompletionCallback callback5;
   4604 
   4605   // One more roundtrip
   4606   rv = trans->RestartWithAuth(AuthCredentials(), callback5.callback());
   4607   EXPECT_EQ(ERR_IO_PENDING, rv);
   4608 
   4609   rv = callback5.WaitForResult();
   4610   EXPECT_EQ(OK, rv);
   4611 
   4612   response = trans->GetResponseInfo();
   4613   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   4614   EXPECT_EQ(13, response->headers->GetContentLength());
   4615 }
   4616 #endif  // NTLM_PORTABLE
   4617 
   4618 // Test reading a server response which has only headers, and no body.
   4619 // After some maximum number of bytes is consumed, the transaction should
   4620 // fail with ERR_RESPONSE_HEADERS_TOO_BIG.
   4621 TEST_P(HttpNetworkTransactionTest, LargeHeadersNoBody) {
   4622   HttpRequestInfo request;
   4623   request.method = "GET";
   4624   request.url = GURL("http://www.google.com/");
   4625   request.load_flags = 0;
   4626 
   4627   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4628   scoped_ptr<HttpTransaction> trans(
   4629       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   4630 
   4631   // Respond with 300 kb of headers (we should fail after 256 kb).
   4632   std::string large_headers_string;
   4633   FillLargeHeadersString(&large_headers_string, 300 * 1024);
   4634 
   4635   MockRead data_reads[] = {
   4636     MockRead("HTTP/1.0 200 OK\r\n"),
   4637     MockRead(ASYNC, large_headers_string.data(), large_headers_string.size()),
   4638     MockRead("\r\nBODY"),
   4639     MockRead(SYNCHRONOUS, OK),
   4640   };
   4641   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   4642   session_deps_.socket_factory->AddSocketDataProvider(&data);
   4643 
   4644   TestCompletionCallback callback;
   4645 
   4646   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   4647   EXPECT_EQ(ERR_IO_PENDING, rv);
   4648 
   4649   rv = callback.WaitForResult();
   4650   EXPECT_EQ(ERR_RESPONSE_HEADERS_TOO_BIG, rv);
   4651 
   4652   const HttpResponseInfo* response = trans->GetResponseInfo();
   4653   EXPECT_TRUE(response == NULL);
   4654 }
   4655 
   4656 // Make sure that we don't try to reuse a TCPClientSocket when failing to
   4657 // establish tunnel.
   4658 // http://code.google.com/p/chromium/issues/detail?id=3772
   4659 TEST_P(HttpNetworkTransactionTest,
   4660        DontRecycleTransportSocketForSSLTunnel) {
   4661   HttpRequestInfo request;
   4662   request.method = "GET";
   4663   request.url = GURL("https://www.google.com/");
   4664   request.load_flags = 0;
   4665 
   4666   // Configure against proxy server "myproxy:70".
   4667   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   4668 
   4669   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4670 
   4671   scoped_ptr<HttpTransaction> trans(
   4672       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4673 
   4674   // Since we have proxy, should try to establish tunnel.
   4675   MockWrite data_writes1[] = {
   4676     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   4677               "Host: www.google.com\r\n"
   4678               "Proxy-Connection: keep-alive\r\n\r\n"),
   4679   };
   4680 
   4681   // The proxy responds to the connect with a 404, using a persistent
   4682   // connection. Usually a proxy would return 501 (not implemented),
   4683   // or 200 (tunnel established).
   4684   MockRead data_reads1[] = {
   4685     MockRead("HTTP/1.1 404 Not Found\r\n"),
   4686     MockRead("Content-Length: 10\r\n\r\n"),
   4687     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   4688   };
   4689 
   4690   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   4691                                  data_writes1, arraysize(data_writes1));
   4692   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   4693 
   4694   TestCompletionCallback callback1;
   4695 
   4696   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   4697   EXPECT_EQ(ERR_IO_PENDING, rv);
   4698 
   4699   rv = callback1.WaitForResult();
   4700   EXPECT_EQ(ERR_TUNNEL_CONNECTION_FAILED, rv);
   4701 
   4702   const HttpResponseInfo* response = trans->GetResponseInfo();
   4703   EXPECT_TRUE(response == NULL);
   4704 
   4705   // Empty the current queue.  This is necessary because idle sockets are
   4706   // added to the connection pool asynchronously with a PostTask.
   4707   base::MessageLoop::current()->RunUntilIdle();
   4708 
   4709   // We now check to make sure the TCPClientSocket was not added back to
   4710   // the pool.
   4711   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4712   trans.reset();
   4713   base::MessageLoop::current()->RunUntilIdle();
   4714   // Make sure that the socket didn't get recycled after calling the destructor.
   4715   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4716 }
   4717 
   4718 // Make sure that we recycle a socket after reading all of the response body.
   4719 TEST_P(HttpNetworkTransactionTest, RecycleSocket) {
   4720   HttpRequestInfo request;
   4721   request.method = "GET";
   4722   request.url = GURL("http://www.google.com/");
   4723   request.load_flags = 0;
   4724 
   4725   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4726 
   4727   scoped_ptr<HttpTransaction> trans(
   4728       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4729 
   4730   MockRead data_reads[] = {
   4731     // A part of the response body is received with the response headers.
   4732     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 11\r\n\r\nhel"),
   4733     // The rest of the response body is received in two parts.
   4734     MockRead("lo"),
   4735     MockRead(" world"),
   4736     MockRead("junk"),  // Should not be read!!
   4737     MockRead(SYNCHRONOUS, OK),
   4738   };
   4739 
   4740   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   4741   session_deps_.socket_factory->AddSocketDataProvider(&data);
   4742 
   4743   TestCompletionCallback callback;
   4744 
   4745   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   4746   EXPECT_EQ(ERR_IO_PENDING, rv);
   4747 
   4748   rv = callback.WaitForResult();
   4749   EXPECT_EQ(OK, rv);
   4750 
   4751   const HttpResponseInfo* response = trans->GetResponseInfo();
   4752   ASSERT_TRUE(response != NULL);
   4753 
   4754   EXPECT_TRUE(response->headers.get() != NULL);
   4755   std::string status_line = response->headers->GetStatusLine();
   4756   EXPECT_EQ("HTTP/1.1 200 OK", status_line);
   4757 
   4758   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4759 
   4760   std::string response_data;
   4761   rv = ReadTransaction(trans.get(), &response_data);
   4762   EXPECT_EQ(OK, rv);
   4763   EXPECT_EQ("hello world", response_data);
   4764 
   4765   // Empty the current queue.  This is necessary because idle sockets are
   4766   // added to the connection pool asynchronously with a PostTask.
   4767   base::MessageLoop::current()->RunUntilIdle();
   4768 
   4769   // We now check to make sure the socket was added back to the pool.
   4770   EXPECT_EQ(1, GetIdleSocketCountInTransportSocketPool(session.get()));
   4771 }
   4772 
   4773 // Make sure that we recycle a SSL socket after reading all of the response
   4774 // body.
   4775 TEST_P(HttpNetworkTransactionTest, RecycleSSLSocket) {
   4776   HttpRequestInfo request;
   4777   request.method = "GET";
   4778   request.url = GURL("https://www.google.com/");
   4779   request.load_flags = 0;
   4780 
   4781   MockWrite data_writes[] = {
   4782     MockWrite("GET / HTTP/1.1\r\n"
   4783               "Host: www.google.com\r\n"
   4784               "Connection: keep-alive\r\n\r\n"),
   4785   };
   4786 
   4787   MockRead data_reads[] = {
   4788     MockRead("HTTP/1.1 200 OK\r\n"),
   4789     MockRead("Content-Length: 11\r\n\r\n"),
   4790     MockRead("hello world"),
   4791     MockRead(SYNCHRONOUS, OK),
   4792   };
   4793 
   4794   SSLSocketDataProvider ssl(ASYNC, OK);
   4795   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   4796 
   4797   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   4798                                 data_writes, arraysize(data_writes));
   4799   session_deps_.socket_factory->AddSocketDataProvider(&data);
   4800 
   4801   TestCompletionCallback callback;
   4802 
   4803   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4804   scoped_ptr<HttpTransaction> trans(
   4805       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4806 
   4807   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   4808 
   4809   EXPECT_EQ(ERR_IO_PENDING, rv);
   4810   EXPECT_EQ(OK, callback.WaitForResult());
   4811 
   4812   const HttpResponseInfo* response = trans->GetResponseInfo();
   4813   ASSERT_TRUE(response != NULL);
   4814   ASSERT_TRUE(response->headers.get() != NULL);
   4815   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   4816 
   4817   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4818 
   4819   std::string response_data;
   4820   rv = ReadTransaction(trans.get(), &response_data);
   4821   EXPECT_EQ(OK, rv);
   4822   EXPECT_EQ("hello world", response_data);
   4823 
   4824   // Empty the current queue.  This is necessary because idle sockets are
   4825   // added to the connection pool asynchronously with a PostTask.
   4826   base::MessageLoop::current()->RunUntilIdle();
   4827 
   4828   // We now check to make sure the socket was added back to the pool.
   4829   EXPECT_EQ(1, GetIdleSocketCountInSSLSocketPool(session.get()));
   4830 }
   4831 
   4832 // Grab a SSL socket, use it, and put it back into the pool.  Then, reuse it
   4833 // from the pool and make sure that we recover okay.
   4834 TEST_P(HttpNetworkTransactionTest, RecycleDeadSSLSocket) {
   4835   HttpRequestInfo request;
   4836   request.method = "GET";
   4837   request.url = GURL("https://www.google.com/");
   4838   request.load_flags = 0;
   4839 
   4840   MockWrite data_writes[] = {
   4841     MockWrite("GET / HTTP/1.1\r\n"
   4842               "Host: www.google.com\r\n"
   4843               "Connection: keep-alive\r\n\r\n"),
   4844     MockWrite("GET / HTTP/1.1\r\n"
   4845               "Host: www.google.com\r\n"
   4846               "Connection: keep-alive\r\n\r\n"),
   4847   };
   4848 
   4849   MockRead data_reads[] = {
   4850     MockRead("HTTP/1.1 200 OK\r\n"),
   4851     MockRead("Content-Length: 11\r\n\r\n"),
   4852     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   4853     MockRead("hello world"),
   4854     MockRead(ASYNC, 0, 0)   // EOF
   4855   };
   4856 
   4857   SSLSocketDataProvider ssl(ASYNC, OK);
   4858   SSLSocketDataProvider ssl2(ASYNC, OK);
   4859   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   4860   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl2);
   4861 
   4862   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   4863                                 data_writes, arraysize(data_writes));
   4864   StaticSocketDataProvider data2(data_reads, arraysize(data_reads),
   4865                                 data_writes, arraysize(data_writes));
   4866   session_deps_.socket_factory->AddSocketDataProvider(&data);
   4867   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   4868 
   4869   TestCompletionCallback callback;
   4870 
   4871   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4872   scoped_ptr<HttpTransaction> trans(
   4873       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4874 
   4875   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   4876 
   4877   EXPECT_EQ(ERR_IO_PENDING, rv);
   4878   EXPECT_EQ(OK, callback.WaitForResult());
   4879 
   4880   const HttpResponseInfo* response = trans->GetResponseInfo();
   4881   ASSERT_TRUE(response != NULL);
   4882   ASSERT_TRUE(response->headers.get() != NULL);
   4883   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   4884 
   4885   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4886 
   4887   std::string response_data;
   4888   rv = ReadTransaction(trans.get(), &response_data);
   4889   EXPECT_EQ(OK, rv);
   4890   EXPECT_EQ("hello world", response_data);
   4891 
   4892   // Empty the current queue.  This is necessary because idle sockets are
   4893   // added to the connection pool asynchronously with a PostTask.
   4894   base::MessageLoop::current()->RunUntilIdle();
   4895 
   4896   // We now check to make sure the socket was added back to the pool.
   4897   EXPECT_EQ(1, GetIdleSocketCountInSSLSocketPool(session.get()));
   4898 
   4899   // Now start the second transaction, which should reuse the previous socket.
   4900 
   4901   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4902 
   4903   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   4904 
   4905   EXPECT_EQ(ERR_IO_PENDING, rv);
   4906   EXPECT_EQ(OK, callback.WaitForResult());
   4907 
   4908   response = trans->GetResponseInfo();
   4909   ASSERT_TRUE(response != NULL);
   4910   ASSERT_TRUE(response->headers.get() != NULL);
   4911   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   4912 
   4913   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4914 
   4915   rv = ReadTransaction(trans.get(), &response_data);
   4916   EXPECT_EQ(OK, rv);
   4917   EXPECT_EQ("hello world", response_data);
   4918 
   4919   // Empty the current queue.  This is necessary because idle sockets are
   4920   // added to the connection pool asynchronously with a PostTask.
   4921   base::MessageLoop::current()->RunUntilIdle();
   4922 
   4923   // We now check to make sure the socket was added back to the pool.
   4924   EXPECT_EQ(1, GetIdleSocketCountInSSLSocketPool(session.get()));
   4925 }
   4926 
   4927 // Make sure that we recycle a socket after a zero-length response.
   4928 // http://crbug.com/9880
   4929 TEST_P(HttpNetworkTransactionTest, RecycleSocketAfterZeroContentLength) {
   4930   HttpRequestInfo request;
   4931   request.method = "GET";
   4932   request.url = GURL("http://www.google.com/csi?v=3&s=web&action=&"
   4933                      "tran=undefined&ei=mAXcSeegAo-SMurloeUN&"
   4934                      "e=17259,18167,19592,19773,19981,20133,20173,20233&"
   4935                      "rt=prt.2642,ol.2649,xjs.2951");
   4936   request.load_flags = 0;
   4937 
   4938   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   4939 
   4940   scoped_ptr<HttpTransaction> trans(
   4941       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   4942 
   4943   MockRead data_reads[] = {
   4944     MockRead("HTTP/1.1 204 No Content\r\n"
   4945              "Content-Length: 0\r\n"
   4946              "Content-Type: text/html\r\n\r\n"),
   4947     MockRead("junk"),  // Should not be read!!
   4948     MockRead(SYNCHRONOUS, OK),
   4949   };
   4950 
   4951   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   4952   session_deps_.socket_factory->AddSocketDataProvider(&data);
   4953 
   4954   TestCompletionCallback callback;
   4955 
   4956   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   4957   EXPECT_EQ(ERR_IO_PENDING, rv);
   4958 
   4959   rv = callback.WaitForResult();
   4960   EXPECT_EQ(OK, rv);
   4961 
   4962   const HttpResponseInfo* response = trans->GetResponseInfo();
   4963   ASSERT_TRUE(response != NULL);
   4964 
   4965   EXPECT_TRUE(response->headers.get() != NULL);
   4966   std::string status_line = response->headers->GetStatusLine();
   4967   EXPECT_EQ("HTTP/1.1 204 No Content", status_line);
   4968 
   4969   EXPECT_EQ(0, GetIdleSocketCountInTransportSocketPool(session.get()));
   4970 
   4971   std::string response_data;
   4972   rv = ReadTransaction(trans.get(), &response_data);
   4973   EXPECT_EQ(OK, rv);
   4974   EXPECT_EQ("", response_data);
   4975 
   4976   // Empty the current queue.  This is necessary because idle sockets are
   4977   // added to the connection pool asynchronously with a PostTask.
   4978   base::MessageLoop::current()->RunUntilIdle();
   4979 
   4980   // We now check to make sure the socket was added back to the pool.
   4981   EXPECT_EQ(1, GetIdleSocketCountInTransportSocketPool(session.get()));
   4982 }
   4983 
   4984 TEST_P(HttpNetworkTransactionTest, ResendRequestOnWriteBodyError) {
   4985   ScopedVector<UploadElementReader> element_readers;
   4986   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   4987   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   4988 
   4989   HttpRequestInfo request[2];
   4990   // Transaction 1: a GET request that succeeds.  The socket is recycled
   4991   // after use.
   4992   request[0].method = "GET";
   4993   request[0].url = GURL("http://www.google.com/");
   4994   request[0].load_flags = 0;
   4995   // Transaction 2: a POST request.  Reuses the socket kept alive from
   4996   // transaction 1.  The first attempts fails when writing the POST data.
   4997   // This causes the transaction to retry with a new socket.  The second
   4998   // attempt succeeds.
   4999   request[1].method = "POST";
   5000   request[1].url = GURL("http://www.google.com/login.cgi");
   5001   request[1].upload_data_stream = &upload_data_stream;
   5002   request[1].load_flags = 0;
   5003 
   5004   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5005 
   5006   // The first socket is used for transaction 1 and the first attempt of
   5007   // transaction 2.
   5008 
   5009   // The response of transaction 1.
   5010   MockRead data_reads1[] = {
   5011     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 11\r\n\r\n"),
   5012     MockRead("hello world"),
   5013     MockRead(SYNCHRONOUS, OK),
   5014   };
   5015   // The mock write results of transaction 1 and the first attempt of
   5016   // transaction 2.
   5017   MockWrite data_writes1[] = {
   5018     MockWrite(SYNCHRONOUS, 64),  // GET
   5019     MockWrite(SYNCHRONOUS, 93),  // POST
   5020     MockWrite(SYNCHRONOUS, ERR_CONNECTION_ABORTED),  // POST data
   5021   };
   5022   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5023                                  data_writes1, arraysize(data_writes1));
   5024 
   5025   // The second socket is used for the second attempt of transaction 2.
   5026 
   5027   // The response of transaction 2.
   5028   MockRead data_reads2[] = {
   5029     MockRead("HTTP/1.1 200 OK\r\nContent-Length: 7\r\n\r\n"),
   5030     MockRead("welcome"),
   5031     MockRead(SYNCHRONOUS, OK),
   5032   };
   5033   // The mock write results of the second attempt of transaction 2.
   5034   MockWrite data_writes2[] = {
   5035     MockWrite(SYNCHRONOUS, 93),  // POST
   5036     MockWrite(SYNCHRONOUS, 3),  // POST data
   5037   };
   5038   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5039                                  data_writes2, arraysize(data_writes2));
   5040 
   5041   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5042   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5043 
   5044   const char* kExpectedResponseData[] = {
   5045     "hello world", "welcome"
   5046   };
   5047 
   5048   for (int i = 0; i < 2; ++i) {
   5049     scoped_ptr<HttpTransaction> trans(
   5050         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5051 
   5052     TestCompletionCallback callback;
   5053 
   5054     int rv = trans->Start(&request[i], callback.callback(), BoundNetLog());
   5055     EXPECT_EQ(ERR_IO_PENDING, rv);
   5056 
   5057     rv = callback.WaitForResult();
   5058     EXPECT_EQ(OK, rv);
   5059 
   5060     const HttpResponseInfo* response = trans->GetResponseInfo();
   5061     ASSERT_TRUE(response != NULL);
   5062 
   5063     EXPECT_TRUE(response->headers.get() != NULL);
   5064     EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   5065 
   5066     std::string response_data;
   5067     rv = ReadTransaction(trans.get(), &response_data);
   5068     EXPECT_EQ(OK, rv);
   5069     EXPECT_EQ(kExpectedResponseData[i], response_data);
   5070   }
   5071 }
   5072 
   5073 // Test the request-challenge-retry sequence for basic auth when there is
   5074 // an identity in the URL. The request should be sent as normal, but when
   5075 // it fails the identity from the URL is used to answer the challenge.
   5076 TEST_P(HttpNetworkTransactionTest, AuthIdentityInURL) {
   5077   HttpRequestInfo request;
   5078   request.method = "GET";
   5079   request.url = GURL("http://foo:b@r@www.google.com/");
   5080   request.load_flags = LOAD_NORMAL;
   5081 
   5082   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5083   scoped_ptr<HttpTransaction> trans(
   5084       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   5085 
   5086   // The password contains an escaped character -- for this test to pass it
   5087   // will need to be unescaped by HttpNetworkTransaction.
   5088   EXPECT_EQ("b%40r", request.url.password());
   5089 
   5090   MockWrite data_writes1[] = {
   5091     MockWrite("GET / HTTP/1.1\r\n"
   5092               "Host: www.google.com\r\n"
   5093               "Connection: keep-alive\r\n\r\n"),
   5094   };
   5095 
   5096   MockRead data_reads1[] = {
   5097     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5098     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5099     MockRead("Content-Length: 10\r\n\r\n"),
   5100     MockRead(SYNCHRONOUS, ERR_FAILED),
   5101   };
   5102 
   5103   // After the challenge above, the transaction will be restarted using the
   5104   // identity from the url (foo, b@r) to answer the challenge.
   5105   MockWrite data_writes2[] = {
   5106     MockWrite("GET / HTTP/1.1\r\n"
   5107               "Host: www.google.com\r\n"
   5108               "Connection: keep-alive\r\n"
   5109               "Authorization: Basic Zm9vOmJAcg==\r\n\r\n"),
   5110   };
   5111 
   5112   MockRead data_reads2[] = {
   5113     MockRead("HTTP/1.0 200 OK\r\n"),
   5114     MockRead("Content-Length: 100\r\n\r\n"),
   5115     MockRead(SYNCHRONOUS, OK),
   5116   };
   5117 
   5118   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5119                                  data_writes1, arraysize(data_writes1));
   5120   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5121                                  data_writes2, arraysize(data_writes2));
   5122   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5123   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5124 
   5125   TestCompletionCallback callback1;
   5126   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5127   EXPECT_EQ(ERR_IO_PENDING, rv);
   5128   rv = callback1.WaitForResult();
   5129   EXPECT_EQ(OK, rv);
   5130   EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   5131 
   5132   TestCompletionCallback callback2;
   5133   rv = trans->RestartWithAuth(AuthCredentials(), callback2.callback());
   5134   EXPECT_EQ(ERR_IO_PENDING, rv);
   5135   rv = callback2.WaitForResult();
   5136   EXPECT_EQ(OK, rv);
   5137   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5138 
   5139   const HttpResponseInfo* response = trans->GetResponseInfo();
   5140   ASSERT_TRUE(response != NULL);
   5141 
   5142   // There is no challenge info, since the identity in URL worked.
   5143   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5144 
   5145   EXPECT_EQ(100, response->headers->GetContentLength());
   5146 
   5147   // Empty the current queue.
   5148   base::MessageLoop::current()->RunUntilIdle();
   5149 }
   5150 
   5151 // Test the request-challenge-retry sequence for basic auth when there is an
   5152 // incorrect identity in the URL. The identity from the URL should be used only
   5153 // once.
   5154 TEST_P(HttpNetworkTransactionTest, WrongAuthIdentityInURL) {
   5155   HttpRequestInfo request;
   5156   request.method = "GET";
   5157   // Note: the URL has a username:password in it.  The password "baz" is
   5158   // wrong (should be "bar").
   5159   request.url = GURL("http://foo:baz@www.google.com/");
   5160 
   5161   request.load_flags = LOAD_NORMAL;
   5162 
   5163   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5164   scoped_ptr<HttpTransaction> trans(
   5165       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   5166 
   5167   MockWrite data_writes1[] = {
   5168     MockWrite("GET / HTTP/1.1\r\n"
   5169               "Host: www.google.com\r\n"
   5170               "Connection: keep-alive\r\n\r\n"),
   5171   };
   5172 
   5173   MockRead data_reads1[] = {
   5174     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5175     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5176     MockRead("Content-Length: 10\r\n\r\n"),
   5177     MockRead(SYNCHRONOUS, ERR_FAILED),
   5178   };
   5179 
   5180   // After the challenge above, the transaction will be restarted using the
   5181   // identity from the url (foo, baz) to answer the challenge.
   5182   MockWrite data_writes2[] = {
   5183     MockWrite("GET / HTTP/1.1\r\n"
   5184               "Host: www.google.com\r\n"
   5185               "Connection: keep-alive\r\n"
   5186               "Authorization: Basic Zm9vOmJheg==\r\n\r\n"),
   5187   };
   5188 
   5189   MockRead data_reads2[] = {
   5190     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5191     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5192     MockRead("Content-Length: 10\r\n\r\n"),
   5193     MockRead(SYNCHRONOUS, ERR_FAILED),
   5194   };
   5195 
   5196   // After the challenge above, the transaction will be restarted using the
   5197   // identity supplied by the user (foo, bar) to answer the challenge.
   5198   MockWrite data_writes3[] = {
   5199     MockWrite("GET / HTTP/1.1\r\n"
   5200               "Host: www.google.com\r\n"
   5201               "Connection: keep-alive\r\n"
   5202               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5203   };
   5204 
   5205   MockRead data_reads3[] = {
   5206     MockRead("HTTP/1.0 200 OK\r\n"),
   5207     MockRead("Content-Length: 100\r\n\r\n"),
   5208     MockRead(SYNCHRONOUS, OK),
   5209   };
   5210 
   5211   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5212                                  data_writes1, arraysize(data_writes1));
   5213   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5214                                  data_writes2, arraysize(data_writes2));
   5215   StaticSocketDataProvider data3(data_reads3, arraysize(data_reads3),
   5216                                  data_writes3, arraysize(data_writes3));
   5217   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5218   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5219   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   5220 
   5221   TestCompletionCallback callback1;
   5222 
   5223   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5224   EXPECT_EQ(ERR_IO_PENDING, rv);
   5225 
   5226   rv = callback1.WaitForResult();
   5227   EXPECT_EQ(OK, rv);
   5228 
   5229   EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   5230   TestCompletionCallback callback2;
   5231   rv = trans->RestartWithAuth(AuthCredentials(), callback2.callback());
   5232   EXPECT_EQ(ERR_IO_PENDING, rv);
   5233   rv = callback2.WaitForResult();
   5234   EXPECT_EQ(OK, rv);
   5235   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5236 
   5237   const HttpResponseInfo* response = trans->GetResponseInfo();
   5238   ASSERT_TRUE(response != NULL);
   5239   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   5240 
   5241   TestCompletionCallback callback3;
   5242   rv = trans->RestartWithAuth(
   5243       AuthCredentials(kFoo, kBar), callback3.callback());
   5244   EXPECT_EQ(ERR_IO_PENDING, rv);
   5245   rv = callback3.WaitForResult();
   5246   EXPECT_EQ(OK, rv);
   5247   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5248 
   5249   response = trans->GetResponseInfo();
   5250   ASSERT_TRUE(response != NULL);
   5251 
   5252   // There is no challenge info, since the identity worked.
   5253   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5254 
   5255   EXPECT_EQ(100, response->headers->GetContentLength());
   5256 
   5257   // Empty the current queue.
   5258   base::MessageLoop::current()->RunUntilIdle();
   5259 }
   5260 
   5261 
   5262 // Test the request-challenge-retry sequence for basic auth when there is a
   5263 // correct identity in the URL, but its use is being suppressed. The identity
   5264 // from the URL should never be used.
   5265 TEST_P(HttpNetworkTransactionTest, AuthIdentityInURLSuppressed) {
   5266   HttpRequestInfo request;
   5267   request.method = "GET";
   5268   request.url = GURL("http://foo:bar@www.google.com/");
   5269   request.load_flags = LOAD_DO_NOT_USE_EMBEDDED_IDENTITY;
   5270 
   5271   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5272   scoped_ptr<HttpTransaction> trans(
   5273       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   5274 
   5275   MockWrite data_writes1[] = {
   5276     MockWrite("GET / HTTP/1.1\r\n"
   5277               "Host: www.google.com\r\n"
   5278               "Connection: keep-alive\r\n\r\n"),
   5279   };
   5280 
   5281   MockRead data_reads1[] = {
   5282     MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5283     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5284     MockRead("Content-Length: 10\r\n\r\n"),
   5285     MockRead(SYNCHRONOUS, ERR_FAILED),
   5286   };
   5287 
   5288   // After the challenge above, the transaction will be restarted using the
   5289   // identity supplied by the user, not the one in the URL, to answer the
   5290   // challenge.
   5291   MockWrite data_writes3[] = {
   5292     MockWrite("GET / HTTP/1.1\r\n"
   5293               "Host: www.google.com\r\n"
   5294               "Connection: keep-alive\r\n"
   5295               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5296   };
   5297 
   5298   MockRead data_reads3[] = {
   5299     MockRead("HTTP/1.0 200 OK\r\n"),
   5300     MockRead("Content-Length: 100\r\n\r\n"),
   5301     MockRead(SYNCHRONOUS, OK),
   5302   };
   5303 
   5304   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5305                                  data_writes1, arraysize(data_writes1));
   5306   StaticSocketDataProvider data3(data_reads3, arraysize(data_reads3),
   5307                                  data_writes3, arraysize(data_writes3));
   5308   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5309   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   5310 
   5311   TestCompletionCallback callback1;
   5312   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5313   EXPECT_EQ(ERR_IO_PENDING, rv);
   5314   rv = callback1.WaitForResult();
   5315   EXPECT_EQ(OK, rv);
   5316   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5317 
   5318   const HttpResponseInfo* response = trans->GetResponseInfo();
   5319   ASSERT_TRUE(response != NULL);
   5320   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   5321 
   5322   TestCompletionCallback callback3;
   5323   rv = trans->RestartWithAuth(
   5324       AuthCredentials(kFoo, kBar), callback3.callback());
   5325   EXPECT_EQ(ERR_IO_PENDING, rv);
   5326   rv = callback3.WaitForResult();
   5327   EXPECT_EQ(OK, rv);
   5328   EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5329 
   5330   response = trans->GetResponseInfo();
   5331   ASSERT_TRUE(response != NULL);
   5332 
   5333   // There is no challenge info, since the identity worked.
   5334   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5335   EXPECT_EQ(100, response->headers->GetContentLength());
   5336 
   5337   // Empty the current queue.
   5338   base::MessageLoop::current()->RunUntilIdle();
   5339 }
   5340 
   5341 // Test that previously tried username/passwords for a realm get re-used.
   5342 TEST_P(HttpNetworkTransactionTest, BasicAuthCacheAndPreauth) {
   5343   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5344 
   5345   // Transaction 1: authenticate (foo, bar) on MyRealm1
   5346   {
   5347     HttpRequestInfo request;
   5348     request.method = "GET";
   5349     request.url = GURL("http://www.google.com/x/y/z");
   5350     request.load_flags = 0;
   5351 
   5352     scoped_ptr<HttpTransaction> trans(
   5353         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5354 
   5355     MockWrite data_writes1[] = {
   5356       MockWrite("GET /x/y/z HTTP/1.1\r\n"
   5357                 "Host: www.google.com\r\n"
   5358                 "Connection: keep-alive\r\n\r\n"),
   5359     };
   5360 
   5361     MockRead data_reads1[] = {
   5362       MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5363       MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5364       MockRead("Content-Length: 10000\r\n\r\n"),
   5365       MockRead(SYNCHRONOUS, ERR_FAILED),
   5366     };
   5367 
   5368     // Resend with authorization (username=foo, password=bar)
   5369     MockWrite data_writes2[] = {
   5370       MockWrite("GET /x/y/z HTTP/1.1\r\n"
   5371                 "Host: www.google.com\r\n"
   5372                 "Connection: keep-alive\r\n"
   5373                 "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5374     };
   5375 
   5376     // Sever accepts the authorization.
   5377     MockRead data_reads2[] = {
   5378       MockRead("HTTP/1.0 200 OK\r\n"),
   5379       MockRead("Content-Length: 100\r\n\r\n"),
   5380       MockRead(SYNCHRONOUS, OK),
   5381     };
   5382 
   5383     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5384                                    data_writes1, arraysize(data_writes1));
   5385     StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5386                                    data_writes2, arraysize(data_writes2));
   5387     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5388     session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5389 
   5390     TestCompletionCallback callback1;
   5391 
   5392     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5393     EXPECT_EQ(ERR_IO_PENDING, rv);
   5394 
   5395     rv = callback1.WaitForResult();
   5396     EXPECT_EQ(OK, rv);
   5397 
   5398     const HttpResponseInfo* response = trans->GetResponseInfo();
   5399     ASSERT_TRUE(response != NULL);
   5400     EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   5401 
   5402     TestCompletionCallback callback2;
   5403 
   5404     rv = trans->RestartWithAuth(
   5405         AuthCredentials(kFoo, kBar), callback2.callback());
   5406     EXPECT_EQ(ERR_IO_PENDING, rv);
   5407 
   5408     rv = callback2.WaitForResult();
   5409     EXPECT_EQ(OK, rv);
   5410 
   5411     response = trans->GetResponseInfo();
   5412     ASSERT_TRUE(response != NULL);
   5413     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5414     EXPECT_EQ(100, response->headers->GetContentLength());
   5415   }
   5416 
   5417   // ------------------------------------------------------------------------
   5418 
   5419   // Transaction 2: authenticate (foo2, bar2) on MyRealm2
   5420   {
   5421     HttpRequestInfo request;
   5422     request.method = "GET";
   5423     // Note that Transaction 1 was at /x/y/z, so this is in the same
   5424     // protection space as MyRealm1.
   5425     request.url = GURL("http://www.google.com/x/y/a/b");
   5426     request.load_flags = 0;
   5427 
   5428     scoped_ptr<HttpTransaction> trans(
   5429         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5430 
   5431     MockWrite data_writes1[] = {
   5432       MockWrite("GET /x/y/a/b HTTP/1.1\r\n"
   5433                 "Host: www.google.com\r\n"
   5434                 "Connection: keep-alive\r\n"
   5435                 // Send preemptive authorization for MyRealm1
   5436                 "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5437     };
   5438 
   5439     // The server didn't like the preemptive authorization, and
   5440     // challenges us for a different realm (MyRealm2).
   5441     MockRead data_reads1[] = {
   5442       MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5443       MockRead("WWW-Authenticate: Basic realm=\"MyRealm2\"\r\n"),
   5444       MockRead("Content-Length: 10000\r\n\r\n"),
   5445       MockRead(SYNCHRONOUS, ERR_FAILED),
   5446     };
   5447 
   5448     // Resend with authorization for MyRealm2 (username=foo2, password=bar2)
   5449     MockWrite data_writes2[] = {
   5450       MockWrite("GET /x/y/a/b HTTP/1.1\r\n"
   5451                 "Host: www.google.com\r\n"
   5452                 "Connection: keep-alive\r\n"
   5453                 "Authorization: Basic Zm9vMjpiYXIy\r\n\r\n"),
   5454     };
   5455 
   5456     // Sever accepts the authorization.
   5457     MockRead data_reads2[] = {
   5458       MockRead("HTTP/1.0 200 OK\r\n"),
   5459       MockRead("Content-Length: 100\r\n\r\n"),
   5460       MockRead(SYNCHRONOUS, OK),
   5461     };
   5462 
   5463     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5464                                    data_writes1, arraysize(data_writes1));
   5465     StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5466                                    data_writes2, arraysize(data_writes2));
   5467     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5468     session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5469 
   5470     TestCompletionCallback callback1;
   5471 
   5472     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5473     EXPECT_EQ(ERR_IO_PENDING, rv);
   5474 
   5475     rv = callback1.WaitForResult();
   5476     EXPECT_EQ(OK, rv);
   5477 
   5478     const HttpResponseInfo* response = trans->GetResponseInfo();
   5479     ASSERT_TRUE(response != NULL);
   5480     ASSERT_TRUE(response->auth_challenge.get());
   5481     EXPECT_FALSE(response->auth_challenge->is_proxy);
   5482     EXPECT_EQ("www.google.com:80",
   5483               response->auth_challenge->challenger.ToString());
   5484     EXPECT_EQ("MyRealm2", response->auth_challenge->realm);
   5485     EXPECT_EQ("basic", response->auth_challenge->scheme);
   5486 
   5487     TestCompletionCallback callback2;
   5488 
   5489     rv = trans->RestartWithAuth(
   5490         AuthCredentials(kFoo2, kBar2), callback2.callback());
   5491     EXPECT_EQ(ERR_IO_PENDING, rv);
   5492 
   5493     rv = callback2.WaitForResult();
   5494     EXPECT_EQ(OK, rv);
   5495 
   5496     response = trans->GetResponseInfo();
   5497     ASSERT_TRUE(response != NULL);
   5498     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5499     EXPECT_EQ(100, response->headers->GetContentLength());
   5500   }
   5501 
   5502   // ------------------------------------------------------------------------
   5503 
   5504   // Transaction 3: Resend a request in MyRealm's protection space --
   5505   // succeed with preemptive authorization.
   5506   {
   5507     HttpRequestInfo request;
   5508     request.method = "GET";
   5509     request.url = GURL("http://www.google.com/x/y/z2");
   5510     request.load_flags = 0;
   5511 
   5512     scoped_ptr<HttpTransaction> trans(
   5513         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5514 
   5515     MockWrite data_writes1[] = {
   5516       MockWrite("GET /x/y/z2 HTTP/1.1\r\n"
   5517                 "Host: www.google.com\r\n"
   5518                 "Connection: keep-alive\r\n"
   5519                 // The authorization for MyRealm1 gets sent preemptively
   5520                 // (since the url is in the same protection space)
   5521                 "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5522     };
   5523 
   5524     // Sever accepts the preemptive authorization
   5525     MockRead data_reads1[] = {
   5526       MockRead("HTTP/1.0 200 OK\r\n"),
   5527       MockRead("Content-Length: 100\r\n\r\n"),
   5528       MockRead(SYNCHRONOUS, OK),
   5529     };
   5530 
   5531     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5532                                    data_writes1, arraysize(data_writes1));
   5533     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5534 
   5535     TestCompletionCallback callback1;
   5536 
   5537     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5538     EXPECT_EQ(ERR_IO_PENDING, rv);
   5539 
   5540     rv = callback1.WaitForResult();
   5541     EXPECT_EQ(OK, rv);
   5542 
   5543     const HttpResponseInfo* response = trans->GetResponseInfo();
   5544     ASSERT_TRUE(response != NULL);
   5545 
   5546     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5547     EXPECT_EQ(100, response->headers->GetContentLength());
   5548   }
   5549 
   5550   // ------------------------------------------------------------------------
   5551 
   5552   // Transaction 4: request another URL in MyRealm (however the
   5553   // url is not known to belong to the protection space, so no pre-auth).
   5554   {
   5555     HttpRequestInfo request;
   5556     request.method = "GET";
   5557     request.url = GURL("http://www.google.com/x/1");
   5558     request.load_flags = 0;
   5559 
   5560     scoped_ptr<HttpTransaction> trans(
   5561         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5562 
   5563     MockWrite data_writes1[] = {
   5564       MockWrite("GET /x/1 HTTP/1.1\r\n"
   5565                 "Host: www.google.com\r\n"
   5566                 "Connection: keep-alive\r\n\r\n"),
   5567     };
   5568 
   5569     MockRead data_reads1[] = {
   5570       MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5571       MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5572       MockRead("Content-Length: 10000\r\n\r\n"),
   5573       MockRead(SYNCHRONOUS, ERR_FAILED),
   5574     };
   5575 
   5576     // Resend with authorization from MyRealm's cache.
   5577     MockWrite data_writes2[] = {
   5578       MockWrite("GET /x/1 HTTP/1.1\r\n"
   5579                 "Host: www.google.com\r\n"
   5580                 "Connection: keep-alive\r\n"
   5581                 "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5582     };
   5583 
   5584     // Sever accepts the authorization.
   5585     MockRead data_reads2[] = {
   5586       MockRead("HTTP/1.0 200 OK\r\n"),
   5587       MockRead("Content-Length: 100\r\n\r\n"),
   5588       MockRead(SYNCHRONOUS, OK),
   5589     };
   5590 
   5591     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5592                                    data_writes1, arraysize(data_writes1));
   5593     StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5594                                    data_writes2, arraysize(data_writes2));
   5595     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5596     session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5597 
   5598     TestCompletionCallback callback1;
   5599 
   5600     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5601     EXPECT_EQ(ERR_IO_PENDING, rv);
   5602 
   5603     rv = callback1.WaitForResult();
   5604     EXPECT_EQ(OK, rv);
   5605 
   5606     EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   5607     TestCompletionCallback callback2;
   5608     rv = trans->RestartWithAuth(AuthCredentials(), callback2.callback());
   5609     EXPECT_EQ(ERR_IO_PENDING, rv);
   5610     rv = callback2.WaitForResult();
   5611     EXPECT_EQ(OK, rv);
   5612     EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5613 
   5614     const HttpResponseInfo* response = trans->GetResponseInfo();
   5615     ASSERT_TRUE(response != NULL);
   5616     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5617     EXPECT_EQ(100, response->headers->GetContentLength());
   5618   }
   5619 
   5620   // ------------------------------------------------------------------------
   5621 
   5622   // Transaction 5: request a URL in MyRealm, but the server rejects the
   5623   // cached identity. Should invalidate and re-prompt.
   5624   {
   5625     HttpRequestInfo request;
   5626     request.method = "GET";
   5627     request.url = GURL("http://www.google.com/p/q/t");
   5628     request.load_flags = 0;
   5629 
   5630     scoped_ptr<HttpTransaction> trans(
   5631         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5632 
   5633     MockWrite data_writes1[] = {
   5634       MockWrite("GET /p/q/t HTTP/1.1\r\n"
   5635                 "Host: www.google.com\r\n"
   5636                 "Connection: keep-alive\r\n\r\n"),
   5637     };
   5638 
   5639     MockRead data_reads1[] = {
   5640       MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5641       MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5642       MockRead("Content-Length: 10000\r\n\r\n"),
   5643       MockRead(SYNCHRONOUS, ERR_FAILED),
   5644     };
   5645 
   5646     // Resend with authorization from cache for MyRealm.
   5647     MockWrite data_writes2[] = {
   5648       MockWrite("GET /p/q/t HTTP/1.1\r\n"
   5649                 "Host: www.google.com\r\n"
   5650                 "Connection: keep-alive\r\n"
   5651                 "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   5652     };
   5653 
   5654     // Sever rejects the authorization.
   5655     MockRead data_reads2[] = {
   5656       MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5657       MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   5658       MockRead("Content-Length: 10000\r\n\r\n"),
   5659       MockRead(SYNCHRONOUS, ERR_FAILED),
   5660     };
   5661 
   5662     // At this point we should prompt for new credentials for MyRealm.
   5663     // Restart with username=foo3, password=foo4.
   5664     MockWrite data_writes3[] = {
   5665       MockWrite("GET /p/q/t HTTP/1.1\r\n"
   5666                 "Host: www.google.com\r\n"
   5667                 "Connection: keep-alive\r\n"
   5668                 "Authorization: Basic Zm9vMzpiYXIz\r\n\r\n"),
   5669     };
   5670 
   5671     // Sever accepts the authorization.
   5672     MockRead data_reads3[] = {
   5673       MockRead("HTTP/1.0 200 OK\r\n"),
   5674       MockRead("Content-Length: 100\r\n\r\n"),
   5675       MockRead(SYNCHRONOUS, OK),
   5676     };
   5677 
   5678     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5679                                    data_writes1, arraysize(data_writes1));
   5680     StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5681                                    data_writes2, arraysize(data_writes2));
   5682     StaticSocketDataProvider data3(data_reads3, arraysize(data_reads3),
   5683                                    data_writes3, arraysize(data_writes3));
   5684     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5685     session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5686     session_deps_.socket_factory->AddSocketDataProvider(&data3);
   5687 
   5688     TestCompletionCallback callback1;
   5689 
   5690     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5691     EXPECT_EQ(ERR_IO_PENDING, rv);
   5692 
   5693     rv = callback1.WaitForResult();
   5694     EXPECT_EQ(OK, rv);
   5695 
   5696     EXPECT_TRUE(trans->IsReadyToRestartForAuth());
   5697     TestCompletionCallback callback2;
   5698     rv = trans->RestartWithAuth(AuthCredentials(), callback2.callback());
   5699     EXPECT_EQ(ERR_IO_PENDING, rv);
   5700     rv = callback2.WaitForResult();
   5701     EXPECT_EQ(OK, rv);
   5702     EXPECT_FALSE(trans->IsReadyToRestartForAuth());
   5703 
   5704     const HttpResponseInfo* response = trans->GetResponseInfo();
   5705     ASSERT_TRUE(response != NULL);
   5706     EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   5707 
   5708     TestCompletionCallback callback3;
   5709 
   5710     rv = trans->RestartWithAuth(
   5711         AuthCredentials(kFoo3, kBar3), callback3.callback());
   5712     EXPECT_EQ(ERR_IO_PENDING, rv);
   5713 
   5714     rv = callback3.WaitForResult();
   5715     EXPECT_EQ(OK, rv);
   5716 
   5717     response = trans->GetResponseInfo();
   5718     ASSERT_TRUE(response != NULL);
   5719     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5720     EXPECT_EQ(100, response->headers->GetContentLength());
   5721   }
   5722 }
   5723 
   5724 // Tests that nonce count increments when multiple auth attempts
   5725 // are started with the same nonce.
   5726 TEST_P(HttpNetworkTransactionTest, DigestPreAuthNonceCount) {
   5727   HttpAuthHandlerDigest::Factory* digest_factory =
   5728       new HttpAuthHandlerDigest::Factory();
   5729   HttpAuthHandlerDigest::FixedNonceGenerator* nonce_generator =
   5730       new HttpAuthHandlerDigest::FixedNonceGenerator("0123456789abcdef");
   5731   digest_factory->set_nonce_generator(nonce_generator);
   5732   session_deps_.http_auth_handler_factory.reset(digest_factory);
   5733   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5734 
   5735   // Transaction 1: authenticate (foo, bar) on MyRealm1
   5736   {
   5737     HttpRequestInfo request;
   5738     request.method = "GET";
   5739     request.url = GURL("http://www.google.com/x/y/z");
   5740     request.load_flags = 0;
   5741 
   5742     scoped_ptr<HttpTransaction> trans(
   5743         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5744 
   5745     MockWrite data_writes1[] = {
   5746       MockWrite("GET /x/y/z HTTP/1.1\r\n"
   5747                 "Host: www.google.com\r\n"
   5748                 "Connection: keep-alive\r\n\r\n"),
   5749     };
   5750 
   5751     MockRead data_reads1[] = {
   5752       MockRead("HTTP/1.0 401 Unauthorized\r\n"),
   5753       MockRead("WWW-Authenticate: Digest realm=\"digestive\", nonce=\"OU812\", "
   5754                "algorithm=MD5, qop=\"auth\"\r\n\r\n"),
   5755       MockRead(SYNCHRONOUS, OK),
   5756     };
   5757 
   5758     // Resend with authorization (username=foo, password=bar)
   5759     MockWrite data_writes2[] = {
   5760       MockWrite("GET /x/y/z HTTP/1.1\r\n"
   5761                 "Host: www.google.com\r\n"
   5762                 "Connection: keep-alive\r\n"
   5763                 "Authorization: Digest username=\"foo\", realm=\"digestive\", "
   5764                 "nonce=\"OU812\", uri=\"/x/y/z\", algorithm=MD5, "
   5765                 "response=\"03ffbcd30add722589c1de345d7a927f\", qop=auth, "
   5766                 "nc=00000001, cnonce=\"0123456789abcdef\"\r\n\r\n"),
   5767     };
   5768 
   5769     // Sever accepts the authorization.
   5770     MockRead data_reads2[] = {
   5771       MockRead("HTTP/1.0 200 OK\r\n"),
   5772       MockRead(SYNCHRONOUS, OK),
   5773     };
   5774 
   5775     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5776                                    data_writes1, arraysize(data_writes1));
   5777     StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   5778                                    data_writes2, arraysize(data_writes2));
   5779     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5780     session_deps_.socket_factory->AddSocketDataProvider(&data2);
   5781 
   5782     TestCompletionCallback callback1;
   5783 
   5784     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5785     EXPECT_EQ(ERR_IO_PENDING, rv);
   5786 
   5787     rv = callback1.WaitForResult();
   5788     EXPECT_EQ(OK, rv);
   5789 
   5790     const HttpResponseInfo* response = trans->GetResponseInfo();
   5791     ASSERT_TRUE(response != NULL);
   5792     EXPECT_TRUE(CheckDigestServerAuth(response->auth_challenge.get()));
   5793 
   5794     TestCompletionCallback callback2;
   5795 
   5796     rv = trans->RestartWithAuth(
   5797         AuthCredentials(kFoo, kBar), callback2.callback());
   5798     EXPECT_EQ(ERR_IO_PENDING, rv);
   5799 
   5800     rv = callback2.WaitForResult();
   5801     EXPECT_EQ(OK, rv);
   5802 
   5803     response = trans->GetResponseInfo();
   5804     ASSERT_TRUE(response != NULL);
   5805     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5806   }
   5807 
   5808   // ------------------------------------------------------------------------
   5809 
   5810   // Transaction 2: Request another resource in digestive's protection space.
   5811   // This will preemptively add an Authorization header which should have an
   5812   // "nc" value of 2 (as compared to 1 in the first use.
   5813   {
   5814     HttpRequestInfo request;
   5815     request.method = "GET";
   5816     // Note that Transaction 1 was at /x/y/z, so this is in the same
   5817     // protection space as digest.
   5818     request.url = GURL("http://www.google.com/x/y/a/b");
   5819     request.load_flags = 0;
   5820 
   5821     scoped_ptr<HttpTransaction> trans(
   5822         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   5823 
   5824     MockWrite data_writes1[] = {
   5825       MockWrite("GET /x/y/a/b HTTP/1.1\r\n"
   5826                 "Host: www.google.com\r\n"
   5827                 "Connection: keep-alive\r\n"
   5828                 "Authorization: Digest username=\"foo\", realm=\"digestive\", "
   5829                 "nonce=\"OU812\", uri=\"/x/y/a/b\", algorithm=MD5, "
   5830                 "response=\"d6f9a2c07d1c5df7b89379dca1269b35\", qop=auth, "
   5831                 "nc=00000002, cnonce=\"0123456789abcdef\"\r\n\r\n"),
   5832     };
   5833 
   5834     // Sever accepts the authorization.
   5835     MockRead data_reads1[] = {
   5836       MockRead("HTTP/1.0 200 OK\r\n"),
   5837       MockRead("Content-Length: 100\r\n\r\n"),
   5838       MockRead(SYNCHRONOUS, OK),
   5839     };
   5840 
   5841     StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   5842                                    data_writes1, arraysize(data_writes1));
   5843     session_deps_.socket_factory->AddSocketDataProvider(&data1);
   5844 
   5845     TestCompletionCallback callback1;
   5846 
   5847     int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   5848     EXPECT_EQ(ERR_IO_PENDING, rv);
   5849 
   5850     rv = callback1.WaitForResult();
   5851     EXPECT_EQ(OK, rv);
   5852 
   5853     const HttpResponseInfo* response = trans->GetResponseInfo();
   5854     ASSERT_TRUE(response != NULL);
   5855     EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5856   }
   5857 }
   5858 
   5859 // Test the ResetStateForRestart() private method.
   5860 TEST_P(HttpNetworkTransactionTest, ResetStateForRestart) {
   5861   // Create a transaction (the dependencies aren't important).
   5862   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5863   scoped_ptr<HttpNetworkTransaction> trans(
   5864       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   5865 
   5866   // Setup some state (which we expect ResetStateForRestart() will clear).
   5867   trans->read_buf_ = new IOBuffer(15);
   5868   trans->read_buf_len_ = 15;
   5869   trans->request_headers_.SetHeader("Authorization", "NTLM");
   5870 
   5871   // Setup state in response_
   5872   HttpResponseInfo* response = &trans->response_;
   5873   response->auth_challenge = new AuthChallengeInfo();
   5874   response->ssl_info.cert_status = static_cast<CertStatus>(-1);  // Nonsensical.
   5875   response->response_time = base::Time::Now();
   5876   response->was_cached = true;  // (Wouldn't ever actually be true...)
   5877 
   5878   { // Setup state for response_.vary_data
   5879     HttpRequestInfo request;
   5880     std::string temp("HTTP/1.1 200 OK\nVary: foo, bar\n\n");
   5881     std::replace(temp.begin(), temp.end(), '\n', '\0');
   5882     scoped_refptr<HttpResponseHeaders> headers(new HttpResponseHeaders(temp));
   5883     request.extra_headers.SetHeader("Foo", "1");
   5884     request.extra_headers.SetHeader("bar", "23");
   5885     EXPECT_TRUE(response->vary_data.Init(request, *headers.get()));
   5886   }
   5887 
   5888   // Cause the above state to be reset.
   5889   trans->ResetStateForRestart();
   5890 
   5891   // Verify that the state that needed to be reset, has been reset.
   5892   EXPECT_TRUE(trans->read_buf_.get() == NULL);
   5893   EXPECT_EQ(0, trans->read_buf_len_);
   5894   EXPECT_TRUE(trans->request_headers_.IsEmpty());
   5895   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   5896   EXPECT_TRUE(response->headers.get() == NULL);
   5897   EXPECT_FALSE(response->was_cached);
   5898   EXPECT_EQ(0U, response->ssl_info.cert_status);
   5899   EXPECT_FALSE(response->vary_data.is_valid());
   5900 }
   5901 
   5902 // Test HTTPS connections to a site with a bad certificate
   5903 TEST_P(HttpNetworkTransactionTest, HTTPSBadCertificate) {
   5904   HttpRequestInfo request;
   5905   request.method = "GET";
   5906   request.url = GURL("https://www.google.com/");
   5907   request.load_flags = 0;
   5908 
   5909   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   5910   scoped_ptr<HttpTransaction> trans(
   5911       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   5912 
   5913   MockWrite data_writes[] = {
   5914     MockWrite("GET / HTTP/1.1\r\n"
   5915               "Host: www.google.com\r\n"
   5916               "Connection: keep-alive\r\n\r\n"),
   5917   };
   5918 
   5919   MockRead data_reads[] = {
   5920     MockRead("HTTP/1.0 200 OK\r\n"),
   5921     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   5922     MockRead("Content-Length: 100\r\n\r\n"),
   5923     MockRead(SYNCHRONOUS, OK),
   5924   };
   5925 
   5926   StaticSocketDataProvider ssl_bad_certificate;
   5927   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   5928                                 data_writes, arraysize(data_writes));
   5929   SSLSocketDataProvider ssl_bad(ASYNC, ERR_CERT_AUTHORITY_INVALID);
   5930   SSLSocketDataProvider ssl(ASYNC, OK);
   5931 
   5932   session_deps_.socket_factory->AddSocketDataProvider(&ssl_bad_certificate);
   5933   session_deps_.socket_factory->AddSocketDataProvider(&data);
   5934   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_bad);
   5935   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   5936 
   5937   TestCompletionCallback callback;
   5938 
   5939   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   5940   EXPECT_EQ(ERR_IO_PENDING, rv);
   5941 
   5942   rv = callback.WaitForResult();
   5943   EXPECT_EQ(ERR_CERT_AUTHORITY_INVALID, rv);
   5944 
   5945   rv = trans->RestartIgnoringLastError(callback.callback());
   5946   EXPECT_EQ(ERR_IO_PENDING, rv);
   5947 
   5948   rv = callback.WaitForResult();
   5949   EXPECT_EQ(OK, rv);
   5950 
   5951   const HttpResponseInfo* response = trans->GetResponseInfo();
   5952 
   5953   ASSERT_TRUE(response != NULL);
   5954   EXPECT_EQ(100, response->headers->GetContentLength());
   5955 }
   5956 
   5957 // Test HTTPS connections to a site with a bad certificate, going through a
   5958 // proxy
   5959 TEST_P(HttpNetworkTransactionTest, HTTPSBadCertificateViaProxy) {
   5960   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   5961 
   5962   HttpRequestInfo request;
   5963   request.method = "GET";
   5964   request.url = GURL("https://www.google.com/");
   5965   request.load_flags = 0;
   5966 
   5967   MockWrite proxy_writes[] = {
   5968     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   5969               "Host: www.google.com\r\n"
   5970               "Proxy-Connection: keep-alive\r\n\r\n"),
   5971   };
   5972 
   5973   MockRead proxy_reads[] = {
   5974     MockRead("HTTP/1.0 200 Connected\r\n\r\n"),
   5975     MockRead(SYNCHRONOUS, OK)
   5976   };
   5977 
   5978   MockWrite data_writes[] = {
   5979     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   5980               "Host: www.google.com\r\n"
   5981               "Proxy-Connection: keep-alive\r\n\r\n"),
   5982     MockWrite("GET / HTTP/1.1\r\n"
   5983               "Host: www.google.com\r\n"
   5984               "Connection: keep-alive\r\n\r\n"),
   5985   };
   5986 
   5987   MockRead data_reads[] = {
   5988     MockRead("HTTP/1.0 200 Connected\r\n\r\n"),
   5989     MockRead("HTTP/1.0 200 OK\r\n"),
   5990     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   5991     MockRead("Content-Length: 100\r\n\r\n"),
   5992     MockRead(SYNCHRONOUS, OK),
   5993   };
   5994 
   5995   StaticSocketDataProvider ssl_bad_certificate(
   5996       proxy_reads, arraysize(proxy_reads),
   5997       proxy_writes, arraysize(proxy_writes));
   5998   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   5999                                 data_writes, arraysize(data_writes));
   6000   SSLSocketDataProvider ssl_bad(ASYNC, ERR_CERT_AUTHORITY_INVALID);
   6001   SSLSocketDataProvider ssl(ASYNC, OK);
   6002 
   6003   session_deps_.socket_factory->AddSocketDataProvider(&ssl_bad_certificate);
   6004   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6005   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_bad);
   6006   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   6007 
   6008   TestCompletionCallback callback;
   6009 
   6010   for (int i = 0; i < 2; i++) {
   6011     session_deps_.socket_factory->ResetNextMockIndexes();
   6012 
   6013     scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6014     scoped_ptr<HttpTransaction> trans(
   6015         new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6016 
   6017     int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6018     EXPECT_EQ(ERR_IO_PENDING, rv);
   6019 
   6020     rv = callback.WaitForResult();
   6021     EXPECT_EQ(ERR_CERT_AUTHORITY_INVALID, rv);
   6022 
   6023     rv = trans->RestartIgnoringLastError(callback.callback());
   6024     EXPECT_EQ(ERR_IO_PENDING, rv);
   6025 
   6026     rv = callback.WaitForResult();
   6027     EXPECT_EQ(OK, rv);
   6028 
   6029     const HttpResponseInfo* response = trans->GetResponseInfo();
   6030 
   6031     ASSERT_TRUE(response != NULL);
   6032     EXPECT_EQ(100, response->headers->GetContentLength());
   6033   }
   6034 }
   6035 
   6036 
   6037 // Test HTTPS connections to a site, going through an HTTPS proxy
   6038 TEST_P(HttpNetworkTransactionTest, HTTPSViaHttpsProxy) {
   6039   session_deps_.proxy_service.reset(
   6040       ProxyService::CreateFixedFromPacResult("HTTPS proxy:70"));
   6041   CapturingNetLog net_log;
   6042   session_deps_.net_log = &net_log;
   6043 
   6044   HttpRequestInfo request;
   6045   request.method = "GET";
   6046   request.url = GURL("https://www.google.com/");
   6047   request.load_flags = 0;
   6048 
   6049   MockWrite data_writes[] = {
   6050     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   6051               "Host: www.google.com\r\n"
   6052               "Proxy-Connection: keep-alive\r\n\r\n"),
   6053     MockWrite("GET / HTTP/1.1\r\n"
   6054               "Host: www.google.com\r\n"
   6055               "Connection: keep-alive\r\n\r\n"),
   6056   };
   6057 
   6058   MockRead data_reads[] = {
   6059     MockRead("HTTP/1.0 200 Connected\r\n\r\n"),
   6060     MockRead("HTTP/1.1 200 OK\r\n"),
   6061     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6062     MockRead("Content-Length: 100\r\n\r\n"),
   6063     MockRead(SYNCHRONOUS, OK),
   6064   };
   6065 
   6066   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6067                                 data_writes, arraysize(data_writes));
   6068   SSLSocketDataProvider proxy_ssl(ASYNC, OK);  // SSL to the proxy
   6069   SSLSocketDataProvider tunnel_ssl(ASYNC, OK);  // SSL through the tunnel
   6070 
   6071   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6072   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy_ssl);
   6073   session_deps_.socket_factory->AddSSLSocketDataProvider(&tunnel_ssl);
   6074 
   6075   TestCompletionCallback callback;
   6076 
   6077   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6078   scoped_ptr<HttpTransaction> trans(
   6079       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6080 
   6081   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6082   EXPECT_EQ(ERR_IO_PENDING, rv);
   6083 
   6084   rv = callback.WaitForResult();
   6085   EXPECT_EQ(OK, rv);
   6086   const HttpResponseInfo* response = trans->GetResponseInfo();
   6087 
   6088   ASSERT_TRUE(response != NULL);
   6089 
   6090   EXPECT_TRUE(response->headers->IsKeepAlive());
   6091   EXPECT_EQ(200, response->headers->response_code());
   6092   EXPECT_EQ(100, response->headers->GetContentLength());
   6093   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   6094 
   6095   LoadTimingInfo load_timing_info;
   6096   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   6097   TestLoadTimingNotReusedWithPac(load_timing_info,
   6098                                  CONNECT_TIMING_HAS_SSL_TIMES);
   6099 }
   6100 
   6101 // Test an HTTPS Proxy's ability to redirect a CONNECT request
   6102 TEST_P(HttpNetworkTransactionTest, RedirectOfHttpsConnectViaHttpsProxy) {
   6103   session_deps_.proxy_service.reset(
   6104       ProxyService::CreateFixedFromPacResult("HTTPS proxy:70"));
   6105   CapturingNetLog net_log;
   6106   session_deps_.net_log = &net_log;
   6107 
   6108   HttpRequestInfo request;
   6109   request.method = "GET";
   6110   request.url = GURL("https://www.google.com/");
   6111   request.load_flags = 0;
   6112 
   6113   MockWrite data_writes[] = {
   6114     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   6115               "Host: www.google.com\r\n"
   6116               "Proxy-Connection: keep-alive\r\n\r\n"),
   6117   };
   6118 
   6119   MockRead data_reads[] = {
   6120     MockRead("HTTP/1.1 302 Redirect\r\n"),
   6121     MockRead("Location: http://login.example.com/\r\n"),
   6122     MockRead("Content-Length: 0\r\n\r\n"),
   6123     MockRead(SYNCHRONOUS, OK),
   6124   };
   6125 
   6126   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6127                                 data_writes, arraysize(data_writes));
   6128   SSLSocketDataProvider proxy_ssl(ASYNC, OK);  // SSL to the proxy
   6129 
   6130   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6131   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy_ssl);
   6132 
   6133   TestCompletionCallback callback;
   6134 
   6135   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6136   scoped_ptr<HttpTransaction> trans(
   6137       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6138 
   6139   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6140   EXPECT_EQ(ERR_IO_PENDING, rv);
   6141 
   6142   rv = callback.WaitForResult();
   6143   EXPECT_EQ(OK, rv);
   6144   const HttpResponseInfo* response = trans->GetResponseInfo();
   6145 
   6146   ASSERT_TRUE(response != NULL);
   6147 
   6148   EXPECT_EQ(302, response->headers->response_code());
   6149   std::string url;
   6150   EXPECT_TRUE(response->headers->IsRedirect(&url));
   6151   EXPECT_EQ("http://login.example.com/", url);
   6152 
   6153   // In the case of redirects from proxies, HttpNetworkTransaction returns
   6154   // timing for the proxy connection instead of the connection to the host,
   6155   // and no send / receive times.
   6156   // See HttpNetworkTransaction::OnHttpsProxyTunnelResponse.
   6157   LoadTimingInfo load_timing_info;
   6158   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   6159 
   6160   EXPECT_FALSE(load_timing_info.socket_reused);
   6161   EXPECT_NE(net::NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
   6162 
   6163   EXPECT_FALSE(load_timing_info.proxy_resolve_start.is_null());
   6164   EXPECT_LE(load_timing_info.proxy_resolve_start,
   6165             load_timing_info.proxy_resolve_end);
   6166   EXPECT_LE(load_timing_info.proxy_resolve_end,
   6167             load_timing_info.connect_timing.connect_start);
   6168   ExpectConnectTimingHasTimes(
   6169       load_timing_info.connect_timing,
   6170       CONNECT_TIMING_HAS_DNS_TIMES | CONNECT_TIMING_HAS_SSL_TIMES);
   6171 
   6172   EXPECT_TRUE(load_timing_info.send_start.is_null());
   6173   EXPECT_TRUE(load_timing_info.send_end.is_null());
   6174   EXPECT_TRUE(load_timing_info.receive_headers_end.is_null());
   6175 }
   6176 
   6177 // Test an HTTPS (SPDY) Proxy's ability to redirect a CONNECT request
   6178 TEST_P(HttpNetworkTransactionTest, RedirectOfHttpsConnectViaSpdyProxy) {
   6179   session_deps_.proxy_service.reset(
   6180       ProxyService::CreateFixed("https://proxy:70"));
   6181 
   6182   HttpRequestInfo request;
   6183   request.method = "GET";
   6184   request.url = GURL("https://www.google.com/");
   6185   request.load_flags = 0;
   6186 
   6187   scoped_ptr<SpdyFrame> conn(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   6188                                                              LOWEST));
   6189   scoped_ptr<SpdyFrame> goaway(
   6190       spdy_util_.ConstructSpdyRstStream(1, RST_STREAM_CANCEL));
   6191   MockWrite data_writes[] = {
   6192     CreateMockWrite(*conn.get(), 0, SYNCHRONOUS),
   6193     CreateMockWrite(*goaway.get(), 3, SYNCHRONOUS),
   6194   };
   6195 
   6196   static const char* const kExtraHeaders[] = {
   6197     "location",
   6198     "http://login.example.com/",
   6199   };
   6200   scoped_ptr<SpdyFrame> resp(
   6201       spdy_util_.ConstructSpdySynReplyError("302 Redirect", kExtraHeaders,
   6202                                  arraysize(kExtraHeaders)/2, 1));
   6203   MockRead data_reads[] = {
   6204     CreateMockRead(*resp.get(), 1, SYNCHRONOUS),
   6205     MockRead(ASYNC, 0, 2),  // EOF
   6206   };
   6207 
   6208   DelayedSocketData data(
   6209       1,  // wait for one write to finish before reading.
   6210       data_reads, arraysize(data_reads),
   6211       data_writes, arraysize(data_writes));
   6212   SSLSocketDataProvider proxy_ssl(ASYNC, OK);  // SSL to the proxy
   6213   proxy_ssl.SetNextProto(GetParam());
   6214 
   6215   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6216   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy_ssl);
   6217 
   6218   TestCompletionCallback callback;
   6219 
   6220   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6221   scoped_ptr<HttpTransaction> trans(
   6222       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6223 
   6224   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6225   EXPECT_EQ(ERR_IO_PENDING, rv);
   6226 
   6227   rv = callback.WaitForResult();
   6228   EXPECT_EQ(OK, rv);
   6229   const HttpResponseInfo* response = trans->GetResponseInfo();
   6230 
   6231   ASSERT_TRUE(response != NULL);
   6232 
   6233   EXPECT_EQ(302, response->headers->response_code());
   6234   std::string url;
   6235   EXPECT_TRUE(response->headers->IsRedirect(&url));
   6236   EXPECT_EQ("http://login.example.com/", url);
   6237 }
   6238 
   6239 // Test that an HTTPS proxy's response to a CONNECT request is filtered.
   6240 TEST_P(HttpNetworkTransactionTest,
   6241        ErrorResponseToHttpsConnectViaHttpsProxy) {
   6242   session_deps_.proxy_service.reset(
   6243       ProxyService::CreateFixed("https://proxy:70"));
   6244 
   6245   HttpRequestInfo request;
   6246   request.method = "GET";
   6247   request.url = GURL("https://www.google.com/");
   6248   request.load_flags = 0;
   6249 
   6250   MockWrite data_writes[] = {
   6251     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   6252               "Host: www.google.com\r\n"
   6253               "Proxy-Connection: keep-alive\r\n\r\n"),
   6254   };
   6255 
   6256   MockRead data_reads[] = {
   6257     MockRead("HTTP/1.1 404 Not Found\r\n"),
   6258     MockRead("Content-Length: 23\r\n\r\n"),
   6259     MockRead("The host does not exist"),
   6260     MockRead(SYNCHRONOUS, OK),
   6261   };
   6262 
   6263   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6264                                 data_writes, arraysize(data_writes));
   6265   SSLSocketDataProvider proxy_ssl(ASYNC, OK);  // SSL to the proxy
   6266 
   6267   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6268   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy_ssl);
   6269 
   6270   TestCompletionCallback callback;
   6271 
   6272   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6273   scoped_ptr<HttpTransaction> trans(
   6274       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6275 
   6276   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6277   EXPECT_EQ(ERR_IO_PENDING, rv);
   6278 
   6279   rv = callback.WaitForResult();
   6280   EXPECT_EQ(ERR_TUNNEL_CONNECTION_FAILED, rv);
   6281 
   6282   // TODO(ttuttle): Anything else to check here?
   6283 }
   6284 
   6285 // Test that a SPDY proxy's response to a CONNECT request is filtered.
   6286 TEST_P(HttpNetworkTransactionTest,
   6287        ErrorResponseToHttpsConnectViaSpdyProxy) {
   6288   session_deps_.proxy_service.reset(
   6289      ProxyService::CreateFixed("https://proxy:70"));
   6290 
   6291   HttpRequestInfo request;
   6292   request.method = "GET";
   6293   request.url = GURL("https://www.google.com/");
   6294   request.load_flags = 0;
   6295 
   6296   scoped_ptr<SpdyFrame> conn(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   6297                                                              LOWEST));
   6298   scoped_ptr<SpdyFrame> rst(
   6299       spdy_util_.ConstructSpdyRstStream(1, RST_STREAM_CANCEL));
   6300   MockWrite data_writes[] = {
   6301     CreateMockWrite(*conn.get(), 0, SYNCHRONOUS),
   6302     CreateMockWrite(*rst.get(), 3, SYNCHRONOUS),
   6303   };
   6304 
   6305   static const char* const kExtraHeaders[] = {
   6306     "location",
   6307     "http://login.example.com/",
   6308   };
   6309   scoped_ptr<SpdyFrame> resp(
   6310       spdy_util_.ConstructSpdySynReplyError("404 Not Found", kExtraHeaders,
   6311                                  arraysize(kExtraHeaders)/2, 1));
   6312   scoped_ptr<SpdyFrame> body(
   6313       spdy_util_.ConstructSpdyBodyFrame(
   6314           1, "The host does not exist", 23, true));
   6315   MockRead data_reads[] = {
   6316     CreateMockRead(*resp.get(), 1, SYNCHRONOUS),
   6317     CreateMockRead(*body.get(), 2, SYNCHRONOUS),
   6318     MockRead(ASYNC, 0, 4),  // EOF
   6319   };
   6320 
   6321   DelayedSocketData data(
   6322       1,  // wait for one write to finish before reading.
   6323       data_reads, arraysize(data_reads),
   6324       data_writes, arraysize(data_writes));
   6325   SSLSocketDataProvider proxy_ssl(ASYNC, OK);  // SSL to the proxy
   6326   proxy_ssl.SetNextProto(GetParam());
   6327 
   6328   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6329   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy_ssl);
   6330 
   6331   TestCompletionCallback callback;
   6332 
   6333   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6334   scoped_ptr<HttpTransaction> trans(
   6335       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6336 
   6337   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6338   EXPECT_EQ(ERR_IO_PENDING, rv);
   6339 
   6340   rv = callback.WaitForResult();
   6341   EXPECT_EQ(ERR_TUNNEL_CONNECTION_FAILED, rv);
   6342 
   6343   // TODO(ttuttle): Anything else to check here?
   6344 }
   6345 
   6346 // Test the request-challenge-retry sequence for basic auth, through
   6347 // a SPDY proxy over a single SPDY session.
   6348 TEST_P(HttpNetworkTransactionTest, BasicAuthSpdyProxy) {
   6349   HttpRequestInfo request;
   6350   request.method = "GET";
   6351   request.url = GURL("https://www.google.com/");
   6352   // when the no authentication data flag is set.
   6353   request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA;
   6354 
   6355   // Configure against https proxy server "myproxy:70".
   6356   session_deps_.proxy_service.reset(
   6357       ProxyService::CreateFixedFromPacResult("HTTPS myproxy:70"));
   6358   CapturingBoundNetLog log;
   6359   session_deps_.net_log = log.bound().net_log();
   6360   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6361 
   6362   // Since we have proxy, should try to establish tunnel.
   6363   scoped_ptr<SpdyFrame> req(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   6364                                                             LOWEST));
   6365   scoped_ptr<SpdyFrame> rst(
   6366       spdy_util_.ConstructSpdyRstStream(1, RST_STREAM_CANCEL));
   6367 
   6368   // After calling trans->RestartWithAuth(), this is the request we should
   6369   // be issuing -- the final header line contains the credentials.
   6370   const char* const kAuthCredentials[] = {
   6371       "proxy-authorization", "Basic Zm9vOmJhcg==",
   6372   };
   6373   scoped_ptr<SpdyFrame> connect2(spdy_util_.ConstructSpdyConnect(
   6374       kAuthCredentials, arraysize(kAuthCredentials) / 2, 3, LOWEST));
   6375   // fetch https://www.google.com/ via HTTP
   6376   const char get[] = "GET / HTTP/1.1\r\n"
   6377     "Host: www.google.com\r\n"
   6378     "Connection: keep-alive\r\n\r\n";
   6379   scoped_ptr<SpdyFrame> wrapped_get(
   6380       spdy_util_.ConstructSpdyBodyFrame(3, get, strlen(get), false));
   6381 
   6382   MockWrite spdy_writes[] = {
   6383     CreateMockWrite(*req, 1, ASYNC),
   6384     CreateMockWrite(*rst, 4, ASYNC),
   6385     CreateMockWrite(*connect2, 5),
   6386     CreateMockWrite(*wrapped_get, 8),
   6387   };
   6388 
   6389   // The proxy responds to the connect with a 407, using a persistent
   6390   // connection.
   6391   const char* const kAuthChallenge[] = {
   6392     spdy_util_.GetStatusKey(), "407 Proxy Authentication Required",
   6393     spdy_util_.GetVersionKey(), "HTTP/1.1",
   6394     "proxy-authenticate", "Basic realm=\"MyRealm1\"",
   6395   };
   6396 
   6397   scoped_ptr<SpdyFrame> conn_auth_resp(
   6398       spdy_util_.ConstructSpdyControlFrame(NULL,
   6399                                            0,
   6400                                            false,
   6401                                            1,
   6402                                            LOWEST,
   6403                                            SYN_REPLY,
   6404                                            CONTROL_FLAG_NONE,
   6405                                            kAuthChallenge,
   6406                                            arraysize(kAuthChallenge),
   6407                                            0));
   6408 
   6409   scoped_ptr<SpdyFrame> conn_resp(
   6410       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   6411   const char resp[] = "HTTP/1.1 200 OK\r\n"
   6412       "Content-Length: 5\r\n\r\n";
   6413 
   6414   scoped_ptr<SpdyFrame> wrapped_get_resp(
   6415       spdy_util_.ConstructSpdyBodyFrame(3, resp, strlen(resp), false));
   6416   scoped_ptr<SpdyFrame> wrapped_body(
   6417       spdy_util_.ConstructSpdyBodyFrame(3, "hello", 5, false));
   6418   MockRead spdy_reads[] = {
   6419     CreateMockRead(*conn_auth_resp, 2, ASYNC),
   6420     CreateMockRead(*conn_resp, 6, ASYNC),
   6421     CreateMockRead(*wrapped_get_resp, 9, ASYNC),
   6422     CreateMockRead(*wrapped_body, 10, ASYNC),
   6423     MockRead(ASYNC, OK, 11),  // EOF.  May or may not be read.
   6424   };
   6425 
   6426   OrderedSocketData spdy_data(
   6427       spdy_reads, arraysize(spdy_reads),
   6428       spdy_writes, arraysize(spdy_writes));
   6429   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   6430   // Negotiate SPDY to the proxy
   6431   SSLSocketDataProvider proxy(ASYNC, OK);
   6432   proxy.SetNextProto(GetParam());
   6433   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy);
   6434   // Vanilla SSL to the server
   6435   SSLSocketDataProvider server(ASYNC, OK);
   6436   session_deps_.socket_factory->AddSSLSocketDataProvider(&server);
   6437 
   6438   TestCompletionCallback callback1;
   6439 
   6440   scoped_ptr<HttpTransaction> trans(
   6441       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   6442 
   6443   int rv = trans->Start(&request, callback1.callback(), log.bound());
   6444   EXPECT_EQ(ERR_IO_PENDING, rv);
   6445 
   6446   rv = callback1.WaitForResult();
   6447   EXPECT_EQ(OK, rv);
   6448   net::CapturingNetLog::CapturedEntryList entries;
   6449   log.GetEntries(&entries);
   6450   size_t pos = ExpectLogContainsSomewhere(
   6451       entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_TUNNEL_HEADERS,
   6452       NetLog::PHASE_NONE);
   6453   ExpectLogContainsSomewhere(
   6454       entries, pos,
   6455       NetLog::TYPE_HTTP_TRANSACTION_READ_TUNNEL_RESPONSE_HEADERS,
   6456       NetLog::PHASE_NONE);
   6457 
   6458   const HttpResponseInfo* response = trans->GetResponseInfo();
   6459   ASSERT_TRUE(response != NULL);
   6460   ASSERT_FALSE(response->headers.get() == NULL);
   6461   EXPECT_EQ(407, response->headers->response_code());
   6462   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   6463   EXPECT_TRUE(response->auth_challenge.get() != NULL);
   6464   EXPECT_TRUE(CheckBasicProxyAuth(response->auth_challenge.get()));
   6465 
   6466   TestCompletionCallback callback2;
   6467 
   6468   rv = trans->RestartWithAuth(AuthCredentials(kFoo, kBar),
   6469                               callback2.callback());
   6470   EXPECT_EQ(ERR_IO_PENDING, rv);
   6471 
   6472   rv = callback2.WaitForResult();
   6473   EXPECT_EQ(OK, rv);
   6474 
   6475   response = trans->GetResponseInfo();
   6476   ASSERT_TRUE(response != NULL);
   6477 
   6478   EXPECT_TRUE(response->headers->IsKeepAlive());
   6479   EXPECT_EQ(200, response->headers->response_code());
   6480   EXPECT_EQ(5, response->headers->GetContentLength());
   6481   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   6482 
   6483   // The password prompt info should not be set.
   6484   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   6485 
   6486   LoadTimingInfo load_timing_info;
   6487   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   6488   TestLoadTimingNotReusedWithPac(load_timing_info,
   6489                                  CONNECT_TIMING_HAS_SSL_TIMES);
   6490 
   6491   trans.reset();
   6492   session->CloseAllConnections();
   6493 }
   6494 
   6495 // Test that an explicitly trusted SPDY proxy can push a resource from an
   6496 // origin that is different from that of its associated resource.
   6497 TEST_P(HttpNetworkTransactionTest, CrossOriginProxyPush) {
   6498   HttpRequestInfo request;
   6499   HttpRequestInfo push_request;
   6500 
   6501   request.method = "GET";
   6502   request.url = GURL("http://www.google.com/");
   6503   push_request.method = "GET";
   6504   push_request.url = GURL("http://www.another-origin.com/foo.dat");
   6505 
   6506   // Configure against https proxy server "myproxy:70".
   6507   session_deps_.proxy_service.reset(
   6508       ProxyService::CreateFixedFromPacResult("HTTPS myproxy:70"));
   6509   CapturingBoundNetLog log;
   6510   session_deps_.net_log = log.bound().net_log();
   6511 
   6512   // Enable cross-origin push.
   6513   session_deps_.trusted_spdy_proxy = "myproxy:70";
   6514 
   6515   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6516 
   6517   scoped_ptr<SpdyFrame> stream1_syn(
   6518       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, false));
   6519 
   6520   MockWrite spdy_writes[] = {
   6521     CreateMockWrite(*stream1_syn, 1, ASYNC),
   6522   };
   6523 
   6524   scoped_ptr<SpdyFrame>
   6525       stream1_reply(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   6526 
   6527   scoped_ptr<SpdyFrame>
   6528       stream1_body(spdy_util_.ConstructSpdyBodyFrame(1, true));
   6529 
   6530   scoped_ptr<SpdyFrame>
   6531       stream2_syn(spdy_util_.ConstructSpdyPush(NULL,
   6532                                     0,
   6533                                     2,
   6534                                     1,
   6535                                     "http://www.another-origin.com/foo.dat"));
   6536   const char kPushedData[] = "pushed";
   6537   scoped_ptr<SpdyFrame> stream2_body(
   6538       spdy_util_.ConstructSpdyBodyFrame(
   6539           2, kPushedData, strlen(kPushedData), true));
   6540 
   6541   MockRead spdy_reads[] = {
   6542     CreateMockRead(*stream1_reply, 2, ASYNC),
   6543     CreateMockRead(*stream2_syn, 3, ASYNC),
   6544     CreateMockRead(*stream1_body, 4, ASYNC),
   6545     CreateMockRead(*stream2_body, 5, ASYNC),
   6546     MockRead(ASYNC, ERR_IO_PENDING, 6),  // Force a pause
   6547   };
   6548 
   6549   OrderedSocketData spdy_data(
   6550       spdy_reads, arraysize(spdy_reads),
   6551       spdy_writes, arraysize(spdy_writes));
   6552   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   6553   // Negotiate SPDY to the proxy
   6554   SSLSocketDataProvider proxy(ASYNC, OK);
   6555   proxy.SetNextProto(GetParam());
   6556   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy);
   6557 
   6558   scoped_ptr<HttpTransaction> trans(
   6559       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   6560   TestCompletionCallback callback;
   6561   int rv = trans->Start(&request, callback.callback(), log.bound());
   6562   EXPECT_EQ(ERR_IO_PENDING, rv);
   6563 
   6564   rv = callback.WaitForResult();
   6565   EXPECT_EQ(OK, rv);
   6566   const HttpResponseInfo* response = trans->GetResponseInfo();
   6567 
   6568   scoped_ptr<HttpTransaction> push_trans(
   6569       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   6570   rv = push_trans->Start(&push_request, callback.callback(), log.bound());
   6571   EXPECT_EQ(ERR_IO_PENDING, rv);
   6572 
   6573   rv = callback.WaitForResult();
   6574   EXPECT_EQ(OK, rv);
   6575   const HttpResponseInfo* push_response = push_trans->GetResponseInfo();
   6576 
   6577   ASSERT_TRUE(response != NULL);
   6578   EXPECT_TRUE(response->headers->IsKeepAlive());
   6579 
   6580   EXPECT_EQ(200, response->headers->response_code());
   6581   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   6582 
   6583   std::string response_data;
   6584   rv = ReadTransaction(trans.get(), &response_data);
   6585   EXPECT_EQ(OK, rv);
   6586   EXPECT_EQ("hello!", response_data);
   6587 
   6588   LoadTimingInfo load_timing_info;
   6589   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   6590   TestLoadTimingNotReusedWithPac(load_timing_info,
   6591                                  CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   6592 
   6593   // Verify the pushed stream.
   6594   EXPECT_TRUE(push_response->headers.get() != NULL);
   6595   EXPECT_EQ(200, push_response->headers->response_code());
   6596 
   6597   rv = ReadTransaction(push_trans.get(), &response_data);
   6598   EXPECT_EQ(OK, rv);
   6599   EXPECT_EQ("pushed", response_data);
   6600 
   6601   LoadTimingInfo push_load_timing_info;
   6602   EXPECT_TRUE(push_trans->GetLoadTimingInfo(&push_load_timing_info));
   6603   TestLoadTimingReusedWithPac(push_load_timing_info);
   6604   // The transactions should share a socket ID, despite being for different
   6605   // origins.
   6606   EXPECT_EQ(load_timing_info.socket_log_id,
   6607             push_load_timing_info.socket_log_id);
   6608 
   6609   trans.reset();
   6610   push_trans.reset();
   6611   session->CloseAllConnections();
   6612 }
   6613 
   6614 // Test that an explicitly trusted SPDY proxy cannot push HTTPS content.
   6615 TEST_P(HttpNetworkTransactionTest, CrossOriginProxyPushCorrectness) {
   6616   HttpRequestInfo request;
   6617 
   6618   request.method = "GET";
   6619   request.url = GURL("http://www.google.com/");
   6620 
   6621   // Configure against https proxy server "myproxy:70".
   6622   session_deps_.proxy_service.reset(
   6623       ProxyService::CreateFixed("https://myproxy:70"));
   6624   CapturingBoundNetLog log;
   6625   session_deps_.net_log = log.bound().net_log();
   6626 
   6627   // Enable cross-origin push.
   6628   session_deps_.trusted_spdy_proxy = "myproxy:70";
   6629 
   6630   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6631 
   6632   scoped_ptr<SpdyFrame> stream1_syn(
   6633       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, false));
   6634 
   6635   scoped_ptr<SpdyFrame> push_rst(
   6636       spdy_util_.ConstructSpdyRstStream(2, RST_STREAM_REFUSED_STREAM));
   6637 
   6638   MockWrite spdy_writes[] = {
   6639     CreateMockWrite(*stream1_syn, 1, ASYNC),
   6640     CreateMockWrite(*push_rst, 4),
   6641   };
   6642 
   6643   scoped_ptr<SpdyFrame>
   6644       stream1_reply(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   6645 
   6646   scoped_ptr<SpdyFrame>
   6647       stream1_body(spdy_util_.ConstructSpdyBodyFrame(1, true));
   6648 
   6649   scoped_ptr<SpdyFrame>
   6650       stream2_syn(spdy_util_.ConstructSpdyPush(NULL,
   6651                                     0,
   6652                                     2,
   6653                                     1,
   6654                                     "https://www.another-origin.com/foo.dat"));
   6655 
   6656   MockRead spdy_reads[] = {
   6657     CreateMockRead(*stream1_reply, 2, ASYNC),
   6658     CreateMockRead(*stream2_syn, 3, ASYNC),
   6659     CreateMockRead(*stream1_body, 5, ASYNC),
   6660     MockRead(ASYNC, ERR_IO_PENDING, 6),  // Force a pause
   6661   };
   6662 
   6663   OrderedSocketData spdy_data(
   6664       spdy_reads, arraysize(spdy_reads),
   6665       spdy_writes, arraysize(spdy_writes));
   6666   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   6667   // Negotiate SPDY to the proxy
   6668   SSLSocketDataProvider proxy(ASYNC, OK);
   6669   proxy.SetNextProto(GetParam());
   6670   session_deps_.socket_factory->AddSSLSocketDataProvider(&proxy);
   6671 
   6672   scoped_ptr<HttpTransaction> trans(
   6673       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   6674   TestCompletionCallback callback;
   6675   int rv = trans->Start(&request, callback.callback(), log.bound());
   6676   EXPECT_EQ(ERR_IO_PENDING, rv);
   6677 
   6678   rv = callback.WaitForResult();
   6679   EXPECT_EQ(OK, rv);
   6680   const HttpResponseInfo* response = trans->GetResponseInfo();
   6681 
   6682   ASSERT_TRUE(response != NULL);
   6683   EXPECT_TRUE(response->headers->IsKeepAlive());
   6684 
   6685   EXPECT_EQ(200, response->headers->response_code());
   6686   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   6687 
   6688   std::string response_data;
   6689   rv = ReadTransaction(trans.get(), &response_data);
   6690   EXPECT_EQ(OK, rv);
   6691   EXPECT_EQ("hello!", response_data);
   6692 
   6693   trans.reset();
   6694   session->CloseAllConnections();
   6695 }
   6696 
   6697 // Test HTTPS connections to a site with a bad certificate, going through an
   6698 // HTTPS proxy
   6699 TEST_P(HttpNetworkTransactionTest, HTTPSBadCertificateViaHttpsProxy) {
   6700   session_deps_.proxy_service.reset(ProxyService::CreateFixed(
   6701       "https://proxy:70"));
   6702 
   6703   HttpRequestInfo request;
   6704   request.method = "GET";
   6705   request.url = GURL("https://www.google.com/");
   6706   request.load_flags = 0;
   6707 
   6708   // Attempt to fetch the URL from a server with a bad cert
   6709   MockWrite bad_cert_writes[] = {
   6710     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   6711               "Host: www.google.com\r\n"
   6712               "Proxy-Connection: keep-alive\r\n\r\n"),
   6713   };
   6714 
   6715   MockRead bad_cert_reads[] = {
   6716     MockRead("HTTP/1.0 200 Connected\r\n\r\n"),
   6717     MockRead(SYNCHRONOUS, OK)
   6718   };
   6719 
   6720   // Attempt to fetch the URL with a good cert
   6721   MockWrite good_data_writes[] = {
   6722     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   6723               "Host: www.google.com\r\n"
   6724               "Proxy-Connection: keep-alive\r\n\r\n"),
   6725     MockWrite("GET / HTTP/1.1\r\n"
   6726               "Host: www.google.com\r\n"
   6727               "Connection: keep-alive\r\n\r\n"),
   6728   };
   6729 
   6730   MockRead good_cert_reads[] = {
   6731     MockRead("HTTP/1.0 200 Connected\r\n\r\n"),
   6732     MockRead("HTTP/1.0 200 OK\r\n"),
   6733     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6734     MockRead("Content-Length: 100\r\n\r\n"),
   6735     MockRead(SYNCHRONOUS, OK),
   6736   };
   6737 
   6738   StaticSocketDataProvider ssl_bad_certificate(
   6739       bad_cert_reads, arraysize(bad_cert_reads),
   6740       bad_cert_writes, arraysize(bad_cert_writes));
   6741   StaticSocketDataProvider data(good_cert_reads, arraysize(good_cert_reads),
   6742                                 good_data_writes, arraysize(good_data_writes));
   6743   SSLSocketDataProvider ssl_bad(ASYNC, ERR_CERT_AUTHORITY_INVALID);
   6744   SSLSocketDataProvider ssl(ASYNC, OK);
   6745 
   6746   // SSL to the proxy, then CONNECT request, then SSL with bad certificate
   6747   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   6748   session_deps_.socket_factory->AddSocketDataProvider(&ssl_bad_certificate);
   6749   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_bad);
   6750 
   6751   // SSL to the proxy, then CONNECT request, then valid SSL certificate
   6752   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   6753   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6754   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   6755 
   6756   TestCompletionCallback callback;
   6757 
   6758   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6759   scoped_ptr<HttpTransaction> trans(
   6760       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6761 
   6762   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6763   EXPECT_EQ(ERR_IO_PENDING, rv);
   6764 
   6765   rv = callback.WaitForResult();
   6766   EXPECT_EQ(ERR_CERT_AUTHORITY_INVALID, rv);
   6767 
   6768   rv = trans->RestartIgnoringLastError(callback.callback());
   6769   EXPECT_EQ(ERR_IO_PENDING, rv);
   6770 
   6771   rv = callback.WaitForResult();
   6772   EXPECT_EQ(OK, rv);
   6773 
   6774   const HttpResponseInfo* response = trans->GetResponseInfo();
   6775 
   6776   ASSERT_TRUE(response != NULL);
   6777   EXPECT_EQ(100, response->headers->GetContentLength());
   6778 }
   6779 
   6780 TEST_P(HttpNetworkTransactionTest, BuildRequest_UserAgent) {
   6781   HttpRequestInfo request;
   6782   request.method = "GET";
   6783   request.url = GURL("http://www.google.com/");
   6784   request.extra_headers.SetHeader(HttpRequestHeaders::kUserAgent,
   6785                                   "Chromium Ultra Awesome X Edition");
   6786 
   6787   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6788   scoped_ptr<HttpTransaction> trans(
   6789       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6790 
   6791   MockWrite data_writes[] = {
   6792     MockWrite("GET / HTTP/1.1\r\n"
   6793               "Host: www.google.com\r\n"
   6794               "Connection: keep-alive\r\n"
   6795               "User-Agent: Chromium Ultra Awesome X Edition\r\n\r\n"),
   6796   };
   6797 
   6798   // Lastly, the server responds with the actual content.
   6799   MockRead data_reads[] = {
   6800     MockRead("HTTP/1.0 200 OK\r\n"),
   6801     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6802     MockRead("Content-Length: 100\r\n\r\n"),
   6803     MockRead(SYNCHRONOUS, OK),
   6804   };
   6805 
   6806   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6807                                 data_writes, arraysize(data_writes));
   6808   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6809 
   6810   TestCompletionCallback callback;
   6811 
   6812   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6813   EXPECT_EQ(ERR_IO_PENDING, rv);
   6814 
   6815   rv = callback.WaitForResult();
   6816   EXPECT_EQ(OK, rv);
   6817 }
   6818 
   6819 TEST_P(HttpNetworkTransactionTest, BuildRequest_UserAgentOverTunnel) {
   6820   HttpRequestInfo request;
   6821   request.method = "GET";
   6822   request.url = GURL("https://www.google.com/");
   6823   request.extra_headers.SetHeader(HttpRequestHeaders::kUserAgent,
   6824                                   "Chromium Ultra Awesome X Edition");
   6825 
   6826   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   6827   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6828   scoped_ptr<HttpTransaction> trans(
   6829       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6830 
   6831   MockWrite data_writes[] = {
   6832     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   6833               "Host: www.google.com\r\n"
   6834               "Proxy-Connection: keep-alive\r\n"
   6835               "User-Agent: Chromium Ultra Awesome X Edition\r\n\r\n"),
   6836   };
   6837   MockRead data_reads[] = {
   6838     // Return an error, so the transaction stops here (this test isn't
   6839     // interested in the rest).
   6840     MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
   6841     MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   6842     MockRead("Proxy-Connection: close\r\n\r\n"),
   6843   };
   6844 
   6845   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6846                                 data_writes, arraysize(data_writes));
   6847   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6848 
   6849   TestCompletionCallback callback;
   6850 
   6851   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6852   EXPECT_EQ(ERR_IO_PENDING, rv);
   6853 
   6854   rv = callback.WaitForResult();
   6855   EXPECT_EQ(OK, rv);
   6856 }
   6857 
   6858 TEST_P(HttpNetworkTransactionTest, BuildRequest_Referer) {
   6859   HttpRequestInfo request;
   6860   request.method = "GET";
   6861   request.url = GURL("http://www.google.com/");
   6862   request.load_flags = 0;
   6863   request.extra_headers.SetHeader(HttpRequestHeaders::kReferer,
   6864                                   "http://the.previous.site.com/");
   6865 
   6866   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6867   scoped_ptr<HttpTransaction> trans(
   6868       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6869 
   6870   MockWrite data_writes[] = {
   6871     MockWrite("GET / HTTP/1.1\r\n"
   6872               "Host: www.google.com\r\n"
   6873               "Connection: keep-alive\r\n"
   6874               "Referer: http://the.previous.site.com/\r\n\r\n"),
   6875   };
   6876 
   6877   // Lastly, the server responds with the actual content.
   6878   MockRead data_reads[] = {
   6879     MockRead("HTTP/1.0 200 OK\r\n"),
   6880     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6881     MockRead("Content-Length: 100\r\n\r\n"),
   6882     MockRead(SYNCHRONOUS, OK),
   6883   };
   6884 
   6885   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6886                                 data_writes, arraysize(data_writes));
   6887   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6888 
   6889   TestCompletionCallback callback;
   6890 
   6891   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6892   EXPECT_EQ(ERR_IO_PENDING, rv);
   6893 
   6894   rv = callback.WaitForResult();
   6895   EXPECT_EQ(OK, rv);
   6896 }
   6897 
   6898 TEST_P(HttpNetworkTransactionTest, BuildRequest_PostContentLengthZero) {
   6899   HttpRequestInfo request;
   6900   request.method = "POST";
   6901   request.url = GURL("http://www.google.com/");
   6902 
   6903   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6904   scoped_ptr<HttpTransaction> trans(
   6905       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6906 
   6907   MockWrite data_writes[] = {
   6908     MockWrite("POST / HTTP/1.1\r\n"
   6909               "Host: www.google.com\r\n"
   6910               "Connection: keep-alive\r\n"
   6911               "Content-Length: 0\r\n\r\n"),
   6912   };
   6913 
   6914   // Lastly, the server responds with the actual content.
   6915   MockRead data_reads[] = {
   6916     MockRead("HTTP/1.0 200 OK\r\n"),
   6917     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6918     MockRead("Content-Length: 100\r\n\r\n"),
   6919     MockRead(SYNCHRONOUS, OK),
   6920   };
   6921 
   6922   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6923                                 data_writes, arraysize(data_writes));
   6924   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6925 
   6926   TestCompletionCallback callback;
   6927 
   6928   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6929   EXPECT_EQ(ERR_IO_PENDING, rv);
   6930 
   6931   rv = callback.WaitForResult();
   6932   EXPECT_EQ(OK, rv);
   6933 }
   6934 
   6935 TEST_P(HttpNetworkTransactionTest, BuildRequest_PutContentLengthZero) {
   6936   HttpRequestInfo request;
   6937   request.method = "PUT";
   6938   request.url = GURL("http://www.google.com/");
   6939 
   6940   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6941   scoped_ptr<HttpTransaction> trans(
   6942       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6943 
   6944   MockWrite data_writes[] = {
   6945     MockWrite("PUT / HTTP/1.1\r\n"
   6946               "Host: www.google.com\r\n"
   6947               "Connection: keep-alive\r\n"
   6948               "Content-Length: 0\r\n\r\n"),
   6949   };
   6950 
   6951   // Lastly, the server responds with the actual content.
   6952   MockRead data_reads[] = {
   6953     MockRead("HTTP/1.0 200 OK\r\n"),
   6954     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6955     MockRead("Content-Length: 100\r\n\r\n"),
   6956     MockRead(SYNCHRONOUS, OK),
   6957   };
   6958 
   6959   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6960                                 data_writes, arraysize(data_writes));
   6961   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6962 
   6963   TestCompletionCallback callback;
   6964 
   6965   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   6966   EXPECT_EQ(ERR_IO_PENDING, rv);
   6967 
   6968   rv = callback.WaitForResult();
   6969   EXPECT_EQ(OK, rv);
   6970 }
   6971 
   6972 TEST_P(HttpNetworkTransactionTest, BuildRequest_HeadContentLengthZero) {
   6973   HttpRequestInfo request;
   6974   request.method = "HEAD";
   6975   request.url = GURL("http://www.google.com/");
   6976 
   6977   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   6978   scoped_ptr<HttpTransaction> trans(
   6979       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   6980 
   6981   MockWrite data_writes[] = {
   6982     MockWrite("HEAD / HTTP/1.1\r\n"
   6983               "Host: www.google.com\r\n"
   6984               "Connection: keep-alive\r\n"
   6985               "Content-Length: 0\r\n\r\n"),
   6986   };
   6987 
   6988   // Lastly, the server responds with the actual content.
   6989   MockRead data_reads[] = {
   6990     MockRead("HTTP/1.0 200 OK\r\n"),
   6991     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   6992     MockRead("Content-Length: 100\r\n\r\n"),
   6993     MockRead(SYNCHRONOUS, OK),
   6994   };
   6995 
   6996   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   6997                                 data_writes, arraysize(data_writes));
   6998   session_deps_.socket_factory->AddSocketDataProvider(&data);
   6999 
   7000   TestCompletionCallback callback;
   7001 
   7002   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7003   EXPECT_EQ(ERR_IO_PENDING, rv);
   7004 
   7005   rv = callback.WaitForResult();
   7006   EXPECT_EQ(OK, rv);
   7007 }
   7008 
   7009 TEST_P(HttpNetworkTransactionTest, BuildRequest_CacheControlNoCache) {
   7010   HttpRequestInfo request;
   7011   request.method = "GET";
   7012   request.url = GURL("http://www.google.com/");
   7013   request.load_flags = LOAD_BYPASS_CACHE;
   7014 
   7015   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7016   scoped_ptr<HttpTransaction> trans(
   7017       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7018 
   7019   MockWrite data_writes[] = {
   7020     MockWrite("GET / HTTP/1.1\r\n"
   7021               "Host: www.google.com\r\n"
   7022               "Connection: keep-alive\r\n"
   7023               "Pragma: no-cache\r\n"
   7024               "Cache-Control: no-cache\r\n\r\n"),
   7025   };
   7026 
   7027   // Lastly, the server responds with the actual content.
   7028   MockRead data_reads[] = {
   7029     MockRead("HTTP/1.0 200 OK\r\n"),
   7030     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   7031     MockRead("Content-Length: 100\r\n\r\n"),
   7032     MockRead(SYNCHRONOUS, OK),
   7033   };
   7034 
   7035   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7036                                 data_writes, arraysize(data_writes));
   7037   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7038 
   7039   TestCompletionCallback callback;
   7040 
   7041   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7042   EXPECT_EQ(ERR_IO_PENDING, rv);
   7043 
   7044   rv = callback.WaitForResult();
   7045   EXPECT_EQ(OK, rv);
   7046 }
   7047 
   7048 TEST_P(HttpNetworkTransactionTest,
   7049        BuildRequest_CacheControlValidateCache) {
   7050   HttpRequestInfo request;
   7051   request.method = "GET";
   7052   request.url = GURL("http://www.google.com/");
   7053   request.load_flags = LOAD_VALIDATE_CACHE;
   7054 
   7055   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7056   scoped_ptr<HttpTransaction> trans(
   7057       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7058 
   7059   MockWrite data_writes[] = {
   7060     MockWrite("GET / HTTP/1.1\r\n"
   7061               "Host: www.google.com\r\n"
   7062               "Connection: keep-alive\r\n"
   7063               "Cache-Control: max-age=0\r\n\r\n"),
   7064   };
   7065 
   7066   // Lastly, the server responds with the actual content.
   7067   MockRead data_reads[] = {
   7068     MockRead("HTTP/1.0 200 OK\r\n"),
   7069     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   7070     MockRead("Content-Length: 100\r\n\r\n"),
   7071     MockRead(SYNCHRONOUS, OK),
   7072   };
   7073 
   7074   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7075                                 data_writes, arraysize(data_writes));
   7076   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7077 
   7078   TestCompletionCallback callback;
   7079 
   7080   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7081   EXPECT_EQ(ERR_IO_PENDING, rv);
   7082 
   7083   rv = callback.WaitForResult();
   7084   EXPECT_EQ(OK, rv);
   7085 }
   7086 
   7087 TEST_P(HttpNetworkTransactionTest, BuildRequest_ExtraHeaders) {
   7088   HttpRequestInfo request;
   7089   request.method = "GET";
   7090   request.url = GURL("http://www.google.com/");
   7091   request.extra_headers.SetHeader("FooHeader", "Bar");
   7092 
   7093   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7094   scoped_ptr<HttpTransaction> trans(
   7095       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7096 
   7097   MockWrite data_writes[] = {
   7098     MockWrite("GET / HTTP/1.1\r\n"
   7099               "Host: www.google.com\r\n"
   7100               "Connection: keep-alive\r\n"
   7101               "FooHeader: Bar\r\n\r\n"),
   7102   };
   7103 
   7104   // Lastly, the server responds with the actual content.
   7105   MockRead data_reads[] = {
   7106     MockRead("HTTP/1.0 200 OK\r\n"),
   7107     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   7108     MockRead("Content-Length: 100\r\n\r\n"),
   7109     MockRead(SYNCHRONOUS, OK),
   7110   };
   7111 
   7112   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7113                                 data_writes, arraysize(data_writes));
   7114   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7115 
   7116   TestCompletionCallback callback;
   7117 
   7118   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7119   EXPECT_EQ(ERR_IO_PENDING, rv);
   7120 
   7121   rv = callback.WaitForResult();
   7122   EXPECT_EQ(OK, rv);
   7123 }
   7124 
   7125 TEST_P(HttpNetworkTransactionTest, BuildRequest_ExtraHeadersStripped) {
   7126   HttpRequestInfo request;
   7127   request.method = "GET";
   7128   request.url = GURL("http://www.google.com/");
   7129   request.extra_headers.SetHeader("referer", "www.foo.com");
   7130   request.extra_headers.SetHeader("hEllo", "Kitty");
   7131   request.extra_headers.SetHeader("FoO", "bar");
   7132 
   7133   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7134   scoped_ptr<HttpTransaction> trans(
   7135       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7136 
   7137   MockWrite data_writes[] = {
   7138     MockWrite("GET / HTTP/1.1\r\n"
   7139               "Host: www.google.com\r\n"
   7140               "Connection: keep-alive\r\n"
   7141               "referer: www.foo.com\r\n"
   7142               "hEllo: Kitty\r\n"
   7143               "FoO: bar\r\n\r\n"),
   7144   };
   7145 
   7146   // Lastly, the server responds with the actual content.
   7147   MockRead data_reads[] = {
   7148     MockRead("HTTP/1.0 200 OK\r\n"),
   7149     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   7150     MockRead("Content-Length: 100\r\n\r\n"),
   7151     MockRead(SYNCHRONOUS, OK),
   7152   };
   7153 
   7154   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7155                                 data_writes, arraysize(data_writes));
   7156   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7157 
   7158   TestCompletionCallback callback;
   7159 
   7160   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7161   EXPECT_EQ(ERR_IO_PENDING, rv);
   7162 
   7163   rv = callback.WaitForResult();
   7164   EXPECT_EQ(OK, rv);
   7165 }
   7166 
   7167 TEST_P(HttpNetworkTransactionTest, SOCKS4_HTTP_GET) {
   7168   HttpRequestInfo request;
   7169   request.method = "GET";
   7170   request.url = GURL("http://www.google.com/");
   7171   request.load_flags = 0;
   7172 
   7173   session_deps_.proxy_service.reset(
   7174       ProxyService::CreateFixedFromPacResult("SOCKS myproxy:1080"));
   7175   CapturingNetLog net_log;
   7176   session_deps_.net_log = &net_log;
   7177 
   7178   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7179   scoped_ptr<HttpTransaction> trans(
   7180       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7181 
   7182   char write_buffer[] = { 0x04, 0x01, 0x00, 0x50, 127, 0, 0, 1, 0 };
   7183   char read_buffer[] = { 0x00, 0x5A, 0x00, 0x00, 0, 0, 0, 0 };
   7184 
   7185   MockWrite data_writes[] = {
   7186     MockWrite(ASYNC, write_buffer, arraysize(write_buffer)),
   7187     MockWrite("GET / HTTP/1.1\r\n"
   7188               "Host: www.google.com\r\n"
   7189               "Connection: keep-alive\r\n\r\n")
   7190   };
   7191 
   7192   MockRead data_reads[] = {
   7193     MockRead(ASYNC, read_buffer, arraysize(read_buffer)),
   7194     MockRead("HTTP/1.0 200 OK\r\n"),
   7195     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n\r\n"),
   7196     MockRead("Payload"),
   7197     MockRead(SYNCHRONOUS, OK)
   7198   };
   7199 
   7200   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7201                                 data_writes, arraysize(data_writes));
   7202   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7203 
   7204   TestCompletionCallback callback;
   7205 
   7206   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7207   EXPECT_EQ(ERR_IO_PENDING, rv);
   7208 
   7209   rv = callback.WaitForResult();
   7210   EXPECT_EQ(OK, rv);
   7211 
   7212   const HttpResponseInfo* response = trans->GetResponseInfo();
   7213   ASSERT_TRUE(response != NULL);
   7214 
   7215   LoadTimingInfo load_timing_info;
   7216   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   7217   TestLoadTimingNotReusedWithPac(load_timing_info,
   7218                                  CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   7219 
   7220   std::string response_text;
   7221   rv = ReadTransaction(trans.get(), &response_text);
   7222   EXPECT_EQ(OK, rv);
   7223   EXPECT_EQ("Payload", response_text);
   7224 }
   7225 
   7226 TEST_P(HttpNetworkTransactionTest, SOCKS4_SSL_GET) {
   7227   HttpRequestInfo request;
   7228   request.method = "GET";
   7229   request.url = GURL("https://www.google.com/");
   7230   request.load_flags = 0;
   7231 
   7232   session_deps_.proxy_service.reset(
   7233       ProxyService::CreateFixedFromPacResult("SOCKS myproxy:1080"));
   7234   CapturingNetLog net_log;
   7235   session_deps_.net_log = &net_log;
   7236 
   7237   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7238   scoped_ptr<HttpTransaction> trans(
   7239       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7240 
   7241   unsigned char write_buffer[] = { 0x04, 0x01, 0x01, 0xBB, 127, 0, 0, 1, 0 };
   7242   unsigned char read_buffer[] = { 0x00, 0x5A, 0x00, 0x00, 0, 0, 0, 0 };
   7243 
   7244   MockWrite data_writes[] = {
   7245     MockWrite(ASYNC, reinterpret_cast<char*>(write_buffer),
   7246               arraysize(write_buffer)),
   7247     MockWrite("GET / HTTP/1.1\r\n"
   7248               "Host: www.google.com\r\n"
   7249               "Connection: keep-alive\r\n\r\n")
   7250   };
   7251 
   7252   MockRead data_reads[] = {
   7253     MockRead(ASYNC, reinterpret_cast<char*>(read_buffer),
   7254              arraysize(read_buffer)),
   7255     MockRead("HTTP/1.0 200 OK\r\n"),
   7256     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n\r\n"),
   7257     MockRead("Payload"),
   7258     MockRead(SYNCHRONOUS, OK)
   7259   };
   7260 
   7261   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7262                                 data_writes, arraysize(data_writes));
   7263   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7264 
   7265   SSLSocketDataProvider ssl(ASYNC, OK);
   7266   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   7267 
   7268   TestCompletionCallback callback;
   7269 
   7270   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7271   EXPECT_EQ(ERR_IO_PENDING, rv);
   7272 
   7273   rv = callback.WaitForResult();
   7274   EXPECT_EQ(OK, rv);
   7275 
   7276   LoadTimingInfo load_timing_info;
   7277   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   7278   TestLoadTimingNotReusedWithPac(load_timing_info,
   7279                                  CONNECT_TIMING_HAS_SSL_TIMES);
   7280 
   7281   const HttpResponseInfo* response = trans->GetResponseInfo();
   7282   ASSERT_TRUE(response != NULL);
   7283 
   7284   std::string response_text;
   7285   rv = ReadTransaction(trans.get(), &response_text);
   7286   EXPECT_EQ(OK, rv);
   7287   EXPECT_EQ("Payload", response_text);
   7288 }
   7289 
   7290 TEST_P(HttpNetworkTransactionTest, SOCKS4_HTTP_GET_no_PAC) {
   7291   HttpRequestInfo request;
   7292   request.method = "GET";
   7293   request.url = GURL("http://www.google.com/");
   7294   request.load_flags = 0;
   7295 
   7296   session_deps_.proxy_service.reset(
   7297       ProxyService::CreateFixed("socks4://myproxy:1080"));
   7298   CapturingNetLog net_log;
   7299   session_deps_.net_log = &net_log;
   7300 
   7301   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7302   scoped_ptr<HttpTransaction> trans(
   7303       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7304 
   7305   char write_buffer[] = { 0x04, 0x01, 0x00, 0x50, 127, 0, 0, 1, 0 };
   7306   char read_buffer[] = { 0x00, 0x5A, 0x00, 0x00, 0, 0, 0, 0 };
   7307 
   7308   MockWrite data_writes[] = {
   7309     MockWrite(ASYNC, write_buffer, arraysize(write_buffer)),
   7310     MockWrite("GET / HTTP/1.1\r\n"
   7311               "Host: www.google.com\r\n"
   7312               "Connection: keep-alive\r\n\r\n")
   7313   };
   7314 
   7315   MockRead data_reads[] = {
   7316     MockRead(ASYNC, read_buffer, arraysize(read_buffer)),
   7317     MockRead("HTTP/1.0 200 OK\r\n"),
   7318     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n\r\n"),
   7319     MockRead("Payload"),
   7320     MockRead(SYNCHRONOUS, OK)
   7321   };
   7322 
   7323   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7324                                 data_writes, arraysize(data_writes));
   7325   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7326 
   7327   TestCompletionCallback callback;
   7328 
   7329   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7330   EXPECT_EQ(ERR_IO_PENDING, rv);
   7331 
   7332   rv = callback.WaitForResult();
   7333   EXPECT_EQ(OK, rv);
   7334 
   7335   const HttpResponseInfo* response = trans->GetResponseInfo();
   7336   ASSERT_TRUE(response != NULL);
   7337 
   7338   LoadTimingInfo load_timing_info;
   7339   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   7340   TestLoadTimingNotReused(load_timing_info,
   7341                           CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   7342 
   7343   std::string response_text;
   7344   rv = ReadTransaction(trans.get(), &response_text);
   7345   EXPECT_EQ(OK, rv);
   7346   EXPECT_EQ("Payload", response_text);
   7347 }
   7348 
   7349 TEST_P(HttpNetworkTransactionTest, SOCKS5_HTTP_GET) {
   7350   HttpRequestInfo request;
   7351   request.method = "GET";
   7352   request.url = GURL("http://www.google.com/");
   7353   request.load_flags = 0;
   7354 
   7355   session_deps_.proxy_service.reset(
   7356       ProxyService::CreateFixedFromPacResult("SOCKS5 myproxy:1080"));
   7357   CapturingNetLog net_log;
   7358   session_deps_.net_log = &net_log;
   7359 
   7360   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7361   scoped_ptr<HttpTransaction> trans(
   7362       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7363 
   7364   const char kSOCKS5GreetRequest[] = { 0x05, 0x01, 0x00 };
   7365   const char kSOCKS5GreetResponse[] = { 0x05, 0x00 };
   7366   const char kSOCKS5OkRequest[] = {
   7367     0x05,  // Version
   7368     0x01,  // Command (CONNECT)
   7369     0x00,  // Reserved.
   7370     0x03,  // Address type (DOMAINNAME).
   7371     0x0E,  // Length of domain (14)
   7372     // Domain string:
   7373     'w', 'w', 'w', '.', 'g', 'o', 'o', 'g', 'l', 'e', '.', 'c', 'o', 'm',
   7374     0x00, 0x50,  // 16-bit port (80)
   7375   };
   7376   const char kSOCKS5OkResponse[] =
   7377       { 0x05, 0x00, 0x00, 0x01, 127, 0, 0, 1, 0x00, 0x50 };
   7378 
   7379   MockWrite data_writes[] = {
   7380     MockWrite(ASYNC, kSOCKS5GreetRequest, arraysize(kSOCKS5GreetRequest)),
   7381     MockWrite(ASYNC, kSOCKS5OkRequest, arraysize(kSOCKS5OkRequest)),
   7382     MockWrite("GET / HTTP/1.1\r\n"
   7383               "Host: www.google.com\r\n"
   7384               "Connection: keep-alive\r\n\r\n")
   7385   };
   7386 
   7387   MockRead data_reads[] = {
   7388     MockRead(ASYNC, kSOCKS5GreetResponse, arraysize(kSOCKS5GreetResponse)),
   7389     MockRead(ASYNC, kSOCKS5OkResponse, arraysize(kSOCKS5OkResponse)),
   7390     MockRead("HTTP/1.0 200 OK\r\n"),
   7391     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n\r\n"),
   7392     MockRead("Payload"),
   7393     MockRead(SYNCHRONOUS, OK)
   7394   };
   7395 
   7396   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7397                                 data_writes, arraysize(data_writes));
   7398   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7399 
   7400   TestCompletionCallback callback;
   7401 
   7402   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7403   EXPECT_EQ(ERR_IO_PENDING, rv);
   7404 
   7405   rv = callback.WaitForResult();
   7406   EXPECT_EQ(OK, rv);
   7407 
   7408   const HttpResponseInfo* response = trans->GetResponseInfo();
   7409   ASSERT_TRUE(response != NULL);
   7410 
   7411   LoadTimingInfo load_timing_info;
   7412   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   7413   TestLoadTimingNotReusedWithPac(load_timing_info,
   7414                                  CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   7415 
   7416   std::string response_text;
   7417   rv = ReadTransaction(trans.get(), &response_text);
   7418   EXPECT_EQ(OK, rv);
   7419   EXPECT_EQ("Payload", response_text);
   7420 }
   7421 
   7422 TEST_P(HttpNetworkTransactionTest, SOCKS5_SSL_GET) {
   7423   HttpRequestInfo request;
   7424   request.method = "GET";
   7425   request.url = GURL("https://www.google.com/");
   7426   request.load_flags = 0;
   7427 
   7428   session_deps_.proxy_service.reset(
   7429       ProxyService::CreateFixedFromPacResult("SOCKS5 myproxy:1080"));
   7430   CapturingNetLog net_log;
   7431   session_deps_.net_log = &net_log;
   7432 
   7433   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7434   scoped_ptr<HttpTransaction> trans(
   7435       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7436 
   7437   const char kSOCKS5GreetRequest[] = { 0x05, 0x01, 0x00 };
   7438   const char kSOCKS5GreetResponse[] = { 0x05, 0x00 };
   7439   const unsigned char kSOCKS5OkRequest[] = {
   7440     0x05,  // Version
   7441     0x01,  // Command (CONNECT)
   7442     0x00,  // Reserved.
   7443     0x03,  // Address type (DOMAINNAME).
   7444     0x0E,  // Length of domain (14)
   7445     // Domain string:
   7446     'w', 'w', 'w', '.', 'g', 'o', 'o', 'g', 'l', 'e', '.', 'c', 'o', 'm',
   7447     0x01, 0xBB,  // 16-bit port (443)
   7448   };
   7449 
   7450   const char kSOCKS5OkResponse[] =
   7451       { 0x05, 0x00, 0x00, 0x01, 0, 0, 0, 0, 0x00, 0x00 };
   7452 
   7453   MockWrite data_writes[] = {
   7454     MockWrite(ASYNC, kSOCKS5GreetRequest, arraysize(kSOCKS5GreetRequest)),
   7455     MockWrite(ASYNC, reinterpret_cast<const char*>(kSOCKS5OkRequest),
   7456               arraysize(kSOCKS5OkRequest)),
   7457     MockWrite("GET / HTTP/1.1\r\n"
   7458               "Host: www.google.com\r\n"
   7459               "Connection: keep-alive\r\n\r\n")
   7460   };
   7461 
   7462   MockRead data_reads[] = {
   7463     MockRead(ASYNC, kSOCKS5GreetResponse, arraysize(kSOCKS5GreetResponse)),
   7464     MockRead(ASYNC, kSOCKS5OkResponse, arraysize(kSOCKS5OkResponse)),
   7465     MockRead("HTTP/1.0 200 OK\r\n"),
   7466     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n\r\n"),
   7467     MockRead("Payload"),
   7468     MockRead(SYNCHRONOUS, OK)
   7469   };
   7470 
   7471   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   7472                                 data_writes, arraysize(data_writes));
   7473   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7474 
   7475   SSLSocketDataProvider ssl(ASYNC, OK);
   7476   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   7477 
   7478   TestCompletionCallback callback;
   7479 
   7480   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7481   EXPECT_EQ(ERR_IO_PENDING, rv);
   7482 
   7483   rv = callback.WaitForResult();
   7484   EXPECT_EQ(OK, rv);
   7485 
   7486   const HttpResponseInfo* response = trans->GetResponseInfo();
   7487   ASSERT_TRUE(response != NULL);
   7488 
   7489   LoadTimingInfo load_timing_info;
   7490   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   7491   TestLoadTimingNotReusedWithPac(load_timing_info,
   7492                                  CONNECT_TIMING_HAS_SSL_TIMES);
   7493 
   7494   std::string response_text;
   7495   rv = ReadTransaction(trans.get(), &response_text);
   7496   EXPECT_EQ(OK, rv);
   7497   EXPECT_EQ("Payload", response_text);
   7498 }
   7499 
   7500 namespace {
   7501 
   7502 // Tests that for connection endpoints the group names are correctly set.
   7503 
   7504 struct GroupNameTest {
   7505   std::string proxy_server;
   7506   std::string url;
   7507   std::string expected_group_name;
   7508   bool ssl;
   7509 };
   7510 
   7511 scoped_refptr<HttpNetworkSession> SetupSessionForGroupNameTests(
   7512     NextProto next_proto,
   7513     SpdySessionDependencies* session_deps_) {
   7514   scoped_refptr<HttpNetworkSession> session(CreateSession(session_deps_));
   7515 
   7516   base::WeakPtr<HttpServerProperties> http_server_properties =
   7517       session->http_server_properties();
   7518   http_server_properties->SetAlternateProtocol(
   7519       HostPortPair("host.with.alternate", 80), 443,
   7520       AlternateProtocolFromNextProto(next_proto));
   7521 
   7522   return session;
   7523 }
   7524 
   7525 int GroupNameTransactionHelper(
   7526     const std::string& url,
   7527     const scoped_refptr<HttpNetworkSession>& session) {
   7528   HttpRequestInfo request;
   7529   request.method = "GET";
   7530   request.url = GURL(url);
   7531   request.load_flags = 0;
   7532 
   7533   scoped_ptr<HttpTransaction> trans(
   7534       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   7535 
   7536   TestCompletionCallback callback;
   7537 
   7538   // We do not complete this request, the dtor will clean the transaction up.
   7539   return trans->Start(&request, callback.callback(), BoundNetLog());
   7540 }
   7541 
   7542 }  // namespace
   7543 
   7544 TEST_P(HttpNetworkTransactionTest, GroupNameForDirectConnections) {
   7545   const GroupNameTest tests[] = {
   7546     {
   7547       "",  // unused
   7548       "http://www.google.com/direct",
   7549       "www.google.com:80",
   7550       false,
   7551     },
   7552     {
   7553       "",  // unused
   7554       "http://[2001:1418:13:1::25]/direct",
   7555       "[2001:1418:13:1::25]:80",
   7556       false,
   7557     },
   7558 
   7559     // SSL Tests
   7560     {
   7561       "",  // unused
   7562       "https://www.google.com/direct_ssl",
   7563       "ssl/www.google.com:443",
   7564       true,
   7565     },
   7566     {
   7567       "",  // unused
   7568       "https://[2001:1418:13:1::25]/direct",
   7569       "ssl/[2001:1418:13:1::25]:443",
   7570       true,
   7571     },
   7572     {
   7573       "",  // unused
   7574       "http://host.with.alternate/direct",
   7575       "ssl/host.with.alternate:443",
   7576       true,
   7577     },
   7578   };
   7579 
   7580   session_deps_.use_alternate_protocols = true;
   7581 
   7582   for (size_t i = 0; i < ARRAYSIZE_UNSAFE(tests); ++i) {
   7583     session_deps_.proxy_service.reset(
   7584         ProxyService::CreateFixed(tests[i].proxy_server));
   7585     scoped_refptr<HttpNetworkSession> session(
   7586         SetupSessionForGroupNameTests(GetParam(), &session_deps_));
   7587 
   7588     HttpNetworkSessionPeer peer(session);
   7589     CaptureGroupNameTransportSocketPool* transport_conn_pool =
   7590         new CaptureGroupNameTransportSocketPool(NULL, NULL);
   7591     CaptureGroupNameSSLSocketPool* ssl_conn_pool =
   7592         new CaptureGroupNameSSLSocketPool(NULL, NULL);
   7593     scoped_ptr<MockClientSocketPoolManager> mock_pool_manager(
   7594         new MockClientSocketPoolManager);
   7595     mock_pool_manager->SetTransportSocketPool(transport_conn_pool);
   7596     mock_pool_manager->SetSSLSocketPool(ssl_conn_pool);
   7597     peer.SetClientSocketPoolManager(
   7598         mock_pool_manager.PassAs<ClientSocketPoolManager>());
   7599 
   7600     EXPECT_EQ(ERR_IO_PENDING,
   7601               GroupNameTransactionHelper(tests[i].url, session));
   7602     if (tests[i].ssl)
   7603       EXPECT_EQ(tests[i].expected_group_name,
   7604                 ssl_conn_pool->last_group_name_received());
   7605     else
   7606       EXPECT_EQ(tests[i].expected_group_name,
   7607                 transport_conn_pool->last_group_name_received());
   7608   }
   7609 
   7610 }
   7611 
   7612 TEST_P(HttpNetworkTransactionTest, GroupNameForHTTPProxyConnections) {
   7613   const GroupNameTest tests[] = {
   7614     {
   7615       "http_proxy",
   7616       "http://www.google.com/http_proxy_normal",
   7617       "www.google.com:80",
   7618       false,
   7619     },
   7620 
   7621     // SSL Tests
   7622     {
   7623       "http_proxy",
   7624       "https://www.google.com/http_connect_ssl",
   7625       "ssl/www.google.com:443",
   7626       true,
   7627     },
   7628 
   7629     {
   7630       "http_proxy",
   7631       "http://host.with.alternate/direct",
   7632       "ssl/host.with.alternate:443",
   7633       true,
   7634     },
   7635 
   7636     {
   7637       "http_proxy",
   7638       "ftp://ftp.google.com/http_proxy_normal",
   7639       "ftp/ftp.google.com:21",
   7640       false,
   7641     },
   7642   };
   7643 
   7644   session_deps_.use_alternate_protocols = true;
   7645 
   7646   for (size_t i = 0; i < ARRAYSIZE_UNSAFE(tests); ++i) {
   7647     session_deps_.proxy_service.reset(
   7648         ProxyService::CreateFixed(tests[i].proxy_server));
   7649     scoped_refptr<HttpNetworkSession> session(
   7650         SetupSessionForGroupNameTests(GetParam(), &session_deps_));
   7651 
   7652     HttpNetworkSessionPeer peer(session);
   7653 
   7654     HostPortPair proxy_host("http_proxy", 80);
   7655     CaptureGroupNameHttpProxySocketPool* http_proxy_pool =
   7656         new CaptureGroupNameHttpProxySocketPool(NULL, NULL);
   7657     CaptureGroupNameSSLSocketPool* ssl_conn_pool =
   7658         new CaptureGroupNameSSLSocketPool(NULL, NULL);
   7659 
   7660     scoped_ptr<MockClientSocketPoolManager> mock_pool_manager(
   7661         new MockClientSocketPoolManager);
   7662     mock_pool_manager->SetSocketPoolForHTTPProxy(proxy_host, http_proxy_pool);
   7663     mock_pool_manager->SetSocketPoolForSSLWithProxy(proxy_host, ssl_conn_pool);
   7664     peer.SetClientSocketPoolManager(
   7665         mock_pool_manager.PassAs<ClientSocketPoolManager>());
   7666 
   7667     EXPECT_EQ(ERR_IO_PENDING,
   7668               GroupNameTransactionHelper(tests[i].url, session));
   7669     if (tests[i].ssl)
   7670       EXPECT_EQ(tests[i].expected_group_name,
   7671                 ssl_conn_pool->last_group_name_received());
   7672     else
   7673       EXPECT_EQ(tests[i].expected_group_name,
   7674                 http_proxy_pool->last_group_name_received());
   7675   }
   7676 }
   7677 
   7678 TEST_P(HttpNetworkTransactionTest, GroupNameForSOCKSConnections) {
   7679   const GroupNameTest tests[] = {
   7680     {
   7681       "socks4://socks_proxy:1080",
   7682       "http://www.google.com/socks4_direct",
   7683       "socks4/www.google.com:80",
   7684       false,
   7685     },
   7686     {
   7687       "socks5://socks_proxy:1080",
   7688       "http://www.google.com/socks5_direct",
   7689       "socks5/www.google.com:80",
   7690       false,
   7691     },
   7692 
   7693     // SSL Tests
   7694     {
   7695       "socks4://socks_proxy:1080",
   7696       "https://www.google.com/socks4_ssl",
   7697       "socks4/ssl/www.google.com:443",
   7698       true,
   7699     },
   7700     {
   7701       "socks5://socks_proxy:1080",
   7702       "https://www.google.com/socks5_ssl",
   7703       "socks5/ssl/www.google.com:443",
   7704       true,
   7705     },
   7706 
   7707     {
   7708       "socks4://socks_proxy:1080",
   7709       "http://host.with.alternate/direct",
   7710       "socks4/ssl/host.with.alternate:443",
   7711       true,
   7712     },
   7713   };
   7714 
   7715   session_deps_.use_alternate_protocols = true;
   7716 
   7717   for (size_t i = 0; i < ARRAYSIZE_UNSAFE(tests); ++i) {
   7718     session_deps_.proxy_service.reset(
   7719         ProxyService::CreateFixed(tests[i].proxy_server));
   7720     scoped_refptr<HttpNetworkSession> session(
   7721         SetupSessionForGroupNameTests(GetParam(), &session_deps_));
   7722 
   7723     HttpNetworkSessionPeer peer(session);
   7724 
   7725     HostPortPair proxy_host("socks_proxy", 1080);
   7726     CaptureGroupNameSOCKSSocketPool* socks_conn_pool =
   7727         new CaptureGroupNameSOCKSSocketPool(NULL, NULL);
   7728     CaptureGroupNameSSLSocketPool* ssl_conn_pool =
   7729         new CaptureGroupNameSSLSocketPool(NULL, NULL);
   7730 
   7731     scoped_ptr<MockClientSocketPoolManager> mock_pool_manager(
   7732         new MockClientSocketPoolManager);
   7733     mock_pool_manager->SetSocketPoolForSOCKSProxy(proxy_host, socks_conn_pool);
   7734     mock_pool_manager->SetSocketPoolForSSLWithProxy(proxy_host, ssl_conn_pool);
   7735     peer.SetClientSocketPoolManager(
   7736         mock_pool_manager.PassAs<ClientSocketPoolManager>());
   7737 
   7738     scoped_ptr<HttpTransaction> trans(
   7739         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   7740 
   7741     EXPECT_EQ(ERR_IO_PENDING,
   7742               GroupNameTransactionHelper(tests[i].url, session));
   7743     if (tests[i].ssl)
   7744       EXPECT_EQ(tests[i].expected_group_name,
   7745                 ssl_conn_pool->last_group_name_received());
   7746     else
   7747       EXPECT_EQ(tests[i].expected_group_name,
   7748                 socks_conn_pool->last_group_name_received());
   7749   }
   7750 }
   7751 
   7752 TEST_P(HttpNetworkTransactionTest, ReconsiderProxyAfterFailedConnection) {
   7753   HttpRequestInfo request;
   7754   request.method = "GET";
   7755   request.url = GURL("http://www.google.com/");
   7756 
   7757   session_deps_.proxy_service.reset(
   7758       ProxyService::CreateFixed("myproxy:70;foobar:80"));
   7759 
   7760   // This simulates failure resolving all hostnames; that means we will fail
   7761   // connecting to both proxies (myproxy:70 and foobar:80).
   7762   session_deps_.host_resolver->rules()->AddSimulatedFailure("*");
   7763 
   7764   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7765   scoped_ptr<HttpTransaction> trans(
   7766       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7767 
   7768   TestCompletionCallback callback;
   7769 
   7770   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7771   EXPECT_EQ(ERR_IO_PENDING, rv);
   7772 
   7773   rv = callback.WaitForResult();
   7774   EXPECT_EQ(ERR_PROXY_CONNECTION_FAILED, rv);
   7775 }
   7776 
   7777 // Base test to make sure that when the load flags for a request specify to
   7778 // bypass the cache, the DNS cache is not used.
   7779 void HttpNetworkTransactionTest::BypassHostCacheOnRefreshHelper(
   7780     int load_flags) {
   7781   // Issue a request, asking to bypass the cache(s).
   7782   HttpRequestInfo request;
   7783   request.method = "GET";
   7784   request.load_flags = load_flags;
   7785   request.url = GURL("http://www.google.com/");
   7786 
   7787   // Select a host resolver that does caching.
   7788   session_deps_.host_resolver.reset(new MockCachingHostResolver);
   7789 
   7790   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7791   scoped_ptr<HttpTransaction> trans(
   7792       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7793 
   7794   // Warm up the host cache so it has an entry for "www.google.com".
   7795   AddressList addrlist;
   7796   TestCompletionCallback callback;
   7797   int rv = session_deps_.host_resolver->Resolve(
   7798       HostResolver::RequestInfo(HostPortPair("www.google.com", 80)),
   7799       DEFAULT_PRIORITY,
   7800       &addrlist,
   7801       callback.callback(),
   7802       NULL,
   7803       BoundNetLog());
   7804   EXPECT_EQ(ERR_IO_PENDING, rv);
   7805   rv = callback.WaitForResult();
   7806   EXPECT_EQ(OK, rv);
   7807 
   7808   // Verify that it was added to host cache, by doing a subsequent async lookup
   7809   // and confirming it completes synchronously.
   7810   rv = session_deps_.host_resolver->Resolve(
   7811       HostResolver::RequestInfo(HostPortPair("www.google.com", 80)),
   7812       DEFAULT_PRIORITY,
   7813       &addrlist,
   7814       callback.callback(),
   7815       NULL,
   7816       BoundNetLog());
   7817   ASSERT_EQ(OK, rv);
   7818 
   7819   // Inject a failure the next time that "www.google.com" is resolved. This way
   7820   // we can tell if the next lookup hit the cache, or the "network".
   7821   // (cache --> success, "network" --> failure).
   7822   session_deps_.host_resolver->rules()->AddSimulatedFailure("www.google.com");
   7823 
   7824   // Connect up a mock socket which will fail with ERR_UNEXPECTED during the
   7825   // first read -- this won't be reached as the host resolution will fail first.
   7826   MockRead data_reads[] = { MockRead(SYNCHRONOUS, ERR_UNEXPECTED) };
   7827   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   7828   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7829 
   7830   // Run the request.
   7831   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7832   ASSERT_EQ(ERR_IO_PENDING, rv);
   7833   rv = callback.WaitForResult();
   7834 
   7835   // If we bypassed the cache, we would have gotten a failure while resolving
   7836   // "www.google.com".
   7837   EXPECT_EQ(ERR_NAME_NOT_RESOLVED, rv);
   7838 }
   7839 
   7840 // There are multiple load flags that should trigger the host cache bypass.
   7841 // Test each in isolation:
   7842 TEST_P(HttpNetworkTransactionTest, BypassHostCacheOnRefresh1) {
   7843   BypassHostCacheOnRefreshHelper(LOAD_BYPASS_CACHE);
   7844 }
   7845 
   7846 TEST_P(HttpNetworkTransactionTest, BypassHostCacheOnRefresh2) {
   7847   BypassHostCacheOnRefreshHelper(LOAD_VALIDATE_CACHE);
   7848 }
   7849 
   7850 TEST_P(HttpNetworkTransactionTest, BypassHostCacheOnRefresh3) {
   7851   BypassHostCacheOnRefreshHelper(LOAD_DISABLE_CACHE);
   7852 }
   7853 
   7854 // Make sure we can handle an error when writing the request.
   7855 TEST_P(HttpNetworkTransactionTest, RequestWriteError) {
   7856   HttpRequestInfo request;
   7857   request.method = "GET";
   7858   request.url = GURL("http://www.foo.com/");
   7859   request.load_flags = 0;
   7860 
   7861   MockWrite write_failure[] = {
   7862     MockWrite(ASYNC, ERR_CONNECTION_RESET),
   7863   };
   7864   StaticSocketDataProvider data(NULL, 0,
   7865                                 write_failure, arraysize(write_failure));
   7866   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7867   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7868 
   7869   TestCompletionCallback callback;
   7870 
   7871   scoped_ptr<HttpTransaction> trans(
   7872       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7873 
   7874   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7875   EXPECT_EQ(ERR_IO_PENDING, rv);
   7876 
   7877   rv = callback.WaitForResult();
   7878   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   7879 }
   7880 
   7881 // Check that a connection closed after the start of the headers finishes ok.
   7882 TEST_P(HttpNetworkTransactionTest, ConnectionClosedAfterStartOfHeaders) {
   7883   HttpRequestInfo request;
   7884   request.method = "GET";
   7885   request.url = GURL("http://www.foo.com/");
   7886   request.load_flags = 0;
   7887 
   7888   MockRead data_reads[] = {
   7889     MockRead("HTTP/1."),
   7890     MockRead(SYNCHRONOUS, OK),
   7891   };
   7892 
   7893   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   7894   session_deps_.socket_factory->AddSocketDataProvider(&data);
   7895   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7896 
   7897   TestCompletionCallback callback;
   7898 
   7899   scoped_ptr<HttpTransaction> trans(
   7900       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   7901 
   7902   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   7903   EXPECT_EQ(ERR_IO_PENDING, rv);
   7904 
   7905   rv = callback.WaitForResult();
   7906   EXPECT_EQ(OK, rv);
   7907 
   7908   const HttpResponseInfo* response = trans->GetResponseInfo();
   7909   ASSERT_TRUE(response != NULL);
   7910 
   7911   EXPECT_TRUE(response->headers.get() != NULL);
   7912   EXPECT_EQ("HTTP/1.0 200 OK", response->headers->GetStatusLine());
   7913 
   7914   std::string response_data;
   7915   rv = ReadTransaction(trans.get(), &response_data);
   7916   EXPECT_EQ(OK, rv);
   7917   EXPECT_EQ("", response_data);
   7918 }
   7919 
   7920 // Make sure that a dropped connection while draining the body for auth
   7921 // restart does the right thing.
   7922 TEST_P(HttpNetworkTransactionTest, DrainResetOK) {
   7923   HttpRequestInfo request;
   7924   request.method = "GET";
   7925   request.url = GURL("http://www.google.com/");
   7926   request.load_flags = 0;
   7927 
   7928   MockWrite data_writes1[] = {
   7929     MockWrite("GET / HTTP/1.1\r\n"
   7930               "Host: www.google.com\r\n"
   7931               "Connection: keep-alive\r\n\r\n"),
   7932   };
   7933 
   7934   MockRead data_reads1[] = {
   7935     MockRead("HTTP/1.1 401 Unauthorized\r\n"),
   7936     MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
   7937     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   7938     MockRead("Content-Length: 14\r\n\r\n"),
   7939     MockRead("Unauth"),
   7940     MockRead(ASYNC, ERR_CONNECTION_RESET),
   7941   };
   7942 
   7943   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   7944                                  data_writes1, arraysize(data_writes1));
   7945   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   7946 
   7947   // After calling trans->RestartWithAuth(), this is the request we should
   7948   // be issuing -- the final header line contains the credentials.
   7949   MockWrite data_writes2[] = {
   7950     MockWrite("GET / HTTP/1.1\r\n"
   7951               "Host: www.google.com\r\n"
   7952               "Connection: keep-alive\r\n"
   7953               "Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
   7954   };
   7955 
   7956   // Lastly, the server responds with the actual content.
   7957   MockRead data_reads2[] = {
   7958     MockRead("HTTP/1.1 200 OK\r\n"),
   7959     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   7960     MockRead("Content-Length: 100\r\n\r\n"),
   7961     MockRead(SYNCHRONOUS, OK),
   7962   };
   7963 
   7964   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   7965                                  data_writes2, arraysize(data_writes2));
   7966   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   7967   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   7968 
   7969   TestCompletionCallback callback1;
   7970 
   7971   scoped_ptr<HttpTransaction> trans(
   7972       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   7973 
   7974   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   7975   EXPECT_EQ(ERR_IO_PENDING, rv);
   7976 
   7977   rv = callback1.WaitForResult();
   7978   EXPECT_EQ(OK, rv);
   7979 
   7980   const HttpResponseInfo* response = trans->GetResponseInfo();
   7981   ASSERT_TRUE(response != NULL);
   7982   EXPECT_TRUE(CheckBasicServerAuth(response->auth_challenge.get()));
   7983 
   7984   TestCompletionCallback callback2;
   7985 
   7986   rv = trans->RestartWithAuth(
   7987       AuthCredentials(kFoo, kBar), callback2.callback());
   7988   EXPECT_EQ(ERR_IO_PENDING, rv);
   7989 
   7990   rv = callback2.WaitForResult();
   7991   EXPECT_EQ(OK, rv);
   7992 
   7993   response = trans->GetResponseInfo();
   7994   ASSERT_TRUE(response != NULL);
   7995   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   7996   EXPECT_EQ(100, response->headers->GetContentLength());
   7997 }
   7998 
   7999 // Test HTTPS connections going through a proxy that sends extra data.
   8000 TEST_P(HttpNetworkTransactionTest, HTTPSViaProxyWithExtraData) {
   8001   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   8002 
   8003   HttpRequestInfo request;
   8004   request.method = "GET";
   8005   request.url = GURL("https://www.google.com/");
   8006   request.load_flags = 0;
   8007 
   8008   MockRead proxy_reads[] = {
   8009     MockRead("HTTP/1.0 200 Connected\r\n\r\nExtra data"),
   8010     MockRead(SYNCHRONOUS, OK)
   8011   };
   8012 
   8013   StaticSocketDataProvider data(proxy_reads, arraysize(proxy_reads), NULL, 0);
   8014   SSLSocketDataProvider ssl(ASYNC, OK);
   8015 
   8016   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8017   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   8018 
   8019   TestCompletionCallback callback;
   8020 
   8021   session_deps_.socket_factory->ResetNextMockIndexes();
   8022 
   8023   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8024   scoped_ptr<HttpTransaction> trans(
   8025       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   8026 
   8027   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8028   EXPECT_EQ(ERR_IO_PENDING, rv);
   8029 
   8030   rv = callback.WaitForResult();
   8031   EXPECT_EQ(ERR_TUNNEL_CONNECTION_FAILED, rv);
   8032 }
   8033 
   8034 TEST_P(HttpNetworkTransactionTest, LargeContentLengthThenClose) {
   8035   HttpRequestInfo request;
   8036   request.method = "GET";
   8037   request.url = GURL("http://www.google.com/");
   8038   request.load_flags = 0;
   8039 
   8040   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8041   scoped_ptr<HttpTransaction> trans(
   8042       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   8043 
   8044   MockRead data_reads[] = {
   8045     MockRead("HTTP/1.0 200 OK\r\nContent-Length:6719476739\r\n\r\n"),
   8046     MockRead(SYNCHRONOUS, OK),
   8047   };
   8048 
   8049   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   8050   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8051 
   8052   TestCompletionCallback callback;
   8053 
   8054   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8055   EXPECT_EQ(ERR_IO_PENDING, rv);
   8056 
   8057   EXPECT_EQ(OK, callback.WaitForResult());
   8058 
   8059   const HttpResponseInfo* response = trans->GetResponseInfo();
   8060   ASSERT_TRUE(response != NULL);
   8061 
   8062   EXPECT_TRUE(response->headers.get() != NULL);
   8063   EXPECT_EQ("HTTP/1.0 200 OK", response->headers->GetStatusLine());
   8064 
   8065   std::string response_data;
   8066   rv = ReadTransaction(trans.get(), &response_data);
   8067   EXPECT_EQ(ERR_CONTENT_LENGTH_MISMATCH, rv);
   8068 }
   8069 
   8070 TEST_P(HttpNetworkTransactionTest, UploadFileSmallerThanLength) {
   8071   base::FilePath temp_file_path;
   8072   ASSERT_TRUE(base::CreateTemporaryFile(&temp_file_path));
   8073   const uint64 kFakeSize = 100000;  // file is actually blank
   8074   UploadFileElementReader::ScopedOverridingContentLengthForTests
   8075       overriding_content_length(kFakeSize);
   8076 
   8077   ScopedVector<UploadElementReader> element_readers;
   8078   element_readers.push_back(
   8079       new UploadFileElementReader(base::MessageLoopProxy::current().get(),
   8080                                   temp_file_path,
   8081                                   0,
   8082                                   kuint64max,
   8083                                   base::Time()));
   8084   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   8085 
   8086   HttpRequestInfo request;
   8087   request.method = "POST";
   8088   request.url = GURL("http://www.google.com/upload");
   8089   request.upload_data_stream = &upload_data_stream;
   8090   request.load_flags = 0;
   8091 
   8092   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8093   scoped_ptr<HttpTransaction> trans(
   8094       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   8095 
   8096   MockRead data_reads[] = {
   8097     MockRead("HTTP/1.0 200 OK\r\n\r\n"),
   8098     MockRead("hello world"),
   8099     MockRead(SYNCHRONOUS, OK),
   8100   };
   8101   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   8102   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8103 
   8104   TestCompletionCallback callback;
   8105 
   8106   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8107   EXPECT_EQ(ERR_IO_PENDING, rv);
   8108 
   8109   rv = callback.WaitForResult();
   8110   EXPECT_EQ(OK, rv);
   8111 
   8112   const HttpResponseInfo* response = trans->GetResponseInfo();
   8113   ASSERT_TRUE(response != NULL);
   8114 
   8115   EXPECT_TRUE(response->headers.get() != NULL);
   8116   EXPECT_EQ("HTTP/1.0 200 OK", response->headers->GetStatusLine());
   8117 
   8118   std::string response_data;
   8119   rv = ReadTransaction(trans.get(), &response_data);
   8120   EXPECT_EQ(OK, rv);
   8121   EXPECT_EQ("hello world", response_data);
   8122 
   8123   base::DeleteFile(temp_file_path, false);
   8124 }
   8125 
   8126 TEST_P(HttpNetworkTransactionTest, UploadUnreadableFile) {
   8127   base::FilePath temp_file;
   8128   ASSERT_TRUE(base::CreateTemporaryFile(&temp_file));
   8129   std::string temp_file_content("Unreadable file.");
   8130   ASSERT_TRUE(base::WriteFile(temp_file, temp_file_content.c_str(),
   8131                                    temp_file_content.length()));
   8132   ASSERT_TRUE(file_util::MakeFileUnreadable(temp_file));
   8133 
   8134   ScopedVector<UploadElementReader> element_readers;
   8135   element_readers.push_back(
   8136       new UploadFileElementReader(base::MessageLoopProxy::current().get(),
   8137                                   temp_file,
   8138                                   0,
   8139                                   kuint64max,
   8140                                   base::Time()));
   8141   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   8142 
   8143   HttpRequestInfo request;
   8144   request.method = "POST";
   8145   request.url = GURL("http://www.google.com/upload");
   8146   request.upload_data_stream = &upload_data_stream;
   8147   request.load_flags = 0;
   8148 
   8149   // If we try to upload an unreadable file, the transaction should fail.
   8150   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8151   scoped_ptr<HttpTransaction> trans(
   8152       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   8153 
   8154   StaticSocketDataProvider data(NULL, 0, NULL, 0);
   8155   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8156 
   8157   TestCompletionCallback callback;
   8158 
   8159   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8160   EXPECT_EQ(ERR_IO_PENDING, rv);
   8161 
   8162   rv = callback.WaitForResult();
   8163   EXPECT_EQ(ERR_ACCESS_DENIED, rv);
   8164 
   8165   const HttpResponseInfo* response = trans->GetResponseInfo();
   8166   EXPECT_FALSE(response);
   8167 
   8168   base::DeleteFile(temp_file, false);
   8169 }
   8170 
   8171 TEST_P(HttpNetworkTransactionTest, CancelDuringInitRequestBody) {
   8172   class FakeUploadElementReader : public UploadElementReader {
   8173    public:
   8174     FakeUploadElementReader() {}
   8175     virtual ~FakeUploadElementReader() {}
   8176 
   8177     const CompletionCallback& callback() const { return callback_; }
   8178 
   8179     // UploadElementReader overrides:
   8180     virtual int Init(const CompletionCallback& callback) OVERRIDE {
   8181       callback_ = callback;
   8182       return ERR_IO_PENDING;
   8183     }
   8184     virtual uint64 GetContentLength() const OVERRIDE { return 0; }
   8185     virtual uint64 BytesRemaining() const OVERRIDE { return 0; }
   8186     virtual int Read(IOBuffer* buf,
   8187                      int buf_length,
   8188                      const CompletionCallback& callback) OVERRIDE {
   8189       return ERR_FAILED;
   8190     }
   8191 
   8192    private:
   8193     CompletionCallback callback_;
   8194   };
   8195 
   8196   FakeUploadElementReader* fake_reader = new FakeUploadElementReader;
   8197   ScopedVector<UploadElementReader> element_readers;
   8198   element_readers.push_back(fake_reader);
   8199   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   8200 
   8201   HttpRequestInfo request;
   8202   request.method = "POST";
   8203   request.url = GURL("http://www.google.com/upload");
   8204   request.upload_data_stream = &upload_data_stream;
   8205   request.load_flags = 0;
   8206 
   8207   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8208   scoped_ptr<HttpTransaction> trans(
   8209       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   8210 
   8211   StaticSocketDataProvider data;
   8212   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8213 
   8214   TestCompletionCallback callback;
   8215   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8216   EXPECT_EQ(ERR_IO_PENDING, rv);
   8217   base::MessageLoop::current()->RunUntilIdle();
   8218 
   8219   // Transaction is pending on request body initialization.
   8220   ASSERT_FALSE(fake_reader->callback().is_null());
   8221 
   8222   // Return Init()'s result after the transaction gets destroyed.
   8223   trans.reset();
   8224   fake_reader->callback().Run(OK);  // Should not crash.
   8225 }
   8226 
   8227 // Tests that changes to Auth realms are treated like auth rejections.
   8228 TEST_P(HttpNetworkTransactionTest, ChangeAuthRealms) {
   8229 
   8230   HttpRequestInfo request;
   8231   request.method = "GET";
   8232   request.url = GURL("http://www.google.com/");
   8233   request.load_flags = 0;
   8234 
   8235   // First transaction will request a resource and receive a Basic challenge
   8236   // with realm="first_realm".
   8237   MockWrite data_writes1[] = {
   8238     MockWrite("GET / HTTP/1.1\r\n"
   8239               "Host: www.google.com\r\n"
   8240               "Connection: keep-alive\r\n"
   8241               "\r\n"),
   8242   };
   8243   MockRead data_reads1[] = {
   8244     MockRead("HTTP/1.1 401 Unauthorized\r\n"
   8245              "WWW-Authenticate: Basic realm=\"first_realm\"\r\n"
   8246              "\r\n"),
   8247   };
   8248 
   8249   // After calling trans->RestartWithAuth(), provide an Authentication header
   8250   // for first_realm. The server will reject and provide a challenge with
   8251   // second_realm.
   8252   MockWrite data_writes2[] = {
   8253     MockWrite("GET / HTTP/1.1\r\n"
   8254               "Host: www.google.com\r\n"
   8255               "Connection: keep-alive\r\n"
   8256               "Authorization: Basic Zmlyc3Q6YmF6\r\n"
   8257               "\r\n"),
   8258   };
   8259   MockRead data_reads2[] = {
   8260     MockRead("HTTP/1.1 401 Unauthorized\r\n"
   8261              "WWW-Authenticate: Basic realm=\"second_realm\"\r\n"
   8262              "\r\n"),
   8263   };
   8264 
   8265   // This again fails, and goes back to first_realm. Make sure that the
   8266   // entry is removed from cache.
   8267   MockWrite data_writes3[] = {
   8268     MockWrite("GET / HTTP/1.1\r\n"
   8269               "Host: www.google.com\r\n"
   8270               "Connection: keep-alive\r\n"
   8271               "Authorization: Basic c2Vjb25kOmZvdQ==\r\n"
   8272               "\r\n"),
   8273   };
   8274   MockRead data_reads3[] = {
   8275     MockRead("HTTP/1.1 401 Unauthorized\r\n"
   8276              "WWW-Authenticate: Basic realm=\"first_realm\"\r\n"
   8277              "\r\n"),
   8278   };
   8279 
   8280   // Try one last time (with the correct password) and get the resource.
   8281   MockWrite data_writes4[] = {
   8282     MockWrite("GET / HTTP/1.1\r\n"
   8283               "Host: www.google.com\r\n"
   8284               "Connection: keep-alive\r\n"
   8285               "Authorization: Basic Zmlyc3Q6YmFy\r\n"
   8286               "\r\n"),
   8287   };
   8288   MockRead data_reads4[] = {
   8289     MockRead("HTTP/1.1 200 OK\r\n"
   8290              "Content-Type: text/html; charset=iso-8859-1\r\n"
   8291              "Content-Length: 5\r\n"
   8292              "\r\n"
   8293              "hello"),
   8294   };
   8295 
   8296   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   8297                                  data_writes1, arraysize(data_writes1));
   8298   StaticSocketDataProvider data2(data_reads2, arraysize(data_reads2),
   8299                                  data_writes2, arraysize(data_writes2));
   8300   StaticSocketDataProvider data3(data_reads3, arraysize(data_reads3),
   8301                                  data_writes3, arraysize(data_writes3));
   8302   StaticSocketDataProvider data4(data_reads4, arraysize(data_reads4),
   8303                                  data_writes4, arraysize(data_writes4));
   8304   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   8305   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   8306   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   8307   session_deps_.socket_factory->AddSocketDataProvider(&data4);
   8308 
   8309   TestCompletionCallback callback1;
   8310 
   8311   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8312   scoped_ptr<HttpTransaction> trans(
   8313       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   8314 
   8315   // Issue the first request with Authorize headers. There should be a
   8316   // password prompt for first_realm waiting to be filled in after the
   8317   // transaction completes.
   8318   int rv = trans->Start(&request, callback1.callback(), BoundNetLog());
   8319   EXPECT_EQ(ERR_IO_PENDING, rv);
   8320   rv = callback1.WaitForResult();
   8321   EXPECT_EQ(OK, rv);
   8322   const HttpResponseInfo* response = trans->GetResponseInfo();
   8323   ASSERT_TRUE(response != NULL);
   8324   const AuthChallengeInfo* challenge = response->auth_challenge.get();
   8325   ASSERT_FALSE(challenge == NULL);
   8326   EXPECT_FALSE(challenge->is_proxy);
   8327   EXPECT_EQ("www.google.com:80", challenge->challenger.ToString());
   8328   EXPECT_EQ("first_realm", challenge->realm);
   8329   EXPECT_EQ("basic", challenge->scheme);
   8330 
   8331   // Issue the second request with an incorrect password. There should be a
   8332   // password prompt for second_realm waiting to be filled in after the
   8333   // transaction completes.
   8334   TestCompletionCallback callback2;
   8335   rv = trans->RestartWithAuth(
   8336       AuthCredentials(kFirst, kBaz), callback2.callback());
   8337   EXPECT_EQ(ERR_IO_PENDING, rv);
   8338   rv = callback2.WaitForResult();
   8339   EXPECT_EQ(OK, rv);
   8340   response = trans->GetResponseInfo();
   8341   ASSERT_TRUE(response != NULL);
   8342   challenge = response->auth_challenge.get();
   8343   ASSERT_FALSE(challenge == NULL);
   8344   EXPECT_FALSE(challenge->is_proxy);
   8345   EXPECT_EQ("www.google.com:80", challenge->challenger.ToString());
   8346   EXPECT_EQ("second_realm", challenge->realm);
   8347   EXPECT_EQ("basic", challenge->scheme);
   8348 
   8349   // Issue the third request with another incorrect password. There should be
   8350   // a password prompt for first_realm waiting to be filled in. If the password
   8351   // prompt is not present, it indicates that the HttpAuthCacheEntry for
   8352   // first_realm was not correctly removed.
   8353   TestCompletionCallback callback3;
   8354   rv = trans->RestartWithAuth(
   8355       AuthCredentials(kSecond, kFou), callback3.callback());
   8356   EXPECT_EQ(ERR_IO_PENDING, rv);
   8357   rv = callback3.WaitForResult();
   8358   EXPECT_EQ(OK, rv);
   8359   response = trans->GetResponseInfo();
   8360   ASSERT_TRUE(response != NULL);
   8361   challenge = response->auth_challenge.get();
   8362   ASSERT_FALSE(challenge == NULL);
   8363   EXPECT_FALSE(challenge->is_proxy);
   8364   EXPECT_EQ("www.google.com:80", challenge->challenger.ToString());
   8365   EXPECT_EQ("first_realm", challenge->realm);
   8366   EXPECT_EQ("basic", challenge->scheme);
   8367 
   8368   // Issue the fourth request with the correct password and username.
   8369   TestCompletionCallback callback4;
   8370   rv = trans->RestartWithAuth(
   8371       AuthCredentials(kFirst, kBar), callback4.callback());
   8372   EXPECT_EQ(ERR_IO_PENDING, rv);
   8373   rv = callback4.WaitForResult();
   8374   EXPECT_EQ(OK, rv);
   8375   response = trans->GetResponseInfo();
   8376   ASSERT_TRUE(response != NULL);
   8377   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   8378 }
   8379 
   8380 TEST_P(HttpNetworkTransactionTest, HonorAlternateProtocolHeader) {
   8381   session_deps_.next_protos = SpdyNextProtos();
   8382   session_deps_.use_alternate_protocols = true;
   8383 
   8384   std::string alternate_protocol_http_header =
   8385       GetAlternateProtocolHttpHeader();
   8386 
   8387   MockRead data_reads[] = {
   8388     MockRead("HTTP/1.1 200 OK\r\n"),
   8389     MockRead(alternate_protocol_http_header.c_str()),
   8390     MockRead("hello world"),
   8391     MockRead(SYNCHRONOUS, OK),
   8392   };
   8393 
   8394   HttpRequestInfo request;
   8395   request.method = "GET";
   8396   request.url = GURL("http://www.google.com/");
   8397   request.load_flags = 0;
   8398 
   8399   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   8400 
   8401   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8402 
   8403   TestCompletionCallback callback;
   8404 
   8405   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8406   scoped_ptr<HttpTransaction> trans(
   8407       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8408 
   8409   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8410   EXPECT_EQ(ERR_IO_PENDING, rv);
   8411 
   8412   HostPortPair http_host_port_pair("www.google.com", 80);
   8413   HttpServerProperties& http_server_properties =
   8414       *session->http_server_properties();
   8415   EXPECT_FALSE(
   8416       http_server_properties.HasAlternateProtocol(http_host_port_pair));
   8417 
   8418   EXPECT_EQ(OK, callback.WaitForResult());
   8419 
   8420   const HttpResponseInfo* response = trans->GetResponseInfo();
   8421   ASSERT_TRUE(response != NULL);
   8422   ASSERT_TRUE(response->headers.get() != NULL);
   8423   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8424   EXPECT_FALSE(response->was_fetched_via_spdy);
   8425   EXPECT_FALSE(response->was_npn_negotiated);
   8426 
   8427   std::string response_data;
   8428   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   8429   EXPECT_EQ("hello world", response_data);
   8430 
   8431   ASSERT_TRUE(http_server_properties.HasAlternateProtocol(http_host_port_pair));
   8432   const PortAlternateProtocolPair alternate =
   8433       http_server_properties.GetAlternateProtocol(http_host_port_pair);
   8434   PortAlternateProtocolPair expected_alternate;
   8435   expected_alternate.port = 443;
   8436   expected_alternate.protocol = AlternateProtocolFromNextProto(GetParam());
   8437   EXPECT_TRUE(expected_alternate.Equals(alternate));
   8438 }
   8439 
   8440 TEST_P(HttpNetworkTransactionTest,
   8441        MarkBrokenAlternateProtocolAndFallback) {
   8442   session_deps_.use_alternate_protocols = true;
   8443 
   8444   HttpRequestInfo request;
   8445   request.method = "GET";
   8446   request.url = GURL("http://www.google.com/");
   8447   request.load_flags = 0;
   8448 
   8449   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   8450   StaticSocketDataProvider first_data;
   8451   first_data.set_connect_data(mock_connect);
   8452   session_deps_.socket_factory->AddSocketDataProvider(&first_data);
   8453 
   8454   MockRead data_reads[] = {
   8455     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8456     MockRead("hello world"),
   8457     MockRead(ASYNC, OK),
   8458   };
   8459   StaticSocketDataProvider second_data(
   8460       data_reads, arraysize(data_reads), NULL, 0);
   8461   session_deps_.socket_factory->AddSocketDataProvider(&second_data);
   8462 
   8463   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8464 
   8465   base::WeakPtr<HttpServerProperties> http_server_properties =
   8466       session->http_server_properties();
   8467   // Port must be < 1024, or the header will be ignored (since initial port was
   8468   // port 80 (another restricted port).
   8469   http_server_properties->SetAlternateProtocol(
   8470       HostPortPair::FromURL(request.url),
   8471       666 /* port is ignored by MockConnect anyway */,
   8472       AlternateProtocolFromNextProto(GetParam()));
   8473 
   8474   scoped_ptr<HttpTransaction> trans(
   8475       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8476   TestCompletionCallback callback;
   8477 
   8478   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8479   EXPECT_EQ(ERR_IO_PENDING, rv);
   8480   EXPECT_EQ(OK, callback.WaitForResult());
   8481 
   8482   const HttpResponseInfo* response = trans->GetResponseInfo();
   8483   ASSERT_TRUE(response != NULL);
   8484   ASSERT_TRUE(response->headers.get() != NULL);
   8485   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8486 
   8487   std::string response_data;
   8488   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   8489   EXPECT_EQ("hello world", response_data);
   8490 
   8491   ASSERT_TRUE(http_server_properties->HasAlternateProtocol(
   8492       HostPortPair::FromURL(request.url)));
   8493   const PortAlternateProtocolPair alternate =
   8494       http_server_properties->GetAlternateProtocol(
   8495           HostPortPair::FromURL(request.url));
   8496   EXPECT_EQ(ALTERNATE_PROTOCOL_BROKEN, alternate.protocol);
   8497 }
   8498 
   8499 TEST_P(HttpNetworkTransactionTest,
   8500        AlternateProtocolPortRestrictedBlocked) {
   8501   // Ensure that we're not allowed to redirect traffic via an alternate
   8502   // protocol to an unrestricted (port >= 1024) when the original traffic was
   8503   // on a restricted port (port < 1024).  Ensure that we can redirect in all
   8504   // other cases.
   8505   session_deps_.use_alternate_protocols = true;
   8506 
   8507   HttpRequestInfo restricted_port_request;
   8508   restricted_port_request.method = "GET";
   8509   restricted_port_request.url = GURL("http://www.google.com:1023/");
   8510   restricted_port_request.load_flags = 0;
   8511 
   8512   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   8513   StaticSocketDataProvider first_data;
   8514   first_data.set_connect_data(mock_connect);
   8515   session_deps_.socket_factory->AddSocketDataProvider(&first_data);
   8516 
   8517   MockRead data_reads[] = {
   8518     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8519     MockRead("hello world"),
   8520     MockRead(ASYNC, OK),
   8521   };
   8522   StaticSocketDataProvider second_data(
   8523       data_reads, arraysize(data_reads), NULL, 0);
   8524   session_deps_.socket_factory->AddSocketDataProvider(&second_data);
   8525 
   8526   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8527 
   8528   base::WeakPtr<HttpServerProperties> http_server_properties =
   8529       session->http_server_properties();
   8530   const int kUnrestrictedAlternatePort = 1024;
   8531   http_server_properties->SetAlternateProtocol(
   8532       HostPortPair::FromURL(restricted_port_request.url),
   8533       kUnrestrictedAlternatePort,
   8534       AlternateProtocolFromNextProto(GetParam()));
   8535 
   8536   scoped_ptr<HttpTransaction> trans(
   8537       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8538   TestCompletionCallback callback;
   8539 
   8540   int rv = trans->Start(
   8541       &restricted_port_request,
   8542       callback.callback(), BoundNetLog());
   8543   EXPECT_EQ(ERR_IO_PENDING, rv);
   8544   // Invalid change to unrestricted port should fail.
   8545   EXPECT_EQ(ERR_CONNECTION_REFUSED, callback.WaitForResult());
   8546 }
   8547 
   8548 TEST_P(HttpNetworkTransactionTest,
   8549        AlternateProtocolPortRestrictedPermitted) {
   8550   // Ensure that we're allowed to redirect traffic via an alternate
   8551   // protocol to an unrestricted (port >= 1024) when the original traffic was
   8552   // on a restricted port (port < 1024) if we set
   8553   // enable_user_alternate_protocol_ports.
   8554 
   8555   session_deps_.use_alternate_protocols = true;
   8556   session_deps_.enable_user_alternate_protocol_ports = true;
   8557 
   8558   HttpRequestInfo restricted_port_request;
   8559   restricted_port_request.method = "GET";
   8560   restricted_port_request.url = GURL("http://www.google.com:1023/");
   8561   restricted_port_request.load_flags = 0;
   8562 
   8563   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   8564   StaticSocketDataProvider first_data;
   8565   first_data.set_connect_data(mock_connect);
   8566   session_deps_.socket_factory->AddSocketDataProvider(&first_data);
   8567 
   8568   MockRead data_reads[] = {
   8569     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8570     MockRead("hello world"),
   8571     MockRead(ASYNC, OK),
   8572   };
   8573   StaticSocketDataProvider second_data(
   8574       data_reads, arraysize(data_reads), NULL, 0);
   8575   session_deps_.socket_factory->AddSocketDataProvider(&second_data);
   8576 
   8577   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8578 
   8579   base::WeakPtr<HttpServerProperties> http_server_properties =
   8580       session->http_server_properties();
   8581   const int kUnrestrictedAlternatePort = 1024;
   8582   http_server_properties->SetAlternateProtocol(
   8583       HostPortPair::FromURL(restricted_port_request.url),
   8584       kUnrestrictedAlternatePort,
   8585       AlternateProtocolFromNextProto(GetParam()));
   8586 
   8587   scoped_ptr<HttpTransaction> trans(
   8588       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8589   TestCompletionCallback callback;
   8590 
   8591   EXPECT_EQ(ERR_IO_PENDING, trans->Start(
   8592       &restricted_port_request,
   8593       callback.callback(), BoundNetLog()));
   8594   // Change to unrestricted port should succeed.
   8595   EXPECT_EQ(OK, callback.WaitForResult());
   8596 }
   8597 
   8598 TEST_P(HttpNetworkTransactionTest,
   8599        AlternateProtocolPortRestrictedAllowed) {
   8600   // Ensure that we're not allowed to redirect traffic via an alternate
   8601   // protocol to an unrestricted (port >= 1024) when the original traffic was
   8602   // on a restricted port (port < 1024).  Ensure that we can redirect in all
   8603   // other cases.
   8604   session_deps_.use_alternate_protocols = true;
   8605 
   8606   HttpRequestInfo restricted_port_request;
   8607   restricted_port_request.method = "GET";
   8608   restricted_port_request.url = GURL("http://www.google.com:1023/");
   8609   restricted_port_request.load_flags = 0;
   8610 
   8611   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   8612   StaticSocketDataProvider first_data;
   8613   first_data.set_connect_data(mock_connect);
   8614   session_deps_.socket_factory->AddSocketDataProvider(&first_data);
   8615 
   8616   MockRead data_reads[] = {
   8617     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8618     MockRead("hello world"),
   8619     MockRead(ASYNC, OK),
   8620   };
   8621   StaticSocketDataProvider second_data(
   8622       data_reads, arraysize(data_reads), NULL, 0);
   8623   session_deps_.socket_factory->AddSocketDataProvider(&second_data);
   8624 
   8625   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8626 
   8627   base::WeakPtr<HttpServerProperties> http_server_properties =
   8628       session->http_server_properties();
   8629   const int kRestrictedAlternatePort = 80;
   8630   http_server_properties->SetAlternateProtocol(
   8631       HostPortPair::FromURL(restricted_port_request.url),
   8632       kRestrictedAlternatePort,
   8633       AlternateProtocolFromNextProto(GetParam()));
   8634 
   8635   scoped_ptr<HttpTransaction> trans(
   8636       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8637   TestCompletionCallback callback;
   8638 
   8639   int rv = trans->Start(
   8640       &restricted_port_request,
   8641       callback.callback(), BoundNetLog());
   8642   EXPECT_EQ(ERR_IO_PENDING, rv);
   8643   // Valid change to restricted port should pass.
   8644   EXPECT_EQ(OK, callback.WaitForResult());
   8645 }
   8646 
   8647 TEST_P(HttpNetworkTransactionTest,
   8648        AlternateProtocolPortUnrestrictedAllowed1) {
   8649   // Ensure that we're not allowed to redirect traffic via an alternate
   8650   // protocol to an unrestricted (port >= 1024) when the original traffic was
   8651   // on a restricted port (port < 1024).  Ensure that we can redirect in all
   8652   // other cases.
   8653   session_deps_.use_alternate_protocols = true;
   8654 
   8655   HttpRequestInfo unrestricted_port_request;
   8656   unrestricted_port_request.method = "GET";
   8657   unrestricted_port_request.url = GURL("http://www.google.com:1024/");
   8658   unrestricted_port_request.load_flags = 0;
   8659 
   8660   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   8661   StaticSocketDataProvider first_data;
   8662   first_data.set_connect_data(mock_connect);
   8663   session_deps_.socket_factory->AddSocketDataProvider(&first_data);
   8664 
   8665   MockRead data_reads[] = {
   8666     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8667     MockRead("hello world"),
   8668     MockRead(ASYNC, OK),
   8669   };
   8670   StaticSocketDataProvider second_data(
   8671       data_reads, arraysize(data_reads), NULL, 0);
   8672   session_deps_.socket_factory->AddSocketDataProvider(&second_data);
   8673 
   8674   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8675 
   8676   base::WeakPtr<HttpServerProperties> http_server_properties =
   8677       session->http_server_properties();
   8678   const int kRestrictedAlternatePort = 80;
   8679   http_server_properties->SetAlternateProtocol(
   8680       HostPortPair::FromURL(unrestricted_port_request.url),
   8681       kRestrictedAlternatePort,
   8682       AlternateProtocolFromNextProto(GetParam()));
   8683 
   8684   scoped_ptr<HttpTransaction> trans(
   8685       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8686   TestCompletionCallback callback;
   8687 
   8688   int rv = trans->Start(
   8689       &unrestricted_port_request, callback.callback(), BoundNetLog());
   8690   EXPECT_EQ(ERR_IO_PENDING, rv);
   8691   // Valid change to restricted port should pass.
   8692   EXPECT_EQ(OK, callback.WaitForResult());
   8693 }
   8694 
   8695 TEST_P(HttpNetworkTransactionTest,
   8696        AlternateProtocolPortUnrestrictedAllowed2) {
   8697   // Ensure that we're not allowed to redirect traffic via an alternate
   8698   // protocol to an unrestricted (port >= 1024) when the original traffic was
   8699   // on a restricted port (port < 1024).  Ensure that we can redirect in all
   8700   // other cases.
   8701   session_deps_.use_alternate_protocols = true;
   8702 
   8703   HttpRequestInfo unrestricted_port_request;
   8704   unrestricted_port_request.method = "GET";
   8705   unrestricted_port_request.url = GURL("http://www.google.com:1024/");
   8706   unrestricted_port_request.load_flags = 0;
   8707 
   8708   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   8709   StaticSocketDataProvider first_data;
   8710   first_data.set_connect_data(mock_connect);
   8711   session_deps_.socket_factory->AddSocketDataProvider(&first_data);
   8712 
   8713   MockRead data_reads[] = {
   8714     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8715     MockRead("hello world"),
   8716     MockRead(ASYNC, OK),
   8717   };
   8718   StaticSocketDataProvider second_data(
   8719       data_reads, arraysize(data_reads), NULL, 0);
   8720   session_deps_.socket_factory->AddSocketDataProvider(&second_data);
   8721 
   8722   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8723 
   8724   base::WeakPtr<HttpServerProperties> http_server_properties =
   8725       session->http_server_properties();
   8726   const int kUnrestrictedAlternatePort = 1024;
   8727   http_server_properties->SetAlternateProtocol(
   8728       HostPortPair::FromURL(unrestricted_port_request.url),
   8729       kUnrestrictedAlternatePort,
   8730       AlternateProtocolFromNextProto(GetParam()));
   8731 
   8732   scoped_ptr<HttpTransaction> trans(
   8733       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8734   TestCompletionCallback callback;
   8735 
   8736   int rv = trans->Start(
   8737       &unrestricted_port_request, callback.callback(), BoundNetLog());
   8738   EXPECT_EQ(ERR_IO_PENDING, rv);
   8739   // Valid change to an unrestricted port should pass.
   8740   EXPECT_EQ(OK, callback.WaitForResult());
   8741 }
   8742 
   8743 TEST_P(HttpNetworkTransactionTest, AlternateProtocolUnsafeBlocked) {
   8744   // Ensure that we're not allowed to redirect traffic via an alternate
   8745   // protocol to an unsafe port, and that we resume the second
   8746   // HttpStreamFactoryImpl::Job once the alternate protocol request fails.
   8747   session_deps_.use_alternate_protocols = true;
   8748 
   8749   HttpRequestInfo request;
   8750   request.method = "GET";
   8751   request.url = GURL("http://www.google.com/");
   8752   request.load_flags = 0;
   8753 
   8754   // The alternate protocol request will error out before we attempt to connect,
   8755   // so only the standard HTTP request will try to connect.
   8756   MockRead data_reads[] = {
   8757     MockRead("HTTP/1.1 200 OK\r\n\r\n"),
   8758     MockRead("hello world"),
   8759     MockRead(ASYNC, OK),
   8760   };
   8761   StaticSocketDataProvider data(
   8762       data_reads, arraysize(data_reads), NULL, 0);
   8763   session_deps_.socket_factory->AddSocketDataProvider(&data);
   8764 
   8765   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8766 
   8767   base::WeakPtr<HttpServerProperties> http_server_properties =
   8768       session->http_server_properties();
   8769   const int kUnsafePort = 7;
   8770   http_server_properties->SetAlternateProtocol(
   8771       HostPortPair::FromURL(request.url),
   8772       kUnsafePort,
   8773       AlternateProtocolFromNextProto(GetParam()));
   8774 
   8775   scoped_ptr<HttpTransaction> trans(
   8776       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8777   TestCompletionCallback callback;
   8778 
   8779   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8780   EXPECT_EQ(ERR_IO_PENDING, rv);
   8781   // The HTTP request should succeed.
   8782   EXPECT_EQ(OK, callback.WaitForResult());
   8783 
   8784   // Disable alternate protocol before the asserts.
   8785  // HttpStreamFactory::set_use_alternate_protocols(false);
   8786 
   8787   const HttpResponseInfo* response = trans->GetResponseInfo();
   8788   ASSERT_TRUE(response != NULL);
   8789   ASSERT_TRUE(response->headers.get() != NULL);
   8790   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8791 
   8792   std::string response_data;
   8793   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   8794   EXPECT_EQ("hello world", response_data);
   8795 }
   8796 
   8797 TEST_P(HttpNetworkTransactionTest, UseAlternateProtocolForNpnSpdy) {
   8798   session_deps_.use_alternate_protocols = true;
   8799   session_deps_.next_protos = SpdyNextProtos();
   8800 
   8801   HttpRequestInfo request;
   8802   request.method = "GET";
   8803   request.url = GURL("http://www.google.com/");
   8804   request.load_flags = 0;
   8805 
   8806   std::string alternate_protocol_http_header =
   8807       GetAlternateProtocolHttpHeader();
   8808 
   8809   MockRead data_reads[] = {
   8810     MockRead("HTTP/1.1 200 OK\r\n"),
   8811     MockRead(alternate_protocol_http_header.c_str()),
   8812     MockRead("hello world"),
   8813     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   8814     MockRead(ASYNC, OK)
   8815   };
   8816 
   8817   StaticSocketDataProvider first_transaction(
   8818       data_reads, arraysize(data_reads), NULL, 0);
   8819   session_deps_.socket_factory->AddSocketDataProvider(&first_transaction);
   8820 
   8821   SSLSocketDataProvider ssl(ASYNC, OK);
   8822   ssl.SetNextProto(GetParam());
   8823   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   8824 
   8825   scoped_ptr<SpdyFrame> req(
   8826       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, true));
   8827   MockWrite spdy_writes[] = { CreateMockWrite(*req) };
   8828 
   8829   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   8830   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   8831   MockRead spdy_reads[] = {
   8832     CreateMockRead(*resp),
   8833     CreateMockRead(*data),
   8834     MockRead(ASYNC, 0, 0),
   8835   };
   8836 
   8837   DelayedSocketData spdy_data(
   8838       1,  // wait for one write to finish before reading.
   8839       spdy_reads, arraysize(spdy_reads),
   8840       spdy_writes, arraysize(spdy_writes));
   8841   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   8842 
   8843   MockConnect never_finishing_connect(SYNCHRONOUS, ERR_IO_PENDING);
   8844   StaticSocketDataProvider hanging_non_alternate_protocol_socket(
   8845       NULL, 0, NULL, 0);
   8846   hanging_non_alternate_protocol_socket.set_connect_data(
   8847       never_finishing_connect);
   8848   session_deps_.socket_factory->AddSocketDataProvider(
   8849       &hanging_non_alternate_protocol_socket);
   8850 
   8851   TestCompletionCallback callback;
   8852 
   8853   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8854   scoped_ptr<HttpTransaction> trans(
   8855       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8856 
   8857   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8858   EXPECT_EQ(ERR_IO_PENDING, rv);
   8859   EXPECT_EQ(OK, callback.WaitForResult());
   8860 
   8861   const HttpResponseInfo* response = trans->GetResponseInfo();
   8862   ASSERT_TRUE(response != NULL);
   8863   ASSERT_TRUE(response->headers.get() != NULL);
   8864   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8865 
   8866   std::string response_data;
   8867   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   8868   EXPECT_EQ("hello world", response_data);
   8869 
   8870   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   8871 
   8872   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   8873   EXPECT_EQ(ERR_IO_PENDING, rv);
   8874   EXPECT_EQ(OK, callback.WaitForResult());
   8875 
   8876   response = trans->GetResponseInfo();
   8877   ASSERT_TRUE(response != NULL);
   8878   ASSERT_TRUE(response->headers.get() != NULL);
   8879   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8880   EXPECT_TRUE(response->was_fetched_via_spdy);
   8881   EXPECT_TRUE(response->was_npn_negotiated);
   8882 
   8883   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   8884   EXPECT_EQ("hello!", response_data);
   8885 }
   8886 
   8887 TEST_P(HttpNetworkTransactionTest, AlternateProtocolWithSpdyLateBinding) {
   8888   session_deps_.use_alternate_protocols = true;
   8889   session_deps_.next_protos = SpdyNextProtos();
   8890 
   8891   HttpRequestInfo request;
   8892   request.method = "GET";
   8893   request.url = GURL("http://www.google.com/");
   8894   request.load_flags = 0;
   8895 
   8896   std::string alternate_protocol_http_header =
   8897       GetAlternateProtocolHttpHeader();
   8898 
   8899   MockRead data_reads[] = {
   8900     MockRead("HTTP/1.1 200 OK\r\n"),
   8901     MockRead(alternate_protocol_http_header.c_str()),
   8902     MockRead("hello world"),
   8903     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   8904     MockRead(ASYNC, OK),
   8905   };
   8906 
   8907   StaticSocketDataProvider first_transaction(
   8908       data_reads, arraysize(data_reads), NULL, 0);
   8909   // Socket 1 is the HTTP transaction with the Alternate-Protocol header.
   8910   session_deps_.socket_factory->AddSocketDataProvider(&first_transaction);
   8911 
   8912   MockConnect never_finishing_connect(SYNCHRONOUS, ERR_IO_PENDING);
   8913   StaticSocketDataProvider hanging_socket(
   8914       NULL, 0, NULL, 0);
   8915   hanging_socket.set_connect_data(never_finishing_connect);
   8916   // Socket 2 and 3 are the hanging Alternate-Protocol and
   8917   // non-Alternate-Protocol jobs from the 2nd transaction.
   8918   session_deps_.socket_factory->AddSocketDataProvider(&hanging_socket);
   8919   session_deps_.socket_factory->AddSocketDataProvider(&hanging_socket);
   8920 
   8921   SSLSocketDataProvider ssl(ASYNC, OK);
   8922   ssl.SetNextProto(GetParam());
   8923   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   8924 
   8925   scoped_ptr<SpdyFrame> req1(
   8926       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, true));
   8927   scoped_ptr<SpdyFrame> req2(
   8928       spdy_util_.ConstructSpdyGet(NULL, 0, false, 3, LOWEST, true));
   8929   MockWrite spdy_writes[] = {
   8930     CreateMockWrite(*req1),
   8931     CreateMockWrite(*req2),
   8932   };
   8933   scoped_ptr<SpdyFrame> resp1(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   8934   scoped_ptr<SpdyFrame> data1(spdy_util_.ConstructSpdyBodyFrame(1, true));
   8935   scoped_ptr<SpdyFrame> resp2(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   8936   scoped_ptr<SpdyFrame> data2(spdy_util_.ConstructSpdyBodyFrame(3, true));
   8937   MockRead spdy_reads[] = {
   8938     CreateMockRead(*resp1),
   8939     CreateMockRead(*data1),
   8940     CreateMockRead(*resp2),
   8941     CreateMockRead(*data2),
   8942     MockRead(ASYNC, 0, 0),
   8943   };
   8944 
   8945   DelayedSocketData spdy_data(
   8946       2,  // wait for writes to finish before reading.
   8947       spdy_reads, arraysize(spdy_reads),
   8948       spdy_writes, arraysize(spdy_writes));
   8949   // Socket 4 is the successful Alternate-Protocol for transaction 3.
   8950   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   8951 
   8952   // Socket 5 is the unsuccessful non-Alternate-Protocol for transaction 3.
   8953   session_deps_.socket_factory->AddSocketDataProvider(&hanging_socket);
   8954 
   8955   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   8956   TestCompletionCallback callback1;
   8957   HttpNetworkTransaction trans1(DEFAULT_PRIORITY, session.get());
   8958 
   8959   int rv = trans1.Start(&request, callback1.callback(), BoundNetLog());
   8960   EXPECT_EQ(ERR_IO_PENDING, rv);
   8961   EXPECT_EQ(OK, callback1.WaitForResult());
   8962 
   8963   const HttpResponseInfo* response = trans1.GetResponseInfo();
   8964   ASSERT_TRUE(response != NULL);
   8965   ASSERT_TRUE(response->headers.get() != NULL);
   8966   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8967 
   8968   std::string response_data;
   8969   ASSERT_EQ(OK, ReadTransaction(&trans1, &response_data));
   8970   EXPECT_EQ("hello world", response_data);
   8971 
   8972   TestCompletionCallback callback2;
   8973   HttpNetworkTransaction trans2(DEFAULT_PRIORITY, session.get());
   8974   rv = trans2.Start(&request, callback2.callback(), BoundNetLog());
   8975   EXPECT_EQ(ERR_IO_PENDING, rv);
   8976 
   8977   TestCompletionCallback callback3;
   8978   HttpNetworkTransaction trans3(DEFAULT_PRIORITY, session.get());
   8979   rv = trans3.Start(&request, callback3.callback(), BoundNetLog());
   8980   EXPECT_EQ(ERR_IO_PENDING, rv);
   8981 
   8982   EXPECT_EQ(OK, callback2.WaitForResult());
   8983   EXPECT_EQ(OK, callback3.WaitForResult());
   8984 
   8985   response = trans2.GetResponseInfo();
   8986   ASSERT_TRUE(response != NULL);
   8987   ASSERT_TRUE(response->headers.get() != NULL);
   8988   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8989   EXPECT_TRUE(response->was_fetched_via_spdy);
   8990   EXPECT_TRUE(response->was_npn_negotiated);
   8991   ASSERT_EQ(OK, ReadTransaction(&trans2, &response_data));
   8992   EXPECT_EQ("hello!", response_data);
   8993 
   8994   response = trans3.GetResponseInfo();
   8995   ASSERT_TRUE(response != NULL);
   8996   ASSERT_TRUE(response->headers.get() != NULL);
   8997   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   8998   EXPECT_TRUE(response->was_fetched_via_spdy);
   8999   EXPECT_TRUE(response->was_npn_negotiated);
   9000   ASSERT_EQ(OK, ReadTransaction(&trans3, &response_data));
   9001   EXPECT_EQ("hello!", response_data);
   9002 }
   9003 
   9004 TEST_P(HttpNetworkTransactionTest, StallAlternateProtocolForNpnSpdy) {
   9005   session_deps_.use_alternate_protocols = true;
   9006   session_deps_.next_protos = SpdyNextProtos();
   9007 
   9008   HttpRequestInfo request;
   9009   request.method = "GET";
   9010   request.url = GURL("http://www.google.com/");
   9011   request.load_flags = 0;
   9012 
   9013   std::string alternate_protocol_http_header =
   9014       GetAlternateProtocolHttpHeader();
   9015 
   9016   MockRead data_reads[] = {
   9017     MockRead("HTTP/1.1 200 OK\r\n"),
   9018     MockRead(alternate_protocol_http_header.c_str()),
   9019     MockRead("hello world"),
   9020     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   9021     MockRead(ASYNC, OK),
   9022   };
   9023 
   9024   StaticSocketDataProvider first_transaction(
   9025       data_reads, arraysize(data_reads), NULL, 0);
   9026   session_deps_.socket_factory->AddSocketDataProvider(&first_transaction);
   9027 
   9028   SSLSocketDataProvider ssl(ASYNC, OK);
   9029   ssl.SetNextProto(GetParam());
   9030   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   9031 
   9032   MockConnect never_finishing_connect(SYNCHRONOUS, ERR_IO_PENDING);
   9033   StaticSocketDataProvider hanging_alternate_protocol_socket(
   9034       NULL, 0, NULL, 0);
   9035   hanging_alternate_protocol_socket.set_connect_data(
   9036       never_finishing_connect);
   9037   session_deps_.socket_factory->AddSocketDataProvider(
   9038       &hanging_alternate_protocol_socket);
   9039 
   9040   // 2nd request is just a copy of the first one, over HTTP again.
   9041   session_deps_.socket_factory->AddSocketDataProvider(&first_transaction);
   9042 
   9043   TestCompletionCallback callback;
   9044 
   9045   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   9046   scoped_ptr<HttpTransaction> trans(
   9047       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9048 
   9049   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9050   EXPECT_EQ(ERR_IO_PENDING, rv);
   9051   EXPECT_EQ(OK, callback.WaitForResult());
   9052 
   9053   const HttpResponseInfo* response = trans->GetResponseInfo();
   9054   ASSERT_TRUE(response != NULL);
   9055   ASSERT_TRUE(response->headers.get() != NULL);
   9056   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9057 
   9058   std::string response_data;
   9059   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9060   EXPECT_EQ("hello world", response_data);
   9061 
   9062   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9063 
   9064   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9065   EXPECT_EQ(ERR_IO_PENDING, rv);
   9066   EXPECT_EQ(OK, callback.WaitForResult());
   9067 
   9068   response = trans->GetResponseInfo();
   9069   ASSERT_TRUE(response != NULL);
   9070   ASSERT_TRUE(response->headers.get() != NULL);
   9071   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9072   EXPECT_FALSE(response->was_fetched_via_spdy);
   9073   EXPECT_FALSE(response->was_npn_negotiated);
   9074 
   9075   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9076   EXPECT_EQ("hello world", response_data);
   9077 }
   9078 
   9079 class CapturingProxyResolver : public ProxyResolver {
   9080  public:
   9081   CapturingProxyResolver() : ProxyResolver(false /* expects_pac_bytes */) {}
   9082   virtual ~CapturingProxyResolver() {}
   9083 
   9084   virtual int GetProxyForURL(const GURL& url,
   9085                              ProxyInfo* results,
   9086                              const CompletionCallback& callback,
   9087                              RequestHandle* request,
   9088                              const BoundNetLog& net_log) OVERRIDE {
   9089     ProxyServer proxy_server(ProxyServer::SCHEME_HTTP,
   9090                              HostPortPair("myproxy", 80));
   9091     results->UseProxyServer(proxy_server);
   9092     resolved_.push_back(url);
   9093     return OK;
   9094   }
   9095 
   9096   virtual void CancelRequest(RequestHandle request) OVERRIDE {
   9097     NOTREACHED();
   9098   }
   9099 
   9100   virtual LoadState GetLoadState(RequestHandle request) const OVERRIDE {
   9101     NOTREACHED();
   9102     return LOAD_STATE_IDLE;
   9103   }
   9104 
   9105   virtual void CancelSetPacScript() OVERRIDE {
   9106     NOTREACHED();
   9107   }
   9108 
   9109   virtual int SetPacScript(const scoped_refptr<ProxyResolverScriptData>&,
   9110                            const CompletionCallback& /*callback*/) OVERRIDE {
   9111     return OK;
   9112   }
   9113 
   9114   const std::vector<GURL>& resolved() const { return resolved_; }
   9115 
   9116  private:
   9117   std::vector<GURL> resolved_;
   9118 
   9119   DISALLOW_COPY_AND_ASSIGN(CapturingProxyResolver);
   9120 };
   9121 
   9122 TEST_P(HttpNetworkTransactionTest,
   9123        UseAlternateProtocolForTunneledNpnSpdy) {
   9124   session_deps_.use_alternate_protocols = true;
   9125   session_deps_.next_protos = SpdyNextProtos();
   9126 
   9127   ProxyConfig proxy_config;
   9128   proxy_config.set_auto_detect(true);
   9129   proxy_config.set_pac_url(GURL("http://fooproxyurl"));
   9130 
   9131   CapturingProxyResolver* capturing_proxy_resolver =
   9132       new CapturingProxyResolver();
   9133   session_deps_.proxy_service.reset(new ProxyService(
   9134       new ProxyConfigServiceFixed(proxy_config), capturing_proxy_resolver,
   9135       NULL));
   9136   CapturingNetLog net_log;
   9137   session_deps_.net_log = &net_log;
   9138 
   9139   HttpRequestInfo request;
   9140   request.method = "GET";
   9141   request.url = GURL("http://www.google.com/");
   9142   request.load_flags = 0;
   9143 
   9144   std::string alternate_protocol_http_header =
   9145       GetAlternateProtocolHttpHeader();
   9146 
   9147   MockRead data_reads[] = {
   9148     MockRead("HTTP/1.1 200 OK\r\n"),
   9149     MockRead(alternate_protocol_http_header.c_str()),
   9150     MockRead("hello world"),
   9151     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   9152     MockRead(ASYNC, OK),
   9153   };
   9154 
   9155   StaticSocketDataProvider first_transaction(
   9156       data_reads, arraysize(data_reads), NULL, 0);
   9157   session_deps_.socket_factory->AddSocketDataProvider(&first_transaction);
   9158 
   9159   SSLSocketDataProvider ssl(ASYNC, OK);
   9160   ssl.SetNextProto(GetParam());
   9161   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   9162 
   9163   scoped_ptr<SpdyFrame> req(
   9164       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, true));
   9165   MockWrite spdy_writes[] = {
   9166     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   9167               "Host: www.google.com\r\n"
   9168               "Proxy-Connection: keep-alive\r\n\r\n"),  // 0
   9169     CreateMockWrite(*req),                              // 3
   9170   };
   9171 
   9172   const char kCONNECTResponse[] = "HTTP/1.1 200 Connected\r\n\r\n";
   9173 
   9174   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   9175   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   9176   MockRead spdy_reads[] = {
   9177     MockRead(ASYNC, kCONNECTResponse, arraysize(kCONNECTResponse) - 1, 1),  // 1
   9178     CreateMockRead(*resp.get(), 4),  // 2, 4
   9179     CreateMockRead(*data.get(), 4),  // 5
   9180     MockRead(ASYNC, 0, 0, 4),  // 6
   9181   };
   9182 
   9183   OrderedSocketData spdy_data(
   9184       spdy_reads, arraysize(spdy_reads),
   9185       spdy_writes, arraysize(spdy_writes));
   9186   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   9187 
   9188   MockConnect never_finishing_connect(SYNCHRONOUS, ERR_IO_PENDING);
   9189   StaticSocketDataProvider hanging_non_alternate_protocol_socket(
   9190       NULL, 0, NULL, 0);
   9191   hanging_non_alternate_protocol_socket.set_connect_data(
   9192       never_finishing_connect);
   9193   session_deps_.socket_factory->AddSocketDataProvider(
   9194       &hanging_non_alternate_protocol_socket);
   9195 
   9196   TestCompletionCallback callback;
   9197 
   9198   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   9199   scoped_ptr<HttpTransaction> trans(
   9200       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9201 
   9202   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9203   EXPECT_EQ(ERR_IO_PENDING, rv);
   9204   EXPECT_EQ(OK, callback.WaitForResult());
   9205 
   9206   const HttpResponseInfo* response = trans->GetResponseInfo();
   9207   ASSERT_TRUE(response != NULL);
   9208   ASSERT_TRUE(response->headers.get() != NULL);
   9209   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9210   EXPECT_FALSE(response->was_fetched_via_spdy);
   9211   EXPECT_FALSE(response->was_npn_negotiated);
   9212 
   9213   std::string response_data;
   9214   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9215   EXPECT_EQ("hello world", response_data);
   9216 
   9217   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9218 
   9219   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9220   EXPECT_EQ(ERR_IO_PENDING, rv);
   9221   EXPECT_EQ(OK, callback.WaitForResult());
   9222 
   9223   response = trans->GetResponseInfo();
   9224   ASSERT_TRUE(response != NULL);
   9225   ASSERT_TRUE(response->headers.get() != NULL);
   9226   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9227   EXPECT_TRUE(response->was_fetched_via_spdy);
   9228   EXPECT_TRUE(response->was_npn_negotiated);
   9229 
   9230   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9231   EXPECT_EQ("hello!", response_data);
   9232   ASSERT_EQ(3u, capturing_proxy_resolver->resolved().size());
   9233   EXPECT_EQ("http://www.google.com/",
   9234             capturing_proxy_resolver->resolved()[0].spec());
   9235   EXPECT_EQ("https://www.google.com/",
   9236             capturing_proxy_resolver->resolved()[1].spec());
   9237 
   9238   LoadTimingInfo load_timing_info;
   9239   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   9240   TestLoadTimingNotReusedWithPac(load_timing_info,
   9241                                  CONNECT_TIMING_HAS_SSL_TIMES);
   9242 }
   9243 
   9244 TEST_P(HttpNetworkTransactionTest,
   9245        UseAlternateProtocolForNpnSpdyWithExistingSpdySession) {
   9246   session_deps_.use_alternate_protocols = true;
   9247   session_deps_.next_protos = SpdyNextProtos();
   9248 
   9249   HttpRequestInfo request;
   9250   request.method = "GET";
   9251   request.url = GURL("http://www.google.com/");
   9252   request.load_flags = 0;
   9253 
   9254   std::string alternate_protocol_http_header =
   9255       GetAlternateProtocolHttpHeader();
   9256 
   9257   MockRead data_reads[] = {
   9258     MockRead("HTTP/1.1 200 OK\r\n"),
   9259     MockRead(alternate_protocol_http_header.c_str()),
   9260     MockRead("hello world"),
   9261     MockRead(ASYNC, OK),
   9262   };
   9263 
   9264   StaticSocketDataProvider first_transaction(
   9265       data_reads, arraysize(data_reads), NULL, 0);
   9266   session_deps_.socket_factory->AddSocketDataProvider(&first_transaction);
   9267 
   9268   SSLSocketDataProvider ssl(ASYNC, OK);
   9269   ssl.SetNextProto(GetParam());
   9270   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   9271 
   9272   scoped_ptr<SpdyFrame> req(
   9273       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, true));
   9274   MockWrite spdy_writes[] = { CreateMockWrite(*req) };
   9275 
   9276   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   9277   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   9278   MockRead spdy_reads[] = {
   9279     CreateMockRead(*resp),
   9280     CreateMockRead(*data),
   9281     MockRead(ASYNC, 0, 0),
   9282   };
   9283 
   9284   DelayedSocketData spdy_data(
   9285       1,  // wait for one write to finish before reading.
   9286       spdy_reads, arraysize(spdy_reads),
   9287       spdy_writes, arraysize(spdy_writes));
   9288   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   9289 
   9290   TestCompletionCallback callback;
   9291 
   9292   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   9293 
   9294   scoped_ptr<HttpTransaction> trans(
   9295       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9296 
   9297   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9298   EXPECT_EQ(ERR_IO_PENDING, rv);
   9299   EXPECT_EQ(OK, callback.WaitForResult());
   9300 
   9301   const HttpResponseInfo* response = trans->GetResponseInfo();
   9302   ASSERT_TRUE(response != NULL);
   9303   ASSERT_TRUE(response->headers.get() != NULL);
   9304   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9305 
   9306   std::string response_data;
   9307   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9308   EXPECT_EQ("hello world", response_data);
   9309 
   9310   // Set up an initial SpdySession in the pool to reuse.
   9311   HostPortPair host_port_pair("www.google.com", 443);
   9312   SpdySessionKey key(host_port_pair, ProxyServer::Direct(),
   9313                      PRIVACY_MODE_DISABLED);
   9314   base::WeakPtr<SpdySession> spdy_session =
   9315       CreateSecureSpdySession(session, key, BoundNetLog());
   9316 
   9317   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9318 
   9319   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9320   EXPECT_EQ(ERR_IO_PENDING, rv);
   9321   EXPECT_EQ(OK, callback.WaitForResult());
   9322 
   9323   response = trans->GetResponseInfo();
   9324   ASSERT_TRUE(response != NULL);
   9325   ASSERT_TRUE(response->headers.get() != NULL);
   9326   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9327   EXPECT_TRUE(response->was_fetched_via_spdy);
   9328   EXPECT_TRUE(response->was_npn_negotiated);
   9329 
   9330   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9331   EXPECT_EQ("hello!", response_data);
   9332 }
   9333 
   9334 // GenerateAuthToken is a mighty big test.
   9335 // It tests all permutation of GenerateAuthToken behavior:
   9336 //   - Synchronous and Asynchronous completion.
   9337 //   - OK or error on completion.
   9338 //   - Direct connection, non-authenticating proxy, and authenticating proxy.
   9339 //   - HTTP or HTTPS backend (to include proxy tunneling).
   9340 //   - Non-authenticating and authenticating backend.
   9341 //
   9342 // In all, there are 44 reasonable permuations (for example, if there are
   9343 // problems generating an auth token for an authenticating proxy, we don't
   9344 // need to test all permutations of the backend server).
   9345 //
   9346 // The test proceeds by going over each of the configuration cases, and
   9347 // potentially running up to three rounds in each of the tests. The TestConfig
   9348 // specifies both the configuration for the test as well as the expectations
   9349 // for the results.
   9350 TEST_P(HttpNetworkTransactionTest, GenerateAuthToken) {
   9351   static const char kServer[] = "http://www.example.com";
   9352   static const char kSecureServer[] = "https://www.example.com";
   9353   static const char kProxy[] = "myproxy:70";
   9354   const int kAuthErr = ERR_INVALID_AUTH_CREDENTIALS;
   9355 
   9356   enum AuthTiming {
   9357     AUTH_NONE,
   9358     AUTH_SYNC,
   9359     AUTH_ASYNC,
   9360   };
   9361 
   9362   const MockWrite kGet(
   9363       "GET / HTTP/1.1\r\n"
   9364       "Host: www.example.com\r\n"
   9365       "Connection: keep-alive\r\n\r\n");
   9366   const MockWrite kGetProxy(
   9367       "GET http://www.example.com/ HTTP/1.1\r\n"
   9368       "Host: www.example.com\r\n"
   9369       "Proxy-Connection: keep-alive\r\n\r\n");
   9370   const MockWrite kGetAuth(
   9371       "GET / HTTP/1.1\r\n"
   9372       "Host: www.example.com\r\n"
   9373       "Connection: keep-alive\r\n"
   9374       "Authorization: auth_token\r\n\r\n");
   9375   const MockWrite kGetProxyAuth(
   9376       "GET http://www.example.com/ HTTP/1.1\r\n"
   9377       "Host: www.example.com\r\n"
   9378       "Proxy-Connection: keep-alive\r\n"
   9379       "Proxy-Authorization: auth_token\r\n\r\n");
   9380   const MockWrite kGetAuthThroughProxy(
   9381       "GET http://www.example.com/ HTTP/1.1\r\n"
   9382       "Host: www.example.com\r\n"
   9383       "Proxy-Connection: keep-alive\r\n"
   9384       "Authorization: auth_token\r\n\r\n");
   9385   const MockWrite kGetAuthWithProxyAuth(
   9386       "GET http://www.example.com/ HTTP/1.1\r\n"
   9387       "Host: www.example.com\r\n"
   9388       "Proxy-Connection: keep-alive\r\n"
   9389       "Proxy-Authorization: auth_token\r\n"
   9390       "Authorization: auth_token\r\n\r\n");
   9391   const MockWrite kConnect(
   9392       "CONNECT www.example.com:443 HTTP/1.1\r\n"
   9393       "Host: www.example.com\r\n"
   9394       "Proxy-Connection: keep-alive\r\n\r\n");
   9395   const MockWrite kConnectProxyAuth(
   9396       "CONNECT www.example.com:443 HTTP/1.1\r\n"
   9397       "Host: www.example.com\r\n"
   9398       "Proxy-Connection: keep-alive\r\n"
   9399       "Proxy-Authorization: auth_token\r\n\r\n");
   9400 
   9401   const MockRead kSuccess(
   9402       "HTTP/1.1 200 OK\r\n"
   9403       "Content-Type: text/html; charset=iso-8859-1\r\n"
   9404       "Content-Length: 3\r\n\r\n"
   9405       "Yes");
   9406   const MockRead kFailure(
   9407       "Should not be called.");
   9408   const MockRead kServerChallenge(
   9409       "HTTP/1.1 401 Unauthorized\r\n"
   9410       "WWW-Authenticate: Mock realm=server\r\n"
   9411       "Content-Type: text/html; charset=iso-8859-1\r\n"
   9412       "Content-Length: 14\r\n\r\n"
   9413       "Unauthorized\r\n");
   9414   const MockRead kProxyChallenge(
   9415       "HTTP/1.1 407 Unauthorized\r\n"
   9416       "Proxy-Authenticate: Mock realm=proxy\r\n"
   9417       "Proxy-Connection: close\r\n"
   9418       "Content-Type: text/html; charset=iso-8859-1\r\n"
   9419       "Content-Length: 14\r\n\r\n"
   9420       "Unauthorized\r\n");
   9421   const MockRead kProxyConnected(
   9422       "HTTP/1.1 200 Connection Established\r\n\r\n");
   9423 
   9424   // NOTE(cbentzel): I wanted TestReadWriteRound to be a simple struct with
   9425   // no constructors, but the C++ compiler on Windows warns about
   9426   // unspecified data in compound literals. So, moved to using constructors,
   9427   // and TestRound's created with the default constructor should not be used.
   9428   struct TestRound {
   9429     TestRound()
   9430         : expected_rv(ERR_UNEXPECTED),
   9431           extra_write(NULL),
   9432           extra_read(NULL) {
   9433     }
   9434     TestRound(const MockWrite& write_arg, const MockRead& read_arg,
   9435               int expected_rv_arg)
   9436         : write(write_arg),
   9437           read(read_arg),
   9438           expected_rv(expected_rv_arg),
   9439           extra_write(NULL),
   9440           extra_read(NULL) {
   9441     }
   9442     TestRound(const MockWrite& write_arg, const MockRead& read_arg,
   9443               int expected_rv_arg, const MockWrite* extra_write_arg,
   9444               const MockRead* extra_read_arg)
   9445         : write(write_arg),
   9446           read(read_arg),
   9447           expected_rv(expected_rv_arg),
   9448           extra_write(extra_write_arg),
   9449           extra_read(extra_read_arg) {
   9450     }
   9451     MockWrite write;
   9452     MockRead read;
   9453     int expected_rv;
   9454     const MockWrite* extra_write;
   9455     const MockRead* extra_read;
   9456   };
   9457 
   9458   static const int kNoSSL = 500;
   9459 
   9460   struct TestConfig {
   9461     const char* proxy_url;
   9462     AuthTiming proxy_auth_timing;
   9463     int proxy_auth_rv;
   9464     const char* server_url;
   9465     AuthTiming server_auth_timing;
   9466     int server_auth_rv;
   9467     int num_auth_rounds;
   9468     int first_ssl_round;
   9469     TestRound rounds[3];
   9470   } test_configs[] = {
   9471     // Non-authenticating HTTP server with a direct connection.
   9472     { NULL, AUTH_NONE, OK, kServer, AUTH_NONE, OK, 1, kNoSSL,
   9473       { TestRound(kGet, kSuccess, OK)}},
   9474     // Authenticating HTTP server with a direct connection.
   9475     { NULL, AUTH_NONE, OK, kServer, AUTH_SYNC, OK, 2, kNoSSL,
   9476       { TestRound(kGet, kServerChallenge, OK),
   9477         TestRound(kGetAuth, kSuccess, OK)}},
   9478     { NULL, AUTH_NONE, OK, kServer, AUTH_SYNC, kAuthErr, 2, kNoSSL,
   9479       { TestRound(kGet, kServerChallenge, OK),
   9480         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9481     { NULL, AUTH_NONE, OK, kServer, AUTH_ASYNC, OK, 2, kNoSSL,
   9482       { TestRound(kGet, kServerChallenge, OK),
   9483         TestRound(kGetAuth, kSuccess, OK)}},
   9484     { NULL, AUTH_NONE, OK, kServer, AUTH_ASYNC, kAuthErr, 2, kNoSSL,
   9485       { TestRound(kGet, kServerChallenge, OK),
   9486         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9487     // Non-authenticating HTTP server through a non-authenticating proxy.
   9488     { kProxy, AUTH_NONE, OK, kServer, AUTH_NONE, OK, 1, kNoSSL,
   9489       { TestRound(kGetProxy, kSuccess, OK)}},
   9490     // Authenticating HTTP server through a non-authenticating proxy.
   9491     { kProxy, AUTH_NONE, OK, kServer, AUTH_SYNC, OK, 2, kNoSSL,
   9492       { TestRound(kGetProxy, kServerChallenge, OK),
   9493         TestRound(kGetAuthThroughProxy, kSuccess, OK)}},
   9494     { kProxy, AUTH_NONE, OK, kServer, AUTH_SYNC, kAuthErr, 2, kNoSSL,
   9495       { TestRound(kGetProxy, kServerChallenge, OK),
   9496         TestRound(kGetAuthThroughProxy, kFailure, kAuthErr)}},
   9497     { kProxy, AUTH_NONE, OK, kServer, AUTH_ASYNC, OK, 2, kNoSSL,
   9498       { TestRound(kGetProxy, kServerChallenge, OK),
   9499         TestRound(kGetAuthThroughProxy, kSuccess, OK)}},
   9500     { kProxy, AUTH_NONE, OK, kServer, AUTH_ASYNC, kAuthErr, 2, kNoSSL,
   9501       { TestRound(kGetProxy, kServerChallenge, OK),
   9502         TestRound(kGetAuthThroughProxy, kFailure, kAuthErr)}},
   9503     // Non-authenticating HTTP server through an authenticating proxy.
   9504     { kProxy, AUTH_SYNC, OK, kServer, AUTH_NONE, OK, 2, kNoSSL,
   9505       { TestRound(kGetProxy, kProxyChallenge, OK),
   9506         TestRound(kGetProxyAuth, kSuccess, OK)}},
   9507     { kProxy, AUTH_SYNC, kAuthErr, kServer, AUTH_NONE, OK, 2, kNoSSL,
   9508       { TestRound(kGetProxy, kProxyChallenge, OK),
   9509         TestRound(kGetProxyAuth, kFailure, kAuthErr)}},
   9510     { kProxy, AUTH_ASYNC, OK, kServer, AUTH_NONE, OK, 2, kNoSSL,
   9511       { TestRound(kGetProxy, kProxyChallenge, OK),
   9512         TestRound(kGetProxyAuth, kSuccess, OK)}},
   9513     { kProxy, AUTH_ASYNC, kAuthErr, kServer, AUTH_NONE, OK, 2, kNoSSL,
   9514       { TestRound(kGetProxy, kProxyChallenge, OK),
   9515         TestRound(kGetProxyAuth, kFailure, kAuthErr)}},
   9516     // Authenticating HTTP server through an authenticating proxy.
   9517     { kProxy, AUTH_SYNC, OK, kServer, AUTH_SYNC, OK, 3, kNoSSL,
   9518       { TestRound(kGetProxy, kProxyChallenge, OK),
   9519         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9520         TestRound(kGetAuthWithProxyAuth, kSuccess, OK)}},
   9521     { kProxy, AUTH_SYNC, OK, kServer, AUTH_SYNC, kAuthErr, 3, kNoSSL,
   9522       { TestRound(kGetProxy, kProxyChallenge, OK),
   9523         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9524         TestRound(kGetAuthWithProxyAuth, kFailure, kAuthErr)}},
   9525     { kProxy, AUTH_ASYNC, OK, kServer, AUTH_SYNC, OK, 3, kNoSSL,
   9526       { TestRound(kGetProxy, kProxyChallenge, OK),
   9527         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9528         TestRound(kGetAuthWithProxyAuth, kSuccess, OK)}},
   9529     { kProxy, AUTH_ASYNC, OK, kServer, AUTH_SYNC, kAuthErr, 3, kNoSSL,
   9530       { TestRound(kGetProxy, kProxyChallenge, OK),
   9531         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9532         TestRound(kGetAuthWithProxyAuth, kFailure, kAuthErr)}},
   9533     { kProxy, AUTH_SYNC, OK, kServer, AUTH_ASYNC, OK, 3, kNoSSL,
   9534       { TestRound(kGetProxy, kProxyChallenge, OK),
   9535         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9536         TestRound(kGetAuthWithProxyAuth, kSuccess, OK)}},
   9537     { kProxy, AUTH_SYNC, OK, kServer, AUTH_ASYNC, kAuthErr, 3, kNoSSL,
   9538       { TestRound(kGetProxy, kProxyChallenge, OK),
   9539         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9540         TestRound(kGetAuthWithProxyAuth, kFailure, kAuthErr)}},
   9541     { kProxy, AUTH_ASYNC, OK, kServer, AUTH_ASYNC, OK, 3, kNoSSL,
   9542       { TestRound(kGetProxy, kProxyChallenge, OK),
   9543         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9544         TestRound(kGetAuthWithProxyAuth, kSuccess, OK)}},
   9545     { kProxy, AUTH_ASYNC, OK, kServer, AUTH_ASYNC, kAuthErr, 3, kNoSSL,
   9546       { TestRound(kGetProxy, kProxyChallenge, OK),
   9547         TestRound(kGetProxyAuth, kServerChallenge, OK),
   9548         TestRound(kGetAuthWithProxyAuth, kFailure, kAuthErr)}},
   9549     // Non-authenticating HTTPS server with a direct connection.
   9550     { NULL, AUTH_NONE, OK, kSecureServer, AUTH_NONE, OK, 1, 0,
   9551       { TestRound(kGet, kSuccess, OK)}},
   9552     // Authenticating HTTPS server with a direct connection.
   9553     { NULL, AUTH_NONE, OK, kSecureServer, AUTH_SYNC, OK, 2, 0,
   9554       { TestRound(kGet, kServerChallenge, OK),
   9555         TestRound(kGetAuth, kSuccess, OK)}},
   9556     { NULL, AUTH_NONE, OK, kSecureServer, AUTH_SYNC, kAuthErr, 2, 0,
   9557       { TestRound(kGet, kServerChallenge, OK),
   9558         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9559     { NULL, AUTH_NONE, OK, kSecureServer, AUTH_ASYNC, OK, 2, 0,
   9560       { TestRound(kGet, kServerChallenge, OK),
   9561         TestRound(kGetAuth, kSuccess, OK)}},
   9562     { NULL, AUTH_NONE, OK, kSecureServer, AUTH_ASYNC, kAuthErr, 2, 0,
   9563       { TestRound(kGet, kServerChallenge, OK),
   9564         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9565     // Non-authenticating HTTPS server with a non-authenticating proxy.
   9566     { kProxy, AUTH_NONE, OK, kSecureServer, AUTH_NONE, OK, 1, 0,
   9567       { TestRound(kConnect, kProxyConnected, OK, &kGet, &kSuccess)}},
   9568     // Authenticating HTTPS server through a non-authenticating proxy.
   9569     { kProxy, AUTH_NONE, OK, kSecureServer, AUTH_SYNC, OK, 2, 0,
   9570       { TestRound(kConnect, kProxyConnected, OK, &kGet, &kServerChallenge),
   9571         TestRound(kGetAuth, kSuccess, OK)}},
   9572     { kProxy, AUTH_NONE, OK, kSecureServer, AUTH_SYNC, kAuthErr, 2, 0,
   9573       { TestRound(kConnect, kProxyConnected, OK, &kGet, &kServerChallenge),
   9574         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9575     { kProxy, AUTH_NONE, OK, kSecureServer, AUTH_ASYNC, OK, 2, 0,
   9576       { TestRound(kConnect, kProxyConnected, OK, &kGet, &kServerChallenge),
   9577         TestRound(kGetAuth, kSuccess, OK)}},
   9578     { kProxy, AUTH_NONE, OK, kSecureServer, AUTH_ASYNC, kAuthErr, 2, 0,
   9579       { TestRound(kConnect, kProxyConnected, OK, &kGet, &kServerChallenge),
   9580         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9581     // Non-Authenticating HTTPS server through an authenticating proxy.
   9582     { kProxy, AUTH_SYNC, OK, kSecureServer, AUTH_NONE, OK, 2, 1,
   9583       { TestRound(kConnect, kProxyChallenge, OK),
   9584         TestRound(kConnectProxyAuth, kProxyConnected, OK, &kGet, &kSuccess)}},
   9585     { kProxy, AUTH_SYNC, kAuthErr, kSecureServer, AUTH_NONE, OK, 2, kNoSSL,
   9586       { TestRound(kConnect, kProxyChallenge, OK),
   9587         TestRound(kConnectProxyAuth, kFailure, kAuthErr)}},
   9588     { kProxy, AUTH_ASYNC, OK, kSecureServer, AUTH_NONE, OK, 2, 1,
   9589       { TestRound(kConnect, kProxyChallenge, OK),
   9590         TestRound(kConnectProxyAuth, kProxyConnected, OK, &kGet, &kSuccess)}},
   9591     { kProxy, AUTH_ASYNC, kAuthErr, kSecureServer, AUTH_NONE, OK, 2, kNoSSL,
   9592       { TestRound(kConnect, kProxyChallenge, OK),
   9593         TestRound(kConnectProxyAuth, kFailure, kAuthErr)}},
   9594     // Authenticating HTTPS server through an authenticating proxy.
   9595     { kProxy, AUTH_SYNC, OK, kSecureServer, AUTH_SYNC, OK, 3, 1,
   9596       { TestRound(kConnect, kProxyChallenge, OK),
   9597         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9598                   &kGet, &kServerChallenge),
   9599         TestRound(kGetAuth, kSuccess, OK)}},
   9600     { kProxy, AUTH_SYNC, OK, kSecureServer, AUTH_SYNC, kAuthErr, 3, 1,
   9601       { TestRound(kConnect, kProxyChallenge, OK),
   9602         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9603                   &kGet, &kServerChallenge),
   9604         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9605     { kProxy, AUTH_ASYNC, OK, kSecureServer, AUTH_SYNC, OK, 3, 1,
   9606       { TestRound(kConnect, kProxyChallenge, OK),
   9607         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9608                   &kGet, &kServerChallenge),
   9609         TestRound(kGetAuth, kSuccess, OK)}},
   9610     { kProxy, AUTH_ASYNC, OK, kSecureServer, AUTH_SYNC, kAuthErr, 3, 1,
   9611       { TestRound(kConnect, kProxyChallenge, OK),
   9612         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9613                   &kGet, &kServerChallenge),
   9614         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9615     { kProxy, AUTH_SYNC, OK, kSecureServer, AUTH_ASYNC, OK, 3, 1,
   9616       { TestRound(kConnect, kProxyChallenge, OK),
   9617         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9618                   &kGet, &kServerChallenge),
   9619         TestRound(kGetAuth, kSuccess, OK)}},
   9620     { kProxy, AUTH_SYNC, OK, kSecureServer, AUTH_ASYNC, kAuthErr, 3, 1,
   9621       { TestRound(kConnect, kProxyChallenge, OK),
   9622         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9623                   &kGet, &kServerChallenge),
   9624         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9625     { kProxy, AUTH_ASYNC, OK, kSecureServer, AUTH_ASYNC, OK, 3, 1,
   9626       { TestRound(kConnect, kProxyChallenge, OK),
   9627         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9628                   &kGet, &kServerChallenge),
   9629         TestRound(kGetAuth, kSuccess, OK)}},
   9630     { kProxy, AUTH_ASYNC, OK, kSecureServer, AUTH_ASYNC, kAuthErr, 3, 1,
   9631       { TestRound(kConnect, kProxyChallenge, OK),
   9632         TestRound(kConnectProxyAuth, kProxyConnected, OK,
   9633                   &kGet, &kServerChallenge),
   9634         TestRound(kGetAuth, kFailure, kAuthErr)}},
   9635   };
   9636 
   9637   for (size_t i = 0; i < ARRAYSIZE_UNSAFE(test_configs); ++i) {
   9638     HttpAuthHandlerMock::Factory* auth_factory(
   9639         new HttpAuthHandlerMock::Factory());
   9640     session_deps_.http_auth_handler_factory.reset(auth_factory);
   9641     const TestConfig& test_config = test_configs[i];
   9642 
   9643     // Set up authentication handlers as necessary.
   9644     if (test_config.proxy_auth_timing != AUTH_NONE) {
   9645       for (int n = 0; n < 2; n++) {
   9646         HttpAuthHandlerMock* auth_handler(new HttpAuthHandlerMock());
   9647         std::string auth_challenge = "Mock realm=proxy";
   9648         GURL origin(test_config.proxy_url);
   9649         HttpAuthChallengeTokenizer tokenizer(auth_challenge.begin(),
   9650                                              auth_challenge.end());
   9651         auth_handler->InitFromChallenge(&tokenizer, HttpAuth::AUTH_PROXY,
   9652                                         origin, BoundNetLog());
   9653         auth_handler->SetGenerateExpectation(
   9654             test_config.proxy_auth_timing == AUTH_ASYNC,
   9655             test_config.proxy_auth_rv);
   9656         auth_factory->AddMockHandler(auth_handler, HttpAuth::AUTH_PROXY);
   9657       }
   9658     }
   9659     if (test_config.server_auth_timing != AUTH_NONE) {
   9660       HttpAuthHandlerMock* auth_handler(new HttpAuthHandlerMock());
   9661       std::string auth_challenge = "Mock realm=server";
   9662       GURL origin(test_config.server_url);
   9663       HttpAuthChallengeTokenizer tokenizer(auth_challenge.begin(),
   9664                                            auth_challenge.end());
   9665       auth_handler->InitFromChallenge(&tokenizer, HttpAuth::AUTH_SERVER,
   9666                                       origin, BoundNetLog());
   9667       auth_handler->SetGenerateExpectation(
   9668           test_config.server_auth_timing == AUTH_ASYNC,
   9669           test_config.server_auth_rv);
   9670       auth_factory->AddMockHandler(auth_handler, HttpAuth::AUTH_SERVER);
   9671     }
   9672     if (test_config.proxy_url) {
   9673       session_deps_.proxy_service.reset(
   9674           ProxyService::CreateFixed(test_config.proxy_url));
   9675     } else {
   9676       session_deps_.proxy_service.reset(ProxyService::CreateDirect());
   9677     }
   9678 
   9679     HttpRequestInfo request;
   9680     request.method = "GET";
   9681     request.url = GURL(test_config.server_url);
   9682     request.load_flags = 0;
   9683 
   9684     scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   9685     HttpNetworkTransaction trans(DEFAULT_PRIORITY, session);
   9686 
   9687     for (int round = 0; round < test_config.num_auth_rounds; ++round) {
   9688       const TestRound& read_write_round = test_config.rounds[round];
   9689 
   9690       // Set up expected reads and writes.
   9691       MockRead reads[2];
   9692       reads[0] = read_write_round.read;
   9693       size_t length_reads = 1;
   9694       if (read_write_round.extra_read) {
   9695         reads[1] = *read_write_round.extra_read;
   9696         length_reads = 2;
   9697       }
   9698 
   9699       MockWrite writes[2];
   9700       writes[0] = read_write_round.write;
   9701       size_t length_writes = 1;
   9702       if (read_write_round.extra_write) {
   9703         writes[1] = *read_write_round.extra_write;
   9704         length_writes = 2;
   9705       }
   9706       StaticSocketDataProvider data_provider(
   9707           reads, length_reads, writes, length_writes);
   9708       session_deps_.socket_factory->AddSocketDataProvider(&data_provider);
   9709 
   9710       // Add an SSL sequence if necessary.
   9711       SSLSocketDataProvider ssl_socket_data_provider(SYNCHRONOUS, OK);
   9712       if (round >= test_config.first_ssl_round)
   9713         session_deps_.socket_factory->AddSSLSocketDataProvider(
   9714             &ssl_socket_data_provider);
   9715 
   9716       // Start or restart the transaction.
   9717       TestCompletionCallback callback;
   9718       int rv;
   9719       if (round == 0) {
   9720         rv = trans.Start(&request, callback.callback(), BoundNetLog());
   9721       } else {
   9722         rv = trans.RestartWithAuth(
   9723             AuthCredentials(kFoo, kBar), callback.callback());
   9724       }
   9725       if (rv == ERR_IO_PENDING)
   9726         rv = callback.WaitForResult();
   9727 
   9728       // Compare results with expected data.
   9729       EXPECT_EQ(read_write_round.expected_rv, rv);
   9730       const HttpResponseInfo* response = trans.GetResponseInfo();
   9731       if (read_write_round.expected_rv == OK) {
   9732         ASSERT_TRUE(response != NULL);
   9733       } else {
   9734         EXPECT_TRUE(response == NULL);
   9735         EXPECT_EQ(round + 1, test_config.num_auth_rounds);
   9736         continue;
   9737       }
   9738       if (round + 1 < test_config.num_auth_rounds) {
   9739         EXPECT_FALSE(response->auth_challenge.get() == NULL);
   9740       } else {
   9741         EXPECT_TRUE(response->auth_challenge.get() == NULL);
   9742       }
   9743     }
   9744   }
   9745 }
   9746 
   9747 TEST_P(HttpNetworkTransactionTest, MultiRoundAuth) {
   9748   // Do multi-round authentication and make sure it works correctly.
   9749   HttpAuthHandlerMock::Factory* auth_factory(
   9750       new HttpAuthHandlerMock::Factory());
   9751   session_deps_.http_auth_handler_factory.reset(auth_factory);
   9752   session_deps_.proxy_service.reset(ProxyService::CreateDirect());
   9753   session_deps_.host_resolver->rules()->AddRule("www.example.com", "10.0.0.1");
   9754   session_deps_.host_resolver->set_synchronous_mode(true);
   9755 
   9756   HttpAuthHandlerMock* auth_handler(new HttpAuthHandlerMock());
   9757   auth_handler->set_connection_based(true);
   9758   std::string auth_challenge = "Mock realm=server";
   9759   GURL origin("http://www.example.com");
   9760   HttpAuthChallengeTokenizer tokenizer(auth_challenge.begin(),
   9761                                        auth_challenge.end());
   9762   auth_handler->InitFromChallenge(&tokenizer, HttpAuth::AUTH_SERVER,
   9763                                   origin, BoundNetLog());
   9764   auth_factory->AddMockHandler(auth_handler, HttpAuth::AUTH_SERVER);
   9765 
   9766   int rv = OK;
   9767   const HttpResponseInfo* response = NULL;
   9768   HttpRequestInfo request;
   9769   request.method = "GET";
   9770   request.url = origin;
   9771   request.load_flags = 0;
   9772 
   9773   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   9774 
   9775   // Use a TCP Socket Pool with only one connection per group. This is used
   9776   // to validate that the TCP socket is not released to the pool between
   9777   // each round of multi-round authentication.
   9778   HttpNetworkSessionPeer session_peer(session);
   9779   ClientSocketPoolHistograms transport_pool_histograms("SmallTCP");
   9780   TransportClientSocketPool* transport_pool = new TransportClientSocketPool(
   9781       50,  // Max sockets for pool
   9782       1,   // Max sockets per group
   9783       &transport_pool_histograms,
   9784       session_deps_.host_resolver.get(),
   9785       session_deps_.socket_factory.get(),
   9786       session_deps_.net_log);
   9787   scoped_ptr<MockClientSocketPoolManager> mock_pool_manager(
   9788       new MockClientSocketPoolManager);
   9789   mock_pool_manager->SetTransportSocketPool(transport_pool);
   9790   session_peer.SetClientSocketPoolManager(
   9791       mock_pool_manager.PassAs<ClientSocketPoolManager>());
   9792 
   9793   scoped_ptr<HttpTransaction> trans(
   9794       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9795   TestCompletionCallback callback;
   9796 
   9797   const MockWrite kGet(
   9798       "GET / HTTP/1.1\r\n"
   9799       "Host: www.example.com\r\n"
   9800       "Connection: keep-alive\r\n\r\n");
   9801   const MockWrite kGetAuth(
   9802       "GET / HTTP/1.1\r\n"
   9803       "Host: www.example.com\r\n"
   9804       "Connection: keep-alive\r\n"
   9805       "Authorization: auth_token\r\n\r\n");
   9806 
   9807   const MockRead kServerChallenge(
   9808       "HTTP/1.1 401 Unauthorized\r\n"
   9809       "WWW-Authenticate: Mock realm=server\r\n"
   9810       "Content-Type: text/html; charset=iso-8859-1\r\n"
   9811       "Content-Length: 14\r\n\r\n"
   9812       "Unauthorized\r\n");
   9813   const MockRead kSuccess(
   9814       "HTTP/1.1 200 OK\r\n"
   9815       "Content-Type: text/html; charset=iso-8859-1\r\n"
   9816       "Content-Length: 3\r\n\r\n"
   9817       "Yes");
   9818 
   9819   MockWrite writes[] = {
   9820     // First round
   9821     kGet,
   9822     // Second round
   9823     kGetAuth,
   9824     // Third round
   9825     kGetAuth,
   9826     // Fourth round
   9827     kGetAuth,
   9828     // Competing request
   9829     kGet,
   9830   };
   9831   MockRead reads[] = {
   9832     // First round
   9833     kServerChallenge,
   9834     // Second round
   9835     kServerChallenge,
   9836     // Third round
   9837     kServerChallenge,
   9838     // Fourth round
   9839     kSuccess,
   9840     // Competing response
   9841     kSuccess,
   9842   };
   9843   StaticSocketDataProvider data_provider(reads, arraysize(reads),
   9844                                          writes, arraysize(writes));
   9845   session_deps_.socket_factory->AddSocketDataProvider(&data_provider);
   9846 
   9847   const char* const kSocketGroup = "www.example.com:80";
   9848 
   9849   // First round of authentication.
   9850   auth_handler->SetGenerateExpectation(false, OK);
   9851   rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9852   if (rv == ERR_IO_PENDING)
   9853     rv = callback.WaitForResult();
   9854   EXPECT_EQ(OK, rv);
   9855   response = trans->GetResponseInfo();
   9856   ASSERT_TRUE(response != NULL);
   9857   EXPECT_FALSE(response->auth_challenge.get() == NULL);
   9858   EXPECT_EQ(0, transport_pool->IdleSocketCountInGroup(kSocketGroup));
   9859 
   9860   // In between rounds, another request comes in for the same domain.
   9861   // It should not be able to grab the TCP socket that trans has already
   9862   // claimed.
   9863   scoped_ptr<HttpTransaction> trans_compete(
   9864       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9865   TestCompletionCallback callback_compete;
   9866   rv = trans_compete->Start(
   9867       &request, callback_compete.callback(), BoundNetLog());
   9868   EXPECT_EQ(ERR_IO_PENDING, rv);
   9869   // callback_compete.WaitForResult at this point would stall forever,
   9870   // since the HttpNetworkTransaction does not release the request back to
   9871   // the pool until after authentication completes.
   9872 
   9873   // Second round of authentication.
   9874   auth_handler->SetGenerateExpectation(false, OK);
   9875   rv = trans->RestartWithAuth(AuthCredentials(kFoo, kBar), callback.callback());
   9876   if (rv == ERR_IO_PENDING)
   9877     rv = callback.WaitForResult();
   9878   EXPECT_EQ(OK, rv);
   9879   response = trans->GetResponseInfo();
   9880   ASSERT_TRUE(response != NULL);
   9881   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   9882   EXPECT_EQ(0, transport_pool->IdleSocketCountInGroup(kSocketGroup));
   9883 
   9884   // Third round of authentication.
   9885   auth_handler->SetGenerateExpectation(false, OK);
   9886   rv = trans->RestartWithAuth(AuthCredentials(), callback.callback());
   9887   if (rv == ERR_IO_PENDING)
   9888     rv = callback.WaitForResult();
   9889   EXPECT_EQ(OK, rv);
   9890   response = trans->GetResponseInfo();
   9891   ASSERT_TRUE(response != NULL);
   9892   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   9893   EXPECT_EQ(0, transport_pool->IdleSocketCountInGroup(kSocketGroup));
   9894 
   9895   // Fourth round of authentication, which completes successfully.
   9896   auth_handler->SetGenerateExpectation(false, OK);
   9897   rv = trans->RestartWithAuth(AuthCredentials(), callback.callback());
   9898   if (rv == ERR_IO_PENDING)
   9899     rv = callback.WaitForResult();
   9900   EXPECT_EQ(OK, rv);
   9901   response = trans->GetResponseInfo();
   9902   ASSERT_TRUE(response != NULL);
   9903   EXPECT_TRUE(response->auth_challenge.get() == NULL);
   9904   EXPECT_EQ(0, transport_pool->IdleSocketCountInGroup(kSocketGroup));
   9905 
   9906   // Read the body since the fourth round was successful. This will also
   9907   // release the socket back to the pool.
   9908   scoped_refptr<IOBufferWithSize> io_buf(new IOBufferWithSize(50));
   9909   rv = trans->Read(io_buf.get(), io_buf->size(), callback.callback());
   9910   if (rv == ERR_IO_PENDING)
   9911     rv = callback.WaitForResult();
   9912   EXPECT_EQ(3, rv);
   9913   rv = trans->Read(io_buf.get(), io_buf->size(), callback.callback());
   9914   EXPECT_EQ(0, rv);
   9915   // There are still 0 idle sockets, since the trans_compete transaction
   9916   // will be handed it immediately after trans releases it to the group.
   9917   EXPECT_EQ(0, transport_pool->IdleSocketCountInGroup(kSocketGroup));
   9918 
   9919   // The competing request can now finish. Wait for the headers and then
   9920   // read the body.
   9921   rv = callback_compete.WaitForResult();
   9922   EXPECT_EQ(OK, rv);
   9923   rv = trans_compete->Read(io_buf.get(), io_buf->size(), callback.callback());
   9924   if (rv == ERR_IO_PENDING)
   9925     rv = callback.WaitForResult();
   9926   EXPECT_EQ(3, rv);
   9927   rv = trans_compete->Read(io_buf.get(), io_buf->size(), callback.callback());
   9928   EXPECT_EQ(0, rv);
   9929 
   9930   // Finally, the socket is released to the group.
   9931   EXPECT_EQ(1, transport_pool->IdleSocketCountInGroup(kSocketGroup));
   9932 }
   9933 
   9934 // This tests the case that a request is issued via http instead of spdy after
   9935 // npn is negotiated.
   9936 TEST_P(HttpNetworkTransactionTest, NpnWithHttpOverSSL) {
   9937   session_deps_.use_alternate_protocols = true;
   9938   NextProtoVector next_protos;
   9939   next_protos.push_back(kProtoHTTP11);
   9940   session_deps_.next_protos = next_protos;
   9941 
   9942   HttpRequestInfo request;
   9943   request.method = "GET";
   9944   request.url = GURL("https://www.google.com/");
   9945   request.load_flags = 0;
   9946 
   9947   MockWrite data_writes[] = {
   9948     MockWrite("GET / HTTP/1.1\r\n"
   9949               "Host: www.google.com\r\n"
   9950               "Connection: keep-alive\r\n\r\n"),
   9951   };
   9952 
   9953   std::string alternate_protocol_http_header =
   9954       GetAlternateProtocolHttpHeader();
   9955 
   9956   MockRead data_reads[] = {
   9957     MockRead("HTTP/1.1 200 OK\r\n"),
   9958     MockRead(alternate_protocol_http_header.c_str()),
   9959     MockRead("hello world"),
   9960     MockRead(SYNCHRONOUS, OK),
   9961   };
   9962 
   9963   SSLSocketDataProvider ssl(ASYNC, OK);
   9964   ssl.next_proto_status = SSLClientSocket::kNextProtoNegotiated;
   9965   ssl.next_proto = "http/1.1";
   9966   ssl.protocol_negotiated = kProtoHTTP11;
   9967 
   9968   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   9969 
   9970   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   9971                                 data_writes, arraysize(data_writes));
   9972   session_deps_.socket_factory->AddSocketDataProvider(&data);
   9973 
   9974   TestCompletionCallback callback;
   9975 
   9976   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   9977   scoped_ptr<HttpTransaction> trans(
   9978       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   9979 
   9980   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   9981 
   9982   EXPECT_EQ(ERR_IO_PENDING, rv);
   9983   EXPECT_EQ(OK, callback.WaitForResult());
   9984 
   9985   const HttpResponseInfo* response = trans->GetResponseInfo();
   9986   ASSERT_TRUE(response != NULL);
   9987   ASSERT_TRUE(response->headers.get() != NULL);
   9988   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   9989 
   9990   std::string response_data;
   9991   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   9992   EXPECT_EQ("hello world", response_data);
   9993 
   9994   EXPECT_FALSE(response->was_fetched_via_spdy);
   9995   EXPECT_TRUE(response->was_npn_negotiated);
   9996 }
   9997 
   9998 TEST_P(HttpNetworkTransactionTest, SpdyPostNPNServerHangup) {
   9999   // Simulate the SSL handshake completing with an NPN negotiation
   10000   // followed by an immediate server closing of the socket.
   10001   // Fix crash:  http://crbug.com/46369
   10002   session_deps_.use_alternate_protocols = true;
   10003   session_deps_.next_protos = SpdyNextProtos();
   10004 
   10005   HttpRequestInfo request;
   10006   request.method = "GET";
   10007   request.url = GURL("https://www.google.com/");
   10008   request.load_flags = 0;
   10009 
   10010   SSLSocketDataProvider ssl(ASYNC, OK);
   10011   ssl.SetNextProto(GetParam());
   10012   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   10013 
   10014   scoped_ptr<SpdyFrame> req(
   10015       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, true));
   10016   MockWrite spdy_writes[] = { CreateMockWrite(*req) };
   10017 
   10018   MockRead spdy_reads[] = {
   10019     MockRead(SYNCHRONOUS, 0, 0)   // Not async - return 0 immediately.
   10020   };
   10021 
   10022   DelayedSocketData spdy_data(
   10023       0,  // don't wait in this case, immediate hangup.
   10024       spdy_reads, arraysize(spdy_reads),
   10025       spdy_writes, arraysize(spdy_writes));
   10026   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   10027 
   10028   TestCompletionCallback callback;
   10029 
   10030   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10031   scoped_ptr<HttpTransaction> trans(
   10032       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10033 
   10034   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   10035   EXPECT_EQ(ERR_IO_PENDING, rv);
   10036   EXPECT_EQ(ERR_CONNECTION_CLOSED, callback.WaitForResult());
   10037 }
   10038 
   10039 // A subclass of HttpAuthHandlerMock that records the request URL when
   10040 // it gets it. This is needed since the auth handler may get destroyed
   10041 // before we get a chance to query it.
   10042 class UrlRecordingHttpAuthHandlerMock : public HttpAuthHandlerMock {
   10043  public:
   10044   explicit UrlRecordingHttpAuthHandlerMock(GURL* url) : url_(url) {}
   10045 
   10046   virtual ~UrlRecordingHttpAuthHandlerMock() {}
   10047 
   10048  protected:
   10049   virtual int GenerateAuthTokenImpl(const AuthCredentials* credentials,
   10050                                     const HttpRequestInfo* request,
   10051                                     const CompletionCallback& callback,
   10052                                     std::string* auth_token) OVERRIDE {
   10053     *url_ = request->url;
   10054     return HttpAuthHandlerMock::GenerateAuthTokenImpl(
   10055         credentials, request, callback, auth_token);
   10056   }
   10057 
   10058  private:
   10059   GURL* url_;
   10060 };
   10061 
   10062 TEST_P(HttpNetworkTransactionTest, SpdyAlternateProtocolThroughProxy) {
   10063   // This test ensures that the URL passed into the proxy is upgraded
   10064   // to https when doing an Alternate Protocol upgrade.
   10065   session_deps_.use_alternate_protocols = true;
   10066   session_deps_.next_protos = SpdyNextProtos();
   10067 
   10068   session_deps_.proxy_service.reset(
   10069       ProxyService::CreateFixedFromPacResult("PROXY myproxy:70"));
   10070   CapturingNetLog net_log;
   10071   session_deps_.net_log = &net_log;
   10072   GURL request_url;
   10073   {
   10074     HttpAuthHandlerMock::Factory* auth_factory =
   10075         new HttpAuthHandlerMock::Factory();
   10076     UrlRecordingHttpAuthHandlerMock* auth_handler =
   10077         new UrlRecordingHttpAuthHandlerMock(&request_url);
   10078     auth_factory->AddMockHandler(auth_handler, HttpAuth::AUTH_PROXY);
   10079     auth_factory->set_do_init_from_challenge(true);
   10080     session_deps_.http_auth_handler_factory.reset(auth_factory);
   10081   }
   10082 
   10083   HttpRequestInfo request;
   10084   request.method = "GET";
   10085   request.url = GURL("http://www.google.com");
   10086   request.load_flags = 0;
   10087 
   10088   // First round goes unauthenticated through the proxy.
   10089   MockWrite data_writes_1[] = {
   10090     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   10091               "Host: www.google.com\r\n"
   10092               "Proxy-Connection: keep-alive\r\n"
   10093               "\r\n"),
   10094   };
   10095   MockRead data_reads_1[] = {
   10096     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   10097     MockRead("HTTP/1.1 200 OK\r\n"
   10098              "Alternate-Protocol: 443:npn-spdy/2\r\n"
   10099              "Proxy-Connection: close\r\n"
   10100              "\r\n"),
   10101   };
   10102   StaticSocketDataProvider data_1(data_reads_1, arraysize(data_reads_1),
   10103                                   data_writes_1, arraysize(data_writes_1));
   10104 
   10105   // Second round tries to tunnel to www.google.com due to the
   10106   // Alternate-Protocol announcement in the first round. It fails due
   10107   // to a proxy authentication challenge.
   10108   // After the failure, a tunnel is established to www.google.com using
   10109   // Proxy-Authorization headers. There is then a SPDY request round.
   10110   //
   10111   // NOTE: Despite the "Proxy-Connection: Close", these are done on the
   10112   // same MockTCPClientSocket since the underlying HttpNetworkClientSocket
   10113   // does a Disconnect and Connect on the same socket, rather than trying
   10114   // to obtain a new one.
   10115   //
   10116   // NOTE: Originally, the proxy response to the second CONNECT request
   10117   // simply returned another 407 so the unit test could skip the SSL connection
   10118   // establishment and SPDY framing issues. Alas, the
   10119   // retry-http-when-alternate-protocol fails logic kicks in, which was more
   10120   // complicated to set up expectations for than the SPDY session.
   10121 
   10122   scoped_ptr<SpdyFrame> req(
   10123       spdy_util_.ConstructSpdyGet(NULL, 0, false, 1, LOWEST, true));
   10124   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   10125   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   10126 
   10127   MockWrite data_writes_2[] = {
   10128     // First connection attempt without Proxy-Authorization.
   10129     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   10130               "Host: www.google.com\r\n"
   10131               "Proxy-Connection: keep-alive\r\n"
   10132               "\r\n"),
   10133 
   10134     // Second connection attempt with Proxy-Authorization.
   10135     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   10136               "Host: www.google.com\r\n"
   10137               "Proxy-Connection: keep-alive\r\n"
   10138               "Proxy-Authorization: auth_token\r\n"
   10139               "\r\n"),
   10140 
   10141     // SPDY request
   10142     CreateMockWrite(*req),
   10143   };
   10144   const char kRejectConnectResponse[] = ("HTTP/1.1 407 Unauthorized\r\n"
   10145                                          "Proxy-Authenticate: Mock\r\n"
   10146                                          "Proxy-Connection: close\r\n"
   10147                                          "\r\n");
   10148   const char kAcceptConnectResponse[] = "HTTP/1.1 200 Connected\r\n\r\n";
   10149   MockRead data_reads_2[] = {
   10150     // First connection attempt fails
   10151     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ, 1),
   10152     MockRead(ASYNC, kRejectConnectResponse,
   10153              arraysize(kRejectConnectResponse) - 1, 1),
   10154 
   10155     // Second connection attempt passes
   10156     MockRead(ASYNC, kAcceptConnectResponse,
   10157              arraysize(kAcceptConnectResponse) -1, 4),
   10158 
   10159     // SPDY response
   10160     CreateMockRead(*resp.get(), 6),
   10161     CreateMockRead(*data.get(), 6),
   10162     MockRead(ASYNC, 0, 0, 6),
   10163   };
   10164   OrderedSocketData data_2(
   10165       data_reads_2, arraysize(data_reads_2),
   10166       data_writes_2, arraysize(data_writes_2));
   10167 
   10168   SSLSocketDataProvider ssl(ASYNC, OK);
   10169   ssl.SetNextProto(GetParam());
   10170 
   10171   MockConnect never_finishing_connect(SYNCHRONOUS, ERR_IO_PENDING);
   10172   StaticSocketDataProvider hanging_non_alternate_protocol_socket(
   10173       NULL, 0, NULL, 0);
   10174   hanging_non_alternate_protocol_socket.set_connect_data(
   10175       never_finishing_connect);
   10176 
   10177   session_deps_.socket_factory->AddSocketDataProvider(&data_1);
   10178   session_deps_.socket_factory->AddSocketDataProvider(&data_2);
   10179   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   10180   session_deps_.socket_factory->AddSocketDataProvider(
   10181       &hanging_non_alternate_protocol_socket);
   10182   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10183 
   10184   // First round should work and provide the Alternate-Protocol state.
   10185   TestCompletionCallback callback_1;
   10186   scoped_ptr<HttpTransaction> trans_1(
   10187       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10188   int rv = trans_1->Start(&request, callback_1.callback(), BoundNetLog());
   10189   EXPECT_EQ(ERR_IO_PENDING, rv);
   10190   EXPECT_EQ(OK, callback_1.WaitForResult());
   10191 
   10192   // Second round should attempt a tunnel connect and get an auth challenge.
   10193   TestCompletionCallback callback_2;
   10194   scoped_ptr<HttpTransaction> trans_2(
   10195       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10196   rv = trans_2->Start(&request, callback_2.callback(), BoundNetLog());
   10197   EXPECT_EQ(ERR_IO_PENDING, rv);
   10198   EXPECT_EQ(OK, callback_2.WaitForResult());
   10199   const HttpResponseInfo* response = trans_2->GetResponseInfo();
   10200   ASSERT_TRUE(response != NULL);
   10201   ASSERT_FALSE(response->auth_challenge.get() == NULL);
   10202 
   10203   // Restart with auth. Tunnel should work and response received.
   10204   TestCompletionCallback callback_3;
   10205   rv = trans_2->RestartWithAuth(
   10206       AuthCredentials(kFoo, kBar), callback_3.callback());
   10207   EXPECT_EQ(ERR_IO_PENDING, rv);
   10208   EXPECT_EQ(OK, callback_3.WaitForResult());
   10209 
   10210   // After all that work, these two lines (or actually, just the scheme) are
   10211   // what this test is all about. Make sure it happens correctly.
   10212   EXPECT_EQ("https", request_url.scheme());
   10213   EXPECT_EQ("www.google.com", request_url.host());
   10214 
   10215   LoadTimingInfo load_timing_info;
   10216   EXPECT_TRUE(trans_2->GetLoadTimingInfo(&load_timing_info));
   10217   TestLoadTimingNotReusedWithPac(load_timing_info,
   10218                                  CONNECT_TIMING_HAS_SSL_TIMES);
   10219 }
   10220 
   10221 // Test that if we cancel the transaction as the connection is completing, that
   10222 // everything tears down correctly.
   10223 TEST_P(HttpNetworkTransactionTest, SimpleCancel) {
   10224   // Setup everything about the connection to complete synchronously, so that
   10225   // after calling HttpNetworkTransaction::Start, the only thing we're waiting
   10226   // for is the callback from the HttpStreamRequest.
   10227   // Then cancel the transaction.
   10228   // Verify that we don't crash.
   10229   MockConnect mock_connect(SYNCHRONOUS, OK);
   10230   MockRead data_reads[] = {
   10231     MockRead(SYNCHRONOUS, "HTTP/1.0 200 OK\r\n\r\n"),
   10232     MockRead(SYNCHRONOUS, "hello world"),
   10233     MockRead(SYNCHRONOUS, OK),
   10234   };
   10235 
   10236   HttpRequestInfo request;
   10237   request.method = "GET";
   10238   request.url = GURL("http://www.google.com/");
   10239   request.load_flags = 0;
   10240 
   10241   session_deps_.host_resolver->set_synchronous_mode(true);
   10242   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10243   scoped_ptr<HttpTransaction> trans(
   10244       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   10245 
   10246   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   10247   data.set_connect_data(mock_connect);
   10248   session_deps_.socket_factory->AddSocketDataProvider(&data);
   10249 
   10250   TestCompletionCallback callback;
   10251 
   10252   CapturingBoundNetLog log;
   10253   int rv = trans->Start(&request, callback.callback(), log.bound());
   10254   EXPECT_EQ(ERR_IO_PENDING, rv);
   10255   trans.reset();  // Cancel the transaction here.
   10256 
   10257   base::MessageLoop::current()->RunUntilIdle();
   10258 }
   10259 
   10260 // Test that if a transaction is cancelled after receiving the headers, the
   10261 // stream is drained properly and added back to the socket pool.  The main
   10262 // purpose of this test is to make sure that an HttpStreamParser can be read
   10263 // from after the HttpNetworkTransaction and the objects it owns have been
   10264 // deleted.
   10265 // See http://crbug.com/368418
   10266 TEST_P(HttpNetworkTransactionTest, CancelAfterHeaders) {
   10267   MockRead data_reads[] = {
   10268     MockRead(ASYNC, "HTTP/1.1 200 OK\r\n"),
   10269     MockRead(ASYNC, "Content-Length: 2\r\n"),
   10270     MockRead(ASYNC, "Connection: Keep-Alive\r\n\r\n"),
   10271     MockRead(ASYNC, "1"),
   10272     // 2 async reads are necessary to trigger a ReadResponseBody call after the
   10273     // HttpNetworkTransaction has been deleted.
   10274     MockRead(ASYNC, "2"),
   10275     MockRead(SYNCHRONOUS, ERR_IO_PENDING),  // Should never read this.
   10276   };
   10277   StaticSocketDataProvider data(data_reads, arraysize(data_reads), NULL, 0);
   10278   session_deps_.socket_factory->AddSocketDataProvider(&data);
   10279 
   10280   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10281 
   10282   {
   10283     HttpRequestInfo request;
   10284     request.method = "GET";
   10285     request.url = GURL("http://www.google.com/");
   10286     request.load_flags = 0;
   10287 
   10288     HttpNetworkTransaction trans(DEFAULT_PRIORITY, session);
   10289     TestCompletionCallback callback;
   10290 
   10291     int rv = trans.Start(&request, callback.callback(), BoundNetLog());
   10292     EXPECT_EQ(ERR_IO_PENDING, rv);
   10293     callback.WaitForResult();
   10294 
   10295     const HttpResponseInfo* response = trans.GetResponseInfo();
   10296     ASSERT_TRUE(response != NULL);
   10297     EXPECT_TRUE(response->headers.get() != NULL);
   10298     EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   10299 
   10300     // The transaction and HttpRequestInfo are deleted.
   10301   }
   10302 
   10303   // Let the HttpResponseBodyDrainer drain the socket.
   10304   base::MessageLoop::current()->RunUntilIdle();
   10305 
   10306   // Socket should now be idle, waiting to be reused.
   10307   EXPECT_EQ(1, GetIdleSocketCountInTransportSocketPool(session));
   10308 }
   10309 
   10310 // Test a basic GET request through a proxy.
   10311 TEST_P(HttpNetworkTransactionTest, ProxyGet) {
   10312   session_deps_.proxy_service.reset(
   10313       ProxyService::CreateFixedFromPacResult("PROXY myproxy:70"));
   10314   CapturingBoundNetLog log;
   10315   session_deps_.net_log = log.bound().net_log();
   10316   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10317 
   10318   HttpRequestInfo request;
   10319   request.method = "GET";
   10320   request.url = GURL("http://www.google.com/");
   10321 
   10322   MockWrite data_writes1[] = {
   10323     MockWrite("GET http://www.google.com/ HTTP/1.1\r\n"
   10324               "Host: www.google.com\r\n"
   10325               "Proxy-Connection: keep-alive\r\n\r\n"),
   10326   };
   10327 
   10328   MockRead data_reads1[] = {
   10329     MockRead("HTTP/1.1 200 OK\r\n"),
   10330     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   10331     MockRead("Content-Length: 100\r\n\r\n"),
   10332     MockRead(SYNCHRONOUS, OK),
   10333   };
   10334 
   10335   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   10336                                  data_writes1, arraysize(data_writes1));
   10337   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   10338 
   10339   TestCompletionCallback callback1;
   10340 
   10341   scoped_ptr<HttpTransaction> trans(
   10342       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10343 
   10344   int rv = trans->Start(&request, callback1.callback(), log.bound());
   10345   EXPECT_EQ(ERR_IO_PENDING, rv);
   10346 
   10347   rv = callback1.WaitForResult();
   10348   EXPECT_EQ(OK, rv);
   10349 
   10350   const HttpResponseInfo* response = trans->GetResponseInfo();
   10351   ASSERT_TRUE(response != NULL);
   10352 
   10353   EXPECT_TRUE(response->headers->IsKeepAlive());
   10354   EXPECT_EQ(200, response->headers->response_code());
   10355   EXPECT_EQ(100, response->headers->GetContentLength());
   10356   EXPECT_TRUE(response->was_fetched_via_proxy);
   10357   EXPECT_TRUE(
   10358       response->proxy_server.Equals(HostPortPair::FromString("myproxy:70")));
   10359   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   10360 
   10361   LoadTimingInfo load_timing_info;
   10362   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   10363   TestLoadTimingNotReusedWithPac(load_timing_info,
   10364                                  CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
   10365 }
   10366 
   10367 // Test a basic HTTPS GET request through a proxy.
   10368 TEST_P(HttpNetworkTransactionTest, ProxyTunnelGet) {
   10369   session_deps_.proxy_service.reset(
   10370       ProxyService::CreateFixedFromPacResult("PROXY myproxy:70"));
   10371   CapturingBoundNetLog log;
   10372   session_deps_.net_log = log.bound().net_log();
   10373   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10374 
   10375   HttpRequestInfo request;
   10376   request.method = "GET";
   10377   request.url = GURL("https://www.google.com/");
   10378 
   10379   // Since we have proxy, should try to establish tunnel.
   10380   MockWrite data_writes1[] = {
   10381     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   10382               "Host: www.google.com\r\n"
   10383               "Proxy-Connection: keep-alive\r\n\r\n"),
   10384 
   10385     MockWrite("GET / HTTP/1.1\r\n"
   10386               "Host: www.google.com\r\n"
   10387               "Connection: keep-alive\r\n\r\n"),
   10388   };
   10389 
   10390   MockRead data_reads1[] = {
   10391     MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
   10392 
   10393     MockRead("HTTP/1.1 200 OK\r\n"),
   10394     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   10395     MockRead("Content-Length: 100\r\n\r\n"),
   10396     MockRead(SYNCHRONOUS, OK),
   10397   };
   10398 
   10399   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   10400                                  data_writes1, arraysize(data_writes1));
   10401   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   10402   SSLSocketDataProvider ssl(ASYNC, OK);
   10403   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   10404 
   10405   TestCompletionCallback callback1;
   10406 
   10407   scoped_ptr<HttpTransaction> trans(
   10408       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10409 
   10410   int rv = trans->Start(&request, callback1.callback(), log.bound());
   10411   EXPECT_EQ(ERR_IO_PENDING, rv);
   10412 
   10413   rv = callback1.WaitForResult();
   10414   EXPECT_EQ(OK, rv);
   10415   net::CapturingNetLog::CapturedEntryList entries;
   10416   log.GetEntries(&entries);
   10417   size_t pos = ExpectLogContainsSomewhere(
   10418       entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_TUNNEL_HEADERS,
   10419       NetLog::PHASE_NONE);
   10420   ExpectLogContainsSomewhere(
   10421       entries, pos,
   10422       NetLog::TYPE_HTTP_TRANSACTION_READ_TUNNEL_RESPONSE_HEADERS,
   10423       NetLog::PHASE_NONE);
   10424 
   10425   const HttpResponseInfo* response = trans->GetResponseInfo();
   10426   ASSERT_TRUE(response != NULL);
   10427 
   10428   EXPECT_TRUE(response->headers->IsKeepAlive());
   10429   EXPECT_EQ(200, response->headers->response_code());
   10430   EXPECT_EQ(100, response->headers->GetContentLength());
   10431   EXPECT_TRUE(HttpVersion(1, 1) == response->headers->GetHttpVersion());
   10432   EXPECT_TRUE(response->was_fetched_via_proxy);
   10433   EXPECT_TRUE(
   10434       response->proxy_server.Equals(HostPortPair::FromString("myproxy:70")));
   10435 
   10436   LoadTimingInfo load_timing_info;
   10437   EXPECT_TRUE(trans->GetLoadTimingInfo(&load_timing_info));
   10438   TestLoadTimingNotReusedWithPac(load_timing_info,
   10439                                  CONNECT_TIMING_HAS_SSL_TIMES);
   10440 }
   10441 
   10442 // Test a basic HTTPS GET request through a proxy, but the server hangs up
   10443 // while establishing the tunnel.
   10444 TEST_P(HttpNetworkTransactionTest, ProxyTunnelGetHangup) {
   10445   session_deps_.proxy_service.reset(ProxyService::CreateFixed("myproxy:70"));
   10446   CapturingBoundNetLog log;
   10447   session_deps_.net_log = log.bound().net_log();
   10448   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10449 
   10450   HttpRequestInfo request;
   10451   request.method = "GET";
   10452   request.url = GURL("https://www.google.com/");
   10453 
   10454   // Since we have proxy, should try to establish tunnel.
   10455   MockWrite data_writes1[] = {
   10456     MockWrite("CONNECT www.google.com:443 HTTP/1.1\r\n"
   10457               "Host: www.google.com\r\n"
   10458               "Proxy-Connection: keep-alive\r\n\r\n"),
   10459 
   10460     MockWrite("GET / HTTP/1.1\r\n"
   10461               "Host: www.google.com\r\n"
   10462               "Connection: keep-alive\r\n\r\n"),
   10463   };
   10464 
   10465   MockRead data_reads1[] = {
   10466     MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
   10467     MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
   10468     MockRead(ASYNC, 0, 0),  // EOF
   10469   };
   10470 
   10471   StaticSocketDataProvider data1(data_reads1, arraysize(data_reads1),
   10472                                  data_writes1, arraysize(data_writes1));
   10473   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   10474   SSLSocketDataProvider ssl(ASYNC, OK);
   10475   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   10476 
   10477   TestCompletionCallback callback1;
   10478 
   10479   scoped_ptr<HttpTransaction> trans(
   10480       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10481 
   10482   int rv = trans->Start(&request, callback1.callback(), log.bound());
   10483   EXPECT_EQ(ERR_IO_PENDING, rv);
   10484 
   10485   rv = callback1.WaitForResult();
   10486   EXPECT_EQ(ERR_EMPTY_RESPONSE, rv);
   10487   net::CapturingNetLog::CapturedEntryList entries;
   10488   log.GetEntries(&entries);
   10489   size_t pos = ExpectLogContainsSomewhere(
   10490       entries, 0, NetLog::TYPE_HTTP_TRANSACTION_SEND_TUNNEL_HEADERS,
   10491       NetLog::PHASE_NONE);
   10492   ExpectLogContainsSomewhere(
   10493       entries, pos,
   10494       NetLog::TYPE_HTTP_TRANSACTION_READ_TUNNEL_RESPONSE_HEADERS,
   10495       NetLog::PHASE_NONE);
   10496 }
   10497 
   10498 // Test for crbug.com/55424.
   10499 TEST_P(HttpNetworkTransactionTest, PreconnectWithExistingSpdySession) {
   10500   scoped_ptr<SpdyFrame> req(
   10501       spdy_util_.ConstructSpdyGet("https://www.google.com", false, 1, LOWEST));
   10502   MockWrite spdy_writes[] = { CreateMockWrite(*req) };
   10503 
   10504   scoped_ptr<SpdyFrame> resp(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   10505   scoped_ptr<SpdyFrame> data(spdy_util_.ConstructSpdyBodyFrame(1, true));
   10506   MockRead spdy_reads[] = {
   10507     CreateMockRead(*resp),
   10508     CreateMockRead(*data),
   10509     MockRead(ASYNC, 0, 0),
   10510   };
   10511 
   10512   DelayedSocketData spdy_data(
   10513       1,  // wait for one write to finish before reading.
   10514       spdy_reads, arraysize(spdy_reads),
   10515       spdy_writes, arraysize(spdy_writes));
   10516   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   10517 
   10518   SSLSocketDataProvider ssl(ASYNC, OK);
   10519   ssl.SetNextProto(GetParam());
   10520   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   10521 
   10522   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10523 
   10524   // Set up an initial SpdySession in the pool to reuse.
   10525   HostPortPair host_port_pair("www.google.com", 443);
   10526   SpdySessionKey key(host_port_pair, ProxyServer::Direct(),
   10527                      PRIVACY_MODE_DISABLED);
   10528   base::WeakPtr<SpdySession> spdy_session =
   10529       CreateInsecureSpdySession(session, key, BoundNetLog());
   10530 
   10531   HttpRequestInfo request;
   10532   request.method = "GET";
   10533   request.url = GURL("https://www.google.com/");
   10534   request.load_flags = 0;
   10535 
   10536   // This is the important line that marks this as a preconnect.
   10537   request.motivation = HttpRequestInfo::PRECONNECT_MOTIVATED;
   10538 
   10539   scoped_ptr<HttpTransaction> trans(
   10540       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10541 
   10542   TestCompletionCallback callback;
   10543   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   10544   EXPECT_EQ(ERR_IO_PENDING, rv);
   10545   EXPECT_EQ(OK, callback.WaitForResult());
   10546 }
   10547 
   10548 // Given a net error, cause that error to be returned from the first Write()
   10549 // call and verify that the HttpTransaction fails with that error.
   10550 void HttpNetworkTransactionTest::CheckErrorIsPassedBack(
   10551     int error, IoMode mode) {
   10552   net::HttpRequestInfo request_info;
   10553   request_info.url = GURL("https://www.example.com/");
   10554   request_info.method = "GET";
   10555   request_info.load_flags = net::LOAD_NORMAL;
   10556 
   10557   SSLSocketDataProvider ssl_data(mode, OK);
   10558   net::MockWrite data_writes[] = {
   10559     net::MockWrite(mode, error),
   10560   };
   10561   net::StaticSocketDataProvider data(NULL, 0,
   10562                                      data_writes, arraysize(data_writes));
   10563   session_deps_.socket_factory->AddSocketDataProvider(&data);
   10564   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data);
   10565 
   10566   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10567   scoped_ptr<HttpTransaction> trans(
   10568       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10569 
   10570   TestCompletionCallback callback;
   10571   int rv = trans->Start(&request_info, callback.callback(), net::BoundNetLog());
   10572   if (rv == net::ERR_IO_PENDING)
   10573     rv = callback.WaitForResult();
   10574   ASSERT_EQ(error, rv);
   10575 }
   10576 
   10577 TEST_P(HttpNetworkTransactionTest, SSLWriteCertError) {
   10578   // Just check a grab bag of cert errors.
   10579   static const int kErrors[] = {
   10580     ERR_CERT_COMMON_NAME_INVALID,
   10581     ERR_CERT_AUTHORITY_INVALID,
   10582     ERR_CERT_DATE_INVALID,
   10583   };
   10584   for (size_t i = 0; i < arraysize(kErrors); i++) {
   10585     CheckErrorIsPassedBack(kErrors[i], ASYNC);
   10586     CheckErrorIsPassedBack(kErrors[i], SYNCHRONOUS);
   10587   }
   10588 }
   10589 
   10590 // Ensure that a client certificate is removed from the SSL client auth
   10591 // cache when:
   10592 //  1) No proxy is involved.
   10593 //  2) TLS False Start is disabled.
   10594 //  3) The initial TLS handshake requests a client certificate.
   10595 //  4) The client supplies an invalid/unacceptable certificate.
   10596 TEST_P(HttpNetworkTransactionTest,
   10597        ClientAuthCertCache_Direct_NoFalseStart) {
   10598   net::HttpRequestInfo request_info;
   10599   request_info.url = GURL("https://www.example.com/");
   10600   request_info.method = "GET";
   10601   request_info.load_flags = net::LOAD_NORMAL;
   10602 
   10603   scoped_refptr<SSLCertRequestInfo> cert_request(new SSLCertRequestInfo());
   10604   cert_request->host_and_port = HostPortPair("www.example.com", 443);
   10605 
   10606   // [ssl_]data1 contains the data for the first SSL handshake. When a
   10607   // CertificateRequest is received for the first time, the handshake will
   10608   // be aborted to allow the caller to provide a certificate.
   10609   SSLSocketDataProvider ssl_data1(ASYNC, net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED);
   10610   ssl_data1.cert_request_info = cert_request.get();
   10611   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data1);
   10612   net::StaticSocketDataProvider data1(NULL, 0, NULL, 0);
   10613   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   10614 
   10615   // [ssl_]data2 contains the data for the second SSL handshake. When TLS
   10616   // False Start is not being used, the result of the SSL handshake will be
   10617   // returned as part of the SSLClientSocket::Connect() call. This test
   10618   // matches the result of a server sending a handshake_failure alert,
   10619   // rather than a Finished message, because it requires a client
   10620   // certificate and none was supplied.
   10621   SSLSocketDataProvider ssl_data2(ASYNC, net::ERR_SSL_PROTOCOL_ERROR);
   10622   ssl_data2.cert_request_info = cert_request.get();
   10623   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data2);
   10624   net::StaticSocketDataProvider data2(NULL, 0, NULL, 0);
   10625   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   10626 
   10627   // [ssl_]data3 contains the data for the third SSL handshake. When a
   10628   // connection to a server fails during an SSL handshake,
   10629   // HttpNetworkTransaction will attempt to fallback to TLSv1 if the previous
   10630   // connection was attempted with TLSv1.1. This is transparent to the caller
   10631   // of the HttpNetworkTransaction. Because this test failure is due to
   10632   // requiring a client certificate, this fallback handshake should also
   10633   // fail.
   10634   SSLSocketDataProvider ssl_data3(ASYNC, net::ERR_SSL_PROTOCOL_ERROR);
   10635   ssl_data3.cert_request_info = cert_request.get();
   10636   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data3);
   10637   net::StaticSocketDataProvider data3(NULL, 0, NULL, 0);
   10638   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   10639 
   10640   // [ssl_]data4 contains the data for the fourth SSL handshake. When a
   10641   // connection to a server fails during an SSL handshake,
   10642   // HttpNetworkTransaction will attempt to fallback to SSLv3 if the previous
   10643   // connection was attempted with TLSv1. This is transparent to the caller
   10644   // of the HttpNetworkTransaction. Because this test failure is due to
   10645   // requiring a client certificate, this fallback handshake should also
   10646   // fail.
   10647   SSLSocketDataProvider ssl_data4(ASYNC, net::ERR_SSL_PROTOCOL_ERROR);
   10648   ssl_data4.cert_request_info = cert_request.get();
   10649   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data4);
   10650   net::StaticSocketDataProvider data4(NULL, 0, NULL, 0);
   10651   session_deps_.socket_factory->AddSocketDataProvider(&data4);
   10652 
   10653   // Need one more if TLSv1.2 is enabled.
   10654   SSLSocketDataProvider ssl_data5(ASYNC, net::ERR_SSL_PROTOCOL_ERROR);
   10655   ssl_data5.cert_request_info = cert_request.get();
   10656   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data5);
   10657   net::StaticSocketDataProvider data5(NULL, 0, NULL, 0);
   10658   session_deps_.socket_factory->AddSocketDataProvider(&data5);
   10659 
   10660   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10661   scoped_ptr<HttpTransaction> trans(
   10662       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10663 
   10664   // Begin the SSL handshake with the peer. This consumes ssl_data1.
   10665   TestCompletionCallback callback;
   10666   int rv = trans->Start(&request_info, callback.callback(), net::BoundNetLog());
   10667   ASSERT_EQ(net::ERR_IO_PENDING, rv);
   10668 
   10669   // Complete the SSL handshake, which should abort due to requiring a
   10670   // client certificate.
   10671   rv = callback.WaitForResult();
   10672   ASSERT_EQ(net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED, rv);
   10673 
   10674   // Indicate that no certificate should be supplied. From the perspective
   10675   // of SSLClientCertCache, NULL is just as meaningful as a real
   10676   // certificate, so this is the same as supply a
   10677   // legitimate-but-unacceptable certificate.
   10678   rv = trans->RestartWithCertificate(NULL, callback.callback());
   10679   ASSERT_EQ(net::ERR_IO_PENDING, rv);
   10680 
   10681   // Ensure the certificate was added to the client auth cache before
   10682   // allowing the connection to continue restarting.
   10683   scoped_refptr<X509Certificate> client_cert;
   10684   ASSERT_TRUE(session->ssl_client_auth_cache()->Lookup(
   10685       HostPortPair("www.example.com", 443), &client_cert));
   10686   ASSERT_EQ(NULL, client_cert.get());
   10687 
   10688   // Restart the handshake. This will consume ssl_data2, which fails, and
   10689   // then consume ssl_data3 and ssl_data4, both of which should also fail.
   10690   // The result code is checked against what ssl_data4 should return.
   10691   rv = callback.WaitForResult();
   10692   ASSERT_EQ(net::ERR_SSL_PROTOCOL_ERROR, rv);
   10693 
   10694   // Ensure that the client certificate is removed from the cache on a
   10695   // handshake failure.
   10696   ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup(
   10697       HostPortPair("www.example.com", 443), &client_cert));
   10698 }
   10699 
   10700 // Ensure that a client certificate is removed from the SSL client auth
   10701 // cache when:
   10702 //  1) No proxy is involved.
   10703 //  2) TLS False Start is enabled.
   10704 //  3) The initial TLS handshake requests a client certificate.
   10705 //  4) The client supplies an invalid/unacceptable certificate.
   10706 TEST_P(HttpNetworkTransactionTest,
   10707        ClientAuthCertCache_Direct_FalseStart) {
   10708   net::HttpRequestInfo request_info;
   10709   request_info.url = GURL("https://www.example.com/");
   10710   request_info.method = "GET";
   10711   request_info.load_flags = net::LOAD_NORMAL;
   10712 
   10713   scoped_refptr<SSLCertRequestInfo> cert_request(new SSLCertRequestInfo());
   10714   cert_request->host_and_port = HostPortPair("www.example.com", 443);
   10715 
   10716   // When TLS False Start is used, SSLClientSocket::Connect() calls will
   10717   // return successfully after reading up to the peer's Certificate message.
   10718   // This is to allow the caller to call SSLClientSocket::Write(), which can
   10719   // enqueue application data to be sent in the same packet as the
   10720   // ChangeCipherSpec and Finished messages.
   10721   // The actual handshake will be finished when SSLClientSocket::Read() is
   10722   // called, which expects to process the peer's ChangeCipherSpec and
   10723   // Finished messages. If there was an error negotiating with the peer,
   10724   // such as due to the peer requiring a client certificate when none was
   10725   // supplied, the alert sent by the peer won't be processed until Read() is
   10726   // called.
   10727 
   10728   // Like the non-False Start case, when a client certificate is requested by
   10729   // the peer, the handshake is aborted during the Connect() call.
   10730   // [ssl_]data1 represents the initial SSL handshake with the peer.
   10731   SSLSocketDataProvider ssl_data1(ASYNC, net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED);
   10732   ssl_data1.cert_request_info = cert_request.get();
   10733   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data1);
   10734   net::StaticSocketDataProvider data1(NULL, 0, NULL, 0);
   10735   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   10736 
   10737   // When a client certificate is supplied, Connect() will not be aborted
   10738   // when the peer requests the certificate. Instead, the handshake will
   10739   // artificially succeed, allowing the caller to write the HTTP request to
   10740   // the socket. The handshake messages are not processed until Read() is
   10741   // called, which then detects that the handshake was aborted, due to the
   10742   // peer sending a handshake_failure because it requires a client
   10743   // certificate.
   10744   SSLSocketDataProvider ssl_data2(ASYNC, net::OK);
   10745   ssl_data2.cert_request_info = cert_request.get();
   10746   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data2);
   10747   net::MockRead data2_reads[] = {
   10748     net::MockRead(ASYNC /* async */, net::ERR_SSL_PROTOCOL_ERROR),
   10749   };
   10750   net::StaticSocketDataProvider data2(
   10751       data2_reads, arraysize(data2_reads), NULL, 0);
   10752   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   10753 
   10754   // As described in ClientAuthCertCache_Direct_NoFalseStart, [ssl_]data3 is
   10755   // the data for the SSL handshake once the TLSv1.1 connection falls back to
   10756   // TLSv1. It has the same behaviour as [ssl_]data2.
   10757   SSLSocketDataProvider ssl_data3(ASYNC, net::OK);
   10758   ssl_data3.cert_request_info = cert_request.get();
   10759   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data3);
   10760   net::StaticSocketDataProvider data3(
   10761       data2_reads, arraysize(data2_reads), NULL, 0);
   10762   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   10763 
   10764   // [ssl_]data4 is the data for the SSL handshake once the TLSv1 connection
   10765   // falls back to SSLv3. It has the same behaviour as [ssl_]data2.
   10766   SSLSocketDataProvider ssl_data4(ASYNC, net::OK);
   10767   ssl_data4.cert_request_info = cert_request.get();
   10768   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data4);
   10769   net::StaticSocketDataProvider data4(
   10770       data2_reads, arraysize(data2_reads), NULL, 0);
   10771   session_deps_.socket_factory->AddSocketDataProvider(&data4);
   10772 
   10773   // Need one more if TLSv1.2 is enabled.
   10774   SSLSocketDataProvider ssl_data5(ASYNC, net::OK);
   10775   ssl_data5.cert_request_info = cert_request.get();
   10776   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data5);
   10777   net::StaticSocketDataProvider data5(
   10778       data2_reads, arraysize(data2_reads), NULL, 0);
   10779   session_deps_.socket_factory->AddSocketDataProvider(&data5);
   10780 
   10781   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10782   scoped_ptr<HttpTransaction> trans(
   10783       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10784 
   10785   // Begin the initial SSL handshake.
   10786   TestCompletionCallback callback;
   10787   int rv = trans->Start(&request_info, callback.callback(), net::BoundNetLog());
   10788   ASSERT_EQ(net::ERR_IO_PENDING, rv);
   10789 
   10790   // Complete the SSL handshake, which should abort due to requiring a
   10791   // client certificate.
   10792   rv = callback.WaitForResult();
   10793   ASSERT_EQ(net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED, rv);
   10794 
   10795   // Indicate that no certificate should be supplied. From the perspective
   10796   // of SSLClientCertCache, NULL is just as meaningful as a real
   10797   // certificate, so this is the same as supply a
   10798   // legitimate-but-unacceptable certificate.
   10799   rv = trans->RestartWithCertificate(NULL, callback.callback());
   10800   ASSERT_EQ(net::ERR_IO_PENDING, rv);
   10801 
   10802   // Ensure the certificate was added to the client auth cache before
   10803   // allowing the connection to continue restarting.
   10804   scoped_refptr<X509Certificate> client_cert;
   10805   ASSERT_TRUE(session->ssl_client_auth_cache()->Lookup(
   10806       HostPortPair("www.example.com", 443), &client_cert));
   10807   ASSERT_EQ(NULL, client_cert.get());
   10808 
   10809   // Restart the handshake. This will consume ssl_data2, which fails, and
   10810   // then consume ssl_data3 and ssl_data4, both of which should also fail.
   10811   // The result code is checked against what ssl_data4 should return.
   10812   rv = callback.WaitForResult();
   10813   ASSERT_EQ(net::ERR_SSL_PROTOCOL_ERROR, rv);
   10814 
   10815   // Ensure that the client certificate is removed from the cache on a
   10816   // handshake failure.
   10817   ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup(
   10818       HostPortPair("www.example.com", 443), &client_cert));
   10819 }
   10820 
   10821 // Ensure that a client certificate is removed from the SSL client auth
   10822 // cache when:
   10823 //  1) An HTTPS proxy is involved.
   10824 //  3) The HTTPS proxy requests a client certificate.
   10825 //  4) The client supplies an invalid/unacceptable certificate for the
   10826 //     proxy.
   10827 // The test is repeated twice, first for connecting to an HTTPS endpoint,
   10828 // then for connecting to an HTTP endpoint.
   10829 TEST_P(HttpNetworkTransactionTest, ClientAuthCertCache_Proxy_Fail) {
   10830   session_deps_.proxy_service.reset(
   10831       ProxyService::CreateFixed("https://proxy:70"));
   10832   CapturingBoundNetLog log;
   10833   session_deps_.net_log = log.bound().net_log();
   10834 
   10835   scoped_refptr<SSLCertRequestInfo> cert_request(new SSLCertRequestInfo());
   10836   cert_request->host_and_port = HostPortPair("proxy", 70);
   10837 
   10838   // See ClientAuthCertCache_Direct_NoFalseStart for the explanation of
   10839   // [ssl_]data[1-3]. Rather than represending the endpoint
   10840   // (www.example.com:443), they represent failures with the HTTPS proxy
   10841   // (proxy:70).
   10842   SSLSocketDataProvider ssl_data1(ASYNC, net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED);
   10843   ssl_data1.cert_request_info = cert_request.get();
   10844   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data1);
   10845   net::StaticSocketDataProvider data1(NULL, 0, NULL, 0);
   10846   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   10847 
   10848   SSLSocketDataProvider ssl_data2(ASYNC, net::ERR_SSL_PROTOCOL_ERROR);
   10849   ssl_data2.cert_request_info = cert_request.get();
   10850   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data2);
   10851   net::StaticSocketDataProvider data2(NULL, 0, NULL, 0);
   10852   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   10853 
   10854   // TODO(wtc): find out why this unit test doesn't need [ssl_]data3.
   10855 #if 0
   10856   SSLSocketDataProvider ssl_data3(ASYNC, net::ERR_SSL_PROTOCOL_ERROR);
   10857   ssl_data3.cert_request_info = cert_request.get();
   10858   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl_data3);
   10859   net::StaticSocketDataProvider data3(NULL, 0, NULL, 0);
   10860   session_deps_.socket_factory->AddSocketDataProvider(&data3);
   10861 #endif
   10862 
   10863   net::HttpRequestInfo requests[2];
   10864   requests[0].url = GURL("https://www.example.com/");
   10865   requests[0].method = "GET";
   10866   requests[0].load_flags = net::LOAD_NORMAL;
   10867 
   10868   requests[1].url = GURL("http://www.example.com/");
   10869   requests[1].method = "GET";
   10870   requests[1].load_flags = net::LOAD_NORMAL;
   10871 
   10872   for (size_t i = 0; i < arraysize(requests); ++i) {
   10873     session_deps_.socket_factory->ResetNextMockIndexes();
   10874     scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10875     scoped_ptr<HttpNetworkTransaction> trans(
   10876         new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   10877 
   10878     // Begin the SSL handshake with the proxy.
   10879     TestCompletionCallback callback;
   10880     int rv = trans->Start(
   10881         &requests[i], callback.callback(), net::BoundNetLog());
   10882     ASSERT_EQ(net::ERR_IO_PENDING, rv);
   10883 
   10884     // Complete the SSL handshake, which should abort due to requiring a
   10885     // client certificate.
   10886     rv = callback.WaitForResult();
   10887     ASSERT_EQ(net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED, rv);
   10888 
   10889     // Indicate that no certificate should be supplied. From the perspective
   10890     // of SSLClientCertCache, NULL is just as meaningful as a real
   10891     // certificate, so this is the same as supply a
   10892     // legitimate-but-unacceptable certificate.
   10893     rv = trans->RestartWithCertificate(NULL, callback.callback());
   10894     ASSERT_EQ(net::ERR_IO_PENDING, rv);
   10895 
   10896     // Ensure the certificate was added to the client auth cache before
   10897     // allowing the connection to continue restarting.
   10898     scoped_refptr<X509Certificate> client_cert;
   10899     ASSERT_TRUE(session->ssl_client_auth_cache()->Lookup(
   10900         HostPortPair("proxy", 70), &client_cert));
   10901     ASSERT_EQ(NULL, client_cert.get());
   10902     // Ensure the certificate was NOT cached for the endpoint. This only
   10903     // applies to HTTPS requests, but is fine to check for HTTP requests.
   10904     ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup(
   10905         HostPortPair("www.example.com", 443), &client_cert));
   10906 
   10907     // Restart the handshake. This will consume ssl_data2, which fails, and
   10908     // then consume ssl_data3, which should also fail. The result code is
   10909     // checked against what ssl_data3 should return.
   10910     rv = callback.WaitForResult();
   10911     ASSERT_EQ(net::ERR_PROXY_CONNECTION_FAILED, rv);
   10912 
   10913     // Now that the new handshake has failed, ensure that the client
   10914     // certificate was removed from the client auth cache.
   10915     ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup(
   10916         HostPortPair("proxy", 70), &client_cert));
   10917     ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup(
   10918         HostPortPair("www.example.com", 443), &client_cert));
   10919   }
   10920 }
   10921 
   10922 // Unlike TEST/TEST_F, which are macros that expand to further macros,
   10923 // TEST_P is a macro that expands directly to code that stringizes the
   10924 // arguments. As a result, macros passed as parameters (such as prefix
   10925 // or test_case_name) will not be expanded by the preprocessor. To
   10926 // work around this, indirect the macro for TEST_P, so that the
   10927 // pre-processor will expand macros such as MAYBE_test_name before
   10928 // instantiating the test.
   10929 #define WRAPPED_TEST_P(test_case_name, test_name) \
   10930   TEST_P(test_case_name, test_name)
   10931 
   10932 // Times out on Win7 dbg(2) bot. http://crbug.com/124776
   10933 #if defined(OS_WIN)
   10934 #define MAYBE_UseIPConnectionPooling DISABLED_UseIPConnectionPooling
   10935 #else
   10936 #define MAYBE_UseIPConnectionPooling UseIPConnectionPooling
   10937 #endif
   10938 WRAPPED_TEST_P(HttpNetworkTransactionTest, MAYBE_UseIPConnectionPooling) {
   10939   session_deps_.use_alternate_protocols = true;
   10940   session_deps_.next_protos = SpdyNextProtos();
   10941 
   10942   // Set up a special HttpNetworkSession with a MockCachingHostResolver.
   10943   session_deps_.host_resolver.reset(new MockCachingHostResolver());
   10944   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   10945   SpdySessionPoolPeer pool_peer(session->spdy_session_pool());
   10946   pool_peer.DisableDomainAuthenticationVerification();
   10947 
   10948   SSLSocketDataProvider ssl(ASYNC, OK);
   10949   ssl.SetNextProto(GetParam());
   10950   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   10951 
   10952   scoped_ptr<SpdyFrame> host1_req(
   10953       spdy_util_.ConstructSpdyGet("https://www.google.com", false, 1, LOWEST));
   10954   scoped_ptr<SpdyFrame> host2_req(
   10955       spdy_util_.ConstructSpdyGet("https://www.gmail.com", false, 3, LOWEST));
   10956   MockWrite spdy_writes[] = {
   10957     CreateMockWrite(*host1_req, 1),
   10958     CreateMockWrite(*host2_req, 4),
   10959   };
   10960   scoped_ptr<SpdyFrame> host1_resp(
   10961       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   10962   scoped_ptr<SpdyFrame> host1_resp_body(
   10963       spdy_util_.ConstructSpdyBodyFrame(1, true));
   10964   scoped_ptr<SpdyFrame> host2_resp(
   10965       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   10966   scoped_ptr<SpdyFrame> host2_resp_body(
   10967       spdy_util_.ConstructSpdyBodyFrame(3, true));
   10968   MockRead spdy_reads[] = {
   10969     CreateMockRead(*host1_resp, 2),
   10970     CreateMockRead(*host1_resp_body, 3),
   10971     CreateMockRead(*host2_resp, 5),
   10972     CreateMockRead(*host2_resp_body, 6),
   10973     MockRead(ASYNC, 0, 7),
   10974   };
   10975 
   10976   IPAddressNumber ip;
   10977   ASSERT_TRUE(ParseIPLiteralToNumber("127.0.0.1", &ip));
   10978   IPEndPoint peer_addr = IPEndPoint(ip, 443);
   10979   MockConnect connect(ASYNC, OK, peer_addr);
   10980   OrderedSocketData spdy_data(
   10981       connect,
   10982       spdy_reads, arraysize(spdy_reads),
   10983       spdy_writes, arraysize(spdy_writes));
   10984   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   10985 
   10986   TestCompletionCallback callback;
   10987   HttpRequestInfo request1;
   10988   request1.method = "GET";
   10989   request1.url = GURL("https://www.google.com/");
   10990   request1.load_flags = 0;
   10991   HttpNetworkTransaction trans1(DEFAULT_PRIORITY, session.get());
   10992 
   10993   int rv = trans1.Start(&request1, callback.callback(), BoundNetLog());
   10994   EXPECT_EQ(ERR_IO_PENDING, rv);
   10995   EXPECT_EQ(OK, callback.WaitForResult());
   10996 
   10997   const HttpResponseInfo* response = trans1.GetResponseInfo();
   10998   ASSERT_TRUE(response != NULL);
   10999   ASSERT_TRUE(response->headers.get() != NULL);
   11000   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11001 
   11002   std::string response_data;
   11003   ASSERT_EQ(OK, ReadTransaction(&trans1, &response_data));
   11004   EXPECT_EQ("hello!", response_data);
   11005 
   11006   // Preload www.gmail.com into HostCache.
   11007   HostPortPair host_port("www.gmail.com", 443);
   11008   HostResolver::RequestInfo resolve_info(host_port);
   11009   AddressList ignored;
   11010   rv = session_deps_.host_resolver->Resolve(resolve_info,
   11011                                             DEFAULT_PRIORITY,
   11012                                             &ignored,
   11013                                             callback.callback(),
   11014                                             NULL,
   11015                                             BoundNetLog());
   11016   EXPECT_EQ(ERR_IO_PENDING, rv);
   11017   rv = callback.WaitForResult();
   11018   EXPECT_EQ(OK, rv);
   11019 
   11020   HttpRequestInfo request2;
   11021   request2.method = "GET";
   11022   request2.url = GURL("https://www.gmail.com/");
   11023   request2.load_flags = 0;
   11024   HttpNetworkTransaction trans2(DEFAULT_PRIORITY, session.get());
   11025 
   11026   rv = trans2.Start(&request2, callback.callback(), BoundNetLog());
   11027   EXPECT_EQ(ERR_IO_PENDING, rv);
   11028   EXPECT_EQ(OK, callback.WaitForResult());
   11029 
   11030   response = trans2.GetResponseInfo();
   11031   ASSERT_TRUE(response != NULL);
   11032   ASSERT_TRUE(response->headers.get() != NULL);
   11033   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11034   EXPECT_TRUE(response->was_fetched_via_spdy);
   11035   EXPECT_TRUE(response->was_npn_negotiated);
   11036   ASSERT_EQ(OK, ReadTransaction(&trans2, &response_data));
   11037   EXPECT_EQ("hello!", response_data);
   11038 }
   11039 #undef MAYBE_UseIPConnectionPooling
   11040 
   11041 TEST_P(HttpNetworkTransactionTest, UseIPConnectionPoolingAfterResolution) {
   11042   session_deps_.use_alternate_protocols = true;
   11043   session_deps_.next_protos = SpdyNextProtos();
   11044 
   11045   // Set up a special HttpNetworkSession with a MockCachingHostResolver.
   11046   session_deps_.host_resolver.reset(new MockCachingHostResolver());
   11047   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11048   SpdySessionPoolPeer pool_peer(session->spdy_session_pool());
   11049   pool_peer.DisableDomainAuthenticationVerification();
   11050 
   11051   SSLSocketDataProvider ssl(ASYNC, OK);
   11052   ssl.SetNextProto(GetParam());
   11053   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   11054 
   11055   scoped_ptr<SpdyFrame> host1_req(
   11056       spdy_util_.ConstructSpdyGet("https://www.google.com", false, 1, LOWEST));
   11057   scoped_ptr<SpdyFrame> host2_req(
   11058       spdy_util_.ConstructSpdyGet("https://www.gmail.com", false, 3, LOWEST));
   11059   MockWrite spdy_writes[] = {
   11060     CreateMockWrite(*host1_req, 1),
   11061     CreateMockWrite(*host2_req, 4),
   11062   };
   11063   scoped_ptr<SpdyFrame> host1_resp(
   11064       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11065   scoped_ptr<SpdyFrame> host1_resp_body(
   11066       spdy_util_.ConstructSpdyBodyFrame(1, true));
   11067   scoped_ptr<SpdyFrame> host2_resp(
   11068       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   11069   scoped_ptr<SpdyFrame> host2_resp_body(
   11070       spdy_util_.ConstructSpdyBodyFrame(3, true));
   11071   MockRead spdy_reads[] = {
   11072     CreateMockRead(*host1_resp, 2),
   11073     CreateMockRead(*host1_resp_body, 3),
   11074     CreateMockRead(*host2_resp, 5),
   11075     CreateMockRead(*host2_resp_body, 6),
   11076     MockRead(ASYNC, 0, 7),
   11077   };
   11078 
   11079   IPAddressNumber ip;
   11080   ASSERT_TRUE(ParseIPLiteralToNumber("127.0.0.1", &ip));
   11081   IPEndPoint peer_addr = IPEndPoint(ip, 443);
   11082   MockConnect connect(ASYNC, OK, peer_addr);
   11083   OrderedSocketData spdy_data(
   11084       connect,
   11085       spdy_reads, arraysize(spdy_reads),
   11086       spdy_writes, arraysize(spdy_writes));
   11087   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   11088 
   11089   TestCompletionCallback callback;
   11090   HttpRequestInfo request1;
   11091   request1.method = "GET";
   11092   request1.url = GURL("https://www.google.com/");
   11093   request1.load_flags = 0;
   11094   HttpNetworkTransaction trans1(DEFAULT_PRIORITY, session.get());
   11095 
   11096   int rv = trans1.Start(&request1, callback.callback(), BoundNetLog());
   11097   EXPECT_EQ(ERR_IO_PENDING, rv);
   11098   EXPECT_EQ(OK, callback.WaitForResult());
   11099 
   11100   const HttpResponseInfo* response = trans1.GetResponseInfo();
   11101   ASSERT_TRUE(response != NULL);
   11102   ASSERT_TRUE(response->headers.get() != NULL);
   11103   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11104 
   11105   std::string response_data;
   11106   ASSERT_EQ(OK, ReadTransaction(&trans1, &response_data));
   11107   EXPECT_EQ("hello!", response_data);
   11108 
   11109   HttpRequestInfo request2;
   11110   request2.method = "GET";
   11111   request2.url = GURL("https://www.gmail.com/");
   11112   request2.load_flags = 0;
   11113   HttpNetworkTransaction trans2(DEFAULT_PRIORITY, session.get());
   11114 
   11115   rv = trans2.Start(&request2, callback.callback(), BoundNetLog());
   11116   EXPECT_EQ(ERR_IO_PENDING, rv);
   11117   EXPECT_EQ(OK, callback.WaitForResult());
   11118 
   11119   response = trans2.GetResponseInfo();
   11120   ASSERT_TRUE(response != NULL);
   11121   ASSERT_TRUE(response->headers.get() != NULL);
   11122   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11123   EXPECT_TRUE(response->was_fetched_via_spdy);
   11124   EXPECT_TRUE(response->was_npn_negotiated);
   11125   ASSERT_EQ(OK, ReadTransaction(&trans2, &response_data));
   11126   EXPECT_EQ("hello!", response_data);
   11127 }
   11128 
   11129 class OneTimeCachingHostResolver : public net::HostResolver {
   11130  public:
   11131   explicit OneTimeCachingHostResolver(const HostPortPair& host_port)
   11132       : host_port_(host_port) {}
   11133   virtual ~OneTimeCachingHostResolver() {}
   11134 
   11135   RuleBasedHostResolverProc* rules() { return host_resolver_.rules(); }
   11136 
   11137   // HostResolver methods:
   11138   virtual int Resolve(const RequestInfo& info,
   11139                       RequestPriority priority,
   11140                       AddressList* addresses,
   11141                       const CompletionCallback& callback,
   11142                       RequestHandle* out_req,
   11143                       const BoundNetLog& net_log) OVERRIDE {
   11144     return host_resolver_.Resolve(
   11145         info, priority, addresses, callback, out_req, net_log);
   11146   }
   11147 
   11148   virtual int ResolveFromCache(const RequestInfo& info,
   11149                                AddressList* addresses,
   11150                                const BoundNetLog& net_log) OVERRIDE {
   11151     int rv = host_resolver_.ResolveFromCache(info, addresses, net_log);
   11152     if (rv == OK && info.host_port_pair().Equals(host_port_))
   11153       host_resolver_.GetHostCache()->clear();
   11154     return rv;
   11155   }
   11156 
   11157   virtual void CancelRequest(RequestHandle req) OVERRIDE {
   11158     host_resolver_.CancelRequest(req);
   11159   }
   11160 
   11161   MockCachingHostResolver* GetMockHostResolver() {
   11162     return &host_resolver_;
   11163   }
   11164 
   11165  private:
   11166   MockCachingHostResolver host_resolver_;
   11167   const HostPortPair host_port_;
   11168 };
   11169 
   11170 // Times out on Win7 dbg(2) bot. http://crbug.com/124776
   11171 #if defined(OS_WIN)
   11172 #define MAYBE_UseIPConnectionPoolingWithHostCacheExpiration \
   11173     DISABLED_UseIPConnectionPoolingWithHostCacheExpiration
   11174 #else
   11175 #define MAYBE_UseIPConnectionPoolingWithHostCacheExpiration \
   11176     UseIPConnectionPoolingWithHostCacheExpiration
   11177 #endif
   11178 WRAPPED_TEST_P(HttpNetworkTransactionTest,
   11179                MAYBE_UseIPConnectionPoolingWithHostCacheExpiration) {
   11180 // Times out on Win7 dbg(2) bot. http://crbug.com/124776 . (MAYBE_
   11181 // prefix doesn't work with parametrized tests).
   11182 #if defined(OS_WIN)
   11183   return;
   11184 #else
   11185   session_deps_.use_alternate_protocols = true;
   11186   session_deps_.next_protos = SpdyNextProtos();
   11187 
   11188   // Set up a special HttpNetworkSession with a OneTimeCachingHostResolver.
   11189   OneTimeCachingHostResolver host_resolver(HostPortPair("www.gmail.com", 443));
   11190   HttpNetworkSession::Params params =
   11191       SpdySessionDependencies::CreateSessionParams(&session_deps_);
   11192   params.host_resolver = &host_resolver;
   11193   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11194   SpdySessionPoolPeer pool_peer(session->spdy_session_pool());
   11195   pool_peer.DisableDomainAuthenticationVerification();
   11196 
   11197   SSLSocketDataProvider ssl(ASYNC, OK);
   11198   ssl.SetNextProto(GetParam());
   11199   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   11200 
   11201   scoped_ptr<SpdyFrame> host1_req(
   11202       spdy_util_.ConstructSpdyGet("https://www.google.com", false, 1, LOWEST));
   11203   scoped_ptr<SpdyFrame> host2_req(
   11204       spdy_util_.ConstructSpdyGet("https://www.gmail.com", false, 3, LOWEST));
   11205   MockWrite spdy_writes[] = {
   11206     CreateMockWrite(*host1_req, 1),
   11207     CreateMockWrite(*host2_req, 4),
   11208   };
   11209   scoped_ptr<SpdyFrame> host1_resp(
   11210       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11211   scoped_ptr<SpdyFrame> host1_resp_body(
   11212       spdy_util_.ConstructSpdyBodyFrame(1, true));
   11213   scoped_ptr<SpdyFrame> host2_resp(
   11214       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   11215   scoped_ptr<SpdyFrame> host2_resp_body(
   11216       spdy_util_.ConstructSpdyBodyFrame(3, true));
   11217   MockRead spdy_reads[] = {
   11218     CreateMockRead(*host1_resp, 2),
   11219     CreateMockRead(*host1_resp_body, 3),
   11220     CreateMockRead(*host2_resp, 5),
   11221     CreateMockRead(*host2_resp_body, 6),
   11222     MockRead(ASYNC, 0, 7),
   11223   };
   11224 
   11225   IPAddressNumber ip;
   11226   ASSERT_TRUE(ParseIPLiteralToNumber("127.0.0.1", &ip));
   11227   IPEndPoint peer_addr = IPEndPoint(ip, 443);
   11228   MockConnect connect(ASYNC, OK, peer_addr);
   11229   OrderedSocketData spdy_data(
   11230       connect,
   11231       spdy_reads, arraysize(spdy_reads),
   11232       spdy_writes, arraysize(spdy_writes));
   11233   session_deps_.socket_factory->AddSocketDataProvider(&spdy_data);
   11234 
   11235   TestCompletionCallback callback;
   11236   HttpRequestInfo request1;
   11237   request1.method = "GET";
   11238   request1.url = GURL("https://www.google.com/");
   11239   request1.load_flags = 0;
   11240   HttpNetworkTransaction trans1(DEFAULT_PRIORITY, session.get());
   11241 
   11242   int rv = trans1.Start(&request1, callback.callback(), BoundNetLog());
   11243   EXPECT_EQ(ERR_IO_PENDING, rv);
   11244   EXPECT_EQ(OK, callback.WaitForResult());
   11245 
   11246   const HttpResponseInfo* response = trans1.GetResponseInfo();
   11247   ASSERT_TRUE(response != NULL);
   11248   ASSERT_TRUE(response->headers.get() != NULL);
   11249   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11250 
   11251   std::string response_data;
   11252   ASSERT_EQ(OK, ReadTransaction(&trans1, &response_data));
   11253   EXPECT_EQ("hello!", response_data);
   11254 
   11255   // Preload cache entries into HostCache.
   11256   HostResolver::RequestInfo resolve_info(HostPortPair("www.gmail.com", 443));
   11257   AddressList ignored;
   11258   rv = host_resolver.Resolve(resolve_info,
   11259                              DEFAULT_PRIORITY,
   11260                              &ignored,
   11261                              callback.callback(),
   11262                              NULL,
   11263                              BoundNetLog());
   11264   EXPECT_EQ(ERR_IO_PENDING, rv);
   11265   rv = callback.WaitForResult();
   11266   EXPECT_EQ(OK, rv);
   11267 
   11268   HttpRequestInfo request2;
   11269   request2.method = "GET";
   11270   request2.url = GURL("https://www.gmail.com/");
   11271   request2.load_flags = 0;
   11272   HttpNetworkTransaction trans2(DEFAULT_PRIORITY, session.get());
   11273 
   11274   rv = trans2.Start(&request2, callback.callback(), BoundNetLog());
   11275   EXPECT_EQ(ERR_IO_PENDING, rv);
   11276   EXPECT_EQ(OK, callback.WaitForResult());
   11277 
   11278   response = trans2.GetResponseInfo();
   11279   ASSERT_TRUE(response != NULL);
   11280   ASSERT_TRUE(response->headers.get() != NULL);
   11281   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11282   EXPECT_TRUE(response->was_fetched_via_spdy);
   11283   EXPECT_TRUE(response->was_npn_negotiated);
   11284   ASSERT_EQ(OK, ReadTransaction(&trans2, &response_data));
   11285   EXPECT_EQ("hello!", response_data);
   11286 #endif
   11287 }
   11288 #undef MAYBE_UseIPConnectionPoolingWithHostCacheExpiration
   11289 
   11290 TEST_P(HttpNetworkTransactionTest, DoNotUseSpdySessionForHttp) {
   11291   const std::string https_url = "https://www.google.com/";
   11292   const std::string http_url = "http://www.google.com:443/";
   11293 
   11294   // SPDY GET for HTTPS URL
   11295   scoped_ptr<SpdyFrame> req1(
   11296       spdy_util_.ConstructSpdyGet(https_url.c_str(), false, 1, LOWEST));
   11297 
   11298   MockWrite writes1[] = {
   11299     CreateMockWrite(*req1, 0),
   11300   };
   11301 
   11302   scoped_ptr<SpdyFrame> resp1(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11303   scoped_ptr<SpdyFrame> body1(spdy_util_.ConstructSpdyBodyFrame(1, true));
   11304   MockRead reads1[] = {
   11305     CreateMockRead(*resp1, 1),
   11306     CreateMockRead(*body1, 2),
   11307     MockRead(ASYNC, ERR_IO_PENDING, 3)
   11308   };
   11309 
   11310   DelayedSocketData data1(
   11311       1, reads1, arraysize(reads1),
   11312       writes1, arraysize(writes1));
   11313   MockConnect connect_data1(ASYNC, OK);
   11314   data1.set_connect_data(connect_data1);
   11315 
   11316   // HTTP GET for the HTTP URL
   11317   MockWrite writes2[] = {
   11318     MockWrite(ASYNC, 4,
   11319               "GET / HTTP/1.1\r\n"
   11320               "Host: www.google.com:443\r\n"
   11321               "Connection: keep-alive\r\n\r\n"),
   11322   };
   11323 
   11324   MockRead reads2[] = {
   11325     MockRead(ASYNC, 5, "HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\n"),
   11326     MockRead(ASYNC, 6, "hello"),
   11327     MockRead(ASYNC, 7, OK),
   11328   };
   11329 
   11330   DelayedSocketData data2(
   11331       1, reads2, arraysize(reads2),
   11332       writes2, arraysize(writes2));
   11333 
   11334   SSLSocketDataProvider ssl(ASYNC, OK);
   11335   ssl.SetNextProto(GetParam());
   11336   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   11337   session_deps_.socket_factory->AddSocketDataProvider(&data1);
   11338   session_deps_.socket_factory->AddSocketDataProvider(&data2);
   11339 
   11340   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11341 
   11342   // Start the first transaction to set up the SpdySession
   11343   HttpRequestInfo request1;
   11344   request1.method = "GET";
   11345   request1.url = GURL(https_url);
   11346   request1.load_flags = 0;
   11347   HttpNetworkTransaction trans1(LOWEST, session.get());
   11348   TestCompletionCallback callback1;
   11349   EXPECT_EQ(ERR_IO_PENDING,
   11350             trans1.Start(&request1, callback1.callback(), BoundNetLog()));
   11351   base::MessageLoop::current()->RunUntilIdle();
   11352 
   11353   EXPECT_EQ(OK, callback1.WaitForResult());
   11354   EXPECT_TRUE(trans1.GetResponseInfo()->was_fetched_via_spdy);
   11355 
   11356   // Now, start the HTTP request
   11357   HttpRequestInfo request2;
   11358   request2.method = "GET";
   11359   request2.url = GURL(http_url);
   11360   request2.load_flags = 0;
   11361   HttpNetworkTransaction trans2(MEDIUM, session.get());
   11362   TestCompletionCallback callback2;
   11363   EXPECT_EQ(ERR_IO_PENDING,
   11364             trans2.Start(&request2, callback2.callback(), BoundNetLog()));
   11365   base::MessageLoop::current()->RunUntilIdle();
   11366 
   11367   EXPECT_EQ(OK, callback2.WaitForResult());
   11368   EXPECT_FALSE(trans2.GetResponseInfo()->was_fetched_via_spdy);
   11369 }
   11370 
   11371 TEST_P(HttpNetworkTransactionTest, DoNotUseSpdySessionForHttpOverTunnel) {
   11372   const std::string https_url = "https://www.google.com/";
   11373   const std::string http_url = "http://www.google.com:443/";
   11374 
   11375   // SPDY GET for HTTPS URL (through CONNECT tunnel)
   11376   scoped_ptr<SpdyFrame> connect(spdy_util_.ConstructSpdyConnect(NULL, 0, 1,
   11377                                                                 LOWEST));
   11378   scoped_ptr<SpdyFrame> req1(
   11379       spdy_util_.ConstructSpdyGet(https_url.c_str(), false, 1, LOWEST));
   11380   scoped_ptr<SpdyFrame> wrapped_req1(
   11381       spdy_util_.ConstructWrappedSpdyFrame(req1, 1));
   11382 
   11383   // SPDY GET for HTTP URL (through the proxy, but not the tunnel).
   11384   SpdySynStreamIR req2_ir(3);
   11385   spdy_util_.SetPriority(MEDIUM, &req2_ir);
   11386   req2_ir.set_fin(true);
   11387   req2_ir.SetHeader(spdy_util_.GetMethodKey(), "GET");
   11388   req2_ir.SetHeader(spdy_util_.GetPathKey(),
   11389                     spdy_util_.is_spdy2() ? http_url.c_str() : "/");
   11390   req2_ir.SetHeader(spdy_util_.GetHostKey(), "www.google.com:443");
   11391   req2_ir.SetHeader(spdy_util_.GetSchemeKey(), "http");
   11392   spdy_util_.MaybeAddVersionHeader(&req2_ir);
   11393   scoped_ptr<SpdyFrame> req2(
   11394       spdy_util_.CreateFramer(false)->SerializeFrame(req2_ir));
   11395 
   11396   MockWrite writes1[] = {
   11397     CreateMockWrite(*connect, 0),
   11398     CreateMockWrite(*wrapped_req1, 2),
   11399     CreateMockWrite(*req2, 5),
   11400   };
   11401 
   11402   scoped_ptr<SpdyFrame> conn_resp(
   11403       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11404   scoped_ptr<SpdyFrame> resp1(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11405   scoped_ptr<SpdyFrame> body1(spdy_util_.ConstructSpdyBodyFrame(1, true));
   11406   scoped_ptr<SpdyFrame> wrapped_resp1(
   11407       spdy_util_.ConstructWrappedSpdyFrame(resp1, 1));
   11408   scoped_ptr<SpdyFrame> wrapped_body1(
   11409       spdy_util_.ConstructWrappedSpdyFrame(body1, 1));
   11410   scoped_ptr<SpdyFrame> resp2(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   11411   scoped_ptr<SpdyFrame> body2(spdy_util_.ConstructSpdyBodyFrame(3, true));
   11412   MockRead reads1[] = {
   11413     CreateMockRead(*conn_resp, 1),
   11414     CreateMockRead(*wrapped_resp1, 3),
   11415     CreateMockRead(*wrapped_body1, 4),
   11416     CreateMockRead(*resp2, 6),
   11417     CreateMockRead(*body2, 7),
   11418     MockRead(ASYNC, ERR_IO_PENDING, 8)
   11419   };
   11420 
   11421   DeterministicSocketData data1(reads1, arraysize(reads1),
   11422                                 writes1, arraysize(writes1));
   11423   MockConnect connect_data1(ASYNC, OK);
   11424   data1.set_connect_data(connect_data1);
   11425 
   11426   session_deps_.proxy_service.reset(
   11427       ProxyService::CreateFixedFromPacResult("HTTPS proxy:70"));
   11428   CapturingNetLog log;
   11429   session_deps_.net_log = &log;
   11430   SSLSocketDataProvider ssl1(ASYNC, OK);  // to the proxy
   11431   ssl1.SetNextProto(GetParam());
   11432   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl1);
   11433   SSLSocketDataProvider ssl2(ASYNC, OK);  // to the server
   11434   ssl2.SetNextProto(GetParam());
   11435   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl2);
   11436   session_deps_.deterministic_socket_factory->AddSocketDataProvider(&data1);
   11437 
   11438   scoped_refptr<HttpNetworkSession> session(
   11439       SpdySessionDependencies::SpdyCreateSessionDeterministic(&session_deps_));
   11440 
   11441   // Start the first transaction to set up the SpdySession
   11442   HttpRequestInfo request1;
   11443   request1.method = "GET";
   11444   request1.url = GURL(https_url);
   11445   request1.load_flags = 0;
   11446   HttpNetworkTransaction trans1(LOWEST, session.get());
   11447   TestCompletionCallback callback1;
   11448   EXPECT_EQ(ERR_IO_PENDING,
   11449             trans1.Start(&request1, callback1.callback(), BoundNetLog()));
   11450   base::MessageLoop::current()->RunUntilIdle();
   11451   data1.RunFor(4);
   11452 
   11453   EXPECT_EQ(OK, callback1.WaitForResult());
   11454   EXPECT_TRUE(trans1.GetResponseInfo()->was_fetched_via_spdy);
   11455 
   11456   LoadTimingInfo load_timing_info1;
   11457   EXPECT_TRUE(trans1.GetLoadTimingInfo(&load_timing_info1));
   11458   TestLoadTimingNotReusedWithPac(load_timing_info1,
   11459                                  CONNECT_TIMING_HAS_SSL_TIMES);
   11460 
   11461   // Now, start the HTTP request
   11462   HttpRequestInfo request2;
   11463   request2.method = "GET";
   11464   request2.url = GURL(http_url);
   11465   request2.load_flags = 0;
   11466   HttpNetworkTransaction trans2(MEDIUM, session.get());
   11467   TestCompletionCallback callback2;
   11468   EXPECT_EQ(ERR_IO_PENDING,
   11469             trans2.Start(&request2, callback2.callback(), BoundNetLog()));
   11470   base::MessageLoop::current()->RunUntilIdle();
   11471   data1.RunFor(3);
   11472 
   11473   EXPECT_EQ(OK, callback2.WaitForResult());
   11474   EXPECT_TRUE(trans2.GetResponseInfo()->was_fetched_via_spdy);
   11475 
   11476   LoadTimingInfo load_timing_info2;
   11477   EXPECT_TRUE(trans2.GetLoadTimingInfo(&load_timing_info2));
   11478   // The established SPDY sessions is considered reused by the HTTP request.
   11479   TestLoadTimingReusedWithPac(load_timing_info2);
   11480   // HTTP requests over a SPDY session should have a different connection
   11481   // socket_log_id than requests over a tunnel.
   11482   EXPECT_NE(load_timing_info1.socket_log_id, load_timing_info2.socket_log_id);
   11483 }
   11484 
   11485 TEST_P(HttpNetworkTransactionTest, UseSpdySessionForHttpWhenForced) {
   11486   session_deps_.force_spdy_always = true;
   11487   const std::string https_url = "https://www.google.com/";
   11488   const std::string http_url = "http://www.google.com:443/";
   11489 
   11490   // SPDY GET for HTTPS URL
   11491   scoped_ptr<SpdyFrame> req1(
   11492       spdy_util_.ConstructSpdyGet(https_url.c_str(), false, 1, LOWEST));
   11493   // SPDY GET for the HTTP URL
   11494   scoped_ptr<SpdyFrame> req2(
   11495       spdy_util_.ConstructSpdyGet(http_url.c_str(), false, 3, MEDIUM));
   11496 
   11497   MockWrite writes[] = {
   11498     CreateMockWrite(*req1, 1),
   11499     CreateMockWrite(*req2, 4),
   11500   };
   11501 
   11502   scoped_ptr<SpdyFrame> resp1(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11503   scoped_ptr<SpdyFrame> body1(spdy_util_.ConstructSpdyBodyFrame(1, true));
   11504   scoped_ptr<SpdyFrame> resp2(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 3));
   11505   scoped_ptr<SpdyFrame> body2(spdy_util_.ConstructSpdyBodyFrame(3, true));
   11506   MockRead reads[] = {
   11507     CreateMockRead(*resp1, 2),
   11508     CreateMockRead(*body1, 3),
   11509     CreateMockRead(*resp2, 5),
   11510     CreateMockRead(*body2, 6),
   11511     MockRead(ASYNC, ERR_IO_PENDING, 7)
   11512   };
   11513 
   11514   OrderedSocketData data(reads, arraysize(reads),
   11515                          writes, arraysize(writes));
   11516 
   11517   SSLSocketDataProvider ssl(ASYNC, OK);
   11518   ssl.SetNextProto(GetParam());
   11519   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   11520   session_deps_.socket_factory->AddSocketDataProvider(&data);
   11521 
   11522   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11523 
   11524   // Start the first transaction to set up the SpdySession
   11525   HttpRequestInfo request1;
   11526   request1.method = "GET";
   11527   request1.url = GURL(https_url);
   11528   request1.load_flags = 0;
   11529   HttpNetworkTransaction trans1(LOWEST, session.get());
   11530   TestCompletionCallback callback1;
   11531   EXPECT_EQ(ERR_IO_PENDING,
   11532             trans1.Start(&request1, callback1.callback(), BoundNetLog()));
   11533   base::MessageLoop::current()->RunUntilIdle();
   11534 
   11535   EXPECT_EQ(OK, callback1.WaitForResult());
   11536   EXPECT_TRUE(trans1.GetResponseInfo()->was_fetched_via_spdy);
   11537 
   11538   // Now, start the HTTP request
   11539   HttpRequestInfo request2;
   11540   request2.method = "GET";
   11541   request2.url = GURL(http_url);
   11542   request2.load_flags = 0;
   11543   HttpNetworkTransaction trans2(MEDIUM, session.get());
   11544   TestCompletionCallback callback2;
   11545   EXPECT_EQ(ERR_IO_PENDING,
   11546             trans2.Start(&request2, callback2.callback(), BoundNetLog()));
   11547   base::MessageLoop::current()->RunUntilIdle();
   11548 
   11549   EXPECT_EQ(OK, callback2.WaitForResult());
   11550   EXPECT_TRUE(trans2.GetResponseInfo()->was_fetched_via_spdy);
   11551 }
   11552 
   11553 // Test that in the case where we have a SPDY session to a SPDY proxy
   11554 // that we do not pool other origins that resolve to the same IP when
   11555 // the certificate does not match the new origin.
   11556 // http://crbug.com/134690
   11557 TEST_P(HttpNetworkTransactionTest, DoNotUseSpdySessionIfCertDoesNotMatch) {
   11558   const std::string url1 = "http://www.google.com/";
   11559   const std::string url2 = "https://mail.google.com/";
   11560   const std::string ip_addr = "1.2.3.4";
   11561 
   11562   // SPDY GET for HTTP URL (through SPDY proxy)
   11563   scoped_ptr<SpdyHeaderBlock> headers(
   11564       spdy_util_.ConstructGetHeaderBlockForProxy("http://www.google.com/"));
   11565   scoped_ptr<SpdyFrame> req1(spdy_util_.ConstructSpdyControlFrame(
   11566       headers.Pass(), false, 1, LOWEST, SYN_STREAM, CONTROL_FLAG_FIN, 0));
   11567 
   11568   MockWrite writes1[] = {
   11569     CreateMockWrite(*req1, 0),
   11570   };
   11571 
   11572   scoped_ptr<SpdyFrame> resp1(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11573   scoped_ptr<SpdyFrame> body1(spdy_util_.ConstructSpdyBodyFrame(1, true));
   11574   MockRead reads1[] = {
   11575     CreateMockRead(*resp1, 1),
   11576     CreateMockRead(*body1, 2),
   11577     MockRead(ASYNC, OK, 3) // EOF
   11578   };
   11579 
   11580   scoped_ptr<DeterministicSocketData> data1(
   11581       new DeterministicSocketData(reads1, arraysize(reads1),
   11582                                   writes1, arraysize(writes1)));
   11583   IPAddressNumber ip;
   11584   ASSERT_TRUE(ParseIPLiteralToNumber(ip_addr, &ip));
   11585   IPEndPoint peer_addr = IPEndPoint(ip, 443);
   11586   MockConnect connect_data1(ASYNC, OK, peer_addr);
   11587   data1->set_connect_data(connect_data1);
   11588 
   11589   // SPDY GET for HTTPS URL (direct)
   11590   scoped_ptr<SpdyFrame> req2(
   11591       spdy_util_.ConstructSpdyGet(url2.c_str(), false, 1, MEDIUM));
   11592 
   11593   MockWrite writes2[] = {
   11594     CreateMockWrite(*req2, 0),
   11595   };
   11596 
   11597   scoped_ptr<SpdyFrame> resp2(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11598   scoped_ptr<SpdyFrame> body2(spdy_util_.ConstructSpdyBodyFrame(1, true));
   11599   MockRead reads2[] = {
   11600     CreateMockRead(*resp2, 1),
   11601     CreateMockRead(*body2, 2),
   11602     MockRead(ASYNC, OK, 3) // EOF
   11603   };
   11604 
   11605   scoped_ptr<DeterministicSocketData> data2(
   11606       new DeterministicSocketData(reads2, arraysize(reads2),
   11607                                   writes2, arraysize(writes2)));
   11608   MockConnect connect_data2(ASYNC, OK);
   11609   data2->set_connect_data(connect_data2);
   11610 
   11611   // Set up a proxy config that sends HTTP requests to a proxy, and
   11612   // all others direct.
   11613   ProxyConfig proxy_config;
   11614   proxy_config.proxy_rules().ParseFromString("http=https://proxy:443");
   11615   CapturingProxyResolver* capturing_proxy_resolver =
   11616       new CapturingProxyResolver();
   11617   session_deps_.proxy_service.reset(new ProxyService(
   11618       new ProxyConfigServiceFixed(proxy_config), capturing_proxy_resolver,
   11619       NULL));
   11620 
   11621   // Load a valid cert.  Note, that this does not need to
   11622   // be valid for proxy because the MockSSLClientSocket does
   11623   // not actually verify it.  But SpdySession will use this
   11624   // to see if it is valid for the new origin
   11625   base::FilePath certs_dir = GetTestCertsDirectory();
   11626   scoped_refptr<X509Certificate> server_cert(
   11627       ImportCertFromFile(certs_dir, "ok_cert.pem"));
   11628   ASSERT_NE(static_cast<X509Certificate*>(NULL), server_cert);
   11629 
   11630   SSLSocketDataProvider ssl1(ASYNC, OK);  // to the proxy
   11631   ssl1.SetNextProto(GetParam());
   11632   ssl1.cert = server_cert;
   11633   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl1);
   11634   session_deps_.deterministic_socket_factory->AddSocketDataProvider(
   11635       data1.get());
   11636 
   11637   SSLSocketDataProvider ssl2(ASYNC, OK);  // to the server
   11638   ssl2.SetNextProto(GetParam());
   11639   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl2);
   11640   session_deps_.deterministic_socket_factory->AddSocketDataProvider(
   11641       data2.get());
   11642 
   11643   session_deps_.host_resolver.reset(new MockCachingHostResolver());
   11644   session_deps_.host_resolver->rules()->AddRule("mail.google.com", ip_addr);
   11645   session_deps_.host_resolver->rules()->AddRule("proxy", ip_addr);
   11646 
   11647   scoped_refptr<HttpNetworkSession> session(
   11648       SpdySessionDependencies::SpdyCreateSessionDeterministic(&session_deps_));
   11649 
   11650   // Start the first transaction to set up the SpdySession
   11651   HttpRequestInfo request1;
   11652   request1.method = "GET";
   11653   request1.url = GURL(url1);
   11654   request1.load_flags = 0;
   11655   HttpNetworkTransaction trans1(LOWEST, session.get());
   11656   TestCompletionCallback callback1;
   11657   ASSERT_EQ(ERR_IO_PENDING,
   11658             trans1.Start(&request1, callback1.callback(), BoundNetLog()));
   11659   data1->RunFor(3);
   11660 
   11661   ASSERT_TRUE(callback1.have_result());
   11662   EXPECT_EQ(OK, callback1.WaitForResult());
   11663   EXPECT_TRUE(trans1.GetResponseInfo()->was_fetched_via_spdy);
   11664 
   11665   // Now, start the HTTP request
   11666   HttpRequestInfo request2;
   11667   request2.method = "GET";
   11668   request2.url = GURL(url2);
   11669   request2.load_flags = 0;
   11670   HttpNetworkTransaction trans2(MEDIUM, session.get());
   11671   TestCompletionCallback callback2;
   11672   EXPECT_EQ(ERR_IO_PENDING,
   11673             trans2.Start(&request2, callback2.callback(), BoundNetLog()));
   11674   base::MessageLoop::current()->RunUntilIdle();
   11675   data2->RunFor(3);
   11676 
   11677   ASSERT_TRUE(callback2.have_result());
   11678   EXPECT_EQ(OK, callback2.WaitForResult());
   11679   EXPECT_TRUE(trans2.GetResponseInfo()->was_fetched_via_spdy);
   11680 }
   11681 
   11682 // Test to verify that a failed socket read (due to an ERR_CONNECTION_CLOSED
   11683 // error) in SPDY session, removes the socket from pool and closes the SPDY
   11684 // session. Verify that new url's from the same HttpNetworkSession (and a new
   11685 // SpdySession) do work. http://crbug.com/224701
   11686 TEST_P(HttpNetworkTransactionTest, ErrorSocketNotConnected) {
   11687   const std::string https_url = "https://www.google.com/";
   11688 
   11689   MockRead reads1[] = {
   11690     MockRead(SYNCHRONOUS, ERR_CONNECTION_CLOSED, 0)
   11691   };
   11692 
   11693   scoped_ptr<DeterministicSocketData> data1(
   11694       new DeterministicSocketData(reads1, arraysize(reads1), NULL, 0));
   11695   data1->SetStop(1);
   11696 
   11697   scoped_ptr<SpdyFrame> req2(
   11698       spdy_util_.ConstructSpdyGet(https_url.c_str(), false, 1, MEDIUM));
   11699   MockWrite writes2[] = {
   11700     CreateMockWrite(*req2, 0),
   11701   };
   11702 
   11703   scoped_ptr<SpdyFrame> resp2(spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11704   scoped_ptr<SpdyFrame> body2(spdy_util_.ConstructSpdyBodyFrame(1, true));
   11705   MockRead reads2[] = {
   11706     CreateMockRead(*resp2, 1),
   11707     CreateMockRead(*body2, 2),
   11708     MockRead(ASYNC, OK, 3)  // EOF
   11709   };
   11710 
   11711   scoped_ptr<DeterministicSocketData> data2(
   11712       new DeterministicSocketData(reads2, arraysize(reads2),
   11713                                   writes2, arraysize(writes2)));
   11714 
   11715   SSLSocketDataProvider ssl1(ASYNC, OK);
   11716   ssl1.SetNextProto(GetParam());
   11717   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl1);
   11718   session_deps_.deterministic_socket_factory->AddSocketDataProvider(
   11719       data1.get());
   11720 
   11721   SSLSocketDataProvider ssl2(ASYNC, OK);
   11722   ssl2.SetNextProto(GetParam());
   11723   session_deps_.deterministic_socket_factory->AddSSLSocketDataProvider(&ssl2);
   11724   session_deps_.deterministic_socket_factory->AddSocketDataProvider(
   11725       data2.get());
   11726 
   11727   scoped_refptr<HttpNetworkSession> session(
   11728       SpdySessionDependencies::SpdyCreateSessionDeterministic(&session_deps_));
   11729 
   11730   // Start the first transaction to set up the SpdySession and verify that
   11731   // connection was closed.
   11732   HttpRequestInfo request1;
   11733   request1.method = "GET";
   11734   request1.url = GURL(https_url);
   11735   request1.load_flags = 0;
   11736   HttpNetworkTransaction trans1(MEDIUM, session.get());
   11737   TestCompletionCallback callback1;
   11738   EXPECT_EQ(ERR_IO_PENDING,
   11739             trans1.Start(&request1, callback1.callback(), BoundNetLog()));
   11740   base::MessageLoop::current()->RunUntilIdle();
   11741   EXPECT_EQ(ERR_CONNECTION_CLOSED, callback1.WaitForResult());
   11742 
   11743   // Now, start the second request and make sure it succeeds.
   11744   HttpRequestInfo request2;
   11745   request2.method = "GET";
   11746   request2.url = GURL(https_url);
   11747   request2.load_flags = 0;
   11748   HttpNetworkTransaction trans2(MEDIUM, session.get());
   11749   TestCompletionCallback callback2;
   11750   EXPECT_EQ(ERR_IO_PENDING,
   11751             trans2.Start(&request2, callback2.callback(), BoundNetLog()));
   11752   base::MessageLoop::current()->RunUntilIdle();
   11753   data2->RunFor(3);
   11754 
   11755   ASSERT_TRUE(callback2.have_result());
   11756   EXPECT_EQ(OK, callback2.WaitForResult());
   11757   EXPECT_TRUE(trans2.GetResponseInfo()->was_fetched_via_spdy);
   11758 }
   11759 
   11760 TEST_P(HttpNetworkTransactionTest, CloseIdleSpdySessionToOpenNewOne) {
   11761   session_deps_.next_protos = SpdyNextProtos();
   11762   ClientSocketPoolManager::set_max_sockets_per_group(
   11763       HttpNetworkSession::NORMAL_SOCKET_POOL, 1);
   11764   ClientSocketPoolManager::set_max_sockets_per_pool(
   11765       HttpNetworkSession::NORMAL_SOCKET_POOL, 1);
   11766 
   11767   // Use two different hosts with different IPs so they don't get pooled.
   11768   session_deps_.host_resolver->rules()->AddRule("www.a.com", "10.0.0.1");
   11769   session_deps_.host_resolver->rules()->AddRule("www.b.com", "10.0.0.2");
   11770   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11771 
   11772   SSLSocketDataProvider ssl1(ASYNC, OK);
   11773   ssl1.SetNextProto(GetParam());
   11774   SSLSocketDataProvider ssl2(ASYNC, OK);
   11775   ssl2.SetNextProto(GetParam());
   11776   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl1);
   11777   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl2);
   11778 
   11779   scoped_ptr<SpdyFrame> host1_req(spdy_util_.ConstructSpdyGet(
   11780       "https://www.a.com", false, 1, DEFAULT_PRIORITY));
   11781   MockWrite spdy1_writes[] = {
   11782     CreateMockWrite(*host1_req, 1),
   11783   };
   11784   scoped_ptr<SpdyFrame> host1_resp(
   11785       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11786   scoped_ptr<SpdyFrame> host1_resp_body(
   11787       spdy_util_.ConstructSpdyBodyFrame(1, true));
   11788   MockRead spdy1_reads[] = {
   11789     CreateMockRead(*host1_resp, 2),
   11790     CreateMockRead(*host1_resp_body, 3),
   11791     MockRead(ASYNC, ERR_IO_PENDING, 4),
   11792   };
   11793 
   11794   scoped_ptr<OrderedSocketData> spdy1_data(
   11795       new OrderedSocketData(
   11796           spdy1_reads, arraysize(spdy1_reads),
   11797           spdy1_writes, arraysize(spdy1_writes)));
   11798   session_deps_.socket_factory->AddSocketDataProvider(spdy1_data.get());
   11799 
   11800   scoped_ptr<SpdyFrame> host2_req(spdy_util_.ConstructSpdyGet(
   11801       "https://www.b.com", false, 1, DEFAULT_PRIORITY));
   11802   MockWrite spdy2_writes[] = {
   11803     CreateMockWrite(*host2_req, 1),
   11804   };
   11805   scoped_ptr<SpdyFrame> host2_resp(
   11806       spdy_util_.ConstructSpdyGetSynReply(NULL, 0, 1));
   11807   scoped_ptr<SpdyFrame> host2_resp_body(
   11808       spdy_util_.ConstructSpdyBodyFrame(1, true));
   11809   MockRead spdy2_reads[] = {
   11810     CreateMockRead(*host2_resp, 2),
   11811     CreateMockRead(*host2_resp_body, 3),
   11812     MockRead(ASYNC, ERR_IO_PENDING, 4),
   11813   };
   11814 
   11815   scoped_ptr<OrderedSocketData> spdy2_data(
   11816       new OrderedSocketData(
   11817           spdy2_reads, arraysize(spdy2_reads),
   11818           spdy2_writes, arraysize(spdy2_writes)));
   11819   session_deps_.socket_factory->AddSocketDataProvider(spdy2_data.get());
   11820 
   11821   MockWrite http_write[] = {
   11822     MockWrite("GET / HTTP/1.1\r\n"
   11823               "Host: www.a.com\r\n"
   11824               "Connection: keep-alive\r\n\r\n"),
   11825   };
   11826 
   11827   MockRead http_read[] = {
   11828     MockRead("HTTP/1.1 200 OK\r\n"),
   11829     MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"),
   11830     MockRead("Content-Length: 6\r\n\r\n"),
   11831     MockRead("hello!"),
   11832   };
   11833   StaticSocketDataProvider http_data(http_read, arraysize(http_read),
   11834                                      http_write, arraysize(http_write));
   11835   session_deps_.socket_factory->AddSocketDataProvider(&http_data);
   11836 
   11837   HostPortPair host_port_pair_a("www.a.com", 443);
   11838   SpdySessionKey spdy_session_key_a(
   11839       host_port_pair_a, ProxyServer::Direct(), PRIVACY_MODE_DISABLED);
   11840   EXPECT_FALSE(
   11841       HasSpdySession(session->spdy_session_pool(), spdy_session_key_a));
   11842 
   11843   TestCompletionCallback callback;
   11844   HttpRequestInfo request1;
   11845   request1.method = "GET";
   11846   request1.url = GURL("https://www.a.com/");
   11847   request1.load_flags = 0;
   11848   scoped_ptr<HttpNetworkTransaction> trans(
   11849       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   11850 
   11851   int rv = trans->Start(&request1, callback.callback(), BoundNetLog());
   11852   EXPECT_EQ(ERR_IO_PENDING, rv);
   11853   EXPECT_EQ(OK, callback.WaitForResult());
   11854 
   11855   const HttpResponseInfo* response = trans->GetResponseInfo();
   11856   ASSERT_TRUE(response != NULL);
   11857   ASSERT_TRUE(response->headers.get() != NULL);
   11858   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11859   EXPECT_TRUE(response->was_fetched_via_spdy);
   11860   EXPECT_TRUE(response->was_npn_negotiated);
   11861 
   11862   std::string response_data;
   11863   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   11864   EXPECT_EQ("hello!", response_data);
   11865   trans.reset();
   11866   EXPECT_TRUE(
   11867       HasSpdySession(session->spdy_session_pool(), spdy_session_key_a));
   11868 
   11869   HostPortPair host_port_pair_b("www.b.com", 443);
   11870   SpdySessionKey spdy_session_key_b(
   11871       host_port_pair_b, ProxyServer::Direct(), PRIVACY_MODE_DISABLED);
   11872   EXPECT_FALSE(
   11873       HasSpdySession(session->spdy_session_pool(), spdy_session_key_b));
   11874   HttpRequestInfo request2;
   11875   request2.method = "GET";
   11876   request2.url = GURL("https://www.b.com/");
   11877   request2.load_flags = 0;
   11878   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   11879 
   11880   rv = trans->Start(&request2, callback.callback(), BoundNetLog());
   11881   EXPECT_EQ(ERR_IO_PENDING, rv);
   11882   EXPECT_EQ(OK, callback.WaitForResult());
   11883 
   11884   response = trans->GetResponseInfo();
   11885   ASSERT_TRUE(response != NULL);
   11886   ASSERT_TRUE(response->headers.get() != NULL);
   11887   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11888   EXPECT_TRUE(response->was_fetched_via_spdy);
   11889   EXPECT_TRUE(response->was_npn_negotiated);
   11890   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   11891   EXPECT_EQ("hello!", response_data);
   11892   EXPECT_FALSE(
   11893       HasSpdySession(session->spdy_session_pool(), spdy_session_key_a));
   11894   EXPECT_TRUE(
   11895       HasSpdySession(session->spdy_session_pool(), spdy_session_key_b));
   11896 
   11897   HostPortPair host_port_pair_a1("www.a.com", 80);
   11898   SpdySessionKey spdy_session_key_a1(
   11899       host_port_pair_a1, ProxyServer::Direct(), PRIVACY_MODE_DISABLED);
   11900   EXPECT_FALSE(
   11901       HasSpdySession(session->spdy_session_pool(), spdy_session_key_a1));
   11902   HttpRequestInfo request3;
   11903   request3.method = "GET";
   11904   request3.url = GURL("http://www.a.com/");
   11905   request3.load_flags = 0;
   11906   trans.reset(new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   11907 
   11908   rv = trans->Start(&request3, callback.callback(), BoundNetLog());
   11909   EXPECT_EQ(ERR_IO_PENDING, rv);
   11910   EXPECT_EQ(OK, callback.WaitForResult());
   11911 
   11912   response = trans->GetResponseInfo();
   11913   ASSERT_TRUE(response != NULL);
   11914   ASSERT_TRUE(response->headers.get() != NULL);
   11915   EXPECT_EQ("HTTP/1.1 200 OK", response->headers->GetStatusLine());
   11916   EXPECT_FALSE(response->was_fetched_via_spdy);
   11917   EXPECT_FALSE(response->was_npn_negotiated);
   11918   ASSERT_EQ(OK, ReadTransaction(trans.get(), &response_data));
   11919   EXPECT_EQ("hello!", response_data);
   11920   EXPECT_FALSE(
   11921       HasSpdySession(session->spdy_session_pool(), spdy_session_key_a));
   11922   EXPECT_FALSE(
   11923       HasSpdySession(session->spdy_session_pool(), spdy_session_key_b));
   11924 }
   11925 
   11926 TEST_P(HttpNetworkTransactionTest, HttpSyncConnectError) {
   11927   HttpRequestInfo request;
   11928   request.method = "GET";
   11929   request.url = GURL("http://www.google.com/");
   11930   request.load_flags = 0;
   11931 
   11932   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11933   scoped_ptr<HttpTransaction> trans(
   11934       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   11935 
   11936   MockConnect mock_connect(SYNCHRONOUS, ERR_CONNECTION_REFUSED);
   11937   StaticSocketDataProvider data;
   11938   data.set_connect_data(mock_connect);
   11939   session_deps_.socket_factory->AddSocketDataProvider(&data);
   11940 
   11941   TestCompletionCallback callback;
   11942 
   11943   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   11944   EXPECT_EQ(ERR_IO_PENDING, rv);
   11945 
   11946   rv = callback.WaitForResult();
   11947   EXPECT_EQ(ERR_CONNECTION_REFUSED, rv);
   11948 
   11949   EXPECT_EQ(NULL, trans->GetResponseInfo());
   11950 
   11951   // We don't care whether this succeeds or fails, but it shouldn't crash.
   11952   HttpRequestHeaders request_headers;
   11953   trans->GetFullRequestHeaders(&request_headers);
   11954 }
   11955 
   11956 TEST_P(HttpNetworkTransactionTest, HttpAsyncConnectError) {
   11957   HttpRequestInfo request;
   11958   request.method = "GET";
   11959   request.url = GURL("http://www.google.com/");
   11960   request.load_flags = 0;
   11961 
   11962   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11963   scoped_ptr<HttpTransaction> trans(
   11964       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   11965 
   11966   MockConnect mock_connect(ASYNC, ERR_CONNECTION_REFUSED);
   11967   StaticSocketDataProvider data;
   11968   data.set_connect_data(mock_connect);
   11969   session_deps_.socket_factory->AddSocketDataProvider(&data);
   11970 
   11971   TestCompletionCallback callback;
   11972 
   11973   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   11974   EXPECT_EQ(ERR_IO_PENDING, rv);
   11975 
   11976   rv = callback.WaitForResult();
   11977   EXPECT_EQ(ERR_CONNECTION_REFUSED, rv);
   11978 
   11979   EXPECT_EQ(NULL, trans->GetResponseInfo());
   11980 
   11981   // We don't care whether this succeeds or fails, but it shouldn't crash.
   11982   HttpRequestHeaders request_headers;
   11983   trans->GetFullRequestHeaders(&request_headers);
   11984 }
   11985 
   11986 TEST_P(HttpNetworkTransactionTest, HttpSyncWriteError) {
   11987   HttpRequestInfo request;
   11988   request.method = "GET";
   11989   request.url = GURL("http://www.google.com/");
   11990   request.load_flags = 0;
   11991 
   11992   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   11993   scoped_ptr<HttpTransaction> trans(
   11994       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   11995 
   11996   MockWrite data_writes[] = {
   11997     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   11998   };
   11999   MockRead data_reads[] = {
   12000     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   12001   };
   12002 
   12003   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   12004                                 data_writes, arraysize(data_writes));
   12005   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12006 
   12007   TestCompletionCallback callback;
   12008 
   12009   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12010   EXPECT_EQ(ERR_IO_PENDING, rv);
   12011 
   12012   rv = callback.WaitForResult();
   12013   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   12014 
   12015   EXPECT_EQ(NULL, trans->GetResponseInfo());
   12016 
   12017   HttpRequestHeaders request_headers;
   12018   EXPECT_TRUE(trans->GetFullRequestHeaders(&request_headers));
   12019   EXPECT_TRUE(request_headers.HasHeader("Host"));
   12020 }
   12021 
   12022 TEST_P(HttpNetworkTransactionTest, HttpAsyncWriteError) {
   12023   HttpRequestInfo request;
   12024   request.method = "GET";
   12025   request.url = GURL("http://www.google.com/");
   12026   request.load_flags = 0;
   12027 
   12028   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12029   scoped_ptr<HttpTransaction> trans(
   12030       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12031 
   12032   MockWrite data_writes[] = {
   12033     MockWrite(ASYNC, ERR_CONNECTION_RESET),
   12034   };
   12035   MockRead data_reads[] = {
   12036     MockRead(SYNCHRONOUS, ERR_UNEXPECTED),  // Should not be reached.
   12037   };
   12038 
   12039   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   12040                                 data_writes, arraysize(data_writes));
   12041   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12042 
   12043   TestCompletionCallback callback;
   12044 
   12045   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12046   EXPECT_EQ(ERR_IO_PENDING, rv);
   12047 
   12048   rv = callback.WaitForResult();
   12049   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   12050 
   12051   EXPECT_EQ(NULL, trans->GetResponseInfo());
   12052 
   12053   HttpRequestHeaders request_headers;
   12054   EXPECT_TRUE(trans->GetFullRequestHeaders(&request_headers));
   12055   EXPECT_TRUE(request_headers.HasHeader("Host"));
   12056 }
   12057 
   12058 TEST_P(HttpNetworkTransactionTest, HttpSyncReadError) {
   12059   HttpRequestInfo request;
   12060   request.method = "GET";
   12061   request.url = GURL("http://www.google.com/");
   12062   request.load_flags = 0;
   12063 
   12064   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12065   scoped_ptr<HttpTransaction> trans(
   12066       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12067 
   12068   MockWrite data_writes[] = {
   12069     MockWrite("GET / HTTP/1.1\r\n"
   12070               "Host: www.google.com\r\n"
   12071               "Connection: keep-alive\r\n\r\n"),
   12072   };
   12073   MockRead data_reads[] = {
   12074     MockRead(SYNCHRONOUS, ERR_CONNECTION_RESET),
   12075   };
   12076 
   12077   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   12078                                 data_writes, arraysize(data_writes));
   12079   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12080 
   12081   TestCompletionCallback callback;
   12082 
   12083   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12084   EXPECT_EQ(ERR_IO_PENDING, rv);
   12085 
   12086   rv = callback.WaitForResult();
   12087   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   12088 
   12089   EXPECT_EQ(NULL, trans->GetResponseInfo());
   12090 
   12091   HttpRequestHeaders request_headers;
   12092   EXPECT_TRUE(trans->GetFullRequestHeaders(&request_headers));
   12093   EXPECT_TRUE(request_headers.HasHeader("Host"));
   12094 }
   12095 
   12096 TEST_P(HttpNetworkTransactionTest, HttpAsyncReadError) {
   12097   HttpRequestInfo request;
   12098   request.method = "GET";
   12099   request.url = GURL("http://www.google.com/");
   12100   request.load_flags = 0;
   12101 
   12102   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12103   scoped_ptr<HttpTransaction> trans(
   12104       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12105 
   12106   MockWrite data_writes[] = {
   12107     MockWrite("GET / HTTP/1.1\r\n"
   12108               "Host: www.google.com\r\n"
   12109               "Connection: keep-alive\r\n\r\n"),
   12110   };
   12111   MockRead data_reads[] = {
   12112     MockRead(ASYNC, ERR_CONNECTION_RESET),
   12113   };
   12114 
   12115   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   12116                                 data_writes, arraysize(data_writes));
   12117   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12118 
   12119   TestCompletionCallback callback;
   12120 
   12121   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12122   EXPECT_EQ(ERR_IO_PENDING, rv);
   12123 
   12124   rv = callback.WaitForResult();
   12125   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   12126 
   12127   EXPECT_EQ(NULL, trans->GetResponseInfo());
   12128 
   12129   HttpRequestHeaders request_headers;
   12130   EXPECT_TRUE(trans->GetFullRequestHeaders(&request_headers));
   12131   EXPECT_TRUE(request_headers.HasHeader("Host"));
   12132 }
   12133 
   12134 TEST_P(HttpNetworkTransactionTest, GetFullRequestHeadersIncludesExtraHeader) {
   12135   HttpRequestInfo request;
   12136   request.method = "GET";
   12137   request.url = GURL("http://www.google.com/");
   12138   request.load_flags = 0;
   12139   request.extra_headers.SetHeader("X-Foo", "bar");
   12140 
   12141   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12142   scoped_ptr<HttpTransaction> trans(
   12143       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12144 
   12145   MockWrite data_writes[] = {
   12146     MockWrite("GET / HTTP/1.1\r\n"
   12147               "Host: www.google.com\r\n"
   12148               "Connection: keep-alive\r\n"
   12149               "X-Foo: bar\r\n\r\n"),
   12150   };
   12151   MockRead data_reads[] = {
   12152     MockRead("HTTP/1.1 200 OK\r\n"
   12153              "Content-Length: 5\r\n\r\n"
   12154              "hello"),
   12155     MockRead(ASYNC, ERR_UNEXPECTED),
   12156   };
   12157 
   12158   StaticSocketDataProvider data(data_reads, arraysize(data_reads),
   12159                                 data_writes, arraysize(data_writes));
   12160   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12161 
   12162   TestCompletionCallback callback;
   12163 
   12164   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12165   EXPECT_EQ(ERR_IO_PENDING, rv);
   12166 
   12167   rv = callback.WaitForResult();
   12168   EXPECT_EQ(OK, rv);
   12169 
   12170   HttpRequestHeaders request_headers;
   12171   EXPECT_TRUE(trans->GetFullRequestHeaders(&request_headers));
   12172   std::string foo;
   12173   EXPECT_TRUE(request_headers.GetHeader("X-Foo", &foo));
   12174   EXPECT_EQ("bar", foo);
   12175 }
   12176 
   12177 namespace {
   12178 
   12179 // Fake HttpStreamBase that simply records calls to SetPriority().
   12180 class FakeStream : public HttpStreamBase,
   12181                    public base::SupportsWeakPtr<FakeStream> {
   12182  public:
   12183   explicit FakeStream(RequestPriority priority) : priority_(priority) {}
   12184   virtual ~FakeStream() {}
   12185 
   12186   RequestPriority priority() const { return priority_; }
   12187 
   12188   virtual int InitializeStream(const HttpRequestInfo* request_info,
   12189                                RequestPriority priority,
   12190                                const BoundNetLog& net_log,
   12191                                const CompletionCallback& callback) OVERRIDE {
   12192     return ERR_IO_PENDING;
   12193   }
   12194 
   12195   virtual int SendRequest(const HttpRequestHeaders& request_headers,
   12196                           HttpResponseInfo* response,
   12197                           const CompletionCallback& callback) OVERRIDE {
   12198     ADD_FAILURE();
   12199     return ERR_UNEXPECTED;
   12200   }
   12201 
   12202   virtual int ReadResponseHeaders(const CompletionCallback& callback) OVERRIDE {
   12203     ADD_FAILURE();
   12204     return ERR_UNEXPECTED;
   12205   }
   12206 
   12207   virtual int ReadResponseBody(IOBuffer* buf, int buf_len,
   12208                                const CompletionCallback& callback) OVERRIDE {
   12209     ADD_FAILURE();
   12210     return ERR_UNEXPECTED;
   12211   }
   12212 
   12213   virtual void Close(bool not_reusable) OVERRIDE {}
   12214 
   12215   virtual bool IsResponseBodyComplete() const OVERRIDE {
   12216     ADD_FAILURE();
   12217     return false;
   12218   }
   12219 
   12220   virtual bool CanFindEndOfResponse() const OVERRIDE {
   12221     return false;
   12222   }
   12223 
   12224   virtual bool IsConnectionReused() const OVERRIDE {
   12225     ADD_FAILURE();
   12226     return false;
   12227   }
   12228 
   12229   virtual void SetConnectionReused() OVERRIDE {
   12230     ADD_FAILURE();
   12231   }
   12232 
   12233   virtual bool IsConnectionReusable() const OVERRIDE {
   12234     ADD_FAILURE();
   12235     return false;
   12236   }
   12237 
   12238   virtual int64 GetTotalReceivedBytes() const OVERRIDE {
   12239     ADD_FAILURE();
   12240     return 0;
   12241   }
   12242 
   12243   virtual bool GetLoadTimingInfo(
   12244       LoadTimingInfo* load_timing_info) const OVERRIDE {
   12245     ADD_FAILURE();
   12246     return false;
   12247   }
   12248 
   12249   virtual void GetSSLInfo(SSLInfo* ssl_info) OVERRIDE {
   12250     ADD_FAILURE();
   12251   }
   12252 
   12253   virtual void GetSSLCertRequestInfo(
   12254       SSLCertRequestInfo* cert_request_info) OVERRIDE {
   12255     ADD_FAILURE();
   12256   }
   12257 
   12258   virtual bool IsSpdyHttpStream() const OVERRIDE {
   12259     ADD_FAILURE();
   12260     return false;
   12261   }
   12262 
   12263   virtual void Drain(HttpNetworkSession* session) OVERRIDE {
   12264     ADD_FAILURE();
   12265   }
   12266 
   12267   virtual void SetPriority(RequestPriority priority) OVERRIDE {
   12268     priority_ = priority;
   12269   }
   12270 
   12271  private:
   12272   RequestPriority priority_;
   12273 
   12274   DISALLOW_COPY_AND_ASSIGN(FakeStream);
   12275 };
   12276 
   12277 // Fake HttpStreamRequest that simply records calls to SetPriority()
   12278 // and vends FakeStreams with its current priority.
   12279 class FakeStreamRequest : public HttpStreamRequest,
   12280                           public base::SupportsWeakPtr<FakeStreamRequest> {
   12281  public:
   12282   FakeStreamRequest(RequestPriority priority,
   12283                     HttpStreamRequest::Delegate* delegate)
   12284       : priority_(priority),
   12285         delegate_(delegate),
   12286         websocket_stream_create_helper_(NULL) {}
   12287 
   12288   FakeStreamRequest(RequestPriority priority,
   12289                     HttpStreamRequest::Delegate* delegate,
   12290                     WebSocketHandshakeStreamBase::CreateHelper* create_helper)
   12291       : priority_(priority),
   12292         delegate_(delegate),
   12293         websocket_stream_create_helper_(create_helper) {}
   12294 
   12295   virtual ~FakeStreamRequest() {}
   12296 
   12297   RequestPriority priority() const { return priority_; }
   12298 
   12299   const WebSocketHandshakeStreamBase::CreateHelper*
   12300   websocket_stream_create_helper() const {
   12301     return websocket_stream_create_helper_;
   12302   }
   12303 
   12304   // Create a new FakeStream and pass it to the request's
   12305   // delegate. Returns a weak pointer to the FakeStream.
   12306   base::WeakPtr<FakeStream> FinishStreamRequest() {
   12307     FakeStream* fake_stream = new FakeStream(priority_);
   12308     // Do this before calling OnStreamReady() as OnStreamReady() may
   12309     // immediately delete |fake_stream|.
   12310     base::WeakPtr<FakeStream> weak_stream = fake_stream->AsWeakPtr();
   12311     delegate_->OnStreamReady(SSLConfig(), ProxyInfo(), fake_stream);
   12312     return weak_stream;
   12313   }
   12314 
   12315   virtual int RestartTunnelWithProxyAuth(
   12316       const AuthCredentials& credentials) OVERRIDE {
   12317     ADD_FAILURE();
   12318     return ERR_UNEXPECTED;
   12319   }
   12320 
   12321   virtual LoadState GetLoadState() const OVERRIDE {
   12322     ADD_FAILURE();
   12323     return LoadState();
   12324   }
   12325 
   12326   virtual void SetPriority(RequestPriority priority) OVERRIDE {
   12327     priority_ = priority;
   12328   }
   12329 
   12330   virtual bool was_npn_negotiated() const OVERRIDE {
   12331     return false;
   12332   }
   12333 
   12334   virtual NextProto protocol_negotiated() const OVERRIDE {
   12335     return kProtoUnknown;
   12336   }
   12337 
   12338   virtual bool using_spdy() const OVERRIDE {
   12339     return false;
   12340   }
   12341 
   12342  private:
   12343   RequestPriority priority_;
   12344   HttpStreamRequest::Delegate* const delegate_;
   12345   WebSocketHandshakeStreamBase::CreateHelper* websocket_stream_create_helper_;
   12346 
   12347   DISALLOW_COPY_AND_ASSIGN(FakeStreamRequest);
   12348 };
   12349 
   12350 // Fake HttpStreamFactory that vends FakeStreamRequests.
   12351 class FakeStreamFactory : public HttpStreamFactory {
   12352  public:
   12353   FakeStreamFactory() {}
   12354   virtual ~FakeStreamFactory() {}
   12355 
   12356   // Returns a WeakPtr<> to the last HttpStreamRequest returned by
   12357   // RequestStream() (which may be NULL if it was destroyed already).
   12358   base::WeakPtr<FakeStreamRequest> last_stream_request() {
   12359     return last_stream_request_;
   12360   }
   12361 
   12362   virtual HttpStreamRequest* RequestStream(
   12363       const HttpRequestInfo& info,
   12364       RequestPriority priority,
   12365       const SSLConfig& server_ssl_config,
   12366       const SSLConfig& proxy_ssl_config,
   12367       HttpStreamRequest::Delegate* delegate,
   12368       const BoundNetLog& net_log) OVERRIDE {
   12369     FakeStreamRequest* fake_request = new FakeStreamRequest(priority, delegate);
   12370     last_stream_request_ = fake_request->AsWeakPtr();
   12371     return fake_request;
   12372   }
   12373 
   12374   virtual HttpStreamRequest* RequestWebSocketHandshakeStream(
   12375       const HttpRequestInfo& info,
   12376       RequestPriority priority,
   12377       const SSLConfig& server_ssl_config,
   12378       const SSLConfig& proxy_ssl_config,
   12379       HttpStreamRequest::Delegate* delegate,
   12380       WebSocketHandshakeStreamBase::CreateHelper* create_helper,
   12381       const BoundNetLog& net_log) OVERRIDE {
   12382     FakeStreamRequest* fake_request =
   12383         new FakeStreamRequest(priority, delegate, create_helper);
   12384     last_stream_request_ = fake_request->AsWeakPtr();
   12385     return fake_request;
   12386   }
   12387 
   12388   virtual void PreconnectStreams(int num_streams,
   12389                                  const HttpRequestInfo& info,
   12390                                  RequestPriority priority,
   12391                                  const SSLConfig& server_ssl_config,
   12392                                  const SSLConfig& proxy_ssl_config) OVERRIDE {
   12393     ADD_FAILURE();
   12394   }
   12395 
   12396   virtual const HostMappingRules* GetHostMappingRules() const OVERRIDE {
   12397     ADD_FAILURE();
   12398     return NULL;
   12399   }
   12400 
   12401  private:
   12402   base::WeakPtr<FakeStreamRequest> last_stream_request_;
   12403 
   12404   DISALLOW_COPY_AND_ASSIGN(FakeStreamFactory);
   12405 };
   12406 
   12407 // TODO(yhirano): Split this class out into a net/websockets file, if it is
   12408 // worth doing.
   12409 class FakeWebSocketStreamCreateHelper :
   12410       public WebSocketHandshakeStreamBase::CreateHelper {
   12411  public:
   12412   virtual WebSocketHandshakeStreamBase* CreateBasicStream(
   12413       scoped_ptr<ClientSocketHandle> connection,
   12414       bool using_proxy) OVERRIDE {
   12415     NOTREACHED();
   12416     return NULL;
   12417   }
   12418 
   12419   virtual WebSocketHandshakeStreamBase* CreateSpdyStream(
   12420       const base::WeakPtr<SpdySession>& session,
   12421       bool use_relative_url) OVERRIDE {
   12422     NOTREACHED();
   12423     return NULL;
   12424   };
   12425 
   12426   virtual ~FakeWebSocketStreamCreateHelper() {}
   12427 
   12428   virtual scoped_ptr<WebSocketStream> Upgrade() {
   12429     NOTREACHED();
   12430     return scoped_ptr<WebSocketStream>();
   12431   }
   12432 };
   12433 
   12434 }  // namespace
   12435 
   12436 // Make sure that HttpNetworkTransaction passes on its priority to its
   12437 // stream request on start.
   12438 TEST_P(HttpNetworkTransactionTest, SetStreamRequestPriorityOnStart) {
   12439   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12440   HttpNetworkSessionPeer peer(session);
   12441   FakeStreamFactory* fake_factory = new FakeStreamFactory();
   12442   peer.SetHttpStreamFactory(scoped_ptr<HttpStreamFactory>(fake_factory));
   12443 
   12444   HttpNetworkTransaction trans(LOW, session);
   12445 
   12446   ASSERT_TRUE(fake_factory->last_stream_request() == NULL);
   12447 
   12448   HttpRequestInfo request;
   12449   TestCompletionCallback callback;
   12450   EXPECT_EQ(ERR_IO_PENDING,
   12451             trans.Start(&request, callback.callback(), BoundNetLog()));
   12452 
   12453   base::WeakPtr<FakeStreamRequest> fake_request =
   12454       fake_factory->last_stream_request();
   12455   ASSERT_TRUE(fake_request != NULL);
   12456   EXPECT_EQ(LOW, fake_request->priority());
   12457 }
   12458 
   12459 // Make sure that HttpNetworkTransaction passes on its priority
   12460 // updates to its stream request.
   12461 TEST_P(HttpNetworkTransactionTest, SetStreamRequestPriority) {
   12462   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12463   HttpNetworkSessionPeer peer(session);
   12464   FakeStreamFactory* fake_factory = new FakeStreamFactory();
   12465   peer.SetHttpStreamFactory(scoped_ptr<HttpStreamFactory>(fake_factory));
   12466 
   12467   HttpNetworkTransaction trans(LOW, session);
   12468 
   12469   HttpRequestInfo request;
   12470   TestCompletionCallback callback;
   12471   EXPECT_EQ(ERR_IO_PENDING,
   12472             trans.Start(&request, callback.callback(), BoundNetLog()));
   12473 
   12474   base::WeakPtr<FakeStreamRequest> fake_request =
   12475       fake_factory->last_stream_request();
   12476   ASSERT_TRUE(fake_request != NULL);
   12477   EXPECT_EQ(LOW, fake_request->priority());
   12478 
   12479   trans.SetPriority(LOWEST);
   12480   ASSERT_TRUE(fake_request != NULL);
   12481   EXPECT_EQ(LOWEST, fake_request->priority());
   12482 }
   12483 
   12484 // Make sure that HttpNetworkTransaction passes on its priority
   12485 // updates to its stream.
   12486 TEST_P(HttpNetworkTransactionTest, SetStreamPriority) {
   12487   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12488   HttpNetworkSessionPeer peer(session);
   12489   FakeStreamFactory* fake_factory = new FakeStreamFactory();
   12490   peer.SetHttpStreamFactory(scoped_ptr<HttpStreamFactory>(fake_factory));
   12491 
   12492   HttpNetworkTransaction trans(LOW, session);
   12493 
   12494   HttpRequestInfo request;
   12495   TestCompletionCallback callback;
   12496   EXPECT_EQ(ERR_IO_PENDING,
   12497             trans.Start(&request, callback.callback(), BoundNetLog()));
   12498 
   12499   base::WeakPtr<FakeStreamRequest> fake_request =
   12500       fake_factory->last_stream_request();
   12501   ASSERT_TRUE(fake_request != NULL);
   12502   base::WeakPtr<FakeStream> fake_stream = fake_request->FinishStreamRequest();
   12503   ASSERT_TRUE(fake_stream != NULL);
   12504   EXPECT_EQ(LOW, fake_stream->priority());
   12505 
   12506   trans.SetPriority(LOWEST);
   12507   EXPECT_EQ(LOWEST, fake_stream->priority());
   12508 }
   12509 
   12510 TEST_P(HttpNetworkTransactionTest, CreateWebSocketHandshakeStream) {
   12511   // The same logic needs to be tested for both ws: and wss: schemes, but this
   12512   // test is already parameterised on NextProto, so it uses a loop to verify
   12513   // that the different schemes work.
   12514   std::string test_cases[] = {"ws://www.google.com/", "wss://www.google.com/"};
   12515   for (size_t i = 0; i < arraysize(test_cases); ++i) {
   12516     scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12517     HttpNetworkSessionPeer peer(session);
   12518     FakeStreamFactory* fake_factory = new FakeStreamFactory();
   12519     FakeWebSocketStreamCreateHelper websocket_stream_create_helper;
   12520     peer.SetHttpStreamFactoryForWebSocket(
   12521         scoped_ptr<HttpStreamFactory>(fake_factory));
   12522 
   12523     HttpNetworkTransaction trans(LOW, session);
   12524     trans.SetWebSocketHandshakeStreamCreateHelper(
   12525         &websocket_stream_create_helper);
   12526 
   12527     HttpRequestInfo request;
   12528     TestCompletionCallback callback;
   12529     request.method = "GET";
   12530     request.url = GURL(test_cases[i]);
   12531 
   12532     EXPECT_EQ(ERR_IO_PENDING,
   12533               trans.Start(&request, callback.callback(), BoundNetLog()));
   12534 
   12535     base::WeakPtr<FakeStreamRequest> fake_request =
   12536         fake_factory->last_stream_request();
   12537     ASSERT_TRUE(fake_request != NULL);
   12538     EXPECT_EQ(&websocket_stream_create_helper,
   12539               fake_request->websocket_stream_create_helper());
   12540   }
   12541 }
   12542 
   12543 // Tests that when a used socket is returned to the SSL socket pool, it's closed
   12544 // if the transport socket pool is stalled on the global socket limit.
   12545 TEST_P(HttpNetworkTransactionTest, CloseSSLSocketOnIdleForHttpRequest) {
   12546   ClientSocketPoolManager::set_max_sockets_per_group(
   12547       HttpNetworkSession::NORMAL_SOCKET_POOL, 1);
   12548   ClientSocketPoolManager::set_max_sockets_per_pool(
   12549       HttpNetworkSession::NORMAL_SOCKET_POOL, 1);
   12550 
   12551   // Set up SSL request.
   12552 
   12553   HttpRequestInfo ssl_request;
   12554   ssl_request.method = "GET";
   12555   ssl_request.url = GURL("https://www.google.com/");
   12556 
   12557   MockWrite ssl_writes[] = {
   12558     MockWrite("GET / HTTP/1.1\r\n"
   12559               "Host: www.google.com\r\n"
   12560               "Connection: keep-alive\r\n\r\n"),
   12561   };
   12562   MockRead ssl_reads[] = {
   12563     MockRead("HTTP/1.1 200 OK\r\n"),
   12564     MockRead("Content-Length: 11\r\n\r\n"),
   12565     MockRead("hello world"),
   12566     MockRead(SYNCHRONOUS, OK),
   12567   };
   12568   StaticSocketDataProvider ssl_data(ssl_reads, arraysize(ssl_reads),
   12569                                     ssl_writes, arraysize(ssl_writes));
   12570   session_deps_.socket_factory->AddSocketDataProvider(&ssl_data);
   12571 
   12572   SSLSocketDataProvider ssl(ASYNC, OK);
   12573   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   12574 
   12575   // Set up HTTP request.
   12576 
   12577   HttpRequestInfo http_request;
   12578   http_request.method = "GET";
   12579   http_request.url = GURL("http://www.google.com/");
   12580 
   12581   MockWrite http_writes[] = {
   12582     MockWrite("GET / HTTP/1.1\r\n"
   12583               "Host: www.google.com\r\n"
   12584               "Connection: keep-alive\r\n\r\n"),
   12585   };
   12586   MockRead http_reads[] = {
   12587     MockRead("HTTP/1.1 200 OK\r\n"),
   12588     MockRead("Content-Length: 7\r\n\r\n"),
   12589     MockRead("falafel"),
   12590     MockRead(SYNCHRONOUS, OK),
   12591   };
   12592   StaticSocketDataProvider http_data(http_reads, arraysize(http_reads),
   12593                                      http_writes, arraysize(http_writes));
   12594   session_deps_.socket_factory->AddSocketDataProvider(&http_data);
   12595 
   12596   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12597 
   12598   // Start the SSL request.
   12599   TestCompletionCallback ssl_callback;
   12600   scoped_ptr<HttpTransaction> ssl_trans(
   12601       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   12602   ASSERT_EQ(ERR_IO_PENDING,
   12603             ssl_trans->Start(&ssl_request, ssl_callback.callback(),
   12604             BoundNetLog()));
   12605 
   12606   // Start the HTTP request.  Pool should stall.
   12607   TestCompletionCallback http_callback;
   12608   scoped_ptr<HttpTransaction> http_trans(
   12609       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   12610   ASSERT_EQ(ERR_IO_PENDING,
   12611             http_trans->Start(&http_request, http_callback.callback(),
   12612                               BoundNetLog()));
   12613   EXPECT_TRUE(IsTransportSocketPoolStalled(session));
   12614 
   12615   // Wait for response from SSL request.
   12616   ASSERT_EQ(OK, ssl_callback.WaitForResult());
   12617   std::string response_data;
   12618   ASSERT_EQ(OK, ReadTransaction(ssl_trans.get(), &response_data));
   12619   EXPECT_EQ("hello world", response_data);
   12620 
   12621   // The SSL socket should automatically be closed, so the HTTP request can
   12622   // start.
   12623   EXPECT_EQ(0, GetIdleSocketCountInSSLSocketPool(session));
   12624   ASSERT_FALSE(IsTransportSocketPoolStalled(session));
   12625 
   12626   // The HTTP request can now complete.
   12627   ASSERT_EQ(OK, http_callback.WaitForResult());
   12628   ASSERT_EQ(OK, ReadTransaction(http_trans.get(), &response_data));
   12629   EXPECT_EQ("falafel", response_data);
   12630 
   12631   EXPECT_EQ(1, GetIdleSocketCountInTransportSocketPool(session));
   12632 }
   12633 
   12634 // Tests that when a SSL connection is established but there's no corresponding
   12635 // request that needs it, the new socket is closed if the transport socket pool
   12636 // is stalled on the global socket limit.
   12637 TEST_P(HttpNetworkTransactionTest, CloseSSLSocketOnIdleForHttpRequest2) {
   12638   ClientSocketPoolManager::set_max_sockets_per_group(
   12639       HttpNetworkSession::NORMAL_SOCKET_POOL, 1);
   12640   ClientSocketPoolManager::set_max_sockets_per_pool(
   12641       HttpNetworkSession::NORMAL_SOCKET_POOL, 1);
   12642 
   12643   // Set up an ssl request.
   12644 
   12645   HttpRequestInfo ssl_request;
   12646   ssl_request.method = "GET";
   12647   ssl_request.url = GURL("https://www.foopy.com/");
   12648 
   12649   // No data will be sent on the SSL socket.
   12650   StaticSocketDataProvider ssl_data;
   12651   session_deps_.socket_factory->AddSocketDataProvider(&ssl_data);
   12652 
   12653   SSLSocketDataProvider ssl(ASYNC, OK);
   12654   session_deps_.socket_factory->AddSSLSocketDataProvider(&ssl);
   12655 
   12656   // Set up HTTP request.
   12657 
   12658   HttpRequestInfo http_request;
   12659   http_request.method = "GET";
   12660   http_request.url = GURL("http://www.google.com/");
   12661 
   12662   MockWrite http_writes[] = {
   12663     MockWrite("GET / HTTP/1.1\r\n"
   12664               "Host: www.google.com\r\n"
   12665               "Connection: keep-alive\r\n\r\n"),
   12666   };
   12667   MockRead http_reads[] = {
   12668     MockRead("HTTP/1.1 200 OK\r\n"),
   12669     MockRead("Content-Length: 7\r\n\r\n"),
   12670     MockRead("falafel"),
   12671     MockRead(SYNCHRONOUS, OK),
   12672   };
   12673   StaticSocketDataProvider http_data(http_reads, arraysize(http_reads),
   12674                                      http_writes, arraysize(http_writes));
   12675   session_deps_.socket_factory->AddSocketDataProvider(&http_data);
   12676 
   12677   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12678 
   12679   // Preconnect an SSL socket.  A preconnect is needed because connect jobs are
   12680   // cancelled when a normal transaction is cancelled.
   12681   net::HttpStreamFactory* http_stream_factory = session->http_stream_factory();
   12682   net::SSLConfig ssl_config;
   12683   session->ssl_config_service()->GetSSLConfig(&ssl_config);
   12684   http_stream_factory->PreconnectStreams(1, ssl_request, DEFAULT_PRIORITY,
   12685                                          ssl_config, ssl_config);
   12686   EXPECT_EQ(0, GetIdleSocketCountInSSLSocketPool(session));
   12687 
   12688   // Start the HTTP request.  Pool should stall.
   12689   TestCompletionCallback http_callback;
   12690   scoped_ptr<HttpTransaction> http_trans(
   12691       new HttpNetworkTransaction(DEFAULT_PRIORITY, session.get()));
   12692   ASSERT_EQ(ERR_IO_PENDING,
   12693             http_trans->Start(&http_request, http_callback.callback(),
   12694                               BoundNetLog()));
   12695   EXPECT_TRUE(IsTransportSocketPoolStalled(session));
   12696 
   12697   // The SSL connection will automatically be closed once the connection is
   12698   // established, to let the HTTP request start.
   12699   ASSERT_EQ(OK, http_callback.WaitForResult());
   12700   std::string response_data;
   12701   ASSERT_EQ(OK, ReadTransaction(http_trans.get(), &response_data));
   12702   EXPECT_EQ("falafel", response_data);
   12703 
   12704   EXPECT_EQ(1, GetIdleSocketCountInTransportSocketPool(session));
   12705 }
   12706 
   12707 TEST_P(HttpNetworkTransactionTest, PostReadsErrorResponseAfterReset) {
   12708   ScopedVector<UploadElementReader> element_readers;
   12709   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   12710   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   12711 
   12712   HttpRequestInfo request;
   12713   request.method = "POST";
   12714   request.url = GURL("http://www.foo.com/");
   12715   request.upload_data_stream = &upload_data_stream;
   12716   request.load_flags = 0;
   12717 
   12718   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12719   scoped_ptr<HttpTransaction> trans(
   12720       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12721   // Send headers successfully, but get an error while sending the body.
   12722   MockWrite data_writes[] = {
   12723     MockWrite("POST / HTTP/1.1\r\n"
   12724               "Host: www.foo.com\r\n"
   12725               "Connection: keep-alive\r\n"
   12726               "Content-Length: 3\r\n\r\n"),
   12727     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   12728   };
   12729 
   12730   MockRead data_reads[] = {
   12731     MockRead("HTTP/1.0 400 Not OK\r\n\r\n"),
   12732     MockRead("hello world"),
   12733     MockRead(SYNCHRONOUS, OK),
   12734   };
   12735   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   12736                                 arraysize(data_writes));
   12737   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12738 
   12739   TestCompletionCallback callback;
   12740 
   12741   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12742   EXPECT_EQ(ERR_IO_PENDING, rv);
   12743 
   12744   rv = callback.WaitForResult();
   12745   EXPECT_EQ(OK, rv);
   12746 
   12747   const HttpResponseInfo* response = trans->GetResponseInfo();
   12748   ASSERT_TRUE(response != NULL);
   12749 
   12750   EXPECT_TRUE(response->headers.get() != NULL);
   12751   EXPECT_EQ("HTTP/1.0 400 Not OK", response->headers->GetStatusLine());
   12752 
   12753   std::string response_data;
   12754   rv = ReadTransaction(trans.get(), &response_data);
   12755   EXPECT_EQ(OK, rv);
   12756   EXPECT_EQ("hello world", response_data);
   12757 }
   12758 
   12759 // This test makes sure the retry logic doesn't trigger when reading an error
   12760 // response from a server that rejected a POST with a CONNECTION_RESET.
   12761 TEST_P(HttpNetworkTransactionTest,
   12762        PostReadsErrorResponseAfterResetOnReusedSocket) {
   12763   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12764   MockWrite data_writes[] = {
   12765     MockWrite("GET / HTTP/1.1\r\n"
   12766               "Host: www.foo.com\r\n"
   12767               "Connection: keep-alive\r\n\r\n"),
   12768     MockWrite("POST / HTTP/1.1\r\n"
   12769               "Host: www.foo.com\r\n"
   12770               "Connection: keep-alive\r\n"
   12771               "Content-Length: 3\r\n\r\n"),
   12772     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   12773   };
   12774 
   12775   MockRead data_reads[] = {
   12776     MockRead("HTTP/1.1 200 Peachy\r\n"
   12777              "Content-Length: 14\r\n\r\n"),
   12778     MockRead("first response"),
   12779     MockRead("HTTP/1.1 400 Not OK\r\n"
   12780              "Content-Length: 15\r\n\r\n"),
   12781     MockRead("second response"),
   12782     MockRead(SYNCHRONOUS, OK),
   12783   };
   12784   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   12785                                 arraysize(data_writes));
   12786   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12787 
   12788   TestCompletionCallback callback;
   12789   HttpRequestInfo request1;
   12790   request1.method = "GET";
   12791   request1.url = GURL("http://www.foo.com/");
   12792   request1.load_flags = 0;
   12793 
   12794   scoped_ptr<HttpTransaction> trans1(
   12795       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12796   int rv = trans1->Start(&request1, callback.callback(), BoundNetLog());
   12797   EXPECT_EQ(ERR_IO_PENDING, rv);
   12798 
   12799   rv = callback.WaitForResult();
   12800   EXPECT_EQ(OK, rv);
   12801 
   12802   const HttpResponseInfo* response1 = trans1->GetResponseInfo();
   12803   ASSERT_TRUE(response1 != NULL);
   12804 
   12805   EXPECT_TRUE(response1->headers.get() != NULL);
   12806   EXPECT_EQ("HTTP/1.1 200 Peachy", response1->headers->GetStatusLine());
   12807 
   12808   std::string response_data1;
   12809   rv = ReadTransaction(trans1.get(), &response_data1);
   12810   EXPECT_EQ(OK, rv);
   12811   EXPECT_EQ("first response", response_data1);
   12812   // Delete the transaction to release the socket back into the socket pool.
   12813   trans1.reset();
   12814 
   12815   ScopedVector<UploadElementReader> element_readers;
   12816   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   12817   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   12818 
   12819   HttpRequestInfo request2;
   12820   request2.method = "POST";
   12821   request2.url = GURL("http://www.foo.com/");
   12822   request2.upload_data_stream = &upload_data_stream;
   12823   request2.load_flags = 0;
   12824 
   12825   scoped_ptr<HttpTransaction> trans2(
   12826       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12827   rv = trans2->Start(&request2, callback.callback(), BoundNetLog());
   12828   EXPECT_EQ(ERR_IO_PENDING, rv);
   12829 
   12830   rv = callback.WaitForResult();
   12831   EXPECT_EQ(OK, rv);
   12832 
   12833   const HttpResponseInfo* response2 = trans2->GetResponseInfo();
   12834   ASSERT_TRUE(response2 != NULL);
   12835 
   12836   EXPECT_TRUE(response2->headers.get() != NULL);
   12837   EXPECT_EQ("HTTP/1.1 400 Not OK", response2->headers->GetStatusLine());
   12838 
   12839   std::string response_data2;
   12840   rv = ReadTransaction(trans2.get(), &response_data2);
   12841   EXPECT_EQ(OK, rv);
   12842   EXPECT_EQ("second response", response_data2);
   12843 }
   12844 
   12845 TEST_P(HttpNetworkTransactionTest,
   12846        PostReadsErrorResponseAfterResetPartialBodySent) {
   12847   ScopedVector<UploadElementReader> element_readers;
   12848   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   12849   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   12850 
   12851   HttpRequestInfo request;
   12852   request.method = "POST";
   12853   request.url = GURL("http://www.foo.com/");
   12854   request.upload_data_stream = &upload_data_stream;
   12855   request.load_flags = 0;
   12856 
   12857   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12858   scoped_ptr<HttpTransaction> trans(
   12859       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12860   // Send headers successfully, but get an error while sending the body.
   12861   MockWrite data_writes[] = {
   12862     MockWrite("POST / HTTP/1.1\r\n"
   12863               "Host: www.foo.com\r\n"
   12864               "Connection: keep-alive\r\n"
   12865               "Content-Length: 3\r\n\r\n"
   12866               "fo"),
   12867     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   12868   };
   12869 
   12870   MockRead data_reads[] = {
   12871     MockRead("HTTP/1.0 400 Not OK\r\n\r\n"),
   12872     MockRead("hello world"),
   12873     MockRead(SYNCHRONOUS, OK),
   12874   };
   12875   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   12876                                 arraysize(data_writes));
   12877   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12878 
   12879   TestCompletionCallback callback;
   12880 
   12881   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12882   EXPECT_EQ(ERR_IO_PENDING, rv);
   12883 
   12884   rv = callback.WaitForResult();
   12885   EXPECT_EQ(OK, rv);
   12886 
   12887   const HttpResponseInfo* response = trans->GetResponseInfo();
   12888   ASSERT_TRUE(response != NULL);
   12889 
   12890   EXPECT_TRUE(response->headers.get() != NULL);
   12891   EXPECT_EQ("HTTP/1.0 400 Not OK", response->headers->GetStatusLine());
   12892 
   12893   std::string response_data;
   12894   rv = ReadTransaction(trans.get(), &response_data);
   12895   EXPECT_EQ(OK, rv);
   12896   EXPECT_EQ("hello world", response_data);
   12897 }
   12898 
   12899 // This tests the more common case than the previous test, where headers and
   12900 // body are not merged into a single request.
   12901 TEST_P(HttpNetworkTransactionTest, ChunkedPostReadsErrorResponseAfterReset) {
   12902   ScopedVector<UploadElementReader> element_readers;
   12903   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   12904   UploadDataStream upload_data_stream(UploadDataStream::CHUNKED, 0);
   12905 
   12906   HttpRequestInfo request;
   12907   request.method = "POST";
   12908   request.url = GURL("http://www.foo.com/");
   12909   request.upload_data_stream = &upload_data_stream;
   12910   request.load_flags = 0;
   12911 
   12912   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12913   scoped_ptr<HttpTransaction> trans(
   12914       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12915   // Send headers successfully, but get an error while sending the body.
   12916   MockWrite data_writes[] = {
   12917     MockWrite("POST / HTTP/1.1\r\n"
   12918               "Host: www.foo.com\r\n"
   12919               "Connection: keep-alive\r\n"
   12920               "Transfer-Encoding: chunked\r\n\r\n"),
   12921     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   12922   };
   12923 
   12924   MockRead data_reads[] = {
   12925     MockRead("HTTP/1.0 400 Not OK\r\n\r\n"),
   12926     MockRead("hello world"),
   12927     MockRead(SYNCHRONOUS, OK),
   12928   };
   12929   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   12930                                 arraysize(data_writes));
   12931   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12932 
   12933   TestCompletionCallback callback;
   12934 
   12935   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12936   EXPECT_EQ(ERR_IO_PENDING, rv);
   12937   // Make sure the headers are sent before adding a chunk.  This ensures that
   12938   // they can't be merged with the body in a single send.  Not currently
   12939   // necessary since a chunked body is never merged with headers, but this makes
   12940   // the test more future proof.
   12941   base::RunLoop().RunUntilIdle();
   12942 
   12943   upload_data_stream.AppendChunk("last chunk", 10, true);
   12944 
   12945   rv = callback.WaitForResult();
   12946   EXPECT_EQ(OK, rv);
   12947 
   12948   const HttpResponseInfo* response = trans->GetResponseInfo();
   12949   ASSERT_TRUE(response != NULL);
   12950 
   12951   EXPECT_TRUE(response->headers.get() != NULL);
   12952   EXPECT_EQ("HTTP/1.0 400 Not OK", response->headers->GetStatusLine());
   12953 
   12954   std::string response_data;
   12955   rv = ReadTransaction(trans.get(), &response_data);
   12956   EXPECT_EQ(OK, rv);
   12957   EXPECT_EQ("hello world", response_data);
   12958 }
   12959 
   12960 TEST_P(HttpNetworkTransactionTest, PostReadsErrorResponseAfterResetAnd100) {
   12961   ScopedVector<UploadElementReader> element_readers;
   12962   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   12963   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   12964 
   12965   HttpRequestInfo request;
   12966   request.method = "POST";
   12967   request.url = GURL("http://www.foo.com/");
   12968   request.upload_data_stream = &upload_data_stream;
   12969   request.load_flags = 0;
   12970 
   12971   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   12972   scoped_ptr<HttpTransaction> trans(
   12973       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   12974 
   12975   MockWrite data_writes[] = {
   12976     MockWrite("POST / HTTP/1.1\r\n"
   12977               "Host: www.foo.com\r\n"
   12978               "Connection: keep-alive\r\n"
   12979               "Content-Length: 3\r\n\r\n"),
   12980     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   12981   };
   12982 
   12983   MockRead data_reads[] = {
   12984     MockRead("HTTP/1.0 100 Continue\r\n\r\n"),
   12985     MockRead("HTTP/1.0 400 Not OK\r\n\r\n"),
   12986     MockRead("hello world"),
   12987     MockRead(SYNCHRONOUS, OK),
   12988   };
   12989   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   12990                                 arraysize(data_writes));
   12991   session_deps_.socket_factory->AddSocketDataProvider(&data);
   12992 
   12993   TestCompletionCallback callback;
   12994 
   12995   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   12996   EXPECT_EQ(ERR_IO_PENDING, rv);
   12997 
   12998   rv = callback.WaitForResult();
   12999   EXPECT_EQ(OK, rv);
   13000 
   13001   const HttpResponseInfo* response = trans->GetResponseInfo();
   13002   ASSERT_TRUE(response != NULL);
   13003 
   13004   EXPECT_TRUE(response->headers.get() != NULL);
   13005   EXPECT_EQ("HTTP/1.0 400 Not OK", response->headers->GetStatusLine());
   13006 
   13007   std::string response_data;
   13008   rv = ReadTransaction(trans.get(), &response_data);
   13009   EXPECT_EQ(OK, rv);
   13010   EXPECT_EQ("hello world", response_data);
   13011 }
   13012 
   13013 TEST_P(HttpNetworkTransactionTest, PostIgnoresNonErrorResponseAfterReset) {
   13014   ScopedVector<UploadElementReader> element_readers;
   13015   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   13016   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   13017 
   13018   HttpRequestInfo request;
   13019   request.method = "POST";
   13020   request.url = GURL("http://www.foo.com/");
   13021   request.upload_data_stream = &upload_data_stream;
   13022   request.load_flags = 0;
   13023 
   13024   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   13025   scoped_ptr<HttpTransaction> trans(
   13026       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   13027   // Send headers successfully, but get an error while sending the body.
   13028   MockWrite data_writes[] = {
   13029     MockWrite("POST / HTTP/1.1\r\n"
   13030               "Host: www.foo.com\r\n"
   13031               "Connection: keep-alive\r\n"
   13032               "Content-Length: 3\r\n\r\n"),
   13033     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   13034   };
   13035 
   13036   MockRead data_reads[] = {
   13037     MockRead("HTTP/1.0 200 Just Dandy\r\n\r\n"),
   13038     MockRead("hello world"),
   13039     MockRead(SYNCHRONOUS, OK),
   13040   };
   13041   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   13042                                 arraysize(data_writes));
   13043   session_deps_.socket_factory->AddSocketDataProvider(&data);
   13044 
   13045   TestCompletionCallback callback;
   13046 
   13047   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   13048   EXPECT_EQ(ERR_IO_PENDING, rv);
   13049 
   13050   rv = callback.WaitForResult();
   13051   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   13052 
   13053   const HttpResponseInfo* response = trans->GetResponseInfo();
   13054   EXPECT_TRUE(response == NULL);
   13055 }
   13056 
   13057 TEST_P(HttpNetworkTransactionTest,
   13058        PostIgnoresNonErrorResponseAfterResetAnd100) {
   13059   ScopedVector<UploadElementReader> element_readers;
   13060   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   13061   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   13062 
   13063   HttpRequestInfo request;
   13064   request.method = "POST";
   13065   request.url = GURL("http://www.foo.com/");
   13066   request.upload_data_stream = &upload_data_stream;
   13067   request.load_flags = 0;
   13068 
   13069   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   13070   scoped_ptr<HttpTransaction> trans(
   13071       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   13072   // Send headers successfully, but get an error while sending the body.
   13073   MockWrite data_writes[] = {
   13074     MockWrite("POST / HTTP/1.1\r\n"
   13075               "Host: www.foo.com\r\n"
   13076               "Connection: keep-alive\r\n"
   13077               "Content-Length: 3\r\n\r\n"),
   13078     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   13079   };
   13080 
   13081   MockRead data_reads[] = {
   13082     MockRead("HTTP/1.0 100 Continue\r\n\r\n"),
   13083     MockRead("HTTP/1.0 302 Redirect\r\n"),
   13084     MockRead("Location: http://somewhere-else.com/\r\n"),
   13085     MockRead("Content-Length: 0\r\n\r\n"),
   13086     MockRead(SYNCHRONOUS, OK),
   13087   };
   13088   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   13089                                 arraysize(data_writes));
   13090   session_deps_.socket_factory->AddSocketDataProvider(&data);
   13091 
   13092   TestCompletionCallback callback;
   13093 
   13094   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   13095   EXPECT_EQ(ERR_IO_PENDING, rv);
   13096 
   13097   rv = callback.WaitForResult();
   13098   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   13099 
   13100   const HttpResponseInfo* response = trans->GetResponseInfo();
   13101   EXPECT_TRUE(response == NULL);
   13102 }
   13103 
   13104 TEST_P(HttpNetworkTransactionTest, PostIgnoresHttp09ResponseAfterReset) {
   13105   ScopedVector<UploadElementReader> element_readers;
   13106   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   13107   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   13108 
   13109   HttpRequestInfo request;
   13110   request.method = "POST";
   13111   request.url = GURL("http://www.foo.com/");
   13112   request.upload_data_stream = &upload_data_stream;
   13113   request.load_flags = 0;
   13114 
   13115   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   13116   scoped_ptr<HttpTransaction> trans(
   13117       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   13118   // Send headers successfully, but get an error while sending the body.
   13119   MockWrite data_writes[] = {
   13120     MockWrite("POST / HTTP/1.1\r\n"
   13121               "Host: www.foo.com\r\n"
   13122               "Connection: keep-alive\r\n"
   13123               "Content-Length: 3\r\n\r\n"),
   13124     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   13125   };
   13126 
   13127   MockRead data_reads[] = {
   13128     MockRead("HTTP 0.9 rocks!"),
   13129     MockRead(SYNCHRONOUS, OK),
   13130   };
   13131   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   13132                                 arraysize(data_writes));
   13133   session_deps_.socket_factory->AddSocketDataProvider(&data);
   13134 
   13135   TestCompletionCallback callback;
   13136 
   13137   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   13138   EXPECT_EQ(ERR_IO_PENDING, rv);
   13139 
   13140   rv = callback.WaitForResult();
   13141   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   13142 
   13143   const HttpResponseInfo* response = trans->GetResponseInfo();
   13144   EXPECT_TRUE(response == NULL);
   13145 }
   13146 
   13147 TEST_P(HttpNetworkTransactionTest, PostIgnoresPartial400HeadersAfterReset) {
   13148   ScopedVector<UploadElementReader> element_readers;
   13149   element_readers.push_back(new UploadBytesElementReader("foo", 3));
   13150   UploadDataStream upload_data_stream(element_readers.Pass(), 0);
   13151 
   13152   HttpRequestInfo request;
   13153   request.method = "POST";
   13154   request.url = GURL("http://www.foo.com/");
   13155   request.upload_data_stream = &upload_data_stream;
   13156   request.load_flags = 0;
   13157 
   13158   scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps_));
   13159   scoped_ptr<HttpTransaction> trans(
   13160       new HttpNetworkTransaction(DEFAULT_PRIORITY, session));
   13161   // Send headers successfully, but get an error while sending the body.
   13162   MockWrite data_writes[] = {
   13163     MockWrite("POST / HTTP/1.1\r\n"
   13164               "Host: www.foo.com\r\n"
   13165               "Connection: keep-alive\r\n"
   13166               "Content-Length: 3\r\n\r\n"),
   13167     MockWrite(SYNCHRONOUS, ERR_CONNECTION_RESET),
   13168   };
   13169 
   13170   MockRead data_reads[] = {
   13171     MockRead("HTTP/1.0 400 Not a Full Response\r\n"),
   13172     MockRead(SYNCHRONOUS, OK),
   13173   };
   13174   StaticSocketDataProvider data(data_reads, arraysize(data_reads), data_writes,
   13175                                 arraysize(data_writes));
   13176   session_deps_.socket_factory->AddSocketDataProvider(&data);
   13177 
   13178   TestCompletionCallback callback;
   13179 
   13180   int rv = trans->Start(&request, callback.callback(), BoundNetLog());
   13181   EXPECT_EQ(ERR_IO_PENDING, rv);
   13182 
   13183   rv = callback.WaitForResult();
   13184   EXPECT_EQ(ERR_CONNECTION_RESET, rv);
   13185 
   13186   const HttpResponseInfo* response = trans->GetResponseInfo();
   13187   EXPECT_TRUE(response == NULL);
   13188 }
   13189 
   13190 }  // namespace net
   13191