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

Side by Side Diff: components/data_reduction_proxy/browser/data_reduction_proxy_tamper_detect_unittest.cc

Issue 338483002: Chrome Participated Tamper Detect (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 6 years, 4 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
(Empty)
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
3 // found in the LICENSE file.
4
5 #include "components/data_reduction_proxy/browser/data_reduction_proxy_tamper_de tect.h"
6
7 #include <string.h>
8 #include <algorithm>
9 #include <map>
10 #include <vector>
11
12 #include "base/base64.h"
13 #include "base/md5.h"
14 #include "base/strings/string_number_conversions.h"
15 #include "base/strings/string_split.h"
16 #include "components/data_reduction_proxy/common/data_reduction_proxy_headers.h"
17 #include "net/android/network_library.h"
18 #include "net/http/http_response_headers.h"
19 #include "net/http/http_util.h"
20 #include "testing/gtest/include/gtest/gtest.h"
21
22 #if defined(OS_ANDROID)
23 #include "base/android/jni_android.h"
24 #include "net/android/network_library.h"
25 #endif
26
27 namespace {
28
29 void HeadersToRaw(std::string* headers) {
bengr 2014/07/28 21:56:52 This seems to be used in a few places by the data
xingx1 2014/07/30 03:44:21 I think this function is more like an utility func
30 std::replace(headers->begin(), headers->end(), '\n', '\0');
31 if (!headers->empty())
32 *headers += '\0';
33 }
34
35 // Calcuates MD5 hash value for a string and then base64 encode it.
36 std::string GetEncoded(const std::string& input) {
bengr 2014/07/28 21:56:52 Why do you need this in the tests? Add the answer
xingx1 2014/07/30 03:44:21 Done.
37 base::MD5Digest digest;
38 base::MD5Sum(input.c_str(), input.size(), &digest);
39 std::string base64encoded;
40 base::Base64Encode(std::string((char*)digest.a,
41 ARRAYSIZE_UNSAFE(digest.a)), &base64encoded);
42 return base64encoded;
43 }
44
45 // Replaces all contents within "[]" by corresponding base64 encoded MD5 value.
46 // It can handle nested case like: [[abc]def].
47 void ReplaceWithEncodedString(std::string* input) {
bengr 2014/07/28 21:56:52 Why is this needed?
xingx1 2014/07/30 03:44:22 Done.
48 size_t start, end, temp;
49 while (true) {
50 start = input->find("[");
51 if (start == std::string::npos) break;
52 while (true) {
53 temp = input->find("[", start + 1);
54 end = input->find("]", start + 1);
55 if (end >= 0 && end < temp)
56 break;
57 else
58 start = temp;
59 }
60 std::string need_to_encode = input->substr(start + 1, end - start - 1);
61 *input = input->substr(0, start) + GetEncoded(need_to_encode) +
62 input->substr(end + 1);
63 }
64 }
65
66 const int kMaxVectorSize = 10;
67 // Put a list of strings into a vector.
68 std::vector<std::string> StringsToVector(std::string* input) {
bengr 2014/07/28 21:56:52 Why is this needed? Here and above, I would have t
xingx1 2014/07/30 03:44:21 Done.
69 std::vector<std::string> vector;
70 for (size_t i=0; i<kMaxVectorSize; ++i) {
71 if (input[i].size()) {
bengr 2014/07/28 21:56:52 i = 0
xingx1 2014/07/30 03:44:21 Done.
72 if (input[i] == " ")
73 vector.push_back("");
74 else
75 vector.push_back(input[i]);
76 }
77 }
78 return vector;
79 }
80
81 // Testcase for fingerprint checking functions. |received_fingerprint| is
82 // fingerprint received from the data reduction proxy. |expected_tampered| is
83 // expected tampered or not result.
84 struct TamperDetectionTestCase {
85 std::string label;
86 std::string raw_header;
87 std::string received_fingerprint;
88 bool expected_tampered;
89 bool expected_has_chrome_proxy_via_header;
90 };
91
92 } // namespace
93
94 namespace data_reduction_proxy {
95
96 class DataReductionProxyTamperDetectionTest : public testing::Test {
97 public:
98 static void TestFingerprintCommon(const TamperDetectionTestCase& test,
99 DataReductionProxyTamperDetection::FingerprintCode fingerprint);
100 };
101
102 // Common function for testing fingerprint checking functions. For a given
103 // header string |test.raw_header|, generates HttpResponseHeaders |headers| and
104 // checks specified fingerprint checking function returns expected result or
105 // not.
106 void DataReductionProxyTamperDetectionTest::TestFingerprintCommon(
107 const TamperDetectionTestCase& test,
108 DataReductionProxyTamperDetection::FingerprintCode fingerprint_code) {
109 std::string raw_headers(test.raw_header);
110 HeadersToRaw(&raw_headers);
111 net::HttpResponseHeaders* headers = new net::HttpResponseHeaders(raw_headers);
112
113 // Removes Chrome-Proxy header's fingerprint from Chrome-Proxy header.
114 std::vector<std::string> chrome_proxy_header_values =
115 DataReductionProxyTamperDetection::
116 GetHeaderValues(headers, "Chrome-Proxy");
117
118 DataReductionProxyTamperDetection::RemoveChromeProxyFingerprint(
119 &chrome_proxy_header_values);
120
121 DataReductionProxyTamperDetection tamper_detection(
122 headers, true, 0, &chrome_proxy_header_values);
123
124 bool tampered, has_chrome_proxy_via_header = false;
125 switch (fingerprint_code) {
126 case DataReductionProxyTamperDetection::CHROMEPROXY:
127 tampered = tamper_detection.IsChromeProxyHeaderTampered(
128 test.received_fingerprint);
129 break;
130 case DataReductionProxyTamperDetection::VIA:
131 tampered = tamper_detection.IsViaHeaderTampered(
132 test.received_fingerprint, &has_chrome_proxy_via_header);
133 EXPECT_EQ(test.expected_has_chrome_proxy_via_header,
134 has_chrome_proxy_via_header) << test.label;
135 break;
136 case DataReductionProxyTamperDetection::OTHERHEADERS:
137 tampered = tamper_detection.AreOtherHeadersTampered(
138 test.received_fingerprint);
139 break;
140 case DataReductionProxyTamperDetection::CONTENTLENGTH:
141 tampered = tamper_detection.IsContentLengthHeaderTampered(
142 test.received_fingerprint);
143 break;
144 case DataReductionProxyTamperDetection::NONEXIST:
145 default:
146 NOTREACHED();
147 break;
148 }
149
150 EXPECT_EQ(test.expected_tampered, tampered) << test.label;
151 }
152
153 // Tests function IsChromeProxyHeaderTampered.
bengr 2014/07/28 21:56:52 Be sure to update comments like this one when you
xingx1 2014/07/30 03:44:21 Done.
154 TEST_F(DataReductionProxyTamperDetectionTest, ChromeProxy) {
155 // |received_fingerprint| is not the actual fingerprint from data reduction
156 // proxy, instead, the base64 encoded field is in plain text (within "[]")
157 // and needs to be encoded first.
158 TamperDetectionTestCase test[] = {
159 {
160 "Checks sorting.",
161 "HTTP/1.1 200 OK\n"
162 "Chrome-Proxy: c,b,a,3,2,1,fcp=f\n",
163 "[1,2,3,a,b,c,]",
164 false,
165 },
166 {
167 "Checks Chrome-Proxy's fingerprint removing.",
168 "HTTP/1.1 200 OK\n"
169 "Chrome-Proxy: a,b,c,d,e,3,2,1,fcp=f\n",
170 "[1,2,3,a,b,c,d,e,]",
171 false,
172 },
173 {
174 "Checks no Chrome-Proxy header case (should not happen).",
175 "HTTP/1.1 200 OK\n",
176 "[]",
177 false,
178 },
179 {
180 "Checks empty Chrome-Proxy header case (should not happen).",
181 "HTTP/1.1 200 OK\n"
182 "Chrome-Proxy: \n",
183 "[,]",
184 false,
185 },
186 {
187 "Checks Chrome-Proxy header with its fingerprint only case.",
188 "HTTP/1.1 200 OK\n"
189 "Chrome-Proxy: fcp=f\n",
190 "[]",
191 false,
192 },
193 {
194 "Checks empty Chrome-Proxy header case, with extra ',' and ' '",
195 "HTTP/1.1 200 OK\n"
196 "Chrome-Proxy: fcp=f , \n",
197 "[]",
198 false,
199 },
200 {
201 "Changed no value to empty value.",
202 "HTTP/1.1 200 OK\n"
203 "Chrome-Proxy: fcp=f\n",
204 "[,]",
205 true,
206 },
207 {
208 "Changed header values.",
209 "HTTP/1.1 200 OK\n"
210 "Chrome-Proxy: a,b=2,c,d=1,fcp=f\n",
211 "[a,b=3,c,d=1,]",
212 true,
213 },
214 {
215 "Changed order of header values.",
216 "HTTP/1.1 200 OK\n"
217 "Chrome-Proxy: c,b,a,fcp=1\n",
218 "[c,b,a,]",
219 true,
220 },
221 {
222 "Checks Chrome-Proxy header with extra ' '.",
223 "HTTP/1.1 200 OK\n"
224 "Chrome-Proxy: a , b , c, d, fcp=f\n",
225 "[a,b,c,d,]",
226 false
227 },
228 {
229 "Check Chrome-Proxy header with multiple lines and ' '.",
230 "HTTP/1.1 200 OK\n"
231 "Chrome-Proxy: a , c , d, fcp=f \n"
232 "Chrome-Proxy: b \n",
233 "[a,b,c,d,]",
234 false
235 },
236 {
237 "Checks Chrome-Proxy header with multiple lines, at different positions",
238 "HTTP/1.1 200 OK\n"
239 "Chrome-Proxy: a \n"
240 "Chrome-Proxy: c \n"
241 "Content-Type: 1\n"
242 "Cache-Control: 2\n"
243 "ETag: 3\n"
244 "Chrome-Proxy: b \n"
245 "Connection: 4\n"
246 "Expires: 5\n"
247 "Chrome-Proxy: fcp=f \n"
248 "Via: \n"
249 "Content-Length: 12345\n",
250 "[a,b,c,]",
251 false
252 },
253 {
254 "Checks Chrome-Proxy header with multiple same values.",
255 "HTTP/1.1 200 OK\n"
256 "Chrome-Proxy: a \n"
257 "Chrome-Proxy: b\n"
258 "Chrome-Proxy: c\n"
259 "Chrome-Proxy: d, fcp=f \n"
260 "Chrome-Proxy: a \n",
261 "[a,a,b,c,d,]",
262 false
263 },
264 {
265 "Changed Chrome-Proxy header with multiple lines..",
266 "HTTP/1.1 200 OK\n"
267 "Chrome-Proxy: a\n"
268 "Chrome-Proxy: a\n"
269 "Chrome-Proxy: b\n"
270 "Chrome-Proxy: c,fcp=f\n",
271 "[a,b,c,]",
272 true,
273 },
274 {
275 "Checks case whose received fingerprint is empty.",
276 "HTTP/1.1 200 OK\n"
277 "Chrome-Proxy: a,b,c,fcp=1\n",
278 "[]",
279 true,
280 },
281 {
282 "Checks case whose received fingerprint cannot be base64 decoded.",
283 "HTTP/1.1 200 OK\n"
284 "Chrome-Proxy: a,b,c,fcp=1\n",
285 "not_base64_encoded",
286 true,
287 },
288 };
289
290 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
bengr 2014/07/28 21:56:52 i = 0
xingx1 2014/07/30 03:44:21 Done.
291 ReplaceWithEncodedString(&test[i].received_fingerprint);
292
293 DataReductionProxyTamperDetectionTest::TestFingerprintCommon(test[i],
bengr 2014/07/28 21:56:52 move test[i] to the beginning of the next line.
xingx1 2014/07/30 03:44:22 Function removed.
294 DataReductionProxyTamperDetection::CHROMEPROXY);
295 }
296 }
297
298 // Tests function IsViaHeaderTampered.
299 TEST_F(DataReductionProxyTamperDetectionTest, Via) {
300 TamperDetectionTestCase test[] = {
301 {
302 "Checks the case that Chrome-Compression-Proxy occurs at the last.",
303 "HTTP/1.1 200 OK\n"
304 "Via: a, b, c, 1.1 Chrome-Compression-Proxy\n",
305 "",
306 false,
307 true,
308 },
309 {
310 "Checks when there is intermediary.",
311 "HTTP/1.1 200 OK\n"
312 "Via: a, b, c, 1.1 Chrome-Compression-Proxy, xyz\n",
313 "",
314 true,
315 true,
316 },
317 {
318 "Checks the case of empty Via header.",
319 "HTTP/1.1 200 OK\n"
320 "Via: \n",
321 "",
322 false,
323 false,
324 },
325 {
326 "Checks the case that only the data reduction proxy's Via header occurs.",
327 "HTTP/1.1 200 OK\n"
328 "Via: 1.1 Chrome-Compression-Proxy \n",
329 "",
330 false,
331 true,
332 },
333 {
334 "Checks the case that there are ' ', i.e., empty value after the data"
335 " reduction proxy's Via header.",
336 "HTTP/1.1 200 OK\n"
337 "Via: 1.1 Chrome-Compression-Proxy , , \n",
338 "",
339 false,
340 true,
341 },
342 {
343 "Checks the case when there is no Via header",
344 "HTTP/1.1 200 OK\n",
345 "",
346 false,
347 false,
348 },
349 // Same to above test cases, but with deprecated data reduciton proxy Via
350 // header.
351 {
352 "Checks the case that Chrome Compression Proxy occurs at the last.",
353 "HTTP/1.1 200 OK\n"
354 "Via: a, b, c, 1.1 Chrome Compression Proxy\n",
355 "",
356 false,
357 true,
358 },
359 {
360 "Checks when there is intermediary.",
361 "HTTP/1.1 200 OK\n"
362 "Via: a, b, c, 1.1 Chrome Compression Proxy, xyz\n",
363 "",
364 true,
365 true,
366 },
367 {
368 "Checks the case of empty Via header.",
369 "HTTP/1.1 200 OK\n"
370 "Via: \n",
371 "",
372 false,
373 false,
374 },
375 {
376 "Checks the case that only the data reduction proxy's Via header occurs.",
377 "HTTP/1.1 200 OK\n"
378 "Via: 1.1 Chrome Compression Proxy \n",
379 "",
380 false,
381 true,
382 },
383 {
384 "Checks the case that there are ' ', i.e., empty value after the data"
385 "reduction proxy's Via header.",
386 "HTTP/1.1 200 OK\n"
387 "Via: 1.1 Chrome Compression Proxy , , \n",
388 "",
389 false,
390 true,
391 },
392 {
393 "Checks the case when there is no Via header",
394 "HTTP/1.1 200 OK\n",
395 "",
396 false,
397 false,
398 },
399 };
400
401 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
bengr 2014/07/28 21:56:52 i = 0
xingx1 2014/07/30 03:44:21 Done.
402 DataReductionProxyTamperDetectionTest::TestFingerprintCommon(test[i],
403 DataReductionProxyTamperDetection::VIA);
404 }
405 }
406
407 // Tests function AreOtherHeadersTampered.
408 TEST_F(DataReductionProxyTamperDetectionTest, OtherHeaders) {
409 // For following testcases, |received_fingerprint| is not the actual
410 // fingerprint from data reduction proxy, instead, the base64 encoded field
411 // is in plain text (within "[]") and needs to be encoded first. For example,
412 // "[12345;]|content-length" needs to be encoded to
413 // "Base64Encoded(MD5(12345;))|content-length" before calling the checking
414 // function.
415 TamperDetectionTestCase test[] = {
416 {
417 "Checks the case that only one header is requested.",
418 "HTTP/1.1 200 OK\n"
419 "Content-Length: 12345\n",
420 "[12345,;]|content-length",
421 false
422 },
423 {
424 "Checks the case that there is only one requested header and it does not"
425 "exist.",
426 "HTTP/1.1 200 OK\n",
427 "[;]|non_exist_header",
428 false
429 },
430 {
431 "Checks the case of multiple headers are requested.",
432 "HTTP/1.1 200 OK\n"
433 "Content-Type: 1\n"
434 "Cache-Control: 2\n"
435 "ETag: 3\n"
436 "Connection: 4\n"
437 "Expires: 5\n",
438 "[1,;2,;3,;4,;5,;]|content-type|cache-control|etag|connection|expires",
439 false
440 },
441 {
442 "Checks the case that one header has multiple values.",
443 "HTTP/1.1 200 OK\n"
444 "Content-Type: aaa1, bbb1, ccc1\n"
445 "Cache-Control: aaa2\n",
446 "[aaa1,bbb1,ccc1,;aaa2,;]|content-type|cache-control",
447 false
448 },
449 {
450 "Checks the case that one header has multiple lines.",
451 "HTTP/1.1 200 OK\n"
452 "Content-Type: aaa1, ccc1\n"
453 "Content-Type: xxx1, bbb1, ccc1\n"
454 "Cache-Control: aaa2\n",
455 "[aaa1,bbb1,ccc1,ccc1,xxx1,;aaa2,;]|content-type|cache-control",
456 false
457 },
458 {
459 "Checks the case that more than one headers have multiple values.",
460 "HTTP/1.1 200 OK\n"
461 "Content-Type: aaa1, ccc1\n"
462 "Cache-Control: ccc2 , bbb2\n"
463 "Content-Type: bbb1, ccc1\n"
464 "Cache-Control: aaa2 \n",
465 "[aaa1,bbb1,ccc1,ccc1,;aaa2,bbb2,ccc2,;]|content-type|cache-control",
466 false
467 },
468 {
469 "Checks the case that one of the requested headers is missing (Expires).",
470 "HTTP/1.1 200 OK\n"
471 "Content-Type: aaa1, ccc1\n",
472 "[aaa1,ccc1,;;]|content-type|expires",
473 false
474 },
475 {
476 "Checks the case that some of the requested headers have empty value.",
477 "HTTP/1.1 200 OK\n"
478 "Content-Type: \n"
479 "Cache-Control: \n",
480 "[,;,;]|content-type|cache-control",
481 false
482 },
483 {
484 "Checks the case that all the requested headers are missing.",
485 "HTTP/1.1 200 OK\n",
486 "[;;]|content-type|expires",
487 false
488 },
489 {
490 "Checks the case that some headers are missing, some of them are empty.",
491 "HTTP/1.1 200 OK\n"
492 "Cache-Control: \n",
493 "[;,;]|content-type|cache-control",
494 false
495 },
496 {
497 "Checks the case there is no requested header (header list is empty).",
498 "HTTP/1.1 200 OK\n"
499 "Chrome-Proxy: aut=aauutthh,bbbypas=0,aaxxx=xxx,bbbloc=1\n"
500 "Content-Type: 1\n"
501 "Cache-Control: 2\n",
502 "[]",
503 false
504 },
505 {
506 "Checks tampered requested header values.",
507 "HTTP/1.1 200 OK\n"
508 "Content-Type: aaa1, ccc1\n"
509 "Cache-Control: ccc2 , bbb2\n",
510 "[aaa1,bbb1,;bbb2,ccc2,;]|content-type|cache-control",
511 true
512 },
513 /* will lead to NOTREACHED() */
514 /*
515 {
516 "Checks the case that base64 decoding fails.",
517 "HTTP/1.1 200 OK\n"
518 "Cache-Control: \n"
519 "Connection: \n"
520 "Expires: 5\n"
521 "Via: \n"
522 "Content-Length: 12345\n",
523 "abcde|content-type|cache-control|etag|connection|expires",
524 true
525 },
526 */
527 };
528
529 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
bengr 2014/07/28 21:56:52 i = 0
xingx1 2014/07/30 03:44:21 Done.
530 ReplaceWithEncodedString(&(test[i].received_fingerprint));
531 DataReductionProxyTamperDetectionTest::TestFingerprintCommon(test[i],
bengr 2014/07/28 21:56:52 Move test[i] to the next line.
xingx1 2014/07/30 03:44:22 Done.
532 DataReductionProxyTamperDetection::OTHERHEADERS);
533 }
534 }
535
536 // Tests function IsContentLengthTampered.
537 TEST_F(DataReductionProxyTamperDetectionTest, ContentLength) {
538 TamperDetectionTestCase test[] = {
539 {
540 "Checks the case fingerprint matches received response.",
541 "HTTP/1.1 200 OK\n"
542 "Content-Length: 12345\n",
543 "12345",
544 false,
545 },
546 {
547 "Checks case that response got modified.",
548 "HTTP/1.1 200 OK\n"
549 "Content-Length: 12345\n",
550 "125",
551 true,
552 },
553 {
554 "Checks the case that the data reduction proxy has not sent"
555 "Content-Length header.",
556 "HTTP/1.1 200 OK\n"
557 "Content-Length: 12345\n",
558 "",
559 false,
560 },
561 {
562 "Checks the case that the data reduction proxy sends invalid"
563 "Content-Length header.",
564 "HTTP/1.1 200 OK\n"
565 "Content-Length: 12345\n",
566 "aaa",
567 false,
568 },
569 {
570 "Checks the case that the data reduction proxy sends invalid"
571 "Content-Length header.",
572 "HTTP/1.1 200 OK\n"
573 "Content-Length: aaa\n",
574 "aaa",
575 false,
576 },
577 {
578 "Checks the case that Content-Length header is missing at the Chromium"
579 "client side.",
580 "HTTP/1.1 200 OK\n",
581 "123",
582 false,
583 },
584 {
585 "Checks the case that Content-Length header are missing at both end.",
586 "HTTP/1.1 200 OK\n",
587 "",
588 false,
589 },
590 };
591
592 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
593 DataReductionProxyTamperDetectionTest::TestFingerprintCommon(test[i],
594 DataReductionProxyTamperDetection::CONTENTLENGTH);
595 }
596 }
597
598 // Tests RemoveChromeProxyFingerprint function.
599 TEST_F(DataReductionProxyTamperDetectionTest, HeaderRemoving) {
600 struct {
601 std::string label;
602 std::string input_values[kMaxVectorSize];
603 std::string expected_output_values[kMaxVectorSize];
604 } test[] = {
605 {
606 "Checks the case that there is no Chrome-Proxy header's fingerprint.",
607 {"1", "2", "3", "5",},
608 {"1", "2", "3", "5",},
609 },
610 {
611 "Checks the case that there is Chrome-Proxy header's fingerprint.",
612 {"1", "2", "3", "fcp=4", "5",},
613 {"1", "2", "3", "5",},
614 },
615 {
616 "Checks the case that there is Chrome-Proxy header's fingerprint, and it"
617 "occurs at the end.",
618 {"1", "2", "3", "fcp=4",},
619 {"1", "2", "3",},
620 },
621 {
622 "Checks the case that there is Chrome-Proxy header's fingerprint, and it"
623 "occurs at the beginning.",
624 {"fcp=1", "2", "3",},
625 {"2", "3",},
626 },
627 };
628
629 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
630 std::vector<std::string> input_values =
631 StringsToVector(test[i].input_values);
632 std::vector<std::string> output_values =
633 StringsToVector(test[i].expected_output_values);
634
635 DataReductionProxyTamperDetection::RemoveChromeProxyFingerprint(
636 &input_values);
637
638 EXPECT_EQ(input_values, output_values) << test[i].label;
639 }
640 }
641
642 // Tests ValuesToSortedString function.
643 TEST_F(DataReductionProxyTamperDetectionTest, ValuesToSortedString) {
644 struct {
645 std::string label;
646 std::string input_values[kMaxVectorSize];
647 std::string expected_output_string;
648 } test[] = {
649 {
650 "Checks the correctness of sorting.",
651 {"1", "2", "3",},
652 "1,2,3,",
653 },
654 {
655 "Checks the case that there is an empty input vector.",
656 {},
657 "",
658 },
659 {
660 "Checks the case that there is an empty string in the input vector.",
661 // Use " " to represent empty value.
662 {" ",},
663 ",",
664 },
665 };
666
667 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
bengr 2014/07/28 21:56:53 i = 0
xingx1 2014/07/30 03:44:22 Done.
668 std::vector<std::string> input_values =
669 StringsToVector(test[i].input_values);
670
671 std::string output_string = DataReductionProxyTamperDetection::
bengr 2014/07/28 21:56:52 Can DataReduction.. fit on the next line?
xingx1 2014/07/30 03:44:22 Done.
672 ValuesToSortedString(&input_values);
673
674 EXPECT_EQ(output_string, test[i].expected_output_string) << test[i].label;
675 }
676 }
677
678 // Tests GetHeaderValues function.
679 TEST_F(DataReductionProxyTamperDetectionTest, GetHeaderValues) {
680 struct {
681 std::string label;
682 std::string raw_header;
683 std::string header_name;
684 std::string expected_output_values[kMaxVectorSize];
685 } test[] = {
686 {
687 "Checks the correctness of getting single line header.",
688 "HTTP/1.1 200 OK\n"
689 "test: 1, 2, 3\n",
690 "test",
691 {"1", "2", "3"},
692 },
693 {
694 "Checks the correctness of getting multiple lines header.",
695 "HTTP/1.1 200 OK\n"
696 "test: 1, 2, 3\n"
697 "test: 4, 5, 6\n"
698 "test: 7, 8, 9\n",
699 "test",
700 {"1", "2", "3", "4", "5", "6", "7", "8", "9"},
701 },
702 {
703 "Checks the correctness of getting missing header.",
704 "HTTP/1.1 200 OK\n",
705 "test",
706 {},
707 },
708 {
709 "Checks the correctness of getting empty header.",
710 "HTTP/1.1 200 OK\n"
711 "test: \n",
712 "test",
713 {" "},
714 },
715 };
716
717 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
bengr 2014/07/28 21:56:52 i = 0
xingx1 2014/07/30 03:44:22 Done.
718 std::string raw_headers(test[i].raw_header);
719 HeadersToRaw(&raw_headers);
720 net::HttpResponseHeaders* headers =
721 new net::HttpResponseHeaders(raw_headers);
722
723 std::vector<std::string> expected_output_values =
724 StringsToVector(test[i].expected_output_values);
725
726 std::vector<std::string> output_values =
727 DataReductionProxyTamperDetection::GetHeaderValues(
728 headers, test[i].header_name);
729 EXPECT_EQ(expected_output_values, output_values) << test[i].label;
730 }
731 }
732
733 // Tests main function DetectAndReport.
734 TEST_F(DataReductionProxyTamperDetectionTest, DetectAndReport) {
735 struct {
736 std::string label;
737 std::string raw_header;
738 bool expected_tampered_with;
739 } test[] = {
740 {
741 "Check no fingerprint added case.",
742 "HTTP/1.1 200 OK\n"
743 "Via: a1, b2, 1.1 Chrome-Compression-Proxy\n"
744 "Content-Length: 12345\n"
745 "Chrome-Proxy: bypass=0\n",
746 false,
747 },
748 {
749 "Check the case Chrome-Proxy fingerprint doesn't match.",
750 "HTTP/1.1 200 OK\n"
751 "Via: a1, b2, 1.1 Chrome-Compression-Proxy\n"
752 "Content-Length: 12345\n"
753 "header1: header_1\n"
754 "header2: header_2\n"
755 "header3: header_3\n"
756 "Chrome-Proxy: fcl=12345, "
757 "foh=[header_1,;header_2,;header_3,;]|header1|header2|header3,fvia=0,"
758 "fcp=abc\n",
759 true,
760 },
761 {
762 "Check the case response matches the fingerprint completely.",
763 "HTTP/1.1 200 OK\n"
764 "Via: a1, b2, 1.1 Chrome-Compression-Proxy\n"
765 "Content-Length: 12345\n"
766 "header1: header_1\n"
767 "header2: header_2\n"
768 "header3: header_3\n"
769 "Chrome-Proxy: fcl=12345, "
770 "foh=[header_1,;header_2,;header_3,;]|header1|header2|header3,"
771 "fvia=0, fcp=[fcl=12345,foh=[header_1,;header_2,;header_3,;]"
772 "|header1|header2|header3,fvia=0,]\n",
773 false,
774 },
775 {
776 "Check the case that Content-Length doesn't match.",
777 "HTTP/1.1 200 OK\n"
778 "Via: a1, b2, 1.1 Chrome-Compression-Proxy\n"
779 "Content-Length: 0\n"
780 "header1: header_1\n"
781 "header2: header_2\n"
782 "header3: header_3\n"
783 "Chrome-Proxy: fcl=12345, "
784 "foh=[header_1,;header_2,;header_3,;]|header1|header2|header3, fvia=0, "
785 "fcp=[fcl=12345,foh=[header_1,;header_2,;header_3,;]|"
786 "header1|header2|header3,fvia=0,]\n",
787 true,
788 },
789 };
790
791 #if defined(OS_ANDROID)
792 JNIEnv* env = base::android::AttachCurrentThread();
793 net::android::RegisterNetworkLibrary(env);
794 #endif
795
796 for (size_t i=0; i<ARRAYSIZE_UNSAFE(test); ++i) {
bengr 2014/07/28 21:56:52 i = 0
xingx1 2014/07/30 03:44:21 Done.
797 std::string raw_headers(test[i].raw_header);
798 ReplaceWithEncodedString(&raw_headers);
799 HeadersToRaw(&raw_headers);
800 net::HttpResponseHeaders* headers =
801 new net::HttpResponseHeaders(raw_headers);
802
803 EXPECT_EQ(test[i].expected_tampered_with,
804 DataReductionProxyTamperDetection::DetectAndReport(headers, true))
805 << test[i].label;
806 }
807 }
808
809 } // namespace
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698