Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(238)

Side by Side Diff: net/spdy/spdy_headers_block_parser_test.cc

Issue 863253002: Update from https://crrev.com/312600 (Closed) Base URL: https://github.com/domokit/mojo.git@master
Patch Set: Created 5 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 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_headers_block_parser.h" 5 #include "net/spdy/spdy_headers_block_parser.h"
6 6
7 #include <string> 7 #include <string>
8 8
9 #include "base/memory/scoped_ptr.h" 9 #include "base/memory/scoped_ptr.h"
10 #include "base/strings/string_number_conversions.h" 10 #include "base/strings/string_number_conversions.h"
11 #include "base/sys_byteorder.h" 11 #include "base/sys_byteorder.h"
12 #include "net/test/gtest_util.h"
12 #include "testing/gmock/include/gmock/gmock.h" 13 #include "testing/gmock/include/gmock/gmock.h"
13 #include "testing/gtest/include/gtest/gtest.h" 14 #include "testing/gtest/include/gtest/gtest.h"
14 15
15 namespace net { 16 namespace net {
16 17
17 using base::IntToString; 18 using base::IntToString;
18 using base::StringPiece; 19 using base::StringPiece;
19 using std::string; 20 using std::string;
20 21
21 // A mock the handler class to check that we parse out the correct headers 22 // A mock the handler class to check that we parse out the correct headers
22 // and call the callback methods when we should. 23 // and call the callback methods when we should.
23 class MockSpdyHeadersHandler : public SpdyHeadersHandlerInterface { 24 class MockSpdyHeadersHandler : public SpdyHeadersHandlerInterface {
24 public: 25 public:
25 MOCK_METHOD2(OnHeaderBlock, void(SpdyStreamId stream_id, 26 MOCK_METHOD1(OnHeaderBlock, void(uint32_t num_of_headers));
26 uint32_t num_of_headers)); 27 MOCK_METHOD1(OnHeaderBlockEnd, void(size_t bytes));
27 MOCK_METHOD2(OnHeaderBlockEnd, void(SpdyStreamId stream_id, size_t bytes)); 28 MOCK_METHOD2(OnHeader, void(StringPiece key, StringPiece value));
28 MOCK_METHOD3(OnHeader, void(SpdyStreamId stream_id,
29 StringPiece,
30 StringPiece));
31 }; 29 };
32 30
33 class SpdyHeadersBlockParserTest : 31 class SpdyHeadersBlockParserTest :
34 public ::testing::TestWithParam<SpdyMajorVersion> { 32 public ::testing::TestWithParam<SpdyMajorVersion> {
35 public: 33 public:
36 virtual ~SpdyHeadersBlockParserTest() {} 34 virtual ~SpdyHeadersBlockParserTest() {}
37 35
38 protected: 36 protected:
39 void SetUp() override { 37 void SetUp() override {
40 // Create a parser using the mock handler. 38 // Create a parser using the mock handler.
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
114 INSTANTIATE_TEST_CASE_P(SpdyHeadersBlockParserTests, 112 INSTANTIATE_TEST_CASE_P(SpdyHeadersBlockParserTests,
115 SpdyHeadersBlockParserTest, 113 SpdyHeadersBlockParserTest,
116 ::testing::Values(SPDY2, SPDY3, SPDY4)); 114 ::testing::Values(SPDY2, SPDY3, SPDY4));
117 115
118 TEST_P(SpdyHeadersBlockParserTest, BasicTest) { 116 TEST_P(SpdyHeadersBlockParserTest, BasicTest) {
119 // Sanity test, verify that we parse out correctly a block with 117 // Sanity test, verify that we parse out correctly a block with
120 // a single key-value pair and that we notify when we start and finish 118 // a single key-value pair and that we notify when we start and finish
121 // handling a headers block. 119 // handling a headers block.
122 string headers(CreateHeaders(1, false)); 120 string headers(CreateHeaders(1, false));
123 121
124 EXPECT_CALL(handler_, OnHeaderBlock(1, 1)).Times(1); 122 EXPECT_CALL(handler_, OnHeaderBlock(1)).Times(1);
125 123
126 std::string expect_key = kBaseKey + IntToString(0); 124 std::string expect_key = kBaseKey + IntToString(0);
127 std::string expect_value = kBaseValue + IntToString(0); 125 std::string expect_value = kBaseValue + IntToString(0);
128 EXPECT_CALL(handler_, OnHeader(1, StringPiece(expect_key), 126 EXPECT_CALL(handler_, OnHeader(StringPiece(expect_key),
129 StringPiece(expect_value))).Times(1); 127 StringPiece(expect_value))).Times(1);
130 EXPECT_CALL(handler_, OnHeaderBlockEnd(1, headers.length())).Times(1); 128 EXPECT_CALL(handler_, OnHeaderBlockEnd(headers.length())).Times(1);
131 129
132 EXPECT_TRUE(parser_-> 130 EXPECT_TRUE(parser_->
133 HandleControlFrameHeadersData(1, headers.c_str(), headers.length())); 131 HandleControlFrameHeadersData(1, headers.c_str(), headers.length()));
134 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error()); 132 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error());
135 } 133 }
136 134
137 TEST_P(SpdyHeadersBlockParserTest, NullsSupportedTest) { 135 TEST_P(SpdyHeadersBlockParserTest, NullsSupportedTest) {
138 // Sanity test, verify that we parse out correctly a block with 136 // Sanity test, verify that we parse out correctly a block with
139 // a single key-value pair when the key and value contain null charecters. 137 // a single key-value pair when the key and value contain null charecters.
140 string headers(CreateHeaders(1, true)); 138 string headers(CreateHeaders(1, true));
141 139
142 EXPECT_CALL(handler_, OnHeaderBlock(1, 1)).Times(1); 140 EXPECT_CALL(handler_, OnHeaderBlock(1)).Times(1);
143 141
144 std::string expect_key = kBaseKey + string("\0", 1) + IntToString(0); 142 std::string expect_key = kBaseKey + string("\0", 1) + IntToString(0);
145 std::string expect_value = kBaseValue + string("\0", 1) + IntToString(0); 143 std::string expect_value = kBaseValue + string("\0", 1) + IntToString(0);
146 EXPECT_CALL(handler_, OnHeader(1, StringPiece(expect_key), 144 EXPECT_CALL(handler_, OnHeader(StringPiece(expect_key),
147 StringPiece(expect_value))).Times(1); 145 StringPiece(expect_value))).Times(1);
148 EXPECT_CALL(handler_, OnHeaderBlockEnd(1, headers.length())).Times(1); 146 EXPECT_CALL(handler_, OnHeaderBlockEnd(headers.length())).Times(1);
149 147
150 EXPECT_TRUE(parser_-> 148 EXPECT_TRUE(parser_->
151 HandleControlFrameHeadersData(1, headers.c_str(), headers.length())); 149 HandleControlFrameHeadersData(1, headers.c_str(), headers.length()));
152 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error()); 150 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error());
153 } 151 }
154 152
155 TEST_P(SpdyHeadersBlockParserTest, MultipleBlocksAndHeadersWithPartialData) { 153 TEST_P(SpdyHeadersBlockParserTest, MultipleBlocksAndHeadersWithPartialData) {
156 testing::InSequence s; 154 testing::InSequence s;
157 155
158 // CreateHeaders is deterministic; we can call it once for the whole test. 156 // CreateHeaders is deterministic; we can call it once for the whole test.
159 string headers(CreateHeaders(kNumHeadersInBlock, false)); 157 string headers(CreateHeaders(kNumHeadersInBlock, false));
160 158
161 // The mock doesn't retain storage of arguments, so keep them in scope. 159 // The mock doesn't retain storage of arguments, so keep them in scope.
162 std::vector<string> retained_arguments; 160 std::vector<string> retained_arguments;
163 for (int i = 0; i < kNumHeadersInBlock; i++) { 161 for (int i = 0; i < kNumHeadersInBlock; i++) {
164 retained_arguments.push_back(kBaseKey + IntToString(i)); 162 retained_arguments.push_back(kBaseKey + IntToString(i));
165 retained_arguments.push_back(kBaseValue + IntToString(i)); 163 retained_arguments.push_back(kBaseValue + IntToString(i));
166 } 164 }
167 // For each block we expect to parse out the headers in order. 165 // For each block we expect to parse out the headers in order.
168 for (int i = 0; i < kNumHeaderBlocks; i++) { 166 for (int i = 0; i < kNumHeaderBlocks; i++) {
169 EXPECT_CALL(handler_, OnHeaderBlock(i, kNumHeadersInBlock)).Times(1); 167 EXPECT_CALL(handler_, OnHeaderBlock(kNumHeadersInBlock)).Times(1);
170 for (int j = 0; j < kNumHeadersInBlock; j++) { 168 for (int j = 0; j < kNumHeadersInBlock; j++) {
171 EXPECT_CALL(handler_, OnHeader( 169 EXPECT_CALL(handler_, OnHeader(
172 i,
173 StringPiece(retained_arguments[2 * j]), 170 StringPiece(retained_arguments[2 * j]),
174 StringPiece(retained_arguments[2 * j + 1]))).Times(1); 171 StringPiece(retained_arguments[2 * j + 1]))).Times(1);
175 } 172 }
176 EXPECT_CALL(handler_, OnHeaderBlockEnd(i, headers.length())).Times(1); 173 EXPECT_CALL(handler_, OnHeaderBlockEnd(headers.length())).Times(1);
177 } 174 }
178 // Parse the header blocks, feeding the parser one byte at a time. 175 // Parse the header blocks, feeding the parser one byte at a time.
179 for (int i = 0; i < kNumHeaderBlocks; i++) { 176 for (int i = 1; i <= kNumHeaderBlocks; i++) {
180 for (string::iterator it = headers.begin(); it != headers.end(); ++it) { 177 for (string::iterator it = headers.begin(); it != headers.end(); ++it) {
181 if ((it + 1) == headers.end()) { 178 if ((it + 1) == headers.end()) {
182 // Last byte completes the block. 179 // Last byte completes the block.
183 EXPECT_TRUE(parser_->HandleControlFrameHeadersData(i, &(*it), 1)); 180 EXPECT_TRUE(parser_->HandleControlFrameHeadersData(i, &(*it), 1));
184 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error()); 181 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error());
185 } else { 182 } else {
186 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(i, &(*it), 1)); 183 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(i, &(*it), 1));
187 EXPECT_EQ(SpdyHeadersBlockParser::NEED_MORE_DATA, parser_->get_error()); 184 EXPECT_EQ(SpdyHeadersBlockParser::NEED_MORE_DATA, parser_->get_error());
188 } 185 }
189 } 186 }
190 } 187 }
191 } 188 }
192 189
193 TEST_P(SpdyHeadersBlockParserTest, HandlesEmptyCallsTest) { 190 TEST_P(SpdyHeadersBlockParserTest, HandlesEmptyCallsTest) {
194 EXPECT_CALL(handler_, OnHeaderBlock(1, 1)).Times(1); 191 EXPECT_CALL(handler_, OnHeaderBlock(1)).Times(1);
195 192
196 string headers(CreateHeaders(1, false)); 193 string headers(CreateHeaders(1, false));
197 194
198 string expect_key = kBaseKey + IntToString(0); 195 string expect_key = kBaseKey + IntToString(0);
199 string expect_value = kBaseValue + IntToString(0); 196 string expect_value = kBaseValue + IntToString(0);
200 EXPECT_CALL(handler_, OnHeader(1, StringPiece(expect_key), 197 EXPECT_CALL(handler_, OnHeader(StringPiece(expect_key),
201 StringPiece(expect_value))).Times(1); 198 StringPiece(expect_value))).Times(1);
202 EXPECT_CALL(handler_, OnHeaderBlockEnd(1, headers.length())).Times(1); 199 EXPECT_CALL(handler_, OnHeaderBlockEnd(headers.length())).Times(1);
203 200
204 // Send a header in pieces with intermediate empty calls. 201 // Send a header in pieces with intermediate empty calls.
205 for (string::iterator it = headers.begin(); it != headers.end(); ++it) { 202 for (string::iterator it = headers.begin(); it != headers.end(); ++it) {
206 if ((it + 1) == headers.end()) { 203 if ((it + 1) == headers.end()) {
207 // Last byte completes the block. 204 // Last byte completes the block.
208 EXPECT_TRUE(parser_->HandleControlFrameHeadersData(1, &(*it), 1)); 205 EXPECT_TRUE(parser_->HandleControlFrameHeadersData(1, &(*it), 1));
209 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error()); 206 EXPECT_EQ(SpdyHeadersBlockParser::OK, parser_->get_error());
210 } else { 207 } else {
211 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(1, &(*it), 1)); 208 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(1, &(*it), 1));
212 EXPECT_EQ(SpdyHeadersBlockParser::NEED_MORE_DATA, parser_->get_error()); 209 EXPECT_EQ(SpdyHeadersBlockParser::NEED_MORE_DATA, parser_->get_error());
213 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(1, NULL, 0)); 210 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(1, NULL, 0));
214 } 211 }
215 } 212 }
216 } 213 }
217 214
218 TEST_P(SpdyHeadersBlockParserTest, LargeBlocksDiscardedTest) { 215 TEST_P(SpdyHeadersBlockParserTest, LargeBlocksDiscardedTest) {
219 // Header block with too many headers. 216 // Header block with too many headers.
220 { 217 {
221 string headers = EncodeLength( 218 string headers = EncodeLength(
222 parser_->MaxNumberOfHeadersForVersion(spdy_version_) + 1); 219 parser_->MaxNumberOfHeadersForVersion(spdy_version_) + 1);
223 EXPECT_FALSE(parser_-> 220 EXPECT_FALSE(parser_->
224 HandleControlFrameHeadersData(1, headers.c_str(), headers.length())); 221 HandleControlFrameHeadersData(1, headers.c_str(), headers.length()));
225 EXPECT_EQ(SpdyHeadersBlockParser::HEADER_BLOCK_TOO_LARGE, 222 EXPECT_EQ(SpdyHeadersBlockParser::HEADER_BLOCK_TOO_LARGE,
226 parser_->get_error()); 223 parser_->get_error());
227 } 224 }
228 parser_.reset(new SpdyHeadersBlockParser(spdy_version_, &handler_)); 225 parser_.reset(new SpdyHeadersBlockParser(spdy_version_, &handler_));
229 // Header block with one header, which has a too-long key. 226 // Header block with one header, which has a too-long key.
230 { 227 {
231 EXPECT_CALL(handler_, OnHeaderBlock(1, 1)).Times(1); 228 EXPECT_CALL(handler_, OnHeaderBlock(1)).Times(1);
232 229
233 string headers = EncodeLength(1) + EncodeLength( 230 string headers = EncodeLength(1) + EncodeLength(
234 SpdyHeadersBlockParser::kMaximumFieldLength + 1); 231 SpdyHeadersBlockParser::kMaximumFieldLength + 1);
235 EXPECT_FALSE(parser_-> 232 EXPECT_FALSE(parser_->
236 HandleControlFrameHeadersData(1, headers.c_str(), headers.length())); 233 HandleControlFrameHeadersData(1, headers.c_str(), headers.length()));
237 EXPECT_EQ(SpdyHeadersBlockParser::HEADER_FIELD_TOO_LARGE, 234 EXPECT_EQ(SpdyHeadersBlockParser::HEADER_FIELD_TOO_LARGE,
238 parser_->get_error()); 235 parser_->get_error());
239 } 236 }
240 } 237 }
241 238
242 TEST_P(SpdyHeadersBlockParserTest, ExtraDataTest) { 239 TEST_P(SpdyHeadersBlockParserTest, ExtraDataTest) {
243 string headers = CreateHeaders(1, false) + "foobar"; 240 string headers = CreateHeaders(1, false) + "foobar";
244 241
245 EXPECT_CALL(handler_, OnHeaderBlock(1, 1)).Times(1); 242 EXPECT_CALL(handler_, OnHeaderBlock(1)).Times(1);
246 EXPECT_CALL(handler_, OnHeaderBlockEnd(1, headers.length())).Times(1); 243 EXPECT_CALL(handler_, OnHeaderBlockEnd(headers.length())).Times(1);
247 244
248 string expect_key = kBaseKey + IntToString(0); 245 string expect_key = kBaseKey + IntToString(0);
249 string expect_value = kBaseValue + IntToString(0); 246 string expect_value = kBaseValue + IntToString(0);
250 EXPECT_CALL(handler_, OnHeader(1, StringPiece(expect_key), 247 EXPECT_CALL(handler_, OnHeader(StringPiece(expect_key),
251 StringPiece(expect_value))).Times(1); 248 StringPiece(expect_value))).Times(1);
252 249
253 EXPECT_FALSE(parser_-> 250 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(1, headers.c_str(),
254 HandleControlFrameHeadersData(1, headers.c_str(), headers.length())); 251 headers.length()));
255 EXPECT_EQ(SpdyHeadersBlockParser::TOO_MUCH_DATA, parser_->get_error()); 252 EXPECT_EQ(SpdyHeadersBlockParser::TOO_MUCH_DATA, parser_->get_error());
256 } 253 }
257 254
255 TEST_P(SpdyHeadersBlockParserTest, WrongStreamIdTest) {
256 string headers(CreateHeaders(kNumHeadersInBlock, false));
257 EXPECT_FALSE(parser_->HandleControlFrameHeadersData(1, headers.data(), 1));
258 EXPECT_EQ(SpdyHeadersBlockParser::NEED_MORE_DATA, parser_->get_error());
259 bool result;
260 EXPECT_DFATAL(
261 result = parser_->HandleControlFrameHeadersData(2, headers.data() + 1, 1),
262 "Unexpected stream id: 2 \\(expected 1\\)");
263 EXPECT_FALSE(result);
264 EXPECT_EQ(SpdyHeadersBlockParser::UNEXPECTED_STREAM_ID, parser_->get_error());
265 }
266
267 TEST_P(SpdyHeadersBlockParserTest, InvalidStreamIdTest) {
268 string headers(CreateHeaders(kNumHeadersInBlock, false));
269 bool result;
270 EXPECT_DFATAL(
271 result = parser_->HandleControlFrameHeadersData(0, headers.data(), 1),
272 "Expected nonzero stream id, saw: 0");
273 EXPECT_FALSE(result);
274 EXPECT_EQ(SpdyHeadersBlockParser::UNEXPECTED_STREAM_ID, parser_->get_error());
275 }
276
258 } // namespace net 277 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698