Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(309)

Unified Diff: components/nacl/loader/sfi_listener_delegate.cc

Issue 439713002: Refactoring: Split NaClListener into two delegated classes. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: components/nacl/loader/sfi_listener_delegate.cc
diff --git a/components/nacl/loader/nacl_listener.cc b/components/nacl/loader/sfi_listener_delegate.cc
similarity index 54%
copy from components/nacl/loader/nacl_listener.cc
copy to components/nacl/loader/sfi_listener_delegate.cc
index 433d9417d2abd291e532156de13b676ba6c57a4c..33ce605f976c6001c06128e6970077643048bf15 100644
--- a/components/nacl/loader/nacl_listener.cc
+++ b/components/nacl/loader/sfi_listener_delegate.cc
@@ -1,54 +1,51 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
+// Copyright 2014 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 "components/nacl/loader/nacl_listener.h"
+#include "components/nacl/loader/sfi_listener_delegate.h"
-#include <errno.h>
-#include <fcntl.h>
-#include <stdlib.h>
-
-#if defined(OS_POSIX)
-#include <unistd.h>
-#endif
-
-#include "base/command_line.h"
#include "base/logging.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/message_loop/message_loop.h"
-#include "base/rand_util.h"
+#include "base/memory/ref_counted.h"
+#include "base/message_loop/message_loop_proxy.h"
#include "components/nacl/common/nacl_messages.h"
+#include "components/nacl/common/nacl_types.h"
#include "components/nacl/loader/nacl_ipc_adapter.h"
#include "components/nacl/loader/nacl_validation_db.h"
#include "components/nacl/loader/nacl_validation_query.h"
+#include "ipc/ipc_channel.h"
#include "ipc/ipc_channel_handle.h"
-#include "ipc/ipc_switches.h"
-#include "ipc/ipc_sync_channel.h"
-#include "ipc/ipc_sync_message_filter.h"
+#include "ipc/ipc_sender.h"
#include "native_client/src/public/chrome_main.h"
#include "native_client/src/public/nacl_app.h"
#include "native_client/src/public/nacl_file_info.h"
#include "native_client/src/trusted/service_runtime/include/sys/fcntl.h"
+#if defined(OS_WIN)
+#include <fcntl.h>
+#include <io.h>
+#include "content/public/common/sandbox_init.h"
+#endif // OS_WIN
+
#if defined(OS_POSIX)
+#include <unistd.h>
#include "base/file_descriptor_posix.h"
-#endif
+#include "base/rand_util.h"
+#endif // OS_POSIX
+
+#if defined(OS_MACOSX)
+#include <errno.h>
+#include <sys/types.h>
+#include "base/atomicops.h"
+#endif // OS_MACOSX
#if defined(OS_LINUX)
-#include "components/nacl/loader/nonsfi/irt_random.h"
-#include "components/nacl/loader/nonsfi/nonsfi_main.h"
#include "content/public/common/child_process_sandbox_support_linux.h"
-#include "ppapi/nacl_irt/plugin_startup.h"
-#endif
+#endif // OS_LINUX
-#if defined(OS_WIN)
-#include <fcntl.h>
-#include <io.h>
-
-#include "content/public/common/sandbox_init.h"
-#endif
+namespace nacl {
namespace {
+
#if defined(OS_MACOSX)
// On Mac OS X, shm_open() works in the sandbox but does not give us
@@ -89,7 +86,7 @@ int CreateMemoryObject(size_t size, int executable) {
#elif defined(OS_WIN)
-NaClListener* g_listener;
+IPC::Sender* g_sender;
// We wrap the function to convert the bool return value to an int.
int BrokerDuplicateHandle(NaClHandle source_handle,
@@ -105,14 +102,14 @@ int BrokerDuplicateHandle(NaClHandle source_handle,
int AttachDebugExceptionHandler(const void* info, size_t info_size) {
std::string info_string(reinterpret_cast<const char*>(info), info_size);
bool result = false;
- if (!g_listener->Send(new NaClProcessMsg_AttachDebugExceptionHandler(
+ if (!g_sender->Send(new NaClProcessMsg_AttachDebugExceptionHandler(
info_string, &result)))
return false;
return result;
}
void DebugStubPortSelectedHandler(uint16_t port) {
- g_listener->Send(new NaClProcessHostMsg_DebugStubPortSelected(port));
+ g_sender->Send(new NaClProcessHostMsg_DebugStubPortSelected(port));
}
#endif
@@ -139,12 +136,10 @@ void SetUpIPCAdapter(IPC::ChannelHandle* handle,
NaClAppSetDesc(nap, nacl_fd, ipc_adapter->MakeNaClDesc());
}
-} // namespace
-
class BrowserValidationDBProxy : public NaClValidationDB {
public:
- explicit BrowserValidationDBProxy(NaClListener* listener)
- : listener_(listener) {
+ explicit BrowserValidationDBProxy(IPC::Sender* sender)
+ : sender_(sender) {
}
virtual bool QueryKnownToValidate(const std::string& signature) OVERRIDE {
@@ -152,8 +147,8 @@ class BrowserValidationDBProxy : public NaClValidationDB {
// value we're safe. For example if the message is (for some reason)
// dispatched as an async message the return parameter will not be written.
bool result = false;
- if (!listener_->Send(new NaClProcessMsg_QueryKnownToValidate(signature,
- &result))) {
+ if (!sender_->Send(new NaClProcessMsg_QueryKnownToValidate(signature,
+ &result))) {
LOG(ERROR) << "Failed to query NaCl validation cache.";
result = false;
}
@@ -162,7 +157,7 @@ class BrowserValidationDBProxy : public NaClValidationDB {
virtual void SetKnownToValidate(const std::string& signature) OVERRIDE {
// Caching is optional: NaCl will still work correctly if the IPC fails.
- if (!listener_->Send(new NaClProcessMsg_SetKnownToValidate(signature))) {
+ if (!sender_->Send(new NaClProcessMsg_SetKnownToValidate(signature))) {
LOG(ERROR) << "Failed to update NaCl validation cache.";
}
}
@@ -176,10 +171,10 @@ class BrowserValidationDBProxy : public NaClValidationDB {
}
IPC::PlatformFileForTransit ipc_fd = IPC::InvalidPlatformFileForTransit();
base::FilePath ipc_path;
- if (!listener_->Send(new NaClProcessMsg_ResolveFileToken(file_token->lo,
- file_token->hi,
- &ipc_fd,
- &ipc_path))) {
+ if (!sender_->Send(new NaClProcessMsg_ResolveFileToken(file_token->lo,
+ file_token->hi,
+ &ipc_fd,
+ &ipc_path))) {
return false;
}
if (ipc_fd == IPC::InvalidPlatformFileForTransit()) {
@@ -200,75 +195,41 @@ class BrowserValidationDBProxy : public NaClValidationDB {
}
private:
- // The listener never dies, otherwise this might be a dangling reference.
- NaClListener* listener_;
+ // Do not own the sender. Practically, this is pointing to NaClListener
+ // instance, which will be alive while the plugin is running.
+ IPC::Sender* sender_;
+
+ DISALLOW_COPY_AND_ASSIGN(BrowserValidationDBProxy);
};
+} // namespace
+
-NaClListener::NaClListener() : shutdown_event_(true, false),
- io_thread_("NaCl_IOThread"),
- uses_nonsfi_mode_(false),
+SfiListenerDelegate::SfiListenerDelegate()
+#if defined(OS_POSIX)
+ :
+#endif // OS_POSIX
#if defined(OS_LINUX)
- prereserved_sandbox_size_(0),
-#endif
+ prereserved_sandbox_size_(0),
+#endif // OS_LINUX
#if defined(OS_POSIX)
- number_of_cores_(-1), // unknown/error
-#endif
- main_loop_(NULL) {
- io_thread_.StartWithOptions(
- base::Thread::Options(base::MessageLoop::TYPE_IO, 0));
-#if defined(OS_WIN)
- DCHECK(g_listener == NULL);
- g_listener = this;
-#endif
+ number_of_cores_(-1)
+#endif // OS_POSIX
+{
}
-NaClListener::~NaClListener() {
- NOTREACHED();
- shutdown_event_.Signal();
-#if defined(OS_WIN)
- g_listener = NULL;
-#endif
+SfiListenerDelegate::~SfiListenerDelegate() {
}
-bool NaClListener::Send(IPC::Message* msg) {
- DCHECK(main_loop_ != NULL);
- if (base::MessageLoop::current() == main_loop_) {
- // This thread owns the channel.
- return channel_->Send(msg);
- } else {
- // This thread does not own the channel.
- return filter_->Send(msg);
- }
-}
-
-void NaClListener::Listen() {
- std::string channel_name =
- CommandLine::ForCurrentProcess()->GetSwitchValueASCII(
- switches::kProcessChannelID);
- channel_ = IPC::SyncChannel::Create(
- this, io_thread_.message_loop_proxy().get(), &shutdown_event_);
- filter_ = new IPC::SyncMessageFilter(&shutdown_event_);
- channel_->AddFilter(filter_.get());
- channel_->Init(channel_name, IPC::Channel::MODE_CLIENT, true);
- main_loop_ = base::MessageLoop::current();
- main_loop_->Run();
-}
-
-bool NaClListener::OnMessageReceived(const IPC::Message& msg) {
- bool handled = true;
- IPC_BEGIN_MESSAGE_MAP(NaClListener, msg)
- IPC_MESSAGE_HANDLER(NaClProcessMsg_Start, OnStart)
- IPC_MESSAGE_UNHANDLED(handled = false)
- IPC_END_MESSAGE_MAP()
- return handled;
-}
-
-void NaClListener::OnStart(const nacl::NaClStartParams& params) {
- if (uses_nonsfi_mode_) {
- StartNonSfi(params);
- return;
- }
+void SfiListenerDelegate::Start(
+ const nacl::NaClStartParams& params,
+ scoped_refptr<base::MessageLoopProxy> io_message_loop_proxy,
+ IPC::ChannelHandle trusted_channel_handle,
+ IPC::Sender* sender) {
+#if defined(OS_WIN)
+ DCHECK(g_sender == NULL);
+ g_sender = sender;
+#endif
#if defined(OS_LINUX) || defined(OS_MACOSX)
int urandom_fd = dup(base::GetUrandomFD());
@@ -287,27 +248,25 @@ void NaClListener::OnStart(const nacl::NaClStartParams& params) {
return;
}
- IPC::ChannelHandle browser_handle;
+ IPC::ChannelHandle ppapi_browser_handle;
IPC::ChannelHandle ppapi_renderer_handle;
if (params.enable_ipc_proxy) {
- browser_handle = IPC::Channel::GenerateVerifiedChannelID("nacl");
+ ppapi_browser_handle = IPC::Channel::GenerateVerifiedChannelID("nacl");
ppapi_renderer_handle = IPC::Channel::GenerateVerifiedChannelID("nacl");
// Create the PPAPI IPC channels between the NaCl IRT and the host
// (browser/renderer) processes. The IRT uses these channels to
// communicate with the host and to initialize the IPC dispatchers.
- SetUpIPCAdapter(&browser_handle, io_thread_.message_loop_proxy(),
+ SetUpIPCAdapter(&ppapi_browser_handle, io_message_loop_proxy,
nap, NACL_CHROME_DESC_BASE);
- SetUpIPCAdapter(&ppapi_renderer_handle, io_thread_.message_loop_proxy(),
+ SetUpIPCAdapter(&ppapi_renderer_handle, io_message_loop_proxy,
nap, NACL_CHROME_DESC_BASE + 1);
}
- IPC::ChannelHandle trusted_renderer_handle = CreateTrustedListener(
- io_thread_.message_loop_proxy(), &shutdown_event_);
- if (!Send(new NaClProcessHostMsg_PpapiChannelsCreated(
- browser_handle, ppapi_renderer_handle,
- trusted_renderer_handle, IPC::ChannelHandle())))
+ if (!sender->Send(new NaClProcessHostMsg_PpapiChannelsCreated(
+ ppapi_browser_handle, ppapi_renderer_handle,
+ trusted_channel_handle, IPC::ChannelHandle())))
LOG(ERROR) << "Failed to send IPC channel handle to NaClProcessHost.";
std::vector<nacl::FileDescriptor> handles = params.handles;
@@ -352,7 +311,7 @@ void NaClListener::OnStart(const nacl::NaClStartParams& params) {
CHECK_EQ(params.validation_cache_key.length(), (size_t) 64);
// The cache structure is not freed and exists until the NaCl process exits.
args->validation_cache = CreateValidationCache(
- new BrowserValidationDBProxy(this), params.validation_cache_key,
+ new BrowserValidationDBProxy(sender), params.validation_cache_key,
params.version);
}
@@ -409,105 +368,4 @@ void NaClListener::OnStart(const nacl::NaClStartParams& params) {
NaClChromeMainStartApp(nap, args);
}
-void NaClListener::StartNonSfi(const nacl::NaClStartParams& params) {
-#if !defined(OS_LINUX)
- NOTREACHED() << "Non-SFI NaCl is only supported on Linux";
-#else
- // Random number source initialization.
- nacl::nonsfi::SetUrandomFd(base::GetUrandomFD());
-
- IPC::ChannelHandle browser_handle;
- IPC::ChannelHandle ppapi_renderer_handle;
- IPC::ChannelHandle manifest_service_handle;
-
- if (params.enable_ipc_proxy) {
- browser_handle = IPC::Channel::GenerateVerifiedChannelID("nacl");
- ppapi_renderer_handle = IPC::Channel::GenerateVerifiedChannelID("nacl");
- manifest_service_handle =
- IPC::Channel::GenerateVerifiedChannelID("nacl");
-
- // In non-SFI mode, we neither intercept nor rewrite the message using
- // NaClIPCAdapter, and the channels are connected between the plugin and
- // the hosts directly. So, the IPC::Channel instances will be created in
- // the plugin side, because the IPC::Listener needs to live on the
- // plugin's main thread. However, on initialization (i.e. before loading
- // the plugin binary), the FD needs to be passed to the hosts. So, here
- // we create raw FD pairs, and pass the client side FDs to the hosts,
- // and the server side FDs to the plugin.
- int browser_server_ppapi_fd;
- int browser_client_ppapi_fd;
- int renderer_server_ppapi_fd;
- int renderer_client_ppapi_fd;
- int manifest_service_server_fd;
- int manifest_service_client_fd;
- if (!IPC::SocketPair(
- &browser_server_ppapi_fd, &browser_client_ppapi_fd) ||
- !IPC::SocketPair(
- &renderer_server_ppapi_fd, &renderer_client_ppapi_fd) ||
- !IPC::SocketPair(
- &manifest_service_server_fd, &manifest_service_client_fd)) {
- LOG(ERROR) << "Failed to create sockets for IPC.";
- return;
- }
-
- // Set the plugin IPC channel FDs.
- ppapi::SetIPCFileDescriptors(browser_server_ppapi_fd,
- renderer_server_ppapi_fd,
- manifest_service_server_fd);
- ppapi::StartUpPlugin();
-
- // Send back to the client side IPC channel FD to the host.
- browser_handle.socket =
- base::FileDescriptor(browser_client_ppapi_fd, true);
- ppapi_renderer_handle.socket =
- base::FileDescriptor(renderer_client_ppapi_fd, true);
- manifest_service_handle.socket =
- base::FileDescriptor(manifest_service_client_fd, true);
- }
-
- // TODO(teravest): Do we plan on using this renderer handle for nexe loading
- // for non-SFI? Right now, passing an empty channel handle instead causes
- // hangs, so we'll keep it.
- IPC::ChannelHandle trusted_renderer_handle = CreateTrustedListener(
- io_thread_.message_loop_proxy(), &shutdown_event_);
- if (!Send(new NaClProcessHostMsg_PpapiChannelsCreated(
- browser_handle, ppapi_renderer_handle,
- trusted_renderer_handle, manifest_service_handle)))
- LOG(ERROR) << "Failed to send IPC channel handle to NaClProcessHost.";
-
- // Ensure that the validation cache key (used as an extra input to the
- // validation cache's hashing) isn't exposed accidentally.
- CHECK(!params.validation_cache_enabled);
- CHECK(params.validation_cache_key.size() == 0);
- CHECK(params.version.size() == 0);
- // Ensure that a debug stub FD isn't passed through accidentally.
- CHECK(!params.enable_debug_stub);
- CHECK(params.debug_stub_server_bound_socket.fd == -1);
-
- CHECK(!params.uses_irt);
- CHECK(params.handles.empty());
-
- CHECK(params.nexe_file != IPC::InvalidPlatformFileForTransit());
- CHECK(params.nexe_token_lo == 0);
- CHECK(params.nexe_token_hi == 0);
- nacl::nonsfi::MainStart(
- IPC::PlatformFileForTransitToPlatformFile(params.nexe_file));
-#endif // defined(OS_LINUX)
-}
-
-IPC::ChannelHandle NaClListener::CreateTrustedListener(
- base::MessageLoopProxy* message_loop_proxy,
- base::WaitableEvent* shutdown_event) {
- // The argument passed to GenerateVerifiedChannelID() here MUST be "nacl".
- // Using an alternate channel name prevents the pipe from being created on
- // Windows when the sandbox is enabled.
- IPC::ChannelHandle trusted_renderer_handle =
- IPC::Channel::GenerateVerifiedChannelID("nacl");
- trusted_listener_ = new NaClTrustedListener(
- trusted_renderer_handle, io_thread_.message_loop_proxy().get());
-#if defined(OS_POSIX)
- trusted_renderer_handle.socket = base::FileDescriptor(
- trusted_listener_->TakeClientFileDescriptor(), true);
-#endif
- return trusted_renderer_handle;
-}
+} // namespace nacl
« components/nacl/loader/listener_delegate.h ('K') | « components/nacl/loader/sfi_listener_delegate.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698