Bug 1401786 - Move the Linux sandboxing parts of GeckoChildProcessHost into security/sandbox. r?gcp
MozReview-Commit-ID: JknJhF5umZc
--- a/ipc/glue/GeckoChildProcessHost.cpp
+++ b/ipc/glue/GeckoChildProcessHost.cpp
@@ -51,17 +51,17 @@
#if defined(MOZ_SANDBOX)
#include "mozilla/Preferences.h"
#include "mozilla/sandboxing/sandboxLogging.h"
#include "WinUtils.h"
#endif
#endif
#if defined(XP_LINUX) && defined(MOZ_SANDBOX)
-#include "mozilla/SandboxReporter.h"
+#include "mozilla/SandboxLaunch.h"
#endif
#include "nsTArray.h"
#include "nsClassHashtable.h"
#include "nsHashKeys.h"
#include "nsNativeCharsetUtils.h"
#include "nscore.h" // for NS_FREE_PERMANENT_DATA
@@ -225,16 +225,20 @@ void
GeckoChildProcessHost::PrepareLaunch()
{
#ifdef MOZ_CRASHREPORTER
if (CrashReporter::GetEnabled()) {
CrashReporter::OOPInit();
}
#endif
+#if defined(XP_LINUX) && defined(MOZ_SANDBOX)
+ SandboxLaunchPrepare(mProcessType, mLaunchOptions.get());
+#endif
+
#ifdef XP_WIN
if (mProcessType == GeckoProcessType_Plugin) {
InitWindowsGroupID();
}
#if defined(MOZ_CONTENT_SANDBOX)
// We need to get the pref here as the process is launched off main thread.
if (mProcessType == GeckoProcessType_Content) {
@@ -703,37 +707,16 @@ GeckoChildProcessHost::PerformAsyncLaunc
mLaunchOptions->environ["DYLD_INSERT_LIBRARIES"] = interpose.get();
# endif // defined(OS_LINUX) || defined(OS_BSD)
}
# endif // defined(OS_LINUX) || defined(OS_MACOSX) || defined(OS_BSD) || defined(OS_SOLARIS)
FilePath exePath;
BinaryPathType pathType = GetPathToBinary(exePath, mProcessType);
-# if defined(XP_LINUX) && defined(MOZ_SANDBOX)
- // Preload libmozsandbox.so so that sandbox-related interpositions
- // can be defined there instead of in the executable.
- // (This could be made conditional on intent to use sandboxing, but
- // it's harmless for non-sandboxed processes.)
- {
- nsAutoCString preload;
- // Prepend this, because people can and do preload libpthread.
- // (See bug 1222500.)
- preload.AssignLiteral("libmozsandbox.so");
- if (const char* oldPreload = PR_GetEnv("LD_PRELOAD")) {
- // Doesn't matter if oldPreload is ""; extra separators are ignored.
- preload.Append(' ');
- preload.Append(oldPreload);
- }
- // Explicitly construct the std::string to make it clear that this
- // isn't retaining a pointer to the nsCString's buffer.
- mLaunchOptions->environ["LD_PRELOAD"] = std::string(preload.get());
- }
-# endif // defined(XP_LINUX) && defined(MOZ_SANDBOX)
-
// remap the IPC socket fd to a well-known int, as the OS does for
// STDOUT_FILENO, for example
int srcChannelFd, dstChannelFd;
channel().GetClientFileDescriptorMapping(&srcChannelFd, &dstChannelFd);
mLaunchOptions->fds_to_remap
.push_back(std::pair<int,int>(srcChannelFd, dstChannelFd));
// no need for kProcessChannelID, the child process inherits the
@@ -800,25 +783,16 @@ GeckoChildProcessHost::PerformAsyncLaunc
// "false" == crash reporting disabled
childArgv.push_back("false");
}
# elif defined(MOZ_WIDGET_COCOA) // defined(OS_LINUX) || defined(OS_BSD) || defined(OS_SOLARIS)
childArgv.push_back(CrashReporter::GetChildNotificationPipe());
# endif // defined(OS_LINUX) || defined(OS_BSD) || defined(OS_SOLARIS)
# endif // defined(MOZ_CRASHREPORTER)
-# if defined(XP_LINUX) && defined(MOZ_SANDBOX)
- {
- int srcFd, dstFd;
- SandboxReporter::Singleton()
- ->GetClientFileDescriptorMapping(&srcFd, &dstFd);
- mLaunchOptions->fds_to_remap.push_back(std::make_pair(srcFd, dstFd));
- }
-# endif // defined(XP_LINUX) && defined(MOZ_SANDBOX)
-
# ifdef MOZ_WIDGET_COCOA
// Add a mach port to the command line so the child can communicate its
// 'task_t' back to the parent.
//
// Put a random number into the channel name, so that a compromised renderer
// can't pretend being the child that's forked off.
std::string mach_connection_name = StringPrintf("org.mozilla.machname.%d",
base::RandInt(0, std::numeric_limits<int>::max()));
new file mode 100644
--- /dev/null
+++ b/security/sandbox/linux/launch/SandboxLaunch.cpp
@@ -0,0 +1,57 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* 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 "SandboxLaunch.h"
+
+#include "mozilla/Assertions.h"
+#include "mozilla/SandboxReporter.h"
+#include "nsString.h"
+#include "prenv.h"
+
+namespace mozilla {
+
+static void
+PreloadSandboxLib(base::environment_map* aEnv)
+{
+ // Preload libmozsandbox.so so that sandbox-related interpositions
+ // can be defined there instead of in the executable.
+ // (This could be made conditional on intent to use sandboxing, but
+ // it's harmless for non-sandboxed processes.)
+ nsAutoCString preload;
+ // Prepend this, because people can and do preload libpthread.
+ // (See bug 1222500.)
+ preload.AssignLiteral("libmozsandbox.so");
+ if (const char* oldPreload = PR_GetEnv("LD_PRELOAD")) {
+ // Doesn't matter if oldPreload is ""; extra separators are ignored.
+ preload.Append(' ');
+ preload.Append(oldPreload);
+ }
+ MOZ_ASSERT(aEnv->count("LD_PRELOAD") == 0);
+ (*aEnv)["LD_PRELOAD"] = preload.get();
+}
+
+static void
+AttachSandboxReporter(base::file_handle_mapping_vector* aFdMap)
+{
+ int srcFd, dstFd;
+ SandboxReporter::Singleton()
+ ->GetClientFileDescriptorMapping(&srcFd, &dstFd);
+ aFdMap->push_back({srcFd, dstFd});
+}
+
+void
+SandboxLaunchPrepare(GeckoProcessType aType,
+ base::LaunchOptions* aOptions)
+{
+ PreloadSandboxLib(&aOptions->environ);
+ AttachSandboxReporter(&aOptions->fds_to_remap);
+
+ // aType will be used in bug 1401062 to take over the functionality
+ // of SandboxEarlyInit
+}
+
+
+} // namespace mozilla
new file mode 100644
--- /dev/null
+++ b/security/sandbox/linux/launch/SandboxLaunch.h
@@ -0,0 +1,23 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* 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/. */
+
+#ifndef mozilla_SandboxLaunch_h
+#define mozilla_SandboxLaunch_h
+
+#include "base/process_util.h"
+#include "nsXULAppAPI.h"
+
+namespace mozilla {
+
+// Called in the parent process to set up launch-time aspects of
+// sandboxing. If aType is GeckoProcessType_Content, this must be
+// called on the main thread in order to access prefs.
+void SandboxLaunchPrepare(GeckoProcessType aType,
+ base::LaunchOptions* aOptions);
+
+} // namespace mozilla
+
+#endif // mozilla_SandboxLaunch_h
new file mode 100644
--- /dev/null
+++ b/security/sandbox/linux/launch/moz.build
@@ -0,0 +1,28 @@
+# -*- Mode: python; python-indent: 4; indent-tabs-mode: nil; tab-width: 40 -*-
+# vim: set filetype=python:
+# 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/.
+
+EXPORTS.mozilla += [
+ 'SandboxLaunch.h',
+]
+
+SOURCES += [
+ 'SandboxLaunch.cpp',
+]
+
+include('/ipc/chromium/chromium-config.mozbuild')
+
+LOCAL_INCLUDES += [
+ # Need this for safe_sprintf.h used by SandboxLogging.h,
+ # but it has to be after ipc/chromium/src.
+ '/security/sandbox/chromium',
+ '/security/sandbox/linux',
+]
+
+USE_LIBS += [
+ 'mozsandbox',
+]
+
+FINAL_LIBRARY = 'xul'
--- a/security/sandbox/linux/moz.build
+++ b/security/sandbox/linux/moz.build
@@ -113,14 +113,15 @@ if CONFIG['OS_TARGET'] != 'Android':
OS_LIBS += [
'rt',
]
DIRS += [
'broker',
'glue',
'interfaces',
+ 'launch',
'reporter',
]
TEST_DIRS += [
'gtest',
]