Adding instrumentation to locate the source of jankiness
[chromium-blink-merge.git] / chrome / browser / extensions / app_background_page_apitest.cc
blob3362922bb5490ffaf487848a4888b1d2ae3c1c1e
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.
5 #include "base/path_service.h"
6 #include "base/strings/stringprintf.h"
7 #include "base/strings/utf_string_conversions.h"
8 #include "chrome/browser/background/background_contents_service.h"
9 #include "chrome/browser/background/background_contents_service_factory.h"
10 #include "chrome/browser/background/background_mode_manager.h"
11 #include "chrome/browser/browser_process.h"
12 #include "chrome/browser/chrome_notification_types.h"
13 #include "chrome/browser/extensions/extension_apitest.h"
14 #include "chrome/browser/extensions/extension_service.h"
15 #include "chrome/browser/profiles/profile.h"
16 #include "chrome/browser/ui/browser.h"
17 #include "chrome/browser/ui/browser_dialogs.h"
18 #include "chrome/browser/ui/browser_window.h"
19 #include "chrome/browser/ui/extensions/application_launch.h"
20 #include "chrome/common/chrome_paths.h"
21 #include "chrome/common/chrome_switches.h"
22 #include "content/public/browser/notification_service.h"
23 #include "content/public/test/test_notification_tracker.h"
24 #include "content/public/test/test_utils.h"
25 #include "extensions/browser/process_manager.h"
26 #include "extensions/common/extension.h"
27 #include "extensions/common/switches.h"
28 #include "extensions/test/extension_test_message_listener.h"
29 #include "net/dns/mock_host_resolver.h"
30 #include "net/test/embedded_test_server/embedded_test_server.h"
32 #if !defined(DISABLE_NACL)
33 #include "components/nacl/browser/nacl_process_host.h"
34 #endif
36 #if defined(OS_MACOSX)
37 #include "base/mac/scoped_nsautorelease_pool.h"
38 #endif
40 using base::ASCIIToUTF16;
41 using extensions::Extension;
43 class AppBackgroundPageApiTest : public ExtensionApiTest {
44 public:
45 virtual void SetUpCommandLine(CommandLine* command_line) override {
46 ExtensionApiTest::SetUpCommandLine(command_line);
47 command_line->AppendSwitch(switches::kDisablePopupBlocking);
48 command_line->AppendSwitch(extensions::switches::kAllowHTTPBackgroundPage);
51 bool CreateApp(const std::string& app_manifest,
52 base::FilePath* app_dir) {
53 if (!app_dir_.CreateUniqueTempDir()) {
54 LOG(ERROR) << "Unable to create a temporary directory.";
55 return false;
57 base::FilePath manifest_path = app_dir_.path().AppendASCII("manifest.json");
58 int bytes_written = base::WriteFile(manifest_path,
59 app_manifest.data(),
60 app_manifest.size());
61 if (bytes_written != static_cast<int>(app_manifest.size())) {
62 LOG(ERROR) << "Unable to write complete manifest to file. Return code="
63 << bytes_written;
64 return false;
66 *app_dir = app_dir_.path();
67 return true;
70 bool WaitForBackgroundMode(bool expected_background_mode) {
71 #if defined(OS_CHROMEOS)
72 // BackgroundMode is not supported on chromeos, so we should test the
73 // behavior of BackgroundContents, but not the background mode state itself.
74 return true;
75 #else
76 BackgroundModeManager* manager =
77 g_browser_process->background_mode_manager();
78 // If background mode is disabled on this platform (e.g. cros), then skip
79 // this check.
80 if (!manager || !manager->IsBackgroundModePrefEnabled()) {
81 DLOG(WARNING) << "Skipping check - background mode disabled";
82 return true;
84 if (manager->IsBackgroundModeActive() == expected_background_mode)
85 return true;
87 // We are not currently in the expected state - wait for the state to
88 // change.
89 content::WindowedNotificationObserver watcher(
90 chrome::NOTIFICATION_BACKGROUND_MODE_CHANGED,
91 content::NotificationService::AllSources());
92 watcher.Wait();
93 return manager->IsBackgroundModeActive() == expected_background_mode;
94 #endif
97 void CloseBrowser(Browser* browser) {
98 content::WindowedNotificationObserver observer(
99 chrome::NOTIFICATION_BROWSER_CLOSED,
100 content::NotificationService::AllSources());
101 browser->window()->Close();
102 #if defined(OS_MACOSX)
103 // BrowserWindowController depends on the auto release pool being recycled
104 // in the message loop to delete itself, which frees the Browser object
105 // which fires this event.
106 AutoreleasePool()->Recycle();
107 #endif
108 observer.Wait();
111 void UnloadExtensionViaTask(const std::string& id) {
112 base::MessageLoop::current()->PostTask(
113 FROM_HERE,
114 base::Bind(&AppBackgroundPageApiTest::UnloadExtension, this, id));
117 private:
118 base::ScopedTempDir app_dir_;
121 namespace {
123 // Fixture to assist in testing v2 app background pages containing
124 // Native Client embeds.
125 class AppBackgroundPageNaClTest : public AppBackgroundPageApiTest {
126 public:
127 AppBackgroundPageNaClTest()
128 : extension_(NULL) {}
129 virtual ~AppBackgroundPageNaClTest() {
132 virtual void SetUpOnMainThread() override {
133 AppBackgroundPageApiTest::SetUpOnMainThread();
134 #if !defined(DISABLE_NACL)
135 nacl::NaClProcessHost::SetPpapiKeepAliveThrottleForTesting(50);
136 #endif
137 extensions::ProcessManager::SetEventPageIdleTimeForTesting(1000);
138 extensions::ProcessManager::SetEventPageSuspendingTimeForTesting(1000);
141 const Extension* extension() { return extension_; }
143 protected:
144 void LaunchTestingApp() {
145 base::FilePath app_dir;
146 PathService::Get(chrome::DIR_GEN_TEST_DATA, &app_dir);
147 app_dir = app_dir.AppendASCII(
148 "ppapi/tests/extensions/background_keepalive/newlib");
149 extension_ = LoadExtension(app_dir);
150 ASSERT_TRUE(extension_);
153 private:
154 const Extension* extension_;
157 // Produces an extensions::ProcessManager::ImpulseCallbackForTesting callback
158 // that will match a specified goal and can be waited on.
159 class ImpulseCallbackCounter {
160 public:
161 explicit ImpulseCallbackCounter(extensions::ProcessManager* manager,
162 const std::string& extension_id)
163 : observed_(0),
164 goal_(0),
165 manager_(manager),
166 extension_id_(extension_id) {
169 extensions::ProcessManager::ImpulseCallbackForTesting
170 SetGoalAndGetCallback(int goal) {
171 observed_ = 0;
172 goal_ = goal;
173 message_loop_runner_ = new content::MessageLoopRunner();
174 return base::Bind(&ImpulseCallbackCounter::ImpulseCallback,
175 base::Unretained(this),
176 message_loop_runner_->QuitClosure(),
177 extension_id_);
180 void Wait() {
181 message_loop_runner_->Run();
183 private:
184 void ImpulseCallback(
185 const base::Closure& quit_callback,
186 const std::string& extension_id_from_test,
187 const std::string& extension_id_from_manager) {
188 if (extension_id_from_test == extension_id_from_manager) {
189 if (++observed_ >= goal_) {
190 // Clear callback to free reference to message loop.
191 manager_->SetKeepaliveImpulseCallbackForTesting(
192 extensions::ProcessManager::ImpulseCallbackForTesting());
193 manager_->SetKeepaliveImpulseDecrementCallbackForTesting(
194 extensions::ProcessManager::ImpulseCallbackForTesting());
195 quit_callback.Run();
200 int observed_;
201 int goal_;
202 extensions::ProcessManager* manager_;
203 const std::string extension_id_;
204 scoped_refptr<content::MessageLoopRunner> message_loop_runner_;
207 } // namespace
209 // Disable on Mac only. http://crbug.com/95139
210 #if defined(OS_MACOSX)
211 #define MAYBE_Basic DISABLED_Basic
212 #else
213 #define MAYBE_Basic Basic
214 #endif
216 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, MAYBE_Basic) {
217 host_resolver()->AddRule("a.com", "127.0.0.1");
218 ASSERT_TRUE(StartEmbeddedTestServer());
220 std::string app_manifest = base::StringPrintf(
222 " \"name\": \"App\","
223 " \"version\": \"0.1\","
224 " \"manifest_version\": 2,"
225 " \"app\": {"
226 " \"urls\": ["
227 " \"http://a.com/\""
228 " ],"
229 " \"launch\": {"
230 " \"web_url\": \"http://a.com:%d/\""
231 " }"
232 " },"
233 " \"permissions\": [\"background\"]"
234 "}",
235 embedded_test_server()->port());
237 base::FilePath app_dir;
238 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
239 ASSERT_TRUE(LoadExtension(app_dir));
240 // Background mode should not be active until a background page is created.
241 ASSERT_TRUE(WaitForBackgroundMode(false));
242 ASSERT_TRUE(RunExtensionTest("app_background_page/basic")) << message_;
243 // The test closes the background contents, so we should fall back to no
244 // background mode at the end.
245 ASSERT_TRUE(WaitForBackgroundMode(false));
248 // Crashy, http://crbug.com/69215.
249 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, DISABLED_LacksPermission) {
250 host_resolver()->AddRule("a.com", "127.0.0.1");
251 ASSERT_TRUE(StartEmbeddedTestServer());
253 std::string app_manifest = base::StringPrintf(
255 " \"name\": \"App\","
256 " \"version\": \"0.1\","
257 " \"manifest_version\": 2,"
258 " \"app\": {"
259 " \"urls\": ["
260 " \"http://a.com/\""
261 " ],"
262 " \"launch\": {"
263 " \"web_url\": \"http://a.com:%d/\""
264 " }"
265 " }"
266 "}",
267 embedded_test_server()->port());
269 base::FilePath app_dir;
270 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
271 ASSERT_TRUE(LoadExtension(app_dir));
272 ASSERT_TRUE(RunExtensionTest("app_background_page/lacks_permission"))
273 << message_;
274 ASSERT_TRUE(WaitForBackgroundMode(false));
277 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, ManifestBackgroundPage) {
278 host_resolver()->AddRule("a.com", "127.0.0.1");
279 ASSERT_TRUE(StartEmbeddedTestServer());
281 std::string app_manifest = base::StringPrintf(
283 " \"name\": \"App\","
284 " \"version\": \"0.1\","
285 " \"manifest_version\": 2,"
286 " \"app\": {"
287 " \"urls\": ["
288 " \"http://a.com/\""
289 " ],"
290 " \"launch\": {"
291 " \"web_url\": \"http://a.com:%d/\""
292 " }"
293 " },"
294 " \"permissions\": [\"background\"],"
295 " \"background\": {"
296 " \"page\": \"http://a.com:%d/test.html\""
297 " }"
298 "}",
299 embedded_test_server()->port(),
300 embedded_test_server()->port());
302 base::FilePath app_dir;
303 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
304 // Background mode should not be active now because no background app was
305 // loaded.
306 ASSERT_TRUE(LoadExtension(app_dir));
307 // Background mode be active now because a background page was created when
308 // the app was loaded.
309 ASSERT_TRUE(WaitForBackgroundMode(true));
311 const Extension* extension = GetSingleLoadedExtension();
312 ASSERT_TRUE(
313 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
314 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
315 UnloadExtension(extension->id());
318 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, NoJsBackgroundPage) {
319 // Keep the task manager up through this test to verify that a crash doesn't
320 // happen when window.open creates a background page that switches
321 // RenderViewHosts. See http://crbug.com/165138.
322 chrome::ShowTaskManager(browser());
324 // Make sure that no BackgroundContentses get deleted (a signal that repeated
325 // window.open calls recreate instances, instead of being no-ops).
326 content::TestNotificationTracker background_deleted_tracker;
327 background_deleted_tracker.ListenFor(
328 chrome::NOTIFICATION_BACKGROUND_CONTENTS_DELETED,
329 content::Source<Profile>(browser()->profile()));
331 host_resolver()->AddRule("a.com", "127.0.0.1");
332 ASSERT_TRUE(StartEmbeddedTestServer());
334 std::string app_manifest = base::StringPrintf(
336 " \"name\": \"App\","
337 " \"version\": \"0.1\","
338 " \"manifest_version\": 2,"
339 " \"app\": {"
340 " \"urls\": ["
341 " \"http://a.com/\""
342 " ],"
343 " \"launch\": {"
344 " \"web_url\": \"http://a.com:%d/test.html\""
345 " }"
346 " },"
347 " \"permissions\": [\"background\"],"
348 " \"background\": {"
349 " \"allow_js_access\": false"
350 " }"
351 "}",
352 embedded_test_server()->port());
354 base::FilePath app_dir;
355 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
356 ASSERT_TRUE(LoadExtension(app_dir));
358 // There isn't a background page loaded initially.
359 const Extension* extension = GetSingleLoadedExtension();
360 ASSERT_FALSE(
361 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
362 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
363 // The test makes sure that window.open returns null.
364 ASSERT_TRUE(RunExtensionTest("app_background_page/no_js")) << message_;
365 // And after it runs there should be a background page.
366 ASSERT_TRUE(
367 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
368 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
370 EXPECT_EQ(0u, background_deleted_tracker.size());
371 UnloadExtension(extension->id());
374 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, NoJsManifestBackgroundPage) {
375 host_resolver()->AddRule("a.com", "127.0.0.1");
376 ASSERT_TRUE(StartEmbeddedTestServer());
378 std::string app_manifest = base::StringPrintf(
380 " \"name\": \"App\","
381 " \"version\": \"0.1\","
382 " \"manifest_version\": 2,"
383 " \"app\": {"
384 " \"urls\": ["
385 " \"http://a.com/\""
386 " ],"
387 " \"launch\": {"
388 " \"web_url\": \"http://a.com:%d/\""
389 " }"
390 " },"
391 " \"permissions\": [\"background\"],"
392 " \"background\": {"
393 " \"page\": \"http://a.com:%d/bg.html\","
394 " \"allow_js_access\": false"
395 " }"
396 "}",
397 embedded_test_server()->port(),
398 embedded_test_server()->port());
400 base::FilePath app_dir;
401 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
402 ASSERT_TRUE(LoadExtension(app_dir));
404 // The background page should load, but window.open should return null.
405 const Extension* extension = GetSingleLoadedExtension();
406 ASSERT_TRUE(
407 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
408 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
409 ASSERT_TRUE(RunExtensionTest("app_background_page/no_js_manifest")) <<
410 message_;
411 UnloadExtension(extension->id());
414 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, OpenTwoBackgroundPages) {
415 host_resolver()->AddRule("a.com", "127.0.0.1");
416 ASSERT_TRUE(StartEmbeddedTestServer());
418 std::string app_manifest = base::StringPrintf(
420 " \"name\": \"App\","
421 " \"version\": \"0.1\","
422 " \"manifest_version\": 2,"
423 " \"app\": {"
424 " \"urls\": ["
425 " \"http://a.com/\""
426 " ],"
427 " \"launch\": {"
428 " \"web_url\": \"http://a.com:%d/\""
429 " }"
430 " },"
431 " \"permissions\": [\"background\"]"
432 "}",
433 embedded_test_server()->port());
435 base::FilePath app_dir;
436 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
437 ASSERT_TRUE(LoadExtension(app_dir));
438 const Extension* extension = GetSingleLoadedExtension();
439 ASSERT_TRUE(RunExtensionTest("app_background_page/two_pages")) << message_;
440 UnloadExtension(extension->id());
443 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, OpenTwoPagesWithManifest) {
444 host_resolver()->AddRule("a.com", "127.0.0.1");
445 ASSERT_TRUE(StartEmbeddedTestServer());
447 std::string app_manifest = base::StringPrintf(
449 " \"name\": \"App\","
450 " \"version\": \"0.1\","
451 " \"manifest_version\": 2,"
452 " \"app\": {"
453 " \"urls\": ["
454 " \"http://a.com/\""
455 " ],"
456 " \"launch\": {"
457 " \"web_url\": \"http://a.com:%d/\""
458 " }"
459 " },"
460 " \"background\": {"
461 " \"page\": \"http://a.com:%d/bg.html\""
462 " },"
463 " \"permissions\": [\"background\"]"
464 "}",
465 embedded_test_server()->port(),
466 embedded_test_server()->port());
468 base::FilePath app_dir;
469 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
470 ASSERT_TRUE(LoadExtension(app_dir));
471 const Extension* extension = GetSingleLoadedExtension();
472 ASSERT_TRUE(RunExtensionTest("app_background_page/two_with_manifest")) <<
473 message_;
474 UnloadExtension(extension->id());
477 // Times out occasionally -- see crbug.com/108493
478 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, DISABLED_OpenPopupFromBGPage) {
479 host_resolver()->AddRule("a.com", "127.0.0.1");
480 ASSERT_TRUE(StartEmbeddedTestServer());
482 std::string app_manifest = base::StringPrintf(
484 " \"name\": \"App\","
485 " \"version\": \"0.1\","
486 " \"manifest_version\": 2,"
487 " \"app\": {"
488 " \"urls\": ["
489 " \"http://a.com/\""
490 " ],"
491 " \"launch\": {"
492 " \"web_url\": \"http://a.com:%d/\""
493 " }"
494 " },"
495 " \"background\": { \"page\": \"http://a.com:%d/extensions/api_test/"
496 "app_background_page/bg_open/bg_open_bg.html\" },"
497 " \"permissions\": [\"background\"]"
498 "}",
499 embedded_test_server()->port(),
500 embedded_test_server()->port());
502 base::FilePath app_dir;
503 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
504 ASSERT_TRUE(LoadExtension(app_dir));
505 ASSERT_TRUE(RunExtensionTest("app_background_page/bg_open")) << message_;
508 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, DISABLED_OpenThenClose) {
509 host_resolver()->AddRule("a.com", "127.0.0.1");
510 ASSERT_TRUE(StartEmbeddedTestServer());
512 std::string app_manifest = base::StringPrintf(
514 " \"name\": \"App\","
515 " \"version\": \"0.1\","
516 " \"manifest_version\": 2,"
517 " \"app\": {"
518 " \"urls\": ["
519 " \"http://a.com/\""
520 " ],"
521 " \"launch\": {"
522 " \"web_url\": \"http://a.com:%d/\""
523 " }"
524 " },"
525 " \"permissions\": [\"background\"]"
526 "}",
527 embedded_test_server()->port());
529 base::FilePath app_dir;
530 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
531 ASSERT_TRUE(LoadExtension(app_dir));
532 // There isn't a background page loaded initially.
533 const Extension* extension = GetSingleLoadedExtension();
534 ASSERT_FALSE(
535 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
536 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
537 // Background mode should not be active until a background page is created.
538 ASSERT_TRUE(WaitForBackgroundMode(false));
539 ASSERT_TRUE(RunExtensionTest("app_background_page/basic_open")) << message_;
540 // Background mode should be active now because a background page was created.
541 ASSERT_TRUE(WaitForBackgroundMode(true));
542 ASSERT_TRUE(
543 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
544 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
545 // Now close the BackgroundContents.
546 ASSERT_TRUE(RunExtensionTest("app_background_page/basic_close")) << message_;
547 // Background mode should no longer be active.
548 ASSERT_TRUE(WaitForBackgroundMode(false));
549 ASSERT_FALSE(
550 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
551 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
554 IN_PROC_BROWSER_TEST_F(AppBackgroundPageApiTest, UnloadExtensionWhileHidden) {
555 host_resolver()->AddRule("a.com", "127.0.0.1");
556 ASSERT_TRUE(StartEmbeddedTestServer());
558 std::string app_manifest = base::StringPrintf(
560 " \"name\": \"App\","
561 " \"version\": \"0.1\","
562 " \"manifest_version\": 2,"
563 " \"app\": {"
564 " \"urls\": ["
565 " \"http://a.com/\""
566 " ],"
567 " \"launch\": {"
568 " \"web_url\": \"http://a.com:%d/\""
569 " }"
570 " },"
571 " \"permissions\": [\"background\"],"
572 " \"background\": {"
573 " \"page\": \"http://a.com:%d/test.html\""
574 " }"
575 "}",
576 embedded_test_server()->port(),
577 embedded_test_server()->port());
579 base::FilePath app_dir;
580 ASSERT_TRUE(CreateApp(app_manifest, &app_dir));
581 // Background mode should not be active now because no background app was
582 // loaded.
583 ASSERT_TRUE(LoadExtension(app_dir));
584 // Background mode be active now because a background page was created when
585 // the app was loaded.
586 ASSERT_TRUE(WaitForBackgroundMode(true));
588 const Extension* extension = GetSingleLoadedExtension();
589 ASSERT_TRUE(
590 BackgroundContentsServiceFactory::GetForProfile(browser()->profile())->
591 GetAppBackgroundContents(ASCIIToUTF16(extension->id())));
593 // Close all browsers - app should continue running.
594 set_exit_when_last_browser_closes(false);
595 CloseBrowser(browser());
597 // Post a task to unload the extension - this should cause Chrome to exit
598 // cleanly (not crash).
599 UnloadExtensionViaTask(extension->id());
600 content::RunAllPendingInMessageLoop();
601 ASSERT_TRUE(WaitForBackgroundMode(false));
604 // Verify active NaCl embeds cause many keepalive impulses to be sent.
605 // Disabled on Windows due to flakiness: http://crbug.com/346278
606 #if defined(OS_WIN)
607 #define MAYBE_BackgroundKeepaliveActive DISABLED_BackgroundKeepaliveActive
608 #else
609 #define MAYBE_BackgroundKeepaliveActive BackgroundKeepaliveActive
610 #endif
611 IN_PROC_BROWSER_TEST_F(AppBackgroundPageNaClTest,
612 MAYBE_BackgroundKeepaliveActive) {
613 #if !defined(DISABLE_NACL)
614 ExtensionTestMessageListener nacl_modules_loaded("nacl_modules_loaded", true);
615 LaunchTestingApp();
616 extensions::ProcessManager* manager =
617 extensions::ExtensionSystem::Get(browser()->profile())->process_manager();
618 ImpulseCallbackCounter active_impulse_counter(manager, extension()->id());
619 EXPECT_TRUE(nacl_modules_loaded.WaitUntilSatisfied());
621 // Target .5 seconds: .5 seconds / 50ms throttle * 2 embeds == 20 impulses.
622 manager->SetKeepaliveImpulseCallbackForTesting(
623 active_impulse_counter.SetGoalAndGetCallback(20));
624 active_impulse_counter.Wait();
625 #endif
628 // Verify that nacl modules that go idle will not send keepalive impulses.
629 // Disabled on windows due to Win XP failures:
630 // DesktopWindowTreeHostWin::HandleCreate not implemented. crbug.com/331954
631 #if defined(OS_WIN)
632 #define MAYBE_BackgroundKeepaliveIdle DISABLED_BackgroundKeepaliveIdle
633 #else
634 // ASAN errors appearing: https://crbug.com/332440
635 #define MAYBE_BackgroundKeepaliveIdle DISABLED_BackgroundKeepaliveIdle
636 #endif
637 IN_PROC_BROWSER_TEST_F(AppBackgroundPageNaClTest,
638 MAYBE_BackgroundKeepaliveIdle) {
639 #if !defined(DISABLE_NACL)
640 ExtensionTestMessageListener nacl_modules_loaded("nacl_modules_loaded", true);
641 LaunchTestingApp();
642 extensions::ProcessManager* manager =
643 extensions::ExtensionSystem::Get(browser()->profile())->process_manager();
644 ImpulseCallbackCounter idle_impulse_counter(manager, extension()->id());
645 EXPECT_TRUE(nacl_modules_loaded.WaitUntilSatisfied());
647 manager->SetKeepaliveImpulseDecrementCallbackForTesting(
648 idle_impulse_counter.SetGoalAndGetCallback(1));
649 nacl_modules_loaded.Reply("be idle");
650 idle_impulse_counter.Wait();
651 #endif