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_client_session.h"
      6 
      7 #include <vector>
      8 
      9 #include "net/base/capturing_net_log.h"
     10 #include "net/base/test_completion_callback.h"
     11 #include "net/quic/crypto/aes_128_gcm_12_encrypter.h"
     12 #include "net/quic/crypto/crypto_protocol.h"
     13 #include "net/quic/crypto/quic_decrypter.h"
     14 #include "net/quic/crypto/quic_encrypter.h"
     15 #include "net/quic/test_tools/crypto_test_utils.h"
     16 #include "net/quic/test_tools/quic_client_session_peer.h"
     17 #include "net/quic/test_tools/quic_test_utils.h"
     18 
     19 using testing::_;
     20 
     21 namespace net {
     22 namespace test {
     23 namespace {
     24 
     25 const char kServerHostname[] = "www.example.com";
     26 
     27 class QuicClientSessionTest : public ::testing::Test {
     28  protected:
     29   QuicClientSessionTest()
     30       : guid_(1),
     31         connection_(new PacketSavingConnection(guid_, IPEndPoint(), false)),
     32         session_(connection_, NULL, NULL, NULL, kServerHostname,
     33                  DefaultQuicConfig(), &crypto_config_, &net_log_) {
     34     session_.config()->SetDefaults();
     35     crypto_config_.SetDefaults();
     36   }
     37 
     38   void CompleteCryptoHandshake() {
     39     ASSERT_EQ(ERR_IO_PENDING,
     40               session_.CryptoConnect(callback_.callback()));
     41     CryptoTestUtils::HandshakeWithFakeServer(
     42         connection_, session_.GetCryptoStream());
     43     ASSERT_EQ(OK, callback_.WaitForResult());
     44   }
     45 
     46   QuicGuid guid_;
     47   PacketSavingConnection* connection_;
     48   CapturingNetLog net_log_;
     49   QuicClientSession session_;
     50   MockClock clock_;
     51   MockRandom random_;
     52   QuicConnectionVisitorInterface* visitor_;
     53   TestCompletionCallback callback_;
     54   QuicCryptoClientConfig crypto_config_;
     55 };
     56 
     57 TEST_F(QuicClientSessionTest, CryptoConnect) {
     58   if (!Aes128Gcm12Encrypter::IsSupported()) {
     59     LOG(INFO) << "AES GCM not supported. Test skipped.";
     60     return;
     61   }
     62 
     63   CompleteCryptoHandshake();
     64 }
     65 
     66 TEST_F(QuicClientSessionTest, MaxNumStreams) {
     67   if (!Aes128Gcm12Encrypter::IsSupported()) {
     68     LOG(INFO) << "AES GCM not supported. Test skipped.";
     69     return;
     70   }
     71 
     72   CompleteCryptoHandshake();
     73 
     74   std::vector<QuicReliableClientStream*> streams;
     75   for (size_t i = 0; i < kDefaultMaxStreamsPerConnection; i++) {
     76     QuicReliableClientStream* stream = session_.CreateOutgoingReliableStream();
     77     EXPECT_TRUE(stream);
     78     streams.push_back(stream);
     79   }
     80   EXPECT_FALSE(session_.CreateOutgoingReliableStream());
     81 
     82   // Close a stream and ensure I can now open a new one.
     83   session_.CloseStream(streams[0]->id());
     84   EXPECT_TRUE(session_.CreateOutgoingReliableStream());
     85 }
     86 
     87 TEST_F(QuicClientSessionTest, MaxNumStreamsViaRequest) {
     88   if (!Aes128Gcm12Encrypter::IsSupported()) {
     89     LOG(INFO) << "AES GCM not supported. Test skipped.";
     90     return;
     91   }
     92 
     93   CompleteCryptoHandshake();
     94 
     95   std::vector<QuicReliableClientStream*> streams;
     96   for (size_t i = 0; i < kDefaultMaxStreamsPerConnection; i++) {
     97     QuicReliableClientStream* stream = session_.CreateOutgoingReliableStream();
     98     EXPECT_TRUE(stream);
     99     streams.push_back(stream);
    100   }
    101 
    102   QuicReliableClientStream* stream;
    103   QuicClientSession::StreamRequest stream_request;
    104   TestCompletionCallback callback;
    105   ASSERT_EQ(ERR_IO_PENDING,
    106             stream_request.StartRequest(session_.GetWeakPtr(), &stream,
    107                                         callback.callback()));
    108 
    109   // Close a stream and ensure I can now open a new one.
    110   session_.CloseStream(streams[0]->id());
    111   ASSERT_TRUE(callback.have_result());
    112   EXPECT_EQ(OK, callback.WaitForResult());
    113   EXPECT_TRUE(stream != NULL);
    114 }
    115 
    116 TEST_F(QuicClientSessionTest, GoAwayReceived) {
    117   if (!Aes128Gcm12Encrypter::IsSupported()) {
    118     LOG(INFO) << "AES GCM not supported. Test skipped.";
    119     return;
    120   }
    121 
    122   CompleteCryptoHandshake();
    123 
    124   // After receiving a GoAway, I should no longer be able to create outgoing
    125   // streams.
    126   session_.OnGoAway(QuicGoAwayFrame(QUIC_PEER_GOING_AWAY, 1u, "Going away."));
    127   EXPECT_EQ(NULL, session_.CreateOutgoingReliableStream());
    128 }
    129 
    130 }  // namespace
    131 }  // namespace test
    132 }  // namespace net
    133