aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2022-02-21 06:36:52 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2022-02-21 06:36:52 +0200
commit9b5acba21213c2bf87d92b0a12f4d41283a13ae3 (patch)
treefef321b943267bf7022f5a762310e943e1bf007b
parent5bc95a2ecdce512d673b3f77c593105230da28fd (diff)
Complete build system command line parsing/processing
-rw-r--r--bpkg/bpkg.cxx110
-rw-r--r--bpkg/package-skeleton.cxx39
-rw-r--r--bpkg/package-skeleton.hxx1
3 files changed, 96 insertions, 54 deletions
diff --git a/bpkg/bpkg.cxx b/bpkg/bpkg.cxx
index 137d823..c85372e 100644
--- a/bpkg/bpkg.cxx
+++ b/bpkg/bpkg.cxx
@@ -21,6 +21,9 @@
#include <libbuild2/scheduler.hxx>
#include <libbuild2/file-cache.hxx>
+#include <libbuild2/cmdline.hxx>
+#include <libbuild2/b-options.hxx>
+
#include <libbuild2/dist/init.hxx>
#include <libbuild2/test/init.hxx>
#include <libbuild2/config/init.hxx>
@@ -100,6 +103,7 @@ namespace bpkg
std::terminate ();
}
+ strings build2_cmd_vars;
build2::scheduler build2_sched;
build2::global_mutexes build2_mutexes;
build2::file_cache build2_fcache;
@@ -426,30 +430,66 @@ init (const char* argv0,
if (bsys)
try
{
- // For now we use the same verbosity as us (equivalent to start_b() with
- // verb_b::normal).
+ using namespace build2;
+ using build2::fail;
+ using build2::endf;
+
+ build2::tracer trace ("init");
+
+ // Parse --build-option values as the build2 driver command line.
//
- build2::init_diag (verb,
- false /* silent */,
- (o.progress () ? optional<bool> (true) :
- o.no_progress () ? optional<bool> (false) :
- nullopt),
- false /* no_lines */,
- false /* no_columns */,
- stderr_term);
-
- build2::init (&build2_terminate,
- argv0,
- //
- // @@ Should we try to parse --build-option and extract
- // these (having config_* is plausible)? Also
- // --file-cache below.
- //
- nullopt /* mtime_check */,
- nullopt /* config_sub */,
- nullopt /* config_guess */);
-
- using build2::load_builtin_module;
+ // With things like verbosity, progress, etc., we use values from
+ // --build-option if specified, falling back to equivalent bpkg values
+ // otherwise.
+ //
+ build2::options bo;
+ cmdline bc;
+ {
+ small_vector<char*, 1> argv {const_cast<char*> (argv0)};
+
+ if (size_t n = o.build_option ().size ())
+ {
+ argv.reserve (n + 1);
+
+ for (const string& a: o.build_option ())
+ argv.push_back (const_cast<char*> (a.c_str ()));
+ }
+
+ // Note that this function also parses the default options files and
+ // gets/sets the relevant environment variables.
+ //
+ // For now we use the same default verbosity as us (equivalent to
+ // start_b() with verb_b::normal).
+ //
+ bc = parse_cmdline (trace,
+ static_cast<int> (argv.size ()), argv.data (),
+ bo,
+ bpkg::verb,
+ o.jobs_specified () ? o.jobs () : 0);
+
+ if (!bc.buildspec.empty ())
+ fail << "argument specified with --build-option";
+
+ if (bo.help () || bo.version ())
+ fail << "--help or --version specified with --build-option";
+ }
+
+ build2_cmd_vars = move (bc.cmd_vars);
+
+ init_diag (bc.verbosity,
+ bo.silent (),
+ (bc.progress ? bc.progress :
+ o.progress () ? optional<bool> (true) :
+ o.no_progress () ? optional<bool> (false) : nullopt),
+ bo.no_line (),
+ bo.no_column (),
+ bpkg::stderr_term);
+
+ init (&build2_terminate,
+ argv0,
+ bc.mtime_check,
+ bc.config_sub,
+ bc.config_guess);
load_builtin_module (&build2::config::build2_config_load);
load_builtin_module (&build2::dist::build2_dist_load);
@@ -472,25 +512,15 @@ init (const char* argv0,
// relatively cheap. The module building logic will then re-tune it to
// parallel if and when necessary.
//
- // @@ TODO: options (scheduler values).
- //
- size_t jobs (0);
-
- if (jobs == 0)
- jobs = build2::scheduler::hardware_concurrency ();
-
- if (jobs == 0)
- jobs = 1;
-
- build2_sched.startup (1 /* max_active */,
- 1 /* init_active */,
- 0 /* max_jobs */,
- 0 /* queue_depth */,
- nullopt /* max_stack */,
- jobs /* orig_max_active */);
+ build2_sched.startup (1 /* max_active */,
+ 1 /* init_active */,
+ bc.max_jobs,
+ bc.jobs * bo.queue_depth (),
+ bc.max_stack,
+ bc.jobs);
build2_mutexes.init (build2_sched.shard_size ());
- build2_fcache.init (true);
+ build2_fcache.init (bc.fcache_compress);
}
catch (const build2::failed&)
{
diff --git a/bpkg/package-skeleton.cxx b/bpkg/package-skeleton.cxx
index 9cffef1..76bd816 100644
--- a/bpkg/package-skeleton.cxx
+++ b/bpkg/package-skeleton.cxx
@@ -31,6 +31,7 @@ namespace bpkg
{
// These are defined in bpkg.cxx and initialized in main().
//
+ extern strings build2_cmd_vars;
extern build2::scheduler build2_sched;
extern build2::global_mutexes build2_mutexes;
extern build2::file_cache build2_fcache;
@@ -59,6 +60,7 @@ namespace bpkg
created_ = v.created_;
ctx_ = move (v.ctx_);
rs_ = v.rs_;
+ cmd_vars_ = move (v.cmd_vars_);
reflect_names_ = move (v.reflect_names_);
reflect_vars_ = move (v.reflect_vars_);
reflect_frag_ = move (v.reflect_frag_);
@@ -78,6 +80,7 @@ namespace bpkg
src_root_ (v.src_root_),
out_root_ (v.out_root_),
created_ (v.created_),
+ cmd_vars_ (v.cmd_vars_),
reflect_names_ (v.reflect_names_),
reflect_vars_ (v.reflect_vars_),
reflect_frag_ (v.reflect_frag_)
@@ -720,22 +723,30 @@ namespace bpkg
// Create build context.
//
- // @@ BUILD2_VAR_OVR, environment/default options files? E.g., !config
- // to find module... Can't we make it reusable in build2?
- //
- // @@ What is our story about build system modules? It seems we will
- // only support built-in and standard pre-installed modules here
- // (otherwise we would need to build all the module dependencies
- // before we can evaluate any of this). Which means they cannot be
- // built except during development. Maybe start parallel scheduler
- // if dev build? But is it not possible someone will use installed
- // bpkg to develop a module? Why don't we just start a parallel
- // scheduler always (though that would be wasted overhead most of
- // the time)? Or maybe provide a command line option?
-
// We can reasonably assume reflect cannot have global or absolute scope
// variable overrides so we don't need to pass them to context.
+
+ // Merge variable overrides (note that the order is important).
//
+ strings* cmd_vars;
+ {
+ strings& v1 (build2_cmd_vars);
+ strings& v2 (config_vars_);
+
+ cmd_vars = (v2.empty () ? &v1 : v1.empty () ? &v2 : nullptr);
+
+ if (cmd_vars == nullptr)
+ {
+ if (cmd_vars_.empty ()) // Cached.
+ {
+ cmd_vars_.reserve (v1.size () + v2.size ());
+ cmd_vars_.assign (v1.begin (), v1.end ());
+ cmd_vars_.insert (cmd_vars_.end (), v2.begin (), v2.end ());
+ }
+
+ cmd_vars = &cmd_vars_;
+ }
+ }
ctx_.reset (
new context (build2_sched,
@@ -745,7 +756,7 @@ namespace bpkg
false /* no_external_modules */,
false /* dry_run */, // Shouldn't matter.
false /* keep_going */, // Shouldnt' matter.
- config_vars_));
+ *cmd_vars));
context& ctx (*ctx_);
diff --git a/bpkg/package-skeleton.hxx b/bpkg/package-skeleton.hxx
index c4c59cc..0b573e4 100644
--- a/bpkg/package-skeleton.hxx
+++ b/bpkg/package-skeleton.hxx
@@ -100,6 +100,7 @@ namespace bpkg
bool created_ = false;
unique_ptr<build2::context> ctx_;
build2::scope* rs_ = nullptr;
+ strings cmd_vars_; // Storage for merged build2_cmd_vars and config_vars_.
strings reflect_names_; // Reflect configuration variable names.
strings reflect_vars_; // Reflect configuration variable overrides.