Home | History | Annotate | Download | only in quic
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "net/quic/quic_stream_factory.h"
      6 
      7 #include "base/run_loop.h"
      8 #include "base/strings/string_util.h"
      9 #include "net/cert/cert_verifier.h"
     10 #include "net/dns/mock_host_resolver.h"
     11 #include "net/http/http_response_headers.h"
     12 #include "net/http/http_response_info.h"
     13 #include "net/http/http_util.h"
     14 #include "net/quic/crypto/crypto_handshake.h"
     15 #include "net/quic/crypto/quic_decrypter.h"
     16 #include "net/quic/crypto/quic_encrypter.h"
     17 #include "net/quic/quic_http_stream.h"
     18 #include "net/quic/test_tools/mock_clock.h"
     19 #include "net/quic/test_tools/mock_crypto_client_stream_factory.h"
     20 #include "net/quic/test_tools/mock_random.h"
     21 #include "net/quic/test_tools/quic_test_utils.h"
     22 #include "net/socket/socket_test_util.h"
     23 #include "testing/gtest/include/gtest/gtest.h"
     24 
     25 using base::StringPiece;
     26 using std::string;
     27 using std::vector;
     28 
     29 namespace net {
     30 namespace test {
     31 
     32 class QuicStreamFactoryPeer {
     33  public:
     34   static QuicCryptoClientConfig* GetOrCreateCryptoConfig(
     35       QuicStreamFactory* factory,
     36       const HostPortProxyPair& host_port_proxy_pair) {
     37     return factory->GetOrCreateCryptoConfig(host_port_proxy_pair);
     38   }
     39 
     40   static bool HasActiveSession(QuicStreamFactory* factory,
     41                                const HostPortProxyPair& host_port_proxy_pair) {
     42     return factory->HasActiveSession(host_port_proxy_pair);
     43   }
     44 
     45   static QuicClientSession* GetActiveSession(
     46       QuicStreamFactory* factory,
     47       const HostPortProxyPair& host_port_proxy_pair) {
     48     DCHECK(factory->HasActiveSession(host_port_proxy_pair));
     49     return factory->active_sessions_[host_port_proxy_pair];
     50   }
     51 
     52   static bool IsLiveSession(QuicStreamFactory* factory,
     53                             QuicClientSession* session) {
     54     for (QuicStreamFactory::SessionSet::iterator it =
     55              factory->all_sessions_.begin();
     56          it != factory->all_sessions_.end(); ++it) {
     57       if (*it == session)
     58         return true;
     59     }
     60     return false;
     61   }
     62 };
     63 
     64 class QuicStreamFactoryTest : public ::testing::Test {
     65  protected:
     66   QuicStreamFactoryTest()
     67       : random_generator_(0),
     68         clock_(new MockClock()),
     69         factory_(&host_resolver_, &socket_factory_,
     70                  base::WeakPtr<HttpServerProperties>(),
     71                  &crypto_client_stream_factory_,
     72                  &random_generator_, clock_, kDefaultMaxPacketSize),
     73         host_port_proxy_pair_(HostPortPair("www.google.com", 443),
     74                               ProxyServer::Direct()),
     75         is_https_(false),
     76         cert_verifier_(CertVerifier::CreateDefault()) {
     77     factory_.set_require_confirmation(false);
     78   }
     79 
     80   scoped_ptr<QuicEncryptedPacket> ConstructRstPacket(
     81       QuicPacketSequenceNumber num,
     82       QuicStreamId stream_id) {
     83     QuicPacketHeader header;
     84     header.public_header.guid = random_generator_.RandUint64();
     85     header.public_header.reset_flag = false;
     86     header.public_header.version_flag = true;
     87     header.packet_sequence_number = num;
     88     header.public_header.sequence_number_length = PACKET_1BYTE_SEQUENCE_NUMBER;
     89     header.entropy_flag = false;
     90     header.fec_flag = false;
     91     header.fec_group = 0;
     92 
     93     QuicRstStreamFrame rst(stream_id, QUIC_STREAM_CANCELLED);
     94     return scoped_ptr<QuicEncryptedPacket>(
     95         ConstructPacket(header, QuicFrame(&rst)));
     96   }
     97 
     98   scoped_ptr<QuicEncryptedPacket> ConstructAckPacket(
     99       QuicPacketSequenceNumber largest_received,
    100       QuicPacketSequenceNumber least_unacked) {
    101     QuicPacketHeader header;
    102     header.public_header.guid = random_generator_.RandUint64();
    103     header.public_header.reset_flag = false;
    104     header.public_header.version_flag = false;
    105     header.packet_sequence_number = 2;
    106     header.entropy_flag = false;
    107     header.fec_flag = false;
    108     header.fec_group = 0;
    109 
    110     QuicAckFrame ack(largest_received, QuicTime::Zero(), least_unacked);
    111     QuicCongestionFeedbackFrame feedback;
    112     feedback.type = kTCP;
    113     feedback.tcp.accumulated_number_of_lost_packets = 0;
    114     feedback.tcp.receive_window = 16000;
    115 
    116     QuicFramer framer(QuicSupportedVersions(), QuicTime::Zero(), false);
    117     QuicFrames frames;
    118     frames.push_back(QuicFrame(&ack));
    119     frames.push_back(QuicFrame(&feedback));
    120     scoped_ptr<QuicPacket> packet(
    121         framer.BuildUnsizedDataPacket(header, frames).packet);
    122     return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(
    123         ENCRYPTION_NONE, header.packet_sequence_number, *packet));
    124   }
    125 
    126   // Returns a newly created packet to send congestion feedback data.
    127   scoped_ptr<QuicEncryptedPacket> ConstructFeedbackPacket(
    128       QuicPacketSequenceNumber sequence_number) {
    129     QuicPacketHeader header;
    130     header.public_header.guid = random_generator_.RandUint64();
    131     header.public_header.reset_flag = false;
    132     header.public_header.version_flag = false;
    133     header.packet_sequence_number = sequence_number;
    134     header.entropy_flag = false;
    135     header.fec_flag = false;
    136     header.fec_group = 0;
    137 
    138     QuicCongestionFeedbackFrame frame;
    139     frame.type = kTCP;
    140     frame.tcp.accumulated_number_of_lost_packets = 0;
    141     frame.tcp.receive_window = 16000;
    142 
    143     return scoped_ptr<QuicEncryptedPacket>(
    144         ConstructPacket(header, QuicFrame(&frame)));
    145   }
    146 
    147   scoped_ptr<QuicEncryptedPacket> ConstructPacket(
    148       const QuicPacketHeader& header,
    149       const QuicFrame& frame) {
    150     QuicFramer framer(QuicSupportedVersions(), QuicTime::Zero(), false);
    151     QuicFrames frames;
    152     frames.push_back(frame);
    153     scoped_ptr<QuicPacket> packet(
    154         framer.BuildUnsizedDataPacket(header, frames).packet);
    155     return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(
    156         ENCRYPTION_NONE, header.packet_sequence_number, *packet));
    157   }
    158 
    159   MockHostResolver host_resolver_;
    160   DeterministicMockClientSocketFactory socket_factory_;
    161   MockCryptoClientStreamFactory crypto_client_stream_factory_;
    162   MockRandom random_generator_;
    163   MockClock* clock_;  // Owned by factory_.
    164   QuicStreamFactory factory_;
    165   HostPortProxyPair host_port_proxy_pair_;
    166   bool is_https_;
    167   scoped_ptr<CertVerifier> cert_verifier_;
    168   BoundNetLog net_log_;
    169   TestCompletionCallback callback_;
    170 };
    171 
    172 TEST_F(QuicStreamFactoryTest, CreateIfSessionExists) {
    173   EXPECT_EQ(NULL, factory_.CreateIfSessionExists(host_port_proxy_pair_,
    174                                                  net_log_).get());
    175 }
    176 
    177 TEST_F(QuicStreamFactoryTest, Create) {
    178   MockRead reads[] = {
    179     MockRead(ASYNC, OK, 0)  // EOF
    180   };
    181   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    182   socket_factory_.AddSocketDataProvider(&socket_data);
    183   socket_data.StopAfter(1);
    184 
    185   QuicStreamRequest request(&factory_);
    186   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    187                                             cert_verifier_.get(), net_log_,
    188                                             callback_.callback()));
    189 
    190   EXPECT_EQ(OK, callback_.WaitForResult());
    191   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    192   EXPECT_TRUE(stream.get());
    193 
    194   // Will reset stream 3.
    195   stream = factory_.CreateIfSessionExists(host_port_proxy_pair_, net_log_);
    196   EXPECT_TRUE(stream.get());
    197 
    198   // TODO(rtenneti): We should probably have a tests that HTTP and HTTPS result
    199   // in streams on different sessions.
    200   QuicStreamRequest request2(&factory_);
    201   EXPECT_EQ(OK, request2.Request(host_port_proxy_pair_, is_https_,
    202                                  cert_verifier_.get(), net_log_,
    203                                  callback_.callback()));
    204   stream = request2.ReleaseStream();  // Will reset stream 5.
    205   stream.reset();  // Will reset stream 7.
    206 
    207   EXPECT_TRUE(socket_data.at_read_eof());
    208   EXPECT_TRUE(socket_data.at_write_eof());
    209 }
    210 
    211 TEST_F(QuicStreamFactoryTest, FailedCreate) {
    212   MockConnect connect(SYNCHRONOUS, ERR_ADDRESS_IN_USE);
    213   DeterministicSocketData socket_data(NULL, 0, NULL, 0);
    214   socket_data.set_connect_data(connect);
    215   socket_factory_.AddSocketDataProvider(&socket_data);
    216   socket_data.StopAfter(1);
    217 
    218   QuicStreamRequest request(&factory_);
    219   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    220                                             cert_verifier_.get(), net_log_,
    221                                             callback_.callback()));
    222 
    223   EXPECT_EQ(ERR_ADDRESS_IN_USE, callback_.WaitForResult());
    224 }
    225 
    226 TEST_F(QuicStreamFactoryTest, Goaway) {
    227   MockRead reads[] = {
    228     MockRead(ASYNC, OK, 0)  // EOF
    229   };
    230   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    231   socket_data.StopAfter(1);
    232   socket_factory_.AddSocketDataProvider(&socket_data);
    233   DeterministicSocketData socket_data2(reads, arraysize(reads), NULL, 0);
    234   socket_data2.StopAfter(1);
    235   socket_factory_.AddSocketDataProvider(&socket_data2);
    236 
    237   QuicStreamRequest request(&factory_);
    238   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    239                                             cert_verifier_.get(), net_log_,
    240                                             callback_.callback()));
    241 
    242   EXPECT_EQ(OK, callback_.WaitForResult());
    243   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    244   EXPECT_TRUE(stream.get());
    245 
    246   // Mark the session as going away.  Ensure that while it is still alive
    247   // that it is no longer active.
    248   QuicClientSession* session = QuicStreamFactoryPeer::GetActiveSession(
    249       &factory_, host_port_proxy_pair_);
    250   factory_.OnSessionGoingAway(session);
    251   EXPECT_EQ(true, QuicStreamFactoryPeer::IsLiveSession(&factory_, session));
    252   EXPECT_FALSE(QuicStreamFactoryPeer::HasActiveSession(&factory_,
    253                                                        host_port_proxy_pair_));
    254   EXPECT_EQ(NULL, factory_.CreateIfSessionExists(host_port_proxy_pair_,
    255                                                  net_log_).get());
    256 
    257   // Create a new request for the same destination and verify that a
    258   // new session is created.
    259   QuicStreamRequest request2(&factory_);
    260   EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
    261                                              cert_verifier_.get(), net_log_,
    262                                              callback_.callback()));
    263   EXPECT_EQ(OK, callback_.WaitForResult());
    264   scoped_ptr<QuicHttpStream> stream2 = request2.ReleaseStream();
    265   EXPECT_TRUE(stream2.get());
    266 
    267   EXPECT_TRUE(QuicStreamFactoryPeer::HasActiveSession(&factory_,
    268                                                       host_port_proxy_pair_));
    269   EXPECT_NE(session,
    270             QuicStreamFactoryPeer::GetActiveSession(
    271                 &factory_, host_port_proxy_pair_));
    272   EXPECT_EQ(true, QuicStreamFactoryPeer::IsLiveSession(&factory_, session));
    273 
    274   stream2.reset();
    275   stream.reset();
    276 
    277   EXPECT_TRUE(socket_data.at_read_eof());
    278   EXPECT_TRUE(socket_data.at_write_eof());
    279 }
    280 
    281 TEST_F(QuicStreamFactoryTest, MaxOpenStream) {
    282   MockRead reads[] = {
    283     MockRead(ASYNC, OK, 0)  // EOF
    284   };
    285   scoped_ptr<QuicEncryptedPacket> rst(ConstructRstPacket(1, 3));
    286   MockWrite writes[] = {
    287     MockWrite(ASYNC, rst->data(), rst->length(), 1),
    288   };
    289   DeterministicSocketData socket_data(reads, arraysize(reads),
    290                                       writes, arraysize(writes));
    291   socket_factory_.AddSocketDataProvider(&socket_data);
    292   socket_data.StopAfter(1);
    293 
    294   HttpRequestInfo request_info;
    295   std::vector<QuicHttpStream*> streams;
    296   // The MockCryptoClientStream sets max_open_streams to be
    297   // 2 * kDefaultMaxStreamsPerConnection.
    298   for (size_t i = 0; i < 2 * kDefaultMaxStreamsPerConnection; i++) {
    299     QuicStreamRequest request(&factory_);
    300     int rv = request.Request(host_port_proxy_pair_, is_https_,
    301                              cert_verifier_.get(), net_log_,
    302                              callback_.callback());
    303     if (i == 0) {
    304       EXPECT_EQ(ERR_IO_PENDING, rv);
    305       EXPECT_EQ(OK, callback_.WaitForResult());
    306     } else {
    307       EXPECT_EQ(OK, rv);
    308     }
    309     scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    310     EXPECT_TRUE(stream);
    311     EXPECT_EQ(OK, stream->InitializeStream(
    312         &request_info, DEFAULT_PRIORITY, net_log_, CompletionCallback()));
    313     streams.push_back(stream.release());
    314   }
    315 
    316   QuicStreamRequest request(&factory_);
    317   EXPECT_EQ(OK, request.Request(host_port_proxy_pair_, is_https_,
    318                                 cert_verifier_.get(), net_log_,
    319                                 CompletionCallback()));
    320   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    321   EXPECT_TRUE(stream);
    322   EXPECT_EQ(ERR_IO_PENDING, stream->InitializeStream(
    323         &request_info, DEFAULT_PRIORITY, net_log_, callback_.callback()));
    324 
    325   // Close the first stream.
    326   streams.front()->Close(false);
    327 
    328   ASSERT_TRUE(callback_.have_result());
    329 
    330   EXPECT_EQ(OK, callback_.WaitForResult());
    331 
    332   EXPECT_TRUE(socket_data.at_read_eof());
    333   EXPECT_TRUE(socket_data.at_write_eof());
    334   STLDeleteElements(&streams);
    335 }
    336 
    337 TEST_F(QuicStreamFactoryTest, CreateError) {
    338   DeterministicSocketData socket_data(NULL, 0, NULL, 0);
    339   socket_factory_.AddSocketDataProvider(&socket_data);
    340 
    341   host_resolver_.rules()->AddSimulatedFailure("www.google.com");
    342 
    343   QuicStreamRequest request(&factory_);
    344   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    345                                             cert_verifier_.get(), net_log_,
    346                                             callback_.callback()));
    347 
    348   EXPECT_EQ(ERR_NAME_NOT_RESOLVED, callback_.WaitForResult());
    349 
    350   EXPECT_TRUE(socket_data.at_read_eof());
    351   EXPECT_TRUE(socket_data.at_write_eof());
    352 }
    353 
    354 TEST_F(QuicStreamFactoryTest, CancelCreate) {
    355   MockRead reads[] = {
    356     MockRead(ASYNC, OK, 0)  // EOF
    357   };
    358   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    359   socket_factory_.AddSocketDataProvider(&socket_data);
    360   {
    361     QuicStreamRequest request(&factory_);
    362     EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    363                                               cert_verifier_.get(), net_log_,
    364                                               callback_.callback()));
    365   }
    366 
    367   socket_data.StopAfter(1);
    368   base::RunLoop run_loop;
    369   run_loop.RunUntilIdle();
    370 
    371   scoped_ptr<QuicHttpStream> stream(
    372       factory_.CreateIfSessionExists(host_port_proxy_pair_, net_log_));
    373   EXPECT_TRUE(stream.get());
    374   stream.reset();
    375 
    376   EXPECT_TRUE(socket_data.at_read_eof());
    377   EXPECT_TRUE(socket_data.at_write_eof());
    378 }
    379 
    380 TEST_F(QuicStreamFactoryTest, CloseAllSessions) {
    381   MockRead reads[] = {
    382     MockRead(ASYNC, 0, 0)  // EOF
    383   };
    384   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    385   socket_factory_.AddSocketDataProvider(&socket_data);
    386   socket_data.StopAfter(1);
    387 
    388   MockRead reads2[] = {
    389     MockRead(ASYNC, 0, 0)  // EOF
    390   };
    391   DeterministicSocketData socket_data2(reads2, arraysize(reads2), NULL, 0);
    392   socket_factory_.AddSocketDataProvider(&socket_data2);
    393   socket_data2.StopAfter(1);
    394 
    395   QuicStreamRequest request(&factory_);
    396   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    397                                             cert_verifier_.get(), net_log_,
    398                                             callback_.callback()));
    399 
    400   EXPECT_EQ(OK, callback_.WaitForResult());
    401   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    402   HttpRequestInfo request_info;
    403   EXPECT_EQ(OK, stream->InitializeStream(&request_info,
    404                                          DEFAULT_PRIORITY,
    405                                          net_log_, CompletionCallback()));
    406 
    407   // Close the session and verify that stream saw the error.
    408   factory_.CloseAllSessions(ERR_INTERNET_DISCONNECTED);
    409   EXPECT_EQ(ERR_INTERNET_DISCONNECTED,
    410             stream->ReadResponseHeaders(callback_.callback()));
    411 
    412   // Now attempting to request a stream to the same origin should create
    413   // a new session.
    414 
    415   QuicStreamRequest request2(&factory_);
    416   EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
    417                                              cert_verifier_.get(), net_log_,
    418                                              callback_.callback()));
    419 
    420   EXPECT_EQ(OK, callback_.WaitForResult());
    421   stream = request2.ReleaseStream();
    422   stream.reset();  // Will reset stream 3.
    423 
    424   EXPECT_TRUE(socket_data.at_read_eof());
    425   EXPECT_TRUE(socket_data.at_write_eof());
    426   EXPECT_TRUE(socket_data2.at_read_eof());
    427   EXPECT_TRUE(socket_data2.at_write_eof());
    428 }
    429 
    430 TEST_F(QuicStreamFactoryTest, OnIPAddressChanged) {
    431   MockRead reads[] = {
    432     MockRead(ASYNC, 0, 0)  // EOF
    433   };
    434   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    435   socket_factory_.AddSocketDataProvider(&socket_data);
    436   socket_data.StopAfter(1);
    437 
    438   MockRead reads2[] = {
    439     MockRead(ASYNC, 0, 0)  // EOF
    440   };
    441   DeterministicSocketData socket_data2(reads2, arraysize(reads2), NULL, 0);
    442   socket_factory_.AddSocketDataProvider(&socket_data2);
    443   socket_data2.StopAfter(1);
    444 
    445   QuicStreamRequest request(&factory_);
    446   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    447                                             cert_verifier_.get(), net_log_,
    448                                             callback_.callback()));
    449 
    450   EXPECT_EQ(OK, callback_.WaitForResult());
    451   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    452   HttpRequestInfo request_info;
    453   EXPECT_EQ(OK, stream->InitializeStream(&request_info,
    454                                          DEFAULT_PRIORITY,
    455                                          net_log_, CompletionCallback()));
    456 
    457   // Change the IP address and verify that stream saw the error.
    458   factory_.OnIPAddressChanged();
    459   EXPECT_EQ(ERR_NETWORK_CHANGED,
    460             stream->ReadResponseHeaders(callback_.callback()));
    461   EXPECT_TRUE(factory_.require_confirmation());
    462 
    463   // Now attempting to request a stream to the same origin should create
    464   // a new session.
    465 
    466   QuicStreamRequest request2(&factory_);
    467   EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
    468                                              cert_verifier_.get(), net_log_,
    469                                              callback_.callback()));
    470 
    471   EXPECT_EQ(OK, callback_.WaitForResult());
    472   stream = request2.ReleaseStream();
    473   stream.reset();  // Will reset stream 3.
    474 
    475   EXPECT_TRUE(socket_data.at_read_eof());
    476   EXPECT_TRUE(socket_data.at_write_eof());
    477   EXPECT_TRUE(socket_data2.at_read_eof());
    478   EXPECT_TRUE(socket_data2.at_write_eof());
    479 }
    480 
    481 TEST_F(QuicStreamFactoryTest, OnCertAdded) {
    482   MockRead reads[] = {
    483     MockRead(ASYNC, 0, 0)  // EOF
    484   };
    485   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    486   socket_factory_.AddSocketDataProvider(&socket_data);
    487   socket_data.StopAfter(1);
    488 
    489   MockRead reads2[] = {
    490     MockRead(ASYNC, 0, 0)  // EOF
    491   };
    492   DeterministicSocketData socket_data2(reads2, arraysize(reads2), NULL, 0);
    493   socket_factory_.AddSocketDataProvider(&socket_data2);
    494   socket_data2.StopAfter(1);
    495 
    496   QuicStreamRequest request(&factory_);
    497   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    498                                             cert_verifier_.get(), net_log_,
    499                                             callback_.callback()));
    500 
    501   EXPECT_EQ(OK, callback_.WaitForResult());
    502   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    503   HttpRequestInfo request_info;
    504   EXPECT_EQ(OK, stream->InitializeStream(&request_info,
    505                                          DEFAULT_PRIORITY,
    506                                          net_log_, CompletionCallback()));
    507 
    508   // Add a cert and verify that stream saw the event.
    509   factory_.OnCertAdded(NULL);
    510   EXPECT_EQ(ERR_CERT_DATABASE_CHANGED,
    511             stream->ReadResponseHeaders(callback_.callback()));
    512   EXPECT_FALSE(factory_.require_confirmation());
    513 
    514   // Now attempting to request a stream to the same origin should create
    515   // a new session.
    516 
    517   QuicStreamRequest request2(&factory_);
    518   EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
    519                                              cert_verifier_.get(), net_log_,
    520                                              callback_.callback()));
    521 
    522   EXPECT_EQ(OK, callback_.WaitForResult());
    523   stream = request2.ReleaseStream();
    524   stream.reset();  // Will reset stream 3.
    525 
    526   EXPECT_TRUE(socket_data.at_read_eof());
    527   EXPECT_TRUE(socket_data.at_write_eof());
    528   EXPECT_TRUE(socket_data2.at_read_eof());
    529   EXPECT_TRUE(socket_data2.at_write_eof());
    530 }
    531 
    532 TEST_F(QuicStreamFactoryTest, OnCACertChanged) {
    533   MockRead reads[] = {
    534     MockRead(ASYNC, 0, 0)  // EOF
    535   };
    536   DeterministicSocketData socket_data(reads, arraysize(reads), NULL, 0);
    537   socket_factory_.AddSocketDataProvider(&socket_data);
    538   socket_data.StopAfter(1);
    539 
    540   MockRead reads2[] = {
    541     MockRead(ASYNC, 0, 0)  // EOF
    542   };
    543   DeterministicSocketData socket_data2(reads2, arraysize(reads2), NULL, 0);
    544   socket_factory_.AddSocketDataProvider(&socket_data2);
    545   socket_data2.StopAfter(1);
    546 
    547   QuicStreamRequest request(&factory_);
    548   EXPECT_EQ(ERR_IO_PENDING, request.Request(host_port_proxy_pair_, is_https_,
    549                                             cert_verifier_.get(), net_log_,
    550                                             callback_.callback()));
    551 
    552   EXPECT_EQ(OK, callback_.WaitForResult());
    553   scoped_ptr<QuicHttpStream> stream = request.ReleaseStream();
    554   HttpRequestInfo request_info;
    555   EXPECT_EQ(OK, stream->InitializeStream(&request_info,
    556                                          DEFAULT_PRIORITY,
    557                                          net_log_, CompletionCallback()));
    558 
    559   // Change the CA cert and verify that stream saw the event.
    560   factory_.OnCACertChanged(NULL);
    561   EXPECT_EQ(ERR_CERT_DATABASE_CHANGED,
    562             stream->ReadResponseHeaders(callback_.callback()));
    563   EXPECT_FALSE(factory_.require_confirmation());
    564 
    565   // Now attempting to request a stream to the same origin should create
    566   // a new session.
    567 
    568   QuicStreamRequest request2(&factory_);
    569   EXPECT_EQ(ERR_IO_PENDING, request2.Request(host_port_proxy_pair_, is_https_,
    570                                              cert_verifier_.get(), net_log_,
    571                                              callback_.callback()));
    572 
    573   EXPECT_EQ(OK, callback_.WaitForResult());
    574   stream = request2.ReleaseStream();
    575   stream.reset();  // Will reset stream 3.
    576 
    577   EXPECT_TRUE(socket_data.at_read_eof());
    578   EXPECT_TRUE(socket_data.at_write_eof());
    579   EXPECT_TRUE(socket_data2.at_read_eof());
    580   EXPECT_TRUE(socket_data2.at_write_eof());
    581 }
    582 
    583 TEST_F(QuicStreamFactoryTest, SharedCryptoConfig) {
    584   vector<string> cannoncial_suffixes;
    585   cannoncial_suffixes.push_back(string(".c.youtube.com"));
    586   cannoncial_suffixes.push_back(string(".googlevideo.com"));
    587 
    588   for (unsigned i = 0; i < cannoncial_suffixes.size(); ++i) {
    589     string r1_host_name("r1");
    590     string r2_host_name("r2");
    591     r1_host_name.append(cannoncial_suffixes[i]);
    592     r2_host_name.append(cannoncial_suffixes[i]);
    593 
    594     HostPortProxyPair host_port_proxy_pair1(HostPortPair(r1_host_name, 80),
    595                                             ProxyServer::Direct());
    596 
    597     QuicCryptoClientConfig* crypto_config1 =
    598         QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
    599                                                        host_port_proxy_pair1);
    600     DCHECK(crypto_config1);
    601     QuicCryptoClientConfig::CachedState* cached1 =
    602         crypto_config1->LookupOrCreate(host_port_proxy_pair1.first.host());
    603     EXPECT_FALSE(cached1->proof_valid());
    604     EXPECT_TRUE(cached1->source_address_token().empty());
    605 
    606     // Mutate the cached1 to have different data.
    607     // TODO(rtenneti): mutate other members of CachedState.
    608     cached1->set_source_address_token(r1_host_name);
    609     cached1->SetProofValid();
    610 
    611     HostPortProxyPair host_port_proxy_pair2(HostPortPair(r2_host_name, 80),
    612                                             ProxyServer::Direct());
    613     QuicCryptoClientConfig* crypto_config2 =
    614         QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
    615                                                        host_port_proxy_pair2);
    616     DCHECK(crypto_config2);
    617     QuicCryptoClientConfig::CachedState* cached2 =
    618         crypto_config2->LookupOrCreate(host_port_proxy_pair2.first.host());
    619     EXPECT_EQ(cached1->source_address_token(), cached2->source_address_token());
    620     EXPECT_TRUE(cached2->proof_valid());
    621   }
    622 }
    623 
    624 TEST_F(QuicStreamFactoryTest, CryptoConfigWhenProofIsInvalid) {
    625   vector<string> cannoncial_suffixes;
    626   cannoncial_suffixes.push_back(string(".c.youtube.com"));
    627   cannoncial_suffixes.push_back(string(".googlevideo.com"));
    628 
    629   for (unsigned i = 0; i < cannoncial_suffixes.size(); ++i) {
    630     string r3_host_name("r3");
    631     string r4_host_name("r4");
    632     r3_host_name.append(cannoncial_suffixes[i]);
    633     r4_host_name.append(cannoncial_suffixes[i]);
    634 
    635     HostPortProxyPair host_port_proxy_pair1(HostPortPair(r3_host_name, 80),
    636                                             ProxyServer::Direct());
    637 
    638     QuicCryptoClientConfig* crypto_config1 =
    639         QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
    640                                                        host_port_proxy_pair1);
    641     DCHECK(crypto_config1);
    642     QuicCryptoClientConfig::CachedState* cached1 =
    643         crypto_config1->LookupOrCreate(host_port_proxy_pair1.first.host());
    644     EXPECT_FALSE(cached1->proof_valid());
    645     EXPECT_TRUE(cached1->source_address_token().empty());
    646 
    647     // Mutate the cached1 to have different data.
    648     // TODO(rtenneti): mutate other members of CachedState.
    649     cached1->set_source_address_token(r3_host_name);
    650     cached1->SetProofInvalid();
    651 
    652     HostPortProxyPair host_port_proxy_pair2(HostPortPair(r4_host_name, 80),
    653                                             ProxyServer::Direct());
    654     QuicCryptoClientConfig* crypto_config2 =
    655         QuicStreamFactoryPeer::GetOrCreateCryptoConfig(&factory_,
    656                                                        host_port_proxy_pair2);
    657     DCHECK(crypto_config2);
    658     QuicCryptoClientConfig::CachedState* cached2 =
    659         crypto_config2->LookupOrCreate(host_port_proxy_pair2.first.host());
    660     EXPECT_NE(cached1->source_address_token(), cached2->source_address_token());
    661     EXPECT_TRUE(cached2->source_address_token().empty());
    662     EXPECT_FALSE(cached2->proof_valid());
    663   }
    664 }
    665 
    666 }  // namespace test
    667 }  // namespace net
    668