Bug 1406971 - Change nsProcess to use LaunchApp from IPC, instead of NSPR, on Unix. r=froydnj

This also fixes the Unix part of bug 678369, and fixes bug 147659 as a
convenient side-effect of using LaunchApp (which has the desired
fd-closing behavior already) rather than directly using fork/exec.

The main goal is to work around bug 227246, where PR_CreateProcess on
Unix interferes with anything else that tries to use child processes.
This does not fix that bug -- NSPR will still cause problems if used in
that way -- but it's an adequate workaround for that bug in Gecko in
almost all cases (the one known exception is nsAuthSambaNTLM, which uses
NSPR directly and needs to be fixed separately).

Waiting for the child process uses waitpid() directly, sharing the
existing code used for OS X.

MozReview-Commit-ID: 6zfZ1Zgk2i9

--HG--
extra : rebase_source : e8230503d82943af4563d8d63baa029d8a698683
This commit is contained in:
Jed Davis 2017-10-06 19:58:33 -06:00
Родитель 54555dd2d6
Коммит b39b9e95d4
2 изменённых файлов: 25 добавлений и 6 удалений

Просмотреть файл

@ -20,7 +20,7 @@
#include "nsIWeakReferenceUtils.h"
#include "nsIObserver.h"
#include "nsString.h"
#ifndef XP_MACOSX
#ifndef XP_UNIX
#include "prproces.h"
#endif
#if defined(PROCESSMODEL_WINAPI)
@ -76,7 +76,7 @@ private:
int32_t mExitValue;
#if defined(PROCESSMODEL_WINAPI)
HANDLE mProcess;
#elif !defined(XP_MACOSX)
#elif !defined(XP_UNIX)
PRProcess* mProcess;
#endif
};

Просмотреть файл

@ -38,6 +38,11 @@
#ifdef XP_MACOSX
#include <crt_externs.h>
#include <spawn.h>
#endif
#ifdef XP_UNIX
#ifndef XP_MACOSX
#include "base/process_util.h"
#endif
#include <sys/wait.h>
#include <sys/errno.h>
#endif
@ -78,7 +83,7 @@ nsProcess::nsProcess()
, mObserver(nullptr)
, mWeakObserver(nullptr)
, mExitValue(-1)
#if !defined(XP_MACOSX)
#if !defined(XP_UNIX)
, mProcess(nullptr)
#endif
{
@ -272,7 +277,7 @@ nsProcess::Monitor(void* aArg)
}
}
#else
#ifdef XP_MACOSX
#ifdef XP_UNIX
int exitCode = -1;
int status = 0;
pid_t result;
@ -296,7 +301,7 @@ nsProcess::Monitor(void* aArg)
// Lock in case Kill or GetExitCode are called during this
{
MutexAutoLock lock(process->mLock);
#if !defined(XP_MACOSX)
#if !defined(XP_UNIX)
process->mProcess = nullptr;
#endif
process->mExitValue = exitCode;
@ -570,6 +575,20 @@ nsProcess::RunProcess(bool aBlocking, char** aMyArgv, nsIObserver* aObserver,
if (result != 0) {
return NS_ERROR_FAILURE;
}
#elif defined(XP_UNIX)
base::file_handle_mapping_vector fdMap;
std::vector<std::string> argvVec;
for (char** arg = aMyArgv; *arg != nullptr; ++arg) {
argvVec.push_back(*arg);
}
pid_t newPid;
if (base::LaunchApp(argvVec, fdMap, false, &newPid)) {
static_assert(sizeof(pid_t) <= sizeof(int32_t),
"mPid is large enough to hold a pid");
mPid = static_cast<int32_t>(newPid);
} else {
return NS_ERROR_FAILURE;
}
#else
mProcess = PR_CreateProcess(aMyArgv[0], aMyArgv, nullptr, nullptr);
if (!mProcess) {
@ -676,7 +695,7 @@ nsProcess::Kill()
if (TerminateProcess(mProcess, 0) == 0) {
return NS_ERROR_FAILURE;
}
#elif defined(XP_MACOSX)
#elif defined(XP_UNIX)
if (kill(mPid, SIGKILL) != 0) {
return NS_ERROR_FAILURE;
}