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/command_line.h" 6 #include "base/logging.h" 7 #include "base/path_service.h" 8 #include "base/prefs/pref_service.h" 9 #include "base/strings/stringprintf.h" 10 #include "chrome/browser/browser_process.h" 11 #include "chrome/browser/download/download_service.h" 12 #include "chrome/browser/download/download_service_factory.h" 13 #include "chrome/browser/download/download_test_file_activity_observer.h" 14 #include "chrome/browser/net/url_request_mock_util.h" 15 #include "chrome/browser/profiles/profile.h" 16 #include "chrome/browser/profiles/profile_manager.h" 17 #include "chrome/browser/ui/browser.h" 18 #include "chrome/browser/ui/browser_iterator.h" 19 #include "chrome/browser/ui/browser_tabstrip.h" 20 #include "chrome/browser/ui/browser_window.h" 21 #include "chrome/browser/ui/host_desktop.h" 22 #include "chrome/browser/ui/tabs/tab_strip_model.h" 23 #include "chrome/common/chrome_paths.h" 24 #include "chrome/common/pref_names.h" 25 #include "chrome/common/url_constants.h" 26 #include "chrome/test/base/in_process_browser_test.h" 27 #include "chrome/test/base/ui_test_utils.h" 28 #include "content/public/browser/download_item.h" 29 #include "content/public/common/page_transition_types.h" 30 #include "content/public/test/browser_test_utils.h" 31 #include "content/public/test/download_test_observer.h" 32 #include "content/test/net/url_request_slow_download_job.h" 33 34 using content::BrowserContext; 35 using content::BrowserThread; 36 using content::DownloadItem; 37 using content::DownloadManager; 38 using content::URLRequestSlowDownloadJob; 39 40 class BrowserCloseTest : public InProcessBrowserTest { 41 public: 42 // Structure defining test cases for DownloadsCloseCheck. 43 struct DownloadsCloseCheckCase { 44 std::string DebugString() const; 45 46 // Input 47 struct { 48 struct { 49 int windows; 50 int downloads; 51 } regular; 52 struct { 53 int windows; 54 int downloads; 55 } incognito; 56 } profile_a; 57 58 struct { 59 struct { 60 int windows; 61 int downloads; 62 } regular; 63 struct { 64 int windows; 65 int downloads; 66 } incognito; 67 } profile_b; 68 69 // We always probe a window in profile A. 70 enum { REGULAR = 0, INCOGNITO = 1 } window_to_probe; 71 72 // Output 73 Browser::DownloadClosePreventionType type; 74 75 // Unchecked if type == DOWNLOAD_CLOSE_OK. 76 int num_blocking; 77 }; 78 79 protected: 80 virtual void SetUpOnMainThread() OVERRIDE { 81 BrowserThread::PostTask( 82 BrowserThread::IO, FROM_HERE, 83 base::Bind(&chrome_browser_net::SetUrlRequestMocksEnabled, true)); 84 } 85 86 // Create a second profile to work within multi-profile. 87 Profile* CreateSecondProfile() { 88 base::FilePath user_data_dir; 89 PathService::Get(chrome::DIR_USER_DATA, &user_data_dir); 90 91 if (!second_profile_data_dir_.CreateUniqueTempDirUnderPath(user_data_dir)) 92 return NULL; 93 94 Profile* second_profile = 95 g_browser_process->profile_manager()->GetProfile( 96 second_profile_data_dir_.path()); 97 if (!second_profile) 98 return NULL; 99 100 bool result = second_profile_downloads_dir_.CreateUniqueTempDir(); 101 if (!result) 102 return NULL; 103 second_profile->GetPrefs()->SetFilePath( 104 prefs::kDownloadDefaultDirectory, 105 second_profile_downloads_dir_.path()); 106 107 return second_profile; 108 } 109 110 // Create |num_downloads| number of downloads that are stalled 111 // (will quickly get to a place where the server won't 112 // provide any more data) so that we can test closing the 113 // browser with active downloads. 114 void CreateStalledDownloads(Browser* browser, int num_downloads) { 115 GURL url(URLRequestSlowDownloadJob::kKnownSizeUrl); 116 117 if (num_downloads == 0) 118 return; 119 120 // Setup an observer waiting for the given number of downloads 121 // to get to IN_PROGRESS. 122 DownloadManager* download_manager = 123 BrowserContext::GetDownloadManager(browser->profile()); 124 scoped_ptr<content::DownloadTestObserver> observer( 125 new content::DownloadTestObserverInProgress(download_manager, 126 num_downloads)); 127 128 // Set of that number of downloads. 129 size_t count_downloads = num_downloads; 130 while (num_downloads--) 131 ui_test_utils::NavigateToURLWithDisposition( 132 browser, url, NEW_BACKGROUND_TAB, 133 ui_test_utils::BROWSER_TEST_NONE); 134 135 // Wait for them. 136 observer->WaitForFinished(); 137 EXPECT_EQ(count_downloads, 138 observer->NumDownloadsSeenInState(DownloadItem::IN_PROGRESS)); 139 } 140 141 // All all downloads created in CreateStalledDownloads() to 142 // complete, and block in this routine until they do complete. 143 void CompleteAllDownloads(Browser* browser) { 144 GURL finish_url(URLRequestSlowDownloadJob::kFinishDownloadUrl); 145 ui_test_utils::NavigateToURL(browser, finish_url); 146 147 // Go through and, for every single profile, wait until there are 148 // no active downloads on that download manager. 149 std::vector<Profile*> profiles( 150 g_browser_process->profile_manager()->GetLoadedProfiles()); 151 for (std::vector<Profile*>::const_iterator pit = profiles.begin(); 152 pit != profiles.end(); ++pit) { 153 DownloadService* download_service = 154 DownloadServiceFactory::GetForBrowserContext(*pit); 155 if (download_service->HasCreatedDownloadManager()) { 156 DownloadManager *mgr = BrowserContext::GetDownloadManager(*pit); 157 scoped_refptr<content::DownloadTestFlushObserver> observer( 158 new content::DownloadTestFlushObserver(mgr)); 159 observer->WaitForFlush(); 160 } 161 if ((*pit)->HasOffTheRecordProfile()) { 162 DownloadService* incognito_download_service = 163 DownloadServiceFactory::GetForBrowserContext( 164 (*pit)->GetOffTheRecordProfile()); 165 if (incognito_download_service->HasCreatedDownloadManager()) { 166 DownloadManager *mgr = BrowserContext::GetDownloadManager( 167 (*pit)->GetOffTheRecordProfile()); 168 scoped_refptr<content::DownloadTestFlushObserver> observer( 169 new content::DownloadTestFlushObserver(mgr)); 170 observer->WaitForFlush(); 171 } 172 } 173 } 174 } 175 176 // Create a Browser (with associated window) on the specified profile. 177 Browser* CreateBrowserOnProfile(Profile* profile, 178 chrome::HostDesktopType host_desktop_type) { 179 Browser* new_browser = 180 new Browser(Browser::CreateParams(profile, host_desktop_type)); 181 chrome::AddSelectedTabWithURL(new_browser, GURL(content::kAboutBlankURL), 182 content::PAGE_TRANSITION_AUTO_TOPLEVEL); 183 content::WaitForLoadStop( 184 new_browser->tab_strip_model()->GetActiveWebContents()); 185 new_browser->window()->Show(); 186 return new_browser; 187 } 188 189 // Adjust the number of browsers and associated windows up or down 190 // to |num_windows|. This routine assumes that there is only a single 191 // browser associated with the profile on entry. |*base_browser| contains 192 // this browser, and the profile is derived from that browser. On output, 193 // if |*base_browser| was destroyed (because |num_windows == 0|), NULL 194 // is assigned to that memory location. 195 bool AdjustBrowsersOnProfile(Browser** base_browser, int num_windows) { 196 int num_downloads_blocking; 197 if (num_windows == 0) { 198 if (Browser::DOWNLOAD_CLOSE_OK != 199 (*base_browser)->OkToCloseWithInProgressDownloads( 200 &num_downloads_blocking)) 201 return false; 202 (*base_browser)->window()->Close(); 203 *base_browser = 0; 204 return true; 205 } 206 207 // num_windows > 0 208 Profile* profile((*base_browser)->profile()); 209 chrome::HostDesktopType host_desktop_type = 210 (*base_browser)->host_desktop_type(); 211 for (int w = 1; w < num_windows; ++w) { 212 CreateBrowserOnProfile(profile, host_desktop_type); 213 } 214 return true; 215 } 216 217 int TotalUnclosedBrowsers() { 218 int count = 0; 219 for (chrome::BrowserIterator it; !it.done(); it.Next()) { 220 if (!it->IsAttemptingToCloseBrowser()) 221 count++; 222 } 223 return count; 224 } 225 226 // Note that this is invalid to call if TotalUnclosedBrowsers() == 0. 227 Browser* FirstUnclosedBrowser() { 228 for (chrome::BrowserIterator it; !it.done(); it.Next()) { 229 if (!it->IsAttemptingToCloseBrowser()) 230 return *it; 231 } 232 return NULL; 233 } 234 235 bool SetupForDownloadCloseCheck() { 236 first_profile_ = browser()->profile(); 237 238 bool result = first_profile_downloads_dir_.CreateUniqueTempDir(); 239 EXPECT_TRUE(result); 240 if (!result) return false; 241 first_profile_->GetPrefs()->SetFilePath( 242 prefs::kDownloadDefaultDirectory, 243 first_profile_downloads_dir_.path()); 244 245 second_profile_ = CreateSecondProfile(); 246 EXPECT_TRUE(second_profile_); 247 if (!second_profile_) return false; 248 249 DownloadTestFileActivityObserver(first_profile_) .EnableFileChooser(false); 250 DownloadTestFileActivityObserver(second_profile_).EnableFileChooser(false); 251 return true; 252 } 253 254 // Test a specific DownloadsCloseCheckCase. Returns false if 255 // an assertion has failed and the test should be aborted. 256 bool ExecuteDownloadCloseCheckCase(size_t i) { 257 const DownloadsCloseCheckCase& check_case(download_close_check_cases[i]); 258 SCOPED_TRACE(testing::Message() << "Case" << i 259 << ": " << check_case.DebugString()); 260 261 // Test invariant: so that we don't actually try and close the browser, 262 // we always enter the function with a single browser window open on the 263 // main profile. That means we need to exit the function the same way. 264 // So we setup everything except for the |first_profile_| regular, and then 265 // flip the bit on the main window. 266 // Note that this means that browser() is unreliable in the context 267 // of this function or its callers; we'll be killing that main window 268 // and recreating it fairly frequently. 269 int unclosed_browsers = TotalUnclosedBrowsers(); 270 EXPECT_EQ(1, unclosed_browsers); 271 if (1 != unclosed_browsers) 272 return false; 273 274 Browser* entry_browser = FirstUnclosedBrowser(); 275 EXPECT_EQ(first_profile_, entry_browser->profile()); 276 if (first_profile_ != entry_browser->profile()) 277 return false; 278 int total_download_count = 279 DownloadService::NonMaliciousDownloadCountAllProfiles(); 280 EXPECT_EQ(0, total_download_count); 281 if (0 != total_download_count) 282 return false; 283 Profile* first_profile_incognito = first_profile_->GetOffTheRecordProfile(); 284 Profile* second_profile_incognito = 285 second_profile_->GetOffTheRecordProfile(); 286 DownloadTestFileActivityObserver(first_profile_incognito) 287 .EnableFileChooser(false); 288 DownloadTestFileActivityObserver(second_profile_incognito) 289 .EnableFileChooser(false); 290 291 // For simplicty of coding, we create a window on each profile so that 292 // we can easily create downloads, then we destroy or create windows 293 // as necessary. 294 chrome::HostDesktopType host_desktop_type = 295 entry_browser->host_desktop_type(); 296 Browser* browser_a_regular(CreateBrowserOnProfile(first_profile_, 297 host_desktop_type)); 298 Browser* browser_a_incognito( 299 CreateBrowserOnProfile(first_profile_incognito, host_desktop_type)); 300 Browser* browser_b_regular(CreateBrowserOnProfile(second_profile_, 301 host_desktop_type)); 302 Browser* browser_b_incognito( 303 CreateBrowserOnProfile(second_profile_incognito, host_desktop_type)); 304 305 // Kill our entry browser. 306 entry_browser->window()->Close(); 307 entry_browser = NULL; 308 309 // Create all downloads needed. 310 CreateStalledDownloads( 311 browser_a_regular, check_case.profile_a.regular.downloads); 312 CreateStalledDownloads( 313 browser_a_incognito, check_case.profile_a.incognito.downloads); 314 CreateStalledDownloads( 315 browser_b_regular, check_case.profile_b.regular.downloads); 316 CreateStalledDownloads( 317 browser_b_incognito, check_case.profile_b.incognito.downloads); 318 319 // Adjust the windows 320 Browser** browsers[] = { 321 &browser_a_regular, &browser_a_incognito, 322 &browser_b_regular, &browser_b_incognito 323 }; 324 int window_counts[] = { 325 check_case.profile_a.regular.windows, 326 check_case.profile_a.incognito.windows, 327 check_case.profile_b.regular.windows, 328 check_case.profile_b.incognito.windows, 329 }; 330 for (size_t j = 0; j < arraysize(browsers); ++j) { 331 bool result = AdjustBrowsersOnProfile(browsers[j], window_counts[j]); 332 EXPECT_TRUE(result); 333 if (!result) 334 return false; 335 } 336 content::RunAllPendingInMessageLoop(); 337 338 // All that work, for this one little test. 339 EXPECT_TRUE((check_case.window_to_probe == 340 DownloadsCloseCheckCase::REGULAR) || 341 (check_case.window_to_probe == 342 DownloadsCloseCheckCase::INCOGNITO)); 343 if (!((check_case.window_to_probe == 344 DownloadsCloseCheckCase::REGULAR) || 345 (check_case.window_to_probe == 346 DownloadsCloseCheckCase::INCOGNITO))) 347 return false; 348 349 int num_downloads_blocking; 350 Browser* browser_to_probe = 351 (check_case.window_to_probe == DownloadsCloseCheckCase::REGULAR ? 352 browser_a_regular : 353 browser_a_incognito); 354 Browser::DownloadClosePreventionType type = 355 browser_to_probe->OkToCloseWithInProgressDownloads( 356 &num_downloads_blocking); 357 EXPECT_EQ(check_case.type, type); 358 if (type != Browser::DOWNLOAD_CLOSE_OK) 359 EXPECT_EQ(check_case.num_blocking, num_downloads_blocking); 360 361 // Release all the downloads. 362 CompleteAllDownloads(browser_to_probe); 363 364 // Create a new main window and kill everything else. 365 entry_browser = CreateBrowserOnProfile(first_profile_, host_desktop_type); 366 for (chrome::BrowserIterator it; !it.done(); it.Next()) { 367 if ((*it) != entry_browser) { 368 if (!it->window()) { 369 ADD_FAILURE(); 370 return false; 371 } 372 it->window()->Close(); 373 } 374 } 375 content::RunAllPendingInMessageLoop(); 376 377 return true; 378 } 379 380 static const DownloadsCloseCheckCase download_close_check_cases[]; 381 382 // DownloadCloseCheck variables. 383 Profile* first_profile_; 384 Profile* second_profile_; 385 386 base::ScopedTempDir first_profile_downloads_dir_; 387 base::ScopedTempDir second_profile_data_dir_; 388 base::ScopedTempDir second_profile_downloads_dir_; 389 }; 390 391 const BrowserCloseTest::DownloadsCloseCheckCase 392 BrowserCloseTest::download_close_check_cases[] = { 393 // Top level nesting is {profile_a, profile_b} 394 // Second level nesting is {regular, incognito 395 // Third level (inner) nesting is {windows, downloads} 396 397 // Last window (incognito) triggers browser close warning. 398 {{{0, 0}, {1, 1}}, {{0, 0}, {0, 0}}, 399 BrowserCloseTest::DownloadsCloseCheckCase::INCOGNITO, 400 Browser::DOWNLOAD_CLOSE_BROWSER_SHUTDOWN, 1}, 401 402 // Last incognito window triggers incognito close warning. 403 {{{1, 0}, {1, 1}}, {{0, 0}, {0, 0}}, 404 BrowserCloseTest::DownloadsCloseCheckCase::INCOGNITO, 405 Browser::DOWNLOAD_CLOSE_LAST_WINDOW_IN_INCOGNITO_PROFILE, 1}, 406 407 // Last incognito window with no downloads triggers no warning. 408 {{{0, 0}, {1, 0}}, {{0, 0}, {0, 0}}, 409 BrowserCloseTest::DownloadsCloseCheckCase::INCOGNITO, 410 Browser::DOWNLOAD_CLOSE_OK}, 411 412 // Last incognito window with window+download on another incognito profile 413 // triggers no warning. 414 {{{0, 0}, {1, 0}}, {{0, 0}, {1, 1}}, 415 BrowserCloseTest::DownloadsCloseCheckCase::INCOGNITO, 416 Browser::DOWNLOAD_CLOSE_OK}, 417 418 // Non-last incognito window triggers no warning. 419 {{{0, 0}, {2, 1}}, {{0, 0}, {0, 0}}, 420 BrowserCloseTest::DownloadsCloseCheckCase::INCOGNITO, 421 Browser::DOWNLOAD_CLOSE_OK}, 422 423 // Non-last regular window triggers no warning. 424 {{{2, 1}, {0, 0}}, {{0, 0}, {0, 0}}, 425 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 426 Browser::DOWNLOAD_CLOSE_OK}, 427 428 // Last regular window triggers browser close. 429 {{{1, 1}, {0, 0}}, {{0, 0}, {0, 0}}, 430 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 431 Browser::DOWNLOAD_CLOSE_BROWSER_SHUTDOWN, 1}, 432 433 // Last regular window triggers browser close for download on different 434 // profile. 435 {{{1, 0}, {0, 0}}, {{0, 1}, {0, 0}}, 436 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 437 Browser::DOWNLOAD_CLOSE_BROWSER_SHUTDOWN, 1}, 438 439 // Last regular window triggers no warning if incognito 440 // active (http://crbug.com/61257). 441 {{{1, 0}, {1, 1}}, {{0, 0}, {0, 0}}, 442 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 443 Browser::DOWNLOAD_CLOSE_OK}, 444 445 // Last regular window triggers no warning if other profile window active. 446 {{{1, 1}, {0, 0}}, {{1, 0}, {0, 0}}, 447 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 448 Browser::DOWNLOAD_CLOSE_OK}, 449 450 // Last regular window triggers no warning if other incognito window 451 // active. 452 {{{1, 0}, {0, 0}}, {{0, 0}, {1, 1}}, 453 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 454 Browser::DOWNLOAD_CLOSE_OK}, 455 456 // Last regular window triggers no warning if incognito active. 457 {{{1, 1}, {1, 0}}, {{0, 0}, {0, 0}}, 458 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 459 Browser::DOWNLOAD_CLOSE_OK}, 460 461 // Test plural for regular. 462 {{{1, 2}, {0, 0}}, {{0, 0}, {0, 0}}, 463 BrowserCloseTest::DownloadsCloseCheckCase::REGULAR, 464 Browser::DOWNLOAD_CLOSE_BROWSER_SHUTDOWN, 2}, 465 466 // Test plural for incognito. 467 {{{1, 0}, {1, 2}}, {{0, 0}, {0, 0}}, 468 BrowserCloseTest::DownloadsCloseCheckCase::INCOGNITO, 469 Browser::DOWNLOAD_CLOSE_LAST_WINDOW_IN_INCOGNITO_PROFILE, 2}, 470 }; 471 472 std::string BrowserCloseTest::DownloadsCloseCheckCase::DebugString() const { 473 std::string result; 474 result += "{"; 475 if (profile_a.regular.windows || profile_a.regular.downloads) 476 result += base::StringPrintf("Regular profile A: (%d w, %d d), ", 477 profile_a.regular.windows, 478 profile_a.regular.downloads); 479 if (profile_a.incognito.windows || profile_a.incognito.downloads) 480 result += base::StringPrintf("Incognito profile A: (%d w, %d d), ", 481 profile_a.incognito.windows, 482 profile_a.incognito.downloads); 483 if (profile_b.regular.windows || profile_b.regular.downloads) 484 result += base::StringPrintf("Regular profile B: (%d w, %d d), ", 485 profile_b.regular.windows, 486 profile_b.regular.downloads); 487 if (profile_b.incognito.windows || profile_b.incognito.downloads) 488 result += base::StringPrintf("Incognito profile B: (%d w, %d d), ", 489 profile_b.incognito.windows, 490 profile_b.incognito.downloads); 491 result += (window_to_probe == REGULAR ? "Probe regular" : 492 window_to_probe == INCOGNITO ? "Probe incognito" : 493 "Probe unknown"); 494 result += "} -> "; 495 if (type == Browser::DOWNLOAD_CLOSE_OK) { 496 result += "No warning"; 497 } else { 498 result += base::StringPrintf( 499 "%s (%d downloads) warning", 500 (type == Browser::DOWNLOAD_CLOSE_BROWSER_SHUTDOWN ? "Browser shutdown" : 501 type == Browser::DOWNLOAD_CLOSE_LAST_WINDOW_IN_INCOGNITO_PROFILE ? 502 "Incognito close" : "Unknown"), 503 num_blocking); 504 } 505 return result; 506 } 507 508 // The following test is split into six chunks to reduce the chance 509 // of hitting the 25s timeout. 510 511 // This test is timing out very often under AddressSanitizer. 512 // http://crbug.com/111914 and http://crbug.com/103371. 513 // Crashing on Linux. http://crbug.com/100566 514 // Timing out on XP debug. http://crbug.com/111914 515 // Timing out, http://crbug.com/159449 . 516 517 #define MAYBE_DownloadsCloseCheck_0 DISABLED_DownloadsCloseCheck_0 518 #define MAYBE_DownloadsCloseCheck_1 DISABLED_DownloadsCloseCheck_1 519 #define MAYBE_DownloadsCloseCheck_2 DISABLED_DownloadsCloseCheck_2 520 #define MAYBE_DownloadsCloseCheck_3 DISABLED_DownloadsCloseCheck_3 521 #define MAYBE_DownloadsCloseCheck_4 DISABLED_DownloadsCloseCheck_4 522 #define MAYBE_DownloadsCloseCheck_5 DISABLED_DownloadsCloseCheck_5 523 524 IN_PROC_BROWSER_TEST_F(BrowserCloseTest, MAYBE_DownloadsCloseCheck_0) { 525 ASSERT_TRUE(SetupForDownloadCloseCheck()); 526 for (size_t i = 0; i < arraysize(download_close_check_cases) / 6; ++i) { 527 ExecuteDownloadCloseCheckCase(i); 528 } 529 } 530 531 IN_PROC_BROWSER_TEST_F(BrowserCloseTest, MAYBE_DownloadsCloseCheck_1) { 532 ASSERT_TRUE(SetupForDownloadCloseCheck()); 533 for (size_t i = arraysize(download_close_check_cases) / 6; 534 i < 2 * arraysize(download_close_check_cases) / 6; ++i) { 535 ExecuteDownloadCloseCheckCase(i); 536 } 537 } 538 539 IN_PROC_BROWSER_TEST_F(BrowserCloseTest, MAYBE_DownloadsCloseCheck_2) { 540 ASSERT_TRUE(SetupForDownloadCloseCheck()); 541 for (size_t i = 2 * arraysize(download_close_check_cases) / 6; 542 i < 3 * arraysize(download_close_check_cases) / 6; ++i) { 543 ExecuteDownloadCloseCheckCase(i); 544 } 545 } 546 547 IN_PROC_BROWSER_TEST_F(BrowserCloseTest, MAYBE_DownloadsCloseCheck_3) { 548 ASSERT_TRUE(SetupForDownloadCloseCheck()); 549 for (size_t i = 3 * arraysize(download_close_check_cases) / 6; 550 i < 4 * arraysize(download_close_check_cases) / 6; ++i) { 551 ExecuteDownloadCloseCheckCase(i); 552 } 553 } 554 555 IN_PROC_BROWSER_TEST_F(BrowserCloseTest, MAYBE_DownloadsCloseCheck_4) { 556 ASSERT_TRUE(SetupForDownloadCloseCheck()); 557 for (size_t i = 4 * arraysize(download_close_check_cases) / 6; 558 i < 5 * arraysize(download_close_check_cases) / 6; ++i) { 559 ExecuteDownloadCloseCheckCase(i); 560 } 561 } 562 563 IN_PROC_BROWSER_TEST_F(BrowserCloseTest, MAYBE_DownloadsCloseCheck_5) { 564 ASSERT_TRUE(SetupForDownloadCloseCheck()); 565 for (size_t i = 5 * arraysize(download_close_check_cases) / 6; 566 i < 6 * arraysize(download_close_check_cases) / 6; ++i) { 567 ExecuteDownloadCloseCheckCase(i); 568 } 569 } 570