summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCheng Zhao <zcbenz@gmail.com>2021-10-06 10:22:21 +0900
committerMichael Dawson <mdawson@devrus.com>2021-10-13 17:27:27 -0400
commit3b72788afb7365e10ae1e97c71d1f60ee29f09f2 (patch)
tree2704d51811fb4d1dd3ce7d6c9122c9982bdb5c28
parent4cf5563147cd562335ec02c4a78f9397a30e6701 (diff)
downloadnode-new-3b72788afb7365e10ae1e97c71d1f60ee29f09f2.tar.gz
src: add flags for controlling process behavior
PR-URL: https://github.com/nodejs/node/pull/40339 Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Michael Dawson <midawson@redhat.com> Reviewed-By: James M Snell <jasnell@gmail.com> Reviewed-By: Shelley Vohr <shelley.vohr@gmail.com> Reviewed-By: Minwoo Jung <nodecorelab@gmail.com>
-rw-r--r--src/node.cc108
-rw-r--r--src/node.h27
-rw-r--r--src/node_internals.h3
3 files changed, 88 insertions, 50 deletions
diff --git a/src/node.cc b/src/node.cc
index e942c108a1..0fa51b2697 100644
--- a/src/node.cc
+++ b/src/node.cc
@@ -843,6 +843,14 @@ static std::atomic_bool init_called{false};
int InitializeNodeWithArgs(std::vector<std::string>* argv,
std::vector<std::string>* exec_argv,
std::vector<std::string>* errors) {
+ return InitializeNodeWithArgs(argv, exec_argv, errors,
+ ProcessFlags::kNoFlags);
+}
+
+int InitializeNodeWithArgs(std::vector<std::string>* argv,
+ std::vector<std::string>* exec_argv,
+ std::vector<std::string>* errors,
+ ProcessFlags::Flags flags) {
// Make sure InitializeNodeWithArgs() is called only once.
CHECK(!init_called.exchange(true));
@@ -853,7 +861,8 @@ int InitializeNodeWithArgs(std::vector<std::string>* argv,
binding::RegisterBuiltinModules();
// Make inherited handles noninheritable.
- uv_disable_stdio_inheritance();
+ if (!(flags & ProcessFlags::kEnableStdioInheritance))
+ uv_disable_stdio_inheritance();
// Cache the original command line to be
// used in diagnostic reports.
@@ -869,67 +878,73 @@ int InitializeNodeWithArgs(std::vector<std::string>* argv,
HandleEnvOptions(per_process::cli_options->per_isolate->per_env);
#if !defined(NODE_WITHOUT_NODE_OPTIONS)
- std::string node_options;
+ if (!(flags & ProcessFlags::kDisableNodeOptionsEnv)) {
+ std::string node_options;
- if (credentials::SafeGetenv("NODE_OPTIONS", &node_options)) {
- std::vector<std::string> env_argv =
- ParseNodeOptionsEnvVar(node_options, errors);
+ if (credentials::SafeGetenv("NODE_OPTIONS", &node_options)) {
+ std::vector<std::string> env_argv =
+ ParseNodeOptionsEnvVar(node_options, errors);
- if (!errors->empty()) return 9;
+ if (!errors->empty()) return 9;
- // [0] is expected to be the program name, fill it in from the real argv.
- env_argv.insert(env_argv.begin(), argv->at(0));
+ // [0] is expected to be the program name, fill it in from the real argv.
+ env_argv.insert(env_argv.begin(), argv->at(0));
- const int exit_code = ProcessGlobalArgs(&env_argv,
- nullptr,
- errors,
- kAllowedInEnvironment);
- if (exit_code != 0) return exit_code;
+ const int exit_code = ProcessGlobalArgs(&env_argv,
+ nullptr,
+ errors,
+ kAllowedInEnvironment);
+ if (exit_code != 0) return exit_code;
+ }
}
#endif
- const int exit_code = ProcessGlobalArgs(argv,
- exec_argv,
- errors,
- kDisallowedInEnvironment);
- if (exit_code != 0) return exit_code;
+ if (!(flags & ProcessFlags::kDisableCLIOptions)) {
+ const int exit_code = ProcessGlobalArgs(argv,
+ exec_argv,
+ errors,
+ kDisallowedInEnvironment);
+ if (exit_code != 0) return exit_code;
+ }
// Set the process.title immediately after processing argv if --title is set.
if (!per_process::cli_options->title.empty())
uv_set_process_title(per_process::cli_options->title.c_str());
#if defined(NODE_HAVE_I18N_SUPPORT)
- // If the parameter isn't given, use the env variable.
- if (per_process::cli_options->icu_data_dir.empty())
- credentials::SafeGetenv("NODE_ICU_DATA",
- &per_process::cli_options->icu_data_dir);
+ if (!(flags & ProcessFlags::kNoICU)) {
+ // If the parameter isn't given, use the env variable.
+ if (per_process::cli_options->icu_data_dir.empty())
+ credentials::SafeGetenv("NODE_ICU_DATA",
+ &per_process::cli_options->icu_data_dir);
#ifdef NODE_ICU_DEFAULT_DATA_DIR
- // If neither the CLI option nor the environment variable was specified,
- // fall back to the configured default
- if (per_process::cli_options->icu_data_dir.empty()) {
- // Check whether the NODE_ICU_DEFAULT_DATA_DIR contains the right data
- // file and can be read.
- static const char full_path[] =
- NODE_ICU_DEFAULT_DATA_DIR "/" U_ICUDATA_NAME ".dat";
-
- FILE* f = fopen(full_path, "rb");
-
- if (f != nullptr) {
- fclose(f);
- per_process::cli_options->icu_data_dir = NODE_ICU_DEFAULT_DATA_DIR;
+ // If neither the CLI option nor the environment variable was specified,
+ // fall back to the configured default
+ if (per_process::cli_options->icu_data_dir.empty()) {
+ // Check whether the NODE_ICU_DEFAULT_DATA_DIR contains the right data
+ // file and can be read.
+ static const char full_path[] =
+ NODE_ICU_DEFAULT_DATA_DIR "/" U_ICUDATA_NAME ".dat";
+
+ FILE* f = fopen(full_path, "rb");
+
+ if (f != nullptr) {
+ fclose(f);
+ per_process::cli_options->icu_data_dir = NODE_ICU_DEFAULT_DATA_DIR;
+ }
}
- }
#endif // NODE_ICU_DEFAULT_DATA_DIR
- // Initialize ICU.
- // If icu_data_dir is empty here, it will load the 'minimal' data.
- if (!i18n::InitializeICUDirectory(per_process::cli_options->icu_data_dir)) {
- errors->push_back("could not initialize ICU "
- "(check NODE_ICU_DATA or --icu-data-dir parameters)\n");
- return 9;
+ // Initialize ICU.
+ // If icu_data_dir is empty here, it will load the 'minimal' data.
+ if (!i18n::InitializeICUDirectory(per_process::cli_options->icu_data_dir)) {
+ errors->push_back("could not initialize ICU "
+ "(check NODE_ICU_DATA or --icu-data-dir parameters)\n");
+ return 9;
+ }
+ per_process::metadata.versions.InitializeIntlVersions();
}
- per_process::metadata.versions.InitializeIntlVersions();
# ifndef __POSIX__
std::string tz;
@@ -956,7 +971,8 @@ InitializationResult InitializeOncePerProcess(int argc, char** argv) {
InitializationResult InitializeOncePerProcess(
int argc,
char** argv,
- InitializationSettingsFlags flags) {
+ InitializationSettingsFlags flags,
+ ProcessFlags::Flags process_flags) {
uint64_t init_flags = flags;
if (init_flags & kDefaultInitialization) {
init_flags = init_flags | kInitializeV8 | kInitOpenSSL | kRunPlatformInit;
@@ -982,8 +998,8 @@ InitializationResult InitializeOncePerProcess(
// This needs to run *before* V8::Initialize().
{
- result.exit_code =
- InitializeNodeWithArgs(&(result.args), &(result.exec_args), &errors);
+ result.exit_code = InitializeNodeWithArgs(
+ &(result.args), &(result.exec_args), &errors, process_flags);
for (const std::string& error : errors)
fprintf(stderr, "%s: %s\n", result.args.at(0).c_str(), error.c_str());
if (result.exit_code != 0) {
diff --git a/src/node.h b/src/node.h
index f34ed39397..8d9e993525 100644
--- a/src/node.h
+++ b/src/node.h
@@ -214,6 +214,20 @@ namespace node {
class IsolateData;
class Environment;
+namespace ProcessFlags {
+enum Flags : uint64_t {
+ kNoFlags = 0,
+ // Enable stdio inheritance, which is disabled by default.
+ kEnableStdioInheritance = 1 << 0,
+ // Disable reading the NODE_OPTIONS environment variable.
+ kDisableNodeOptionsEnv = 1 << 1,
+ // Do not parse CLI options.
+ kDisableCLIOptions = 1 << 2,
+ // Do not initialize ICU.
+ kNoICU = 1 << 3,
+};
+} // namespace ProcessFlags
+
// TODO(addaleax): Officially deprecate this and replace it with something
// better suited for a public embedder API.
NODE_EXTERN int Start(int argc, char* argv[]);
@@ -226,9 +240,16 @@ NODE_EXTERN int Stop(Environment* env);
// from argv, fill exec_argv, and possibly add errors resulting from parsing
// the arguments to `errors`. The return value is a suggested exit code for the
// program; If it is 0, then initializing Node.js succeeded.
-NODE_EXTERN int InitializeNodeWithArgs(std::vector<std::string>* argv,
- std::vector<std::string>* exec_argv,
- std::vector<std::string>* errors);
+NODE_EXTERN int InitializeNodeWithArgs(
+ std::vector<std::string>* argv,
+ std::vector<std::string>* exec_argv,
+ std::vector<std::string>* errors);
+// TODO(zcbenz): Turn above overloaded version into below's default argument.
+NODE_EXTERN int InitializeNodeWithArgs(
+ std::vector<std::string>* argv,
+ std::vector<std::string>* exec_argv,
+ std::vector<std::string>* errors,
+ ProcessFlags::Flags flags);
enum OptionEnvvarSettings {
kAllowedInEnvironment,
diff --git a/src/node_internals.h b/src/node_internals.h
index c996723db5..2671bec874 100644
--- a/src/node_internals.h
+++ b/src/node_internals.h
@@ -324,7 +324,8 @@ InitializationResult InitializeOncePerProcess(int argc, char** argv);
InitializationResult InitializeOncePerProcess(
int argc,
char** argv,
- InitializationSettingsFlags flags);
+ InitializationSettingsFlags flags,
+ ProcessFlags::Flags process_flags = ProcessFlags::kNoFlags);
void TearDownOncePerProcess();
void SetIsolateErrorHandlers(v8::Isolate* isolate, const IsolateSettings& s);
void SetIsolateMiscHandlers(v8::Isolate* isolate, const IsolateSettings& s);