OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 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 | 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 "net/quic/quic_headers_stream.h" | 5 #include "net/quic/quic_headers_stream.h" |
6 | 6 |
7 #include <string> | 7 #include <string> |
8 | 8 |
9 #include "base/strings/string_number_conversions.h" | 9 #include "base/strings/string_number_conversions.h" |
10 #include "net/quic/quic_bug_tracker.h" | 10 #include "net/quic/quic_bug_tracker.h" |
(...skipping 19 matching lines...) Expand all Loading... |
30 using testing::_; | 30 using testing::_; |
31 using testing::AtLeast; | 31 using testing::AtLeast; |
32 using testing::HasSubstr; | 32 using testing::HasSubstr; |
33 using testing::InSequence; | 33 using testing::InSequence; |
34 using testing::Invoke; | 34 using testing::Invoke; |
35 using testing::Return; | 35 using testing::Return; |
36 using testing::StrictMock; | 36 using testing::StrictMock; |
37 using testing::WithArgs; | 37 using testing::WithArgs; |
38 using testing::_; | 38 using testing::_; |
39 | 39 |
| 40 // TODO(bnc): Merge these correctly. |
| 41 bool FLAGS_use_http2_frame_decoder_adapter; |
| 42 bool FLAGS_use_nested_spdy_framer_decoder; |
| 43 bool FLAGS_spdy_use_hpack_decoder2; |
| 44 bool FLAGS_spdy_framer_use_new_methods2; |
| 45 |
40 namespace net { | 46 namespace net { |
41 namespace test { | 47 namespace test { |
42 | 48 |
43 class MockHpackDebugVisitor : public QuicHeadersStream::HpackDebugVisitor { | 49 class MockHpackDebugVisitor : public QuicHeadersStream::HpackDebugVisitor { |
44 public: | 50 public: |
45 explicit MockHpackDebugVisitor() : HpackDebugVisitor() {} | 51 explicit MockHpackDebugVisitor() : HpackDebugVisitor() {} |
46 | 52 |
47 MOCK_METHOD1(OnUseEntry, void(QuicTime::Delta elapsed)); | 53 MOCK_METHOD1(OnUseEntry, void(QuicTime::Delta elapsed)); |
48 | 54 |
49 private: | 55 private: |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
131 size_t total_acked_bytes() { return total_acked_bytes_; } | 137 size_t total_acked_bytes() { return total_acked_bytes_; } |
132 | 138 |
133 private: | 139 private: |
134 ~ForceHolAckListener() override {} | 140 ~ForceHolAckListener() override {} |
135 | 141 |
136 size_t total_acked_bytes_; | 142 size_t total_acked_bytes_; |
137 | 143 |
138 DISALLOW_COPY_AND_ASSIGN(ForceHolAckListener); | 144 DISALLOW_COPY_AND_ASSIGN(ForceHolAckListener); |
139 }; | 145 }; |
140 | 146 |
141 // Run all tests with each version, perspective (client or server), | 147 enum Http2DecoderChoice { |
142 // and relevant flag options (false or true) | 148 HTTP2_DECODER_SPDY, |
| 149 HTTP2_DECODER_NESTED_SPDY, |
| 150 HTTP2_DECODER_NEW |
| 151 }; |
| 152 ostream& operator<<(ostream& os, Http2DecoderChoice v) { |
| 153 switch (v) { |
| 154 case HTTP2_DECODER_SPDY: |
| 155 return os << "SPDY"; |
| 156 case HTTP2_DECODER_NESTED_SPDY: |
| 157 return os << "NESTED_SPDY"; |
| 158 case HTTP2_DECODER_NEW: |
| 159 return os << "NEW"; |
| 160 } |
| 161 } |
| 162 |
| 163 enum HpackDecoderChoice { HPACK_DECODER_SPDY, HPACK_DECODER_NEW }; |
| 164 ostream& operator<<(ostream& os, HpackDecoderChoice v) { |
| 165 switch (v) { |
| 166 case HPACK_DECODER_SPDY: |
| 167 return os << "SPDY"; |
| 168 case HPACK_DECODER_NEW: |
| 169 return os << "NEW"; |
| 170 } |
| 171 } |
| 172 |
| 173 typedef std:: |
| 174 tuple<QuicVersion, Perspective, Http2DecoderChoice, HpackDecoderChoice> |
| 175 TestParamsTuple; |
| 176 |
143 struct TestParams { | 177 struct TestParams { |
144 TestParams(QuicVersion version, Perspective perspective) | 178 explicit TestParams(TestParamsTuple params) |
145 : version(version), perspective(perspective) {} | 179 : version(std::get<0>(params)), |
146 | 180 perspective(std::get<1>(params)), |
147 friend ostream& operator<<(ostream& os, const TestParams& p) { | 181 http2_decoder(std::get<2>(params)), |
148 os << "{ version: " << QuicVersionToString(p.version); | 182 hpack_decoder(std::get<3>(params)) { |
149 os << ", perspective: " << p.perspective << " }"; | 183 switch (http2_decoder) { |
150 return os; | 184 case HTTP2_DECODER_SPDY: |
| 185 FLAGS_use_nested_spdy_framer_decoder = false; |
| 186 FLAGS_use_http2_frame_decoder_adapter = false; |
| 187 break; |
| 188 case HTTP2_DECODER_NESTED_SPDY: |
| 189 FLAGS_use_nested_spdy_framer_decoder = true; |
| 190 FLAGS_use_http2_frame_decoder_adapter = false; |
| 191 break; |
| 192 case HTTP2_DECODER_NEW: |
| 193 FLAGS_use_nested_spdy_framer_decoder = false; |
| 194 FLAGS_use_http2_frame_decoder_adapter = true; |
| 195 // Http2FrameDecoderAdapter needs the new header methods, else |
| 196 // --use_http2_frame_decoder_adapter=true will be ignored. |
| 197 FLAGS_spdy_framer_use_new_methods2 = true; |
| 198 break; |
| 199 } |
| 200 switch (hpack_decoder) { |
| 201 case HPACK_DECODER_SPDY: |
| 202 FLAGS_spdy_use_hpack_decoder2 = false; |
| 203 break; |
| 204 case HPACK_DECODER_NEW: |
| 205 FLAGS_spdy_use_hpack_decoder2 = true; |
| 206 // Needs new header methods to be used. |
| 207 FLAGS_spdy_framer_use_new_methods2 = true; |
| 208 break; |
| 209 } |
| 210 FLAGS_quic_supports_push_promise = true; |
| 211 FLAGS_quic_always_log_bugs_for_tests = true; |
| 212 VLOG(1) << "TestParams: version: " << QuicVersionToString(version) |
| 213 << ", perspective: " << perspective |
| 214 << ", http2_decoder: " << http2_decoder |
| 215 << ", hpack_decoder: " << hpack_decoder; |
151 } | 216 } |
152 | 217 |
153 QuicVersion version; | 218 QuicVersion version; |
154 Perspective perspective; | 219 Perspective perspective; |
| 220 Http2DecoderChoice http2_decoder; |
| 221 HpackDecoderChoice hpack_decoder; |
155 }; | 222 }; |
156 | 223 |
157 // Constructs various test permutations. | 224 class QuicHeadersStreamTest : public ::testing::TestWithParam<TestParamsTuple> { |
158 vector<TestParams> GetTestParams() { | |
159 vector<TestParams> params; | |
160 QuicVersionVector all_supported_versions = QuicSupportedVersions(); | |
161 for (const QuicVersion version : all_supported_versions) { | |
162 params.push_back(TestParams(version, Perspective::IS_CLIENT)); | |
163 params.push_back(TestParams(version, Perspective::IS_SERVER)); | |
164 } | |
165 FLAGS_quic_supports_push_promise = true; | |
166 return params; | |
167 } | |
168 | |
169 class QuicHeadersStreamTest : public ::testing::TestWithParam<TestParams> { | |
170 public: | 225 public: |
| 226 // Constructing the test_params_ object will set the necessary flags before |
| 227 // the MockQuicConnection is constructed, which we need because the latter |
| 228 // will construct a SpdyFramer that will use those flags to decide whether |
| 229 // to construct a decoder adapter. |
171 QuicHeadersStreamTest() | 230 QuicHeadersStreamTest() |
172 : connection_(new StrictMock<MockQuicConnection>(&helper_, | 231 : test_params_(GetParam()), |
| 232 connection_(new StrictMock<MockQuicConnection>(&helper_, |
173 &alarm_factory_, | 233 &alarm_factory_, |
174 perspective(), | 234 perspective(), |
175 GetVersion())), | 235 GetVersion())), |
176 session_(connection_), | 236 session_(connection_), |
177 headers_stream_(QuicSpdySessionPeer::GetHeadersStream(&session_)), | 237 headers_stream_(QuicSpdySessionPeer::GetHeadersStream(&session_)), |
178 body_("hello world"), | 238 body_("hello world"), |
179 hpack_encoder_visitor_(new StrictMock<MockHpackDebugVisitor>), | 239 hpack_encoder_visitor_(new StrictMock<MockHpackDebugVisitor>), |
180 hpack_decoder_visitor_(new StrictMock<MockHpackDebugVisitor>), | 240 hpack_decoder_visitor_(new StrictMock<MockHpackDebugVisitor>), |
181 stream_frame_(kHeadersStreamId, /*fin=*/false, /*offset=*/0, ""), | 241 stream_frame_(kHeadersStreamId, /*fin=*/false, /*offset=*/0, ""), |
182 next_promised_stream_id_(2) { | 242 next_promised_stream_id_(2) { |
183 FLAGS_quic_always_log_bugs_for_tests = true; | |
184 headers_[":version"] = "HTTP/1.1"; | 243 headers_[":version"] = "HTTP/1.1"; |
185 headers_[":status"] = "200 Ok"; | 244 headers_[":status"] = "200 Ok"; |
186 headers_["content-length"] = "11"; | 245 headers_["content-length"] = "11"; |
187 framer_ = std::unique_ptr<SpdyFramer>(new SpdyFramer(HTTP2)); | 246 framer_ = std::unique_ptr<SpdyFramer>(new SpdyFramer(HTTP2)); |
188 framer_->set_visitor(&visitor_); | 247 framer_->set_visitor(&visitor_); |
189 EXPECT_EQ(version(), session_.connection()->version()); | 248 EXPECT_EQ(version(), session_.connection()->version()); |
190 EXPECT_TRUE(headers_stream_ != nullptr); | 249 EXPECT_TRUE(headers_stream_ != nullptr); |
191 VLOG(1) << GetParam(); | |
192 connection_->AdvanceTime(QuicTime::Delta::FromMilliseconds(1)); | 250 connection_->AdvanceTime(QuicTime::Delta::FromMilliseconds(1)); |
193 } | 251 } |
194 | 252 |
195 QuicConsumedData SaveIov(const QuicIOVector& data) { | 253 QuicConsumedData SaveIov(const QuicIOVector& data) { |
196 const iovec* iov = data.iov; | 254 const iovec* iov = data.iov; |
197 int count = data.iov_count; | 255 int count = data.iov_count; |
198 int consumed = 0; | 256 int consumed = 0; |
199 for (int i = 0; i < count; ++i) { | 257 for (int i = 0; i < count; ++i) { |
200 saved_data_.append(static_cast<char*>(iov[i].iov_base), iov[i].iov_len); | 258 saved_data_.append(static_cast<char*>(iov[i].iov_base), iov[i].iov_len); |
201 consumed += iov[i].iov_len; | 259 consumed += iov[i].iov_len; |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
298 | 356 |
299 CheckHeaders(); | 357 CheckHeaders(); |
300 saved_data_.clear(); | 358 saved_data_.clear(); |
301 } | 359 } |
302 | 360 |
303 void CheckHeaders() { | 361 void CheckHeaders() { |
304 EXPECT_EQ(headers_, headers_handler_->decoded_block()); | 362 EXPECT_EQ(headers_, headers_handler_->decoded_block()); |
305 headers_handler_.reset(); | 363 headers_handler_.reset(); |
306 } | 364 } |
307 | 365 |
308 Perspective perspective() { return GetParam().perspective; } | 366 Perspective perspective() const { return test_params_.perspective; } |
309 | 367 |
310 QuicVersion version() { return GetParam().version; } | 368 QuicVersion version() const { return test_params_.version; } |
311 | 369 |
312 QuicVersionVector GetVersion() { | 370 QuicVersionVector GetVersion() { |
313 QuicVersionVector versions; | 371 QuicVersionVector versions; |
314 versions.push_back(version()); | 372 versions.push_back(version()); |
315 return versions; | 373 return versions; |
316 } | 374 } |
317 | 375 |
318 void TearDownLocalConnectionState() { | 376 void TearDownLocalConnectionState() { |
319 QuicConnectionPeer::TearDownLocalConnectionState(connection_); | 377 QuicConnectionPeer::TearDownLocalConnectionState(connection_); |
320 } | 378 } |
321 | 379 |
322 QuicStreamId NextPromisedStreamId() { return next_promised_stream_id_ += 2; } | 380 QuicStreamId NextPromisedStreamId() { return next_promised_stream_id_ += 2; } |
323 | 381 |
324 static const bool kFrameComplete = true; | 382 static const bool kFrameComplete = true; |
325 static const bool kHasPriority = true; | 383 static const bool kHasPriority = true; |
326 | 384 |
| 385 const TestParams test_params_; |
327 MockQuicConnectionHelper helper_; | 386 MockQuicConnectionHelper helper_; |
328 MockAlarmFactory alarm_factory_; | 387 MockAlarmFactory alarm_factory_; |
329 StrictMock<MockQuicConnection>* connection_; | 388 StrictMock<MockQuicConnection>* connection_; |
330 StrictMock<MockQuicSpdySession> session_; | 389 StrictMock<MockQuicSpdySession> session_; |
331 QuicHeadersStream* headers_stream_; | 390 QuicHeadersStream* headers_stream_; |
332 SpdyHeaderBlock headers_; | 391 SpdyHeaderBlock headers_; |
333 std::unique_ptr<TestHeadersHandler> headers_handler_; | 392 std::unique_ptr<TestHeadersHandler> headers_handler_; |
334 string body_; | 393 string body_; |
335 string saved_data_; | 394 string saved_data_; |
336 string saved_header_data_; | 395 string saved_header_data_; |
337 string saved_payloads_; | 396 string saved_payloads_; |
338 std::unique_ptr<SpdyFramer> framer_; | 397 std::unique_ptr<SpdyFramer> framer_; |
339 StrictMock<MockVisitor> visitor_; | 398 StrictMock<MockVisitor> visitor_; |
340 std::unique_ptr<StrictMock<MockHpackDebugVisitor>> hpack_encoder_visitor_; | 399 std::unique_ptr<StrictMock<MockHpackDebugVisitor>> hpack_encoder_visitor_; |
341 std::unique_ptr<StrictMock<MockHpackDebugVisitor>> hpack_decoder_visitor_; | 400 std::unique_ptr<StrictMock<MockHpackDebugVisitor>> hpack_decoder_visitor_; |
342 QuicStreamFrame stream_frame_; | 401 QuicStreamFrame stream_frame_; |
343 QuicStreamId next_promised_stream_id_; | 402 QuicStreamId next_promised_stream_id_; |
344 }; | 403 }; |
345 | 404 |
346 INSTANTIATE_TEST_CASE_P(Tests, | 405 // Run all tests with each version, perspective (client or server), |
347 QuicHeadersStreamTest, | 406 // HTTP/2 and HPACK decoder. |
348 ::testing::ValuesIn(GetTestParams())); | 407 INSTANTIATE_TEST_CASE_P( |
| 408 Tests, |
| 409 QuicHeadersStreamTest, |
| 410 ::testing::Combine( |
| 411 ::testing::ValuesIn(QuicSupportedVersions()), |
| 412 ::testing::Values(Perspective::IS_CLIENT, Perspective::IS_SERVER), |
| 413 ::testing::Values(HTTP2_DECODER_SPDY, |
| 414 HTTP2_DECODER_NESTED_SPDY, |
| 415 HTTP2_DECODER_NEW), |
| 416 ::testing::Values(HPACK_DECODER_SPDY, HPACK_DECODER_NEW))); |
349 | 417 |
350 TEST_P(QuicHeadersStreamTest, StreamId) { | 418 TEST_P(QuicHeadersStreamTest, StreamId) { |
351 EXPECT_EQ(3u, headers_stream_->id()); | 419 EXPECT_EQ(3u, headers_stream_->id()); |
352 } | 420 } |
353 | 421 |
354 TEST_P(QuicHeadersStreamTest, WriteHeaders) { | 422 TEST_P(QuicHeadersStreamTest, WriteHeaders) { |
355 for (QuicStreamId stream_id = kClientDataStreamId1; | 423 for (QuicStreamId stream_id = kClientDataStreamId1; |
356 stream_id < kClientDataStreamId3; stream_id += 2) { | 424 stream_id < kClientDataStreamId3; stream_id += 2) { |
357 for (bool fin : kFins) { | 425 for (bool fin : kFins) { |
358 if (perspective() == Perspective::IS_SERVER) { | 426 if (perspective() == Perspective::IS_SERVER) { |
(...skipping 540 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
899 } | 967 } |
900 saved_data_.clear(); | 968 saved_data_.clear(); |
901 saved_payloads_.clear(); | 969 saved_payloads_.clear(); |
902 } | 970 } |
903 } | 971 } |
904 } | 972 } |
905 | 973 |
906 } // namespace | 974 } // namespace |
907 } // namespace test | 975 } // namespace test |
908 } // namespace net | 976 } // namespace net |
OLD | NEW |