summaryrefslogtreecommitdiffstats
path: root/ipc/contentproc/plugin-container.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'ipc/contentproc/plugin-container.cpp')
-rw-r--r--ipc/contentproc/plugin-container.cpp201
1 files changed, 201 insertions, 0 deletions
diff --git a/ipc/contentproc/plugin-container.cpp b/ipc/contentproc/plugin-container.cpp
new file mode 100644
index 000000000..f293889b0
--- /dev/null
+++ b/ipc/contentproc/plugin-container.cpp
@@ -0,0 +1,201 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
+ * vim: sw=4 ts=4 et :
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#include "nsXPCOM.h"
+#include "nsXULAppAPI.h"
+#include "nsAutoPtr.h"
+
+#ifdef XP_WIN
+#include <windows.h>
+// we want a wmain entry point
+// but we don't want its DLL load protection, because we'll handle it here
+#define XRE_DONT_PROTECT_DLL_LOAD
+#include "nsWindowsWMain.cpp"
+#include "nsSetDllDirectory.h"
+#else
+// FIXME/cjones testing
+#include <unistd.h>
+#endif
+
+#include "GMPLoader.h"
+
+#if defined(XP_WIN) && defined(MOZ_SANDBOX)
+#include "mozilla/sandboxing/SandboxInitialization.h"
+#include "mozilla/sandboxing/sandboxLogging.h"
+#endif
+
+#if defined(XP_LINUX) && defined(MOZ_GMP_SANDBOX)
+#include "mozilla/Sandbox.h"
+#include "mozilla/SandboxInfo.h"
+#endif
+
+#ifdef MOZ_WIDGET_GONK
+# include <sys/time.h>
+# include <sys/resource.h>
+
+# include <binder/ProcessState.h>
+
+# ifdef LOGE_IF
+# undef LOGE_IF
+# endif
+
+# include <android/log.h>
+# define LOGE_IF(cond, ...) \
+ ( (CONDITION(cond)) \
+ ? ((void)__android_log_print(ANDROID_LOG_ERROR, \
+ "Gecko:MozillaRntimeMain", __VA_ARGS__)) \
+ : (void)0 )
+
+# ifdef MOZ_CONTENT_SANDBOX
+# include "mozilla/Sandbox.h"
+# endif
+
+#endif // MOZ_WIDGET_GONK
+
+#ifdef MOZ_WIDGET_GONK
+static void
+InitializeBinder(void *aDummy) {
+ // Change thread priority to 0 only during calling ProcessState::self().
+ // The priority is registered to binder driver and used for default Binder
+ // Thread's priority.
+ // To change the process's priority to small value need's root permission.
+ int curPrio = getpriority(PRIO_PROCESS, 0);
+ int err = setpriority(PRIO_PROCESS, 0, 0);
+ MOZ_ASSERT(!err);
+ LOGE_IF(err, "setpriority failed. Current process needs root permission.");
+ android::ProcessState::self()->startThreadPool();
+ setpriority(PRIO_PROCESS, 0, curPrio);
+}
+#endif
+
+#if defined(XP_WIN) && defined(MOZ_SANDBOX)
+class WinSandboxStarter : public mozilla::gmp::SandboxStarter {
+public:
+ virtual bool Start(const char *aLibPath) override {
+ if (IsSandboxedProcess()) {
+ mozilla::sandboxing::LowerSandbox();
+ }
+ return true;
+ }
+};
+#endif
+
+#if defined(XP_LINUX) && defined(MOZ_GMP_SANDBOX)
+class LinuxSandboxStarter : public mozilla::gmp::SandboxStarter {
+ LinuxSandboxStarter() { }
+public:
+ static SandboxStarter* Make() {
+ if (mozilla::SandboxInfo::Get().CanSandboxMedia()) {
+ return new LinuxSandboxStarter();
+ } else {
+ // Sandboxing isn't possible, but the parent has already
+ // checked that this plugin doesn't require it. (Bug 1074561)
+ return nullptr;
+ }
+ }
+ virtual bool Start(const char *aLibPath) override {
+ mozilla::SetMediaPluginSandbox(aLibPath);
+ return true;
+ }
+};
+#endif
+
+#if defined(XP_MACOSX) && defined(MOZ_GMP_SANDBOX)
+class MacSandboxStarter : public mozilla::gmp::SandboxStarter {
+public:
+ virtual bool Start(const char *aLibPath) override {
+ std::string err;
+ bool rv = mozilla::StartMacSandbox(mInfo, err);
+ if (!rv) {
+ fprintf(stderr, "sandbox_init() failed! Error \"%s\"\n", err.c_str());
+ }
+ return rv;
+ }
+ virtual void SetSandboxInfo(MacSandboxInfo* aSandboxInfo) override {
+ mInfo = *aSandboxInfo;
+ }
+private:
+ MacSandboxInfo mInfo;
+};
+#endif
+
+mozilla::gmp::SandboxStarter*
+MakeSandboxStarter()
+{
+#if defined(XP_WIN) && defined(MOZ_SANDBOX)
+ return new WinSandboxStarter();
+#elif defined(XP_LINUX) && defined(MOZ_GMP_SANDBOX)
+ return LinuxSandboxStarter::Make();
+#elif defined(XP_MACOSX) && defined(MOZ_GMP_SANDBOX)
+ return new MacSandboxStarter();
+#else
+ return nullptr;
+#endif
+}
+
+int
+content_process_main(int argc, char* argv[])
+{
+ // Check for the absolute minimum number of args we need to move
+ // forward here. We expect the last arg to be the child process type.
+ if (argc < 1) {
+ return 3;
+ }
+
+ XREChildData childData;
+
+#if defined(XP_WIN) && defined(MOZ_SANDBOX)
+ if (IsSandboxedProcess()) {
+ childData.sandboxTargetServices =
+ mozilla::sandboxing::GetInitializedTargetServices();
+ if (!childData.sandboxTargetServices) {
+ return 1;
+ }
+
+ childData.ProvideLogFunction = mozilla::sandboxing::ProvideLogFunction;
+ }
+#endif
+
+ XRE_SetProcessType(argv[--argc]);
+
+#if defined(XP_LINUX) && defined(MOZ_SANDBOX)
+ // This has to happen while we're still single-threaded, and on
+ // B2G that means before the Android Binder library is
+ // initialized.
+ mozilla::SandboxEarlyInit(XRE_GetProcessType());
+#endif
+
+#ifdef MOZ_WIDGET_GONK
+ // This creates a ThreadPool for binder ipc. A ThreadPool is necessary to
+ // receive binder calls, though not necessary to send binder calls.
+ // ProcessState::Self() also needs to be called once on the main thread to
+ // register the main thread with the binder driver.
+
+ InitializeBinder(nullptr);
+#endif
+
+#ifdef XP_WIN
+ // For plugins, this is done in PluginProcessChild::Init, as we need to
+ // avoid it for unsupported plugins. See PluginProcessChild::Init for
+ // the details.
+ if (XRE_GetProcessType() != GeckoProcessType_Plugin) {
+ mozilla::SanitizeEnvironmentVariables();
+ SetDllDirectoryW(L"");
+ }
+#endif
+#if !defined(MOZ_WIDGET_ANDROID) && !defined(MOZ_WIDGET_GONK) && defined(MOZ_PLUGIN_CONTAINER)
+ // On desktop, the GMPLoader lives in plugin-container, so that its
+ // code can be covered by an EME/GMP vendor's voucher.
+ nsAutoPtr<mozilla::gmp::SandboxStarter> starter(MakeSandboxStarter());
+ if (XRE_GetProcessType() == GeckoProcessType_GMPlugin) {
+ childData.gmpLoader = mozilla::gmp::CreateGMPLoader(starter);
+ }
+#endif
+ nsresult rv = XRE_InitChildProcess(argc, argv, &childData);
+ NS_ENSURE_SUCCESS(rv, 1);
+
+ return 0;
+}