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.
5 #include "chrome/browser/ssl/chrome_ssl_host_state_delegate.h"
9 #include "base/command_line.h"
10 #include "base/strings/string_number_conversions.h"
11 #include "base/test/simple_test_clock.h"
12 #include "chrome/browser/browsing_data/browsing_data_helper.h"
13 #include "chrome/browser/browsing_data/browsing_data_remover.h"
14 #include "chrome/browser/browsing_data/browsing_data_remover_test_util.h"
15 #include "chrome/browser/profiles/profile.h"
16 #include "chrome/browser/ssl/chrome_ssl_host_state_delegate_factory.h"
17 #include "chrome/browser/ui/browser.h"
18 #include "chrome/browser/ui/tabs/tab_strip_model.h"
19 #include "chrome/common/chrome_switches.h"
20 #include "chrome/test/base/in_process_browser_test.h"
21 #include "content/public/browser/ssl_host_state_delegate.h"
22 #include "content/public/browser/web_contents.h"
23 #include "content/public/test/browser_test_utils.h"
24 #include "net/base/test_data_directory.h"
25 #include "net/test/cert_test_util.h"
26 #include "testing/gtest/include/gtest/gtest.h"
30 const char kOkCertFile
[] = "ok_cert.pem";
32 const char kWWWGoogleHost
[] = "www.google.com";
33 const char kGoogleHost
[] = "google.com";
34 const char kExampleHost
[] = "example.com";
36 const uint64_t kDeltaOneDayInSeconds
= UINT64_C(86400);
37 const uint64_t kDeltaOneWeekInSeconds
= UINT64_C(604800);
39 scoped_refptr
<net::X509Certificate
> GetOkCert() {
40 return net::ImportCertFromFile(net::GetTestCertsDirectory(), kOkCertFile
);
43 // Helper function for setting Finch options
44 void SetFinchConfig(base::CommandLine
* command_line
, const std::string
& group
) {
45 command_line
->AppendSwitchASCII("--force-fieldtrials",
46 "RevertCertificateErrorDecisions/" + group
);
51 class ChromeSSLHostStateDelegateTest
: public InProcessBrowserTest
{};
53 // ChromeSSLHostStateDelegateTest tests basic unit test functionality of the
54 // SSLHostStateDelegate class. For example, tests that if a certificate is
55 // accepted, then it is added to queryable, and if it is revoked, it is not
56 // queryable. Even though it is effectively a unit test, in needs to be an
57 // InProcessBrowserTest because the actual functionality is provided by
58 // ChromeSSLHostStateDelegate which is provided per-profile.
60 // QueryPolicy unit tests the expected behavior of calling QueryPolicy on the
61 // SSLHostStateDelegate class after various SSL cert decisions have been made.
62 IN_PROC_BROWSER_TEST_F(ChromeSSLHostStateDelegateTest
, QueryPolicy
) {
63 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
64 content::WebContents
* tab
=
65 browser()->tab_strip_model()->GetActiveWebContents();
66 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
67 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
70 // Verifying that all three of the certs we will be looking at are denied
71 // before any action has been taken.
72 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
73 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
74 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
75 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
76 state
->QueryPolicy(kGoogleHost
, *cert
,
77 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
78 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
79 state
->QueryPolicy(kExampleHost
, *cert
,
80 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
82 // Simulate a user decision to allow an invalid certificate exception for
84 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
86 // Verify that only kWWWGoogleHost is allowed and that the other two certs
87 // being tested still are denied.
88 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
89 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
90 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
91 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
92 state
->QueryPolicy(kGoogleHost
, *cert
,
93 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
94 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
95 state
->QueryPolicy(kExampleHost
, *cert
,
96 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
98 // Simulate a user decision to allow an invalid certificate exception for
100 state
->AllowCert(kExampleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
102 // Verify that both kWWWGoogleHost and kExampleHost have allow exceptions
103 // while kGoogleHost still is denied.
104 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
105 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
106 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
107 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
108 state
->QueryPolicy(kGoogleHost
, *cert
,
109 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
110 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
111 state
->QueryPolicy(kExampleHost
, *cert
,
112 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
115 // HasPolicyAndRevoke unit tests the expected behavior of calling
116 // HasAllowException before and after calling RevokeUserAllowExceptions on the
117 // SSLHostStateDelegate class.
118 IN_PROC_BROWSER_TEST_F(ChromeSSLHostStateDelegateTest
, HasPolicyAndRevoke
) {
119 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
120 content::WebContents
* tab
=
121 browser()->tab_strip_model()->GetActiveWebContents();
122 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
123 ChromeSSLHostStateDelegate
* state
=
124 ChromeSSLHostStateDelegateFactory::GetForProfile(profile
);
127 // Simulate a user decision to allow an invalid certificate exception for
128 // kWWWGoogleHost and for kExampleHost.
129 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
130 state
->AllowCert(kExampleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
132 // Verify that HasAllowException correctly acknowledges that a user decision
133 // has been made about kWWWGoogleHost. Then verify that HasAllowException
134 // correctly identifies that the decision has been revoked.
135 EXPECT_TRUE(state
->HasAllowException(kWWWGoogleHost
));
136 state
->RevokeUserAllowExceptions(kWWWGoogleHost
);
137 EXPECT_FALSE(state
->HasAllowException(kWWWGoogleHost
));
138 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
139 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
140 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
142 // Verify that the revocation of the kWWWGoogleHost decision does not affect
143 // the Allow for kExampleHost.
144 EXPECT_TRUE(state
->HasAllowException(kExampleHost
));
146 // Verify the revocation of the kWWWGoogleHost decision does not affect the
147 // non-decision for kGoogleHost. Then verify that a revocation of a URL with
148 // no decision has no effect.
149 EXPECT_FALSE(state
->HasAllowException(kGoogleHost
));
150 state
->RevokeUserAllowExceptions(kGoogleHost
);
151 EXPECT_FALSE(state
->HasAllowException(kGoogleHost
));
154 // Clear unit tests the expected behavior of calling Clear to forget all cert
155 // decision state on the SSLHostStateDelegate class.
156 IN_PROC_BROWSER_TEST_F(ChromeSSLHostStateDelegateTest
, Clear
) {
157 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
158 content::WebContents
* tab
=
159 browser()->tab_strip_model()->GetActiveWebContents();
160 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
161 ChromeSSLHostStateDelegate
* state
=
162 ChromeSSLHostStateDelegateFactory::GetForProfile(profile
);
165 // Simulate a user decision to allow an invalid certificate exception for
166 // kWWWGoogleHost and for kExampleHost.
167 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
169 // Do a full clear, then make sure that both kWWWGoogleHost, which had a
170 // decision made, and kExampleHost, which was untouched, are now in a denied
173 EXPECT_FALSE(state
->HasAllowException(kWWWGoogleHost
));
174 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
175 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
176 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
177 EXPECT_FALSE(state
->HasAllowException(kExampleHost
));
178 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
179 state
->QueryPolicy(kExampleHost
, *cert
,
180 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
183 // DidHostRunInsecureContent unit tests the expected behavior of calling
184 // DidHostRunInsecureContent as well as HostRanInsecureContent to check if
185 // insecure content has been run and to mark it as such.
186 IN_PROC_BROWSER_TEST_F(ChromeSSLHostStateDelegateTest
,
187 DidHostRunInsecureContent
) {
188 content::WebContents
* tab
=
189 browser()->tab_strip_model()->GetActiveWebContents();
190 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
191 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
193 EXPECT_FALSE(state
->DidHostRunInsecureContent("www.google.com", 42));
194 EXPECT_FALSE(state
->DidHostRunInsecureContent("www.google.com", 191));
195 EXPECT_FALSE(state
->DidHostRunInsecureContent("example.com", 42));
197 state
->HostRanInsecureContent("www.google.com", 42);
199 EXPECT_TRUE(state
->DidHostRunInsecureContent("www.google.com", 42));
200 EXPECT_FALSE(state
->DidHostRunInsecureContent("www.google.com", 191));
201 EXPECT_FALSE(state
->DidHostRunInsecureContent("example.com", 42));
203 state
->HostRanInsecureContent("example.com", 42);
205 EXPECT_TRUE(state
->DidHostRunInsecureContent("www.google.com", 42));
206 EXPECT_FALSE(state
->DidHostRunInsecureContent("www.google.com", 191));
207 EXPECT_TRUE(state
->DidHostRunInsecureContent("example.com", 42));
210 class ForgetAtSessionEndSSLHostStateDelegateTest
211 : public ChromeSSLHostStateDelegateTest
{
213 void SetUpCommandLine(base::CommandLine
* command_line
) override
{
214 ChromeSSLHostStateDelegateTest::SetUpCommandLine(command_line
);
215 SetFinchConfig(command_line
, "Session");
219 // QueryPolicyExpired unit tests to make sure that if a certificate decision has
220 // expired, the return value from QueryPolicy returns the correct vaule.
221 IN_PROC_BROWSER_TEST_F(ForgetAtSessionEndSSLHostStateDelegateTest
,
222 PRE_QueryPolicyExpired
) {
223 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
224 content::WebContents
* tab
=
225 browser()->tab_strip_model()->GetActiveWebContents();
226 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
227 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
228 bool expired_previous_decision
;
230 // The certificate has never been seen before, so it should be UNKNOWN and
231 // should also indicate that it hasn't expired.
233 content::SSLHostStateDelegate::DENIED
,
234 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
235 &expired_previous_decision
));
236 EXPECT_FALSE(expired_previous_decision
);
238 // After allowing the certificate, a query should say that it is allowed and
239 // also specify that it hasn't expired.
240 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
242 content::SSLHostStateDelegate::ALLOWED
,
243 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
244 &expired_previous_decision
));
245 EXPECT_FALSE(expired_previous_decision
);
248 // Since this is being checked on a browser instance that expires security
249 // decisions after restart, the test needs to wait until after a restart to
250 // verify that the expiration state is correct.
251 IN_PROC_BROWSER_TEST_F(ForgetAtSessionEndSSLHostStateDelegateTest
,
252 QueryPolicyExpired
) {
253 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
254 content::WebContents
* tab
=
255 browser()->tab_strip_model()->GetActiveWebContents();
256 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
257 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
258 bool expired_previous_decision
;
260 // The browser content has restart thus expiring the user decision made above,
261 // so it should indicate that the certificate and error are DENIED but also
262 // that they expired since the last query.
264 content::SSLHostStateDelegate::DENIED
,
265 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
266 &expired_previous_decision
));
267 EXPECT_TRUE(expired_previous_decision
);
269 // However, with a new query, it should indicate that no new expiration has
272 content::SSLHostStateDelegate::DENIED
,
273 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
274 &expired_previous_decision
));
275 EXPECT_FALSE(expired_previous_decision
);
278 // Tests the basic behavior of cert memory in incognito.
279 class IncognitoSSLHostStateDelegateTest
280 : public ChromeSSLHostStateDelegateTest
{
282 void SetUpCommandLine(base::CommandLine
* command_line
) override
{
283 ChromeSSLHostStateDelegateTest::SetUpCommandLine(command_line
);
284 SetFinchConfig(command_line
, "OneWeek");
288 IN_PROC_BROWSER_TEST_F(IncognitoSSLHostStateDelegateTest
, PRE_AfterRestart
) {
289 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
290 content::WebContents
* tab
=
291 browser()->tab_strip_model()->GetActiveWebContents();
292 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
293 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
296 // Add a cert exception to the profile and then verify that it still exists
297 // in the incognito profile.
298 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
300 scoped_ptr
<Profile
> incognito(profile
->CreateOffTheRecordProfile());
301 content::SSLHostStateDelegate
* incognito_state
=
302 incognito
->GetSSLHostStateDelegate();
305 content::SSLHostStateDelegate::ALLOWED
,
306 incognito_state
->QueryPolicy(
307 kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
, &unused_value
));
309 // Add a cert exception to the incognito profile. It will be checked after
310 // restart that this exception does not exist. Note the different cert URL and
311 // error than above thus mapping to a second exception. Also validate that it
312 // was not added as an exception to the regular profile.
313 incognito_state
->AllowCert(kGoogleHost
, *cert
,
314 net::CERT_STATUS_COMMON_NAME_INVALID
);
317 content::SSLHostStateDelegate::DENIED
,
318 state
->QueryPolicy(kGoogleHost
, *cert
,
319 net::CERT_STATUS_COMMON_NAME_INVALID
, &unused_value
));
322 // AfterRestart ensures that any cert decisions made in an incognito profile are
323 // forgetten after a session restart even if the field trial group parameter
324 // specifies to remember cert decisions after restart.
325 IN_PROC_BROWSER_TEST_F(IncognitoSSLHostStateDelegateTest
, AfterRestart
) {
326 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
327 content::WebContents
* tab
=
328 browser()->tab_strip_model()->GetActiveWebContents();
329 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
330 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
333 // Verify that the exception added before restart to the regular
334 // (non-incognito) profile still exists and was not cleared after the
335 // incognito session ended.
336 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
337 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
338 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
340 scoped_ptr
<Profile
> incognito(profile
->CreateOffTheRecordProfile());
341 content::SSLHostStateDelegate
* incognito_state
=
342 incognito
->GetSSLHostStateDelegate();
344 // Verify that the exception added before restart to the incognito profile was
345 // cleared when the incognito session ended.
346 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
347 incognito_state
->QueryPolicy(kGoogleHost
, *cert
,
348 net::CERT_STATUS_COMMON_NAME_INVALID
,
352 // Tests the default certificate memory, which is one week.
353 class DefaultMemorySSLHostStateDelegateTest
354 : public ChromeSSLHostStateDelegateTest
{};
356 IN_PROC_BROWSER_TEST_F(DefaultMemorySSLHostStateDelegateTest
,
358 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
359 content::WebContents
* tab
=
360 browser()->tab_strip_model()->GetActiveWebContents();
361 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
362 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
365 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
366 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
367 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
368 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
371 IN_PROC_BROWSER_TEST_F(DefaultMemorySSLHostStateDelegateTest
, AfterRestart
) {
372 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
373 content::WebContents
* tab
=
374 browser()->tab_strip_model()->GetActiveWebContents();
375 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
376 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
379 // chrome_state takes ownership of this clock
380 base::SimpleTestClock
* clock
= new base::SimpleTestClock();
381 ChromeSSLHostStateDelegate
* chrome_state
=
382 static_cast<ChromeSSLHostStateDelegate
*>(state
);
383 chrome_state
->SetClock(scoped_ptr
<base::Clock
>(clock
));
385 // Start the clock at standard system time.
386 clock
->SetNow(base::Time::NowFromSystemTime());
388 // This should only pass if the cert was allowed before the test was restart
389 // and thus has now been rememebered across browser restarts.
390 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
391 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
392 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
394 // Simulate the clock advancing by one day, which is less than the expiration
396 clock
->Advance(base::TimeDelta::FromSeconds(kDeltaOneDayInSeconds
+ 1));
398 // The cert should still be |ALLOWED| because the default expiration length
399 // has not passed yet.
400 EXPECT_EQ(content::SSLHostStateDelegate::ALLOWED
,
401 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
402 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
404 // Now simulate the clock advancing by one week, which is past the expiration
406 clock
->Advance(base::TimeDelta::FromSeconds(kDeltaOneWeekInSeconds
-
407 kDeltaOneDayInSeconds
+ 1));
409 // The cert should now be |DENIED| because the specified delta has passed.
410 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
411 state
->QueryPolicy(kWWWGoogleHost
, *cert
,
412 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
415 // The same test as ChromeSSLHostStateDelegateTest.QueryPolicyExpired but now
416 // applied to a browser context that expires based on time, not restart. This
417 // unit tests to make sure that if a certificate decision has expired, the
418 // return value from QueryPolicy returns the correct vaule.
419 IN_PROC_BROWSER_TEST_F(DefaultMemorySSLHostStateDelegateTest
,
420 QueryPolicyExpired
) {
421 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
422 content::WebContents
* tab
=
423 browser()->tab_strip_model()->GetActiveWebContents();
424 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
425 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
426 bool expired_previous_decision
;
428 // chrome_state takes ownership of this clock
429 base::SimpleTestClock
* clock
= new base::SimpleTestClock();
430 ChromeSSLHostStateDelegate
* chrome_state
=
431 static_cast<ChromeSSLHostStateDelegate
*>(state
);
432 chrome_state
->SetClock(scoped_ptr
<base::Clock
>(clock
));
434 // Start the clock at standard system time but do not advance at all to
435 // emphasize that instant forget works.
436 clock
->SetNow(base::Time::NowFromSystemTime());
438 // The certificate has never been seen before, so it should be UNKONWN and
439 // should also indicate that it hasn't expired.
441 content::SSLHostStateDelegate::DENIED
,
442 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
443 &expired_previous_decision
));
444 EXPECT_FALSE(expired_previous_decision
);
446 // After allowing the certificate, a query should say that it is allowed and
447 // also specify that it hasn't expired.
448 state
->AllowCert(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
450 content::SSLHostStateDelegate::ALLOWED
,
451 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
452 &expired_previous_decision
));
453 EXPECT_FALSE(expired_previous_decision
);
455 // Simulate the clock advancing by one week, the default expiration time.
456 clock
->Advance(base::TimeDelta::FromSeconds(kDeltaOneWeekInSeconds
+ 1));
458 // The decision expiration time has come, so it should indicate that the
459 // certificate and error are DENIED but also that they expired since the last
462 content::SSLHostStateDelegate::DENIED
,
463 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
464 &expired_previous_decision
));
465 EXPECT_TRUE(expired_previous_decision
);
467 // However, with a new query, it should indicate that no new expiration has
470 content::SSLHostStateDelegate::DENIED
,
471 state
->QueryPolicy(kWWWGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
,
472 &expired_previous_decision
));
473 EXPECT_FALSE(expired_previous_decision
);
476 // Tests to make sure that if the user deletes their browser history, SSL
477 // exceptions will be deleted as well.
478 class RemoveBrowsingHistorySSLHostStateDelegateTest
479 : public ChromeSSLHostStateDelegateTest
{
481 void RemoveAndWait(Profile
* profile
) {
482 BrowsingDataRemover
* remover
= BrowsingDataRemover::CreateForPeriod(
483 profile
, BrowsingDataRemover::LAST_HOUR
);
484 BrowsingDataRemoverCompletionObserver
completion_observer(remover
);
485 remover
->Remove(BrowsingDataRemover::REMOVE_HISTORY
,
486 BrowsingDataHelper::UNPROTECTED_WEB
);
487 completion_observer
.BlockUntilCompletion();
491 IN_PROC_BROWSER_TEST_F(RemoveBrowsingHistorySSLHostStateDelegateTest
,
493 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
494 content::WebContents
* tab
=
495 browser()->tab_strip_model()->GetActiveWebContents();
496 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
497 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
500 // Add an exception for an invalid certificate. Then remove the last hour's
501 // worth of browsing history and verify that the exception has been deleted.
502 state
->AllowCert(kGoogleHost
, *cert
, net::CERT_STATUS_DATE_INVALID
);
503 RemoveAndWait(profile
);
504 EXPECT_EQ(content::SSLHostStateDelegate::DENIED
,
505 state
->QueryPolicy(kGoogleHost
, *cert
,
506 net::CERT_STATUS_DATE_INVALID
, &unused_value
));
509 // Tests to make sure that localhost certificate errors are treated as
510 // normal errors or ignored, depending on whether the
511 // kAllowInsecureLocalhost flag is set.
513 // When the flag isn't set, requests to localhost with invalid
514 // certificates should be denied.
515 IN_PROC_BROWSER_TEST_F(ChromeSSLHostStateDelegateTest
,
516 LocalhostErrorWithoutFlag
) {
517 // Serve the Google cert for localhost to generate an error.
518 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
519 content::WebContents
* tab
=
520 browser()->tab_strip_model()->GetActiveWebContents();
521 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
522 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
526 content::SSLHostStateDelegate::DENIED
,
527 state
->QueryPolicy("localhost", *cert
,
528 net::CERT_STATUS_COMMON_NAME_INVALID
, &unused_value
));
531 content::SSLHostStateDelegate::DENIED
,
532 state
->QueryPolicy("127.0.0.1", *cert
,
533 net::CERT_STATUS_COMMON_NAME_INVALID
, &unused_value
));
536 // When the flag is set, requests to localhost with invalid certificates
537 // should be allowed.
538 class AllowLocalhostErrorsSSLHostStateDelegateTest
539 : public ChromeSSLHostStateDelegateTest
{
541 void SetUpCommandLine(base::CommandLine
* command_line
) override
{
542 ChromeSSLHostStateDelegateTest::SetUpCommandLine(command_line
);
543 command_line
->AppendSwitch(switches::kAllowInsecureLocalhost
);
547 IN_PROC_BROWSER_TEST_F(AllowLocalhostErrorsSSLHostStateDelegateTest
,
548 LocalhostErrorWithFlag
) {
549 // Serve the Google cert for localhost to generate an error.
550 scoped_refptr
<net::X509Certificate
> cert
= GetOkCert();
551 content::WebContents
* tab
=
552 browser()->tab_strip_model()->GetActiveWebContents();
553 Profile
* profile
= Profile::FromBrowserContext(tab
->GetBrowserContext());
554 content::SSLHostStateDelegate
* state
= profile
->GetSSLHostStateDelegate();
558 content::SSLHostStateDelegate::ALLOWED
,
559 state
->QueryPolicy("localhost", *cert
,
560 net::CERT_STATUS_COMMON_NAME_INVALID
, &unused_value
));
563 content::SSLHostStateDelegate::ALLOWED
,
564 state
->QueryPolicy("127.0.0.1", *cert
,
565 net::CERT_STATUS_COMMON_NAME_INVALID
, &unused_value
));