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 "net/spdy/spdy_framer.h" | 5 #include "net/spdy/spdy_framer.h" |
6 | 6 |
7 #include <stdlib.h> | 7 #include <stdlib.h> |
8 #include <string.h> | 8 #include <string.h> |
9 | 9 |
10 #include <algorithm> | 10 #include <algorithm> |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
53 public: | 53 public: |
54 // Decompress a single frame using the decompression context held by | 54 // Decompress a single frame using the decompression context held by |
55 // the SpdyFramer. The implemention is meant for use only in tests | 55 // the SpdyFramer. The implemention is meant for use only in tests |
56 // and will CHECK fail if the input is anything other than a single, | 56 // and will CHECK fail if the input is anything other than a single, |
57 // well-formed compressed frame. | 57 // well-formed compressed frame. |
58 // | 58 // |
59 // Returns a new decompressed SpdySerializedFrame. | 59 // Returns a new decompressed SpdySerializedFrame. |
60 template <class SpdyFrameType> | 60 template <class SpdyFrameType> |
61 static SpdySerializedFrame DecompressFrame(SpdyFramer* framer, | 61 static SpdySerializedFrame DecompressFrame(SpdyFramer* framer, |
62 const SpdyFrameType& frame) { | 62 const SpdyFrameType& frame) { |
63 DecompressionVisitor visitor(framer->protocol_version()); | 63 NewDecompressionVisitor visitor; |
64 framer->set_visitor(&visitor); | 64 framer->set_visitor(&visitor); |
65 CHECK_EQ(frame.size(), framer->ProcessInput(frame.data(), frame.size())); | 65 CHECK_EQ(frame.size(), framer->ProcessInput(frame.data(), frame.size())); |
66 CHECK_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer->state()); | 66 CHECK_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer->state()); |
67 framer->set_visitor(NULL); | 67 framer->set_visitor(nullptr); |
| 68 SpdyFramer serializer(framer->protocol_version()); |
| 69 serializer.set_enable_compression(false); |
| 70 return serializer.SerializeFrame(visitor.GetFrame()); |
| 71 } |
68 | 72 |
69 char* buffer = visitor.ReleaseBuffer(); | 73 class NewDecompressionVisitor : public SpdyFramerVisitorInterface { |
70 CHECK(buffer != NULL); | 74 public: |
71 SpdySerializedFrame decompressed_frame(buffer, visitor.size(), true); | 75 NewDecompressionVisitor() : finished_(false) {} |
72 SetFrameLength(&decompressed_frame, | 76 |
73 visitor.size() - framer->GetControlFrameHeaderSize(), | 77 const SpdyFrameIR& GetFrame() const { |
74 framer->protocol_version()); | 78 CHECK(finished_); |
75 return decompressed_frame; | 79 return *frame_; |
76 } | 80 } |
| 81 |
| 82 SpdyHeadersHandlerInterface* OnHeaderFrameStart( |
| 83 SpdyStreamId stream_id) override { |
| 84 if (headers_handler_ == nullptr) { |
| 85 headers_handler_.reset(new TestHeadersHandler); |
| 86 } |
| 87 return headers_handler_.get(); |
| 88 } |
| 89 |
| 90 void OnHeaderFrameEnd(SpdyStreamId stream_id, bool end_headers) override { |
| 91 CHECK(!finished_); |
| 92 frame_->set_header_block(headers_handler_->decoded_block()); |
| 93 finished_ = true; |
| 94 if (end_headers) { |
| 95 headers_handler_.reset(); |
| 96 } |
| 97 } |
| 98 |
| 99 void OnSynStream(SpdyStreamId stream_id, |
| 100 SpdyStreamId associated_stream_id, |
| 101 SpdyPriority priority, |
| 102 bool fin, |
| 103 bool unidirectional) override { |
| 104 SpdySynStreamIR* syn_stream = new SpdySynStreamIR(stream_id); |
| 105 syn_stream->set_associated_to_stream_id(associated_stream_id); |
| 106 syn_stream->set_priority(priority); |
| 107 syn_stream->set_fin(fin); |
| 108 syn_stream->set_unidirectional(unidirectional); |
| 109 frame_.reset(syn_stream); |
| 110 } |
| 111 |
| 112 void OnSynReply(SpdyStreamId stream_id, bool fin) override { |
| 113 SpdyHeadersIR* headers = new SpdyHeadersIR(stream_id); |
| 114 headers->set_fin(fin); |
| 115 frame_.reset(headers); |
| 116 } |
| 117 |
| 118 void OnHeaders(SpdyStreamId stream_id, |
| 119 bool has_priority, |
| 120 SpdyPriority priority, |
| 121 SpdyStreamId parent_stream_id, |
| 122 bool exclusive, |
| 123 bool fin, |
| 124 bool end) override { |
| 125 SpdyHeadersIR* headers = new SpdyHeadersIR(stream_id); |
| 126 headers->set_has_priority(has_priority); |
| 127 headers->set_priority(priority); |
| 128 headers->set_parent_stream_id(parent_stream_id); |
| 129 headers->set_exclusive(exclusive); |
| 130 headers->set_fin(fin); |
| 131 frame_.reset(headers); |
| 132 } |
| 133 |
| 134 void OnPushPromise(SpdyStreamId stream_id, |
| 135 SpdyStreamId promised_stream_id, |
| 136 bool end) override { |
| 137 SpdyPushPromiseIR* push_promise = |
| 138 new SpdyPushPromiseIR(stream_id, promised_stream_id); |
| 139 frame_.reset(push_promise); |
| 140 } |
| 141 |
| 142 // TODO(birenroy): Add support for CONTINUATION. |
| 143 void OnContinuation(SpdyStreamId stream_id, bool end) override { |
| 144 LOG(FATAL); |
| 145 } |
| 146 |
| 147 // All other methods just LOG(FATAL). |
| 148 void OnError(SpdyFramer* framer) override { LOG(FATAL); } |
| 149 void OnDataFrameHeader(SpdyStreamId stream_id, |
| 150 size_t length, |
| 151 bool fin) override { |
| 152 LOG(FATAL) << "Unexpected data frame header"; |
| 153 } |
| 154 void OnStreamFrameData(SpdyStreamId stream_id, |
| 155 const char* data, |
| 156 size_t len) override { |
| 157 LOG(FATAL); |
| 158 } |
| 159 |
| 160 void OnStreamEnd(SpdyStreamId stream_id) override { LOG(FATAL); } |
| 161 |
| 162 void OnStreamPadding(SpdyStreamId stream_id, size_t len) override { |
| 163 LOG(FATAL); |
| 164 } |
| 165 |
| 166 bool OnControlFrameHeaderData(SpdyStreamId stream_id, |
| 167 const char* header_data, |
| 168 size_t len) override { |
| 169 LOG(FATAL); |
| 170 return true; |
| 171 } |
| 172 |
| 173 void OnRstStream(SpdyStreamId stream_id, |
| 174 SpdyRstStreamStatus status) override { |
| 175 LOG(FATAL); |
| 176 } |
| 177 void OnSetting(SpdySettingsIds id, uint8_t flags, uint32_t value) override { |
| 178 LOG(FATAL); |
| 179 } |
| 180 void OnPing(SpdyPingId unique_id, bool is_ack) override { LOG(FATAL); } |
| 181 void OnSettingsEnd() override { LOG(FATAL); } |
| 182 void OnGoAway(SpdyStreamId last_accepted_stream_id, |
| 183 SpdyGoAwayStatus status) override { |
| 184 LOG(FATAL); |
| 185 } |
| 186 |
| 187 void OnWindowUpdate(SpdyStreamId stream_id, |
| 188 int delta_window_size) override { |
| 189 LOG(FATAL); |
| 190 } |
| 191 |
| 192 void OnPriority(SpdyStreamId stream_id, |
| 193 SpdyStreamId parent_stream_id, |
| 194 uint8_t weight, |
| 195 bool exclusive) override { |
| 196 // Do nothing. |
| 197 } |
| 198 |
| 199 bool OnUnknownFrame(SpdyStreamId stream_id, int frame_type) override { |
| 200 LOG(FATAL); |
| 201 return false; |
| 202 } |
| 203 |
| 204 private: |
| 205 std::unique_ptr<TestHeadersHandler> headers_handler_; |
| 206 std::unique_ptr<SpdyFrameWithHeaderBlockIR> frame_; |
| 207 bool finished_; |
| 208 |
| 209 DISALLOW_COPY_AND_ASSIGN(NewDecompressionVisitor); |
| 210 }; |
77 | 211 |
78 class DecompressionVisitor : public SpdyFramerVisitorInterface { | 212 class DecompressionVisitor : public SpdyFramerVisitorInterface { |
79 public: | 213 public: |
80 explicit DecompressionVisitor(SpdyMajorVersion version) | 214 explicit DecompressionVisitor(SpdyMajorVersion version) |
81 : version_(version), size_(0), finished_(false) {} | 215 : version_(version), size_(0), finished_(false) {} |
82 | 216 |
83 void ResetBuffer() { | 217 void ResetBuffer() { |
84 CHECK(buffer_.get() == NULL); | 218 CHECK(buffer_.get() == NULL); |
85 CHECK_EQ(0u, size_); | 219 CHECK_EQ(0u, size_); |
86 CHECK(!finished_); | 220 CHECK(!finished_); |
(...skipping 13 matching lines...) Expand all Loading... |
100 } | 234 } |
101 | 235 |
102 void OnStreamEnd(SpdyStreamId stream_id) override { LOG(FATAL); } | 236 void OnStreamEnd(SpdyStreamId stream_id) override { LOG(FATAL); } |
103 | 237 |
104 void OnStreamPadding(SpdyStreamId stream_id, size_t len) override { | 238 void OnStreamPadding(SpdyStreamId stream_id, size_t len) override { |
105 LOG(FATAL); | 239 LOG(FATAL); |
106 } | 240 } |
107 | 241 |
108 SpdyHeadersHandlerInterface* OnHeaderFrameStart( | 242 SpdyHeadersHandlerInterface* OnHeaderFrameStart( |
109 SpdyStreamId stream_id) override { | 243 SpdyStreamId stream_id) override { |
110 LOG(FATAL); | 244 LOG(FATAL) << "Not implemented."; |
111 return nullptr; | 245 return nullptr; |
112 } | 246 } |
113 | 247 |
114 void OnHeaderFrameEnd(SpdyStreamId stream_id, bool end_headers) override { | 248 void OnHeaderFrameEnd(SpdyStreamId stream_id, bool end_headers) override { |
115 LOG(FATAL); | 249 LOG(FATAL) << "Not implemented."; |
116 } | 250 } |
117 | 251 |
118 bool OnControlFrameHeaderData(SpdyStreamId stream_id, | 252 bool OnControlFrameHeaderData(SpdyStreamId stream_id, |
119 const char* header_data, | 253 const char* header_data, |
120 size_t len) override { | 254 size_t len) override { |
121 CHECK(buffer_.get() != NULL); | 255 CHECK(buffer_.get() != NULL); |
122 CHECK_GE(kMaxDecompressedSize, size_ + len); | 256 CHECK_GE(kMaxDecompressedSize, size_ + len); |
123 CHECK(!finished_); | 257 CHECK(!finished_); |
124 if (len != 0) { | 258 if (len != 0) { |
125 memcpy(buffer_.get() + size_, header_data, len); | 259 memcpy(buffer_.get() + size_, header_data, len); |
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
233 return buffer_.release(); | 367 return buffer_.release(); |
234 } | 368 } |
235 | 369 |
236 size_t size() const { | 370 size_t size() const { |
237 CHECK(finished_); | 371 CHECK(finished_); |
238 return size_; | 372 return size_; |
239 } | 373 } |
240 | 374 |
241 private: | 375 private: |
242 SpdyMajorVersion version_; | 376 SpdyMajorVersion version_; |
| 377 TestHeadersHandler* headers_handler_; |
243 std::unique_ptr<char[]> buffer_; | 378 std::unique_ptr<char[]> buffer_; |
244 size_t size_; | 379 size_t size_; |
245 bool finished_; | 380 bool finished_; |
246 | 381 |
247 DISALLOW_COPY_AND_ASSIGN(DecompressionVisitor); | 382 DISALLOW_COPY_AND_ASSIGN(DecompressionVisitor); |
248 }; | 383 }; |
249 | 384 |
250 private: | 385 private: |
251 DISALLOW_COPY_AND_ASSIGN(SpdyFramerTestUtil); | 386 DISALLOW_COPY_AND_ASSIGN(SpdyFramerTestUtil); |
252 }; | 387 }; |
253 | 388 |
| 389 class SpdyFramerPeer { |
| 390 public: |
| 391 static size_t ControlFrameBufferSize() { |
| 392 return SpdyFramer::kControlFrameBufferSize; |
| 393 } |
| 394 static size_t GetNumberRequiredContinuationFrames(SpdyFramer* framer, |
| 395 size_t size) { |
| 396 return framer->GetNumberRequiredContinuationFrames(size); |
| 397 } |
| 398 static void SetError(SpdyFramer* framer, SpdyFramer::SpdyError error) { |
| 399 framer->set_error(error); |
| 400 } |
| 401 }; |
| 402 |
254 class TestSpdyVisitor : public SpdyFramerVisitorInterface, | 403 class TestSpdyVisitor : public SpdyFramerVisitorInterface, |
255 public SpdyFramerDebugVisitorInterface { | 404 public SpdyFramerDebugVisitorInterface { |
256 public: | 405 public: |
257 // This is larger than our max frame size because header blocks that | 406 // This is larger than our max frame size because header blocks that |
258 // are too long can spill over into CONTINUATION frames. | 407 // are too long can spill over into CONTINUATION frames. |
259 static const size_t kDefaultHeaderBufferSize = 16 * 1024 * 1024; | 408 static const size_t kDefaultHeaderBufferSize = 16 * 1024 * 1024; |
260 | 409 |
261 explicit TestSpdyVisitor(SpdyMajorVersion version) | 410 explicit TestSpdyVisitor(SpdyMajorVersion version) |
262 : framer_(version), | 411 : framer_(version), |
263 use_compression_(false), | 412 use_compression_(false), |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
328 } | 477 } |
329 | 478 |
330 void OnStreamPadding(SpdyStreamId stream_id, size_t len) override { | 479 void OnStreamPadding(SpdyStreamId stream_id, size_t len) override { |
331 VLOG(1) << "OnStreamPadding(" << stream_id << ", " << len << ")\n"; | 480 VLOG(1) << "OnStreamPadding(" << stream_id << ", " << len << ")\n"; |
332 EXPECT_EQ(header_stream_id_, stream_id); | 481 EXPECT_EQ(header_stream_id_, stream_id); |
333 data_bytes_ += len; | 482 data_bytes_ += len; |
334 } | 483 } |
335 | 484 |
336 SpdyHeadersHandlerInterface* OnHeaderFrameStart( | 485 SpdyHeadersHandlerInterface* OnHeaderFrameStart( |
337 SpdyStreamId stream_id) override { | 486 SpdyStreamId stream_id) override { |
338 LOG(FATAL) << "OnHeaderFrameStart(" << stream_id << ")"; | 487 if (headers_handler_ == nullptr) { |
339 return nullptr; | 488 headers_handler_.reset(new TestHeadersHandler); |
| 489 } |
| 490 return headers_handler_.get(); |
340 } | 491 } |
341 | 492 |
342 void OnHeaderFrameEnd(SpdyStreamId stream_id, bool end_headers) override { | 493 void OnHeaderFrameEnd(SpdyStreamId stream_id, bool end_headers) override { |
343 LOG(FATAL) << "OnHeaderFrameEnd(" << stream_id << ", " << end_headers | 494 CHECK(headers_handler_ != nullptr); |
344 << ")"; | 495 headers_ = headers_handler_->decoded_block(); |
| 496 header_bytes_received_ = headers_handler_->header_bytes_parsed(); |
| 497 if (end_headers) { |
| 498 headers_handler_.reset(); |
| 499 } |
345 } | 500 } |
346 | 501 |
347 bool OnControlFrameHeaderData(SpdyStreamId stream_id, | 502 bool OnControlFrameHeaderData(SpdyStreamId stream_id, |
348 const char* header_data, | 503 const char* header_data, |
349 size_t len) override { | 504 size_t len) override { |
350 VLOG(1) << "OnControlFrameHeaderData(" << stream_id << ", data, " << len | 505 VLOG(1) << "OnControlFrameHeaderData(" << stream_id << ", data, " << len |
351 << ")"; | 506 << ")"; |
352 ++control_frame_header_data_count_; | 507 ++control_frame_header_data_count_; |
353 CHECK_EQ(header_stream_id_, stream_id); | 508 CHECK_EQ(header_stream_id_, stream_id); |
354 if (len == 0) { | 509 if (len == 0) { |
(...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
624 // The count of zero-length control frame header data chunks received. | 779 // The count of zero-length control frame header data chunks received. |
625 int zero_length_control_frame_header_data_count_; | 780 int zero_length_control_frame_header_data_count_; |
626 int data_frame_count_; | 781 int data_frame_count_; |
627 size_t last_payload_len_; | 782 size_t last_payload_len_; |
628 size_t last_frame_len_; | 783 size_t last_frame_len_; |
629 | 784 |
630 // Header block streaming state: | 785 // Header block streaming state: |
631 std::unique_ptr<char[]> header_buffer_; | 786 std::unique_ptr<char[]> header_buffer_; |
632 size_t header_buffer_length_; | 787 size_t header_buffer_length_; |
633 size_t header_buffer_size_; | 788 size_t header_buffer_size_; |
| 789 size_t header_bytes_received_; |
634 SpdyStreamId header_stream_id_; | 790 SpdyStreamId header_stream_id_; |
635 SpdyFrameType header_control_type_; | 791 SpdyFrameType header_control_type_; |
636 bool header_buffer_valid_; | 792 bool header_buffer_valid_; |
| 793 std::unique_ptr<TestHeadersHandler> headers_handler_; |
637 SpdyHeaderBlock headers_; | 794 SpdyHeaderBlock headers_; |
638 bool header_has_priority_; | 795 bool header_has_priority_; |
639 SpdyStreamId header_parent_stream_id_; | 796 SpdyStreamId header_parent_stream_id_; |
640 bool header_exclusive_; | 797 bool header_exclusive_; |
641 }; | 798 }; |
642 | 799 |
643 class SpdyFramerPeer { | |
644 public: | |
645 static size_t ControlFrameBufferSize() { | |
646 return SpdyFramer::kControlFrameBufferSize; | |
647 } | |
648 static size_t GetNumberRequiredContinuationFrames(SpdyFramer* framer, | |
649 size_t size) { | |
650 return framer->GetNumberRequiredContinuationFrames(size); | |
651 } | |
652 }; | |
653 | |
654 // Retrieves serialized headers from a HEADERS or SYN_STREAM frame. | 800 // Retrieves serialized headers from a HEADERS or SYN_STREAM frame. |
655 StringPiece GetSerializedHeaders(const SpdySerializedFrame& frame, | 801 StringPiece GetSerializedHeaders(const SpdySerializedFrame& frame, |
656 const SpdyFramer& framer) { | 802 const SpdyFramer& framer) { |
657 SpdyFrameReader reader(frame.data(), frame.size()); | 803 SpdyFrameReader reader(frame.data(), frame.size()); |
658 if (framer.protocol_version() == SPDY3) { | 804 if (framer.protocol_version() == SPDY3) { |
659 reader.Seek(2); // Seek past the frame length. | 805 reader.Seek(2); // Seek past the frame length. |
660 } else { | 806 } else { |
661 reader.Seek(3); // Seek past the frame length. | 807 reader.Seek(3); // Seek past the frame length. |
662 } | 808 } |
663 SpdyFrameType frame_type; | 809 SpdyFrameType frame_type; |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
741 headers.set_priority(1); | 887 headers.set_priority(1); |
742 headers.SetHeader("cookie", | 888 headers.SetHeader("cookie", |
743 "=; key=value; ; = ; foo; bar=; ; = ; k2=v2 ; ="); | 889 "=; key=value; ; = ; foo; bar=; ; = ; k2=v2 ; ="); |
744 SpdySerializedFrame frame(framer.SerializeHeaders(headers)); | 890 SpdySerializedFrame frame(framer.SerializeHeaders(headers)); |
745 | 891 |
746 TestSpdyVisitor visitor(spdy_version_); | 892 TestSpdyVisitor visitor(spdy_version_); |
747 visitor.use_compression_ = true; | 893 visitor.use_compression_ = true; |
748 visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()), | 894 visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()), |
749 frame.size()); | 895 frame.size()); |
750 | 896 |
751 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 897 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
752 EXPECT_NE(headers.header_block(), visitor.headers_); | 898 EXPECT_NE(headers.header_block(), visitor.headers_); |
753 EXPECT_EQ(1u, visitor.headers_.size()); | 899 EXPECT_EQ(1u, visitor.headers_.size()); |
754 EXPECT_EQ("key=value; foo; bar=; k2=v2 ", visitor.headers_["cookie"]); | 900 EXPECT_EQ("key=value; foo; bar=; k2=v2 ", visitor.headers_["cookie"]); |
755 } | 901 } |
756 | 902 |
757 // Test that we can encode and decode a SpdyHeaderBlock in serialized form. | 903 // Test that we can encode and decode a SpdyHeaderBlock in serialized form. |
758 TEST_P(SpdyFramerTest, HeaderBlockInBuffer) { | 904 TEST_P(SpdyFramerTest, HeaderBlockInBuffer) { |
759 SpdyFramer framer(spdy_version_); | 905 SpdyFramer framer(spdy_version_); |
760 framer.set_enable_compression(false); | 906 framer.set_enable_compression(false); |
761 | 907 |
762 // Encode the header block into a Headers frame. | 908 // Encode the header block into a Headers frame. |
763 SpdyHeadersIR headers(1); | 909 SpdyHeadersIR headers(1); |
764 headers.set_priority(1); | 910 headers.set_priority(1); |
765 headers.SetHeader("alpha", "beta"); | 911 headers.SetHeader("alpha", "beta"); |
766 headers.SetHeader("gamma", "charlie"); | 912 headers.SetHeader("gamma", "charlie"); |
767 headers.SetHeader("cookie", "key1=value1; key2=value2"); | 913 headers.SetHeader("cookie", "key1=value1; key2=value2"); |
768 SpdySerializedFrame frame(framer.SerializeHeaders(headers)); | 914 SpdySerializedFrame frame(framer.SerializeHeaders(headers)); |
769 | 915 |
770 TestSpdyVisitor visitor(spdy_version_); | 916 TestSpdyVisitor visitor(spdy_version_); |
771 visitor.use_compression_ = false; | 917 visitor.use_compression_ = false; |
772 visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()), | 918 visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()), |
773 frame.size()); | 919 frame.size()); |
774 | 920 |
775 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 921 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
776 EXPECT_EQ(headers.header_block(), visitor.headers_); | 922 EXPECT_EQ(headers.header_block(), visitor.headers_); |
777 } | 923 } |
778 | 924 |
779 // Test that if there's not a full frame, we fail to parse it. | 925 // Test that if there's not a full frame, we fail to parse it. |
780 TEST_P(SpdyFramerTest, UndersizedHeaderBlockInBuffer) { | 926 TEST_P(SpdyFramerTest, UndersizedHeaderBlockInBuffer) { |
781 SpdyFramer framer(spdy_version_); | 927 SpdyFramer framer(spdy_version_); |
782 framer.set_enable_compression(false); | 928 framer.set_enable_compression(false); |
783 | 929 |
784 // Encode the header block into a Headers frame. | 930 // Encode the header block into a Headers frame. |
785 SpdyHeadersIR headers(1); | 931 SpdyHeadersIR headers(1); |
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
928 0x08, // Flags (PADDED) | 1074 0x08, // Flags (PADDED) |
929 0x00, 0x00, 0x00, 0x01, // Stream id | 1075 0x00, 0x00, 0x00, 0x01, // Stream id |
930 0xFF, // Padding length (here larger than length) | 1076 0xFF, // Padding length (here larger than length) |
931 0x00, 0x00, 0x00, 0x00, // Arbitrary data payload | 1077 0x00, 0x00, 0x00, 0x00, // Arbitrary data payload |
932 }; | 1078 }; |
933 | 1079 |
934 SpdySerializedFrame frame(reinterpret_cast<char*>(kH2FrameData), | 1080 SpdySerializedFrame frame(reinterpret_cast<char*>(kH2FrameData), |
935 sizeof(kH2FrameData), false); | 1081 sizeof(kH2FrameData), false); |
936 | 1082 |
937 EXPECT_CALL(visitor, OnHeaders(1, false, 0, 0, false, false, false)); | 1083 EXPECT_CALL(visitor, OnHeaders(1, false, 0, 0, false, false, false)); |
| 1084 EXPECT_CALL(visitor, OnHeaderFrameStart(1)).Times(1); |
938 EXPECT_CALL(visitor, OnError(testing::Eq(&framer))); | 1085 EXPECT_CALL(visitor, OnError(testing::Eq(&framer))); |
939 EXPECT_EQ(frame.size(), framer.ProcessInput(frame.data(), frame.size())); | 1086 EXPECT_EQ(frame.size(), framer.ProcessInput(frame.data(), frame.size())); |
940 EXPECT_TRUE(framer.HasError()); | 1087 EXPECT_TRUE(framer.HasError()); |
941 EXPECT_EQ(SpdyFramer::SPDY_INVALID_PADDING, framer.error_code()) | 1088 EXPECT_EQ(SpdyFramer::SPDY_INVALID_PADDING, framer.error_code()) |
942 << SpdyFramer::ErrorCodeToString(framer.error_code()); | 1089 << SpdyFramer::ErrorCodeToString(framer.error_code()); |
943 } | 1090 } |
944 | 1091 |
945 // Test that if we receive a HEADERS frame with padding length not larger | 1092 // Test that if we receive a HEADERS frame with padding length not larger |
946 // than the payload length, we do not set an error of SPDY_INVALID_PADDING | 1093 // than the payload length, we do not set an error of SPDY_INVALID_PADDING |
947 TEST_P(SpdyFramerTest, CorrectlySizedHeadersPaddingNoError) { | 1094 TEST_P(SpdyFramerTest, CorrectlySizedHeadersPaddingNoError) { |
(...skipping 11 matching lines...) Expand all Loading... |
959 0x01, // Type (HEADERS) | 1106 0x01, // Type (HEADERS) |
960 0x08, // Flags (PADDED) | 1107 0x08, // Flags (PADDED) |
961 0x00, 0x00, 0x00, 0x01, // Stream id | 1108 0x00, 0x00, 0x00, 0x01, // Stream id |
962 0x04, // Padding length | 1109 0x04, // Padding length |
963 0x00, 0x00, 0x00, 0x00, // Padding | 1110 0x00, 0x00, 0x00, 0x00, // Padding |
964 }; | 1111 }; |
965 | 1112 |
966 SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false); | 1113 SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false); |
967 | 1114 |
968 EXPECT_CALL(visitor, OnHeaders(1, false, 0, 0, false, false, false)); | 1115 EXPECT_CALL(visitor, OnHeaders(1, false, 0, 0, false, false, false)); |
969 | 1116 EXPECT_CALL(visitor, OnHeaderFrameStart(1)).Times(1); |
970 EXPECT_EQ(frame.size(), framer.ProcessInput(frame.data(), frame.size())); | 1117 EXPECT_EQ(frame.size(), framer.ProcessInput(frame.data(), frame.size())); |
971 EXPECT_FALSE(framer.HasError()); | 1118 EXPECT_FALSE(framer.HasError()); |
972 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) | 1119 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) |
973 << SpdyFramer::ErrorCodeToString(framer.error_code()); | 1120 << SpdyFramer::ErrorCodeToString(framer.error_code()); |
974 } | 1121 } |
975 | 1122 |
976 // Test that if we receive a SYN_REPLY with stream ID zero, we signal an error | 1123 // Test that if we receive a SYN_REPLY with stream ID zero, we signal an error |
977 // (but don't crash). | 1124 // (but don't crash). |
978 TEST_P(SpdyFramerTest, SynReplyWithStreamIdZero) { | 1125 TEST_P(SpdyFramerTest, SynReplyWithStreamIdZero) { |
979 if (!IsSpdy3()) { | 1126 if (!IsSpdy3()) { |
(...skipping 2524 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3504 headers_ir.SetHeader("alpha", "beta"); | 3651 headers_ir.SetHeader("alpha", "beta"); |
3505 headers_ir.SetHeader("gamma", "delta"); | 3652 headers_ir.SetHeader("gamma", "delta"); |
3506 SpdyHeaderBlock headers = headers_ir.header_block(); | 3653 SpdyHeaderBlock headers = headers_ir.header_block(); |
3507 SpdySerializedFrame control_frame(framer.SerializeHeaders(headers_ir)); | 3654 SpdySerializedFrame control_frame(framer.SerializeHeaders(headers_ir)); |
3508 TestSpdyVisitor visitor(spdy_version_); | 3655 TestSpdyVisitor visitor(spdy_version_); |
3509 visitor.use_compression_ = true; | 3656 visitor.use_compression_ = true; |
3510 visitor.SimulateInFramer( | 3657 visitor.SimulateInFramer( |
3511 reinterpret_cast<unsigned char*>(control_frame.data()), | 3658 reinterpret_cast<unsigned char*>(control_frame.data()), |
3512 control_frame.size()); | 3659 control_frame.size()); |
3513 EXPECT_EQ(1, visitor.headers_frame_count_); | 3660 EXPECT_EQ(1, visitor.headers_frame_count_); |
3514 // control_frame_header_data_count_ depends on the random sequence | 3661 EXPECT_EQ(0, visitor.control_frame_header_data_count_); |
3515 // produced by rand(), so adding, removing or running single tests | 3662 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
3516 // alters this value. The best we can do is assert that it happens | |
3517 // at least twice. | |
3518 EXPECT_LE(2, visitor.control_frame_header_data_count_); | |
3519 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | |
3520 EXPECT_EQ(0, visitor.end_of_stream_count_); | 3663 EXPECT_EQ(0, visitor.end_of_stream_count_); |
3521 EXPECT_EQ(headers, visitor.headers_); | 3664 EXPECT_EQ(headers, visitor.headers_); |
3522 } | 3665 } |
3523 | 3666 |
3524 TEST_P(SpdyFramerTest, ReadCompressedHeadersHeaderBlockWithHalfClose) { | 3667 TEST_P(SpdyFramerTest, ReadCompressedHeadersHeaderBlockWithHalfClose) { |
3525 SpdyFramer framer(spdy_version_); | 3668 SpdyFramer framer(spdy_version_); |
3526 SpdyHeadersIR headers_ir(1); | 3669 SpdyHeadersIR headers_ir(1); |
3527 headers_ir.set_fin(true); | 3670 headers_ir.set_fin(true); |
3528 headers_ir.SetHeader("alpha", "beta"); | 3671 headers_ir.SetHeader("alpha", "beta"); |
3529 headers_ir.SetHeader("gamma", "delta"); | 3672 headers_ir.SetHeader("gamma", "delta"); |
3530 SpdyHeaderBlock headers = headers_ir.header_block(); | 3673 SpdyHeaderBlock headers = headers_ir.header_block(); |
3531 SpdySerializedFrame control_frame(framer.SerializeHeaders(headers_ir)); | 3674 SpdySerializedFrame control_frame(framer.SerializeHeaders(headers_ir)); |
3532 TestSpdyVisitor visitor(spdy_version_); | 3675 TestSpdyVisitor visitor(spdy_version_); |
3533 visitor.use_compression_ = true; | 3676 visitor.use_compression_ = true; |
3534 visitor.SimulateInFramer( | 3677 visitor.SimulateInFramer( |
3535 reinterpret_cast<unsigned char*>(control_frame.data()), | 3678 reinterpret_cast<unsigned char*>(control_frame.data()), |
3536 control_frame.size()); | 3679 control_frame.size()); |
3537 EXPECT_EQ(1, visitor.headers_frame_count_); | 3680 EXPECT_EQ(1, visitor.headers_frame_count_); |
3538 // control_frame_header_data_count_ depends on the random sequence | 3681 EXPECT_EQ(0, visitor.control_frame_header_data_count_); |
3539 // produced by rand(), so adding, removing or running single tests | 3682 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
3540 // alters this value. The best we can do is assert that it happens | |
3541 // at least twice. | |
3542 EXPECT_LE(2, visitor.control_frame_header_data_count_); | |
3543 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | |
3544 EXPECT_EQ(1, visitor.end_of_stream_count_); | 3683 EXPECT_EQ(1, visitor.end_of_stream_count_); |
3545 EXPECT_EQ(headers, visitor.headers_); | 3684 EXPECT_EQ(headers, visitor.headers_); |
3546 } | 3685 } |
3547 | 3686 |
3548 TEST_P(SpdyFramerTest, ControlFrameAtMaxSizeLimit) { | 3687 TEST_P(SpdyFramerTest, ControlFrameAtMaxSizeLimit) { |
3549 if (!IsSpdy3()) { | 3688 if (!IsSpdy3()) { |
3550 // TODO(jgraettinger): This test setup doesn't work with HPACK. | 3689 // TODO(jgraettinger): This test setup doesn't work with HPACK. |
3551 return; | 3690 return; |
3552 } | 3691 } |
3553 | 3692 |
(...skipping 15 matching lines...) Expand all Loading... |
3569 EXPECT_EQ(TestSpdyVisitor::sent_control_frame_max_size(), | 3708 EXPECT_EQ(TestSpdyVisitor::sent_control_frame_max_size(), |
3570 control_frame.size()); | 3709 control_frame.size()); |
3571 | 3710 |
3572 TestSpdyVisitor visitor(spdy_version_); | 3711 TestSpdyVisitor visitor(spdy_version_); |
3573 visitor.SimulateInFramer( | 3712 visitor.SimulateInFramer( |
3574 reinterpret_cast<unsigned char*>(control_frame.data()), | 3713 reinterpret_cast<unsigned char*>(control_frame.data()), |
3575 control_frame.size()); | 3714 control_frame.size()); |
3576 EXPECT_TRUE(visitor.header_buffer_valid_); | 3715 EXPECT_TRUE(visitor.header_buffer_valid_); |
3577 EXPECT_EQ(0, visitor.error_count_); | 3716 EXPECT_EQ(0, visitor.error_count_); |
3578 EXPECT_EQ(1, visitor.syn_frame_count_); | 3717 EXPECT_EQ(1, visitor.syn_frame_count_); |
3579 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 3718 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
3580 EXPECT_EQ(0, visitor.end_of_stream_count_); | 3719 EXPECT_EQ(0, visitor.end_of_stream_count_); |
3581 EXPECT_LT(kBigValueSize, visitor.header_buffer_length_); | |
3582 } | 3720 } |
3583 | 3721 |
3584 TEST_P(SpdyFramerTest, ControlFrameTooLarge) { | 3722 TEST_P(SpdyFramerTest, ControlFrameTooLarge) { |
3585 if (!IsSpdy3()) { | 3723 if (!IsSpdy3()) { |
3586 // TODO(jgraettinger): This test setup doesn't work with HPACK. | 3724 // TODO(jgraettinger): This test setup doesn't work with HPACK. |
3587 return; | 3725 return; |
3588 } | 3726 } |
3589 | 3727 |
3590 // First find the size of the header value in order to just reach the control | 3728 // First find the size of the header value in order to just reach the control |
3591 // frame max size. | 3729 // frame max size. |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3646 TestSpdyVisitor::sent_control_frame_max_size()); | 3784 TestSpdyVisitor::sent_control_frame_max_size()); |
3647 | 3785 |
3648 TestSpdyVisitor visitor(spdy_version_); | 3786 TestSpdyVisitor visitor(spdy_version_); |
3649 visitor.SimulateInFramer( | 3787 visitor.SimulateInFramer( |
3650 reinterpret_cast<unsigned char*>(control_frame.data()), | 3788 reinterpret_cast<unsigned char*>(control_frame.data()), |
3651 control_frame.size()); | 3789 control_frame.size()); |
3652 EXPECT_TRUE(visitor.header_buffer_valid_); | 3790 EXPECT_TRUE(visitor.header_buffer_valid_); |
3653 EXPECT_EQ(0, visitor.error_count_); | 3791 EXPECT_EQ(0, visitor.error_count_); |
3654 EXPECT_EQ(1, visitor.headers_frame_count_); | 3792 EXPECT_EQ(1, visitor.headers_frame_count_); |
3655 EXPECT_EQ(1, visitor.continuation_count_); | 3793 EXPECT_EQ(1, visitor.continuation_count_); |
3656 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 3794 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
3657 } | 3795 } |
3658 | 3796 |
3659 TEST_P(SpdyFramerTest, TooLargePushPromiseFrameUsesContinuation) { | 3797 TEST_P(SpdyFramerTest, TooLargePushPromiseFrameUsesContinuation) { |
3660 if (!IsHttp2()) { | 3798 if (!IsHttp2()) { |
3661 return; | 3799 return; |
3662 } | 3800 } |
3663 | 3801 |
3664 SpdyFramer framer(spdy_version_); | 3802 SpdyFramer framer(spdy_version_); |
3665 framer.set_enable_compression(false); | 3803 framer.set_enable_compression(false); |
3666 SpdyPushPromiseIR push_promise(1, 2); | 3804 SpdyPushPromiseIR push_promise(1, 2); |
3667 push_promise.set_padding_len(256); | 3805 push_promise.set_padding_len(256); |
3668 | 3806 |
3669 // Exact payload length will change with HPACK, but this should be long | 3807 // Exact payload length will change with HPACK, but this should be long |
3670 // enough to cause an overflow. | 3808 // enough to cause an overflow. |
3671 const size_t kBigValueSize = TestSpdyVisitor::sent_control_frame_max_size(); | 3809 const size_t kBigValueSize = TestSpdyVisitor::sent_control_frame_max_size(); |
3672 string big_value(kBigValueSize, 'x'); | 3810 string big_value(kBigValueSize, 'x'); |
3673 push_promise.SetHeader("aa", big_value); | 3811 push_promise.SetHeader("aa", big_value); |
3674 SpdySerializedFrame control_frame(framer.SerializePushPromise(push_promise)); | 3812 SpdySerializedFrame control_frame(framer.SerializePushPromise(push_promise)); |
3675 EXPECT_GT(control_frame.size(), | 3813 EXPECT_GT(control_frame.size(), |
3676 TestSpdyVisitor::sent_control_frame_max_size()); | 3814 TestSpdyVisitor::sent_control_frame_max_size()); |
3677 | 3815 |
3678 TestSpdyVisitor visitor(spdy_version_); | 3816 TestSpdyVisitor visitor(spdy_version_); |
3679 visitor.SimulateInFramer( | 3817 visitor.SimulateInFramer( |
3680 reinterpret_cast<unsigned char*>(control_frame.data()), | 3818 reinterpret_cast<unsigned char*>(control_frame.data()), |
3681 control_frame.size()); | 3819 control_frame.size()); |
3682 EXPECT_TRUE(visitor.header_buffer_valid_); | 3820 EXPECT_TRUE(visitor.header_buffer_valid_); |
3683 EXPECT_EQ(0, visitor.error_count_); | 3821 EXPECT_EQ(0, visitor.error_count_); |
3684 EXPECT_EQ(1, visitor.push_promise_frame_count_); | 3822 EXPECT_EQ(1, visitor.push_promise_frame_count_); |
3685 EXPECT_EQ(1, visitor.continuation_count_); | 3823 EXPECT_EQ(1, visitor.continuation_count_); |
3686 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 3824 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
3687 } | 3825 } |
3688 | 3826 |
3689 // Check that the framer stops delivering header data chunks once the visitor | 3827 // Check that the framer stops delivering header data chunks once the visitor |
3690 // declares it doesn't want any more. This is important to guard against | 3828 // declares it doesn't want any more. This is important to guard against |
3691 // "zip bomb" types of attacks. | 3829 // "zip bomb" types of attacks. |
3692 TEST_P(SpdyFramerTest, ControlFrameMuchTooLarge) { | 3830 TEST_P(SpdyFramerTest, ControlFrameMuchTooLarge) { |
3693 const size_t kHeaderBufferChunks = 4; | 3831 const size_t kHeaderBufferChunks = 4; |
3694 const size_t kHeaderBufferSize = | 3832 const size_t kHeaderBufferSize = |
3695 TestSpdyVisitor::header_data_chunk_max_size() * kHeaderBufferChunks; | 3833 TestSpdyVisitor::header_data_chunk_max_size() * kHeaderBufferChunks; |
3696 const size_t kBigValueSize = kHeaderBufferSize * 2; | 3834 const size_t kBigValueSize = kHeaderBufferSize * 2; |
3697 string big_value(kBigValueSize, 'x'); | 3835 string big_value(kBigValueSize, 'x'); |
3698 SpdyFramer framer(spdy_version_); | 3836 SpdyFramer framer(spdy_version_); |
3699 SpdyHeadersIR headers(1); | 3837 SpdyHeadersIR headers(1); |
3700 headers.set_priority(1); | 3838 headers.set_priority(1); |
3701 headers.set_fin(true); | 3839 headers.set_fin(true); |
3702 headers.SetHeader("aa", big_value); | 3840 headers.SetHeader("aa", big_value); |
3703 SpdySerializedFrame control_frame(framer.SerializeHeaders(headers)); | 3841 SpdySerializedFrame control_frame(framer.SerializeHeaders(headers)); |
3704 TestSpdyVisitor visitor(spdy_version_); | 3842 TestSpdyVisitor visitor(spdy_version_); |
3705 visitor.set_header_buffer_size(kHeaderBufferSize); | 3843 visitor.set_header_buffer_size(kHeaderBufferSize); |
3706 visitor.use_compression_ = true; | 3844 visitor.use_compression_ = true; |
3707 visitor.SimulateInFramer( | 3845 visitor.SimulateInFramer( |
3708 reinterpret_cast<unsigned char*>(control_frame.data()), | 3846 reinterpret_cast<unsigned char*>(control_frame.data()), |
3709 control_frame.size()); | 3847 control_frame.size()); |
3710 EXPECT_FALSE(visitor.header_buffer_valid_); | 3848 // It's up to the visitor to ignore extraneous header data; the framer |
3711 EXPECT_EQ(1, visitor.error_count_); | 3849 // won't throw an error. |
3712 EXPECT_EQ(SpdyFramer::SPDY_CONTROL_PAYLOAD_TOO_LARGE, | 3850 EXPECT_GT(visitor.header_bytes_received_, visitor.header_buffer_size_); |
3713 visitor.framer_.error_code()) | 3851 EXPECT_EQ(1, visitor.end_of_stream_count_); |
3714 << SpdyFramer::ErrorCodeToString(visitor.framer_.error_code()); | |
3715 | |
3716 // The framer should have stoped delivering chunks after the visitor | |
3717 // signaled "stop" by returning false from OnControlFrameHeaderData(). | |
3718 // | |
3719 // control_frame_header_data_count_ depends on the random sequence | |
3720 // produced by rand(), so adding, removing or running single tests | |
3721 // alters this value. The best we can do is assert that it happens | |
3722 // at least kHeaderBufferChunks + 1. | |
3723 EXPECT_LE(kHeaderBufferChunks + 1, | |
3724 static_cast<unsigned>(visitor.control_frame_header_data_count_)); | |
3725 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); | |
3726 | |
3727 // The framer should not have sent half-close to the visitor. | |
3728 EXPECT_EQ(0, visitor.end_of_stream_count_); | |
3729 } | 3852 } |
3730 | 3853 |
3731 TEST_P(SpdyFramerTest, DecompressCorruptHeaderBlock) { | 3854 TEST_P(SpdyFramerTest, DecompressCorruptHeaderBlock) { |
3732 if (!IsSpdy3()) { | 3855 if (!IsSpdy3()) { |
3733 // Deflate compression doesn't apply to HPACK. | 3856 // Deflate compression doesn't apply to HPACK. |
3734 return; | 3857 return; |
3735 } | 3858 } |
3736 | 3859 |
3737 SpdyFramer framer(spdy_version_); | 3860 SpdyFramer framer(spdy_version_); |
3738 framer.set_enable_compression(false); | 3861 framer.set_enable_compression(false); |
(...skipping 433 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4172 }; | 4295 }; |
4173 | 4296 |
4174 SpdyFramer framer(spdy_version_); | 4297 SpdyFramer framer(spdy_version_); |
4175 TestSpdyVisitor visitor(spdy_version_); | 4298 TestSpdyVisitor visitor(spdy_version_); |
4176 visitor.SimulateInFramer(kInput, sizeof(kInput)); | 4299 visitor.SimulateInFramer(kInput, sizeof(kInput)); |
4177 | 4300 |
4178 EXPECT_EQ(0, visitor.error_count_); | 4301 EXPECT_EQ(0, visitor.error_count_); |
4179 EXPECT_EQ(1, visitor.headers_frame_count_); | 4302 EXPECT_EQ(1, visitor.headers_frame_count_); |
4180 EXPECT_EQ(2, visitor.continuation_count_); | 4303 EXPECT_EQ(2, visitor.continuation_count_); |
4181 EXPECT_EQ(1, visitor.fin_flag_count_); | 4304 EXPECT_EQ(1, visitor.fin_flag_count_); |
4182 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 4305 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
4183 EXPECT_EQ(1, visitor.end_of_stream_count_); | 4306 EXPECT_EQ(1, visitor.end_of_stream_count_); |
4184 | 4307 |
4185 EXPECT_THAT(visitor.headers_, | 4308 EXPECT_THAT(visitor.headers_, |
4186 testing::ElementsAre( | 4309 testing::ElementsAre( |
4187 testing::Pair("cookie", "foo=bar; baz=bing; "), | 4310 testing::Pair("cookie", "foo=bar; baz=bing; "), |
4188 testing::Pair("name", "value"))); | 4311 testing::Pair("name", "value"))); |
4189 } | 4312 } |
4190 | 4313 |
4191 TEST_P(SpdyFramerTest, ReadPushPromiseWithContinuation) { | 4314 TEST_P(SpdyFramerTest, ReadPushPromiseWithContinuation) { |
4192 if (!IsHttp2()) { | 4315 if (!IsHttp2()) { |
(...skipping 29 matching lines...) Expand all Loading... |
4222 }; | 4345 }; |
4223 | 4346 |
4224 SpdyFramer framer(spdy_version_); | 4347 SpdyFramer framer(spdy_version_); |
4225 TestSpdyVisitor visitor(spdy_version_); | 4348 TestSpdyVisitor visitor(spdy_version_); |
4226 visitor.SimulateInFramer(kInput, sizeof(kInput)); | 4349 visitor.SimulateInFramer(kInput, sizeof(kInput)); |
4227 | 4350 |
4228 EXPECT_EQ(0, visitor.error_count_); | 4351 EXPECT_EQ(0, visitor.error_count_); |
4229 EXPECT_EQ(1u, visitor.last_push_promise_stream_); | 4352 EXPECT_EQ(1u, visitor.last_push_promise_stream_); |
4230 EXPECT_EQ(42u, visitor.last_push_promise_promised_stream_); | 4353 EXPECT_EQ(42u, visitor.last_push_promise_promised_stream_); |
4231 EXPECT_EQ(2, visitor.continuation_count_); | 4354 EXPECT_EQ(2, visitor.continuation_count_); |
4232 EXPECT_EQ(1, visitor.zero_length_control_frame_header_data_count_); | 4355 EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_); |
4233 EXPECT_EQ(0, visitor.end_of_stream_count_); | 4356 EXPECT_EQ(0, visitor.end_of_stream_count_); |
4234 | 4357 |
4235 EXPECT_THAT(visitor.headers_, | 4358 EXPECT_THAT(visitor.headers_, |
4236 testing::ElementsAre( | 4359 testing::ElementsAre( |
4237 testing::Pair("cookie", "foo=bar; baz=bing; "), | 4360 testing::Pair("cookie", "foo=bar; baz=bing; "), |
4238 testing::Pair("name", "value"))); | 4361 testing::Pair("name", "value"))); |
4239 } | 4362 } |
4240 | 4363 |
4241 // Receiving an unknown frame when a continuation is expected should | 4364 // Receiving an unknown frame when a continuation is expected should |
4242 // result in a SPDY_UNEXPECTED_FRAME error | 4365 // result in a SPDY_UNEXPECTED_FRAME error |
(...skipping 586 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4829 syn_stream.SetHeader("foo", "bar"); | 4952 syn_stream.SetHeader("foo", "bar"); |
4830 SpdySerializedFrame frame(framer.SerializeSynStream(syn_stream)); | 4953 SpdySerializedFrame frame(framer.SerializeSynStream(syn_stream)); |
4831 SetFrameFlags(&frame, flags, spdy_version_); | 4954 SetFrameFlags(&frame, flags, spdy_version_); |
4832 | 4955 |
4833 if (flags & ~(CONTROL_FLAG_FIN | CONTROL_FLAG_UNIDIRECTIONAL)) { | 4956 if (flags & ~(CONTROL_FLAG_FIN | CONTROL_FLAG_UNIDIRECTIONAL)) { |
4834 EXPECT_CALL(visitor, OnError(_)); | 4957 EXPECT_CALL(visitor, OnError(_)); |
4835 } else { | 4958 } else { |
4836 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(8, SYN_STREAM, _)); | 4959 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(8, SYN_STREAM, _)); |
4837 EXPECT_CALL(visitor, OnSynStream(8, 3, 1, flags & CONTROL_FLAG_FIN, | 4960 EXPECT_CALL(visitor, OnSynStream(8, 3, 1, flags & CONTROL_FLAG_FIN, |
4838 flags & CONTROL_FLAG_UNIDIRECTIONAL)); | 4961 flags & CONTROL_FLAG_UNIDIRECTIONAL)); |
4839 EXPECT_CALL(visitor, OnControlFrameHeaderData(8, _, _)) | 4962 EXPECT_CALL(visitor, OnHeaderFrameStart(8)).Times(1); |
4840 .WillRepeatedly(testing::Return(true)); | 4963 EXPECT_CALL(visitor, OnHeaderFrameEnd(8, _)).Times(1); |
4841 if (flags & DATA_FLAG_FIN) { | 4964 if (flags & DATA_FLAG_FIN) { |
4842 EXPECT_CALL(visitor, OnStreamEnd(_)); | 4965 EXPECT_CALL(visitor, OnStreamEnd(_)); |
4843 } else { | 4966 } else { |
4844 // Do not close the stream if we are expecting a CONTINUATION frame. | 4967 // Do not close the stream if we are expecting a CONTINUATION frame. |
4845 EXPECT_CALL(visitor, OnStreamEnd(_)).Times(0); | 4968 EXPECT_CALL(visitor, OnStreamEnd(_)).Times(0); |
4846 } | 4969 } |
4847 } | 4970 } |
4848 | 4971 |
4849 framer.ProcessInput(frame.data(), frame.size()); | 4972 framer.ProcessInput(frame.data(), frame.size()); |
4850 if (flags & ~(CONTROL_FLAG_FIN | CONTROL_FLAG_UNIDIRECTIONAL)) { | 4973 if (flags & ~(CONTROL_FLAG_FIN | CONTROL_FLAG_UNIDIRECTIONAL)) { |
(...skipping 25 matching lines...) Expand all Loading... |
4876 | 4999 |
4877 SpdySynReplyIR syn_reply(37); | 5000 SpdySynReplyIR syn_reply(37); |
4878 syn_reply.SetHeader("foo", "bar"); | 5001 syn_reply.SetHeader("foo", "bar"); |
4879 SpdySerializedFrame frame(framer.SerializeSynReply(syn_reply)); | 5002 SpdySerializedFrame frame(framer.SerializeSynReply(syn_reply)); |
4880 SetFrameFlags(&frame, flags, spdy_version_); | 5003 SetFrameFlags(&frame, flags, spdy_version_); |
4881 | 5004 |
4882 if (flags & ~CONTROL_FLAG_FIN) { | 5005 if (flags & ~CONTROL_FLAG_FIN) { |
4883 EXPECT_CALL(visitor, OnError(_)); | 5006 EXPECT_CALL(visitor, OnError(_)); |
4884 } else { | 5007 } else { |
4885 EXPECT_CALL(visitor, OnSynReply(37, flags & CONTROL_FLAG_FIN)); | 5008 EXPECT_CALL(visitor, OnSynReply(37, flags & CONTROL_FLAG_FIN)); |
4886 EXPECT_CALL(visitor, OnControlFrameHeaderData(37, _, _)) | 5009 EXPECT_CALL(visitor, OnHeaderFrameStart(37)).Times(1); |
4887 .WillRepeatedly(testing::Return(true)); | 5010 EXPECT_CALL(visitor, OnHeaderFrameEnd(37, _)).Times(1); |
4888 if (flags & DATA_FLAG_FIN) { | 5011 if (flags & DATA_FLAG_FIN) { |
4889 EXPECT_CALL(visitor, OnStreamEnd(_)); | 5012 EXPECT_CALL(visitor, OnStreamEnd(_)); |
4890 } | 5013 } |
4891 } | 5014 } |
4892 | 5015 |
4893 framer.ProcessInput(frame.data(), frame.size()); | 5016 framer.ProcessInput(frame.data(), frame.size()); |
4894 if (flags & ~CONTROL_FLAG_FIN) { | 5017 if (flags & ~CONTROL_FLAG_FIN) { |
4895 EXPECT_EQ(SpdyFramer::SPDY_ERROR, framer.state()); | 5018 EXPECT_EQ(SpdyFramer::SPDY_ERROR, framer.state()); |
4896 EXPECT_EQ(SpdyFramer::SPDY_INVALID_CONTROL_FRAME_FLAGS, | 5019 EXPECT_EQ(SpdyFramer::SPDY_INVALID_CONTROL_FRAME_FLAGS, |
4897 framer.error_code()) | 5020 framer.error_code()) |
(...skipping 177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5075 bool fin = flags & CONTROL_FLAG_FIN; | 5198 bool fin = flags & CONTROL_FLAG_FIN; |
5076 bool end = IsSpdy3() || (flags & HEADERS_FLAG_END_HEADERS); | 5199 bool end = IsSpdy3() || (flags & HEADERS_FLAG_END_HEADERS); |
5077 if (IsHttp2() && flags & HEADERS_FLAG_PRIORITY) { | 5200 if (IsHttp2() && flags & HEADERS_FLAG_PRIORITY) { |
5078 has_priority = true; | 5201 has_priority = true; |
5079 priority = 3; | 5202 priority = 3; |
5080 parent_stream_id = 5; | 5203 parent_stream_id = 5; |
5081 exclusive = true; | 5204 exclusive = true; |
5082 } | 5205 } |
5083 EXPECT_CALL(visitor, OnHeaders(stream_id, has_priority, priority, | 5206 EXPECT_CALL(visitor, OnHeaders(stream_id, has_priority, priority, |
5084 parent_stream_id, exclusive, fin, end)); | 5207 parent_stream_id, exclusive, fin, end)); |
5085 EXPECT_CALL(visitor, OnControlFrameHeaderData(57, _, _)) | 5208 EXPECT_CALL(visitor, OnHeaderFrameStart(57)).Times(1); |
5086 .WillRepeatedly(testing::Return(true)); | 5209 if (end) { |
| 5210 EXPECT_CALL(visitor, OnHeaderFrameEnd(57, _)).Times(1); |
| 5211 } |
5087 if (flags & DATA_FLAG_FIN && | 5212 if (flags & DATA_FLAG_FIN && |
5088 (IsSpdy3() || flags & HEADERS_FLAG_END_HEADERS)) { | 5213 (IsSpdy3() || flags & HEADERS_FLAG_END_HEADERS)) { |
5089 EXPECT_CALL(visitor, OnStreamEnd(_)); | 5214 EXPECT_CALL(visitor, OnStreamEnd(_)); |
5090 } else { | 5215 } else { |
5091 // Do not close the stream if we are expecting a CONTINUATION frame. | 5216 // Do not close the stream if we are expecting a CONTINUATION frame. |
5092 EXPECT_CALL(visitor, OnStreamEnd(_)).Times(0); | 5217 EXPECT_CALL(visitor, OnStreamEnd(_)).Times(0); |
5093 } | 5218 } |
5094 | 5219 |
5095 framer.ProcessInput(frame.data(), frame.size()); | 5220 framer.ProcessInput(frame.data(), frame.size()); |
5096 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); | 5221 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); |
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5172 SpdyPushPromiseIR push_promise(client_id, promised_id); | 5297 SpdyPushPromiseIR push_promise(client_id, promised_id); |
5173 push_promise.SetHeader("foo", "bar"); | 5298 push_promise.SetHeader("foo", "bar"); |
5174 SpdySerializedFrame frame(framer.SerializePushPromise(push_promise)); | 5299 SpdySerializedFrame frame(framer.SerializePushPromise(push_promise)); |
5175 // TODO(jgraettinger): Add padding to SpdyPushPromiseIR, | 5300 // TODO(jgraettinger): Add padding to SpdyPushPromiseIR, |
5176 // and implement framing. | 5301 // and implement framing. |
5177 SetFrameFlags(&frame, flags & ~HEADERS_FLAG_PADDED, spdy_version_); | 5302 SetFrameFlags(&frame, flags & ~HEADERS_FLAG_PADDED, spdy_version_); |
5178 | 5303 |
5179 bool end = flags & PUSH_PROMISE_FLAG_END_PUSH_PROMISE; | 5304 bool end = flags & PUSH_PROMISE_FLAG_END_PUSH_PROMISE; |
5180 EXPECT_CALL(debug_visitor, | 5305 EXPECT_CALL(debug_visitor, |
5181 OnReceiveCompressedFrame(client_id, PUSH_PROMISE, _)); | 5306 OnReceiveCompressedFrame(client_id, PUSH_PROMISE, _)); |
5182 EXPECT_CALL(visitor, OnPushPromise(client_id, promised_id, end)); | 5307 EXPECT_CALL(visitor, |
5183 EXPECT_CALL(visitor, OnControlFrameHeaderData(client_id, _, _)) | 5308 OnPushPromise(client_id, promised_id, |
5184 .WillRepeatedly(testing::Return(true)); | 5309 flags & PUSH_PROMISE_FLAG_END_PUSH_PROMISE)); |
| 5310 EXPECT_CALL(visitor, OnHeaderFrameStart(client_id)).Times(1); |
| 5311 if (end) { |
| 5312 EXPECT_CALL(visitor, OnHeaderFrameEnd(client_id, _)).Times(1); |
| 5313 } |
5185 | 5314 |
5186 framer.ProcessInput(frame.data(), frame.size()); | 5315 framer.ProcessInput(frame.data(), frame.size()); |
5187 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); | 5316 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); |
5188 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) | 5317 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) |
5189 << SpdyFramer::ErrorCodeToString(framer.error_code()); | 5318 << SpdyFramer::ErrorCodeToString(framer.error_code()); |
5190 } while (++flags != 0); | 5319 } while (++flags != 0); |
5191 } | 5320 } |
5192 | 5321 |
5193 TEST_P(SpdyFramerTest, ContinuationFrameFlags) { | 5322 TEST_P(SpdyFramerTest, ContinuationFrameFlags) { |
5194 if (!IsHttp2()) { | 5323 if (!IsHttp2()) { |
5195 return; | 5324 return; |
5196 } | 5325 } |
5197 | 5326 |
5198 uint8_t flags = 0; | 5327 uint8_t flags = 0; |
5199 do { | 5328 do { |
5200 SCOPED_TRACE(testing::Message() << "Flags " << flags << std::hex | 5329 SCOPED_TRACE(testing::Message() << "Flags " << flags << std::hex |
5201 << static_cast<int>(flags)); | 5330 << static_cast<int>(flags)); |
5202 | 5331 |
5203 testing::StrictMock<test::MockSpdyFramerVisitor> visitor; | 5332 testing::StrictMock<test::MockSpdyFramerVisitor> visitor; |
5204 testing::StrictMock<test::MockDebugVisitor> debug_visitor; | 5333 testing::StrictMock<test::MockDebugVisitor> debug_visitor; |
5205 SpdyFramer framer(spdy_version_); | 5334 SpdyFramer framer(spdy_version_); |
5206 framer.set_visitor(&visitor); | 5335 framer.set_visitor(&visitor); |
5207 framer.set_debug_visitor(&debug_visitor); | 5336 framer.set_debug_visitor(&debug_visitor); |
5208 | 5337 |
5209 EXPECT_CALL(debug_visitor, OnSendCompressedFrame(42, HEADERS, _, _)); | 5338 EXPECT_CALL(debug_visitor, OnSendCompressedFrame(42, HEADERS, _, _)); |
5210 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(42, HEADERS, _)); | 5339 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(42, HEADERS, _)); |
5211 EXPECT_CALL(visitor, OnHeaders(42, false, 0, 0, false, false, false)); | 5340 EXPECT_CALL(visitor, OnHeaders(42, false, 0, 0, false, false, false)); |
5212 EXPECT_CALL(visitor, OnControlFrameHeaderData(42, _, _)) | 5341 EXPECT_CALL(visitor, OnHeaderFrameStart(42)).Times(1); |
5213 .WillRepeatedly(testing::Return(true)); | |
5214 | 5342 |
5215 SpdyHeadersIR headers_ir(42); | 5343 SpdyHeadersIR headers_ir(42); |
5216 headers_ir.SetHeader("foo", "bar"); | 5344 headers_ir.SetHeader("foo", "bar"); |
5217 SpdySerializedFrame frame0(framer.SerializeHeaders(headers_ir)); | 5345 SpdySerializedFrame frame0(framer.SerializeHeaders(headers_ir)); |
5218 SetFrameFlags(&frame0, 0, spdy_version_); | 5346 SetFrameFlags(&frame0, 0, spdy_version_); |
5219 | 5347 |
5220 SpdyContinuationIR continuation(42); | 5348 SpdyContinuationIR continuation(42); |
5221 continuation.SetHeader("foo", "bar"); | 5349 continuation.SetHeader("foo", "bar"); |
5222 SpdySerializedFrame frame(framer.SerializeContinuation(continuation)); | 5350 SpdySerializedFrame frame(framer.SerializeContinuation(continuation)); |
5223 SetFrameFlags(&frame, flags, spdy_version_); | 5351 SetFrameFlags(&frame, flags, spdy_version_); |
5224 | 5352 |
5225 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(42, CONTINUATION, _)); | 5353 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(42, CONTINUATION, _)); |
5226 EXPECT_CALL(visitor, OnContinuation(42, flags & HEADERS_FLAG_END_HEADERS)); | 5354 EXPECT_CALL(visitor, OnContinuation(42, flags & HEADERS_FLAG_END_HEADERS)); |
5227 EXPECT_CALL(visitor, OnControlFrameHeaderData(42, _, _)) | 5355 bool end = flags & HEADERS_FLAG_END_HEADERS; |
5228 .WillRepeatedly(testing::Return(true)); | 5356 if (end) { |
| 5357 EXPECT_CALL(visitor, OnHeaderFrameEnd(42, _)).Times(1); |
| 5358 } |
5229 | 5359 |
5230 framer.ProcessInput(frame0.data(), frame0.size()); | 5360 framer.ProcessInput(frame0.data(), frame0.size()); |
5231 framer.ProcessInput(frame.data(), frame.size()); | 5361 framer.ProcessInput(frame.data(), frame.size()); |
5232 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); | 5362 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); |
5233 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) | 5363 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) |
5234 << SpdyFramer::ErrorCodeToString(framer.error_code()); | 5364 << SpdyFramer::ErrorCodeToString(framer.error_code()); |
5235 } while (++flags != 0); | 5365 } while (++flags != 0); |
5236 } | 5366 } |
5237 | 5367 |
5238 // TODO(mlavan): Add TEST_P(SpdyFramerTest, AltSvcFrameFlags) | 5368 // TODO(mlavan): Add TEST_P(SpdyFramerTest, AltSvcFrameFlags) |
(...skipping 16 matching lines...) Expand all Loading... |
5255 SpdySynStreamIR syn_stream(1); | 5385 SpdySynStreamIR syn_stream(1); |
5256 syn_stream.set_priority(1); | 5386 syn_stream.set_priority(1); |
5257 SpdySerializedFrame frame(framer.SerializeSynStream(syn_stream)); | 5387 SpdySerializedFrame frame(framer.SerializeSynStream(syn_stream)); |
5258 // Adjust size to remove the header block. | 5388 // Adjust size to remove the header block. |
5259 SetFrameLength(&frame, framer.GetSynStreamMinimumSize() - | 5389 SetFrameLength(&frame, framer.GetSynStreamMinimumSize() - |
5260 framer.GetControlFrameHeaderSize(), | 5390 framer.GetControlFrameHeaderSize(), |
5261 spdy_version_); | 5391 spdy_version_); |
5262 | 5392 |
5263 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(1, SYN_STREAM, _)); | 5393 EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(1, SYN_STREAM, _)); |
5264 EXPECT_CALL(visitor, OnSynStream(1, 0, 1, false, false)); | 5394 EXPECT_CALL(visitor, OnSynStream(1, 0, 1, false, false)); |
5265 EXPECT_CALL(visitor, OnControlFrameHeaderData(1, NULL, 0)); | 5395 EXPECT_CALL(visitor, OnHeaderFrameStart(1)).Times(1); |
| 5396 EXPECT_CALL(visitor, OnHeaderFrameEnd(1, _)).Times(1); |
5266 | 5397 |
5267 framer.ProcessInput(frame.data(), framer.GetSynStreamMinimumSize()); | 5398 framer.ProcessInput(frame.data(), framer.GetSynStreamMinimumSize()); |
5268 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); | 5399 EXPECT_EQ(SpdyFramer::SPDY_READY_FOR_FRAME, framer.state()); |
5269 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) | 5400 EXPECT_EQ(SpdyFramer::SPDY_NO_ERROR, framer.error_code()) |
5270 << SpdyFramer::ErrorCodeToString(framer.error_code()); | 5401 << SpdyFramer::ErrorCodeToString(framer.error_code()); |
5271 } | 5402 } |
5272 | 5403 |
5273 TEST_P(SpdyFramerTest, SettingsFlagsAndId) { | 5404 TEST_P(SpdyFramerTest, SettingsFlagsAndId) { |
5274 const uint32_t kId = 0x020304; | 5405 const uint32_t kId = 0x020304; |
5275 const uint32_t kFlags = 0x01; | 5406 const uint32_t kFlags = 0x01; |
(...skipping 581 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5857 | 5988 |
5858 EXPECT_EQ(1, visitor->data_frame_count_); | 5989 EXPECT_EQ(1, visitor->data_frame_count_); |
5859 EXPECT_EQ(strlen(four_score), static_cast<unsigned>(visitor->data_bytes_)); | 5990 EXPECT_EQ(strlen(four_score), static_cast<unsigned>(visitor->data_bytes_)); |
5860 EXPECT_EQ(0, visitor->headers_frame_count_); | 5991 EXPECT_EQ(0, visitor->headers_frame_count_); |
5861 } | 5992 } |
5862 } | 5993 } |
5863 | 5994 |
5864 } // namespace test | 5995 } // namespace test |
5865 | 5996 |
5866 } // namespace net | 5997 } // namespace net |
OLD | NEW |