Index: net/tools/quic/end_to_end_test.cc |
diff --git a/net/tools/quic/end_to_end_test.cc b/net/tools/quic/end_to_end_test.cc |
index dd1b28be80526d1ed5ac07478ff1e156e860605e..19985a80faab0ce95ce3a77d5b3b661cc843bb42 100644 |
--- a/net/tools/quic/end_to_end_test.cc |
+++ b/net/tools/quic/end_to_end_test.cc |
@@ -23,8 +23,10 @@ |
#include "net/quic/quic_protocol.h" |
#include "net/quic/quic_sent_packet_manager.h" |
#include "net/quic/quic_server_id.h" |
+#include "net/quic/quic_utils.h" |
#include "net/quic/test_tools/quic_connection_peer.h" |
#include "net/quic/test_tools/quic_flow_controller_peer.h" |
+#include "net/quic/test_tools/quic_sent_packet_manager_peer.h" |
#include "net/quic/test_tools/quic_session_peer.h" |
#include "net/quic/test_tools/quic_test_utils.h" |
#include "net/quic/test_tools/reliable_quic_stream_peer.h" |
@@ -52,6 +54,7 @@ using net::EpollServer; |
using net::test::GenerateBody; |
using net::test::QuicConnectionPeer; |
using net::test::QuicFlowControllerPeer; |
+using net::test::QuicSentPacketManagerPeer; |
using net::test::QuicSessionPeer; |
using net::test::ReliableQuicStreamPeer; |
using net::test::ValueRestore; |
@@ -76,11 +79,15 @@ struct TestParams { |
TestParams(const QuicVersionVector& client_supported_versions, |
const QuicVersionVector& server_supported_versions, |
QuicVersion negotiated_version, |
- bool use_pacing) |
+ bool use_pacing, |
+ bool use_fec, |
+ QuicTag congestion_control_tag) |
: client_supported_versions(client_supported_versions), |
server_supported_versions(server_supported_versions), |
negotiated_version(negotiated_version), |
- use_pacing(use_pacing) { |
+ use_pacing(use_pacing), |
+ use_fec(use_fec), |
+ congestion_control_tag(congestion_control_tag) { |
} |
friend ostream& operator<<(ostream& os, const TestParams& p) { |
@@ -89,7 +96,10 @@ struct TestParams { |
os << " client_supported_versions: " |
<< QuicVersionVectorToString(p.client_supported_versions); |
os << " negotiated_version: " << QuicVersionToString(p.negotiated_version); |
- os << " use_pacing: " << p.use_pacing << " }"; |
+ os << " use_pacing: " << p.use_pacing; |
+ os << " use_fec: " << p.use_fec; |
+ os << " congestion_control_tag: " |
+ << QuicUtils::TagToString(p.congestion_control_tag) << " }"; |
return os; |
} |
@@ -97,36 +107,53 @@ struct TestParams { |
QuicVersionVector server_supported_versions; |
QuicVersion negotiated_version; |
bool use_pacing; |
+ bool use_fec; |
+ QuicTag congestion_control_tag; |
}; |
// Constructs various test permutations. |
vector<TestParams> GetTestParams() { |
vector<TestParams> params; |
QuicVersionVector all_supported_versions = QuicSupportedVersions(); |
- for (int use_pacing = 0; use_pacing < 2; ++use_pacing) { |
- // Add an entry for server and client supporting all versions. |
- params.push_back(TestParams(all_supported_versions, |
- all_supported_versions, |
- all_supported_versions[0], |
- use_pacing != 0)); |
- |
- // Test client supporting all versions and server supporting 1 version. |
- // Simulate an old server and exercise version downgrade in the client. |
- // Protocol negotiation should occur. Skip the i = 0 case because it is |
- // essentially the same as the default case. |
- for (size_t i = 1; i < all_supported_versions.size(); ++i) { |
- QuicVersionVector server_supported_versions; |
- server_supported_versions.push_back(all_supported_versions[i]); |
- if (all_supported_versions[i] >= QUIC_VERSION_18) { |
- // Until flow control is globally rolled out and we remove |
- // QUIC_VERSION_16, the server MUST support at least one QUIC version |
- // that does not use flow control. |
- server_supported_versions.push_back(QUIC_VERSION_16); |
+ // TODO(rtenneti): Add kTBBR after BBR code is checked in. |
+ // QuicTag congestion_control_tags[] = {kRENO, kTBBR, kQBIC}; |
+ QuicTag congestion_control_tags[] = {kRENO, kQBIC}; |
+ for (size_t congestion_control_index = 0; |
+ congestion_control_index < arraysize(congestion_control_tags); |
+ congestion_control_index++) { |
+ QuicTag congestion_control_tag = |
+ congestion_control_tags[congestion_control_index]; |
+ for (int use_fec = 0; use_fec < 2; ++use_fec) { |
+ for (int use_pacing = 0; use_pacing < 2; ++use_pacing) { |
+ // Add an entry for server and client supporting all versions. |
+ params.push_back(TestParams(all_supported_versions, |
+ all_supported_versions, |
+ all_supported_versions[0], |
+ use_pacing != 0, |
+ use_fec != 0, |
+ congestion_control_tag)); |
+ |
+ // Test client supporting all versions and server supporting 1 version. |
+ // Simulate an old server and exercise version downgrade in the client. |
+ // Protocol negotiation should occur. Skip the i = 0 case because it is |
+ // essentially the same as the default case. |
+ for (size_t i = 1; i < all_supported_versions.size(); ++i) { |
+ QuicVersionVector server_supported_versions; |
+ server_supported_versions.push_back(all_supported_versions[i]); |
+ if (all_supported_versions[i] >= QUIC_VERSION_18) { |
+ // Until flow control is globally rolled out and we remove |
+ // QUIC_VERSION_16, the server MUST support at least one QUIC |
+ // version that does not use flow control. |
+ server_supported_versions.push_back(QUIC_VERSION_16); |
+ } |
+ params.push_back(TestParams(all_supported_versions, |
+ server_supported_versions, |
+ server_supported_versions[0], |
+ use_pacing != 0, |
+ use_fec != 0, |
+ congestion_control_tag)); |
+ } |
} |
- params.push_back(TestParams(all_supported_versions, |
- server_supported_versions, |
- server_supported_versions[0], |
- use_pacing != 0)); |
} |
} |
return params; |
@@ -168,6 +195,7 @@ class EndToEndTest : public ::testing::TestWithParam<TestParams> { |
server_supported_versions_ = GetParam().server_supported_versions; |
negotiated_version_ = GetParam().negotiated_version; |
FLAGS_enable_quic_pacing = GetParam().use_pacing; |
+ FLAGS_enable_quic_fec = GetParam().use_fec; |
if (negotiated_version_ >= QUIC_VERSION_19) { |
FLAGS_enable_quic_connection_flow_control_2 = true; |
@@ -256,11 +284,36 @@ class EndToEndTest : public ::testing::TestWithParam<TestParams> { |
server_config_.SetInitialSessionFlowControlWindowToSend(window); |
} |
+ const QuicSentPacketManager * |
+ GetSentPacketManagerFromFirstServerSession() const { |
+ QuicDispatcher* dispatcher = |
+ QuicServerPeer::GetDispatcher(server_thread_->server()); |
+ QuicSession* session = dispatcher->session_map().begin()->second; |
+ return &session->connection()->sent_packet_manager(); |
+ } |
+ |
bool Initialize() { |
+ QuicTagVector copt; |
+ |
+ // TODO(nimia): Consider setting the congestion control algorithm for the |
+ // client as well according to the test parameter. |
+ copt.push_back(GetParam().congestion_control_tag); |
+ |
+ if (GetParam().use_fec) { |
+ // Set FEC config in client's connection options and in client session. |
+ copt.push_back(kFHDR); |
+ } |
+ |
+ client_config_.SetConnectionOptionsToSend(copt); |
+ |
// Start the server first, because CreateQuicClient() attempts |
// to connect to the server. |
StartServer(); |
client_.reset(CreateQuicClient(client_writer_)); |
+ if (GetParam().use_fec) { |
+ // Set FecPolicy to always protect data on all streams. |
+ client_->SetFecPolicy(FEC_PROTECT_ALWAYS); |
+ } |
static EpollEvent event(EPOLLOUT, false); |
client_writer_->Initialize( |
reinterpret_cast<QuicEpollConnectionHelper*>( |
@@ -668,69 +721,30 @@ TEST_P(EndToEndTest, DISABLED_LargePostZeroRTTFailure) { |
VerifyCleanConnection(false); |
} |
-TEST_P(EndToEndTest, LargePostFec) { |
- ValueRestore<bool> old_flag(&FLAGS_enable_quic_fec, true); |
- |
- // Connect without packet loss to avoid issues with losing handshake packets, |
- // and then up the packet loss rate (b/10126687). |
- ASSERT_TRUE(Initialize()); |
- |
- // Wait for the server SHLO before upping the packet loss. |
- client_->client()->WaitForCryptoHandshakeConfirmed(); |
- SetPacketLossPercentage(30); |
- |
- // Verify that FEC is enabled. |
- QuicPacketCreator* creator = QuicConnectionPeer::GetPacketCreator( |
- client_->client()->session()->connection()); |
- EXPECT_TRUE(creator->IsFecEnabled()); |
- |
- // Set FecPolicy to always protect data on all streams. |
- client_->SetFecPolicy(FEC_PROTECT_ALWAYS); |
- |
- string body; |
- GenerateBody(&body, 10240); |
- |
- HTTPMessage request(HttpConstants::HTTP_1_1, |
- HttpConstants::POST, "/foo"); |
- request.AddBody(body, true); |
- EXPECT_EQ(kFooResponseBody, client_->SendCustomSynchronousRequest(request)); |
- VerifyCleanConnection(true); |
-} |
- |
-TEST_P(EndToEndTest, ClientSpecifiedFecProtectionForHeaders) { |
- ValueRestore<bool> old_flag(&FLAGS_enable_quic_fec, true); |
- |
- // Set FEC config in client's connection options and in client session. |
- QuicTagVector copt; |
- copt.push_back(kFHDR); |
- client_config_.SetConnectionOptionsToSend(copt); |
- |
- // Connect without packet loss to avoid issues with losing handshake packets, |
- // and then up the packet loss rate (b/10126687). |
+TEST_P(EndToEndTest, CorrectlyConfiguredFec) { |
ASSERT_TRUE(Initialize()); |
client_->client()->WaitForCryptoHandshakeConfirmed(); |
server_thread_->WaitForCryptoHandshakeConfirmed(); |
- // Verify that FEC is enabled. |
- QuicPacketCreator* creator = QuicConnectionPeer::GetPacketCreator( |
- client_->client()->session()->connection()); |
- EXPECT_TRUE(creator->IsFecEnabled()); |
+ FecPolicy expected_policy = |
+ GetParam().use_fec ? FEC_PROTECT_ALWAYS : FEC_PROTECT_OPTIONAL; |
- // Verify that server headers stream is FEC protected. |
+ // Verify that server's FEC configuration is correct. |
server_thread_->Pause(); |
QuicDispatcher* dispatcher = |
QuicServerPeer::GetDispatcher(server_thread_->server()); |
ASSERT_EQ(1u, dispatcher->session_map().size()); |
QuicSession* session = dispatcher->session_map().begin()->second; |
- EXPECT_EQ(FEC_PROTECT_ALWAYS, |
+ EXPECT_EQ(expected_policy, |
QuicSessionPeer::GetHeadersStream(session)->fec_policy()); |
server_thread_->Resume(); |
- // Verify that at the client, headers stream is protected and other data |
- // streams are optionally protected. |
- EXPECT_EQ(FEC_PROTECT_ALWAYS, QuicSessionPeer::GetHeadersStream( |
- client_->client()->session())->fec_policy()); |
- EXPECT_EQ(FEC_PROTECT_OPTIONAL, client_->GetOrCreateStream()->fec_policy()); |
+ // Verify that client's FEC configuration is correct. |
+ EXPECT_EQ(expected_policy, |
+ QuicSessionPeer::GetHeadersStream( |
+ client_->client()->session())->fec_policy()); |
+ EXPECT_EQ(expected_policy, |
+ client_->GetOrCreateStream()->fec_policy()); |
} |
// TODO(shess): This is flaky on ChromiumOS bots. |
@@ -884,6 +898,31 @@ TEST_P(EndToEndTest, NegotiateMaxOpenStreams) { |
EXPECT_EQ(QUIC_TOO_MANY_OPEN_STREAMS, client_->connection_error()); |
} |
+TEST_P(EndToEndTest, NegotiateCongestionControl) { |
+ ASSERT_TRUE(Initialize()); |
+ client_->client()->WaitForCryptoHandshakeConfirmed(); |
+ |
+ CongestionControlType expected_congestion_control_type; |
+ switch (GetParam().congestion_control_tag) { |
+ case kRENO: |
+ expected_congestion_control_type = kReno; |
+ break; |
+ case kTBBR: |
+ expected_congestion_control_type = kBBR; |
+ break; |
+ case kQBIC: |
+ expected_congestion_control_type = kCubic; |
+ break; |
+ default: |
+ DLOG(FATAL) << "Unexpected congestion control tag"; |
+ } |
+ |
+ EXPECT_EQ(expected_congestion_control_type, |
+ QuicSentPacketManagerPeer::GetCongestionControlAlgorithm( |
+ *GetSentPacketManagerFromFirstServerSession()) |
+ ->GetCongestionControlType()); |
+} |
+ |
TEST_P(EndToEndTest, LimitMaxOpenStreams) { |
// Server limits the number of max streams to 2. |
server_config_.set_max_streams_per_connection(2, 2); |
@@ -913,11 +952,10 @@ TEST_P(EndToEndTest, DISABLED_LimitCongestionWindowAndRTT) { |
QuicDispatcher* dispatcher = |
QuicServerPeer::GetDispatcher(server_thread_->server()); |
ASSERT_EQ(1u, dispatcher->session_map().size()); |
- QuicSession* session = dispatcher->session_map().begin()->second; |
const QuicSentPacketManager& client_sent_packet_manager = |
client_->client()->session()->connection()->sent_packet_manager(); |
const QuicSentPacketManager& server_sent_packet_manager = |
- session->connection()->sent_packet_manager(); |
+ *GetSentPacketManagerFromFirstServerSession(); |
// The client shouldn't set it's initial window based on the negotiated value. |
EXPECT_EQ(kDefaultInitialWindow * kDefaultTCPMSS, |
@@ -1110,11 +1148,12 @@ TEST_P(EndToEndTest, ConnectionMigrationClientIPChanged) { |
EXPECT_EQ(kFooResponseBody, client_->SendSynchronousRequest("/foo")); |
EXPECT_EQ(200u, client_->response_headers()->parsed_response_code()); |
- scoped_ptr<WrongAddressWriter> writer(new WrongAddressWriter()); |
+ WrongAddressWriter* writer = new WrongAddressWriter(); |
writer->set_writer(new QuicDefaultPacketWriter(client_->client()->fd())); |
QuicConnectionPeer::SetWriter(client_->client()->session()->connection(), |
- writer.get()); |
+ writer, |
+ true /* owns_writer */); |
client_->SendSynchronousRequest("/bar"); |