#include "content/public/browser/browser_child_process_observer.h"
#include "base/functional/bind.h"
#include "base/run_loop.h"
#include "build/build_config.h"
#include "content/browser/browser_child_process_host_impl.h"
#include "content/browser/child_process_host_impl.h"
#include "content/browser/utility_process_host.h"
#include "content/public/browser/browser_child_process_host.h"
#include "content/public/browser/browser_child_process_host_delegate.h"
#include "content/public/browser/child_process_data.h"
#include "content/public/common/content_switches.h"
#include "content/public/common/process_type.h"
#include "content/public/common/sandboxed_process_launcher_delegate.h"
#include "content/public/test/browser_test.h"
#include "content/public/test/content_browser_test.h"
#include "content/public/test/test_service.mojom.h"
#include "sandbox/policy/sandbox_type.h"
#include "testing/gmock/include/gmock/gmock.h"
namespace content {
namespace {
enum class Notification { … };
std::ostream& operator<<(std::ostream& os, Notification notification) { … }
bool IsHostAlive(int child_id) { … }
}
class BrowserChildProcessNotificationObserver
: public BrowserChildProcessObserver { … };
class WaitForNotificationObserver { … };
class TestSandboxedProcessLauncherDelegate
: public SandboxedProcessLauncherDelegate { … };
class TestProcessHost : public BrowserChildProcessHostDelegate { … };
class TestBrowserChildProcessObserver { … };
class BrowserChildProcessObserverBrowserTest : public ContentBrowserTest { … };
#if defined(ADDRESS_SANITIZER)
#define MAYBE_LaunchAndForceShutdown …
#else
#define MAYBE_LaunchAndForceShutdown …
#endif
IN_PROC_BROWSER_TEST_F(BrowserChildProcessObserverBrowserTest,
MAYBE_LaunchAndForceShutdown) { … }
IN_PROC_BROWSER_TEST_F(BrowserChildProcessObserverBrowserTest,
LaunchAndDelete) { … }
#if defined(ADDRESS_SANITIZER)
#define MAYBE_LaunchAndDisconnect …
#else
#define MAYBE_LaunchAndDisconnect …
#endif
IN_PROC_BROWSER_TEST_F(BrowserChildProcessObserverBrowserTest,
MAYBE_LaunchAndDisconnect) { … }
#if BUILDFLAG(IS_ANDROID)
#define MAYBE_LaunchAndCrash …
#else
#define MAYBE_LaunchAndCrash …
#endif
IN_PROC_BROWSER_TEST_F(BrowserChildProcessObserverBrowserTest,
MAYBE_LaunchAndCrash) { … }
#if !BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_MAC)
IN_PROC_BROWSER_TEST_F(BrowserChildProcessObserverBrowserTest, LaunchFailed) {
base::WeakPtr<TestProcessHost> host = TestProcessHost::Create();
int child_id = host->GetId();
#if BUILDFLAG(IS_WIN)
host->SetSandboxType(sandbox::mojom::Sandbox::kNoSandbox);
#endif
base::CommandLine::ForCurrentProcess()->AppendSwitchPath(
switches::kBrowserSubprocessPath,
base::FilePath(FILE_PATH_LITERAL("non_existent_path")));
TestBrowserChildProcessObserver observer(child_id);
{
WaitForNotificationObserver waiter(child_id, Notification::kLaunchFailed);
host->LaunchProcess();
waiter.Wait();
}
EXPECT_FALSE(host);
EXPECT_FALSE(IsHostAlive(child_id));
EXPECT_THAT(observer.notifications(),
testing::ElementsAreArray({Notification::kLaunchFailed}));
}
#endif
}