blob: 602f0f843c72e6c270b2de8be29b243db87b4ddf [file] [log] [blame]
// Copyright 2014 The Bazel Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#include "src/main/cpp/startup_options.h"
#include <assert.h>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include "src/main/cpp/blaze_util.h"
#include "src/main/cpp/blaze_util_platform.h"
#include "src/main/cpp/util/errors.h"
#include "src/main/cpp/util/exit_code.h"
#include "src/main/cpp/util/file.h"
#include "src/main/cpp/util/logging.h"
#include "src/main/cpp/util/numbers.h"
#include "src/main/cpp/util/path.h"
#include "src/main/cpp/util/path_platform.h"
#include "src/main/cpp/util/strings.h"
#include "src/main/cpp/workspace_layout.h"
namespace blaze {
using std::string;
using std::vector;
void StartupOptions::RegisterNullaryStartupFlag(const std::string &flag_name) {
valid_nullary_startup_flags_.insert(std::string("--") + flag_name);
valid_nullary_startup_flags_.insert(std::string("--no") + flag_name);
}
void StartupOptions::RegisterUnaryStartupFlag(const std::string &flag_name) {
valid_unary_startup_flags_.insert(std::string("--") + flag_name);
}
StartupOptions::StartupOptions(const string &product_name,
const WorkspaceLayout *workspace_layout)
: product_name(product_name),
ignore_all_rc_files(false),
deep_execroot(true),
block_for_lock(true),
host_jvm_debug(false),
batch(false),
batch_cpu_scheduling(false),
io_nice_level(-1),
shutdown_on_low_sys_mem(false),
oom_more_eagerly(false),
oom_more_eagerly_threshold(100),
write_command_log(true),
watchfs(false),
fatal_event_bus_exceptions(false),
command_port(0),
connect_timeout_secs(30),
have_invocation_policy_(false),
client_debug(false),
java_logging_formatter(
"com.google.devtools.build.lib.util.SingleLineFormatter"),
expand_configs_in_place(true),
digest_function(),
idle_server_tasks(true),
original_startup_options_(std::vector<RcStartupFlag>()),
#if defined(__APPLE__)
macos_qos_class(QOS_CLASS_DEFAULT),
#endif
unlimit_coredumps(false),
incompatible_enable_execution_transition(false) {
if (blaze::IsRunningWithinTest()) {
output_root = blaze_util::MakeAbsolute(blaze::GetPathEnv("TEST_TMPDIR"));
max_idle_secs = 15;
BAZEL_LOG(USER) << "$TEST_TMPDIR defined: output root default is '"
<< output_root << "' and max_idle_secs default is '"
<< max_idle_secs << "'.";
} else {
output_root = workspace_layout->GetOutputRoot();
max_idle_secs = 3 * 3600;
BAZEL_LOG(INFO) << "output root is '" << output_root
<< "' and max_idle_secs default is '" << max_idle_secs
<< "'.";
}
#if defined(_WIN32) || defined(__CYGWIN__)
string windows_unix_root = DetectBashAndExportBazelSh();
if (!windows_unix_root.empty()) {
host_jvm_args.push_back(string("-Dbazel.windows_unix_root=") +
windows_unix_root);
}
#endif // defined(_WIN32) || defined(__CYGWIN__)
const string product_name_lower = GetLowercaseProductName();
output_user_root = blaze_util::JoinPath(
output_root, "_" + product_name_lower + "_" + GetUserName());
// IMPORTANT: Before modifying the statements below please contact a Bazel
// core team member that knows the internal procedure for adding/deprecating
// startup flags.
RegisterNullaryStartupFlag("batch");
RegisterNullaryStartupFlag("batch_cpu_scheduling");
RegisterNullaryStartupFlag("block_for_lock");
RegisterNullaryStartupFlag("client_debug");
RegisterNullaryStartupFlag("deep_execroot");
RegisterNullaryStartupFlag("expand_configs_in_place");
RegisterNullaryStartupFlag("experimental_oom_more_eagerly");
RegisterNullaryStartupFlag("fatal_event_bus_exceptions");
RegisterNullaryStartupFlag("host_jvm_debug");
RegisterNullaryStartupFlag("idle_server_tasks");
RegisterNullaryStartupFlag("incompatible_enable_execution_transition");
RegisterNullaryStartupFlag("shutdown_on_low_sys_mem");
RegisterNullaryStartupFlag("ignore_all_rc_files");
RegisterNullaryStartupFlag("unlimit_coredumps");
RegisterNullaryStartupFlag("watchfs");
RegisterNullaryStartupFlag("write_command_log");
RegisterUnaryStartupFlag("command_port");
RegisterUnaryStartupFlag("connect_timeout_secs");
RegisterUnaryStartupFlag("digest_function");
RegisterUnaryStartupFlag("experimental_oom_more_eagerly_threshold");
RegisterUnaryStartupFlag("server_javabase");
RegisterUnaryStartupFlag("host_jvm_args");
RegisterUnaryStartupFlag("host_jvm_profile");
RegisterUnaryStartupFlag("invocation_policy");
RegisterUnaryStartupFlag("io_nice_level");
RegisterUnaryStartupFlag("install_base");
RegisterUnaryStartupFlag("macos_qos_class");
RegisterUnaryStartupFlag("max_idle_secs");
RegisterUnaryStartupFlag("output_base");
RegisterUnaryStartupFlag("output_user_root");
RegisterUnaryStartupFlag("server_jvm_out");
}
StartupOptions::~StartupOptions() {}
string StartupOptions::GetLowercaseProductName() const {
string lowercase_product_name = product_name;
blaze_util::ToLower(&lowercase_product_name);
return lowercase_product_name;
}
bool StartupOptions::IsUnary(const string &arg) const {
std::string::size_type i = arg.find_first_of('=');
if (i == std::string::npos) {
return valid_unary_startup_flags_.find(arg) !=
valid_unary_startup_flags_.end();
} else {
return valid_unary_startup_flags_.find(arg.substr(0, i)) !=
valid_unary_startup_flags_.end();
}
}
bool StartupOptions::IsNullary(const string &arg) const {
std::string::size_type i = arg.find_first_of('=');
if (i == std::string::npos) {
return valid_nullary_startup_flags_.find(arg) !=
valid_nullary_startup_flags_.end();
} else {
std::string f = arg.substr(0, i);
if (valid_nullary_startup_flags_.find(f) !=
valid_nullary_startup_flags_.end()) {
BAZEL_DIE(blaze_exit_code::BAD_ARGV)
<< "In argument '" << arg << "': option '" << f
<< "' does not take a value.";
}
return false;
}
}
void StartupOptions::AddExtraOptions(vector<string> *result) const {
if (incompatible_enable_execution_transition) {
result->push_back("--incompatible_enable_execution_transition");
} else {
result->push_back("--noincompatible_enable_execution_transition");
}
}
blaze_exit_code::ExitCode StartupOptions::ProcessArg(
const string &argstr, const string &next_argstr, const string &rcfile,
bool *is_space_separated, string *error) {
// We have to parse a specific option syntax, so GNU getopts won't do. All
// options begin with "--" or "-". Values are given together with the option
// delimited by '=' or in the next option.
const char* arg = argstr.c_str();
const char* next_arg = next_argstr.empty() ? NULL : next_argstr.c_str();
const char* value = NULL;
if ((value = GetUnaryOption(arg, next_arg, "--output_base")) != NULL) {
output_base = blaze::AbsolutePathFromFlag(value);
option_sources["output_base"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg,
"--install_base")) != NULL) {
install_base = blaze::AbsolutePathFromFlag(value);
option_sources["install_base"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg,
"--output_user_root")) != NULL) {
output_user_root = blaze::AbsolutePathFromFlag(value);
option_sources["output_user_root"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg,
"--server_jvm_out")) != NULL) {
server_jvm_out = blaze::AbsolutePathFromFlag(value);
option_sources["server_jvm_out"] = rcfile;
} else if (GetNullaryOption(arg, "--deep_execroot")) {
deep_execroot = true;
option_sources["deep_execroot"] = rcfile;
} else if (GetNullaryOption(arg, "--nodeep_execroot")) {
deep_execroot = false;
option_sources["deep_execroot"] = rcfile;
} else if (GetNullaryOption(arg, "--block_for_lock")) {
block_for_lock = true;
option_sources["block_for_lock"] = rcfile;
} else if (GetNullaryOption(arg, "--noblock_for_lock")) {
block_for_lock = false;
option_sources["block_for_lock"] = rcfile;
} else if (GetNullaryOption(arg, "--host_jvm_debug")) {
host_jvm_debug = true;
option_sources["host_jvm_debug"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--host_jvm_profile")) !=
NULL) {
host_jvm_profile = value;
option_sources["host_jvm_profile"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--server_javabase")) !=
NULL) {
// TODO(bazel-team): Consider examining the javabase and re-execing in case
// of architecture mismatch.
explicit_server_javabase_ = blaze::AbsolutePathFromFlag(value);
option_sources["server_javabase"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--host_jvm_args")) !=
NULL) {
host_jvm_args.push_back(value);
option_sources["host_jvm_args"] = rcfile; // NB: This is incorrect
} else if (GetNullaryOption(arg, "--ignore_all_rc_files")) {
if (!rcfile.empty()) {
*error = "Can't specify --ignore_all_rc_files in an rc file.";
return blaze_exit_code::BAD_ARGV;
}
ignore_all_rc_files = true;
option_sources["ignore_all_rc_files"] = rcfile;
} else if (GetNullaryOption(arg, "--noignore_all_rc_files")) {
if (!rcfile.empty()) {
*error = "Can't specify --noignore_all_rc_files in an rc file.";
return blaze_exit_code::BAD_ARGV;
}
ignore_all_rc_files = false;
option_sources["ignore_all_rc_files"] = rcfile;
} else if (GetNullaryOption(arg, "--batch")) {
batch = true;
option_sources["batch"] = rcfile;
} else if (GetNullaryOption(arg, "--nobatch")) {
batch = false;
option_sources["batch"] = rcfile;
} else if (GetNullaryOption(arg, "--batch_cpu_scheduling")) {
batch_cpu_scheduling = true;
option_sources["batch_cpu_scheduling"] = rcfile;
} else if (GetNullaryOption(arg, "--nobatch_cpu_scheduling")) {
batch_cpu_scheduling = false;
option_sources["batch_cpu_scheduling"] = rcfile;
} else if (GetNullaryOption(arg, "--fatal_event_bus_exceptions")) {
fatal_event_bus_exceptions = true;
option_sources["fatal_event_bus_exceptions"] = rcfile;
} else if (GetNullaryOption(arg, "--nofatal_event_bus_exceptions")) {
fatal_event_bus_exceptions = false;
option_sources["fatal_event_bus_exceptions"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--io_nice_level")) !=
NULL) {
if (!blaze_util::safe_strto32(value, &io_nice_level) ||
io_nice_level > 7) {
blaze_util::StringPrintf(error,
"Invalid argument to --io_nice_level: '%s'. Must not exceed 7.",
value);
return blaze_exit_code::BAD_ARGV;
}
option_sources["io_nice_level"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--max_idle_secs")) !=
NULL) {
if (!blaze_util::safe_strto32(value, &max_idle_secs) ||
max_idle_secs < 0) {
blaze_util::StringPrintf(error,
"Invalid argument to --max_idle_secs: '%s'.", value);
return blaze_exit_code::BAD_ARGV;
}
option_sources["max_idle_secs"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--macos_qos_class")) !=
NULL) {
// We parse the value of this flag on all platforms even if it is
// macOS-specific to ensure that rc files mentioning it are valid.
if (strcmp(value, "user-interactive") == 0) {
#if defined(__APPLE__)
macos_qos_class = QOS_CLASS_USER_INTERACTIVE;
#endif
} else if (strcmp(value, "user-initiated") == 0) {
#if defined(__APPLE__)
macos_qos_class = QOS_CLASS_USER_INITIATED;
#endif
} else if (strcmp(value, "default") == 0) {
#if defined(__APPLE__)
macos_qos_class = QOS_CLASS_DEFAULT;
#endif
} else if (strcmp(value, "utility") == 0) {
#if defined(__APPLE__)
macos_qos_class = QOS_CLASS_UTILITY;
#endif
} else if (strcmp(value, "background") == 0) {
#if defined(__APPLE__)
macos_qos_class = QOS_CLASS_BACKGROUND;
#endif
} else {
blaze_util::StringPrintf(
error, "Invalid argument to --macos_qos_class: '%s'.", value);
return blaze_exit_code::BAD_ARGV;
}
option_sources["macos_qos_class"] = rcfile;
} else if (GetNullaryOption(arg, "--shutdown_on_low_sys_mem")) {
shutdown_on_low_sys_mem = true;
option_sources["shutdown_on_low_sys_mem"] = rcfile;
} else if (GetNullaryOption(arg, "--noshutdown_on_low_sys_mem")) {
shutdown_on_low_sys_mem = false;
option_sources["shutdown_on_low_sys_mem"] = rcfile;
} else if (GetNullaryOption(arg, "--experimental_oom_more_eagerly")) {
oom_more_eagerly = true;
option_sources["experimental_oom_more_eagerly"] = rcfile;
} else if (GetNullaryOption(arg, "--noexperimental_oom_more_eagerly")) {
oom_more_eagerly = false;
option_sources["experimental_oom_more_eagerly"] = rcfile;
} else if ((value = GetUnaryOption(
arg, next_arg,
"--experimental_oom_more_eagerly_threshold")) != NULL) {
if (!blaze_util::safe_strto32(value, &oom_more_eagerly_threshold) ||
oom_more_eagerly_threshold < 0) {
blaze_util::StringPrintf(error,
"Invalid argument to "
"--experimental_oom_more_eagerly_threshold: "
"'%s'.",
value);
return blaze_exit_code::BAD_ARGV;
}
option_sources["experimental_oom_more_eagerly_threshold"] = rcfile;
} else if (GetNullaryOption(arg, "--write_command_log")) {
write_command_log = true;
option_sources["write_command_log"] = rcfile;
} else if (GetNullaryOption(arg, "--nowrite_command_log")) {
write_command_log = false;
option_sources["write_command_log"] = rcfile;
} else if (GetNullaryOption(arg, "--watchfs")) {
watchfs = true;
option_sources["watchfs"] = rcfile;
} else if (GetNullaryOption(arg, "--nowatchfs")) {
watchfs = false;
option_sources["watchfs"] = rcfile;
} else if (GetNullaryOption(arg, "--client_debug")) {
client_debug = true;
option_sources["client_debug"] = rcfile;
} else if (GetNullaryOption(arg, "--noclient_debug")) {
client_debug = false;
option_sources["client_debug"] = rcfile;
} else if (GetNullaryOption(arg, "--expand_configs_in_place")) {
expand_configs_in_place = true;
option_sources["expand_configs_in_place"] = rcfile;
} else if (GetNullaryOption(arg, "--noexpand_configs_in_place")) {
expand_configs_in_place = false;
option_sources["expand_configs_in_place"] = rcfile;
} else if (GetNullaryOption(arg, "--idle_server_tasks")) {
idle_server_tasks = true;
option_sources["idle_server_tasks"] = rcfile;
} else if (GetNullaryOption(arg, "--noidle_server_tasks")) {
idle_server_tasks = false;
option_sources["idle_server_tasks"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg,
"--connect_timeout_secs")) != NULL) {
if (!blaze_util::safe_strto32(value, &connect_timeout_secs) ||
connect_timeout_secs < 1 || connect_timeout_secs > 120) {
blaze_util::StringPrintf(error,
"Invalid argument to --connect_timeout_secs: '%s'.\n"
"Must be an integer between 1 and 120.\n",
value);
return blaze_exit_code::BAD_ARGV;
}
option_sources["connect_timeout_secs"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--digest_function")) !=
NULL) {
digest_function = value;
option_sources["digest_function"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--command_port")) !=
NULL) {
if (!blaze_util::safe_strto32(value, &command_port) ||
command_port < 0 || command_port > 65535) {
blaze_util::StringPrintf(error,
"Invalid argument to --command_port: '%s'.\n"
"Must be a valid port number or 0.\n",
value);
return blaze_exit_code::BAD_ARGV;
}
option_sources["command_port"] = rcfile;
} else if ((value = GetUnaryOption(arg, next_arg, "--invocation_policy")) !=
NULL) {
if (!have_invocation_policy_) {
have_invocation_policy_ = true;
invocation_policy = value;
option_sources["invocation_policy"] = rcfile;
} else {
*error = "The startup flag --invocation_policy cannot be specified "
"multiple times.";
return blaze_exit_code::BAD_ARGV;
}
} else if (GetNullaryOption(arg, "--unlimit_coredumps")) {
unlimit_coredumps = true;
option_sources["unlimit_coredumps"] = rcfile;
} else if (GetNullaryOption(arg, "--nounlimit_coredumps")) {
unlimit_coredumps = false;
option_sources["unlimit_coredumps"] = rcfile;
} else if (GetNullaryOption(arg,
"--incompatible_enable_execution_transition")) {
incompatible_enable_execution_transition = true;
option_sources["incompatible_enable_execution_transition"] = rcfile;
} else if (GetNullaryOption(arg,
"--noincompatible_enable_execution_transition")) {
incompatible_enable_execution_transition = false;
option_sources["incompatible_enable_execution_transition"] = rcfile;
} else {
bool extra_argument_processed;
blaze_exit_code::ExitCode process_extra_arg_exit_code = ProcessArgExtra(
arg, next_arg, rcfile, &value, &extra_argument_processed, error);
if (process_extra_arg_exit_code != blaze_exit_code::SUCCESS) {
return process_extra_arg_exit_code;
}
if (!extra_argument_processed) {
blaze_util::StringPrintf(
error,
"Unknown startup option: '%s'.\n"
" For more info, run '%s help startup_options'.",
arg, GetLowercaseProductName().c_str());
return blaze_exit_code::BAD_ARGV;
}
}
*is_space_separated = ((value == next_arg) && (value != NULL));
return blaze_exit_code::SUCCESS;
}
blaze_exit_code::ExitCode StartupOptions::ProcessArgs(
const std::vector<RcStartupFlag>& rcstartup_flags,
std::string *error) {
std::vector<RcStartupFlag>::size_type i = 0;
while (i < rcstartup_flags.size()) {
bool is_space_separated = false;
const std::string next_value =
(i == rcstartup_flags.size() - 1) ? "" : rcstartup_flags[i + 1].value;
const blaze_exit_code::ExitCode process_arg_exit_code =
ProcessArg(rcstartup_flags[i].value, next_value,
rcstartup_flags[i].source, &is_space_separated, error);
// Store the provided option in --flag(=value)? form. Store these before
// propagating any error code, since we want to have the correct
// information for the output. The fact that the options aren't parseable
// doesn't matter for this step.
if (is_space_separated) {
const std::string combined_value =
rcstartup_flags[i].value + "=" + next_value;
original_startup_options_.push_back(
RcStartupFlag(rcstartup_flags[i].source, combined_value));
i += 2;
} else {
original_startup_options_.push_back(
RcStartupFlag(rcstartup_flags[i].source, rcstartup_flags[i].value));
i++;
}
if (process_arg_exit_code != blaze_exit_code::SUCCESS) {
return process_arg_exit_code;
}
}
return blaze_exit_code::SUCCESS;
}
string StartupOptions::GetSystemJavabase() const {
return blaze::GetSystemJavabase();
}
string StartupOptions::GetEmbeddedJavabase() const {
string bundled_jre_path = blaze_util::JoinPath(
install_base, "_embedded_binaries/embedded_tools/jdk");
if (blaze_util::CanExecuteFile(blaze_util::JoinPath(
bundled_jre_path, GetJavaBinaryUnderJavabase()))) {
return bundled_jre_path;
}
return "";
}
string StartupOptions::GetServerJavabase() const {
// 1) Allow overriding the server_javabase via --server_javabase.
if (!explicit_server_javabase_.empty()) {
return explicit_server_javabase_;
}
if (default_server_javabase_.empty()) {
string bundled_jre_path = GetEmbeddedJavabase();
if (!bundled_jre_path.empty()) {
// 2) Use a bundled JVM if we have one.
default_server_javabase_ = bundled_jre_path;
} else {
// 3) Otherwise fall back to using the default system JVM.
string system_javabase = GetSystemJavabase();
if (system_javabase.empty()) {
BAZEL_DIE(blaze_exit_code::LOCAL_ENVIRONMENTAL_ERROR)
<< "Could not find system javabase. Ensure JAVA_HOME is set, or "
"javac is on your PATH.";
}
default_server_javabase_ = system_javabase;
}
}
return default_server_javabase_;
}
string StartupOptions::GetExplicitServerJavabase() const {
return explicit_server_javabase_;
}
string StartupOptions::GetJvm() const {
string java_program =
blaze_util::JoinPath(GetServerJavabase(), GetJavaBinaryUnderJavabase());
if (!blaze_util::CanExecuteFile(java_program)) {
if (!blaze_util::PathExists(java_program)) {
BAZEL_LOG(ERROR) << "Couldn't find java at '" << java_program << "'.";
} else {
BAZEL_LOG(ERROR) << "Java at '" << java_program
<< "' exists but is not executable: "
<< blaze_util::GetLastErrorString();
}
exit(1);
}
// If the full JDK is installed
string jdk_rt_jar =
blaze_util::JoinPath(GetServerJavabase(), "jre/lib/rt.jar");
// If just the JRE is installed
string jre_rt_jar = blaze_util::JoinPath(GetServerJavabase(), "lib/rt.jar");
// rt.jar does not exist in java 9+ so check for java instead
string jre_java = blaze_util::JoinPath(GetServerJavabase(), "bin/java");
string jre_java_exe =
blaze_util::JoinPath(GetServerJavabase(), "bin/java.exe");
if (blaze_util::CanReadFile(jdk_rt_jar) ||
blaze_util::CanReadFile(jre_rt_jar) ||
blaze_util::CanReadFile(jre_java) ||
blaze_util::CanReadFile(jre_java_exe)) {
return java_program;
}
BAZEL_LOG(ERROR) << "Problem with java installation: couldn't find/access "
"rt.jar or java in "
<< GetServerJavabase();
exit(1);
}
string StartupOptions::GetExe(const string &jvm, const string &jar_path) const {
return jvm;
}
void StartupOptions::AddJVMArgumentPrefix(const string &javabase,
std::vector<string> *result) const {
}
void StartupOptions::AddJVMArgumentSuffix(const string &real_install_dir,
const string &jar_path,
std::vector<string> *result) const {
result->push_back("-jar");
result->push_back(blaze_util::PathAsJvmFlag(
blaze_util::JoinPath(real_install_dir, jar_path)));
}
blaze_exit_code::ExitCode StartupOptions::AddJVMArguments(
const string &server_javabase, std::vector<string> *result,
const vector<string> &user_options, string *error) const {
AddJVMLoggingArguments(result);
// Disable the JVM's own unlimiting of file descriptors. We do this
// ourselves in blaze.cc so we want our setting to propagate to the JVM.
//
// The reason to do this is that the JVM's unlimiting is suboptimal on
// macOS. Under that platform, the JVM limits the open file descriptors
// to the OPEN_MAX constant... which is much lower than the per-process
// kernel allowed limit of kern.maxfilesperproc (which is what we set
// ourselves to).
result->push_back("-XX:-MaxFDLimit");
return AddJVMMemoryArguments(server_javabase, result, user_options, error);
}
static std::string GetSimpleLogHandlerProps(
const std::string &java_log, const std::string &java_logging_formatter) {
return "handlers=com.google.devtools.build.lib.util.SimpleLogHandler\n"
".level=INFO\n"
"com.google.devtools.build.lib.util.SimpleLogHandler.level=INFO\n"
"com.google.devtools.build.lib.util.SimpleLogHandler.prefix=" +
java_log +
"\n"
"com.google.devtools.build.lib.util.SimpleLogHandler.limit=1024000\n"
"com.google.devtools.build.lib.util.SimpleLogHandler.total_limit="
"20971520\n" // 20 MB.
"com.google.devtools.build.lib.util.SimpleLogHandler.formatter=" +
java_logging_formatter + "\n";
}
void StartupOptions::AddJVMLoggingArguments(std::vector<string> *result) const {
// Configure logging
const string propFile = blaze_util::PathAsJvmFlag(
blaze_util::JoinPath(output_base, "javalog.properties"));
const string java_log(
blaze_util::PathAsJvmFlag(blaze_util::JoinPath(output_base, "java.log")));
const std::string loggingProps =
GetSimpleLogHandlerProps(java_log, java_logging_formatter);
if (!blaze_util::WriteFile(loggingProps, propFile)) {
perror(("Couldn't write logging file " + propFile).c_str());
} else {
result->push_back("-Djava.util.logging.config.file=" + propFile);
result->push_back(
"-Dcom.google.devtools.build.lib.util.LogHandlerQuerier.class="
"com.google.devtools.build.lib.util.SimpleLogHandler$HandlerQuerier");
}
}
blaze_exit_code::ExitCode StartupOptions::AddJVMMemoryArguments(
const string &, std::vector<string> *, const vector<string> &,
string *) const {
return blaze_exit_code::SUCCESS;
}
} // namespace blaze