| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include <stddef.h> | 5 #include <stddef.h> |
| 6 #include <sys/epoll.h> | 6 #include <sys/epoll.h> |
| 7 | 7 |
| 8 #include <list> | 8 #include <list> |
| 9 #include <memory> | 9 #include <memory> |
| 10 #include <string> | 10 #include <string> |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 92 const float kSessionToStreamRatio = 1.5; | 92 const float kSessionToStreamRatio = 1.5; |
| 93 | 93 |
| 94 // Run all tests with the cross products of all versions. | 94 // Run all tests with the cross products of all versions. |
| 95 struct TestParams { | 95 struct TestParams { |
| 96 TestParams(const QuicVersionVector& client_supported_versions, | 96 TestParams(const QuicVersionVector& client_supported_versions, |
| 97 const QuicVersionVector& server_supported_versions, | 97 const QuicVersionVector& server_supported_versions, |
| 98 QuicVersion negotiated_version, | 98 QuicVersion negotiated_version, |
| 99 bool client_supports_stateless_rejects, | 99 bool client_supports_stateless_rejects, |
| 100 bool server_uses_stateless_rejects_if_peer_supported, | 100 bool server_uses_stateless_rejects_if_peer_supported, |
| 101 QuicTag congestion_control_tag, | 101 QuicTag congestion_control_tag, |
| 102 bool auto_tune_flow_control_window, | |
| 103 bool disable_hpack_dynamic_table, | 102 bool disable_hpack_dynamic_table, |
| 104 bool force_hol_blocking) | 103 bool force_hol_blocking) |
| 105 : client_supported_versions(client_supported_versions), | 104 : client_supported_versions(client_supported_versions), |
| 106 server_supported_versions(server_supported_versions), | 105 server_supported_versions(server_supported_versions), |
| 107 negotiated_version(negotiated_version), | 106 negotiated_version(negotiated_version), |
| 108 client_supports_stateless_rejects(client_supports_stateless_rejects), | 107 client_supports_stateless_rejects(client_supports_stateless_rejects), |
| 109 server_uses_stateless_rejects_if_peer_supported( | 108 server_uses_stateless_rejects_if_peer_supported( |
| 110 server_uses_stateless_rejects_if_peer_supported), | 109 server_uses_stateless_rejects_if_peer_supported), |
| 111 congestion_control_tag(congestion_control_tag), | 110 congestion_control_tag(congestion_control_tag), |
| 112 auto_tune_flow_control_window(auto_tune_flow_control_window), | |
| 113 disable_hpack_dynamic_table(disable_hpack_dynamic_table), | 111 disable_hpack_dynamic_table(disable_hpack_dynamic_table), |
| 114 force_hol_blocking(force_hol_blocking) {} | 112 force_hol_blocking(force_hol_blocking) {} |
| 115 | 113 |
| 116 friend ostream& operator<<(ostream& os, const TestParams& p) { | 114 friend ostream& operator<<(ostream& os, const TestParams& p) { |
| 117 os << "{ server_supported_versions: " | 115 os << "{ server_supported_versions: " |
| 118 << QuicVersionVectorToString(p.server_supported_versions); | 116 << QuicVersionVectorToString(p.server_supported_versions); |
| 119 os << " client_supported_versions: " | 117 os << " client_supported_versions: " |
| 120 << QuicVersionVectorToString(p.client_supported_versions); | 118 << QuicVersionVectorToString(p.client_supported_versions); |
| 121 os << " negotiated_version: " << QuicVersionToString(p.negotiated_version); | 119 os << " negotiated_version: " << QuicVersionToString(p.negotiated_version); |
| 122 os << " client_supports_stateless_rejects: " | 120 os << " client_supports_stateless_rejects: " |
| 123 << p.client_supports_stateless_rejects; | 121 << p.client_supports_stateless_rejects; |
| 124 os << " server_uses_stateless_rejects_if_peer_supported: " | 122 os << " server_uses_stateless_rejects_if_peer_supported: " |
| 125 << p.server_uses_stateless_rejects_if_peer_supported; | 123 << p.server_uses_stateless_rejects_if_peer_supported; |
| 126 os << " congestion_control_tag: " | 124 os << " congestion_control_tag: " |
| 127 << QuicUtils::TagToString(p.congestion_control_tag); | 125 << QuicUtils::TagToString(p.congestion_control_tag); |
| 128 os << " auto_tune_flow_control_window: " << p.auto_tune_flow_control_window; | |
| 129 os << " disable_hpack_dynamic_table: " << p.disable_hpack_dynamic_table; | 126 os << " disable_hpack_dynamic_table: " << p.disable_hpack_dynamic_table; |
| 130 os << " force_hol_blocking: " << p.force_hol_blocking << " }"; | 127 os << " force_hol_blocking: " << p.force_hol_blocking << " }"; |
| 131 return os; | 128 return os; |
| 132 } | 129 } |
| 133 | 130 |
| 134 QuicVersionVector client_supported_versions; | 131 QuicVersionVector client_supported_versions; |
| 135 QuicVersionVector server_supported_versions; | 132 QuicVersionVector server_supported_versions; |
| 136 QuicVersion negotiated_version; | 133 QuicVersion negotiated_version; |
| 137 bool client_supports_stateless_rejects; | 134 bool client_supports_stateless_rejects; |
| 138 bool server_uses_stateless_rejects_if_peer_supported; | 135 bool server_uses_stateless_rejects_if_peer_supported; |
| 139 QuicTag congestion_control_tag; | 136 QuicTag congestion_control_tag; |
| 140 bool auto_tune_flow_control_window; | |
| 141 bool disable_hpack_dynamic_table; | 137 bool disable_hpack_dynamic_table; |
| 142 bool force_hol_blocking; | 138 bool force_hol_blocking; |
| 143 }; | 139 }; |
| 144 | 140 |
| 145 // Constructs various test permutations. | 141 // Constructs various test permutations. |
| 146 vector<TestParams> GetTestParams() { | 142 vector<TestParams> GetTestParams() { |
| 147 // Divide the versions into buckets in which the intra-frame format | 143 // Divide the versions into buckets in which the intra-frame format |
| 148 // is compatible. When clients encounter QUIC version negotiation | 144 // is compatible. When clients encounter QUIC version negotiation |
| 149 // they simply retransmit all packets using the new version's | 145 // they simply retransmit all packets using the new version's |
| 150 // QUIC framing. However, they are unable to change the intra-frame | 146 // QUIC framing. However, they are unable to change the intra-frame |
| (...skipping 20 matching lines...) Expand all Loading... |
| 171 } else { | 167 } else { |
| 172 // Versions: 34+ | 168 // Versions: 34+ |
| 173 // QUIC_VERSION_34 deprecates entropy and uses new ack and stop waiting | 169 // QUIC_VERSION_34 deprecates entropy and uses new ack and stop waiting |
| 174 // wire formats. | 170 // wire formats. |
| 175 version_buckets[3].push_back(version); | 171 version_buckets[3].push_back(version); |
| 176 } | 172 } |
| 177 } | 173 } |
| 178 | 174 |
| 179 // This must be kept in sync with the number of nested for-loops below as it | 175 // This must be kept in sync with the number of nested for-loops below as it |
| 180 // is used to prune the number of tests that are run. | 176 // is used to prune the number of tests that are run. |
| 181 const int kMaxEnabledOptions = 5; | 177 const int kMaxEnabledOptions = 4; |
| 182 int max_enabled_options = 0; | 178 int max_enabled_options = 0; |
| 183 vector<TestParams> params; | 179 vector<TestParams> params; |
| 184 for (bool server_uses_stateless_rejects_if_peer_supported : {true, false}) { | 180 for (bool server_uses_stateless_rejects_if_peer_supported : {true, false}) { |
| 185 for (bool client_supports_stateless_rejects : {true, false}) { | 181 for (bool client_supports_stateless_rejects : {true, false}) { |
| 186 for (const QuicTag congestion_control_tag : {kRENO, kQBIC}) { | 182 for (const QuicTag congestion_control_tag : {kRENO, kQBIC}) { |
| 187 for (bool auto_tune_flow_control_window : {true, false}) { | 183 for (bool disable_hpack_dynamic_table : {false}) { |
| 188 for (bool disable_hpack_dynamic_table : {false}) { | 184 for (bool force_hol_blocking : {true, false}) { |
| 189 for (bool force_hol_blocking : {true, false}) { | 185 int enabled_options = 0; |
| 190 int enabled_options = 0; | 186 if (force_hol_blocking) { |
| 191 if (force_hol_blocking) { | 187 ++enabled_options; |
| 192 ++enabled_options; | 188 } |
| 193 } | 189 if (congestion_control_tag != kQBIC) { |
| 194 if (congestion_control_tag != kQBIC) { | 190 ++enabled_options; |
| 195 ++enabled_options; | 191 } |
| 196 } | 192 if (disable_hpack_dynamic_table) { |
| 197 if (auto_tune_flow_control_window) { | 193 ++enabled_options; |
| 198 ++enabled_options; | 194 } |
| 199 } | 195 if (client_supports_stateless_rejects) { |
| 200 if (disable_hpack_dynamic_table) { | 196 ++enabled_options; |
| 201 ++enabled_options; | 197 } |
| 202 } | 198 if (server_uses_stateless_rejects_if_peer_supported) { |
| 203 if (client_supports_stateless_rejects) { | 199 ++enabled_options; |
| 204 ++enabled_options; | 200 } |
| 205 } | 201 CHECK_GE(kMaxEnabledOptions, enabled_options); |
| 206 if (server_uses_stateless_rejects_if_peer_supported) { | 202 if (enabled_options > max_enabled_options) { |
| 207 ++enabled_options; | 203 max_enabled_options = enabled_options; |
| 208 } | 204 } |
| 209 CHECK_GE(kMaxEnabledOptions, enabled_options); | |
| 210 if (enabled_options > max_enabled_options) { | |
| 211 max_enabled_options = enabled_options; | |
| 212 } | |
| 213 | 205 |
| 214 // Run tests with no options, a single option, or all the options | 206 // Run tests with no options, a single option, or all the options |
| 215 // enabled to avoid a combinatorial explosion. | 207 // enabled to avoid a combinatorial explosion. |
| 216 if (enabled_options > 1 && enabled_options < kMaxEnabledOptions) { | 208 if (enabled_options > 1 && enabled_options < kMaxEnabledOptions) { |
| 209 continue; |
| 210 } |
| 211 |
| 212 for (const QuicVersionVector& client_versions : version_buckets) { |
| 213 CHECK(!client_versions.empty()); |
| 214 // Add an entry for server and client supporting all versions. |
| 215 params.push_back(TestParams( |
| 216 client_versions, all_supported_versions, |
| 217 client_versions.front(), client_supports_stateless_rejects, |
| 218 server_uses_stateless_rejects_if_peer_supported, |
| 219 congestion_control_tag, disable_hpack_dynamic_table, |
| 220 force_hol_blocking)); |
| 221 |
| 222 // Run version negotiation tests tests with no options, or all |
| 223 // the options enabled to avoid a combinatorial explosion. |
| 224 if (enabled_options > 0 && enabled_options < kMaxEnabledOptions) { |
| 217 continue; | 225 continue; |
| 218 } | 226 } |
| 219 | 227 |
| 220 for (const QuicVersionVector& client_versions : version_buckets) { | 228 // Test client supporting all versions and server |
| 221 CHECK(!client_versions.empty()); | 229 // supporting 1 version. Simulate an old server and |
| 222 // Add an entry for server and client supporting all versions. | 230 // exercise version downgrade in the client. Protocol |
| 231 // negotiation should occur. Skip the i = 0 case |
| 232 // because it is essentially the same as the default |
| 233 // case. |
| 234 for (size_t i = 1; i < client_versions.size(); ++i) { |
| 235 QuicVersionVector server_supported_versions; |
| 236 server_supported_versions.push_back(client_versions[i]); |
| 223 params.push_back(TestParams( | 237 params.push_back(TestParams( |
| 224 client_versions, all_supported_versions, | 238 client_versions, server_supported_versions, |
| 225 client_versions.front(), client_supports_stateless_rejects, | 239 server_supported_versions.front(), |
| 240 client_supports_stateless_rejects, |
| 226 server_uses_stateless_rejects_if_peer_supported, | 241 server_uses_stateless_rejects_if_peer_supported, |
| 227 congestion_control_tag, auto_tune_flow_control_window, | 242 congestion_control_tag, disable_hpack_dynamic_table, |
| 228 disable_hpack_dynamic_table, force_hol_blocking)); | 243 force_hol_blocking)); |
| 229 | |
| 230 // Run version negotiation tests tests with no options, or all | |
| 231 // the options enabled to avoid a combinatorial explosion. | |
| 232 if (enabled_options > 0 && | |
| 233 enabled_options < kMaxEnabledOptions) { | |
| 234 continue; | |
| 235 } | |
| 236 | |
| 237 // Test client supporting all versions and server | |
| 238 // supporting 1 version. Simulate an old server and | |
| 239 // exercise version downgrade in the client. Protocol | |
| 240 // negotiation should occur. Skip the i = 0 case | |
| 241 // because it is essentially the same as the default | |
| 242 // case. | |
| 243 for (size_t i = 1; i < client_versions.size(); ++i) { | |
| 244 QuicVersionVector server_supported_versions; | |
| 245 server_supported_versions.push_back(client_versions[i]); | |
| 246 params.push_back(TestParams( | |
| 247 client_versions, server_supported_versions, | |
| 248 server_supported_versions.front(), | |
| 249 client_supports_stateless_rejects, | |
| 250 server_uses_stateless_rejects_if_peer_supported, | |
| 251 congestion_control_tag, auto_tune_flow_control_window, | |
| 252 disable_hpack_dynamic_table, force_hol_blocking)); | |
| 253 } | |
| 254 } | 244 } |
| 255 } | 245 } |
| 256 } | 246 } |
| 257 } | 247 } |
| 258 } | 248 } |
| 259 } | 249 } |
| 260 CHECK_EQ(kMaxEnabledOptions, max_enabled_options); | 250 CHECK_EQ(kMaxEnabledOptions, max_enabled_options); |
| 261 } | 251 } |
| 262 return params; | 252 return params; |
| 263 } | 253 } |
| (...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 392 | 382 |
| 393 // TODO(nimia): Consider setting the congestion control algorithm for the | 383 // TODO(nimia): Consider setting the congestion control algorithm for the |
| 394 // client as well according to the test parameter. | 384 // client as well according to the test parameter. |
| 395 copt.push_back(GetParam().congestion_control_tag); | 385 copt.push_back(GetParam().congestion_control_tag); |
| 396 if (support_server_push_) { | 386 if (support_server_push_) { |
| 397 copt.push_back(kSPSH); | 387 copt.push_back(kSPSH); |
| 398 } | 388 } |
| 399 if (GetParam().client_supports_stateless_rejects) { | 389 if (GetParam().client_supports_stateless_rejects) { |
| 400 copt.push_back(kSREJ); | 390 copt.push_back(kSREJ); |
| 401 } | 391 } |
| 402 if (GetParam().auto_tune_flow_control_window) { | |
| 403 copt.push_back(kAFCW); | |
| 404 copt.push_back(kIFW5); | |
| 405 } | |
| 406 if (GetParam().disable_hpack_dynamic_table) { | 392 if (GetParam().disable_hpack_dynamic_table) { |
| 407 copt.push_back(kDHDT); | 393 copt.push_back(kDHDT); |
| 408 } | 394 } |
| 409 if (GetParam().force_hol_blocking) { | 395 if (GetParam().force_hol_blocking) { |
| 410 client_config_.SetForceHolBlocking(); | 396 client_config_.SetForceHolBlocking(); |
| 411 QuicConfigPeer::SetReceivedForceHolBlocking(&server_config_); | 397 QuicConfigPeer::SetReceivedForceHolBlocking(&server_config_); |
| 412 } | 398 } |
| 413 client_config_.SetConnectionOptionsToSend(copt); | 399 client_config_.SetConnectionOptionsToSend(copt); |
| 414 | 400 |
| 415 // Start the server first, because CreateQuicClient() attempts | 401 // Start the server first, because CreateQuicClient() attempts |
| (...skipping 1199 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1615 | 1601 |
| 1616 TEST_P(EndToEndTest, DifferentFlowControlWindows) { | 1602 TEST_P(EndToEndTest, DifferentFlowControlWindows) { |
| 1617 // Client and server can set different initial flow control receive windows. | 1603 // Client and server can set different initial flow control receive windows. |
| 1618 // These are sent in CHLO/SHLO. Tests that these values are exchanged properly | 1604 // These are sent in CHLO/SHLO. Tests that these values are exchanged properly |
| 1619 // in the crypto handshake. | 1605 // in the crypto handshake. |
| 1620 const uint32_t kClientStreamIFCW = 123456; | 1606 const uint32_t kClientStreamIFCW = 123456; |
| 1621 const uint32_t kClientSessionIFCW = 234567; | 1607 const uint32_t kClientSessionIFCW = 234567; |
| 1622 set_client_initial_stream_flow_control_receive_window(kClientStreamIFCW); | 1608 set_client_initial_stream_flow_control_receive_window(kClientStreamIFCW); |
| 1623 set_client_initial_session_flow_control_receive_window(kClientSessionIFCW); | 1609 set_client_initial_session_flow_control_receive_window(kClientSessionIFCW); |
| 1624 | 1610 |
| 1625 uint32_t kServerStreamIFCW = | 1611 uint32_t kServerStreamIFCW = 32 * 1024; |
| 1626 GetParam().auto_tune_flow_control_window ? 32 * 1024 : 654321; | 1612 uint32_t kServerSessionIFCW = 48 * 1024; |
| 1627 uint32_t kServerSessionIFCW = | |
| 1628 GetParam().auto_tune_flow_control_window ? 48 * 1024 : 765432; | |
| 1629 set_server_initial_stream_flow_control_receive_window(kServerStreamIFCW); | 1613 set_server_initial_stream_flow_control_receive_window(kServerStreamIFCW); |
| 1630 set_server_initial_session_flow_control_receive_window(kServerSessionIFCW); | 1614 set_server_initial_session_flow_control_receive_window(kServerSessionIFCW); |
| 1631 | 1615 |
| 1632 ASSERT_TRUE(Initialize()); | 1616 ASSERT_TRUE(Initialize()); |
| 1633 | 1617 |
| 1634 // Values are exchanged during crypto handshake, so wait for that to finish. | 1618 // Values are exchanged during crypto handshake, so wait for that to finish. |
| 1635 client_->client()->WaitForCryptoHandshakeConfirmed(); | 1619 client_->client()->WaitForCryptoHandshakeConfirmed(); |
| 1636 server_thread_->WaitForCryptoHandshakeConfirmed(); | 1620 server_thread_->WaitForCryptoHandshakeConfirmed(); |
| 1637 | 1621 |
| 1638 // Open a data stream to make sure the stream level flow control is updated. | 1622 // Open a data stream to make sure the stream level flow control is updated. |
| (...skipping 27 matching lines...) Expand all Loading... |
| 1666 EXPECT_EQ(kClientSessionIFCW, | 1650 EXPECT_EQ(kClientSessionIFCW, |
| 1667 session->config()->ReceivedInitialSessionFlowControlWindowBytes()); | 1651 session->config()->ReceivedInitialSessionFlowControlWindowBytes()); |
| 1668 EXPECT_EQ(kClientSessionIFCW, QuicFlowControllerPeer::SendWindowOffset( | 1652 EXPECT_EQ(kClientSessionIFCW, QuicFlowControllerPeer::SendWindowOffset( |
| 1669 session->flow_controller())); | 1653 session->flow_controller())); |
| 1670 server_thread_->Resume(); | 1654 server_thread_->Resume(); |
| 1671 } | 1655 } |
| 1672 | 1656 |
| 1673 TEST_P(EndToEndTest, HeadersAndCryptoStreamsNoConnectionFlowControl) { | 1657 TEST_P(EndToEndTest, HeadersAndCryptoStreamsNoConnectionFlowControl) { |
| 1674 // The special headers and crypto streams should be subject to per-stream flow | 1658 // The special headers and crypto streams should be subject to per-stream flow |
| 1675 // control limits, but should not be subject to connection level flow control | 1659 // control limits, but should not be subject to connection level flow control |
| 1676 const uint32_t kStreamIFCW = | 1660 const uint32_t kStreamIFCW = 32 * 1024; |
| 1677 GetParam().auto_tune_flow_control_window ? 32 * 1024 : 123456; | 1661 const uint32_t kSessionIFCW = 48 * 1024; |
| 1678 const uint32_t kSessionIFCW = | |
| 1679 GetParam().auto_tune_flow_control_window ? 48 * 1024 : 234567; | |
| 1680 set_client_initial_stream_flow_control_receive_window(kStreamIFCW); | 1662 set_client_initial_stream_flow_control_receive_window(kStreamIFCW); |
| 1681 set_client_initial_session_flow_control_receive_window(kSessionIFCW); | 1663 set_client_initial_session_flow_control_receive_window(kSessionIFCW); |
| 1682 set_server_initial_stream_flow_control_receive_window(kStreamIFCW); | 1664 set_server_initial_stream_flow_control_receive_window(kStreamIFCW); |
| 1683 set_server_initial_session_flow_control_receive_window(kSessionIFCW); | 1665 set_server_initial_session_flow_control_receive_window(kSessionIFCW); |
| 1684 | 1666 |
| 1685 ASSERT_TRUE(Initialize()); | 1667 ASSERT_TRUE(Initialize()); |
| 1686 | 1668 |
| 1687 // Wait for crypto handshake to finish. This should have contributed to the | 1669 // Wait for crypto handshake to finish. This should have contributed to the |
| 1688 // crypto stream flow control window, but not affected the session flow | 1670 // crypto stream flow control window, but not affected the session flow |
| 1689 // control window. | 1671 // control window. |
| (...skipping 1112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2802 client_->WaitForResponse(); | 2784 client_->WaitForResponse(); |
| 2803 // TODO(fayang): Fix this test to work with stateless rejects. | 2785 // TODO(fayang): Fix this test to work with stateless rejects. |
| 2804 if (!BothSidesSupportStatelessRejects()) { | 2786 if (!BothSidesSupportStatelessRejects()) { |
| 2805 VerifyCleanConnection(true); | 2787 VerifyCleanConnection(true); |
| 2806 } | 2788 } |
| 2807 } | 2789 } |
| 2808 | 2790 |
| 2809 } // namespace | 2791 } // namespace |
| 2810 } // namespace test | 2792 } // namespace test |
| 2811 } // namespace net | 2793 } // namespace net |
| OLD | NEW |