Revert "[dartdev] Use VmInteropHandler for invoking sub commands"
This reverts commit 08252fc9e91cea505d1f65353675206b24ff8b85.
Reason for revert: https://github.com/dart-lang/sdk/issues/59784
Original change's description:
> [dartdev] Use VmInteropHandler for invoking sub commands
>
> Use VmInteropHandler for invoking sub commands instead of running them
> in an isolate. Running sub commands in an isolate causes an increased footprint.
> Changing this to use VmInteropHandler avoids the additional memory footprint.
>
> Commands that need to use an AOT runtime for execution now exec the AOT
> runtime and run the command.
>
> TEST=ci
>
> Change-Id: If7aed1cab2fec9d9940bd562ad5aa9c4e9a6ac7f
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/398604
> Reviewed-by: Ben Konyi <bkonyi@google.com>
> Reviewed-by: Brian Quinlan <bquinlan@google.com>
> Commit-Queue: Siva Annamalai <asiva@google.com>
Change-Id: I82a997d49a7d52e1fdaa7d75f509603ebe5e51dd
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/401901
Reviewed-by: Siva Annamalai <asiva@google.com>
Reviewed-by: Sigmund Cherem <sigmund@google.com>
Bot-Commit: Rubber Stamper <rubber-stamper@appspot.gserviceaccount.com>
diff --git a/pkg/dartdev/lib/src/commands/compile.dart b/pkg/dartdev/lib/src/commands/compile.dart
index 75f113c..54ad454 100644
--- a/pkg/dartdev/lib/src/commands/compile.dart
+++ b/pkg/dartdev/lib/src/commands/compile.dart
@@ -17,7 +17,6 @@
import '../native_assets.dart';
import '../sdk.dart';
import '../utils.dart';
-import '../vm_interop_handler.dart';
const int genericErrorExitCode = 255;
const int compileErrorExitCode = 254;
@@ -94,18 +93,17 @@
final args = argResults!;
var snapshot = sdk.dart2jsAotSnapshot;
var runtime = sdk.dartAotRuntime;
- var isAOT = true;
if (!Sdk.checkArtifactExists(snapshot, logError: false)) {
// AOT snapshots cannot be generated on IA32, so we need this fallback
// branch until support for IA32 is dropped (https://dartbug.com/49969).
snapshot = sdk.dart2jsSnapshot;
+ runtime = sdk.dart;
if (!Sdk.checkArtifactExists(snapshot)) {
return genericErrorExitCode;
}
- runtime = sdk.dart;
- isAOT = false;
}
final dart2jsCommand = [
+ runtime,
snapshot,
'--libraries-spec=${sdk.librariesJson}',
'--cfe-invocation-modes=compile',
@@ -114,13 +112,8 @@
if (args.rest.isNotEmpty) ...args.rest.sublist(0),
];
try {
- VmInteropHandler.run(
- runtime,
- dart2jsCommand,
- packageConfigOverride: null,
- isAOT : isAOT,
- );
- return 0;
+ final exitCode = await runProcessInheritStdio(dart2jsCommand);
+ return exitCode;
} catch (e, st) {
log.stderr('Error: JS compilation failed');
log.stderr(e.toString());
diff --git a/pkg/dartdev/lib/src/vm_interop_handler.dart b/pkg/dartdev/lib/src/vm_interop_handler.dart
index 43bd647..37eed1d 100644
--- a/pkg/dartdev/lib/src/vm_interop_handler.dart
+++ b/pkg/dartdev/lib/src/vm_interop_handler.dart
@@ -18,9 +18,6 @@
///
/// If [markMainIsolateAsSystemIsolate] is given and set to true, the spawned
/// isolate will run with `--mark-main-isolate-as-system-isolate` enabled.
- ///
- /// If [isAOT] is given and set to true, the script is executed by
- /// execing the dartaotruntime.
static void run(
String script,
List<String> args, {
@@ -30,12 +27,11 @@
//
// See https://github.com/dart-lang/sdk/issues/53576
bool markMainIsolateAsSystemIsolate = false,
- bool isAOT = false,
}) {
final port = _port;
if (port == null) return;
final message = <dynamic>[
- isAOT ? _kResultRunAOT : _kResultRunJIT,
+ _kResultRun,
script,
packageConfigOverride,
markMainIsolateAsSystemIsolate,
@@ -55,9 +51,8 @@
}
// Note: keep in sync with runtime/bin/dartdev_isolate.h
- static const int _kResultRunJIT = 1;
- static const int _kResultRunAOT = 2;
- static const int _kResultExit = 3;
+ static const int _kResultRun = 1;
+ static const int _kResultExit = 2;
static SendPort? _port;
}
diff --git a/runtime/bin/dartdev_isolate.cc b/runtime/bin/dartdev_isolate.cc
index 95c9fd5..c7aab45 100644
--- a/runtime/bin/dartdev_isolate.cc
+++ b/runtime/bin/dartdev_isolate.cc
@@ -38,7 +38,6 @@
DartDevIsolate::DartDevRunner();
bool DartDevIsolate::should_run_dart_dev_ = false;
bool DartDevIsolate::print_usage_error_ = false;
-CommandLineOptions* DartDevIsolate::vm_options_ = nullptr;
Monitor* DartDevIsolate::DartDevRunner::monitor_ = new Monitor();
DartDevIsolate::DartDev_Result DartDevIsolate::DartDevRunner::result_ =
DartDevIsolate::DartDev_Result_Unknown;
@@ -139,7 +138,7 @@
Thread::Start("DartDev Runner", RunCallback, reinterpret_cast<uword>(this));
monitor_->WaitMicros(Monitor::kNoTimeout);
- if (result_ == DartDevIsolate::DartDev_Result_RunJIT) {
+ if (result_ == DartDevIsolate::DartDev_Result_Run) {
// Clear the DartDev dart_options and replace them with the processed
// options provided by DartDev.
dart_options_->Reset();
@@ -158,8 +157,8 @@
ASSERT(message->type == Dart_CObject_kArray);
int32_t type = GetArrayItem(message, 0)->value.as_int32;
switch (type) {
- case DartDevIsolate::DartDev_Result_RunJIT: {
- result_ = DartDevIsolate::DartDev_Result_RunJIT;
+ case DartDevIsolate::DartDev_Result_Run: {
+ result_ = DartDevIsolate::DartDev_Result_Run;
ASSERT(GetArrayItem(message, 1)->type == Dart_CObject_kString);
auto item2 = GetArrayItem(message, 2);
@@ -205,86 +204,6 @@
}
break;
}
- case DartDevIsolate::DartDev_Result_RunAOT: {
- result_ = DartDevIsolate::DartDev_Result_RunAOT;
- ASSERT(GetArrayItem(message, 1)->type == Dart_CObject_kString);
- auto item2 = GetArrayItem(message, 2);
-
- ASSERT(item2->type == Dart_CObject_kString ||
- item2->type == Dart_CObject_kNull);
-
- auto item3 = GetArrayItem(message, 3);
-
- ASSERT(item3->type == Dart_CObject_kBool);
- const bool mark_main_isolate_as_system_isolate = item3->value.as_bool;
- if (mark_main_isolate_as_system_isolate) {
- Options::set_mark_main_isolate_as_system_isolate(true);
- }
-
- if (*script_ != nullptr) {
- free(*script_);
- }
- if (*package_config_override_ != nullptr) {
- free(*package_config_override_);
- *package_config_override_ = nullptr;
- }
- *script_ = Utils::StrDup(GetArrayItem(message, 1)->value.as_string);
-
- if (item2->type == Dart_CObject_kString) {
- *package_config_override_ = Utils::StrDup(item2->value.as_string);
- }
-
- intptr_t num_vm_options = 0;
- const char** vm_options = nullptr;
- ASSERT(GetArrayItem(message, 4)->type == Dart_CObject_kArray);
- Dart_CObject* args = GetArrayItem(message, 4);
- intptr_t argc = args->value.as_array.length;
- Dart_CObject** dart_args = args->value.as_array.values;
-
- if (vm_options_ != nullptr) {
- num_vm_options = vm_options_->count();
- vm_options = vm_options_->arguments();
- }
- auto deleter = [](char** args) {
- for (intptr_t i = 0; i < argc_; ++i) {
- free(args[i]);
- }
- delete[] args;
- };
- // Total count of arguments to be passed to the script being execed.
- argc_ = argc + num_vm_options + 1;
-
- // Array of arguments to be passed to the script being execed.
- argv_ = std::unique_ptr<char*[], void (*)(char**)>(new char*[argc_ + 1],
- deleter);
-
- intptr_t idx = 0;
- // Copy in name of the script to run (dartaotruntime).
- argv_[0] = Utils::StrDup(GetArrayItem(message, 1)->value.as_string);
- idx += 1;
- // Copy in any vm options that need to be passed to the execed process.
- for (intptr_t i = 0; i < num_vm_options; ++i) {
- argv_[i + idx] = Utils::StrDup(vm_options[i]);
- }
- idx += num_vm_options;
- // Copy in the dart options that need to be passed to the command.
- for (intptr_t i = 0; i < argc; ++i) {
- argv_[i + idx] = Utils::StrDup(dart_args[i]->value.as_string);
- }
- // Null terminate the argv array.
- argv_[argc + idx] = nullptr;
-
- // Exec the script to be run and pass the arguments.
- char err_msg[256];
- err_msg[0] = '\0';
- int ret = Process::Exec(nullptr, *script_,
- const_cast<const char**>(argv_.get()), argc_,
- nullptr, err_msg, sizeof(err_msg));
- if (ret != 0) {
- ProcessError(err_msg, kErrorExitCode);
- }
- break;
- }
case DartDevIsolate::DartDev_Result_Exit: {
ASSERT(GetArrayItem(message, 1)->type == Dart_CObject_kInt32);
int32_t dartdev_exit_code = GetArrayItem(message, 1)->value.as_int32;
@@ -395,9 +314,7 @@
Dart_IsolateGroupCreateCallback create_isolate,
char** packages_file,
char** script,
- CommandLineOptions* vm_options,
CommandLineOptions* dart_options) {
- vm_options_ = vm_options;
runner_.Run(create_isolate, packages_file, script, dart_options);
return runner_.result();
}
diff --git a/runtime/bin/dartdev_isolate.h b/runtime/bin/dartdev_isolate.h
index ed997cc..79566c6 100644
--- a/runtime/bin/dartdev_isolate.h
+++ b/runtime/bin/dartdev_isolate.h
@@ -27,9 +27,8 @@
// Note: keep in sync with pkg/dartdev/lib/vm_interop_handler.dart
typedef enum {
DartDev_Result_Unknown = -1,
- DartDev_Result_RunJIT = 1,
- DartDev_Result_RunAOT = 2,
- DartDev_Result_Exit = 3,
+ DartDev_Result_Run = 1,
+ DartDev_Result_Exit = 2,
} DartDev_Result;
// Returns true if there does not exist a file at |script_uri| or the URI is
@@ -59,7 +58,6 @@
Dart_IsolateGroupCreateCallback create_isolate,
char** packages_file,
char** script,
- CommandLineOptions* vm_options,
CommandLineOptions* dart_options);
protected:
@@ -85,11 +83,11 @@
static char** package_config_override_;
static std::unique_ptr<char*[], void (*)(char**)> argv_;
static intptr_t argc_;
- static Monitor* monitor_;
Dart_IsolateGroupCreateCallback create_isolate_;
CommandLineOptions* dart_options_;
const char* packages_file_;
+ static Monitor* monitor_;
DISALLOW_ALLOCATION();
};
@@ -100,7 +98,6 @@
static DartDevRunner runner_;
static bool should_run_dart_dev_;
static bool print_usage_error_;
- static CommandLineOptions* vm_options_;
DISALLOW_ALLOCATION();
DISALLOW_IMPLICIT_CONSTRUCTORS(DartDevIsolate);
diff --git a/runtime/bin/main_impl.cc b/runtime/bin/main_impl.cc
index cd4fab2..4a26768 100644
--- a/runtime/bin/main_impl.cc
+++ b/runtime/bin/main_impl.cc
@@ -1421,11 +1421,11 @@
Options::gen_snapshot_kind() == SnapshotKind::kNone) {
DartDevIsolate::DartDev_Result dartdev_result = DartDevIsolate::RunDartDev(
CreateIsolateGroupAndSetup, &package_config_override, &script_name,
- &vm_options, &dart_options);
+ &dart_options);
ASSERT(dartdev_result != DartDevIsolate::DartDev_Result_Unknown);
ran_dart_dev = true;
should_run_user_program =
- (dartdev_result == DartDevIsolate::DartDev_Result_RunJIT);
+ (dartdev_result == DartDevIsolate::DartDev_Result_Run);
if (should_run_user_program) {
try_load_snapshots_lambda();
}
diff --git a/runtime/bin/process.cc b/runtime/bin/process.cc
index dfb0b77..f990e80 100644
--- a/runtime/bin/process.cc
+++ b/runtime/bin/process.cc
@@ -114,9 +114,9 @@
const char* path = DartUtils::GetStringValue(path_handle);
Dart_Handle arguments = Dart_GetNativeArgument(args, 3);
intptr_t args_length = 0;
- const char** string_args = const_cast<const char**>(
+ char** string_args =
ExtractCStringList(arguments, status_handle,
- "Arguments must be builtin strings", &args_length));
+ "Arguments must be builtin strings", &args_length);
if (string_args == nullptr) {
Dart_SetBooleanReturnValue(args, false);
return;
diff --git a/runtime/bin/process.h b/runtime/bin/process.h
index 2aa40cd..9bd547c 100644
--- a/runtime/bin/process.h
+++ b/runtime/bin/process.h
@@ -94,7 +94,7 @@
// process exit streams.
static int Start(Namespace* namespc,
const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -114,23 +114,6 @@
intptr_t exit_handler,
ProcessResult* result);
- // Exec process.
- // On systems that support 'exec' it will use it to replace
- // the current process image with the image corresponding to 'path'
- // On systems that do not support it (Windows) it will start in a
- // child process in the same group as the parent so that when the parent
- // is killed the child also dies.
- // Returns 0 if the process could be execed successfully
- // Returns -1 if the exec could not be done successfully and 'errmsg'
- // points to the error message
- static int Exec(Namespace* namespc,
- const char* path,
- const char* arguments[],
- intptr_t arguments_length,
- const char* working_directory,
- char* errmsg,
- intptr_t errmsg_len);
-
// Kill a process with a given pid.
static bool Kill(intptr_t id, int signal);
diff --git a/runtime/bin/process_fuchsia.cc b/runtime/bin/process_fuchsia.cc
index 170f074..eed2af0 100644
--- a/runtime/bin/process_fuchsia.cc
+++ b/runtime/bin/process_fuchsia.cc
@@ -838,19 +838,6 @@
return starter.Start();
}
-// The command line dart utility does not run on Fuchsia, this functionality
-// is not supported on that platform.
-int Process::Exec(Namespace* namespc,
- const char* path,
- const char** arguments,
- const char* working_directory,
- char* errmsg,
- intptr_t errmsg_len) {
- snprintf(errmsg, errmsg_len,
- "Process::Exec is not supported on this platform");
- return -1;
-}
-
intptr_t Process::SetSignalHandler(intptr_t signal) {
errno = ENOSYS;
return -1;
diff --git a/runtime/bin/process_linux.cc b/runtime/bin/process_linux.cc
index da95e5a..64e74fc 100644
--- a/runtime/bin/process_linux.cc
+++ b/runtime/bin/process_linux.cc
@@ -246,47 +246,11 @@
bool ExitCodeHandler::terminate_done_ = false;
Monitor* ExitCodeHandler::monitor_ = nullptr;
-// Tries to find path relative to the current namespace unless it should be
-// searched in the PATH environment variable.
-// The path that should be passed to exec is returned in realpath.
-// Returns true on success, and false if there was an error that should
-// be reported to the parent.
-static bool PathInNamespace(char* realpath,
- intptr_t realpath_size,
- Namespace* namespc,
- const char* path) {
- // Perform a PATH search if there's no slash in the path.
- if (Namespace::IsDefault(namespc) || strchr(path, '/') == nullptr) {
- // TODO(zra): If there is a non-default namespace, the entries in PATH
- // should be treated as relative to the namespace.
- strncpy(realpath, path, realpath_size);
- realpath[realpath_size - 1] = '\0';
- return true;
- }
- NamespaceScope ns(namespc, path);
- const int fd =
- TEMP_FAILURE_RETRY(openat64(ns.fd(), ns.path(), O_RDONLY | O_CLOEXEC));
- if (fd == -1) {
- return false;
- }
- char procpath[PATH_MAX];
- snprintf(procpath, PATH_MAX, "/proc/self/fd/%d", fd);
- const intptr_t length =
- TEMP_FAILURE_RETRY(readlink(procpath, realpath, realpath_size));
- if (length < 0) {
- FDUtils::SaveErrorAndClose(fd);
- return false;
- }
- realpath[length] = '\0';
- FDUtils::SaveErrorAndClose(fd);
- return true;
-}
-
class ProcessStarter {
public:
ProcessStarter(Namespace* namespc,
const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -317,7 +281,7 @@
exec_control_[0] = -1;
exec_control_[1] = -1;
- program_arguments_ = reinterpret_cast<const char**>(Dart_ScopeAllocate(
+ program_arguments_ = reinterpret_cast<char**>(Dart_ScopeAllocate(
(arguments_length + 2) * sizeof(*program_arguments_)));
program_arguments_[0] = const_cast<char*>(path_);
for (int i = 0; i < arguments_length; i++) {
@@ -483,7 +447,31 @@
// Returns true on success, and false if there was an error that should
// be reported to the parent.
bool FindPathInNamespace(char* realpath, intptr_t realpath_size) {
- return PathInNamespace(realpath, realpath_size, namespc_, path_);
+ // Perform a PATH search if there's no slash in the path.
+ if (Namespace::IsDefault(namespc_) || strchr(path_, '/') == nullptr) {
+ // TODO(zra): If there is a non-default namespace, the entries in PATH
+ // should be treated as relative to the namespace.
+ strncpy(realpath, path_, realpath_size);
+ realpath[realpath_size - 1] = '\0';
+ return true;
+ }
+ NamespaceScope ns(namespc_, path_);
+ const int fd =
+ TEMP_FAILURE_RETRY(openat64(ns.fd(), ns.path(), O_RDONLY | O_CLOEXEC));
+ if (fd == -1) {
+ return false;
+ }
+ char procpath[PATH_MAX];
+ snprintf(procpath, PATH_MAX, "/proc/self/fd/%d", fd);
+ const intptr_t length =
+ TEMP_FAILURE_RETRY(readlink(procpath, realpath, realpath_size));
+ if (length < 0) {
+ FDUtils::SaveErrorAndClose(fd);
+ return false;
+ }
+ realpath[length] = '\0';
+ FDUtils::SaveErrorAndClose(fd);
+ return true;
}
void ExecProcess() {
@@ -784,7 +772,7 @@
int write_out_[2]; // Pipe for stdin to child process.
int exec_control_[2]; // Pipe to get the result from exec.
- const char** program_arguments_;
+ char** program_arguments_;
char** program_environment_;
Namespace* namespc_;
@@ -804,7 +792,7 @@
int Process::Start(Namespace* namespc,
const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -926,31 +914,6 @@
return true;
}
-int Process::Exec(Namespace* namespc,
- const char* path,
- const char* arguments[],
- intptr_t arguments_length,
- const char* working_directory,
- char* errmsg,
- intptr_t errmsg_len) {
- if (working_directory != nullptr &&
- !Directory::SetCurrent(namespc, working_directory)) {
- Utils::StrError(errno, errmsg, errmsg_len);
- return -1;
- }
-
- char realpath[PATH_MAX];
- if (!PathInNamespace(realpath, PATH_MAX, namespc, path)) {
- Utils::StrError(errno, errmsg, errmsg_len);
- return -1;
- }
- // TODO(dart:io) Test for the existence of execveat, and use it instead.
- execvp(const_cast<const char*>(realpath),
- const_cast<char* const*>(arguments));
- Utils::StrError(errno, errmsg, errmsg_len);
- return -1;
-}
-
bool Process::Kill(intptr_t id, int signal) {
return (TEMP_FAILURE_RETRY(kill(id, signal)) != -1);
}
diff --git a/runtime/bin/process_macos.cc b/runtime/bin/process_macos.cc
index 94568e3..d7eb45e 100644
--- a/runtime/bin/process_macos.cc
+++ b/runtime/bin/process_macos.cc
@@ -249,7 +249,7 @@
class ProcessStarter {
public:
ProcessStarter(const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -279,7 +279,7 @@
exec_control_[0] = -1;
exec_control_[1] = -1;
- program_arguments_ = reinterpret_cast<const char**>(Dart_ScopeAllocate(
+ program_arguments_ = reinterpret_cast<char**>(Dart_ScopeAllocate(
(arguments_length + 2) * sizeof(*program_arguments_)));
program_arguments_[0] = const_cast<char*>(path_);
for (int i = 0; i < arguments_length; i++) {
@@ -740,7 +740,7 @@
int write_out_[2]; // Pipe for stdin to child process.
int exec_control_[2]; // Pipe to get the result from exec.
- const char** program_arguments_;
+ char** program_arguments_;
char** program_environment_;
const char* path_;
@@ -760,7 +760,7 @@
int Process::Start(Namespace* namespc,
const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -898,24 +898,6 @@
#endif // defined(DART_HOST_OS_IOS)
}
-int Process::Exec(Namespace* namespc,
- const char* path,
- const char* arguments[],
- intptr_t arguments_length,
- const char* working_directory,
- char* errmsg,
- intptr_t errmsg_len) {
- if (working_directory != nullptr &&
- TEMP_FAILURE_RETRY(chdir(working_directory)) == -1) {
- Utils::StrError(errno, errmsg, errmsg_len);
- return -1;
- }
-
- execvp(const_cast<const char*>(path), const_cast<char* const*>(arguments));
- Utils::StrError(errno, errmsg, errmsg_len);
- return -1;
-}
-
static int SignalMap(intptr_t id) {
switch (static_cast<ProcessSignals>(id)) {
case kSighup:
diff --git a/runtime/bin/process_win.cc b/runtime/bin/process_win.cc
index b9949c9..e9a353b 100644
--- a/runtime/bin/process_win.cc
+++ b/runtime/bin/process_win.cc
@@ -20,7 +20,6 @@
#include "bin/utils.h"
#include "bin/utils_win.h"
#include "platform/syslog.h"
-#include "platform/text_buffer.h"
namespace dart {
namespace bin {
@@ -345,7 +344,7 @@
class ProcessStarter {
public:
ProcessStarter(const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -374,12 +373,11 @@
stderr_handles_[kWriteHandle] = INVALID_HANDLE_VALUE;
exit_handles_[kReadHandle] = INVALID_HANDLE_VALUE;
exit_handles_[kWriteHandle] = INVALID_HANDLE_VALUE;
- child_process_handle_ = INVALID_HANDLE_VALUE;
// Transform input strings to system format.
const wchar_t* system_path = StringUtilsWin::Utf8ToWide(path_);
- const wchar_t** system_arguments;
- system_arguments = reinterpret_cast<const wchar_t**>(
+ wchar_t** system_arguments;
+ system_arguments = reinterpret_cast<wchar_t**>(
Dart_ScopeAllocate(arguments_length * sizeof(*system_arguments)));
for (int i = 0; i < arguments_length; i++) {
system_arguments[i] = StringUtilsWin::Utf8ToWide(arguments[i]);
@@ -564,42 +562,7 @@
*exit_handler_ = reinterpret_cast<intptr_t>(exit_handle);
}
}
- child_process_handle_ = process_info.hProcess;
- CloseHandle(process_info.hThread);
- // Return process id.
- *id_ = process_info.dwProcessId;
- return 0;
- }
-
- int StartForExec() {
- // Setup info
- STARTUPINFOEXW startup_info;
- ZeroMemory(&startup_info, sizeof(startup_info));
- startup_info.StartupInfo.cb = sizeof(startup_info);
- ASSERT(mode_ == kInheritStdio);
- ASSERT(Process::ModeIsAttached(mode_));
- ASSERT(!Process::ModeHasStdio(mode_));
-
- PROCESS_INFORMATION process_info;
- ZeroMemory(&process_info, sizeof(process_info));
-
- // Create process.
- DWORD creation_flags =
- EXTENDED_STARTUPINFO_PRESENT | CREATE_UNICODE_ENVIRONMENT;
- BOOL result = CreateProcessW(
- nullptr, // ApplicationName
- command_line_,
- nullptr, // ProcessAttributes
- nullptr, // ThreadAttributes
- TRUE, // InheritHandles
- creation_flags, environment_block_, system_working_directory_,
- reinterpret_cast<STARTUPINFOW*>(&startup_info), &process_info);
-
- if (result == 0) {
- return SetOsErrorMessage(os_error_message_);
- }
- child_process_handle_ = process_info.hProcess;
CloseHandle(process_info.hThread);
// Return process id.
@@ -664,7 +627,6 @@
HANDLE stdout_handles_[2];
HANDLE stderr_handles_[2];
HANDLE exit_handles_[2];
- HANDLE child_process_handle_;
const wchar_t* system_working_directory_;
wchar_t* command_line_;
@@ -689,7 +651,7 @@
int Process::Start(Namespace* namespc,
const char* path,
- const char* arguments[],
+ char* arguments[],
intptr_t arguments_length,
const char* working_directory,
char* environment[],
@@ -918,92 +880,6 @@
return true;
}
-int Process::Exec(Namespace* namespc,
- const char* path,
- const char* arguments[],
- intptr_t arguments_length,
- const char* working_directory,
- char* errmsg,
- intptr_t errmsg_len) {
- // Create a Job object with JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE
- HANDLE hjob = CreateJobObject(nullptr, nullptr);
- if (hjob == nullptr) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - CreateJobObject failed %d\n", GetLastError());
- return -1;
- }
- JOBOBJECT_EXTENDED_LIMIT_INFORMATION info;
- DWORD qresult;
- if (!QueryInformationJobObject(hjob, JobObjectExtendedLimitInformation, &info,
- sizeof(JOBOBJECT_EXTENDED_LIMIT_INFORMATION),
- &qresult)) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - QueryInformationJobObject failed %d\n",
- GetLastError());
- return -1;
- }
- info.BasicLimitInformation.LimitFlags |= JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE;
- if (!SetInformationJobObject(hjob, JobObjectExtendedLimitInformation, &info,
- sizeof(JOBOBJECT_EXTENDED_LIMIT_INFORMATION))) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - SetInformationJobObject failed %d\n",
- GetLastError());
- return -1;
- }
-
- // Put the current process into the job object (there is a race here
- // as the process can crash before it is in the Job object, but since
- // we haven't spawned any children yet this race is harmless)
- if (!AssignProcessToJobObject(hjob, GetCurrentProcess())) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - AssignProcessToJobObject failed %d\n",
- GetLastError());
- return -1;
- }
-
- // Spawn the new child process (this child will automatically get
- // added to the Job object).
- // If the parent process is killed or it crashes the Job object
- // will get destroyed and all the child processes will also get killed.
- // arguments includes the name of the executable to run which is the same
- // as the value passed in 'path', we strip that off when starting the
- // process.
- intptr_t pid = -1;
- char* os_error_message = nullptr; // Scope allocated by Process::Start.
- ProcessStarter starter(path, &(arguments[1]), (arguments_length - 1),
- working_directory, nullptr, 0, kInheritStdio, nullptr,
- nullptr, nullptr, &pid, nullptr, &os_error_message);
- int result = starter.StartForExec();
- if (result != 0) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - %s\n", os_error_message);
- return -1;
- }
-
- // Now wait for this child process to terminate (normal exit or crash).
- HANDLE child_process = starter.child_process_handle_;
- ASSERT(child_process != INVALID_HANDLE_VALUE);
- DWORD wait_result = WaitForSingleObject(child_process, INFINITE);
- if (wait_result != WAIT_OBJECT_0) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - WaitForSingleObject failed %d\n", GetLastError());
- CloseHandle(child_process);
- return -1;
- }
- int retval;
- if (!GetExitCodeProcess(child_process, reinterpret_cast<DWORD*>(&retval))) {
- BufferFormatter f(errmsg, errmsg_len);
- f.Printf("Process::Exec - GetExitCodeProcess failed %d\n", GetLastError());
- CloseHandle(child_process);
- return -1;
- }
- CloseHandle(child_process);
- // We exit the process here to simulate the same behaviour as exec on systems
- // that support it.
- ExitProcess(retval);
- return 0;
-}
-
bool Process::Kill(intptr_t id, int signal) {
USE(signal); // signal is not used on Windows.
HANDLE process_handle;