ssl_browser_tests.cc revision 513209b27ff55e2841eac0e4120199c23acce758
1// Copyright (c) 2010 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/stringprintf.h" 6#include "base/time.h" 7#include "chrome/app/chrome_command_ids.h" 8#include "chrome/browser/browser.h" 9#include "chrome/browser/browser_navigator.h" 10#include "chrome/browser/prefs/pref_service.h" 11#include "chrome/browser/profile.h" 12#include "chrome/browser/tab_contents/interstitial_page.h" 13#include "chrome/browser/tab_contents/navigation_entry.h" 14#include "chrome/browser/tab_contents/tab_contents.h" 15#include "chrome/browser/tabs/tab_strip_model.h" 16#include "chrome/common/pref_names.h" 17#include "chrome/test/in_process_browser_test.h" 18#include "chrome/test/ui_test_utils.h" 19#include "net/base/cert_status_flags.h" 20#include "net/test/test_server.h" 21 22const FilePath::CharType kDocRoot[] = FILE_PATH_LITERAL("chrome/test/data"); 23 24class SSLUITest : public InProcessBrowserTest { 25 typedef net::TestServer::HTTPSOptions HTTPSOptions; 26 27 public: 28 SSLUITest() 29 : https_server_( 30 HTTPSOptions(HTTPSOptions::CERT_OK), FilePath(kDocRoot)), 31 https_server_expired_( 32 HTTPSOptions(HTTPSOptions::CERT_EXPIRED), FilePath(kDocRoot)), 33 https_server_mismatched_( 34 HTTPSOptions(HTTPSOptions::CERT_MISMATCHED_NAME), 35 FilePath(kDocRoot)) { 36 EnableDOMAutomation(); 37 } 38 39 void CheckAuthenticatedState(TabContents* tab, 40 bool displayed_insecure_content) { 41 NavigationEntry* entry = tab->controller().GetActiveEntry(); 42 ASSERT_TRUE(entry); 43 EXPECT_EQ(NavigationEntry::NORMAL_PAGE, entry->page_type()); 44 EXPECT_EQ(SECURITY_STYLE_AUTHENTICATED, entry->ssl().security_style()); 45 EXPECT_EQ(0, entry->ssl().cert_status() & net::CERT_STATUS_ALL_ERRORS); 46 EXPECT_EQ(displayed_insecure_content, 47 entry->ssl().displayed_insecure_content()); 48 EXPECT_FALSE(entry->ssl().ran_insecure_content()); 49 } 50 51 void CheckUnauthenticatedState(TabContents* tab) { 52 NavigationEntry* entry = tab->controller().GetActiveEntry(); 53 ASSERT_TRUE(entry); 54 EXPECT_EQ(NavigationEntry::NORMAL_PAGE, entry->page_type()); 55 EXPECT_EQ(SECURITY_STYLE_UNAUTHENTICATED, entry->ssl().security_style()); 56 EXPECT_EQ(0, entry->ssl().cert_status() & net::CERT_STATUS_ALL_ERRORS); 57 EXPECT_FALSE(entry->ssl().displayed_insecure_content()); 58 EXPECT_FALSE(entry->ssl().ran_insecure_content()); 59 } 60 61 void CheckAuthenticationBrokenState(TabContents* tab, 62 int error, 63 bool ran_insecure_content, 64 bool interstitial) { 65 NavigationEntry* entry = tab->controller().GetActiveEntry(); 66 ASSERT_TRUE(entry); 67 EXPECT_EQ(interstitial ? NavigationEntry::INTERSTITIAL_PAGE : 68 NavigationEntry::NORMAL_PAGE, 69 entry->page_type()); 70 EXPECT_EQ(SECURITY_STYLE_AUTHENTICATION_BROKEN, 71 entry->ssl().security_style()); 72 // CERT_STATUS_UNABLE_TO_CHECK_REVOCATION doesn't lower the security style 73 // to SECURITY_STYLE_AUTHENTICATION_BROKEN. 74 ASSERT_NE(net::CERT_STATUS_UNABLE_TO_CHECK_REVOCATION, error); 75 EXPECT_EQ(error, entry->ssl().cert_status() & net::CERT_STATUS_ALL_ERRORS); 76 EXPECT_FALSE(entry->ssl().displayed_insecure_content()); 77 EXPECT_EQ(ran_insecure_content, entry->ssl().ran_insecure_content()); 78 } 79 80 void CheckWorkerLoadResult(TabContents* tab, bool expectLoaded) { 81 // Workers are async and we don't have notifications for them passing 82 // messages since they do it between renderer and worker processes. 83 // So have a polling loop, check every 200ms, timeout at 30s. 84 const int timeout_ms = 200; 85 base::Time timeToQuit = base::Time::Now() + 86 base::TimeDelta::FromMilliseconds(30000); 87 88 while (base::Time::Now() < timeToQuit) { 89 bool workerFinished = false; 90 ASSERT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 91 tab->render_view_host(), std::wstring(), 92 L"window.domAutomationController.send(IsWorkerFinished());", 93 &workerFinished)); 94 95 if (workerFinished) 96 break; 97 98 // Wait a bit. 99 MessageLoop::current()->PostDelayedTask( 100 FROM_HERE, new MessageLoop::QuitTask, timeout_ms); 101 ui_test_utils::RunMessageLoop(); 102 } 103 104 bool actuallyLoadedContent = false; 105 ASSERT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 106 tab->render_view_host(), std::wstring(), 107 L"window.domAutomationController.send(IsContentLoaded());", 108 &actuallyLoadedContent)); 109 EXPECT_EQ(expectLoaded, actuallyLoadedContent); 110 } 111 112 void ProceedThroughInterstitial(TabContents* tab) { 113 InterstitialPage* interstitial_page = tab->interstitial_page(); 114 ASSERT_TRUE(interstitial_page); 115 interstitial_page->Proceed(); 116 // Wait for the navigation to be done. 117 ui_test_utils::WaitForNavigation(&(tab->controller())); 118 } 119 120 std::string GetFileWithHostAndPortReplacement( 121 const std::string& original_path, 122 const net::HostPortPair& host_port_pair) const { 123 return StringPrintf("%s?replace_orig=%s&replace_new=%s", 124 original_path.c_str(), 125 kReplaceText_, 126 host_port_pair.ToString().c_str()); 127 } 128 129 net::TestServer https_server_; 130 net::TestServer https_server_expired_; 131 net::TestServer https_server_mismatched_; 132 133 private: 134 DISALLOW_COPY_AND_ASSIGN(SSLUITest); 135 136 static const char* const kReplaceText_; 137}; 138 139// static 140const char* const SSLUITest::kReplaceText_ = "REPLACE_WITH_HOST_AND_PORT"; 141 142// Visits a regular page over http. 143IN_PROC_BROWSER_TEST_F(SSLUITest, TestHTTP) { 144 ASSERT_TRUE(test_server()->Start()); 145 146 ui_test_utils::NavigateToURL(browser(), 147 test_server()->GetURL("files/ssl/google.html")); 148 149 CheckUnauthenticatedState(browser()->GetSelectedTabContents()); 150} 151 152// Visits a page over http which includes broken https resources (status should 153// be OK). 154// TODO(jcampan): test that bad HTTPS content is blocked (otherwise we'll give 155// the secure cookies away!). 156IN_PROC_BROWSER_TEST_F(SSLUITest, TestHTTPWithBrokenHTTPSResource) { 157 ASSERT_TRUE(test_server()->Start()); 158 ASSERT_TRUE(https_server_expired_.Start()); 159 160 std::string replacement_path = GetFileWithHostAndPortReplacement( 161 "files/ssl/page_with_unsafe_contents.html", 162 https_server_expired_.host_port_pair()); 163 164 ui_test_utils::NavigateToURL( 165 browser(), test_server()->GetURL(replacement_path)); 166 167 CheckUnauthenticatedState(browser()->GetSelectedTabContents()); 168} 169 170// Visits a page over OK https: 171IN_PROC_BROWSER_TEST_F(SSLUITest, TestOKHTTPS) { 172 ASSERT_TRUE(https_server_.Start()); 173 174 ui_test_utils::NavigateToURL(browser(), 175 https_server_.GetURL("files/ssl/google.html")); 176 177 CheckAuthenticatedState(browser()->GetSelectedTabContents(), false); 178} 179 180// Visits a page with https error and proceed: 181IN_PROC_BROWSER_TEST_F(SSLUITest, TestHTTPSExpiredCertAndProceed) { 182 ASSERT_TRUE(https_server_expired_.Start()); 183 184 ui_test_utils::NavigateToURL(browser(), 185 https_server_expired_.GetURL("files/ssl/google.html")); 186 187 TabContents* tab = browser()->GetSelectedTabContents(); 188 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 189 true); // Interstitial showing 190 191 ProceedThroughInterstitial(tab); 192 193 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 194 false); // No interstitial showing 195} 196 197// Visits a page with https error and don't proceed (and ensure we can still 198// navigate at that point): 199#if defined(OS_WIN) 200// Disabled, flakily exceeds test timeout, http://crbug.com/43575. 201#define MAYBE_TestHTTPSExpiredCertAndDontProceed \ 202 DISABLED_TestHTTPSExpiredCertAndDontProceed 203#else 204// Marked as flaky, see bug 40932. 205#define MAYBE_TestHTTPSExpiredCertAndDontProceed \ 206 FLAKY_TestHTTPSExpiredCertAndDontProceed 207#endif 208IN_PROC_BROWSER_TEST_F(SSLUITest, MAYBE_TestHTTPSExpiredCertAndDontProceed) { 209 ASSERT_TRUE(test_server()->Start()); 210 ASSERT_TRUE(https_server_.Start()); 211 ASSERT_TRUE(https_server_expired_.Start()); 212 213 // First navigate to an OK page. 214 ui_test_utils::NavigateToURL(browser(), 215 https_server_.GetURL("files/ssl/google.html")); 216 217 TabContents* tab = browser()->GetSelectedTabContents(); 218 NavigationEntry* entry = tab->controller().GetActiveEntry(); 219 ASSERT_TRUE(entry); 220 221 GURL cross_site_url = 222 https_server_expired_.GetURL("files/ssl/google.html"); 223 // Change the host name from 127.0.0.1 to localhost so it triggers a 224 // cross-site navigation so we can test http://crbug.com/5800 is gone. 225 ASSERT_EQ("127.0.0.1", cross_site_url.host()); 226 GURL::Replacements replacements; 227 std::string new_host("localhost"); 228 replacements.SetHostStr(new_host); 229 cross_site_url = cross_site_url.ReplaceComponents(replacements); 230 231 // Now go to a bad HTTPS page. 232 ui_test_utils::NavigateToURL(browser(), cross_site_url); 233 234 // An interstitial should be showing. 235 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_COMMON_NAME_INVALID, 236 false, true); 237 238 // Simulate user clicking "Take me back". 239 InterstitialPage* interstitial_page = tab->interstitial_page(); 240 ASSERT_TRUE(interstitial_page); 241 interstitial_page->DontProceed(); 242 243 // We should be back to the original good page. 244 CheckAuthenticatedState(tab, false); 245 246 // Try to navigate to a new page. (to make sure bug 5800 is fixed). 247 ui_test_utils::NavigateToURL(browser(), 248 test_server()->GetURL("files/ssl/google.html")); 249 CheckUnauthenticatedState(tab); 250} 251 252// Visits a page with https error and then goes back using Browser::GoBack. 253#if defined(OS_WIN) 254// Disabled on win. Times out. crbug.com/43575 and crbug.com/61528 255#define TestHTTPSExpiredCertAndGoBackViaButton \ 256 DISABLED_TestHTTPSExpiredCertAndGoBackViaButton 257#endif 258IN_PROC_BROWSER_TEST_F(SSLUITest, TestHTTPSExpiredCertAndGoBackViaButton) { 259 ASSERT_TRUE(test_server()->Start()); 260 ASSERT_TRUE(https_server_expired_.Start()); 261 262 // First navigate to an HTTP page. 263 ui_test_utils::NavigateToURL(browser(), 264 test_server()->GetURL("files/ssl/google.html")); 265 TabContents* tab = browser()->GetSelectedTabContents(); 266 NavigationEntry* entry = tab->controller().GetActiveEntry(); 267 ASSERT_TRUE(entry); 268 269 // Now go to a bad HTTPS page that shows an interstitial. 270 ui_test_utils::NavigateToURL(browser(), 271 https_server_expired_.GetURL("files/ssl/google.html")); 272 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 273 true); // Interstitial showing 274 275 // Simulate user clicking on back button (crbug.com/39248). 276 browser()->GoBack(CURRENT_TAB); 277 278 // We should be back at the original good page. 279 EXPECT_FALSE(browser()->GetSelectedTabContents()->interstitial_page()); 280 CheckUnauthenticatedState(tab); 281} 282 283// Visits a page with https error and then goes back using GoToOffset. 284// Marked as flaky, see bug 40932. 285#if defined(OS_WIN) 286// Disabled on win. Times out. crbug.com/43575 and crbug.com/61528 287#define FLAKY_TestHTTPSExpiredCertAndGoBackViaMenu \ 288 DISABLED_TestHTTPSExpiredCertAndGoBackViaMenu 289#endif 290IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestHTTPSExpiredCertAndGoBackViaMenu) { 291 ASSERT_TRUE(test_server()->Start()); 292 ASSERT_TRUE(https_server_expired_.Start()); 293 294 // First navigate to an HTTP page. 295 ui_test_utils::NavigateToURL(browser(), 296 test_server()->GetURL("files/ssl/google.html")); 297 TabContents* tab = browser()->GetSelectedTabContents(); 298 NavigationEntry* entry = tab->controller().GetActiveEntry(); 299 ASSERT_TRUE(entry); 300 301 // Now go to a bad HTTPS page that shows an interstitial. 302 ui_test_utils::NavigateToURL(browser(), 303 https_server_expired_.GetURL("files/ssl/google.html")); 304 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 305 true); // Interstitial showing 306 307 // Simulate user clicking and holding on back button (crbug.com/37215). 308 tab->controller().GoToOffset(-1); 309 310 // We should be back at the original good page. 311 EXPECT_FALSE(browser()->GetSelectedTabContents()->interstitial_page()); 312 CheckUnauthenticatedState(tab); 313} 314 315// Visits a page with https error and then goes forward using GoToOffset. 316// Marked as flaky, see bug 40932. 317IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestHTTPSExpiredCertAndGoForward) { 318 ASSERT_TRUE(test_server()->Start()); 319 ASSERT_TRUE(https_server_expired_.Start()); 320 321 // First navigate to two HTTP pages. 322 ui_test_utils::NavigateToURL(browser(), 323 test_server()->GetURL("files/ssl/google.html")); 324 TabContents* tab = browser()->GetSelectedTabContents(); 325 NavigationEntry* entry1 = tab->controller().GetActiveEntry(); 326 ASSERT_TRUE(entry1); 327 ui_test_utils::NavigateToURL(browser(), 328 test_server()->GetURL("files/ssl/blank_page.html")); 329 NavigationEntry* entry2 = tab->controller().GetActiveEntry(); 330 ASSERT_TRUE(entry2); 331 332 // Now go back so that a page is in the forward history. 333 tab->controller().GoBack(); 334 ui_test_utils::WaitForNavigation(&(tab->controller())); 335 ASSERT_TRUE(tab->controller().CanGoForward()); 336 NavigationEntry* entry3 = tab->controller().GetActiveEntry(); 337 ASSERT_TRUE(entry1 == entry3); 338 339 // Now go to a bad HTTPS page that shows an interstitial. 340 ui_test_utils::NavigateToURL(browser(), 341 https_server_expired_.GetURL("files/ssl/google.html")); 342 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 343 true); // Interstitial showing 344 345 // Simulate user clicking and holding on forward button. 346 tab->controller().GoToOffset(1); 347 ui_test_utils::WaitForNavigation(&(tab->controller())); 348 349 // We should be showing the second good page. 350 EXPECT_FALSE(browser()->GetSelectedTabContents()->interstitial_page()); 351 CheckUnauthenticatedState(tab); 352 EXPECT_FALSE(tab->controller().CanGoForward()); 353 NavigationEntry* entry4 = tab->controller().GetActiveEntry(); 354 EXPECT_TRUE(entry2 == entry4); 355} 356 357// Open a page with a HTTPS error in a tab with no prior navigation (through a 358// link with a blank target). This is to test that the lack of navigation entry 359// does not cause any problems (it was causing a crasher, see 360// http://crbug.com/19941). 361IN_PROC_BROWSER_TEST_F(SSLUITest, TestHTTPSErrorWithNoNavEntry) { 362 ASSERT_TRUE(https_server_expired_.Start()); 363 364 GURL url = https_server_expired_.GetURL("files/ssl/google.htm"); 365 TabContents* tab2 = 366 browser()->AddSelectedTabWithURL(url, PageTransition::TYPED); 367 ui_test_utils::WaitForLoadStop(&(tab2->controller())); 368 369 // Verify our assumption that there was no prior navigation. 370 EXPECT_FALSE(browser()->command_updater()->IsCommandEnabled(IDC_BACK)); 371 372 // We should have an interstitial page showing. 373 ASSERT_TRUE(tab2->interstitial_page()); 374} 375 376// 377// Insecure content 378// 379 380// Visits a page that displays insecure content. 381IN_PROC_BROWSER_TEST_F(SSLUITest, TestDisplaysInsecureContent) { 382 ASSERT_TRUE(test_server()->Start()); 383 ASSERT_TRUE(https_server_.Start()); 384 385 std::string replacement_path = GetFileWithHostAndPortReplacement( 386 "files/ssl/page_displays_insecure_content.html", 387 test_server()->host_port_pair()); 388 389 // Load a page that displays insecure content. 390 ui_test_utils::NavigateToURL(browser(), 391 https_server_.GetURL(replacement_path)); 392 393 CheckAuthenticatedState(browser()->GetSelectedTabContents(), true); 394} 395 396// Visits a page that runs insecure content and tries to suppress the insecure 397// content warnings by randomizing location.hash. 398// Based on http://crbug.com/8706 399// Fails to terminate on all platforms. See bug http://crbug.com/58230 400IN_PROC_BROWSER_TEST_F(SSLUITest, 401 DISABLED_TestRunsInsecuredContentRandomizeHash) { 402 ASSERT_TRUE(test_server()->Start()); 403 ASSERT_TRUE(https_server_.Start()); 404 405 ui_test_utils::NavigateToURL(browser(), https_server_.GetURL( 406 "files/ssl/page_runs_insecure_content.html")); 407 408 CheckAuthenticationBrokenState(browser()->GetSelectedTabContents(), 0, true, 409 false); 410} 411 412// Visits a page with unsafe content and make sure that: 413// - frames content is replaced with warning 414// - images and scripts are filtered out entirely 415// Marked as flaky, see bug 40932. 416IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestUnsafeContents) { 417 ASSERT_TRUE(https_server_.Start()); 418 ASSERT_TRUE(https_server_expired_.Start()); 419 420 std::string replacement_path = GetFileWithHostAndPortReplacement( 421 "files/ssl/page_with_unsafe_contents.html", 422 https_server_expired_.host_port_pair()); 423 ui_test_utils::NavigateToURL(browser(), 424 https_server_.GetURL(replacement_path)); 425 426 TabContents* tab = browser()->GetSelectedTabContents(); 427 // When the bad content is filtered, the state is expected to be 428 // authenticated. 429 CheckAuthenticatedState(tab, false); 430 431 // Because of cross-frame scripting restrictions, we cannot access the iframe 432 // content. So to know if the frame was loaded, we just check if a popup was 433 // opened (the iframe content opens one). 434 // Note: because of bug 1115868, no constrained window is opened right now. 435 // Once the bug is fixed, this will do the real check. 436 EXPECT_EQ(0, static_cast<int>(tab->constrained_window_count())); 437 438 int img_width; 439 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractInt( 440 tab->render_view_host(), std::wstring(), 441 L"window.domAutomationController.send(ImageWidth());", &img_width)); 442 // In order to check that the image was not loaded, we check its width. 443 // The actual image (Google logo) is 114 pixels wide, we assume the broken 444 // image is less than 100. 445 EXPECT_LT(img_width, 100); 446 447 bool js_result = false; 448 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 449 tab->render_view_host(), std::wstring(), 450 L"window.domAutomationController.send(IsFooSet());", &js_result)); 451 EXPECT_FALSE(js_result); 452} 453 454// Visits a page with insecure content loaded by JS (after the initial page 455// load). 456IN_PROC_BROWSER_TEST_F(SSLUITest, TestDisplaysInsecureContentLoadedFromJS) { 457 ASSERT_TRUE(test_server()->Start()); 458 ASSERT_TRUE(https_server_.Start()); 459 460 std::string replacement_path = GetFileWithHostAndPortReplacement( 461 "files/ssl/page_with_dynamic_insecure_content.html", 462 test_server()->host_port_pair()); 463 ui_test_utils::NavigateToURL(browser(), https_server_.GetURL( 464 replacement_path)); 465 466 TabContents* tab = browser()->GetSelectedTabContents(); 467 CheckAuthenticatedState(tab, false); 468 469 // Load the insecure image. 470 bool js_result = false; 471 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 472 tab->render_view_host(), std::wstring(), L"loadBadImage();", &js_result)); 473 EXPECT_TRUE(js_result); 474 475 // We should now have insecure content. 476 CheckAuthenticatedState(tab, true); 477} 478 479// Visits two pages from the same origin: one that displays insecure content and 480// one that doesn't. The test checks that we do not propagate the insecure 481// content state from one to the other. 482IN_PROC_BROWSER_TEST_F(SSLUITest, TestDisplaysInsecureContentTwoTabs) { 483 ASSERT_TRUE(test_server()->Start()); 484 ASSERT_TRUE(https_server_.Start()); 485 486 ui_test_utils::NavigateToURL(browser(), 487 https_server_.GetURL("files/ssl/blank_page.html")); 488 489 TabContents* tab1 = browser()->GetSelectedTabContents(); 490 491 // This tab should be fine. 492 CheckAuthenticatedState(tab1, false); 493 494 // Create a new tab. 495 std::string replacement_path = GetFileWithHostAndPortReplacement( 496 "files/ssl/page_displays_insecure_content.html", 497 test_server()->host_port_pair()); 498 499 GURL url = https_server_.GetURL(replacement_path); 500 browser::NavigateParams params(browser(), url, PageTransition::TYPED); 501 params.disposition = NEW_FOREGROUND_TAB; 502 params.tabstrip_index = 0; 503 params.source_contents = tab1; 504 browser::Navigate(¶ms); 505 TabContents* tab2 = params.target_contents; 506 ui_test_utils::WaitForNavigation(&(tab2->controller())); 507 508 // The new tab has insecure content. 509 CheckAuthenticatedState(tab2, true); 510 511 // The original tab should not be contaminated. 512 CheckAuthenticatedState(tab1, false); 513} 514 515// Visits two pages from the same origin: one that runs insecure content and one 516// that doesn't. The test checks that we propagate the insecure content state 517// from one to the other. 518IN_PROC_BROWSER_TEST_F(SSLUITest, TestRunsInsecureContentTwoTabs) { 519 ASSERT_TRUE(test_server()->Start()); 520 ASSERT_TRUE(https_server_.Start()); 521 522 ui_test_utils::NavigateToURL(browser(), 523 https_server_.GetURL("files/ssl/blank_page.html")); 524 525 TabContents* tab1 = browser()->GetSelectedTabContents(); 526 527 // This tab should be fine. 528 CheckAuthenticatedState(tab1, false); 529 530 std::string replacement_path = GetFileWithHostAndPortReplacement( 531 "files/ssl/page_runs_insecure_content.html", 532 test_server()->host_port_pair()); 533 534 // Create a new tab. 535 GURL url = https_server_.GetURL(replacement_path); 536 browser::NavigateParams params(browser(), url, PageTransition::TYPED); 537 params.disposition = NEW_FOREGROUND_TAB; 538 params.source_contents = tab1; 539 browser::Navigate(¶ms); 540 TabContents* tab2 = params.target_contents; 541 ui_test_utils::WaitForNavigation(&(tab2->controller())); 542 543 // The new tab has insecure content. 544 CheckAuthenticationBrokenState(tab2, 0, true, false); 545 546 // Which means the origin for the first tab has also been contaminated with 547 // insecure content. 548 CheckAuthenticationBrokenState(tab1, 0, true, false); 549} 550 551// Visits a page with an image over http. Visits another page over https 552// referencing that same image over http (hoping it is coming from the webcore 553// memory cache). 554IN_PROC_BROWSER_TEST_F(SSLUITest, TestDisplaysCachedInsecureContent) { 555 ASSERT_TRUE(test_server()->Start()); 556 ASSERT_TRUE(https_server_.Start()); 557 558 std::string replacement_path = GetFileWithHostAndPortReplacement( 559 "files/ssl/page_displays_insecure_content.html", 560 test_server()->host_port_pair()); 561 562 // Load original page over HTTP. 563 const GURL url_http = test_server()->GetURL(replacement_path); 564 ui_test_utils::NavigateToURL(browser(), url_http); 565 TabContents* tab = browser()->GetSelectedTabContents(); 566 CheckUnauthenticatedState(tab); 567 568 // Load again but over SSL. It should be marked as displaying insecure 569 // content (even though the image comes from the WebCore memory cache). 570 const GURL url_https = https_server_.GetURL(replacement_path); 571 ui_test_utils::NavigateToURL(browser(), url_https); 572 CheckAuthenticatedState(tab, true); 573} 574 575// Visits a page with script over http. Visits another page over https 576// referencing that same script over http (hoping it is coming from the webcore 577// memory cache). 578IN_PROC_BROWSER_TEST_F(SSLUITest, TestRunsCachedInsecureContent) { 579 ASSERT_TRUE(test_server()->Start()); 580 ASSERT_TRUE(https_server_.Start()); 581 582 std::string replacement_path = GetFileWithHostAndPortReplacement( 583 "files/ssl/page_runs_insecure_content.html", 584 test_server()->host_port_pair()); 585 586 // Load original page over HTTP. 587 const GURL url_http = test_server()->GetURL(replacement_path); 588 ui_test_utils::NavigateToURL(browser(), url_http); 589 TabContents* tab = browser()->GetSelectedTabContents(); 590 CheckUnauthenticatedState(tab); 591 592 // Load again but over SSL. It should be marked as displaying insecure 593 // content (even though the image comes from the WebCore memory cache). 594 const GURL url_https = https_server_.GetURL(replacement_path); 595 ui_test_utils::NavigateToURL(browser(), url_https); 596 CheckAuthenticationBrokenState(tab, 0, true, false); 597} 598 599#if defined(OS_WIN) 600// See http://crbug.com/47170 601#define MAYBE_TestCNInvalidStickiness FLAKY_TestCNInvalidStickiness 602#else 603#define MAYBE_TestCNInvalidStickiness TestCNInvalidStickiness 604#endif 605 606// This test ensures the CN invalid status does not 'stick' to a certificate 607// (see bug #1044942) and that it depends on the host-name. 608IN_PROC_BROWSER_TEST_F(SSLUITest, MAYBE_TestCNInvalidStickiness) { 609 ASSERT_TRUE(https_server_.Start()); 610 ASSERT_TRUE(https_server_mismatched_.Start()); 611 612 // First we hit the server with hostname, this generates an invalid policy 613 // error. 614 ui_test_utils::NavigateToURL(browser(), 615 https_server_mismatched_.GetURL("files/ssl/google.html")); 616 617 // We get an interstitial page as a result. 618 TabContents* tab = browser()->GetSelectedTabContents(); 619 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_COMMON_NAME_INVALID, 620 false, true); // Interstitial showing. 621 ProceedThroughInterstitial(tab); 622 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_COMMON_NAME_INVALID, 623 false, false); // No interstitial showing. 624 625 // Now we try again with the right host name this time. 626 GURL url(https_server_.GetURL("files/ssl/google.html")); 627 ui_test_utils::NavigateToURL(browser(), url); 628 629 // Security state should be OK. 630 CheckAuthenticatedState(tab, false); 631 632 // Now try again the broken one to make sure it is still broken. 633 ui_test_utils::NavigateToURL(browser(), 634 https_server_mismatched_.GetURL("files/ssl/google.html")); 635 636 // Since we OKed the interstitial last time, we get right to the page. 637 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_COMMON_NAME_INVALID, 638 false, false); // No interstitial showing. 639} 640 641// Test that navigating to a #ref does not change a bad security state. 642IN_PROC_BROWSER_TEST_F(SSLUITest, TestRefNavigation) { 643 ASSERT_TRUE(https_server_expired_.Start()); 644 645 ui_test_utils::NavigateToURL(browser(), 646 https_server_expired_.GetURL("files/ssl/page_with_refs.html")); 647 648 TabContents* tab = browser()->GetSelectedTabContents(); 649 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 650 true); // Interstitial showing. 651 652 ProceedThroughInterstitial(tab); 653 654 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 655 false); // No interstitial showing. 656 657 // Now navigate to a ref in the page, the security state should not have 658 // changed. 659 ui_test_utils::NavigateToURL(browser(), 660 https_server_expired_.GetURL("files/ssl/page_with_refs.html#jp")); 661 662 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 663 false); // No interstitial showing. 664} 665 666// Tests that closing a page that has a unsafe pop-up does not crash the 667// browser (bug #1966). 668// TODO(jcampan): http://crbug.com/2136 disabled because the popup is not 669// opened as it is not initiated by a user gesture. 670IN_PROC_BROWSER_TEST_F(SSLUITest, DISABLED_TestCloseTabWithUnsafePopup) { 671 ASSERT_TRUE(test_server()->Start()); 672 ASSERT_TRUE(https_server_expired_.Start()); 673 674 std::string replacement_path = GetFileWithHostAndPortReplacement( 675 "files/ssl/page_with_unsafe_popup.html", 676 https_server_expired_.host_port_pair()); 677 678 ui_test_utils::NavigateToURL(browser(), 679 test_server()->GetURL(replacement_path)); 680 681 TabContents* tab1 = browser()->GetSelectedTabContents(); 682 // It is probably overkill to add a notification for a popup-opening, let's 683 // just poll. 684 for (int i = 0; i < 10; i++) { 685 if (static_cast<int>(tab1->constrained_window_count()) > 0) 686 break; 687 MessageLoop::current()->PostDelayedTask(FROM_HERE, 688 new MessageLoop::QuitTask(), 1000); 689 ui_test_utils::RunMessageLoop(); 690 } 691 ASSERT_EQ(1, static_cast<int>(tab1->constrained_window_count())); 692 693 // Let's add another tab to make sure the browser does not exit when we close 694 // the first tab. 695 GURL url = test_server()->GetURL("files/ssl/google.html"); 696 TabContents* tab2 = 697 browser()->AddSelectedTabWithURL(url, PageTransition::TYPED); 698 ui_test_utils::WaitForNavigation(&(tab2->controller())); 699 700 // Close the first tab. 701 browser()->CloseTabContents(tab1); 702} 703 704// Visit a page over bad https that is a redirect to a page with good https. 705// Marked as flaky, see bug 40932. 706IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestRedirectBadToGoodHTTPS) { 707 ASSERT_TRUE(https_server_.Start()); 708 ASSERT_TRUE(https_server_expired_.Start()); 709 710 GURL url1 = https_server_expired_.GetURL("server-redirect?"); 711 GURL url2 = https_server_.GetURL("files/ssl/google.html"); 712 713 ui_test_utils::NavigateToURL(browser(), GURL(url1.spec() + url2.spec())); 714 715 TabContents* tab = browser()->GetSelectedTabContents(); 716 717 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 718 true); // Interstitial showing. 719 720 ProceedThroughInterstitial(tab); 721 722 // We have been redirected to the good page. 723 CheckAuthenticatedState(tab, false); 724} 725 726// Visit a page over good https that is a redirect to a page with bad https. 727// Marked as flaky, see bug 40932. 728IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestRedirectGoodToBadHTTPS) { 729 ASSERT_TRUE(https_server_.Start()); 730 ASSERT_TRUE(https_server_expired_.Start()); 731 732 GURL url1 = https_server_.GetURL("server-redirect?"); 733 GURL url2 = https_server_expired_.GetURL("files/ssl/google.html"); 734 ui_test_utils::NavigateToURL(browser(), GURL(url1.spec() + url2.spec())); 735 736 TabContents* tab = browser()->GetSelectedTabContents(); 737 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 738 true); // Interstitial showing. 739 740 ProceedThroughInterstitial(tab); 741 742 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 743 false); // No interstitial showing. 744} 745 746// Visit a page over http that is a redirect to a page with good HTTPS. 747IN_PROC_BROWSER_TEST_F(SSLUITest, TestRedirectHTTPToGoodHTTPS) { 748 ASSERT_TRUE(test_server()->Start()); 749 ASSERT_TRUE(https_server_.Start()); 750 751 TabContents* tab = browser()->GetSelectedTabContents(); 752 753 // HTTP redirects to good HTTPS. 754 GURL http_url = test_server()->GetURL("server-redirect?"); 755 GURL good_https_url = 756 https_server_.GetURL("files/ssl/google.html"); 757 758 ui_test_utils::NavigateToURL(browser(), 759 GURL(http_url.spec() + good_https_url.spec())); 760 CheckAuthenticatedState(tab, false); 761} 762 763// Visit a page over http that is a redirect to a page with bad HTTPS. 764IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestRedirectHTTPToBadHTTPS) { 765 ASSERT_TRUE(test_server()->Start()); 766 ASSERT_TRUE(https_server_expired_.Start()); 767 768 TabContents* tab = browser()->GetSelectedTabContents(); 769 770 GURL http_url = test_server()->GetURL("server-redirect?"); 771 GURL bad_https_url = 772 https_server_expired_.GetURL("files/ssl/google.html"); 773 ui_test_utils::NavigateToURL(browser(), 774 GURL(http_url.spec() + bad_https_url.spec())); 775 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 776 true); // Interstitial showing. 777 778 ProceedThroughInterstitial(tab); 779 780 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 781 false); // No interstitial showing. 782} 783 784// Visit a page over https that is a redirect to a page with http (to make sure 785// we don't keep the secure state). 786// Marked as flaky, see bug 40932. 787IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestRedirectHTTPSToHTTP) { 788 ASSERT_TRUE(test_server()->Start()); 789 ASSERT_TRUE(https_server_.Start()); 790 791 GURL https_url = https_server_.GetURL("server-redirect?"); 792 GURL http_url = test_server()->GetURL("files/ssl/google.html"); 793 794 ui_test_utils::NavigateToURL(browser(), 795 GURL(https_url.spec() + http_url.spec())); 796 CheckUnauthenticatedState(browser()->GetSelectedTabContents()); 797} 798 799// Visits a page to which we could not connect (bad port) over http and https 800// and make sure the security style is correct. 801IN_PROC_BROWSER_TEST_F(SSLUITest, TestConnectToBadPort) { 802 ui_test_utils::NavigateToURL(browser(), GURL("http://localhost:17")); 803 CheckUnauthenticatedState(browser()->GetSelectedTabContents()); 804 805 // Same thing over HTTPS. 806 ui_test_utils::NavigateToURL(browser(), GURL("https://localhost:17")); 807 CheckUnauthenticatedState(browser()->GetSelectedTabContents()); 808} 809 810// 811// Frame navigation 812// 813 814// From a good HTTPS top frame: 815// - navigate to an OK HTTPS frame 816// - navigate to a bad HTTPS (expect unsafe content and filtered frame), then 817// back 818// - navigate to HTTP (expect insecure content), then back 819// Disabled, http://crbug.com/18626. 820IN_PROC_BROWSER_TEST_F(SSLUITest, DISABLED_TestGoodFrameNavigation) { 821 ASSERT_TRUE(test_server()->Start()); 822 ASSERT_TRUE(https_server_.Start()); 823 ASSERT_TRUE(https_server_expired_.Start()); 824 825 TabContents* tab = browser()->GetSelectedTabContents(); 826 ui_test_utils::NavigateToURL(browser(), 827 https_server_.GetURL("files/ssl/top_frame.html")); 828 829 CheckAuthenticatedState(tab, false); 830 831 bool success = false; 832 // Now navigate inside the frame. 833 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 834 tab->render_view_host(), std::wstring(), 835 L"window.domAutomationController.send(clickLink('goodHTTPSLink'));", 836 &success)); 837 EXPECT_TRUE(success); 838 ui_test_utils::WaitForNavigation(&tab->controller()); 839 840 // We should still be fine. 841 CheckAuthenticatedState(tab, false); 842 843 // Now let's hit a bad page. 844 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 845 tab->render_view_host(), std::wstring(), 846 L"window.domAutomationController.send(clickLink('badHTTPSLink'));", 847 &success)); 848 EXPECT_TRUE(success); 849 ui_test_utils::WaitForNavigation(&tab->controller()); 850 851 // The security style should still be secure. 852 CheckAuthenticatedState(tab, false); 853 854 // And the frame should be blocked. 855 bool is_content_evil = true; 856 std::wstring content_frame_xpath(L"html/frameset/frame[2]"); 857 std::wstring is_evil_js(L"window.domAutomationController.send(" 858 L"document.getElementById('evilDiv') != null);"); 859 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 860 tab->render_view_host(), content_frame_xpath, is_evil_js, 861 &is_content_evil)); 862 EXPECT_FALSE(is_content_evil); 863 864 // Now go back, our state should still be OK. 865 tab->controller().GoBack(); 866 ui_test_utils::WaitForNavigation(&tab->controller()); 867 CheckAuthenticatedState(tab, false); 868 869 // Navigate to a page served over HTTP. 870 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 871 tab->render_view_host(), std::wstring(), 872 L"window.domAutomationController.send(clickLink('HTTPLink'));", 873 &success)); 874 EXPECT_TRUE(success); 875 ui_test_utils::WaitForNavigation(&tab->controller()); 876 877 // Our state should be insecure. 878 CheckAuthenticatedState(tab, true); 879 880 // Go back, our state should be unchanged. 881 tab->controller().GoBack(); 882 ui_test_utils::WaitForNavigation(&tab->controller()); 883 CheckAuthenticatedState(tab, true); 884} 885 886// From a bad HTTPS top frame: 887// - navigate to an OK HTTPS frame (expected to be still authentication broken). 888// Marked as flaky, see bug 40932. 889IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestBadFrameNavigation) { 890 ASSERT_TRUE(https_server_.Start()); 891 ASSERT_TRUE(https_server_expired_.Start()); 892 893 TabContents* tab = browser()->GetSelectedTabContents(); 894 ui_test_utils::NavigateToURL(browser(), 895 https_server_expired_.GetURL("files/ssl/top_frame.html")); 896 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 897 true); // Interstitial showing 898 899 ProceedThroughInterstitial(tab); 900 901 // Navigate to a good frame. 902 bool success = false; 903 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 904 tab->render_view_host(), std::wstring(), 905 L"window.domAutomationController.send(clickLink('goodHTTPSLink'));", 906 &success)); 907 EXPECT_TRUE(success); 908 ui_test_utils::WaitForNavigation(&tab->controller()); 909 910 // We should still be authentication broken. 911 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 912 false); 913} 914 915// From an HTTP top frame, navigate to good and bad HTTPS (security state should 916// stay unauthenticated). 917#if defined(OS_WIN) || defined(OS_CHROMEOS) || defined(OS_LINUX) 918// Disabled, flakily exceeds test timeout, http://crbug.com/43437. 919#define MAYBE_TestUnauthenticatedFrameNavigation \ 920 DISABLED_TestUnauthenticatedFrameNavigation 921#else 922// Marked as flaky, see bug 40932. 923#define MAYBE_TestUnauthenticatedFrameNavigation \ 924 FLAKY_TestUnauthenticatedFrameNavigation 925#endif 926IN_PROC_BROWSER_TEST_F(SSLUITest, MAYBE_TestUnauthenticatedFrameNavigation) { 927 ASSERT_TRUE(test_server()->Start()); 928 ASSERT_TRUE(https_server_.Start()); 929 ASSERT_TRUE(https_server_expired_.Start()); 930 931 TabContents* tab = browser()->GetSelectedTabContents(); 932 ui_test_utils::NavigateToURL(browser(), 933 test_server()->GetURL("files/ssl/top_frame.html")); 934 CheckUnauthenticatedState(tab); 935 936 // Now navigate inside the frame to a secure HTTPS frame. 937 bool success = false; 938 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 939 tab->render_view_host(), std::wstring(), 940 L"window.domAutomationController.send(clickLink('goodHTTPSLink'));", 941 &success)); 942 EXPECT_TRUE(success); 943 ui_test_utils::WaitForNavigation(&tab->controller()); 944 945 // We should still be unauthenticated. 946 CheckUnauthenticatedState(tab); 947 948 // Now navigate to a bad HTTPS frame. 949 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 950 tab->render_view_host(), std::wstring(), 951 L"window.domAutomationController.send(clickLink('badHTTPSLink'));", 952 &success)); 953 EXPECT_TRUE(success); 954 ui_test_utils::WaitForNavigation(&tab->controller()); 955 956 // State should not have changed. 957 CheckUnauthenticatedState(tab); 958 959 // And the frame should have been blocked (see bug #2316). 960 bool is_content_evil = true; 961 std::wstring content_frame_xpath(L"html/frameset/frame[2]"); 962 std::wstring is_evil_js(L"window.domAutomationController.send(" 963 L"document.getElementById('evilDiv') != null);"); 964 EXPECT_TRUE(ui_test_utils::ExecuteJavaScriptAndExtractBool( 965 tab->render_view_host(), content_frame_xpath, is_evil_js, 966 &is_content_evil)); 967 EXPECT_FALSE(is_content_evil); 968} 969 970// Marked as flaky, see bug 40932. 971IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestUnsafeContentsInWorkerFiltered) { 972 ASSERT_TRUE(https_server_.Start()); 973 ASSERT_TRUE(https_server_expired_.Start()); 974 975 // This page will spawn a Worker which will try to load content from 976 // BadCertServer. 977 ui_test_utils::NavigateToURL(browser(), https_server_.GetURL( 978 "files/ssl/page_with_unsafe_worker.html")); 979 TabContents* tab = browser()->GetSelectedTabContents(); 980 // Expect Worker not to load insecure content. 981 CheckWorkerLoadResult(tab, false); 982 // The bad content is filtered, expect the state to be authenticated. 983 CheckAuthenticatedState(tab, false); 984} 985 986// Marked as flaky, see bug 40932. 987IN_PROC_BROWSER_TEST_F(SSLUITest, FLAKY_TestUnsafeContentsInWorker) { 988 ASSERT_TRUE(https_server_.Start()); 989 ASSERT_TRUE(https_server_expired_.Start()); 990 991 // Navigate to an unsafe site. Proceed with interstitial page to indicate 992 // the user approves the bad certificate. 993 ui_test_utils::NavigateToURL(browser(), 994 https_server_expired_.GetURL("files/ssl/blank_page.html")); 995 TabContents* tab = browser()->GetSelectedTabContents(); 996 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 997 true); // Interstitial showing 998 ProceedThroughInterstitial(tab); 999 CheckAuthenticationBrokenState(tab, net::CERT_STATUS_DATE_INVALID, false, 1000 false); // No Interstitial 1001 1002 // Navigate to safe page that has Worker loading unsafe content. 1003 // Expect content to load but be marked as auth broken due to running insecure 1004 // content. 1005 ui_test_utils::NavigateToURL(browser(), https_server_.GetURL( 1006 "files/ssl/page_with_unsafe_worker.html")); 1007 CheckWorkerLoadResult(tab, true); // Worker loads insecure content 1008 CheckAuthenticationBrokenState(tab, 0, true, false); 1009} 1010 1011// TODO(jcampan): more tests to do below. 1012 1013// Visit a page over https that contains a frame with a redirect. 1014 1015// XMLHttpRequest insecure content in synchronous mode. 1016 1017// XMLHttpRequest insecure content in asynchronous mode. 1018 1019// XMLHttpRequest over bad ssl in synchronous mode. 1020 1021// XMLHttpRequest over OK ssl in synchronous mode. 1022