Skip to content

Commit

Permalink
Chrome Cleaner UI: Reporter no longer uses mojo.
Browse files Browse the repository at this point in the history
The reporter will no longer use mojo to communicate with Chrome.
That will instead be the responsibility of the Chrome Cleaner process.

BUG=690020

Review-Url: https://codereview.chromium.org/2890023005
Cr-Commit-Position: refs/heads/master@{#474778}
  • Loading branch information
alito authored and Commit bot committed May 25, 2017
1 parent 66e4a1e commit bb6caf2
Show file tree
Hide file tree
Showing 16 changed files with 1,272 additions and 594 deletions.
2 changes: 2 additions & 0 deletions chrome/browser/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -1169,6 +1169,8 @@ split_static_library("browser") {
"safe_browsing/chrome_cleaner/chrome_cleaner_controller_win.h",
"safe_browsing/chrome_cleaner/chrome_cleaner_fetcher_win.cc",
"safe_browsing/chrome_cleaner/chrome_cleaner_fetcher_win.h",
"safe_browsing/chrome_cleaner/chrome_cleaner_runner_win.cc",
"safe_browsing/chrome_cleaner/chrome_cleaner_runner_win.h",
"safe_browsing/chrome_cleaner/reporter_runner_win.cc",
"safe_browsing/chrome_cleaner/reporter_runner_win.h",
"safe_browsing/chrome_cleaner/srt_chrome_prompt_impl.cc",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,243 @@
// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/safe_browsing/chrome_cleaner/chrome_cleaner_runner_win.h"

#include <utility>

#include "base/base_paths.h"
#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/feature_list.h"
#include "base/location.h"
#include "base/memory/ptr_util.h"
#include "base/path_service.h"
#include "base/strings/string_number_conversions.h"
#include "base/task_scheduler/post_task.h"
#include "chrome/browser/safe_browsing/chrome_cleaner/srt_client_info_win.h"
#include "chrome/browser/safe_browsing/chrome_cleaner/srt_field_trial_win.h"
#include "chrome/installer/util/install_util.h"
#include "components/chrome_cleaner/public/constants/constants.h"
#include "components/chrome_cleaner/public/interfaces/chrome_prompt.mojom.h"
#include "components/version_info/version_info.h"
#include "content/public/browser/browser_thread.h"
#include "mojo/edk/embedder/connection_params.h"
#include "mojo/edk/embedder/embedder.h"
#include "mojo/edk/embedder/outgoing_broker_client_invitation.h"
#include "mojo/edk/embedder/platform_channel_pair.h"
#include "mojo/edk/embedder/transport_protocol.h"
#include "mojo/public/cpp/system/message_pipe.h"

using chrome_cleaner::mojom::ChromePrompt;
using chrome_cleaner::mojom::ChromePromptRequest;
using content::BrowserThread;

namespace safe_browsing {

namespace {

// Global delegate used to override the launching of the Cleaner process during
// tests.
ChromeCleanerRunnerTestDelegate* g_test_delegate = nullptr;

void ReleaseChromePromptImpl(
std::unique_ptr<ChromePromptImpl> chrome_prompt_impl) {
DCHECK_CURRENTLY_ON(BrowserThread::IO);
DCHECK(chrome_prompt_impl);
chrome_prompt_impl.reset();
}

} // namespace

// static
void ChromeCleanerRunner::RunChromeCleanerAndReplyWithExitCode(
const base::FilePath& cleaner_executable_path,
const SwReporterInvocation& reporter_invocation,
ChromeMetricsStatus metrics_status,
CleanerLogsStatus cleaner_logs_status,
ChromePromptImpl::OnPromptUser on_prompt_user,
base::OnceClosure on_connection_closed,
ChromeCleanerRunner::ProcessDoneCallback on_process_done,
scoped_refptr<base::SequencedTaskRunner> task_runner) {
auto cleaner_runner = make_scoped_refptr(new ChromeCleanerRunner(
cleaner_executable_path, reporter_invocation, metrics_status,
cleaner_logs_status, std::move(on_prompt_user),
std::move(on_connection_closed), std::move(on_process_done),
std::move(task_runner)));
auto launch_and_wait = base::BindOnce(
&ChromeCleanerRunner::LaunchAndWaitForExitOnBackgroundThread,
cleaner_runner);
auto process_done =
base::BindOnce(&ChromeCleanerRunner::OnProcessDone, cleaner_runner);
base::PostTaskWithTraitsAndReplyWithResult(
FROM_HERE,
// LaunchAndWaitForExitOnBackgroundThread creates (MayBlock()) and joins
// (WithBaseSyncPrimitives()) a process.
{base::MayBlock(), base::WithBaseSyncPrimitives(),
base::TaskPriority::BACKGROUND,
base::TaskShutdownBehavior::CONTINUE_ON_SHUTDOWN},
std::move(launch_and_wait), std::move(process_done));
}

ChromeCleanerRunner::ChromeCleanerRunner(
const base::FilePath& cleaner_executable_path,
const SwReporterInvocation& reporter_invocation,
ChromeMetricsStatus metrics_status,
CleanerLogsStatus cleaner_logs_status,
ChromePromptImpl::OnPromptUser on_prompt_user,
base::OnceClosure on_connection_closed,
ProcessDoneCallback on_process_done,
scoped_refptr<base::SequencedTaskRunner> task_runner)
: task_runner_(std::move(task_runner)),
cleaner_command_line_(cleaner_executable_path),
on_prompt_user_(std::move(on_prompt_user)),
on_connection_closed_(std::move(on_connection_closed)),
on_process_done_(std::move(on_process_done)) {
DCHECK(base::FeatureList::IsEnabled(kInBrowserCleanerUIFeature));
DCHECK(on_prompt_user_);
DCHECK(on_connection_closed_);
DCHECK(on_process_done_);
DCHECK(!cleaner_executable_path.empty());

// Add the non-IPC switches that should be passed to the Cleaner process.

// Add switches that pass information about this Chrome installation.
cleaner_command_line_.AppendSwitchASCII(chrome_cleaner::kChromeVersionSwitch,
version_info::GetVersionNumber());
cleaner_command_line_.AppendSwitchASCII(chrome_cleaner::kChromeChannelSwitch,
base::IntToString(ChannelAsInt()));
base::FilePath chrome_exe_path;
PathService::Get(base::FILE_EXE, &chrome_exe_path);
cleaner_command_line_.AppendSwitchPath(chrome_cleaner::kChromeExePathSwitch,
chrome_exe_path);
if (!InstallUtil::IsPerUserInstall())
cleaner_command_line_.AppendSwitch(
chrome_cleaner::kChromeSystemInstallSwitch);

// Start the cleaner process in scanning mode.
cleaner_command_line_.AppendSwitchASCII(
chrome_cleaner::kExecutionModeSwitch,
base::IntToString(
static_cast<int>(chrome_cleaner::ExecutionMode::kScanning)));

// If set, forward the engine flag from the reporter. Otherwise, set the
// engine flag explicitly to 1.
const std::string& reporter_engine =
reporter_invocation.command_line.GetSwitchValueASCII(
chrome_cleaner::kEngineSwitch);
cleaner_command_line_.AppendSwitchASCII(
chrome_cleaner::kEngineSwitch,
reporter_engine.empty() ? "1" : reporter_engine);

// If metrics is enabled, we can enable crash reporting in the Chrome Cleaner
// process.
if (metrics_status == ChromeMetricsStatus::kEnabled) {
cleaner_command_line_.AppendSwitch(chrome_cleaner::kUmaUserSwitch);
cleaner_command_line_.AppendSwitch(
chrome_cleaner::kEnableCrashReportingSwitch);
}

// Enable logs upload for users who have opted into safe browsing extended
// reporting v2.
if (cleaner_logs_status == CleanerLogsStatus::kUploadEnabled)
cleaner_command_line_.AppendSwitch(
chrome_cleaner::kEnableCleanerLoggingSwitch);
}

ChromeCleanerRunner::LaunchStatus
ChromeCleanerRunner::LaunchAndWaitForExitOnBackgroundThread() {
mojo::edk::OutgoingBrokerClientInvitation invitation;
std::string mojo_pipe_token = mojo::edk::GenerateRandomToken();
mojo::ScopedMessagePipeHandle mojo_pipe =
invitation.AttachMessagePipe(mojo_pipe_token);
cleaner_command_line_.AppendSwitchASCII(
chrome_cleaner::kChromeMojoPipeTokenSwitch, mojo_pipe_token);

mojo::edk::PlatformChannelPair channel;
base::HandlesToInheritVector handles_to_inherit;
channel.PrepareToPassClientHandleToChildProcess(&cleaner_command_line_,
&handles_to_inherit);
base::LaunchOptions launch_options;
launch_options.handles_to_inherit = &handles_to_inherit;

base::Process cleaner_process =
g_test_delegate
? g_test_delegate->LaunchTestProcess(cleaner_command_line_,
launch_options)
: base::LaunchProcess(cleaner_command_line_, launch_options);

constexpr int kBadProcessExitCode = std::numeric_limits<int>::max();
if (!cleaner_process.IsValid())
return {false, kBadProcessExitCode};

// ChromePromptImpl tasks will need to run on the IO thread. There is no
// need to synchronize its creation, since the client end will wait for this
// initialization to be done before sending requests.
BrowserThread::GetTaskRunnerForThread(BrowserThread::IO)
->PostTask(FROM_HERE,
base::BindOnce(&ChromeCleanerRunner::CreateChromePromptImpl,
base::RetainedRef(this),
chrome_cleaner::mojom::ChromePromptRequest(
std::move(mojo_pipe))));

invitation.Send(
cleaner_process.Handle(),
mojo::edk::ConnectionParams(mojo::edk::TransportProtocol::kLegacy,
channel.PassServerHandle()));

int exit_code = kBadProcessExitCode;
if (cleaner_process.WaitForExit(&exit_code))
return {true, exit_code};
return {false, kBadProcessExitCode};
}

ChromeCleanerRunner::~ChromeCleanerRunner() {
if (chrome_prompt_impl_) {
BrowserThread::GetTaskRunnerForThread(BrowserThread::IO)
->PostTask(FROM_HERE, base::Bind(&ReleaseChromePromptImpl,
base::Passed(&chrome_prompt_impl_)));
}
}

void ChromeCleanerRunner::CreateChromePromptImpl(
ChromePromptRequest chrome_prompt_request) {
DCHECK_CURRENTLY_ON(BrowserThread::IO);
DCHECK(!chrome_prompt_impl_);

chrome_prompt_impl_ = base::MakeUnique<ChromePromptImpl>(
std::move(chrome_prompt_request),
base::Bind(&ChromeCleanerRunner::OnConnectionClosed,
base::RetainedRef(this)),
base::Bind(&ChromeCleanerRunner::OnPromptUser, base::RetainedRef(this)));
}

void ChromeCleanerRunner::OnPromptUser(
std::unique_ptr<std::set<base::FilePath>> files_to_delete,
ChromePrompt::PromptUserCallback prompt_user_callback) {
if (on_prompt_user_) {
task_runner_->PostTask(FROM_HERE,
base::BindOnce(std::move(on_prompt_user_),
base::Passed(&files_to_delete),
base::Passed(&prompt_user_callback)));
}
}

void ChromeCleanerRunner::OnConnectionClosed() {
if (on_connection_closed_)
task_runner_->PostTask(FROM_HERE, std::move(on_connection_closed_));
}

void ChromeCleanerRunner::OnProcessDone(LaunchStatus launch_status) {
if (on_process_done_) {
task_runner_->PostTask(
FROM_HERE, base::BindOnce(std::move(on_process_done_), launch_status));
}
}

void SetChromeCleanerRunnerTestDelegateForTesting(
ChromeCleanerRunnerTestDelegate* test_delegate) {
g_test_delegate = test_delegate;
}

} // namespace safe_browsing
Loading

0 comments on commit bb6caf2

Please sign in to comment.