OLD | NEW |
---|---|
(Empty) | |
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 | |
3 // found in the LICENSE file. | |
4 | |
5 #include "base/base64.h" | |
6 #include "base/sha1.h" | |
7 #include "base/string_piece.h" | |
8 #include "crypto/sha2.h" | |
9 #include "net/base/asn1_util.h" | |
10 #include "net/base/cert_test_util.h" | |
11 #include "net/base/cert_verifier.h" | |
12 #include "net/base/cert_verify_result.h" | |
13 #include "net/base/net_log.h" | |
14 #include "net/base/ssl_info.h" | |
15 #include "net/base/test_completion_callback.h" | |
16 #include "net/base/test_root_certs.h" | |
17 #include "net/http/http_security_headers.h" | |
18 #include "net/http/http_util.h" | |
19 #include "testing/gtest/include/gtest/gtest.h" | |
20 | |
21 | |
22 namespace net { | |
23 | |
24 class HttpSecurityHeadersTest : public testing::Test { | |
25 }; | |
26 | |
27 static bool GetPublicKeyHash(const net::X509Certificate::OSCertHandle& cert, | |
Ryan Sleevi
2012/10/25 01:59:09
nit: see previous nit regarding unnamed namespaces
unsafe
2012/10/25 06:59:54
This is pre-existing code moved from TSS_unit_test
| |
28 HashValue* hash) { | |
29 std::string der_bytes; | |
30 if (!net::X509Certificate::GetDEREncoded(cert, &der_bytes)) | |
31 return false; | |
32 base::StringPiece spki; | |
33 if (!asn1::ExtractSPKIFromDERCert(der_bytes, &spki)) | |
34 return false; | |
35 | |
36 switch (hash->tag) { | |
37 case HASH_VALUE_SHA1: | |
38 base::SHA1HashBytes(reinterpret_cast<const unsigned char*>(spki.data()), | |
39 spki.size(), hash->data()); | |
40 break; | |
41 case HASH_VALUE_SHA256: | |
42 crypto::SHA256HashString(spki, hash->data(), crypto::kSHA256Length); | |
43 break; | |
44 default: | |
45 NOTREACHED() << "Unknown HashValueTag " << hash->tag; | |
Ryan Sleevi
2012/10/25 01:59:09
BUG: return false ?
unsafe
2012/10/25 06:59:54
Pre-existing issue (but fixed).
| |
46 } | |
47 | |
48 return true; | |
49 } | |
50 | |
51 static std::string GetPinFromCert(X509Certificate* cert, HashValueTag tag) { | |
52 HashValue spki_hash(tag); | |
53 EXPECT_TRUE(GetPublicKeyHash(cert->os_cert_handle(), &spki_hash)); | |
54 | |
55 std::string base64; | |
56 base::Base64Encode(base::StringPiece( | |
57 reinterpret_cast<char*>(spki_hash.data()), spki_hash.size()), &base64); | |
Ryan Sleevi
2012/10/25 01:59:09
design: Why not use the existing functions you add
unsafe
2012/10/25 06:59:54
Those functions use the type/base64 format, not th
| |
58 | |
59 std::string label; | |
60 switch (tag) { | |
61 case HASH_VALUE_SHA1: | |
62 label = "pin-sha1="; | |
63 break; | |
64 case HASH_VALUE_SHA256: | |
65 label = "pin-sha256="; | |
66 break; | |
67 default: | |
68 NOTREACHED() << "Unknown HashValueTag " << tag; | |
69 } | |
70 | |
71 return label + HttpUtil::Quote(base64); | |
Ryan Sleevi
2012/10/25 01:59:09
nit: It's not required to be quoted, is it?
unsafe
2012/10/25 06:59:54
Not my code - the base64 is required to have quote
| |
72 } | |
73 | |
74 TEST_F(HttpSecurityHeadersTest, BogusHeaders) { | |
75 base::Time now = base::Time::Now(); | |
76 base::Time expiry = now; | |
77 bool include_subdomains = false; | |
78 | |
79 EXPECT_FALSE(ParseHSTSHeader(now, "", &expiry, &include_subdomains)); | |
80 EXPECT_FALSE(ParseHSTSHeader(now, " ", &expiry, &include_subdomains)); | |
81 EXPECT_FALSE(ParseHSTSHeader(now, "abc", &expiry, &include_subdomains)); | |
82 EXPECT_FALSE(ParseHSTSHeader(now, " abc", &expiry, &include_subdomains)); | |
83 EXPECT_FALSE(ParseHSTSHeader(now, " abc ", &expiry, &include_subdomains)); | |
84 EXPECT_FALSE(ParseHSTSHeader(now, "max-age", &expiry, &include_subdomains)); | |
85 EXPECT_FALSE(ParseHSTSHeader(now, " max-age", &expiry, | |
86 &include_subdomains)); | |
87 EXPECT_FALSE(ParseHSTSHeader(now, " max-age ", &expiry, | |
88 &include_subdomains)); | |
89 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=", &expiry, &include_subdomains)); | |
90 EXPECT_FALSE(ParseHSTSHeader(now, " max-age=", &expiry, | |
91 &include_subdomains)); | |
92 EXPECT_FALSE(ParseHSTSHeader(now, " max-age =", &expiry, | |
93 &include_subdomains)); | |
94 EXPECT_FALSE(ParseHSTSHeader(now, " max-age= ", &expiry, | |
95 &include_subdomains)); | |
96 EXPECT_FALSE(ParseHSTSHeader(now, " max-age = ", &expiry, | |
97 &include_subdomains)); | |
98 EXPECT_FALSE(ParseHSTSHeader(now, " max-age = xy", &expiry, | |
99 &include_subdomains)); | |
100 EXPECT_FALSE(ParseHSTSHeader(now, " max-age = 3488a923", &expiry, | |
101 &include_subdomains)); | |
102 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488a923 ", &expiry, | |
103 &include_subdomains)); | |
104 EXPECT_FALSE(ParseHSTSHeader(now, "max-ag=3488923", &expiry, | |
105 &include_subdomains)); | |
106 EXPECT_FALSE(ParseHSTSHeader(now, "max-aged=3488923", &expiry, | |
107 &include_subdomains)); | |
108 EXPECT_FALSE(ParseHSTSHeader(now, "max-age==3488923", &expiry, | |
109 &include_subdomains)); | |
110 EXPECT_FALSE(ParseHSTSHeader(now, "amax-age=3488923", &expiry, | |
111 &include_subdomains)); | |
112 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=-3488923", &expiry, | |
113 &include_subdomains)); | |
114 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923;", &expiry, | |
115 &include_subdomains)); | |
116 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923 e", &expiry, | |
117 &include_subdomains)); | |
118 EXPECT_FALSE(ParseHSTSHeader(now, | |
119 "max-age=3488923 includesubdomain", | |
120 &expiry, &include_subdomains)); | |
121 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923includesubdomains", | |
122 &expiry, &include_subdomains)); | |
123 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923=includesubdomains", | |
124 &expiry, &include_subdomains)); | |
125 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923 includesubdomainx", | |
126 &expiry, &include_subdomains)); | |
127 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923 includesubdomain=", | |
128 &expiry, &include_subdomains)); | |
129 EXPECT_FALSE(ParseHSTSHeader(now, | |
130 "max-age=3488923 includesubdomain=true", | |
131 &expiry, &include_subdomains)); | |
132 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=3488923 includesubdomainsx", | |
133 &expiry, &include_subdomains)); | |
134 EXPECT_FALSE(ParseHSTSHeader(now, | |
135 "max-age=3488923 includesubdomains x", | |
136 &expiry, &include_subdomains)); | |
137 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=34889.23 includesubdomains", | |
138 &expiry, &include_subdomains)); | |
139 EXPECT_FALSE(ParseHSTSHeader(now, "max-age=34889 includesubdomains", | |
140 &expiry, &include_subdomains)); | |
141 | |
142 // Check the out args were not updated by checking the default | |
143 // values for its predictable fields. | |
144 EXPECT_EQ(now, expiry); | |
145 EXPECT_FALSE(include_subdomains); | |
146 } | |
147 | |
148 static void TestBogusPinsHeaders(HashValueTag tag) { | |
149 base::Time now = base::Time::Now(); | |
150 base::Time expiry = now; | |
151 HashValueVector hashes; | |
152 | |
153 SSLInfo ssl_info; | |
154 ssl_info.cert = | |
155 ImportCertFromFile(GetTestCertsDirectory(), "test_mail_google_com.pem"); | |
156 std::string good_pin = GetPinFromCert(ssl_info.cert, tag); | |
157 | |
158 // The backup pin is fake --- it just has to not be in the chain. | |
159 std::string backup_pin = "pin-sha1=" + | |
160 HttpUtil::Quote("6dcfXufJLW3J6S/9rRe4vUlBj5g="); | |
161 | |
162 EXPECT_FALSE(ParseHPKPHeader(now, "", ssl_info, &expiry, &hashes)); | |
163 EXPECT_FALSE(ParseHPKPHeader(now, " ", ssl_info, &expiry, &hashes)); | |
164 EXPECT_FALSE(ParseHPKPHeader(now, "abc", ssl_info, &expiry, &hashes)); | |
165 EXPECT_FALSE(ParseHPKPHeader(now, " abc", ssl_info, &expiry, &hashes)); | |
166 EXPECT_FALSE(ParseHPKPHeader(now, " abc ", ssl_info, &expiry, &hashes)); | |
167 EXPECT_FALSE(ParseHPKPHeader(now, "max-age", ssl_info, &expiry, &hashes)); | |
168 EXPECT_FALSE(ParseHPKPHeader(now, " max-age", ssl_info, &expiry, &hashes)); | |
169 EXPECT_FALSE(ParseHPKPHeader(now, " max-age ", ssl_info, &expiry, | |
170 &hashes)); | |
171 EXPECT_FALSE(ParseHPKPHeader(now, "max-age=", ssl_info, &expiry, &hashes)); | |
172 EXPECT_FALSE(ParseHPKPHeader(now, " max-age=", ssl_info, &expiry, | |
173 &hashes)); | |
174 EXPECT_FALSE(ParseHPKPHeader(now, " max-age =", ssl_info, &expiry, | |
175 &hashes)); | |
176 EXPECT_FALSE(ParseHPKPHeader(now, " max-age= ", ssl_info, &expiry, | |
177 &hashes)); | |
178 EXPECT_FALSE(ParseHPKPHeader(now, " max-age = ", ssl_info, &expiry, | |
179 &hashes)); | |
180 EXPECT_FALSE(ParseHPKPHeader(now, " max-age = xy", ssl_info, | |
181 &expiry, &hashes)); | |
182 EXPECT_FALSE(ParseHPKPHeader(now, | |
183 " max-age = 3488a923", | |
184 ssl_info, &expiry, &hashes)); | |
185 EXPECT_FALSE(ParseHPKPHeader(now, "max-age=3488a923 ", ssl_info, &expiry, | |
186 &hashes)); | |
187 EXPECT_FALSE(ParseHPKPHeader(now, | |
188 "max-ag=3488923pins=" + good_pin + "," + | |
189 backup_pin, | |
190 ssl_info, &expiry, &hashes)); | |
191 EXPECT_FALSE(ParseHPKPHeader(now, "max-aged=3488923" + backup_pin, | |
192 ssl_info, &expiry, &hashes)); | |
193 EXPECT_FALSE(ParseHPKPHeader(now, "max-aged=3488923; " + backup_pin, | |
194 ssl_info, &expiry, &hashes)); | |
195 EXPECT_FALSE(ParseHPKPHeader(now, | |
196 "max-aged=3488923; " + backup_pin + ";" + | |
197 backup_pin, | |
198 ssl_info, &expiry, &hashes)); | |
199 EXPECT_FALSE(ParseHPKPHeader(now, | |
200 "max-aged=3488923; " + good_pin + ";" + | |
201 good_pin, | |
202 ssl_info, &expiry, &hashes)); | |
203 EXPECT_FALSE(ParseHPKPHeader(now, "max-aged=3488923; " + good_pin, | |
204 ssl_info, &expiry, &hashes)); | |
205 EXPECT_FALSE(ParseHPKPHeader(now, "max-age==3488923", ssl_info, &expiry, | |
206 &hashes)); | |
207 EXPECT_FALSE(ParseHPKPHeader(now, "amax-age=3488923", ssl_info, &expiry, | |
208 &hashes)); | |
209 EXPECT_FALSE(ParseHPKPHeader(now, "max-age=-3488923", ssl_info, &expiry, | |
210 &hashes)); | |
211 EXPECT_FALSE(ParseHPKPHeader(now, "max-age=3488923;", ssl_info, &expiry, | |
212 &hashes)); | |
213 EXPECT_FALSE(ParseHPKPHeader(now, "max-age=3488923 e", ssl_info, | |
214 &expiry, &hashes)); | |
215 EXPECT_FALSE(ParseHPKPHeader(now, | |
216 "max-age=3488923 includesubdomain", | |
217 ssl_info, &expiry, &hashes)); | |
218 EXPECT_FALSE(ParseHPKPHeader(now, "max-age=34889.23", ssl_info, &expiry, | |
219 &hashes)); | |
220 | |
221 // Check the out args were not updated by checking the default | |
222 // values for its predictable fields. | |
223 EXPECT_EQ(now, expiry); | |
224 EXPECT_EQ(hashes.size(), (size_t)0); | |
225 } | |
226 | |
227 TEST_F(HttpSecurityHeadersTest, ValidSTSHeaders) { | |
228 base::Time now = base::Time::Now(); | |
229 base::Time expiry = now; | |
230 base::Time expect_expiry = now; | |
231 bool include_subdomains = false; | |
232 | |
233 EXPECT_TRUE(ParseHSTSHeader(now, "max-age=243", &expiry, | |
234 &include_subdomains)); | |
235 expect_expiry = now + base::TimeDelta::FromSeconds(243); | |
236 EXPECT_EQ(expect_expiry, expiry); | |
237 EXPECT_FALSE(include_subdomains); | |
238 | |
239 EXPECT_TRUE(ParseHSTSHeader(now, " Max-agE = 567", &expiry, | |
240 &include_subdomains)); | |
241 expect_expiry = now + base::TimeDelta::FromSeconds(567); | |
242 EXPECT_EQ(expect_expiry, expiry); | |
243 EXPECT_FALSE(include_subdomains); | |
244 | |
245 EXPECT_TRUE(ParseHSTSHeader(now, " mAx-aGe = 890 ", &expiry, | |
246 &include_subdomains)); | |
247 expect_expiry = now + base::TimeDelta::FromSeconds(890); | |
248 EXPECT_EQ(expect_expiry, expiry); | |
249 EXPECT_FALSE(include_subdomains); | |
250 | |
251 EXPECT_TRUE(ParseHSTSHeader(now, "max-age=123;incLudesUbdOmains", &expiry, | |
252 &include_subdomains)); | |
253 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
254 EXPECT_EQ(expect_expiry, expiry); | |
255 EXPECT_TRUE(include_subdomains); | |
256 | |
257 EXPECT_TRUE(ParseHSTSHeader(now, "incLudesUbdOmains; max-age=123", &expiry, | |
258 &include_subdomains)); | |
259 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
260 EXPECT_EQ(expect_expiry, expiry); | |
261 EXPECT_TRUE(include_subdomains); | |
262 | |
263 EXPECT_TRUE(ParseHSTSHeader(now, " incLudesUbdOmains; max-age=123", | |
264 &expiry, &include_subdomains)); | |
265 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
266 EXPECT_EQ(expect_expiry, expiry); | |
267 EXPECT_TRUE(include_subdomains); | |
268 | |
269 EXPECT_TRUE(ParseHSTSHeader(now, | |
270 " incLudesUbdOmains; max-age=123; pumpkin=kitten", &expiry, | |
271 &include_subdomains)); | |
272 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
273 EXPECT_EQ(expect_expiry, expiry); | |
274 EXPECT_TRUE(include_subdomains); | |
275 | |
276 EXPECT_TRUE(ParseHSTSHeader(now, | |
277 " pumpkin=894; incLudesUbdOmains; max-age=123 ", &expiry, | |
278 &include_subdomains)); | |
279 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
280 EXPECT_EQ(expect_expiry, expiry); | |
281 EXPECT_TRUE(include_subdomains); | |
282 | |
283 EXPECT_TRUE(ParseHSTSHeader(now, | |
284 " pumpkin; incLudesUbdOmains; max-age=123 ", &expiry, | |
285 &include_subdomains)); | |
286 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
287 EXPECT_EQ(expect_expiry, expiry); | |
288 EXPECT_TRUE(include_subdomains); | |
289 | |
290 EXPECT_TRUE(ParseHSTSHeader(now, | |
291 " pumpkin; incLudesUbdOmains; max-age=\"123\" ", &expiry, | |
292 &include_subdomains)); | |
293 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
294 EXPECT_EQ(expect_expiry, expiry); | |
295 EXPECT_TRUE(include_subdomains); | |
296 | |
297 EXPECT_TRUE(ParseHSTSHeader(now, | |
298 "animal=\"squirrel; distinguished\"; incLudesUbdOmains; max-age=123", | |
299 &expiry, &include_subdomains)); | |
300 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
301 EXPECT_EQ(expect_expiry, expiry); | |
302 EXPECT_TRUE(include_subdomains); | |
303 | |
304 EXPECT_TRUE(ParseHSTSHeader(now, "max-age=394082; incLudesUbdOmains", | |
305 &expiry, &include_subdomains)); | |
306 expect_expiry = now + base::TimeDelta::FromSeconds(394082); | |
307 EXPECT_EQ(expect_expiry, expiry); | |
308 EXPECT_TRUE(include_subdomains); | |
309 | |
310 EXPECT_TRUE(ParseHSTSHeader( | |
311 now, "max-age=39408299 ;incLudesUbdOmains", &expiry, | |
312 &include_subdomains)); | |
313 expect_expiry = now + base::TimeDelta::FromSeconds( | |
314 std::min(kMaxHSTSAgeSecs, 39408299l)); | |
315 EXPECT_EQ(expect_expiry, expiry); | |
316 EXPECT_TRUE(include_subdomains); | |
317 | |
318 EXPECT_TRUE(ParseHSTSHeader( | |
319 now, "max-age=394082038 ; incLudesUbdOmains", &expiry, | |
320 &include_subdomains)); | |
321 expect_expiry = now + base::TimeDelta::FromSeconds( | |
322 std::min(kMaxHSTSAgeSecs, 394082038l)); | |
323 EXPECT_EQ(expect_expiry, expiry); | |
324 EXPECT_TRUE(include_subdomains); | |
325 | |
326 EXPECT_TRUE(ParseHSTSHeader( | |
327 now, " max-age=0 ; incLudesUbdOmains ", &expiry, | |
328 &include_subdomains)); | |
329 expect_expiry = now + base::TimeDelta::FromSeconds(0); | |
330 EXPECT_EQ(expect_expiry, expiry); | |
331 EXPECT_TRUE(include_subdomains); | |
332 | |
333 EXPECT_TRUE(ParseHSTSHeader( | |
334 now, | |
335 " max-age=999999999999999999999999999999999999999999999 ;" | |
336 " incLudesUbdOmains ", &expiry, &include_subdomains)); | |
337 expect_expiry = now + base::TimeDelta::FromSeconds( | |
338 kMaxHSTSAgeSecs); | |
339 EXPECT_EQ(expect_expiry, expiry); | |
340 EXPECT_TRUE(include_subdomains); | |
341 } | |
342 | |
343 static void TestValidPinsHeaders(HashValueTag tag) { | |
344 base::Time now = base::Time::Now(); | |
345 base::Time expiry = now; | |
346 base::Time expect_expiry = now; | |
347 HashValueVector hashes; | |
348 | |
349 // Set up a realistic SSLInfo with a realistic cert chain. | |
350 FilePath certs_dir = GetTestCertsDirectory(); | |
351 scoped_refptr<X509Certificate> ee_cert = | |
352 ImportCertFromFile(certs_dir, | |
353 "2048-rsa-ee-by-2048-rsa-intermediate.pem"); | |
354 ASSERT_NE(static_cast<X509Certificate*>(NULL), ee_cert); | |
355 scoped_refptr<X509Certificate> intermediate = | |
356 ImportCertFromFile(certs_dir, "2048-rsa-intermediate.pem"); | |
357 ASSERT_NE(static_cast<X509Certificate*>(NULL), intermediate); | |
358 X509Certificate::OSCertHandles intermediates; | |
359 intermediates.push_back(intermediate->os_cert_handle()); | |
360 SSLInfo ssl_info; | |
361 ssl_info.cert = X509Certificate::CreateFromHandle(ee_cert->os_cert_handle(), | |
362 intermediates); | |
363 | |
364 // Add the root that signed the intermediate for this test. | |
365 scoped_refptr<X509Certificate> root_cert = | |
366 ImportCertFromFile(certs_dir, "2048-rsa-root.pem"); | |
367 ASSERT_NE(static_cast<X509Certificate*>(NULL), root_cert); | |
368 ScopedTestRoot scoped_root(root_cert); | |
369 | |
370 // Verify has the side-effect of populating public_key_hashes, which | |
371 // ParsePinsHeader needs. (It wants to check pins against the validated | |
372 // chain, not just the presented chain.) | |
373 int rv = ERR_FAILED; | |
374 CertVerifyResult result; | |
375 scoped_ptr<CertVerifier> verifier(CertVerifier::CreateDefault()); | |
376 TestCompletionCallback callback; | |
377 CertVerifier::RequestHandle handle = NULL; | |
378 rv = verifier->Verify(ssl_info.cert, "127.0.0.1", 0, NULL, &result, | |
379 callback.callback(), &handle, BoundNetLog()); | |
380 rv = callback.GetResult(rv); | |
381 ASSERT_EQ(OK, rv); | |
382 // Normally, ssl_client_socket_nss would do this, but for a unit test we | |
383 // fake it. | |
384 ssl_info.public_key_hashes = result.public_key_hashes; | |
385 std::string good_pin = GetPinFromCert(ssl_info.cert, /*tag*/HASH_VALUE_SHA1); | |
386 DLOG(WARNING) << "good pin: " << good_pin; | |
387 | |
388 // The backup pin is fake --- we just need an SPKI hash that does not match | |
389 // the hash of any SPKI in the certificate chain. | |
390 std::string backup_pin = "pin-sha1=" + | |
391 HttpUtil::Quote("6dcfXufJLW3J6S/9rRe4vUlBj5g="); | |
392 | |
393 EXPECT_TRUE(ParseHPKPHeader( | |
394 now, | |
395 "max-age=243; " + good_pin + ";" + backup_pin, | |
396 ssl_info, &expiry, &hashes)); | |
397 expect_expiry = now + base::TimeDelta::FromSeconds(243); | |
398 EXPECT_EQ(expect_expiry, expiry); | |
399 | |
400 EXPECT_TRUE(ParseHPKPHeader( | |
401 now, | |
402 " " + good_pin + "; " + backup_pin + " ; Max-agE = 567", | |
403 ssl_info, &expiry, &hashes)); | |
404 expect_expiry = now + base::TimeDelta::FromSeconds(567); | |
405 EXPECT_EQ(expect_expiry, expiry); | |
406 | |
407 EXPECT_TRUE(ParseHPKPHeader( | |
408 now, | |
409 good_pin + ";" + backup_pin + " ; mAx-aGe = 890 ", | |
410 ssl_info, &expiry, &hashes)); | |
411 expect_expiry = now + base::TimeDelta::FromSeconds(890); | |
412 EXPECT_EQ(expect_expiry, expiry); | |
413 | |
414 EXPECT_TRUE(ParseHPKPHeader( | |
415 now, | |
416 good_pin + ";" + backup_pin + "; max-age=123;IGNORED;", | |
417 ssl_info, &expiry, &hashes)); | |
418 expect_expiry = now + base::TimeDelta::FromSeconds(123); | |
419 EXPECT_EQ(expect_expiry, expiry); | |
420 | |
421 EXPECT_TRUE(ParseHPKPHeader( | |
422 now, | |
423 "max-age=394082;" + backup_pin + ";" + good_pin + "; ", | |
424 ssl_info, &expiry, &hashes)); | |
425 expect_expiry = now + base::TimeDelta::FromSeconds(394082); | |
426 EXPECT_EQ(expect_expiry, expiry); | |
427 | |
428 EXPECT_TRUE(ParseHPKPHeader( | |
429 now, | |
430 "max-age=39408299 ;" + backup_pin + ";" + good_pin + "; ", | |
431 ssl_info, &expiry, &hashes)); | |
432 expect_expiry = now + base::TimeDelta::FromSeconds( | |
433 std::min(kMaxHSTSAgeSecs, 39408299l)); | |
434 EXPECT_EQ(expect_expiry, expiry); | |
435 | |
436 EXPECT_TRUE(ParseHPKPHeader( | |
437 now, | |
438 "max-age=39408038 ; cybers=39408038 ; " + | |
439 good_pin + ";" + backup_pin + "; ", | |
440 ssl_info, &expiry, &hashes)); | |
441 expect_expiry = now + base::TimeDelta::FromSeconds( | |
442 std::min(kMaxHSTSAgeSecs, 394082038l)); | |
443 EXPECT_EQ(expect_expiry, expiry); | |
444 | |
445 EXPECT_TRUE(ParseHPKPHeader( | |
446 now, | |
447 " max-age=0 ; " + good_pin + ";" + backup_pin, | |
448 ssl_info, &expiry, &hashes)); | |
449 expect_expiry = now + base::TimeDelta::FromSeconds(0); | |
450 EXPECT_EQ(expect_expiry, expiry); | |
451 | |
452 EXPECT_TRUE(ParseHPKPHeader( | |
453 now, | |
454 " max-age=999999999999999999999999999999999999999999999 ; " + | |
455 backup_pin + ";" + good_pin + "; ", | |
456 ssl_info, &expiry, &hashes)); | |
457 expect_expiry = now + | |
458 base::TimeDelta::FromSeconds(kMaxHSTSAgeSecs); | |
459 EXPECT_EQ(expect_expiry, expiry); | |
460 } | |
461 | |
462 TEST_F(HttpSecurityHeadersTest, BogusPinsHeadersSHA1) { | |
463 TestBogusPinsHeaders(HASH_VALUE_SHA1); | |
464 } | |
465 | |
466 TEST_F(HttpSecurityHeadersTest, BogusPinsHeadersSHA256) { | |
467 TestBogusPinsHeaders(HASH_VALUE_SHA256); | |
468 } | |
469 | |
470 TEST_F(HttpSecurityHeadersTest, ValidPinsHeadersSHA1) { | |
471 TestValidPinsHeaders(HASH_VALUE_SHA1); | |
472 } | |
473 | |
474 TEST_F(HttpSecurityHeadersTest, ValidPinsHeadersSHA256) { | |
475 TestValidPinsHeaders(HASH_VALUE_SHA256); | |
476 } | |
477 }; | |
478 | |
OLD | NEW |