From 448125cb7b1f04813438332d8bbd378c761db7d4 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Mon, 28 Mar 2022 21:20:50 -0700 Subject: [PATCH 01/39] Update args.rst --- docs/source/user_api/args.rst | 43 +++++++++++++++++++++++------------ 1 file changed, 29 insertions(+), 14 deletions(-) diff --git a/docs/source/user_api/args.rst b/docs/source/user_api/args.rst index a0c8d482..0786e917 100644 --- a/docs/source/user_api/args.rst +++ b/docs/source/user_api/args.rst @@ -8,40 +8,55 @@ args.h .. doxygenclass:: buildcc::Args::Instance +.. doxygenstruct:: buildcc::ArgCustom + .. doxygenstruct:: buildcc::ArgToolchainState .. doxygenstruct:: buildcc::ArgToolchain +.. doxygenstruct:: buildcc::ArgTarget + Example --------- .. code-block:: cpp :linenos: + using namespace buildcc; + + struct CustomData : ArgCustom { + void Add(CLI::App & app) override { + // setup your app from data1, data2, data3, data... + // NOTE: The Add method should not be invoked by the user + // NOTE: The Add method is only expected to be invoked once, not multiple times. + } + + std::string data1; + int data2; + float data3; + // etc + }; + int main(int argc, char ** argv) { - Args args; ArgToolchain arg_gcc_toolchain; - args.AddToolchain("gcc", "Generic GCC toolchain", arg_gcc_toolchain); - - // TODO, Add ArgTarget example (Currently incomplete) - args.Parse(argc, argv); + ArgCustomData custom_data; + Args::Init() + .AddToolchain("gcc", "Generic GCC toolchain", arg_gcc_toolchain) + .AddCustomCallback([](CLI::App &app) {}); + .AddCustomData(custom_data); + .Parse(argc, argv); // Root - args.GetProjectRootDir(); // Contains ``root_dir`` value - args.GetProjectBuildDir(); // Contains ``build_dir`` value - args.GetLogLevel(); // Contains ``loglevel`` enum - args.Clean(); // Contains ``clean`` value + Args::GetProjectRootDir(); // Contains ``root_dir`` value + Args::GetProjectBuildDir(); // Contains ``build_dir`` value + Args::GetLogLevel(); // Contains ``loglevel`` enum + Args::Clean(); // Contains ``clean`` value // Toolchain // .build, .test arg_gcc_toolchain.state; // .id, .name, .asm_compiler, .c_compiler, .cpp_compiler, .archiver, .linker -> BaseToolchain BaseToolchain gcc_toolchain = arg_gcc_toolchain.ConstructToolchain(); - - // Underlying CLI11 library - auto & app = args.Ref(); - const auto & app = args.ConstRef(); - return 0; } From 363d3ff6a311497ab9965b6c2fb376b8154b371c Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Mon, 28 Mar 2022 23:38:15 -0700 Subject: [PATCH 02/39] Updated Args --- buildcc/lib/args/include/args/args.h | 4 +++- buildcc/lib/args/mock/parse.cpp | 2 +- buildcc/lib/args/src/args.cpp | 30 +++++++++++++++++----------- buildcc/lib/args/src/parse.cpp | 2 +- 4 files changed, 23 insertions(+), 15 deletions(-) diff --git a/buildcc/lib/args/include/args/args.h b/buildcc/lib/args/include/args/args.h index f26e006d..f3aab1ea 100644 --- a/buildcc/lib/args/include/args/args.h +++ b/buildcc/lib/args/include/args/args.h @@ -151,6 +151,7 @@ class Args { static void Deinit(); // Getters + static bool IsParsed(); static bool Clean(); static env::LogLevel GetLogLevel(); @@ -159,7 +160,8 @@ class Args { private: static void RootArgs(); - static CLI::App &Ref(); + static Internal &RefInternal(); + static CLI::App &RefApp(); private: static std::unique_ptr internal_; diff --git a/buildcc/lib/args/mock/parse.cpp b/buildcc/lib/args/mock/parse.cpp index 53213201..db3a1c6f 100644 --- a/buildcc/lib/args/mock/parse.cpp +++ b/buildcc/lib/args/mock/parse.cpp @@ -6,7 +6,7 @@ namespace buildcc { void Args::Instance::Parse(int argc, const char *const *argv) { try { - Ref().parse(argc, argv); + RefApp().parse(argc, argv); } catch (const CLI::ParseError &e) { env::assert_fatal(e.what()); } diff --git a/buildcc/lib/args/src/args.cpp b/buildcc/lib/args/src/args.cpp index 378bd7d4..f257af9f 100644 --- a/buildcc/lib/args/src/args.cpp +++ b/buildcc/lib/args/src/args.cpp @@ -18,6 +18,10 @@ namespace { +// Error messages +constexpr const char *const kArgsNotInit = + "Initialize Args using the Args::Init API"; + // Groups constexpr const char *const kRootGroup = "Root"; @@ -99,9 +103,10 @@ std::unique_ptr Args::internal_; Args::Instance &Args::Init() { if (!internal_) { internal_ = std::make_unique(); + auto &app = RefApp(); internal_->toolchain = - Ref().add_subcommand(kToolchainSubcommand, kToolchainDesc); - internal_->target = Ref().add_subcommand(kTargetSubcommand, kTargetDesc); + app.add_subcommand(kToolchainSubcommand, kToolchainDesc); + internal_->target = app.add_subcommand(kTargetSubcommand, kTargetDesc); RootArgs(); } return internal_->instance; @@ -109,6 +114,7 @@ Args::Instance &Args::Init() { void Args::Deinit() { internal_.reset(nullptr); } +bool Args::IsParsed() { return RefApp().parsed(); } bool Args::Clean() { return clean_; } env::LogLevel Args::GetLogLevel() { return loglevel_; } @@ -118,7 +124,7 @@ const fs::path &Args::GetProjectBuildDir() { return project_build_dir_; } // Private void Args::RootArgs() { - auto &app = Ref(); + auto &app = RefApp(); app.set_help_all_flag(kHelpAllParam, kHelpAllDesc); app.set_config(kConfigParam, "", kConfigDesc)->expected(kMinFiles, kMaxFiles); @@ -137,7 +143,11 @@ void Args::RootArgs() { ->required(); } -CLI::App &Args::Ref() { return internal_->app; } +Args::Internal &Args::RefInternal() { + env::assert_fatal(internal_ != nullptr, kArgsNotInit); + return *internal_; +} +CLI::App &Args::RefApp() { return RefInternal().app; } // Args::Instance @@ -151,9 +161,7 @@ Args::Instance &Args::Instance::AddToolchain(const std::string &name, const std::string &description, ArgToolchain &out, const ArgToolchain &initial) { - CLI::App *toolchain = internal_->toolchain; - env::assert_fatal(toolchain != nullptr, - "Initialize Args using the Args::Init API"); + CLI::App *toolchain = RefInternal().toolchain; CLI::App *t_user = toolchain->add_subcommand(name, description)->group(kToolchainGroup); t_user->add_flag(kToolchainBuildParam, out.state.build); @@ -186,9 +194,7 @@ Args::Instance &Args::Instance::AddTarget(const std::string &name, const std::string &description, ArgTarget &out, const ArgTarget &initial) { - CLI::App *target = internal_->target; - env::assert_fatal(target != nullptr, - "Initialize Args using the Args::Init API"); + CLI::App *target = RefInternal().target; CLI::App *targetuser = target->add_subcommand(name, description)->group(kTargetGroup); targetuser->add_option(kTargetCompileCommandParam, out.compile_command) @@ -200,13 +206,13 @@ Args::Instance &Args::Instance::AddTarget(const std::string &name, Args::Instance &Args::Instance::AddCustomCallback( const std::function &add_cb) { - auto &app = Ref(); + auto &app = RefApp(); add_cb(app); return *this; } Args::Instance &Args::Instance::AddCustomData(ArgCustom &data) { - auto &app = Ref(); + auto &app = RefApp(); data.Add(app); return *this; } diff --git a/buildcc/lib/args/src/parse.cpp b/buildcc/lib/args/src/parse.cpp index bbb6b745..0d2aa186 100644 --- a/buildcc/lib/args/src/parse.cpp +++ b/buildcc/lib/args/src/parse.cpp @@ -19,7 +19,7 @@ namespace buildcc { void Args::Instance::Parse(int argc, const char *const *argv) { - auto &app = Ref(); + auto &app = RefApp(); try { app.parse(argc, argv); } catch (const CLI::ParseError &e) { From d78b3799d278c7ad8f7b1b5faa2042e99d9c6076 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Mon, 28 Mar 2022 23:55:25 -0700 Subject: [PATCH 03/39] Updated Args bool APIs --- buildcc/lib/args/include/args/args.h | 1 + buildcc/lib/args/src/args.cpp | 1 + buildcc/lib/args/test/test_args.cpp | 5 +++++ 3 files changed, 7 insertions(+) diff --git a/buildcc/lib/args/include/args/args.h b/buildcc/lib/args/include/args/args.h index f3aab1ea..5d186b60 100644 --- a/buildcc/lib/args/include/args/args.h +++ b/buildcc/lib/args/include/args/args.h @@ -151,6 +151,7 @@ class Args { static void Deinit(); // Getters + static bool IsInit(); static bool IsParsed(); static bool Clean(); static env::LogLevel GetLogLevel(); diff --git a/buildcc/lib/args/src/args.cpp b/buildcc/lib/args/src/args.cpp index f257af9f..4af02a20 100644 --- a/buildcc/lib/args/src/args.cpp +++ b/buildcc/lib/args/src/args.cpp @@ -114,6 +114,7 @@ Args::Instance &Args::Init() { void Args::Deinit() { internal_.reset(nullptr); } +bool Args::IsInit() { return static_cast(internal_); } bool Args::IsParsed() { return RefApp().parsed(); } bool Args::Clean() { return clean_; } env::LogLevel Args::GetLogLevel() { return loglevel_; } diff --git a/buildcc/lib/args/test/test_args.cpp b/buildcc/lib/args/test/test_args.cpp index 697df743..b1603fe4 100644 --- a/buildcc/lib/args/test/test_args.cpp +++ b/buildcc/lib/args/test/test_args.cpp @@ -19,6 +19,9 @@ TEST(ArgsTestGroup, Args_BasicParse) { std::vector av{"", "--config", "configs/basic_parse.toml"}; int argc = av.size(); + CHECK_FALSE(buildcc::Args::IsInit()); + CHECK_THROWS(std::exception, buildcc::Args::IsParsed()); + (void)buildcc::Args::Init(); auto &instance = buildcc::Args::Init(); // Second init does nothing when // already initialized @@ -28,6 +31,8 @@ TEST(ArgsTestGroup, Args_BasicParse) { STRCMP_EQUAL(buildcc::Args::GetProjectBuildDir().string().c_str(), "build"); CHECK(buildcc::Args::GetLogLevel() == buildcc::env::LogLevel::Trace); CHECK_TRUE(buildcc::Args::Clean()); + CHECK_TRUE(buildcc::Args::IsInit()); + CHECK_TRUE(buildcc::Args::IsParsed()); } TEST(ArgsTestGroup, Args_BasicExit) { From 7c3c300c663d81a93bd9c7c176760dfab1f967e3 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Tue, 29 Mar 2022 22:48:42 -0700 Subject: [PATCH 04/39] Updated args and test_args --- buildcc/lib/args/src/args.cpp | 7 ++++++- buildcc/lib/args/test/test_args.cpp | 2 +- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/buildcc/lib/args/src/args.cpp b/buildcc/lib/args/src/args.cpp index 4af02a20..0d10823c 100644 --- a/buildcc/lib/args/src/args.cpp +++ b/buildcc/lib/args/src/args.cpp @@ -115,7 +115,12 @@ Args::Instance &Args::Init() { void Args::Deinit() { internal_.reset(nullptr); } bool Args::IsInit() { return static_cast(internal_); } -bool Args::IsParsed() { return RefApp().parsed(); } +bool Args::IsParsed() { + if (!IsInit()) { + return false; + } + return RefApp().parsed(); +} bool Args::Clean() { return clean_; } env::LogLevel Args::GetLogLevel() { return loglevel_; } diff --git a/buildcc/lib/args/test/test_args.cpp b/buildcc/lib/args/test/test_args.cpp index b1603fe4..8b519174 100644 --- a/buildcc/lib/args/test/test_args.cpp +++ b/buildcc/lib/args/test/test_args.cpp @@ -20,7 +20,7 @@ TEST(ArgsTestGroup, Args_BasicParse) { int argc = av.size(); CHECK_FALSE(buildcc::Args::IsInit()); - CHECK_THROWS(std::exception, buildcc::Args::IsParsed()); + CHECK_FALSE(buildcc::Args::IsParsed()); (void)buildcc::Args::Init(); auto &instance = buildcc::Args::Init(); // Second init does nothing when From b743dc07636867fb2a27d33a7a40006030978a9e Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 31 Mar 2022 02:39:48 -0700 Subject: [PATCH 05/39] Added Reg API Uses static Register internally --- buildcc/lib/args/include/args/register.h | 56 +++++++++++++++++++++--- buildcc/lib/args/src/register.cpp | 44 +++++++++++++++---- 2 files changed, 86 insertions(+), 14 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 110e5246..634d607e 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -33,7 +33,7 @@ namespace buildcc { class Register { public: - Register() { Initialize(); } + Register() = default; Register(const Register &) = delete; /** @@ -143,11 +143,6 @@ class Register { private: private: - void Initialize(); - - // Setup env:: defaults - void Env(); - // BuildTasks tf::Task BuildTargetTask(BaseTarget &target); tf::Task BuildGeneratorTask(BaseGenerator &generator); @@ -166,6 +161,55 @@ class Register { tf::Executor executor_; }; +class Reg { +private: + class ToolchainInstance { + public: + ToolchainInstance(const ArgToolchainState &condition) + : condition_(condition) {} + template + ToolchainInstance &Build(const C &build_cb, BaseTarget &target, + Params &&...params) { + reg_.Build(condition_, target, std::forward(params)...); + return *this; + } + + ToolchainInstance &Dep(const internal::BuilderInterface &target, + const internal::BuilderInterface &dependency) { + reg_.Dep(target, dependency); + return *this; + } + + ToolchainInstance &Test(const std::string &command, + const BaseTarget &target, + const TestConfig &config = TestConfig()) { + reg_.Test(condition_, command, target, config); + return *this; + } + + private: + ArgToolchainState condition_; + }; + + class CallbackInstance { + public: + CallbackInstance(bool condition = true) : condition_(condition) {} + CallbackInstance &Func(const std::function &cb); + + private: + bool condition_; + }; + +public: + static void Init(); + static CallbackInstance Call(bool condition = true); + static ToolchainInstance Toolchain(const ArgToolchainState &condition); + +private: + static bool is_init_; + static Register reg_; +}; + } // namespace buildcc #endif diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index cbd1e719..77dbb974 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -26,6 +26,11 @@ namespace fs = std::filesystem; +namespace { +constexpr const char *const kRegkNotInit = + "Initialize Reg using the Reg::Init API"; +} + namespace { void DepDetectDuplicate(const tf::Task &target_task, const std::string &match) { @@ -60,6 +65,37 @@ void DepDetectCyclicDependency(const tf::Task &target_task, namespace buildcc { +bool Reg::is_init_{false}; +Register Reg::reg_; + +void Reg::Init() { + if (!is_init_) { + env::assert_fatal(Args::IsParsed(), "Setup your Args"); + Project::Init(fs::current_path() / Args::GetProjectRootDir(), + fs::current_path() / Args::GetProjectBuildDir()); + env::set_log_level(Args::GetLogLevel()); + is_init_ = true; + } +} + +Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { + env::assert_fatal(is_init_, kRegkNotInit); + return ToolchainInstance(condition); +} + +Reg::CallbackInstance Reg::Call(bool condition) { + env::assert_fatal(is_init_, kRegkNotInit); + return CallbackInstance(condition); +} + +Reg::CallbackInstance & +Reg::CallbackInstance::Func(const std::function &cb) { + if (condition_ && cb) { + cb(); + } + return *this; +} + void Register::Clean(const std::function &clean_cb) { if (Args::Clean()) { clean_cb(); @@ -116,14 +152,6 @@ void Register::BuildStoreTask(const std::string &unique_id, unique_id)); } -void Register::Initialize() { Env(); } - -void Register::Env() { - Project::Init(fs::current_path() / Args::GetProjectRootDir(), - fs::current_path() / Args::GetProjectBuildDir()); - env::set_log_level(Args::GetLogLevel()); -} - // void TestInfo::TestRunner() const { From 9808773ce787843fd50680fb15775f6dd1a2d2a2 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 31 Mar 2022 03:00:37 -0700 Subject: [PATCH 06/39] Updated register --- buildcc/lib/args/include/args/register.h | 17 ++++++--------- buildcc/lib/args/src/register.cpp | 27 ++++++++++++++++++++++++ 2 files changed, 33 insertions(+), 11 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 634d607e..f52ccbe0 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -167,25 +167,19 @@ class Reg { public: ToolchainInstance(const ArgToolchainState &condition) : condition_(condition) {} + + ToolchainInstance &Func(const std::function &cb); template ToolchainInstance &Build(const C &build_cb, BaseTarget &target, Params &&...params) { - reg_.Build(condition_, target, std::forward(params)...); + reg_.Build(condition_, build_cb, target, std::forward(params)...); return *this; } - ToolchainInstance &Dep(const internal::BuilderInterface &target, - const internal::BuilderInterface &dependency) { - reg_.Dep(target, dependency); - return *this; - } - + const internal::BuilderInterface &dependency); ToolchainInstance &Test(const std::string &command, const BaseTarget &target, - const TestConfig &config = TestConfig()) { - reg_.Test(condition_, command, target, config); - return *this; - } + const TestConfig &config = TestConfig()); private: ArgToolchainState condition_; @@ -202,6 +196,7 @@ class Reg { public: static void Init(); + static void Run(); static CallbackInstance Call(bool condition = true); static ToolchainInstance Toolchain(const ArgToolchainState &condition); diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 77dbb974..55741675 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -78,11 +78,38 @@ void Reg::Init() { } } +void Reg::Run() { + reg_.RunBuild(); + reg_.RunTest(); +} + Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { env::assert_fatal(is_init_, kRegkNotInit); return ToolchainInstance(condition); } +Reg::ToolchainInstance & +Reg::ToolchainInstance::Func(const std::function &cb) { + if (condition_.build && cb) { + cb(); + } + return *this; +} + +Reg::ToolchainInstance & +Reg::ToolchainInstance::Dep(const internal::BuilderInterface &target, + const internal::BuilderInterface &dependency) { + reg_.Dep(target, dependency); + return *this; +} + +Reg::ToolchainInstance &Reg::ToolchainInstance::Test(const std::string &command, + const BaseTarget &target, + const TestConfig &config) { + reg_.Test(condition_, command, target, config); + return *this; +} + Reg::CallbackInstance Reg::Call(bool condition) { env::assert_fatal(is_init_, kRegkNotInit); return CallbackInstance(condition); From 8429d17c4529889eac011f44281373c32312c6ee Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 31 Mar 2022 03:44:12 -0700 Subject: [PATCH 07/39] Updated register --- buildcc/lib/args/include/args/register.h | 8 +++++++- buildcc/lib/args/src/register.cpp | 8 -------- 2 files changed, 7 insertions(+), 9 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index f52ccbe0..55e2273b 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -168,7 +168,13 @@ class Reg { ToolchainInstance(const ArgToolchainState &condition) : condition_(condition) {} - ToolchainInstance &Func(const std::function &cb); + template + ToolchainInstance &Func(const C &cb, Params &&...params) { + if (condition_.build) { + cb(std::forward(params)...); + } + return *this; + } template ToolchainInstance &Build(const C &build_cb, BaseTarget &target, Params &&...params) { diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 55741675..cdb553fa 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -88,14 +88,6 @@ Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { return ToolchainInstance(condition); } -Reg::ToolchainInstance & -Reg::ToolchainInstance::Func(const std::function &cb) { - if (condition_.build && cb) { - cb(); - } - return *this; -} - Reg::ToolchainInstance & Reg::ToolchainInstance::Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency) { From 32d45d30f191635881c83a4a11dd7a73dca247c3 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 05:29:28 -0700 Subject: [PATCH 08/39] Updated register --- buildcc/lib/args/include/args/register.h | 21 +++++++++++++++++++-- buildcc/lib/args/src/register.cpp | 21 ++++++++++++--------- 2 files changed, 31 insertions(+), 11 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 55e2273b..3cbef8d0 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -161,6 +161,12 @@ class Register { tf::Executor executor_; }; +struct RegConfig { + std::function pre_build_cb; + std::function post_build_cb; + std::function post_test_cb; +}; + class Reg { private: class ToolchainInstance { @@ -168,6 +174,7 @@ class Reg { ToolchainInstance(const ArgToolchainState &condition) : condition_(condition) {} + // Duplicated code template ToolchainInstance &Func(const C &cb, Params &&...params) { if (condition_.build) { @@ -175,6 +182,7 @@ class Reg { } return *this; } + template ToolchainInstance &Build(const C &build_cb, BaseTarget &target, Params &&...params) { @@ -194,7 +202,15 @@ class Reg { class CallbackInstance { public: CallbackInstance(bool condition = true) : condition_(condition) {} - CallbackInstance &Func(const std::function &cb); + + // Duplicated code + template + CallbackInstance &Func(const C &cb, Params &&...params) { + if (condition_) { + cb(std::forward(params)...); + } + return *this; + } private: bool condition_; @@ -202,7 +218,8 @@ class Reg { public: static void Init(); - static void Run(); + static void Run(const RegConfig &config = RegConfig()); + static const tf::Taskflow &GetTaskflow(); static CallbackInstance Call(bool condition = true); static ToolchainInstance Toolchain(const ArgToolchainState &condition); diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index cdb553fa..b539ea82 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -78,11 +78,22 @@ void Reg::Init() { } } -void Reg::Run() { +void Reg::Run(const RegConfig &config) { + if (config.pre_build_cb) { + config.pre_build_cb(); + } reg_.RunBuild(); + if (config.post_build_cb) { + config.post_build_cb(); + } reg_.RunTest(); + if (config.post_test_cb) { + config.post_test_cb(); + } } +const tf::Taskflow &Reg::GetTaskflow() { return reg_.GetTaskflow(); } + Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { env::assert_fatal(is_init_, kRegkNotInit); return ToolchainInstance(condition); @@ -107,14 +118,6 @@ Reg::CallbackInstance Reg::Call(bool condition) { return CallbackInstance(condition); } -Reg::CallbackInstance & -Reg::CallbackInstance::Func(const std::function &cb) { - if (condition_ && cb) { - cb(); - } - return *this; -} - void Register::Clean(const std::function &clean_cb) { if (Args::Clean()) { clean_cb(); From 4ecbcea95c2c4300ba8298a92250a598c09c0cda Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 05:29:54 -0700 Subject: [PATCH 09/39] Updated example build files --- example/hybrid/external_lib/build.main.cpp | 15 ++- example/hybrid/foolib/build.main.cpp | 15 ++- example/hybrid/generic/build.cpp | 108 +++++++++++---------- example/hybrid/pch/build.cpp | 40 ++++---- example/hybrid/simple/build.cpp | 42 ++++---- example/hybrid/single/build.cpp | 21 ++-- example/hybrid/target_info/build.cpp | 74 ++++++-------- 7 files changed, 143 insertions(+), 172 deletions(-) diff --git a/example/hybrid/external_lib/build.main.cpp b/example/hybrid/external_lib/build.main.cpp index b181281b..d74b63ef 100644 --- a/example/hybrid/external_lib/build.main.cpp +++ b/example/hybrid/external_lib/build.main.cpp @@ -19,23 +19,22 @@ int main(int argc, char **argv) { .Parse(argc, argv); // 2. Initialize your environment - Register reg; + Reg::Init(); // 3. Pre-build steps - reg.Clean(clean_cb); + Reg::Call(Args::Clean()).Func(clean_cb); // 4. Build steps Toolchain_gcc gcc; - Toolchain_msvc msvc; - ExecutableTarget_gcc g_foolib("cppflags", gcc, ""); - ExecutableTarget_msvc m_foolib("cppflags", msvc, ""); + Reg::Toolchain(arg_gcc.state).Build(foolib_build_cb, g_foolib); - reg.Build(arg_gcc.state, foolib_build_cb, g_foolib); - reg.Build(arg_msvc.state, foolib_build_cb, m_foolib); + Toolchain_msvc msvc; + ExecutableTarget_msvc m_foolib("cppflags", msvc, ""); + Reg::Toolchain(arg_msvc.state).Build(foolib_build_cb, m_foolib); // 5. - reg.RunBuild(); + Reg::Run(); // 6. plugin::ClangCompileCommands({&g_foolib, &m_foolib}).Generate(); diff --git a/example/hybrid/foolib/build.main.cpp b/example/hybrid/foolib/build.main.cpp index dc723d7b..aa005469 100644 --- a/example/hybrid/foolib/build.main.cpp +++ b/example/hybrid/foolib/build.main.cpp @@ -19,23 +19,22 @@ int main(int argc, char **argv) { .Parse(argc, argv); // 2. Initialize your environment - Register reg; + Reg::Init(); // 3. Pre-build steps - reg.Clean(clean_cb); + Reg::Call(Args::Clean()).Func(clean_cb); // 4. Build steps Toolchain_gcc gcc; - Toolchain_msvc msvc; - ExecutableTarget_gcc g_foolib("foolib", gcc, ""); - ExecutableTarget_msvc m_foolib("foolib", msvc, ""); + Reg::Toolchain(arg_gcc.state).Build(foolib_build_cb, g_foolib); - reg.Build(arg_gcc.state, foolib_build_cb, g_foolib); - reg.Build(arg_msvc.state, foolib_build_cb, m_foolib); + Toolchain_msvc msvc; + ExecutableTarget_msvc m_foolib("foolib", msvc, ""); + Reg::Toolchain(arg_msvc.state).Build(foolib_build_cb, m_foolib); // 5. - reg.RunBuild(); + Reg::Run(); // 6. plugin::ClangCompileCommands({&g_foolib, &m_foolib}).Generate(); diff --git a/example/hybrid/generic/build.cpp b/example/hybrid/generic/build.cpp index 3b9dcaa3..22876504 100644 --- a/example/hybrid/generic/build.cpp +++ b/example/hybrid/generic/build.cpp @@ -20,8 +20,11 @@ static void foolib_build_cb(BaseTarget &foolib_target); static void generic_build_cb(BaseTarget &generic_target, BaseTarget &foolib_target); +static void post_build_cb(BaseTarget &generic_target, + BaseTarget &foolib_target); + int main(int argc, char **argv) { - // 1. Get arguments + // Get arguments ArgToolchain custom_toolchain; TargetType default_lib_type{TargetType::StaticLibrary}; Args::Init() @@ -30,70 +33,37 @@ int main(int argc, char **argv) { [&](CLI::App &app) { args_lib_type_cb(app, default_lib_type); }) .Parse(argc, argv); - // 2. Initialize your environment - Register reg; + // Initialize your environment + Reg::Init(); - // 3. Pre-build steps - reg.Clean(clean_cb); + // Pre-build steps + Reg::Call(Args::Clean()).Func(clean_cb); - // 4. Build steps + // Build steps // Toolchain + Generic Target BaseToolchain toolchain = custom_toolchain.ConstructToolchain(); Target_generic foolib_target("libfoo", default_lib_type, toolchain, ""); - reg.Build(custom_toolchain.state, foolib_build_cb, foolib_target); - - // Target specific settings Target_generic generic_target("generic", TargetType::Executable, toolchain, "src"); - reg.Build(custom_toolchain.state, generic_build_cb, generic_target, - foolib_target); - reg.Dep(generic_target, foolib_target); - - // 5. Test steps - reg.Test(custom_toolchain.state, "{executable}", generic_target); - - // 6. Build Target - reg.RunBuild(); - - // 7. Post Build steps - // For Static Lib do nothing - // For Dynamic Lib we need to handle special cases - // - MSVC behaviour - // - Copy to executable location - if (default_lib_type == TargetType::DynamicLibrary) { - - // MSVC special case - fs::path copy_from_path; - fs::path copy_to_path; - if (toolchain.GetId() == ToolchainId::Msvc) { - copy_from_path = - fmt::format("{}.dll", path_as_string(foolib_target.GetTargetPath())); - copy_to_path = - generic_target.GetTargetBuildDir() / - fmt::format("{}.dll", - foolib_target.GetTargetPath().filename().string()); - } else { - copy_from_path = foolib_target.GetTargetPath(); - copy_to_path = - generic_target.GetTargetBuildDir() / - (foolib_target.GetName() + foolib_target.GetConfig().target_ext); - } - - // Copy case - if (generic_target.IsBuilt()) { - fs::remove(copy_to_path); - fs::copy(copy_from_path, copy_to_path); - } - } - - // 8. Test Target - reg.RunTest(); + Reg::Toolchain(custom_toolchain.state) + .Func([&]() { toolchain.Verify(); }) + .Build(foolib_build_cb, foolib_target) + .Build(generic_build_cb, generic_target, foolib_target) + .Dep(generic_target, foolib_target) + .Test("{executable}", generic_target); + + // Build Target + RegConfig reg_config; + reg_config.post_build_cb = [&]() { + post_build_cb(generic_target, foolib_target); + }; + Reg::Run(reg_config); // - Clang Compile Commands plugin::ClangCompileCommands({&foolib_target, &generic_target}).Generate(); // - Plugin Graph - std::string output = reg.GetTaskflow().dump(); + std::string output = Reg::GetTaskflow().dump(); const bool saved = env::save_file("graph.dot", output, false); env::assert_fatal(saved, "Could not save graph.dot file"); @@ -131,3 +101,35 @@ static void generic_build_cb(BaseTarget &generic_target, generic_target.AddSource("main.cpp"); generic_target.Build(); } + +void post_build_cb(BaseTarget &generic_target, BaseTarget &foolib_target) { + // For Static Lib do nothing + // For Dynamic Lib we need to handle special cases + // - MSVC behaviour + // - Copy to executable location + if (foolib_target.GetType() == TargetType::DynamicLibrary) { + // MSVC special case + fs::path copy_from_path; + fs::path copy_to_path; + if (foolib_target.GetToolchain().GetId() == ToolchainId::Msvc) { + copy_from_path = + fmt::format("{}.dll", path_as_string(foolib_target.GetTargetPath())); + copy_to_path = + generic_target.GetTargetBuildDir() / + fmt::format("{}.dll", + foolib_target.GetTargetPath().filename().string()); + } else { + copy_from_path = foolib_target.GetTargetPath(); + copy_to_path = + generic_target.GetTargetBuildDir() / + (foolib_target.GetName() + foolib_target.GetConfig().target_ext); + } + + // Copy case + // TODO, This should be baked into the `Target` API + if (generic_target.IsBuilt()) { + fs::remove(copy_to_path); + fs::copy(copy_from_path, copy_to_path); + } + } +} diff --git a/example/hybrid/pch/build.cpp b/example/hybrid/pch/build.cpp index a305367d..88bfc426 100644 --- a/example/hybrid/pch/build.cpp +++ b/example/hybrid/pch/build.cpp @@ -21,39 +21,33 @@ int main(int argc, char **argv) { .Parse(argc, argv); // 2. Initialize your environment - Register reg; + Reg::Init(); // 3. Pre-build steps - reg.Clean(clean_cb); + Reg::Call(Args::Clean()).Func(clean_cb); // 4. Build steps // Explicit toolchain - target pairs Toolchain_gcc gcc; - Toolchain_msvc msvc; - ExecutableTarget_gcc g_cppflags("cppflags", gcc, "files"); ExecutableTarget_gcc g_cflags("cflags", gcc, "files"); - ExecutableTarget_msvc m_cppflags("cppflags", msvc, "files"); - ExecutableTarget_msvc m_cflags("cflags", msvc, "files"); - // Select your builds and tests using the .toml files - reg.Build(arg_gcc.state, cppflags_build_cb, g_cppflags); - reg.Build(arg_msvc.state, cppflags_build_cb, m_cppflags); - reg.Build(arg_gcc.state, cflags_build_cb, g_cflags); - reg.Build(arg_msvc.state, cflags_build_cb, m_cflags); + Reg::Toolchain(arg_gcc.state) + .Build(cppflags_build_cb, g_cppflags) + .Build(cflags_build_cb, g_cflags) + .Test("{executable}", g_cppflags) + .Test("{executable}", g_cflags); - // 5. Test steps - // NOTE, For now they are just dummy callbacks - reg.Test(arg_gcc.state, "{executable}", g_cppflags); - reg.Test(arg_msvc.state, "{executable}", m_cppflags); - reg.Test(arg_gcc.state, "{executable}", g_cflags); - reg.Test(arg_msvc.state, "{executable}", m_cflags); - - // 6. Build Target - reg.RunBuild(); + Toolchain_msvc msvc; + ExecutableTarget_msvc m_cppflags("cppflags", msvc, "files"); + ExecutableTarget_msvc m_cflags("cflags", msvc, "files"); + Reg::Toolchain(arg_msvc.state) + .Build(cppflags_build_cb, m_cppflags) + .Build(cflags_build_cb, m_cflags) + .Test("{executable}", m_cppflags) + .Test("{executable}", m_cflags); - // 7. Test Target - reg.RunTest(); + Reg::Run(); // 8. Post Build steps @@ -61,7 +55,7 @@ int main(int argc, char **argv) { plugin::ClangCompileCommands({&g_cflags, &g_cppflags}).Generate(); // - Plugin Graph - std::string output = reg.GetTaskflow().dump(); + std::string output = Reg::GetTaskflow().dump(); const bool saved = env::save_file("graph.dot", output, false); env::assert_fatal(saved, "Could not save graph.dot file"); diff --git a/example/hybrid/simple/build.cpp b/example/hybrid/simple/build.cpp index 94c447f7..229f4f97 100644 --- a/example/hybrid/simple/build.cpp +++ b/example/hybrid/simple/build.cpp @@ -21,38 +21,34 @@ int main(int argc, char **argv) { .Parse(argc, argv); // 2. Initialize your environment - Register reg; + Reg::Init(); // 3. Pre-build steps - reg.Clean(clean_cb); + Reg::Call(Args::Clean()).Func(clean_cb); // 4. Build steps // Explicit toolchain - target pairs Toolchain_gcc gcc; - Toolchain_msvc msvc; - ExecutableTarget_gcc g_cppflags("cppflags", gcc, "files"); - ExecutableTarget_msvc m_cppflags("cppflags", msvc, "files"); ExecutableTarget_gcc g_cflags("cflags", gcc, "files"); - ExecutableTarget_msvc m_cflags("cflags", msvc, "files"); - - // Select your builds and tests using the .toml files - reg.Build(arg_gcc.state, cppflags_build_cb, g_cppflags); - reg.Build(arg_msvc.state, cppflags_build_cb, m_cppflags); - reg.Build(arg_gcc.state, cflags_build_cb, g_cflags); - reg.Build(arg_msvc.state, cflags_build_cb, m_cflags); + Reg::Toolchain(arg_gcc.state) + .Func([&]() { gcc.Verify(); }) + .Build(cppflags_build_cb, g_cppflags) + .Build(cflags_build_cb, g_cflags) + .Test("{executable}", g_cppflags) + .Test("{executable}", g_cflags); - // 5. Test steps - reg.Test(arg_gcc.state, "{executable}", g_cppflags); - reg.Test(arg_msvc.state, "{executable}", m_cppflags); - reg.Test(arg_gcc.state, "{executable}", g_cflags); - reg.Test(arg_msvc.state, "{executable}", m_cflags); - - // 6. Build Target - reg.RunBuild(); + Toolchain_msvc msvc; + ExecutableTarget_msvc m_cppflags("cppflags", msvc, "files"); + ExecutableTarget_msvc m_cflags("cflags", msvc, "files"); + Reg::Toolchain(arg_msvc.state) + .Func([&]() { msvc.Verify(); }) + .Build(cppflags_build_cb, m_cppflags) + .Build(cflags_build_cb, m_cflags) + .Test("{executable}", m_cppflags) + .Test("{executable}", m_cflags); - // 7. Test Target - reg.RunTest(); + Reg::Run(); // 8. Post Build steps @@ -61,7 +57,7 @@ int main(int argc, char **argv) { .Generate(); // - Plugin Graph - std::string output = reg.GetTaskflow().dump(); + std::string output = Reg::GetTaskflow().dump(); const bool saved = env::save_file("graph.dot", output, false); env::assert_fatal(saved, "Could not save graph.dot file"); diff --git a/example/hybrid/single/build.cpp b/example/hybrid/single/build.cpp index 491c8fc2..a6e59996 100644 --- a/example/hybrid/single/build.cpp +++ b/example/hybrid/single/build.cpp @@ -16,29 +16,24 @@ int main(int argc, char **argv) { .Parse(argc, argv); // 2. Initialize your environment - Register reg; + Reg::Init(); // 3. Pre-build steps - reg.Clean(clean_cb); + Reg::Call(Args::Clean()).Func(clean_cb); // 4. Build steps // Explicit toolchain - target pairs Toolchain_gcc gcc; - gcc.Verify(); - ExecutableTarget_gcc hello_world("hello_world", gcc, ""); // Select your builds and tests using the .toml files - reg.Build(arg_gcc.state, hello_world_build_cb, hello_world); - - // 5. Test steps - reg.Test(arg_gcc.state, "{executable}", hello_world); - - // 6. Build Target - reg.RunBuild(); + Reg::Toolchain(arg_gcc.state) + .Func([&]() { gcc.Verify(); }) + .Build(hello_world_build_cb, hello_world) + .Test("{executable}", hello_world); - // 7. Test Target - reg.RunTest(); + // 6. Build and Test Target + Reg::Run(); // 8. Post Build steps // - Clang Compile Commands diff --git a/example/hybrid/target_info/build.cpp b/example/hybrid/target_info/build.cpp index 600a8c71..e2684d0f 100644 --- a/example/hybrid/target_info/build.cpp +++ b/example/hybrid/target_info/build.cpp @@ -13,7 +13,7 @@ static void genericadd2_build_cb(BaseTarget &genericadd, const TargetInfo &genericadd_ho); int main(int argc, char **argv) { - // 1. Get arguments + // Get arguments ArgToolchain arg_gcc; ArgToolchain arg_msvc; Args::Init() @@ -21,61 +21,47 @@ int main(int argc, char **argv) { .AddToolchain("msvc", "Generic msvc toolchain", arg_msvc) .Parse(argc, argv); - // 2. Initialize your environment - Register reg; + // Initialize your environment + Reg::Init(); - // 3. Pre-build steps - reg.Clean(clean_cb); + // Pre-build steps + Reg::Call(Args::Clean()).Func(clean_cb); - // 4. Build steps + // Build steps // Explicit toolchain - target pairs Toolchain_gcc gcc; - Toolchain_msvc msvc; - - // TargetInfo TargetInfo gcc_genericadd_ho(gcc, "files"); - TargetInfo msvc_genericadd_ho(msvc, "files"); - reg.Callback(genericadd_ho_cb, gcc_genericadd_ho); - reg.Callback(genericadd_ho_cb, msvc_genericadd_ho); - ExecutableTarget_gcc g_genericadd1("generic_add_1", gcc, "files"); - ExecutableTarget_msvc m_genericadd1("generic_add_1", msvc, "files"); - ExecutableTarget_gcc g_genericadd2("generic_add_2", gcc, "files"); - ExecutableTarget_msvc m_genericadd2("generic_add_2", msvc, "files"); - - // Select your builds and tests using the .toml files - reg.Build(arg_gcc.state, genericadd1_build_cb, g_genericadd1, - gcc_genericadd_ho); - reg.Build(arg_gcc.state, genericadd2_build_cb, g_genericadd2, - gcc_genericadd_ho); - - reg.Build(arg_msvc.state, genericadd1_build_cb, m_genericadd1, - msvc_genericadd_ho); - reg.Build(arg_msvc.state, genericadd2_build_cb, m_genericadd2, - msvc_genericadd_ho); - - // 5. Test steps - // NOTE, For now they are just dummy callbacks - reg.Test(arg_gcc.state, "{executable}", g_genericadd1); - reg.Test(arg_msvc.state, "{executable}", m_genericadd1); - - reg.Test(arg_gcc.state, "{executable}", g_genericadd2); - reg.Test(arg_msvc.state, "{executable}", m_genericadd2); - - // 6. Build Target - reg.RunBuild(); - - // 7. Test Target - reg.RunTest(); - - // 8. Post Build steps + Reg::Toolchain(arg_gcc.state) + .Func([&]() { gcc.Verify(); }) + .Func(genericadd_ho_cb, gcc_genericadd_ho) + .Build(genericadd1_build_cb, g_genericadd1, gcc_genericadd_ho) + .Build(genericadd2_build_cb, g_genericadd2, gcc_genericadd_ho) + .Test("{executable}", g_genericadd1) + .Test("{executable}", g_genericadd2); + Toolchain_msvc msvc; + TargetInfo msvc_genericadd_ho(msvc, "files"); + ExecutableTarget_msvc m_genericadd1("generic_add_1", msvc, "files"); + ExecutableTarget_msvc m_genericadd2("generic_add_2", msvc, "files"); + Reg::Toolchain(arg_msvc.state) + .Func([&]() { msvc.Verify(); }) + .Func(genericadd_ho_cb, msvc_genericadd_ho) + .Build(genericadd1_build_cb, m_genericadd1, msvc_genericadd_ho) + .Build(genericadd2_build_cb, m_genericadd2, msvc_genericadd_ho) + .Test("{executable}", m_genericadd1) + .Test("{executable}", m_genericadd2); + + // Run + Reg::Run(); + + // Post Build steps // - Clang Compile Commands plugin::ClangCompileCommands({&g_genericadd1, &m_genericadd1}).Generate(); // - Plugin Graph - std::string output = reg.GetTaskflow().dump(); + std::string output = Reg::GetTaskflow().dump(); const bool saved = env::save_file("graph.dot", output, false); env::assert_fatal(saved, "Could not save graph.dot file"); From 0c2c1ac12cca55a1972bf105d8788b8d7399a8bd Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 05:53:50 -0700 Subject: [PATCH 10/39] Update register.h --- buildcc/lib/args/include/args/register.h | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 3cbef8d0..8a931c39 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -212,6 +212,15 @@ class Reg { return *this; } + template + CallbackInstance &Build(const C &build_cb, BaseGenerator &generator, + Params &&...params) { + if (condition_) { + reg_.Build(build_cb, generator, std::forward(params)...); + } + return *this; + } + private: bool condition_; }; From 3115ace333f644d65005fa308018c1d09dc6e5db Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 06:09:11 -0700 Subject: [PATCH 11/39] Update args.h --- buildcc/lib/args/include/args/args.h | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/buildcc/lib/args/include/args/args.h b/buildcc/lib/args/include/args/args.h index 5d186b60..51ebeb05 100644 --- a/buildcc/lib/args/include/args/args.h +++ b/buildcc/lib/args/include/args/args.h @@ -27,6 +27,8 @@ #include "toolchain/toolchain.h" +#include "target/common/target_config.h" + namespace fs = std::filesystem; namespace buildcc { @@ -81,8 +83,15 @@ struct ArgToolchain { struct ArgTarget { ArgTarget(){}; - std::string compile_command{""}; - std::string link_command{""}; + TargetConfig GetTargetConfig() { + TargetConfig config; + config.compile_command = compile_command; + config.link_command = link_command; + return config; + } + + std::string compile_command; + std::string link_command; }; struct ArgCustom { From 524a0331d4512aebb47b8eba7f0f3fb4b3c9810d Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 06:09:23 -0700 Subject: [PATCH 12/39] Updated examples --- example/hybrid/custom_target/build.main.cpp | 47 ++++++------- example/hybrid/dep_chaining/build.cpp | 73 +++++++++------------ 2 files changed, 53 insertions(+), 67 deletions(-) diff --git a/example/hybrid/custom_target/build.main.cpp b/example/hybrid/custom_target/build.main.cpp index 6b0829c0..c93b618c 100644 --- a/example/hybrid/custom_target/build.main.cpp +++ b/example/hybrid/custom_target/build.main.cpp @@ -8,49 +8,44 @@ static void foolib_build_cb(BaseTarget &target); static constexpr std::string_view EXE = "build"; int main(int argc, char **argv) { - // 1. Get arguments + // Get arguments ArgToolchain arg_gcc; ArgToolchain arg_msvc; - ArgToolchain toolchain_clang_gnu; - ArgTarget target_clang_gnu; + ArgToolchain arg_toolchain_clang_gnu; + ArgTarget arg_target_clang_gnu; Args::Init() .AddToolchain("gcc", "Generic gcc toolchain", arg_gcc) .AddToolchain("msvc", "Generic msvc toolchain", arg_msvc) - .AddToolchain("clang_gnu", "Clang GNU toolchain", toolchain_clang_gnu) - .AddTarget("clang_gnu", "Clang GNU target", target_clang_gnu) + .AddToolchain("clang_gnu", "Clang GNU toolchain", arg_toolchain_clang_gnu) + .AddTarget("clang_gnu", "Clang GNU target", arg_target_clang_gnu) .Parse(argc, argv); - // 2. Initialize your environment - Register reg; + // Initialize your environment + Reg::Init(); - // 3. Pre-build steps - reg.Clean(clean_cb); + // Pre-build steps + Reg::Call(Args::Clean()).Func(clean_cb); - // 4. Build steps + // Build steps Toolchain_gcc gcc; - Toolchain_msvc msvc; - ExecutableTarget_gcc g_foolib("foolib", gcc, ""); - ExecutableTarget_msvc m_foolib("foolib", msvc, ""); + Reg::Toolchain(arg_gcc.state).Build(foolib_build_cb, g_foolib); - reg.Build(arg_gcc.state, foolib_build_cb, g_foolib); - reg.Build(arg_msvc.state, foolib_build_cb, m_foolib); + Toolchain_msvc msvc; + ExecutableTarget_msvc m_foolib("foolib", msvc, ""); + Reg::Toolchain(arg_msvc.state).Build(foolib_build_cb, m_foolib); // * NOTE, This is how we add our custom toolchain - BaseToolchain clang = toolchain_clang_gnu.ConstructToolchain(); - - // * M2, Get from Args (see build_linux.toml or build_win.toml files) - TargetConfig config; - config.compile_command = target_clang_gnu.compile_command; - config.link_command = target_clang_gnu.link_command; + BaseToolchain clang = arg_toolchain_clang_gnu.ConstructToolchain(); Target_custom c_foolib("CFoolib.exe", TargetType::Executable, clang, "", - config); - reg.Build(toolchain_clang_gnu.state, foolib_build_cb, c_foolib); + arg_target_clang_gnu.GetTargetConfig()); + Reg::Toolchain(arg_toolchain_clang_gnu.state) + .Build(foolib_build_cb, c_foolib); - // 5. - reg.RunBuild(); + // + Reg::Run(); - // 6. + // plugin::ClangCompileCommands({&g_foolib, &m_foolib, &c_foolib}).Generate(); return 0; diff --git a/example/hybrid/dep_chaining/build.cpp b/example/hybrid/dep_chaining/build.cpp index 49722ad4..3baddfe0 100644 --- a/example/hybrid/dep_chaining/build.cpp +++ b/example/hybrid/dep_chaining/build.cpp @@ -15,7 +15,7 @@ static void cpp_generator_cb(BaseGenerator &generator); static void c_generator_cb(BaseGenerator &generator); int main(int argc, char **argv) { - // 1. Get arguments + // Get arguments ArgToolchain arg_gcc; ArgToolchain arg_msvc; Args::Init() @@ -23,54 +23,45 @@ int main(int argc, char **argv) { .AddToolchain("msvc", "Generic msvc toolchain", arg_msvc) .Parse(argc, argv); - // 2. Initialize your environment - Register reg; + // Initialize your environment + Reg::Init(); - // 3. Pre-build steps - reg.Clean(clean_cb); + // Pre-build steps + Reg::Call(Args::Clean()).Func(clean_cb); - // 4. Build steps - // Explicit toolchain - target pairs - Toolchain_gcc gcc; - Toolchain_msvc msvc; - - // CPP + // Generator BaseGenerator cpp_generator("cpp_generator", ""); - reg.Build(cpp_generator_cb, cpp_generator); - - ExecutableTarget_gcc g_cpptarget("cpptarget", gcc, ""); - reg.Build(arg_gcc.state, cpp_target_cb, g_cpptarget, cpp_generator); - - ExecutableTarget_msvc m_cpptarget("cpptarget", msvc, ""); - reg.Build(arg_msvc.state, cpp_target_cb, m_cpptarget, cpp_generator); - - reg.Dep(g_cpptarget, cpp_generator); - reg.Dep(m_cpptarget, cpp_generator); - - // C BaseGenerator c_generator("c_generator", ""); - reg.Build(c_generator_cb, c_generator); + Reg::Call() + .Build(cpp_generator_cb, cpp_generator) + .Build(c_generator_cb, c_generator); + // Build steps + // Explicit toolchain - target pairs + Toolchain_gcc gcc; + ExecutableTarget_gcc g_cpptarget("cpptarget", gcc, ""); ExecutableTarget_gcc g_ctarget("ctarget", gcc, ""); - reg.Build(arg_gcc.state, c_target_cb, g_ctarget, c_generator); + Reg::Toolchain(arg_gcc.state) + .Build(cpp_target_cb, g_cpptarget, cpp_generator) + .Build(c_target_cb, g_ctarget, c_generator) + .Dep(g_cpptarget, cpp_generator) + .Dep(g_ctarget, c_generator) + .Test("{executable}", g_cpptarget) + .Test("{executable}", g_ctarget); + Toolchain_msvc msvc; + ExecutableTarget_msvc m_cpptarget("cpptarget", msvc, ""); ExecutableTarget_msvc m_ctarget("ctarget", msvc, ""); - reg.Build(arg_msvc.state, c_target_cb, m_ctarget, c_generator); - - reg.Dep(g_ctarget, c_generator); - reg.Dep(m_ctarget, c_generator); - - // Tests - reg.Test(arg_gcc.state, "{executable}", g_cpptarget); - reg.Test(arg_gcc.state, "{executable}", g_ctarget); - reg.Test(arg_msvc.state, "{executable}", m_cpptarget); - reg.Test(arg_msvc.state, "{executable}", m_ctarget); - - // 6. Build Target - reg.RunBuild(); + Reg::Toolchain(arg_msvc.state) + .Build(cpp_target_cb, m_cpptarget, cpp_generator) + .Build(c_target_cb, m_ctarget, c_generator) + .Dep(m_cpptarget, cpp_generator) + .Dep(m_ctarget, c_generator) + .Test("{executable}", m_cpptarget) + .Test("{executable}", m_ctarget); - // 7. Test Target - reg.RunTest(); + // Build and Test + Reg::Run(); // - Clang Compile Commands plugin::ClangCompileCommands( @@ -78,7 +69,7 @@ int main(int argc, char **argv) { .Generate(); // - Plugin Graph - std::string output = reg.GetTaskflow().dump(); + std::string output = Reg::GetTaskflow().dump(); const bool saved = env::save_file("graph.dot", output, false); env::assert_fatal(saved, "Could not save graph.dot file"); From b5cb26f7887d93a074163de7c27296815a175c8d Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 06:51:07 -0700 Subject: [PATCH 13/39] Updated bootstrap and buildexe --- bootstrap/include/bootstrap/build_buildcc.h | 6 ++-- bootstrap/main.buildcc.cpp | 18 +++++------ bootstrap/src/build_buildcc.cpp | 34 +++++++++++---------- buildexe/buildexe.cpp | 6 ++-- buildexe/include/buildexe/build_env_setup.h | 5 ++- buildexe/src/build_env_setup.cpp | 10 +++--- 6 files changed, 39 insertions(+), 40 deletions(-) diff --git a/bootstrap/include/bootstrap/build_buildcc.h b/bootstrap/include/bootstrap/build_buildcc.h index 340066a5..7dcb9aee 100644 --- a/bootstrap/include/bootstrap/build_buildcc.h +++ b/bootstrap/include/bootstrap/build_buildcc.h @@ -59,9 +59,8 @@ class BuildBuildCC { static constexpr const char *const kBuildccLibName = "libbuildcc"; public: - BuildBuildCC(Register ®, const BaseToolchain &toolchain, - const TargetEnv &env) - : reg_(reg), toolchain_(toolchain), env_(env) {} + BuildBuildCC(const BaseToolchain &toolchain, const TargetEnv &env) + : toolchain_(toolchain), env_(env) {} BuildBuildCC(const BuildBuildCC &) = delete; void Setup(const ArgToolchainState &state); @@ -75,7 +74,6 @@ class BuildBuildCC { } private: - Register ®_; const BaseToolchain &toolchain_; TargetEnv env_; diff --git a/bootstrap/main.buildcc.cpp b/bootstrap/main.buildcc.cpp index 7ee8afd6..fd3d365a 100644 --- a/bootstrap/main.buildcc.cpp +++ b/bootstrap/main.buildcc.cpp @@ -38,31 +38,31 @@ int main(int argc, char **argv) { .AddToolchain("host", "Host Toolchain", custom_toolchain_arg) .Parse(argc, argv); - Register reg; - reg.Clean(clean_cb); + Reg::Init(); + Reg::Call(Args::Clean()).Func(clean_cb); BaseToolchain toolchain = custom_toolchain_arg.ConstructToolchain(); BuildBuildCC buildcc( - reg, toolchain, TargetEnv(Project::GetRootDir(), Project::GetBuildDir())); + toolchain, TargetEnv(Project::GetRootDir(), Project::GetBuildDir())); buildcc.Setup(custom_toolchain_arg.state); const auto &buildcc_lib = buildcc.GetBuildcc(); ExecutableTarget_generic buildcc_hybrid_simple_example( "buildcc_hybrid_simple_example", toolchain, "example/hybrid/simple"); - reg.Build(custom_toolchain_arg.state, hybrid_simple_example_cb, - buildcc_hybrid_simple_example, buildcc_lib); - reg.Dep(buildcc_hybrid_simple_example, buildcc_lib); + Reg::Toolchain(custom_toolchain_arg.state) + .Build(hybrid_simple_example_cb, buildcc_hybrid_simple_example, + buildcc_lib) + .Dep(buildcc_hybrid_simple_example, buildcc_lib); // Runners - reg.RunBuild(); - reg.RunTest(); + Reg::Run(); // - Clang Compile Commands plugin::ClangCompileCommands({&buildcc_lib}).Generate(); // - Plugin Graph - std::string output = reg.GetTaskflow().dump(); + std::string output = Reg::GetTaskflow().dump(); const bool saved = env::save_file("graph.dot", output, false); env::assert_fatal(saved, "Could not save graph.dot file"); diff --git a/bootstrap/src/build_buildcc.cpp b/bootstrap/src/build_buildcc.cpp index 0d367c3d..2cef25fa 100644 --- a/bootstrap/src/build_buildcc.cpp +++ b/bootstrap/src/build_buildcc.cpp @@ -196,51 +196,52 @@ void BuildBuildCC::Setup(const ArgToolchainState &state) { TargetEnv(env_.GetTargetRootDir() / "third_party" / "flatbuffers", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, global_flags_cb, flatc_exe, toolchain_); - reg_.Build(state, build_flatc_exe_cb, flatc_exe); + auto &toolchain_instance = Reg::Toolchain(state) + .Func(global_flags_cb, flatc_exe, toolchain_) + .Build(build_flatc_exe_cb, flatc_exe); // Schema auto &schema_gen = storage_.Add( kSchemaGenName, kSchemaGenName, TargetEnv(env_.GetTargetRootDir() / "buildcc" / "schema", env_.GetTargetBuildDir() / toolchain_.GetName())); - reg_.Build(schema_gen_cb, schema_gen, flatc_exe); - reg_.Dep(schema_gen, flatc_exe); + Reg::Call().Build(schema_gen_cb, schema_gen, flatc_exe); + toolchain_instance.Dep(schema_gen, flatc_exe); // Flatbuffers HO lib auto &flatbuffers_ho_lib = storage_.Add( kFlatbuffersHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "flatbuffers", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, flatbuffers_ho_cb, flatbuffers_ho_lib); + toolchain_instance.Func(flatbuffers_ho_cb, flatbuffers_ho_lib); // CLI11 HO lib auto &cli11_ho_lib = storage_.Add( kCli11HoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "CLI11", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, cli11_ho_cb, cli11_ho_lib); + toolchain_instance.Func(cli11_ho_cb, cli11_ho_lib); // fmt HO lib auto &fmt_ho_lib = storage_.Add( kFmtHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "fmt", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, fmt_ho_cb, fmt_ho_lib); + toolchain_instance.Func(fmt_ho_cb, fmt_ho_lib); // spdlog HO lib auto &spdlog_ho_lib = storage_.Add( kSpdlogHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "spdlog", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, spdlog_ho_cb, spdlog_ho_lib); + toolchain_instance.Func(spdlog_ho_cb, spdlog_ho_lib); // taskflow HO lib auto &taskflow_ho_lib = storage_.Add( kTaskflowHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "taskflow", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, taskflow_ho_cb, taskflow_ho_lib); + toolchain_instance.Func(taskflow_ho_cb, taskflow_ho_lib); // Tiny-process-library lib // TODO, Make this a generic selection between StaticTarget and @@ -250,21 +251,22 @@ void BuildBuildCC::Setup(const ArgToolchainState &state) { TargetEnv(env_.GetTargetRootDir() / "third_party" / "tiny-process-library", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, global_flags_cb, tpl_lib, toolchain_); + toolchain_instance.Func(global_flags_cb, tpl_lib, toolchain_); TplConfig tpl_config; tpl_config.os_id = get_host_os(); - reg_.Build(state, tpl_cb, tpl_lib, tpl_config); + toolchain_instance.Build(tpl_cb, tpl_lib, tpl_config); // TODO, Make this a generic selection between StaticTarget and // DynamicTarget auto &buildcc_lib = storage_.Add( kBuildccLibName, kBuildccLibName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "buildcc", env_.GetTargetBuildDir())); - reg_.CallbackIf(state, global_flags_cb, buildcc_lib, toolchain_); - reg_.Build(state, buildcc_cb, buildcc_lib, schema_gen, flatbuffers_ho_lib, - fmt_ho_lib, spdlog_ho_lib, cli11_ho_lib, taskflow_ho_lib, tpl_lib); - reg_.Dep(buildcc_lib, schema_gen); - reg_.Dep(buildcc_lib, tpl_lib); + toolchain_instance.Func(global_flags_cb, buildcc_lib, toolchain_); + toolchain_instance + .Build(buildcc_cb, buildcc_lib, schema_gen, flatbuffers_ho_lib, + fmt_ho_lib, spdlog_ho_lib, cli11_ho_lib, taskflow_ho_lib, tpl_lib) + .Dep(buildcc_lib, schema_gen) + .Dep(buildcc_lib, tpl_lib); } } // namespace buildcc diff --git a/buildexe/buildexe.cpp b/buildexe/buildexe.cpp index 0af85b3f..16549953 100644 --- a/buildexe/buildexe.cpp +++ b/buildexe/buildexe.cpp @@ -53,8 +53,8 @@ int main(int argc, char **argv) { // TODO, Add libraries (git cloned) // TODO, Add extension (git cloned) - Register reg; - reg.Clean(clean_cb); + Reg::Init(); + Reg::Call(Args::Clean()).Func(clean_cb); // Host Toolchain BaseToolchain toolchain = @@ -66,7 +66,7 @@ int main(int argc, char **argv) { } // Build Target - BuildEnvSetup build_setup(reg, toolchain, buildexe_args); + BuildEnvSetup build_setup(toolchain, buildexe_args); build_setup.ConstructTarget(); // Run Target if script mode diff --git a/buildexe/include/buildexe/build_env_setup.h b/buildexe/include/buildexe/build_env_setup.h index d73c9e9c..e36983d4 100644 --- a/buildexe/include/buildexe/build_env_setup.h +++ b/buildexe/include/buildexe/build_env_setup.h @@ -31,9 +31,9 @@ class BuildEnvSetup { static constexpr const char *const kUserTargetName = "UserTarget"; public: - BuildEnvSetup(Register ®, const BaseToolchain &toolchain, + BuildEnvSetup(const BaseToolchain &toolchain, const BuildExeArgs &buildexe_args) - : reg_(reg), toolchain_(toolchain), buildexe_args_(buildexe_args) { + : toolchain_(toolchain), buildexe_args_(buildexe_args) { state_.build = true; } @@ -62,7 +62,6 @@ class BuildEnvSetup { void DepUserTargetOnBuildcc(); private: - Register ®_; const BaseToolchain &toolchain_; const BuildExeArgs &buildexe_args_; diff --git a/buildexe/src/build_env_setup.cpp b/buildexe/src/build_env_setup.cpp index 2bfcac96..72b17fba 100644 --- a/buildexe/src/build_env_setup.cpp +++ b/buildexe/src/build_env_setup.cpp @@ -29,7 +29,7 @@ void BuildEnvSetup::ConstructTarget() { // user target ConstructUserTarget(); } - reg_.RunBuild(); + Reg::Run(); } void BuildEnvSetup::RunUserTarget(const ArgScriptInfo &arg_script_info) { @@ -76,7 +76,7 @@ void BuildEnvSetup::ConstructUserTargetWithBuildcc() { void BuildEnvSetup::BuildccTargetSetup() { const fs::path &buildcc_base = BuildccHome::GetBuildccBaseDir(); auto &buildcc_package = storage_.Add( - kBuildccPackageName, reg_, toolchain_, + kBuildccPackageName, toolchain_, TargetEnv(buildcc_base, buildcc_base / "_build_exe")); buildcc_package.Setup(state_); } @@ -206,12 +206,12 @@ struct BuildExeLibDir {{ } void BuildEnvSetup::UserTargetBuild() { - reg_.Build( - state_, [](BaseTarget &target) { target.Build(); }, GetUserTarget()); + Reg::Toolchain(state_).Build([](BaseTarget &target) { target.Build(); }, + GetUserTarget()); } void BuildEnvSetup::DepUserTargetOnBuildcc() { - reg_.Dep(GetUserTarget(), GetBuildcc()); + Reg::Toolchain(state_).Dep(GetUserTarget(), GetBuildcc()); } } // namespace buildcc From 991839e9e25002f39ba80d95f8aea7ff88fb4820 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 07:00:57 -0700 Subject: [PATCH 14/39] Update build.main.cpp --- example/buildexe/libs/build.main.cpp | 45 ++++++++++++---------------- 1 file changed, 19 insertions(+), 26 deletions(-) diff --git a/example/buildexe/libs/build.main.cpp b/example/buildexe/libs/build.main.cpp index c051e83b..64301e32 100644 --- a/example/buildexe/libs/build.main.cpp +++ b/example/buildexe/libs/build.main.cpp @@ -16,49 +16,42 @@ static void clean_cb(); static void hello_world_build_cb(BaseTarget &target, BaseTarget &fmt_lib); int main(int argc, char **argv) { - // 1. Get arguments - Args::Init(); + // Get arguments ArgToolchain arg_gcc; - Args::AddToolchain("gcc", "Generic gcc toolchain", arg_gcc); - Args::Parse(argc, argv); + Args::Init() + .AddToolchain("gcc", "Generic gcc toolchain", arg_gcc) + .Parse(argc, argv); - // 2. Initialize your environment - Register reg; + // Initialize your environment + Reg::Init(); - // 3. Pre-build steps - reg.Clean(clean_cb); + // Pre-build steps + Reg::Call(Args::Clean()).Func(clean_cb); - // 4. Build steps + // Build steps // Explicit toolchain - target pairs Toolchain_gcc gcc; - auto verified_toolchains = gcc.Verify(); - env::assert_fatal(!verified_toolchains.empty(), "GCC Toolchain not found"); StaticTarget_gcc fmt_lib( "libfmt", gcc, TargetEnv(BuildExeLibDir::fmt, Project::GetBuildDir() / "fmt")); FmtConfig fmt_config; - reg.Build(arg_gcc.state, build_fmt_cb, fmt_lib, fmt_config); - ExecutableTarget_gcc hello_world("hello_world", gcc, ""); - reg.Build(arg_gcc.state, hello_world_build_cb, hello_world, fmt_lib); - - reg.Dep(hello_world, fmt_lib); - - // 5. Test steps - reg.Test(arg_gcc.state, "{executable}", hello_world); - - // 6. Build Target - reg.RunBuild(); + Reg::Toolchain(arg_gcc.state) + .Func([&]() { gcc.Verify(); }) + .Build(build_fmt_cb, fmt_lib, fmt_config) + .Build(hello_world_build_cb, hello_world, fmt_lib) + .Dep(hello_world, fmt_lib) + .Test("{executable}", hello_world); - // 7. Test Target - reg.RunTest(); + // Build Target + Reg::Run(); - // 8. Post Build steps + // Post Build steps // - Clang Compile Commands plugin::ClangCompileCommands({&hello_world}).Generate(); // - Graphviz dump - std::cout << reg.GetTaskflow().dump() << std::endl; + std::cout << Reg::GetTaskflow().dump() << std::endl; return 0; } From f8f3bac7802f59d9a70ce1956c5f22e5804b6486 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 07:11:43 -0700 Subject: [PATCH 15/39] Updated Register --- buildcc/lib/args/include/args/register.h | 1 + buildcc/lib/args/src/register.cpp | 5 +++++ 2 files changed, 6 insertions(+) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 8a931c39..ecbb4b4c 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -227,6 +227,7 @@ class Reg { public: static void Init(); + static void Deinit(); static void Run(const RegConfig &config = RegConfig()); static const tf::Taskflow &GetTaskflow(); static CallbackInstance Call(bool condition = true); diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index b539ea82..81ce3d5f 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -78,6 +78,11 @@ void Reg::Init() { } } +void Reg::Deinit() { + Project::Deinit(); + is_init_ = false; +} + void Reg::Run(const RegConfig &config) { if (config.pre_build_cb) { config.pre_build_cb(); From 4c76a28c99e0d687d2a7db5f85f1975736f5c9b3 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Fri, 1 Apr 2022 08:07:31 -0700 Subject: [PATCH 16/39] Updated register --- buildcc/lib/args/include/args/register.h | 10 +++++++--- buildcc/lib/args/src/register.cpp | 20 ++++++++++++++------ 2 files changed, 21 insertions(+), 9 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index ecbb4b4c..c5b08348 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -186,7 +186,8 @@ class Reg { template ToolchainInstance &Build(const C &build_cb, BaseTarget &target, Params &&...params) { - reg_.Build(condition_, build_cb, target, std::forward(params)...); + Ref().Build(condition_, build_cb, target, + std::forward(params)...); return *this; } ToolchainInstance &Dep(const internal::BuilderInterface &target, @@ -216,7 +217,7 @@ class Reg { CallbackInstance &Build(const C &build_cb, BaseGenerator &generator, Params &&...params) { if (condition_) { - reg_.Build(build_cb, generator, std::forward(params)...); + Ref().Build(build_cb, generator, std::forward(params)...); } return *this; } @@ -233,9 +234,12 @@ class Reg { static CallbackInstance Call(bool condition = true); static ToolchainInstance Toolchain(const ArgToolchainState &condition); +private: + static Register &Ref(); + private: static bool is_init_; - static Register reg_; + static std::unique_ptr reg_; }; } // namespace buildcc diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 81ce3d5f..4ca58bda 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -66,10 +66,11 @@ void DepDetectCyclicDependency(const tf::Task &target_task, namespace buildcc { bool Reg::is_init_{false}; -Register Reg::reg_; +std::unique_ptr Reg::reg_; void Reg::Init() { if (!is_init_) { + reg_ = std::make_unique(); env::assert_fatal(Args::IsParsed(), "Setup your Args"); Project::Init(fs::current_path() / Args::GetProjectRootDir(), fs::current_path() / Args::GetProjectBuildDir()); @@ -79,25 +80,32 @@ void Reg::Init() { } void Reg::Deinit() { + reg_.reset(nullptr); Project::Deinit(); is_init_ = false; } void Reg::Run(const RegConfig &config) { + auto &ref = Ref(); if (config.pre_build_cb) { config.pre_build_cb(); } - reg_.RunBuild(); + ref.RunBuild(); if (config.post_build_cb) { config.post_build_cb(); } - reg_.RunTest(); + ref.RunTest(); if (config.post_test_cb) { config.post_test_cb(); } } -const tf::Taskflow &Reg::GetTaskflow() { return reg_.GetTaskflow(); } +const tf::Taskflow &Reg::GetTaskflow() { return Ref().GetTaskflow(); } + +Register &Reg::Ref() { + env::assert_fatal(reg_ != nullptr, kRegkNotInit); + return *reg_; +} Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { env::assert_fatal(is_init_, kRegkNotInit); @@ -107,14 +115,14 @@ Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { Reg::ToolchainInstance & Reg::ToolchainInstance::Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency) { - reg_.Dep(target, dependency); + Ref().Dep(target, dependency); return *this; } Reg::ToolchainInstance &Reg::ToolchainInstance::Test(const std::string &command, const BaseTarget &target, const TestConfig &config) { - reg_.Test(condition_, command, target, config); + Ref().Test(condition_, command, target, config); return *this; } From 3ce59752d9e2088d999a2a51e9978f475c20f786 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 08:50:34 -0700 Subject: [PATCH 17/39] Update test_register.cpp --- buildcc/lib/args/test/test_register.cpp | 382 +++++++++++++----------- 1 file changed, 201 insertions(+), 181 deletions(-) diff --git a/buildcc/lib/args/test/test_register.cpp b/buildcc/lib/args/test/test_register.cpp index bcd6b191..28e18d0d 100644 --- a/buildcc/lib/args/test/test_register.cpp +++ b/buildcc/lib/args/test/test_register.cpp @@ -15,6 +15,7 @@ TEST_GROUP(RegisterTestGroup) { void teardown() { + buildcc::Reg::Deinit(); buildcc::Args::Deinit(); mock().clear(); } @@ -32,7 +33,7 @@ TEST(RegisterTestGroup, Register_Initialize) { CHECK(buildcc::Args::GetLogLevel() == buildcc::env::LogLevel::Trace); CHECK_TRUE(buildcc::Args::Clean()); - buildcc::Register reg; + buildcc::Reg::Init(); } TEST(RegisterTestGroup, Register_Clean) { @@ -47,9 +48,12 @@ TEST(RegisterTestGroup, Register_Clean) { CHECK(buildcc::Args::GetLogLevel() == buildcc::env::LogLevel::Trace); CHECK_TRUE(buildcc::Args::Clean()); - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectOneCall("CleanCb"); - reg.Clean([]() { mock().actualCall("CleanCb"); }); + buildcc::Reg::Call(buildcc::Args::Clean()).Func([]() { + mock().actualCall("CleanCb"); + }); + buildcc::Reg::Deinit(); buildcc::Args::Deinit(); } @@ -70,8 +74,11 @@ TEST(RegisterTestGroup, Register_Clean) { CHECK(buildcc::Args::GetLogLevel() == buildcc::env::LogLevel::Trace); CHECK_FALSE(buildcc::Args::Clean()); - buildcc::Register reg; - reg.Clean([]() { mock().actualCall("CleanCb"); }); + buildcc::Reg::Init(); + buildcc::Reg::Call(buildcc::Args::Clean()).Func([]() { + mock().actualCall("CleanCb"); + }); + buildcc::Reg::Deinit(); buildcc::Args::Deinit(); } @@ -108,18 +115,20 @@ TEST(RegisterTestGroup, Register_Build) { { buildcc::ArgToolchainState state{false, false}; - buildcc::Register reg; - reg.Build( - state, [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(state).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Deinit(); } { buildcc::ArgToolchainState state{true, true}; - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - state, [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(state).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); @@ -167,43 +176,48 @@ TEST(RegisterTestGroup, Register_NoBuildAndDep) { // T0D0 { - buildcc::Register reg; - CHECK_THROWS(std::exception, reg.Dep(target, dependency)); + buildcc::Reg::Init(); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency)); + buildcc::Reg::Deinit(); } // T0D1 { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_depT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency); - CHECK_THROWS(std::exception, reg.Dep(target, dependency)); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency)); + buildcc::Reg::Deinit(); } // T1D0 { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); - CHECK_THROWS(std::exception, reg.Dep(target, dependency)); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency)); + buildcc::Reg::Deinit(); } // T1D1 { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); mock().expectNCalls(1, "BuildTask_depT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency); - reg.Dep(target, dependency); + buildcc::Reg::Toolchain(trueState).Dep(target, dependency); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); @@ -251,54 +265,48 @@ TEST(RegisterTestGroup, Register_BuildAndDep) { // T0D0 { - buildcc::Register reg; - reg.Build( - falseState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - falseState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - - reg.Dep(target, dependency); + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(falseState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target) + .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency) + .Dep(target, dependency); + buildcc::Reg::Deinit(); } // T0D1 { - buildcc::Register reg; - reg.Build( - falseState, [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(falseState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); mock().expectNCalls(1, "BuildTask_depT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - - reg.Dep(target, dependency); + buildcc::Reg::Toolchain(trueState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency) + .Dep(target, dependency); + buildcc::Reg::Deinit(); } // T1D0 { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - falseState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - - reg.Dep(target, dependency); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(falseState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency); + buildcc::Reg::Toolchain(trueState).Dep(target, dependency); + buildcc::Reg::Deinit(); } // T1D1 { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); mock().expectNCalls(1, "BuildTask_depT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - - reg.Dep(target, dependency); + buildcc::Reg::Toolchain(trueState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target) + .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency) + .Dep(target, dependency); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); @@ -340,41 +348,41 @@ TEST(RegisterTestGroup, Register_DepDuplicate) { // Duplicate dependency with 2 Targets { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); mock().expectNCalls(1, "BuildTask_depT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - - reg.Dep(target, dependency); - CHECK_THROWS(std::exception, reg.Dep(target, dependency)); + buildcc::Reg::Toolchain(trueState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target) + .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency) + .Dep(target, dependency); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency)); + buildcc::Reg::Deinit(); } // Duplicate dependency with 3 Targets { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); mock().expectNCalls(1, "BuildTask_depT"); mock().expectNCalls(1, "BuildTask_dep2T"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency2); - - reg.Dep(dependency, dependency2); - reg.Dep(target, dependency); - reg.Dep(target, dependency2); - - CHECK_THROWS(std::exception, reg.Dep(target, dependency)); - CHECK_THROWS(std::exception, reg.Dep(target, dependency2)); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency2); + + buildcc::Reg::Toolchain(trueState).Dep(dependency, dependency2); + buildcc::Reg::Toolchain(trueState).Dep(target, dependency); + buildcc::Reg::Toolchain(trueState).Dep(target, dependency2); + + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency)); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency2)); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); @@ -416,40 +424,41 @@ TEST(RegisterTestGroup, Register_DepCyclic) { // Immediate cyclic depdendency { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); mock().expectNCalls(1, "BuildTask_depT"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - - reg.Dep(target, dependency); - CHECK_THROWS(std::exception, reg.Dep(dependency, target)); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency); + + buildcc::Reg::Toolchain(trueState).Dep(target, dependency); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(dependency, target)); + buildcc::Reg::Deinit(); } // Duplicate dependency with 3 Targets { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); mock().expectNCalls(1, "BuildTask_depT"); mock().expectNCalls(1, "BuildTask_dep2T"); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, target); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency); - reg.Build( - trueState, [](buildcc::BaseTarget &target) { (void)target; }, - dependency2); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency); + buildcc::Reg::Toolchain(trueState).Build( + [](buildcc::BaseTarget &target) { (void)target; }, dependency2); - reg.Dep(dependency, dependency2); - reg.Dep(target, dependency); + buildcc::Reg::Toolchain(trueState).Dep(dependency, dependency2); + buildcc::Reg::Toolchain(trueState).Dep(target, dependency); // dependency2 -> dependency -> target -> dependency2 - CHECK_THROWS(std::exception, reg.Dep(dependency2, target)); + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(dependency2, target)); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); @@ -498,43 +507,48 @@ TEST(RegisterTestGroup, Register_Test) { // FF { - buildcc::Register reg; - reg.Test(stateFail, "{executable}", target); + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(stateFail).Test("{executable}", target); + buildcc::Reg::Deinit(); } // TF { - buildcc::Register reg; - reg.Test(state1, "{executable}", target); + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(state1).Test("{executable}", target); + buildcc::Reg::Deinit(); } // FT { - buildcc::Register reg; - reg.Test(state2, "{executable}", target); + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(state2).Test("{executable}", target); + buildcc::Reg::Deinit(); } // TT // Register::Build not called { - buildcc::Register reg; - CHECK_THROWS(std::exception, - reg.Test(stateSuccess, "{executable}", target)); + buildcc::Reg::Init(); + CHECK_THROWS( + std::exception, + buildcc::Reg::Toolchain(stateSuccess).Test("{executable}", target)); + buildcc::Reg::Deinit(); } // Correct Usage { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test(stateSuccess, "{executable}", target); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess).Test("{executable}", target); std::vector stdout_data; std::vector stderr_data; buildcc::env::m::CommandExpect_Execute(1, true, &stdout_data, &stderr_data); - reg.RunTest(); + buildcc::Reg::Run(); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); @@ -575,105 +589,111 @@ TEST(RegisterTestGroup, Register_TestWithOutput) { // TestOutput::Type::DefaultBehaviour { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test( - stateSuccess, "{executable}", target, - buildcc::TestConfig( - {}, {}, - buildcc::TestOutput(buildcc::TestOutput::Type::DefaultBehaviour))); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess) + .Test("{executable}", target, + buildcc::TestConfig( + {}, {}, + buildcc::TestOutput( + buildcc::TestOutput::Type::DefaultBehaviour))); buildcc::env::m::CommandExpect_Execute(1, true); - reg.RunTest(); + buildcc::Reg::Run(); + buildcc::Reg::Deinit(); } // TestOutput::Type::TestPrintOnStderr { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test( - stateSuccess, "{executable}", target, - buildcc::TestConfig( - {}, {}, - buildcc::TestOutput(buildcc::TestOutput::Type::TestPrintOnStderr))); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess) + .Test("{executable}", target, + buildcc::TestConfig( + {}, {}, + buildcc::TestOutput( + buildcc::TestOutput::Type::TestPrintOnStderr))); std::vector stderr_data; buildcc::env::m::CommandExpect_Execute(1, true, nullptr, &stderr_data); - reg.RunTest(); + buildcc::Reg::Run(); + buildcc::Reg::Deinit(); } // TestOutput::Type::TestPrintOnStdout { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test( - stateSuccess, "{executable}", target, - buildcc::TestConfig( - {}, {}, - buildcc::TestOutput(buildcc::TestOutput::Type::TestPrintOnStdout))); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess) + .Test("{executable}", target, + buildcc::TestConfig( + {}, {}, + buildcc::TestOutput( + buildcc::TestOutput::Type::TestPrintOnStdout))); std::vector stdout_data; buildcc::env::m::CommandExpect_Execute(1, true, &stdout_data, nullptr); - reg.RunTest(); + buildcc::Reg::Run(); + buildcc::Reg::Deinit(); } // TestOutput::Type::TestPrintOnStderrAndStdout { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test(stateSuccess, "{executable}", target, - buildcc::TestConfig( - {}, {}, - buildcc::TestOutput( - buildcc::TestOutput::Type::TestPrintOnStderrAndStdout))); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess) + .Test("{executable}", target, + buildcc::TestConfig( + {}, {}, + buildcc::TestOutput( + buildcc::TestOutput::Type::TestPrintOnStderrAndStdout))); std::vector stdout_data; std::vector stderr_data; buildcc::env::m::CommandExpect_Execute(1, true, &stdout_data, &stderr_data); - reg.RunTest(); + buildcc::Reg::Run(); + buildcc::Reg::Deinit(); } // TestOutput::Type::UserRedirect { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test(stateSuccess, "{executable}", target, - buildcc::TestConfig( - {}, {}, - buildcc::TestOutput(buildcc::TestOutput::Type::UserRedirect, - nullptr, nullptr))); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess) + .Test("{executable}", target, + buildcc::TestConfig( + {}, {}, + buildcc::TestOutput(buildcc::TestOutput::Type::UserRedirect, + nullptr, nullptr))); buildcc::env::m::CommandExpect_Execute(1, true); - reg.RunTest(); + buildcc::Reg::Run(); + buildcc::Reg::Deinit(); } // TestOutput::Type::UserRedirect { - buildcc::Register reg; + buildcc::Reg::Init(); mock().expectNCalls(1, "BuildTask_dummyT"); - reg.Build( - stateSuccess, [](buildcc::BaseTarget &target) { (void)target; }, - target); - reg.Test( - stateSuccess, "{executable}", target, - buildcc::TestConfig( - {}, {}, buildcc::TestOutput(buildcc::TestOutput::Type(65535)))); - CHECK_THROWS(std::exception, reg.RunTest()); + buildcc::Reg::Toolchain(stateSuccess) + .Build([](buildcc::BaseTarget &target) { (void)target; }, target); + buildcc::Reg::Toolchain(stateSuccess) + .Test( + "{executable}", target, + buildcc::TestConfig( + {}, {}, buildcc::TestOutput(buildcc::TestOutput::Type(65535)))); + CHECK_THROWS(std::exception, buildcc::Reg::Run()); + buildcc::Reg::Deinit(); } buildcc::Project::Deinit(); From b4d6faf01c592b5c7eba5cea3ac02ec403f06a5f Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 08:51:21 -0700 Subject: [PATCH 18/39] Updated register, Shifted internally --- buildcc/lib/args/include/args/register.h | 139 +++++++++++------------ buildcc/lib/args/mock/tasks.cpp | 8 +- buildcc/lib/args/src/register.cpp | 32 +++--- buildcc/lib/args/src/tasks.cpp | 8 +- 4 files changed, 88 insertions(+), 99 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index c5b08348..e862bf42 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -31,11 +31,32 @@ namespace buildcc { -class Register { +class Reg { +private: + // TODO, Rename to Instance + class Register; + class CallbackInstance; + class ToolchainInstance; + public: - Register() = default; - Register(const Register &) = delete; + static void Init(); + static void Deinit(); + static void Run(const std::function &post_build_cb = []() {}); + static CallbackInstance Call(bool condition = true); + static ToolchainInstance Toolchain(const ArgToolchainState &condition); + + static const tf::Taskflow &GetTaskflow(); + +private: + static Register &Ref(); +private: + static bool is_init_; + static std::unique_ptr reg_; +}; + +class Reg::Register { +public: /** * @brief Folders and files that need to be cleaned when `clean == true` */ @@ -161,85 +182,59 @@ class Register { tf::Executor executor_; }; -struct RegConfig { - std::function pre_build_cb; - std::function post_build_cb; - std::function post_test_cb; -}; - -class Reg { -private: - class ToolchainInstance { - public: - ToolchainInstance(const ArgToolchainState &condition) - : condition_(condition) {} - - // Duplicated code - template - ToolchainInstance &Func(const C &cb, Params &&...params) { - if (condition_.build) { - cb(std::forward(params)...); - } - return *this; - } +class Reg::CallbackInstance { +public: + CallbackInstance(bool condition = true) : condition_(condition) {} - template - ToolchainInstance &Build(const C &build_cb, BaseTarget &target, - Params &&...params) { - Ref().Build(condition_, build_cb, target, - std::forward(params)...); - return *this; - } - ToolchainInstance &Dep(const internal::BuilderInterface &target, - const internal::BuilderInterface &dependency); - ToolchainInstance &Test(const std::string &command, - const BaseTarget &target, - const TestConfig &config = TestConfig()); - - private: - ArgToolchainState condition_; - }; - - class CallbackInstance { - public: - CallbackInstance(bool condition = true) : condition_(condition) {} - - // Duplicated code - template - CallbackInstance &Func(const C &cb, Params &&...params) { - if (condition_) { - cb(std::forward(params)...); - } - return *this; + // Duplicated code + template + CallbackInstance &Func(const C &cb, Params &&...params) { + if (condition_) { + cb(std::forward(params)...); } + return *this; + } - template - CallbackInstance &Build(const C &build_cb, BaseGenerator &generator, - Params &&...params) { - if (condition_) { - Ref().Build(build_cb, generator, std::forward(params)...); - } - return *this; + template + CallbackInstance &Build(const C &build_cb, BaseGenerator &generator, + Params &&...params) { + if (condition_) { + Ref().Build(build_cb, generator, std::forward(params)...); } + return *this; + } - private: - bool condition_; - }; +private: + bool condition_; +}; +class Reg::ToolchainInstance { public: - static void Init(); - static void Deinit(); - static void Run(const RegConfig &config = RegConfig()); - static const tf::Taskflow &GetTaskflow(); - static CallbackInstance Call(bool condition = true); - static ToolchainInstance Toolchain(const ArgToolchainState &condition); + ToolchainInstance(const ArgToolchainState &condition) + : condition_(condition) {} -private: - static Register &Ref(); + // Duplicated code + template + ToolchainInstance &Func(const C &cb, Params &&...params) { + if (condition_.build) { + cb(std::forward(params)...); + } + return *this; + } + + template + ToolchainInstance &Build(const C &build_cb, BaseTarget &target, + Params &&...params) { + Ref().Build(condition_, build_cb, target, std::forward(params)...); + return *this; + } + ToolchainInstance &Dep(const internal::BuilderInterface &target, + const internal::BuilderInterface &dependency); + ToolchainInstance &Test(const std::string &command, const BaseTarget &target, + const TestConfig &config = TestConfig()); private: - static bool is_init_; - static std::unique_ptr reg_; + ArgToolchainState condition_; }; } // namespace buildcc diff --git a/buildcc/lib/args/mock/tasks.cpp b/buildcc/lib/args/mock/tasks.cpp index 939e0100..8fd65666 100644 --- a/buildcc/lib/args/mock/tasks.cpp +++ b/buildcc/lib/args/mock/tasks.cpp @@ -4,20 +4,20 @@ namespace buildcc { -tf::Task Register::BuildTargetTask(BaseTarget &target) { +tf::Task Reg::Register::BuildTargetTask(BaseTarget &target) { mock().actualCall(fmt::format("BuildTask_{}", target.GetName()).c_str()); return build_tf_.placeholder().name(target.GetUniqueId()); } -tf::Task Register::BuildGeneratorTask(BaseGenerator &generator) { +tf::Task Reg::Register::BuildGeneratorTask(BaseGenerator &generator) { mock().actualCall( fmt::format("BuildGeneratorTask_{}", generator.GetName()).c_str()); return build_tf_.placeholder().name(generator.GetUniqueId()); } -void Register::RunBuild() {} +void Reg::Register::RunBuild() {} -void Register::RunTest() { +void Reg::Register::RunTest() { std::for_each(tests_.begin(), tests_.end(), [](const auto &p) { p.second.TestRunner(); }); } diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 4ca58bda..94d3ddcf 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -66,7 +66,7 @@ void DepDetectCyclicDependency(const tf::Task &target_task, namespace buildcc { bool Reg::is_init_{false}; -std::unique_ptr Reg::reg_; +std::unique_ptr Reg::reg_; void Reg::Init() { if (!is_init_) { @@ -85,24 +85,18 @@ void Reg::Deinit() { is_init_ = false; } -void Reg::Run(const RegConfig &config) { +void Reg::Run(const std::function &post_build_cb) { auto &ref = Ref(); - if (config.pre_build_cb) { - config.pre_build_cb(); - } ref.RunBuild(); - if (config.post_build_cb) { - config.post_build_cb(); + if (post_build_cb) { + post_build_cb(); } ref.RunTest(); - if (config.post_test_cb) { - config.post_test_cb(); - } } const tf::Taskflow &Reg::GetTaskflow() { return Ref().GetTaskflow(); } -Register &Reg::Ref() { +Reg::Register &Reg::Ref() { env::assert_fatal(reg_ != nullptr, kRegkNotInit); return *reg_; } @@ -131,14 +125,14 @@ Reg::CallbackInstance Reg::Call(bool condition) { return CallbackInstance(condition); } -void Register::Clean(const std::function &clean_cb) { +void Reg::Register::Clean(const std::function &clean_cb) { if (Args::Clean()) { clean_cb(); } } -void Register::Dep(const internal::BuilderInterface &target, - const internal::BuilderInterface &dependency) { +void Reg::Register::Dep(const internal::BuilderInterface &target, + const internal::BuilderInterface &dependency) { const auto target_iter = build_.find(target.GetUniqueId()); const auto dep_iter = build_.find(dependency.GetUniqueId()); env::assert_fatal(!(target_iter == build_.end() || dep_iter == build_.end()), @@ -158,9 +152,9 @@ void Register::Dep(const internal::BuilderInterface &target, target_iter->second.succeed(dep_iter->second); } -void Register::Test(const ArgToolchainState &toolchain_state, - const std::string &command, const BaseTarget &target, - const TestConfig &config) { +void Reg::Register::Test(const ArgToolchainState &toolchain_state, + const std::string &command, const BaseTarget &target, + const TestConfig &config) { if (!(toolchain_state.build && toolchain_state.test)) { return; } @@ -179,8 +173,8 @@ void Register::Test(const ArgToolchainState &toolchain_state, // Private -void Register::BuildStoreTask(const std::string &unique_id, - const tf::Task &task) { +void Reg::Register::BuildStoreTask(const std::string &unique_id, + const tf::Task &task) { const bool stored = build_.emplace(unique_id, task).second; env::assert_fatal( stored, fmt::format("Duplicate `Register::Build` call detected for '{}'", diff --git a/buildcc/lib/args/src/tasks.cpp b/buildcc/lib/args/src/tasks.cpp index 97e9cc4a..02d6f977 100644 --- a/buildcc/lib/args/src/tasks.cpp +++ b/buildcc/lib/args/src/tasks.cpp @@ -20,16 +20,16 @@ namespace buildcc { -tf::Task Register::BuildTargetTask(BaseTarget &target) { +tf::Task Reg::Register::BuildTargetTask(BaseTarget &target) { return build_tf_.composed_of(target.GetTaskflow()).name(target.GetUniqueId()); } -tf::Task Register::BuildGeneratorTask(BaseGenerator &generator) { +tf::Task Reg::Register::BuildGeneratorTask(BaseGenerator &generator) { return build_tf_.composed_of(generator.GetTaskflow()) .name(generator.GetUniqueId()); } -void Register::RunBuild() { +void Reg::Register::RunBuild() { env::log_info(__FUNCTION__, fmt::format("Running with {} workers", executor_.num_workers())); executor_.run(build_tf_); @@ -38,7 +38,7 @@ void Register::RunBuild() { "Task state is not successful!"); } -void Register::RunTest() { +void Reg::Register::RunTest() { tf::Taskflow test_tf{"Tests"}; test_tf.for_each( tests_.begin(), tests_.end(), From 7b35311c0512cc9236b9831dc1744c1ae2d4c01a Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 08:51:26 -0700 Subject: [PATCH 19/39] Update build.cpp --- example/hybrid/generic/build.cpp | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/example/hybrid/generic/build.cpp b/example/hybrid/generic/build.cpp index 22876504..f5631b03 100644 --- a/example/hybrid/generic/build.cpp +++ b/example/hybrid/generic/build.cpp @@ -53,11 +53,7 @@ int main(int argc, char **argv) { .Test("{executable}", generic_target); // Build Target - RegConfig reg_config; - reg_config.post_build_cb = [&]() { - post_build_cb(generic_target, foolib_target); - }; - Reg::Run(reg_config); + Reg::Run([&]() { post_build_cb(generic_target, foolib_target); }); // - Clang Compile Commands plugin::ClangCompileCommands({&foolib_target, &generic_target}).Generate(); From 623aefd2f33d065d95da8516eaf974570e11d1c0 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 09:20:32 -0700 Subject: [PATCH 20/39] Renamed Register to Instance Instance is now nested as Reg::Instance --- buildcc/lib/args/include/args/args.h | 3 +-- buildcc/lib/args/include/args/register.h | 23 +++++++++---------- .../args/include/args/register/test_info.h | 4 ++-- buildcc/lib/args/mock/tasks.cpp | 8 +++---- buildcc/lib/args/src/register.cpp | 22 +++++++++--------- buildcc/lib/args/src/tasks.cpp | 8 +++---- buildcc/lib/args/test/test_register.cpp | 2 +- 7 files changed, 34 insertions(+), 36 deletions(-) diff --git a/buildcc/lib/args/include/args/args.h b/buildcc/lib/args/include/args/args.h index 51ebeb05..8387b0ce 100644 --- a/buildcc/lib/args/include/args/args.h +++ b/buildcc/lib/args/include/args/args.h @@ -34,8 +34,7 @@ namespace fs = std::filesystem; namespace buildcc { /** - * @brief Toolchain State used by the Register module to selectively build or - * test targets + * @brief Toolchain State used to selectively build and test targets */ struct ArgToolchainState { bool build{false}; diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index e862bf42..4b62d876 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -33,8 +33,7 @@ namespace buildcc { class Reg { private: - // TODO, Rename to Instance - class Register; + class Instance; class CallbackInstance; class ToolchainInstance; @@ -48,14 +47,14 @@ class Reg { static const tf::Taskflow &GetTaskflow(); private: - static Register &Ref(); + static Instance &Ref(); private: static bool is_init_; - static std::unique_ptr reg_; + static std::unique_ptr reg_; }; -class Reg::Register { +class Reg::Instance { public: /** * @brief Folders and files that need to be cleaned when `clean == true` @@ -96,7 +95,7 @@ class Reg::Register { } /** - * @brief Register the Target to be built + * @brief Reg::Instance for Target to be built */ template void Build(const ArgToolchainState &toolchain_state, const C &build_cb, @@ -113,7 +112,7 @@ class Reg::Register { } /** - * @brief Register the generator to be built + * @brief Reg::Instance for Generator to be built */ template void Build(const C &build_cb, BaseGenerator &generator, Params &&...params) { @@ -124,7 +123,7 @@ class Reg::Register { /** * @brief Setup dependency between 2 Targets - * PreReq: Call `Register::Build` before calling `Register::Dep` + * PreReq: Call `Reg::Instance::Build` before calling `Reg::Instance::Dep` * * Target runs after dependency is built */ @@ -132,8 +131,8 @@ class Reg::Register { const internal::BuilderInterface &dependency); /** - * @brief Register the Target to be run - * PreReq: Call `Register::Build` before calling `Register::Test` + * @brief Instance the Target to be run + * PreReq: Call `Reg::Instance::Build` before calling `Reg::Instance::Test` * PreReq: Requires ArgToolchainState::build && ArgToolchainState::test to be * true * @@ -147,13 +146,13 @@ class Reg::Register { /** * @brief Builds the targets that have been dynamically added through - * `Register::Build` + * `Reg::Instance::Build` */ void RunBuild(); /** * @brief Runs the targets that have been dynamically added through - * `Register::Test` + * `Reg::Instance::Test` */ void RunTest(); diff --git a/buildcc/lib/args/include/args/register/test_info.h b/buildcc/lib/args/include/args/register/test_info.h index 50d61f41..a2e25dc7 100644 --- a/buildcc/lib/args/include/args/register/test_info.h +++ b/buildcc/lib/args/include/args/register/test_info.h @@ -35,7 +35,7 @@ struct TestOutput { }; /** - * @brief Configure your Register::Test to get test output + * @brief Configure your `Reg::Instance::Test` to get test output * * @param output_type Select your output type (behaviour) * @param redirect_stdout User stdout redirection @@ -64,7 +64,7 @@ struct TestOutput { struct TestConfig { public: /** - * @brief Configure your Register::Test using TestConfig + * @brief Configure your `Reg::Instance::Test` using TestConfig * * @param arguments fmt::format args passed to test commands * @param working_directory Working directory from which the test runs diff --git a/buildcc/lib/args/mock/tasks.cpp b/buildcc/lib/args/mock/tasks.cpp index 8fd65666..40bc8eec 100644 --- a/buildcc/lib/args/mock/tasks.cpp +++ b/buildcc/lib/args/mock/tasks.cpp @@ -4,20 +4,20 @@ namespace buildcc { -tf::Task Reg::Register::BuildTargetTask(BaseTarget &target) { +tf::Task Reg::Instance::BuildTargetTask(BaseTarget &target) { mock().actualCall(fmt::format("BuildTask_{}", target.GetName()).c_str()); return build_tf_.placeholder().name(target.GetUniqueId()); } -tf::Task Reg::Register::BuildGeneratorTask(BaseGenerator &generator) { +tf::Task Reg::Instance::BuildGeneratorTask(BaseGenerator &generator) { mock().actualCall( fmt::format("BuildGeneratorTask_{}", generator.GetName()).c_str()); return build_tf_.placeholder().name(generator.GetUniqueId()); } -void Reg::Register::RunBuild() {} +void Reg::Instance::RunBuild() {} -void Reg::Register::RunTest() { +void Reg::Instance::RunTest() { std::for_each(tests_.begin(), tests_.end(), [](const auto &p) { p.second.TestRunner(); }); } diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 94d3ddcf..cbc6623f 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -66,11 +66,11 @@ void DepDetectCyclicDependency(const tf::Task &target_task, namespace buildcc { bool Reg::is_init_{false}; -std::unique_ptr Reg::reg_; +std::unique_ptr Reg::reg_; void Reg::Init() { if (!is_init_) { - reg_ = std::make_unique(); + reg_ = std::make_unique(); env::assert_fatal(Args::IsParsed(), "Setup your Args"); Project::Init(fs::current_path() / Args::GetProjectRootDir(), fs::current_path() / Args::GetProjectBuildDir()); @@ -96,7 +96,7 @@ void Reg::Run(const std::function &post_build_cb) { const tf::Taskflow &Reg::GetTaskflow() { return Ref().GetTaskflow(); } -Reg::Register &Reg::Ref() { +Reg::Instance &Reg::Ref() { env::assert_fatal(reg_ != nullptr, kRegkNotInit); return *reg_; } @@ -125,19 +125,19 @@ Reg::CallbackInstance Reg::Call(bool condition) { return CallbackInstance(condition); } -void Reg::Register::Clean(const std::function &clean_cb) { +void Reg::Instance::Clean(const std::function &clean_cb) { if (Args::Clean()) { clean_cb(); } } -void Reg::Register::Dep(const internal::BuilderInterface &target, +void Reg::Instance::Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency) { const auto target_iter = build_.find(target.GetUniqueId()); const auto dep_iter = build_.find(dependency.GetUniqueId()); env::assert_fatal(!(target_iter == build_.end() || dep_iter == build_.end()), - "Call Register::Build API on target and " - "dependency before Register::Dep API"); + "Call Instance::Build API on target and " + "dependency before Instance::Dep API"); // empty tasks -> not built so skip if (target_iter->second.empty() || dep_iter->second.empty()) { @@ -152,7 +152,7 @@ void Reg::Register::Dep(const internal::BuilderInterface &target, target_iter->second.succeed(dep_iter->second); } -void Reg::Register::Test(const ArgToolchainState &toolchain_state, +void Reg::Instance::Test(const ArgToolchainState &toolchain_state, const std::string &command, const BaseTarget &target, const TestConfig &config) { if (!(toolchain_state.build && toolchain_state.test)) { @@ -162,7 +162,7 @@ void Reg::Register::Test(const ArgToolchainState &toolchain_state, const auto target_iter = build_.find(target.GetUniqueId()); env::assert_fatal( !(target_iter == build_.end()), - "Call Register::Build API on target before Register::Test API"); + "Call Instance::Build API on target before Instance::Test API"); const bool added = tests_.emplace(target.GetUniqueId(), TestInfo(target, command, config)) @@ -173,11 +173,11 @@ void Reg::Register::Test(const ArgToolchainState &toolchain_state, // Private -void Reg::Register::BuildStoreTask(const std::string &unique_id, +void Reg::Instance::BuildStoreTask(const std::string &unique_id, const tf::Task &task) { const bool stored = build_.emplace(unique_id, task).second; env::assert_fatal( - stored, fmt::format("Duplicate `Register::Build` call detected for '{}'", + stored, fmt::format("Duplicate `Instance::Build` call detected for '{}'", unique_id)); } diff --git a/buildcc/lib/args/src/tasks.cpp b/buildcc/lib/args/src/tasks.cpp index 02d6f977..7072ca72 100644 --- a/buildcc/lib/args/src/tasks.cpp +++ b/buildcc/lib/args/src/tasks.cpp @@ -20,16 +20,16 @@ namespace buildcc { -tf::Task Reg::Register::BuildTargetTask(BaseTarget &target) { +tf::Task Reg::Instance::BuildTargetTask(BaseTarget &target) { return build_tf_.composed_of(target.GetTaskflow()).name(target.GetUniqueId()); } -tf::Task Reg::Register::BuildGeneratorTask(BaseGenerator &generator) { +tf::Task Reg::Instance::BuildGeneratorTask(BaseGenerator &generator) { return build_tf_.composed_of(generator.GetTaskflow()) .name(generator.GetUniqueId()); } -void Reg::Register::RunBuild() { +void Reg::Instance::RunBuild() { env::log_info(__FUNCTION__, fmt::format("Running with {} workers", executor_.num_workers())); executor_.run(build_tf_); @@ -38,7 +38,7 @@ void Reg::Register::RunBuild() { "Task state is not successful!"); } -void Reg::Register::RunTest() { +void Reg::Instance::RunTest() { tf::Taskflow test_tf{"Tests"}; test_tf.for_each( tests_.begin(), tests_.end(), diff --git a/buildcc/lib/args/test/test_register.cpp b/buildcc/lib/args/test/test_register.cpp index 28e18d0d..92584c7d 100644 --- a/buildcc/lib/args/test/test_register.cpp +++ b/buildcc/lib/args/test/test_register.cpp @@ -527,7 +527,7 @@ TEST(RegisterTestGroup, Register_Test) { } // TT - // Register::Build not called + // Reg::Instance::Build not called { buildcc::Reg::Init(); CHECK_THROWS( From a7e851ac39c8dab5472196bb7fdc3d4c7ee33865 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 09:38:57 -0700 Subject: [PATCH 21/39] Updated Reg::Instance --- buildcc/lib/args/include/args/register.h | 59 ++++++++---------------- buildcc/lib/args/src/register.cpp | 6 --- 2 files changed, 19 insertions(+), 46 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 4b62d876..5859cb56 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -56,17 +56,12 @@ class Reg { class Reg::Instance { public: - /** - * @brief Folders and files that need to be cleaned when `clean == true` - */ - void Clean(const std::function &clean_cb); - /** * @brief Generic register callback with variable arguments * Can be used to organize code into functional chunks */ template - void Callback(const C &build_cb, Params &&...params) { + static void Callback(const C &build_cb, Params &&...params) { build_cb(std::forward(params)...); } @@ -76,38 +71,25 @@ class Reg::Instance { * Can be used to add Toolchain-Target specific information */ template - void CallbackIf(bool expression, const C &build_cb, Params &&...params) { + static void CallbackIf(bool expression, const C &build_cb, + Params &&...params) { if (expression) { Callback(build_cb, std::forward(params)...); } } - /** - * @brief Generic register callback that is run when `toolchain_state.build == - * true` - * Can be used to add Toolchain-Target specific information - */ - template - void CallbackIf(const ArgToolchainState &toolchain_state, const C &build_cb, - Params &&...params) { - CallbackIf(toolchain_state.build, build_cb, - std::forward(params)...); - } - /** * @brief Reg::Instance for Target to be built */ template void Build(const ArgToolchainState &toolchain_state, const C &build_cb, BaseTarget &target, Params &&...params) { + // TODO, No empty task when .build is false tf::Task task; - CallbackIf( - toolchain_state, - [&](BaseTarget <arget, Params &&...lparams) { - build_cb(ltarget, std::forward(lparams)...); - task = BuildTargetTask(ltarget); - }, - target, std::forward(params)...); + if (toolchain_state.build) { + build_cb(target, std::forward(params)...); + task = BuildTargetTask(target); + } BuildStoreTask(target.GetUniqueId(), task); } @@ -115,10 +97,13 @@ class Reg::Instance { * @brief Reg::Instance for Generator to be built */ template - void Build(const C &build_cb, BaseGenerator &generator, Params &&...params) { - build_cb(generator, std::forward(params)...); - tf::Task task = BuildGeneratorTask(generator); - BuildStoreTask(generator.GetUniqueId(), task); + void Build(bool condition, const C &build_cb, BaseGenerator &generator, + Params &&...params) { + if (condition) { + build_cb(generator, std::forward(params)...); + tf::Task task = BuildGeneratorTask(generator); + BuildStoreTask(generator.GetUniqueId(), task); + } } /** @@ -188,18 +173,15 @@ class Reg::CallbackInstance { // Duplicated code template CallbackInstance &Func(const C &cb, Params &&...params) { - if (condition_) { - cb(std::forward(params)...); - } + Instance::CallbackIf(condition_, cb, std::forward(params)...); return *this; } template CallbackInstance &Build(const C &build_cb, BaseGenerator &generator, Params &&...params) { - if (condition_) { - Ref().Build(build_cb, generator, std::forward(params)...); - } + Ref().Build(condition_, build_cb, generator, + std::forward(params)...); return *this; } @@ -212,12 +194,9 @@ class Reg::ToolchainInstance { ToolchainInstance(const ArgToolchainState &condition) : condition_(condition) {} - // Duplicated code template ToolchainInstance &Func(const C &cb, Params &&...params) { - if (condition_.build) { - cb(std::forward(params)...); - } + Instance::CallbackIf(condition_.build, cb, std::forward(params)...); return *this; } diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index cbc6623f..87bf9e68 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -125,12 +125,6 @@ Reg::CallbackInstance Reg::Call(bool condition) { return CallbackInstance(condition); } -void Reg::Instance::Clean(const std::function &clean_cb) { - if (Args::Clean()) { - clean_cb(); - } -} - void Reg::Instance::Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency) { const auto target_iter = build_.find(target.GetUniqueId()); From deb2666348547828475139898c9a8b3f474e51b5 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 10:27:26 -0700 Subject: [PATCH 22/39] Updated register dep usage --- buildcc/lib/args/include/args/register.h | 34 ++++++++++-------------- buildcc/lib/args/src/register.cpp | 20 +++++--------- buildcc/lib/args/test/test_register.cpp | 16 ++++++++--- 3 files changed, 33 insertions(+), 37 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 5859cb56..a270110f 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -82,14 +82,9 @@ class Reg::Instance { * @brief Reg::Instance for Target to be built */ template - void Build(const ArgToolchainState &toolchain_state, const C &build_cb, - BaseTarget &target, Params &&...params) { - // TODO, No empty task when .build is false - tf::Task task; - if (toolchain_state.build) { - build_cb(target, std::forward(params)...); - task = BuildTargetTask(target); - } + void Build(const C &build_cb, BaseTarget &target, Params &&...params) { + build_cb(target, std::forward(params)...); + tf::Task task = BuildTargetTask(target); BuildStoreTask(target.GetUniqueId(), task); } @@ -97,13 +92,10 @@ class Reg::Instance { * @brief Reg::Instance for Generator to be built */ template - void Build(bool condition, const C &build_cb, BaseGenerator &generator, - Params &&...params) { - if (condition) { - build_cb(generator, std::forward(params)...); - tf::Task task = BuildGeneratorTask(generator); - BuildStoreTask(generator.GetUniqueId(), task); - } + void Build(const C &build_cb, BaseGenerator &generator, Params &&...params) { + build_cb(generator, std::forward(params)...); + tf::Task task = BuildGeneratorTask(generator); + BuildStoreTask(generator.GetUniqueId(), task); } /** @@ -125,8 +117,7 @@ class Reg::Instance { * We can add more fmt::format arguments using the TestConfig arguments * parameter */ - void Test(const ArgToolchainState &toolchain_state, - const std::string &command, const BaseTarget &target, + void Test(const std::string &command, const BaseTarget &target, const TestConfig &config = TestConfig()); /** @@ -180,8 +171,9 @@ class Reg::CallbackInstance { template CallbackInstance &Build(const C &build_cb, BaseGenerator &generator, Params &&...params) { - Ref().Build(condition_, build_cb, generator, - std::forward(params)...); + if (condition_) { + Ref().Build(build_cb, generator, std::forward(params)...); + }; return *this; } @@ -203,7 +195,9 @@ class Reg::ToolchainInstance { template ToolchainInstance &Build(const C &build_cb, BaseTarget &target, Params &&...params) { - Ref().Build(condition_, build_cb, target, std::forward(params)...); + if (condition_.build) { + Ref().Build(build_cb, target, std::forward(params)...); + } return *this; } ToolchainInstance &Dep(const internal::BuilderInterface &target, diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 87bf9e68..0290c549 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -109,14 +109,18 @@ Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { Reg::ToolchainInstance & Reg::ToolchainInstance::Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency) { - Ref().Dep(target, dependency); + if (condition_.build) { + Ref().Dep(target, dependency); + } return *this; } Reg::ToolchainInstance &Reg::ToolchainInstance::Test(const std::string &command, const BaseTarget &target, const TestConfig &config) { - Ref().Test(condition_, command, target, config); + if (condition_.build && condition_.test) { + Ref().Test(command, target, config); + } return *this; } @@ -133,11 +137,6 @@ void Reg::Instance::Dep(const internal::BuilderInterface &target, "Call Instance::Build API on target and " "dependency before Instance::Dep API"); - // empty tasks -> not built so skip - if (target_iter->second.empty() || dep_iter->second.empty()) { - return; - } - const std::string &dep_unique_id = dependency.GetUniqueId(); DepDetectDuplicate(target_iter->second, dep_unique_id); DepDetectCyclicDependency(target_iter->second, dep_unique_id); @@ -146,13 +145,8 @@ void Reg::Instance::Dep(const internal::BuilderInterface &target, target_iter->second.succeed(dep_iter->second); } -void Reg::Instance::Test(const ArgToolchainState &toolchain_state, - const std::string &command, const BaseTarget &target, +void Reg::Instance::Test(const std::string &command, const BaseTarget &target, const TestConfig &config) { - if (!(toolchain_state.build && toolchain_state.test)) { - return; - } - const auto target_iter = build_.find(target.GetUniqueId()); env::assert_fatal( !(target_iter == build_.end()), diff --git a/buildcc/lib/args/test/test_register.cpp b/buildcc/lib/args/test/test_register.cpp index 92584c7d..1f2d7c46 100644 --- a/buildcc/lib/args/test/test_register.cpp +++ b/buildcc/lib/args/test/test_register.cpp @@ -279,9 +279,13 @@ TEST(RegisterTestGroup, Register_BuildAndDep) { buildcc::Reg::Toolchain(falseState) .Build([](buildcc::BaseTarget &target) { (void)target; }, target); mock().expectNCalls(1, "BuildTask_depT"); - buildcc::Reg::Toolchain(trueState) - .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency) - .Dep(target, dependency); + // In this case, target is not built so Dep throws + // Bad usage + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState) + .Build([](buildcc::BaseTarget &target) { (void)target; }, + dependency) + .Dep(target, dependency)); buildcc::Reg::Deinit(); } @@ -293,7 +297,11 @@ TEST(RegisterTestGroup, Register_BuildAndDep) { [](buildcc::BaseTarget &target) { (void)target; }, target); buildcc::Reg::Toolchain(falseState) .Build([](buildcc::BaseTarget &target) { (void)target; }, dependency); - buildcc::Reg::Toolchain(trueState).Dep(target, dependency); + + // In this case dependency is not built + // Bad usage + CHECK_THROWS(std::exception, + buildcc::Reg::Toolchain(trueState).Dep(target, dependency)); buildcc::Reg::Deinit(); } From 4333c9cf28ec837c700cc5033910e4bbc58b07f4 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 10:39:57 -0700 Subject: [PATCH 23/39] Removed executor from Reg::Instance --- buildcc/lib/args/include/args/register.h | 5 ----- buildcc/lib/args/src/tasks.cpp | 14 ++++++++------ 2 files changed, 8 insertions(+), 11 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index a270110f..98e43874 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -149,12 +149,7 @@ class Reg::Instance { tf::Taskflow build_tf_{"Targets"}; std::unordered_map build_; - - // Tests std::unordered_map tests_; - - // - tf::Executor executor_; }; class Reg::CallbackInstance { diff --git a/buildcc/lib/args/src/tasks.cpp b/buildcc/lib/args/src/tasks.cpp index 7072ca72..054b8eed 100644 --- a/buildcc/lib/args/src/tasks.cpp +++ b/buildcc/lib/args/src/tasks.cpp @@ -30,10 +30,11 @@ tf::Task Reg::Instance::BuildGeneratorTask(BaseGenerator &generator) { } void Reg::Instance::RunBuild() { - env::log_info(__FUNCTION__, fmt::format("Running with {} workers", - executor_.num_workers())); - executor_.run(build_tf_); - executor_.wait_for_all(); + tf::Executor executor; + env::log_info(__FUNCTION__, + fmt::format("Running with {} workers", executor.num_workers())); + executor.run(build_tf_); + executor.wait_for_all(); env::assert_fatal(env::get_task_state() == env::TaskState::SUCCESS, "Task state is not successful!"); } @@ -44,8 +45,9 @@ void Reg::Instance::RunTest() { tests_.begin(), tests_.end(), [](const std::pair &p) { p.second.TestRunner(); }); - executor_.run(test_tf); - executor_.wait_for_all(); + tf::Executor executor; + executor.run(test_tf); + executor.wait_for_all(); } } // namespace buildcc From d4a4cb0024237661e73f10870af7f669d29c17f9 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Sat, 2 Apr 2022 10:49:59 -0700 Subject: [PATCH 24/39] Updated register --- buildcc/lib/args/include/args/register.h | 3 +-- buildcc/lib/args/src/register.cpp | 25 +++++++++++++----------- 2 files changed, 15 insertions(+), 13 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index 98e43874..d708bde8 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -50,8 +50,7 @@ class Reg { static Instance &Ref(); private: - static bool is_init_; - static std::unique_ptr reg_; + static std::unique_ptr instance_; }; class Reg::Instance { diff --git a/buildcc/lib/args/src/register.cpp b/buildcc/lib/args/src/register.cpp index 0290c549..dd042ae3 100644 --- a/buildcc/lib/args/src/register.cpp +++ b/buildcc/lib/args/src/register.cpp @@ -65,24 +65,21 @@ void DepDetectCyclicDependency(const tf::Task &target_task, namespace buildcc { -bool Reg::is_init_{false}; -std::unique_ptr Reg::reg_; +std::unique_ptr Reg::instance_; void Reg::Init() { - if (!is_init_) { - reg_ = std::make_unique(); + if (!instance_) { + instance_ = std::make_unique(); env::assert_fatal(Args::IsParsed(), "Setup your Args"); Project::Init(fs::current_path() / Args::GetProjectRootDir(), fs::current_path() / Args::GetProjectBuildDir()); env::set_log_level(Args::GetLogLevel()); - is_init_ = true; } } void Reg::Deinit() { - reg_.reset(nullptr); + instance_.reset(nullptr); Project::Deinit(); - is_init_ = false; } void Reg::Run(const std::function &post_build_cb) { @@ -97,12 +94,14 @@ void Reg::Run(const std::function &post_build_cb) { const tf::Taskflow &Reg::GetTaskflow() { return Ref().GetTaskflow(); } Reg::Instance &Reg::Ref() { - env::assert_fatal(reg_ != nullptr, kRegkNotInit); - return *reg_; + env::assert_fatal(instance_ != nullptr, kRegkNotInit); + return *instance_; } +// Reg::ToolchainInstance + Reg::ToolchainInstance Reg::Toolchain(const ArgToolchainState &condition) { - env::assert_fatal(is_init_, kRegkNotInit); + env::assert_fatal(instance_ != nullptr, kRegkNotInit); return ToolchainInstance(condition); } @@ -124,11 +123,15 @@ Reg::ToolchainInstance &Reg::ToolchainInstance::Test(const std::string &command, return *this; } +// Reg::CallbackInstance + Reg::CallbackInstance Reg::Call(bool condition) { - env::assert_fatal(is_init_, kRegkNotInit); + env::assert_fatal(instance_ != nullptr, kRegkNotInit); return CallbackInstance(condition); } +// Reg::Instance + void Reg::Instance::Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency) { const auto target_iter = build_.find(target.GetUniqueId()); From 9ceecd0568aeba3626e87ed465a912624f20e599 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Wed, 6 Apr 2022 23:37:12 -0700 Subject: [PATCH 25/39] Update tpl buildcc script --- bootstrap/include/bootstrap/build_tpl.h | 8 +------- bootstrap/src/build_tpl.cpp | 15 +++++---------- 2 files changed, 6 insertions(+), 17 deletions(-) diff --git a/bootstrap/include/bootstrap/build_tpl.h b/bootstrap/include/bootstrap/build_tpl.h index 9695f7d3..9d00cc5e 100644 --- a/bootstrap/include/bootstrap/build_tpl.h +++ b/bootstrap/include/bootstrap/build_tpl.h @@ -21,13 +21,7 @@ namespace buildcc { -struct TplConfig { - TplConfig() = default; - - OsId os_id{OsId::Linux}; -}; - -void tpl_cb(BaseTarget &target, const TplConfig &config = TplConfig()); +void tpl_cb(BaseTarget &target); } // namespace buildcc diff --git a/bootstrap/src/build_tpl.cpp b/bootstrap/src/build_tpl.cpp index 0bd53b14..847161b1 100644 --- a/bootstrap/src/build_tpl.cpp +++ b/bootstrap/src/build_tpl.cpp @@ -18,22 +18,17 @@ namespace buildcc { -void tpl_cb(BaseTarget &target, const TplConfig &config) { +void tpl_cb(BaseTarget &target) { target.AddSource("process.cpp"); target.AddIncludeDir(""); target.AddHeader("process.hpp"); - switch (config.os_id) { - case OsId::Win: + if constexpr (env::is_win()) { target.AddSource("process_win.cpp"); - break; - case OsId::Linux: - case OsId::Unix: - case OsId::Mac: + } + + if constexpr (env::is_linux() || env::is_unix() || env::is_clang()) { target.AddSource("process_unix.cpp"); - break; - default: - break; } target.Build(); From 0d82f8bbdbf4bf2d356cf7021d69911ae96dd70c Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Wed, 6 Apr 2022 23:37:17 -0700 Subject: [PATCH 26/39] Update build_buildcc.cpp --- bootstrap/src/build_buildcc.cpp | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-) diff --git a/bootstrap/src/build_buildcc.cpp b/bootstrap/src/build_buildcc.cpp index 2cef25fa..15e926ab 100644 --- a/bootstrap/src/build_buildcc.cpp +++ b/bootstrap/src/build_buildcc.cpp @@ -131,7 +131,6 @@ void buildcc_cb(BaseTarget &target, const BaseGenerator &schema_gen, if constexpr (env::is_win()) { // TODO, Clang switch (target.GetToolchain().GetId()) { - case ToolchainId::Gcc: case ToolchainId::MinGW: { target.AddPreprocessorFlag("-DFMT_HEADER_ONLY=1"); target.AddPreprocessorFlag("-DSPDLOG_FMT_EXTERNAL"); @@ -196,16 +195,16 @@ void BuildBuildCC::Setup(const ArgToolchainState &state) { TargetEnv(env_.GetTargetRootDir() / "third_party" / "flatbuffers", env_.GetTargetBuildDir())); - auto &toolchain_instance = Reg::Toolchain(state) - .Func(global_flags_cb, flatc_exe, toolchain_) - .Build(build_flatc_exe_cb, flatc_exe); - // Schema auto &schema_gen = storage_.Add( kSchemaGenName, kSchemaGenName, TargetEnv(env_.GetTargetRootDir() / "buildcc" / "schema", env_.GetTargetBuildDir() / toolchain_.GetName())); Reg::Call().Build(schema_gen_cb, schema_gen, flatc_exe); + + auto &toolchain_instance = Reg::Toolchain(state) + .Func(global_flags_cb, flatc_exe, toolchain_) + .Build(build_flatc_exe_cb, flatc_exe); toolchain_instance.Dep(schema_gen, flatc_exe); // Flatbuffers HO lib @@ -252,9 +251,7 @@ void BuildBuildCC::Setup(const ArgToolchainState &state) { "tiny-process-library", env_.GetTargetBuildDir())); toolchain_instance.Func(global_flags_cb, tpl_lib, toolchain_); - TplConfig tpl_config; - tpl_config.os_id = get_host_os(); - toolchain_instance.Build(tpl_cb, tpl_lib, tpl_config); + toolchain_instance.Build(tpl_cb, tpl_lib); // TODO, Make this a generic selection between StaticTarget and // DynamicTarget From 01e910c707cd132f34bd55521807cd62b18c031f Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Wed, 6 Apr 2022 23:37:29 -0700 Subject: [PATCH 27/39] Update register.h --- buildcc/lib/args/include/args/register.h | 20 ++++++++++++++++---- 1 file changed, 16 insertions(+), 4 deletions(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index d708bde8..fa34a155 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -186,19 +186,31 @@ class Reg::ToolchainInstance { return *this; } + template + ToolchainInstance &Build(const C &build_cb, BaseGenerator &generator, + Params &&...params) { + return BuildInternal(build_cb, generator, std::forward(params)...); + } template ToolchainInstance &Build(const C &build_cb, BaseTarget &target, Params &&...params) { - if (condition_.build) { - Ref().Build(build_cb, target, std::forward(params)...); - } - return *this; + return BuildInternal(build_cb, target, std::forward(params)...); } ToolchainInstance &Dep(const internal::BuilderInterface &target, const internal::BuilderInterface &dependency); ToolchainInstance &Test(const std::string &command, const BaseTarget &target, const TestConfig &config = TestConfig()); +private: + template + ToolchainInstance &BuildInternal(const C &build_cb, T &t, + Params &&...params) { + if (condition_.build) { + Ref().Build(build_cb, t, std::forward(params)...); + } + return *this; + } + private: ArgToolchainState condition_; }; From 7476c0e3d9d067c7647ecd507188273d45491057 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Wed, 6 Apr 2022 23:47:56 -0700 Subject: [PATCH 28/39] Update build_buildcc.cpp --- bootstrap/src/build_buildcc.cpp | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/bootstrap/src/build_buildcc.cpp b/bootstrap/src/build_buildcc.cpp index 15e926ab..a764915c 100644 --- a/bootstrap/src/build_buildcc.cpp +++ b/bootstrap/src/build_buildcc.cpp @@ -200,47 +200,36 @@ void BuildBuildCC::Setup(const ArgToolchainState &state) { kSchemaGenName, kSchemaGenName, TargetEnv(env_.GetTargetRootDir() / "buildcc" / "schema", env_.GetTargetBuildDir() / toolchain_.GetName())); - Reg::Call().Build(schema_gen_cb, schema_gen, flatc_exe); - - auto &toolchain_instance = Reg::Toolchain(state) - .Func(global_flags_cb, flatc_exe, toolchain_) - .Build(build_flatc_exe_cb, flatc_exe); - toolchain_instance.Dep(schema_gen, flatc_exe); // Flatbuffers HO lib auto &flatbuffers_ho_lib = storage_.Add( kFlatbuffersHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "flatbuffers", env_.GetTargetBuildDir())); - toolchain_instance.Func(flatbuffers_ho_cb, flatbuffers_ho_lib); // CLI11 HO lib auto &cli11_ho_lib = storage_.Add( kCli11HoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "CLI11", env_.GetTargetBuildDir())); - toolchain_instance.Func(cli11_ho_cb, cli11_ho_lib); // fmt HO lib auto &fmt_ho_lib = storage_.Add( kFmtHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "fmt", env_.GetTargetBuildDir())); - toolchain_instance.Func(fmt_ho_cb, fmt_ho_lib); // spdlog HO lib auto &spdlog_ho_lib = storage_.Add( kSpdlogHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "spdlog", env_.GetTargetBuildDir())); - toolchain_instance.Func(spdlog_ho_cb, spdlog_ho_lib); // taskflow HO lib auto &taskflow_ho_lib = storage_.Add( kTaskflowHoName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "third_party" / "taskflow", env_.GetTargetBuildDir())); - toolchain_instance.Func(taskflow_ho_cb, taskflow_ho_lib); // Tiny-process-library lib // TODO, Make this a generic selection between StaticTarget and @@ -250,16 +239,27 @@ void BuildBuildCC::Setup(const ArgToolchainState &state) { TargetEnv(env_.GetTargetRootDir() / "third_party" / "tiny-process-library", env_.GetTargetBuildDir())); - toolchain_instance.Func(global_flags_cb, tpl_lib, toolchain_); - toolchain_instance.Build(tpl_cb, tpl_lib); + // BuildCC lib // TODO, Make this a generic selection between StaticTarget and // DynamicTarget auto &buildcc_lib = storage_.Add( kBuildccLibName, kBuildccLibName, toolchain_, TargetEnv(env_.GetTargetRootDir() / "buildcc", env_.GetTargetBuildDir())); - toolchain_instance.Func(global_flags_cb, buildcc_lib, toolchain_); - toolchain_instance + + Reg::Toolchain(state) + .Func(global_flags_cb, flatc_exe, toolchain_) + .Build(build_flatc_exe_cb, flatc_exe) + .Build(schema_gen_cb, schema_gen, flatc_exe) + .Dep(schema_gen, flatc_exe) + .Func(flatbuffers_ho_cb, flatbuffers_ho_lib) + .Func(cli11_ho_cb, cli11_ho_lib) + .Func(fmt_ho_cb, fmt_ho_lib) + .Func(spdlog_ho_cb, spdlog_ho_lib) + .Func(taskflow_ho_cb, taskflow_ho_lib) + .Func(global_flags_cb, tpl_lib, toolchain_) + .Build(tpl_cb, tpl_lib) + .Func(global_flags_cb, buildcc_lib, toolchain_) .Build(buildcc_cb, buildcc_lib, schema_gen, flatbuffers_ho_lib, fmt_ho_lib, spdlog_ho_lib, cli11_ho_lib, taskflow_ho_lib, tpl_lib) .Dep(buildcc_lib, schema_gen) From b5c4ba995860e2aaff422c3b58f2516428d2c863 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 19:10:47 -0700 Subject: [PATCH 29/39] Update register.h --- buildcc/lib/args/include/args/register.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index fa34a155..b277754b 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -40,7 +40,8 @@ class Reg { public: static void Init(); static void Deinit(); - static void Run(const std::function &post_build_cb = []() {}); + static void Run(const std::function &post_build_cb = + std::function()); static CallbackInstance Call(bool condition = true); static ToolchainInstance Toolchain(const ArgToolchainState &condition); From 62c88fc165de31035d7ec50b11589c0cdafb4943 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 19:22:08 -0700 Subject: [PATCH 30/39] Update build_buildcc.cpp --- bootstrap/src/build_buildcc.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bootstrap/src/build_buildcc.cpp b/bootstrap/src/build_buildcc.cpp index a764915c..d5b111b6 100644 --- a/bootstrap/src/build_buildcc.cpp +++ b/bootstrap/src/build_buildcc.cpp @@ -146,7 +146,7 @@ void buildcc_cb(BaseTarget &target, const BaseGenerator &schema_gen, } } - if constexpr (env::is_linux()) { + if constexpr (env::is_linux() || env::is_unix() || env::is_clang()) { // TODO, Clang switch (target.GetToolchain().GetId()) { case ToolchainId::Gcc: { From 7e78a67f5e2e973bd91c4e13a03413928fd9d106 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 20:01:43 -0700 Subject: [PATCH 31/39] Update main.buildcc.cpp --- bootstrap/main.buildcc.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/bootstrap/main.buildcc.cpp b/bootstrap/main.buildcc.cpp index fd3d365a..9115346e 100644 --- a/bootstrap/main.buildcc.cpp +++ b/bootstrap/main.buildcc.cpp @@ -42,6 +42,7 @@ int main(int argc, char **argv) { Reg::Call(Args::Clean()).Func(clean_cb); BaseToolchain toolchain = custom_toolchain_arg.ConstructToolchain(); + toolchain.Verify(); BuildBuildCC buildcc( toolchain, TargetEnv(Project::GetRootDir(), Project::GetBuildDir())); From 49dc94ad68774a18cd86000934bc9b14f15853f2 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 20:01:55 -0700 Subject: [PATCH 32/39] Update args.h --- buildcc/lib/args/include/args/args.h | 103 ++++++++++++++------------- 1 file changed, 53 insertions(+), 50 deletions(-) diff --git a/buildcc/lib/args/include/args/args.h b/buildcc/lib/args/include/args/args.h index 8387b0ce..6cccb1f3 100644 --- a/buildcc/lib/args/include/args/args.h +++ b/buildcc/lib/args/include/args/args.h @@ -99,56 +99,8 @@ struct ArgCustom { class Args { private: - class Instance { - public: - /** - * @brief Parse command line information to CLI11 - * - * @param argc from int main(int argc, char ** argv) - * @param argv from int main(int argc, char ** argv) - */ - static void Parse(int argc, const char *const *argv); - - /** - * @brief Add toolchain with a unique name and description - * - * @param out Receive the toolchain information through the CLI - * @param initial Set the default toolchain information as a fallback - */ - Instance &AddToolchain(const std::string &name, - const std::string &description, ArgToolchain &out, - const ArgToolchain &initial = ArgToolchain()); - - /** - * @brief Add toolchain with a unique name and description - * - * @param out Receive the toolchain information through the CLI - * @param initial Set the default toolchain information as a fallback - */ - Instance &AddTarget(const std::string &name, const std::string &description, - ArgTarget &out, const ArgTarget &initial = ArgTarget()); - - /** - * @brief Custom callback for data - * - * @param add_cb Add callback that exposes underlying CLI::App - */ - Instance &AddCustomCallback(const std::function &add_cb); - - /** - * @brief Add custom data - * - * @param data Derive from `buildcc::ArgCustom` and override the `Add` API - */ - Instance &AddCustomData(ArgCustom &data); - }; - - struct Internal { - Instance instance; - CLI::App app{"BuildCC Buildsystem"}; - CLI::App *toolchain{nullptr}; - CLI::App *target{nullptr}; - }; + class Instance; + struct Internal; public: Args() = delete; @@ -176,6 +128,57 @@ class Args { static std::unique_ptr internal_; }; +class Args::Instance { +public: + /** + * @brief Parse command line information to CLI11 + * + * @param argc from int main(int argc, char ** argv) + * @param argv from int main(int argc, char ** argv) + */ + static void Parse(int argc, const char *const *argv); + + /** + * @brief Add toolchain with a unique name and description + * + * @param out Receive the toolchain information through the CLI + * @param initial Set the default toolchain information as a fallback + */ + Instance &AddToolchain(const std::string &name, + const std::string &description, ArgToolchain &out, + const ArgToolchain &initial = ArgToolchain()); + + /** + * @brief Add toolchain with a unique name and description + * + * @param out Receive the toolchain information through the CLI + * @param initial Set the default toolchain information as a fallback + */ + Instance &AddTarget(const std::string &name, const std::string &description, + ArgTarget &out, const ArgTarget &initial = ArgTarget()); + + /** + * @brief Custom callback for data + * + * @param add_cb Add callback that exposes underlying CLI::App + */ + Instance &AddCustomCallback(const std::function &add_cb); + + /** + * @brief Add custom data + * + * @param data Derive from `buildcc::ArgCustom` and override the `Add` API + */ + Instance &AddCustomData(ArgCustom &data); +}; + +struct Args::Internal { + Instance instance; + CLI::App app{"BuildCC Buildsystem"}; + CLI::App *toolchain{nullptr}; + CLI::App *target{nullptr}; +}; + } // namespace buildcc #endif From d00723aaeacae39eab8e3f882acb401f4e6d80ca Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 20:02:01 -0700 Subject: [PATCH 33/39] Update register.h --- buildcc/lib/args/include/args/register.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/buildcc/lib/args/include/args/register.h b/buildcc/lib/args/include/args/register.h index b277754b..a52a08de 100644 --- a/buildcc/lib/args/include/args/register.h +++ b/buildcc/lib/args/include/args/register.h @@ -38,6 +38,10 @@ class Reg { class ToolchainInstance; public: + Reg() = delete; + Reg(const Reg &) = delete; + Reg(Reg &&) = delete; + static void Init(); static void Deinit(); static void Run(const std::function &post_build_cb = From b46eba8b300abb453eda1a8ff27b58cbe5c9ab4b Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 22:22:16 -0700 Subject: [PATCH 34/39] Updated documentation --- docs/source/examples/hybrid.rst | 167 +++++++++--------- .../buildexe_package_manager.rst | 46 +++-- .../buildexe_script_example.rst | 33 ++-- docs/source/user_api/register.rst | 22 +-- 4 files changed, 131 insertions(+), 137 deletions(-) diff --git a/docs/source/examples/hybrid.rst b/docs/source/examples/hybrid.rst index abc73c73..01db43a3 100644 --- a/docs/source/examples/hybrid.rst +++ b/docs/source/examples/hybrid.rst @@ -14,20 +14,18 @@ We are only using a single Toolchain - Target pair :linenos: int main(int argc, char ** argv) { - // Args module to get data from the command line or .toml file passed in through --config - Args args; - // Register your [toolchain.{name}] // In this case it will be [toolchain.gcc] ArgToolchain arg_gcc; - args.AddToolchain("gcc", "Generic gcc toolchain", arg_gcc); - // Parse the arguments from the command line - args.Parse(argc, argv); + // Args module to get data from the command line or .toml file passed in through --config + Args::Init() + .AddToolchain("gcc", "Generic gcc toolchain", arg_gcc) + .Parse(argc, argv); // Register module - Register reg(args); - reg.Clean(clean_cb); + Reg::Init(); + Reg::Call(Args::Clean()).Func(clean_cb); // TODO, Write your target builds here // See examples below @@ -75,14 +73,13 @@ Compile a single source with a single GCC compiler. ExecutableTarget_gcc hello_world("hello_world", gcc, ""); // Select your builds and tests using the .toml files - reg.Build(arg_gcc.state, hello_world_build_cb, hello_world); - reg.Test(arg_gcc.state, "{executable}", hello_world); + Reg::Toolchain(arg_gcc.state) + .Func([&]() { gcc.Verify(); }) + .Build(arg_gcc.state, hello_world_build_cb, hello_world) + .Test(arg_gcc.state, "{executable}", hello_world); - // Build Target - reg.RunBuild(); - - // Test Target - reg.RunTest(); + // Build and Test Target + Reg::Run(); } static void hello_world_build_cb(BaseTarget &target) { @@ -100,23 +97,21 @@ We are using multiple Toolchain - Target pairs :linenos: int main(int argc, char ** argv) { - // Args module to get data from the command line or .toml file passed in through --config - Args args; - // Register your [toolchain.{name}] // In this case it will be [toolchain.gcc] and [toolchain.msvc] ArgToolchain arg_gcc; ArgToolchain arg_msvc; - args.AddToolchain("gcc", "Generic gcc toolchain", arg_gcc); - args.AddToolchain("msvc", "Generic msvc toolchain", arg_msvc); - // NOTE, You can add more toolchains here as per your project requirement - // Parse the arguments from the command line - args.Parse(argc, argv); + // Args module to get data from the command line or .toml file passed in through --config + Args::Init() + .AddToolchain("gcc", "Generic gcc toolchain", arg_gcc) + .AddToolchain("msvc", "Generic msvc toolchain", arg_msvc) + .Parse(argc, argv); + // NOTE, You can add more toolchains here as per your project requirement // Register module - Register reg(args); - reg.Clean(clean_cb); + Reg::Init(); + Reg::Call(Args::Clean()).Func(clean_cb); // TODO, Write your target builds here // See examples below @@ -167,30 +162,30 @@ Similar to lowlevel GCC Flags example for both the GCC and MSVC compiler // See Multiple Boilerplate Toolchain_gcc gcc; - Toolchain_msvc msvc; - ExecutableTarget_gcc g_cppflags("cppflags", gcc, "files"); - ExecutableTarget_msvc m_cppflags("cppflags", msvc, "files"); ExecutableTarget_gcc g_cflags("cflags", gcc, "files"); + // Select your builds and tests using the .toml files + Reg::Toolchain(arg_gcc.state) + .Func([&](){ gcc.Verify(); }) + .Build(cppflags_build_cb, g_cppflags) + .Build(cflags_build_cb, g_cflags) + .Test("{executable}", g_cppflags) + .Test("{executable}", g_cflags); + + Toolchain_msvc msvc; + ExecutableTarget_msvc m_cppflags("cppflags", msvc, "files"); ExecutableTarget_msvc m_cflags("cflags", msvc, "files"); + Reg::Toolchain(arg_msvc.state) + .Func([&](){ msvc.Verify(); }) + .Build(cppflags_build_cb, m_cppflags) + .Build(cflags_build_cb, m_cflags) + .Test("{executable}", m_cppflags) + .Test("{executable}", m_cflags); - // Select your builds and tests using the .toml files - reg.Build(arg_gcc.state, cppflags_build_cb, g_cppflags); - reg.Build(arg_msvc.state, cppflags_build_cb, m_cppflags); - reg.Build(arg_gcc.state, cflags_build_cb, g_cflags); - reg.Build(arg_msvc.state, cflags_build_cb, m_cflags); - - // Test steps - reg.Test(arg_gcc.state, "{executable}", g_cppflags); - reg.Test(arg_msvc.state, "{executable}", m_cppflags); - reg.Test(arg_gcc.state, "{executable}", g_cflags); - reg.Test(arg_msvc.state, "{executable}", m_cflags); - - // Build Target - reg.RunBuild(); - - // Test Target - reg.RunTest(); + // Build and Test target + Reg::Run(); + + return 0; } static void cppflags_build_cb(BaseTarget &cppflags) { @@ -312,13 +307,16 @@ For end users consuming third party libraries Toolchain_gcc gcc; Toolchain_msvc msvc; - ExecutableTarget_gcc g_foolib("foolib", gcc, ""); - ExecutableTarget_msvc m_foolib("foolib", msvc, ""); + ExecutableTarget_gcc g_foolib("foolib", gcc, TargetEnv("...")); + ExecutableTarget_msvc m_foolib("foolib", msvc, TargetEnv("..."); - reg.Build(arg_gcc.state, foolib_build_cb, g_foolib); - reg.Build(arg_msvc.state, foolib_build_cb, m_foolib); + Reg::Toolchain(arg_gcc.state) + .Build(foolib_build_cb, g_foolib); + + Reg::Toolchain(arg_msvc.state) + .Build(foolib_build_cb, m_foolib); - reg.RunBuild(); + Reg::Run(); } static void foolib_build_cb(BaseTarget &target) { @@ -338,44 +336,40 @@ For super customized targets and toolchains int main(int argc, char ** argv) { - Args args; ArgToolchain arg_gcc; ArgToolchain arg_msvc; ArgToolchain toolchain_clang_gnu; ArgTarget target_clang_gnu; - args.AddToolchain("gcc", "Generic gcc toolchain", arg_gcc); - args.AddToolchain("msvc", "Generic msvc toolchain", arg_msvc); - // Add your custom toolchain - target to the command line - args.AddToolchain("clang_gnu", "Clang GNU toolchain", toolchain_clang_gnu); - args.AddTarget("clang_gnu", "Clang GNU target", target_clang_gnu); - - args.Parse(argc, argv); + Args::Init() + .AddToolchain("gcc", "Generic gcc toolchain", arg_gcc) + .AddToolchain("msvc", "Generic msvc toolchain", arg_msvc) + .AddToolchain("clang_gnu", "Clang GNU toolchain", toolchain_clang_gnu) + .AddTarget("clang_gnu", "Clang GNU target", target_clang_gnu) + .Parse(argc, argv); // Additional boilerplate // Supplied at compile time Toolchain_gcc gcc; Toolchain_msvc msvc; - - ExecutableTarget_gcc g_foolib("foolib", gcc, ""); - ExecutableTarget_msvc m_foolib("foolib", msvc, ""); - - reg.Build(arg_gcc.state, foolib_build_cb, g_foolib); - reg.Build(arg_msvc.state, foolib_build_cb, m_foolib); - // Get custom toolchain from the command line, supplied at run time BaseToolchain clang = toolchain_clang_gnu.ConstructToolchain(); + ExecutableTarget_gcc g_foolib("foolib", gcc, ""); + ExecutableTarget_msvc m_foolib("foolib", msvc, ""); // Get compile_command and link_command from the command line - TargetConfig config; - config.compile_command = target_clang_gnu.compile_command; - config.link_command = target_clang_gnu.link_command; - Target_custom c_foolib("CFoolib.exe", TargetType::Executable, clang, "", config); - reg.Build(toolchain_clang_gnu.state, foolib_build_cb, c_foolib); + Target_custom c_foolib("CFoolib.exe", TargetType::Executable, clang, "", target_clang_gnu.GetTargetConfig()); + + Reg::Toolchain(arg_gcc.state) + .Build(foolib_build_cb, g_foolib); + Reg::Toolchain(arg_msvc.state) + .Build(foolib_build_cb, m_foolib); + Reg::Toolchain(toolchain_clang_gnu.state) + .Build( foolib_build_cb, c_foolib); // Build targets - reg.RunBuild(); + Reg::Run(); } static void foolib_build_cb(BaseTarget &target) { @@ -496,17 +490,19 @@ Chain **Generators** and **Targets** using the ``Register`` module Toolchain_msvc msvc; BaseGenerator cpp_generator("cpp_generator", ""); - reg.Build(cpp_generator_cb, cpp_generator); + Reg::Call().Build(cpp_generator_cb, cpp_generator); ExecutableTarget_gcc g_cpptarget("cpptarget", gcc, ""); - reg.Build(arg_gcc.state, cpp_target_cb, g_cpptarget, cpp_generator); + Reg::Toolchain(arg_gcc.state) + .Func([&](){ gcc.Verify(); }) + .Build(cpp_target_cb, g_cpptarget, cpp_generator) + .Dep(g_cpptarget, cpp_generator); ExecutableTarget_msvc m_cpptarget("cpptarget", msvc, ""); - reg.Build(arg_msvc.state, cpp_target_cb, m_cpptarget, cpp_generator); - - // cpp_generator runs before g_cpptarget and m_cpptarget - reg.Dep(g_cpptarget, cpp_generator); - reg.Dep(m_cpptarget, cpp_generator); + Reg::Toolchain(arg_msvc.state) + .Func([&](){ msvc.Verify(); }) + .Build(cpp_target_cb, m_cpptarget, cpp_generator) + .Dep(m_cpptarget, cpp_generator); } // Use a python generator to create main.cpp @@ -546,14 +542,17 @@ Target Info Toolchain_msvc msvc; // TargetInfo - TargetInfo genericadd_ho("files"); - reg.Callback(genericadd_ho_cb, genericadd_ho); - + TargetInfo g_genericadd_ho(gcc, "files"); ExecutableTarget_gcc g_genericadd1("generic_add_1", gcc, "files"); - ExecutableTarget_msvc m_genericadd1("generic_add_1", msvc, "files"); + Reg::Toolchain(arg_gcc.state) + .Func(genericadd_ho_cb, g_genericadd_ho) + .Build(genericadd1_build_cb, g_genericadd1, g_genericadd_ho); - reg.Build(arg_gcc.state, genericadd1_build_cb, g_genericadd1, genericadd_ho); - reg.Build(arg_msvc.state, genericadd1_build_cb, m_genericadd1, genericadd_ho); + TargetInfo m_genericadd_ho(msvc, "files"); + ExecutableTarget_msvc m_genericadd1("generic_add_1", msvc, "files"); + Reg::Toolchain(arg_msvc.state) + .Func(genericadd_ho_cb, m_genericadd_ho) + .Build(genericadd1_build_cb, m_genericadd1, m_genericadd_ho); } // HO library contains include dirs and header files which are copied into executable target diff --git a/docs/source/getting_started/buildexe_package_manager.rst b/docs/source/getting_started/buildexe_package_manager.rst index 161e09ad..13c93b35 100644 --- a/docs/source/getting_started/buildexe_package_manager.rst +++ b/docs/source/getting_started/buildexe_package_manager.rst @@ -210,23 +210,22 @@ Write your C++ "script" static void hello_world_build_cb(BaseTarget &target, BaseTarget &fmt_lib); int main(int argc, char **argv) { - // 1. Get arguments - Args args; + // Get arguments ArgToolchain arg_gcc; - args.AddToolchain("gcc", "Generic gcc toolchain", arg_gcc); - args.Parse(argc, argv); - // 2. Initialize your environment - Register reg(args); + Args::Init() + .AddToolchain("gcc", "Generic gcc toolchain", arg_gcc) + .Parse(argc, argv); - // 3. Pre-build steps - reg.Clean(clean_cb); + // Initialize your environment + Reg::Init(); - // 4. Build steps + // Pre-build steps + Reg::Call(Args::Clean().Func(clean_cb); + + // Build steps // Explicit toolchain - target pairs Toolchain_gcc gcc; - auto verified_toolchains = gcc.Verify(); - env::assert_fatal(!verified_toolchains.empty(), "GCC Toolchain not found"); // Setup your [Library]Target_[toolchain] fmtlib instance // Update your TargetEnv to point to `BuildExeLibDir::fmt` folder @@ -237,29 +236,24 @@ Write your C++ "script" // We use the build.fmt.h and build.fmt.cpp APIs to define how we build our fmtlib FmtConfig fmt_config; - reg.Build(arg_gcc.state, build_fmt_cb, fmt_lib, fmt_config); // Define our hello world executable ExecutableTarget_gcc hello_world("hello_world", gcc, ""); - reg.Build(arg_gcc.state, hello_world_build_cb, hello_world, fmt_lib); - + // Fmt lib is a dependency to the Hello world executable // This means that fmt lib is guaranteed to be built before the hello world executable - reg.Dep(hello_world, fmt_lib); - - // 5. Test steps i.e Hello world is automatically run - reg.Test(arg_gcc.state, "{executable}", hello_world); + Reg::Toolchain(arg_gcc.state) + .Build(arg_gcc.state, build_fmt_cb, fmt_lib, fmt_config) + .Build(hello_world_build_cb, hello_world, fmt_lib) + .Dep(hello_world, fmt_lib) + .Test("{executable}", hello_world);; + - // 6. Build Target + // Build and Test Target // Builds libfmt.a and ./hello_world - reg.RunBuild(); - - // 7. Test Target - // Executes ./hello_world - // Output -> Hello World - reg.RunTest(); + Reg::Run(); - // 8. Post Build steps + // Post Build steps // - Clang Compile Commands plugin::ClangCompileCommands({&hello_world}).Generate(); // - Graphviz dump diff --git a/docs/source/getting_started/buildexe_script_example.rst b/docs/source/getting_started/buildexe_script_example.rst index 23a3f211..bcf83423 100644 --- a/docs/source/getting_started/buildexe_script_example.rst +++ b/docs/source/getting_started/buildexe_script_example.rst @@ -96,32 +96,33 @@ We then setup our main **toolchain**-**target** pairs. Highlighted below void hello_world_build_cb(BaseTarget & target); int main(int argc, char ** argv) { - // Step 1. Setup your args - Args args; + // Setup your args ArgToolchain arg_gcc; - args.AddToolchain("gcc", "GCC toolchain", arg_gcc); - args.Parse(argc, argv); - // Step 2. Register - Register reg(args); + Args::Init() + .AddToolchain("gcc", "GCC toolchain", arg_gcc) + .Parse(argc, argv); - // Step 3. Pre build steps + // Register + Reg::Init(); + + // Pre build steps // for example. clean your environment - reg.Clean(clean_cb); + Reg::Call(Args::Clean()).Func(clean_cb); - // Step 4. Build steps + // Build steps // Main setup Toolchain_gcc gcc; - auto verified_gcc_toolchains = gcc.Verify(); - env::assert_fatal(!verified_gcc_toolchains.empty(), "GCC toolchain not found"); - ExecutableTarget_gcc hello_world("hello_world", gcc, ""); - reg.Build(arg_gcc.state, hello_world_build_cb, hello_world); - // Step 5. Build your targets - reg.RunBuild(); + Reg::Toolchain(arg_gcc.state) + .Func([&](){ gcc.Verify() }) + .Build(hello_world_build_cb, hello_world); + + // Build your targets + Reg::Run(); - // Step 6. Post build steps + // Post build steps // for example. clang compile commands database plugin::ClangCompileCommands({&hello_world}).Generate(); diff --git a/docs/source/user_api/register.rst b/docs/source/user_api/register.rst index 77033451..5a97f8ba 100644 --- a/docs/source/user_api/register.rst +++ b/docs/source/user_api/register.rst @@ -4,9 +4,8 @@ Register register.h ----------- -.. doxygenclass:: buildcc::Register - :members: Register, Clean, Callback, CallbackIf, Build, Dep, Test, RunBuild, RunTest - +.. doxygenclass:: buildcc::Reg + :members: test_info.h ------------- @@ -26,19 +25,20 @@ Example static void callback_usage_func(const BigObj & cobj, BigObj & obj); int main(int argc, char ** argv) { - Args args; - args.Parse(argc, argv); + Args::Init() + .Parse(argc, argv); + + Reg::Init(); + Reg::Call(Args::Clean()).Func([](){ + fs::remove_all(Project::GetBuildDir()); + }) - Register reg(args); - reg.Clean([](){ - fs::remove_all(env::get_project_build_dir()); - }); BigObj obj; - reg.Callback(callback_usage_func, BigObj(), obj); + Reg::Call().Func(callback_usage_func, BigObj(), obj) bool expression = true; // false - reg.CallbackIf(expression, callback_usage_func, BigObj(), obj); + Reg::Call(expression).Func(callback_usage_func, BigObj(), obj) // Example snippets of these given in Target API // Build From beea75992b0aa635a429d31da839993d9fac7ddc Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 22:25:51 -0700 Subject: [PATCH 35/39] Updated documentation --- docs/source/user_api/args.rst | 2 -- docs/source/user_api/register.rst | 1 - 2 files changed, 3 deletions(-) diff --git a/docs/source/user_api/args.rst b/docs/source/user_api/args.rst index 0786e917..e21db691 100644 --- a/docs/source/user_api/args.rst +++ b/docs/source/user_api/args.rst @@ -6,8 +6,6 @@ args.h .. doxygenclass:: buildcc::Args -.. doxygenclass:: buildcc::Args::Instance - .. doxygenstruct:: buildcc::ArgCustom .. doxygenstruct:: buildcc::ArgToolchainState diff --git a/docs/source/user_api/register.rst b/docs/source/user_api/register.rst index 5a97f8ba..4d8d5795 100644 --- a/docs/source/user_api/register.rst +++ b/docs/source/user_api/register.rst @@ -5,7 +5,6 @@ register.h ----------- .. doxygenclass:: buildcc::Reg - :members: test_info.h ------------- From 37c839a8677dbbf1dbd0071c127ab9868af02998 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 22:27:31 -0700 Subject: [PATCH 36/39] Updated documentation --- docs/source/examples/hybrid.rst | 6 ------ docs/source/getting_started/buildexe_package_manager.rst | 1 - docs/source/getting_started/buildexe_script_example.rst | 1 - 3 files changed, 8 deletions(-) diff --git a/docs/source/examples/hybrid.rst b/docs/source/examples/hybrid.rst index 01db43a3..38c611a8 100644 --- a/docs/source/examples/hybrid.rst +++ b/docs/source/examples/hybrid.rst @@ -296,7 +296,6 @@ For end users consuming third party libraries .. code-block:: cpp :linenos: - :emphasize-lines: 18 #include "build.foo.h" @@ -332,7 +331,6 @@ For super customized targets and toolchains .. code-block:: cpp :linenos: - :emphasize-lines: 12,13,30,34,35,36 int main(int argc, char ** argv) { @@ -381,7 +379,6 @@ For super customized targets and toolchains .. code-block:: toml :linenos: - :emphasize-lines: 4,18 # See Multiple boilerplate .toml file @@ -412,7 +409,6 @@ Precompile header usage with GCC and MSVC compilers .. code-block:: cpp :linenos: - :emphasize-lines: 8,9,10,36,37,38 // Modified Lowlevel GCC Flags example for PCH @@ -481,7 +477,6 @@ Chain **Generators** and **Targets** using the ``Register`` module .. code-block:: cpp :linenos: - :emphasize-lines: 7,8,17,18 int main(int argc, char ** argv) { // See Multiple Boilerplate @@ -533,7 +528,6 @@ Target Info .. code-block:: cpp :linenos: - :emphasize-lines: 8,9 int main(int argc, char ** argv) { // See Multiple boilerplate diff --git a/docs/source/getting_started/buildexe_package_manager.rst b/docs/source/getting_started/buildexe_package_manager.rst index 13c93b35..5e9493c8 100644 --- a/docs/source/getting_started/buildexe_package_manager.rst +++ b/docs/source/getting_started/buildexe_package_manager.rst @@ -192,7 +192,6 @@ Write your C++ "script" .. code-block:: cpp :linenos: - :emphasize-lines: 4,8,38,39,40,43,44,47,48,52,79 #include "buildcc.h" diff --git a/docs/source/getting_started/buildexe_script_example.rst b/docs/source/getting_started/buildexe_script_example.rst index bcf83423..ca229500 100644 --- a/docs/source/getting_started/buildexe_script_example.rst +++ b/docs/source/getting_started/buildexe_script_example.rst @@ -84,7 +84,6 @@ We then setup our main **toolchain**-**target** pairs. Highlighted below .. code-block:: cpp :linenos: - :emphasize-lines: 25,26,27,29,30 :caption: build.helloworld.cpp #include "buildcc.h" From a0bc5ab84fc8149f242c3f124f5dbd81cfb4e2c8 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 22:34:14 -0700 Subject: [PATCH 37/39] Update test_register.cpp --- buildcc/lib/args/test/test_register.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/buildcc/lib/args/test/test_register.cpp b/buildcc/lib/args/test/test_register.cpp index 1f2d7c46..a91cc92e 100644 --- a/buildcc/lib/args/test/test_register.cpp +++ b/buildcc/lib/args/test/test_register.cpp @@ -34,6 +34,7 @@ TEST(RegisterTestGroup, Register_Initialize) { CHECK_TRUE(buildcc::Args::Clean()); buildcc::Reg::Init(); + buildcc::Reg::Init(); // Second init does nothing } TEST(RegisterTestGroup, Register_Clean) { @@ -118,7 +119,9 @@ TEST(RegisterTestGroup, Register_Build) { buildcc::Reg::Init(); buildcc::Reg::Toolchain(state).Build( [](buildcc::BaseTarget &target) { (void)target; }, target); + CHECK_TRUE(!buildcc::Reg::GetTaskflow().empty()); buildcc::Reg::Deinit(); + CHECK_THROWS(std::exception, buildcc::Reg::GetTaskflow()); } { From 4e76dd6b18ee16b814160c44479d2154eb30c141 Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 22:38:01 -0700 Subject: [PATCH 38/39] Update test_register.cpp --- buildcc/lib/args/test/test_register.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/buildcc/lib/args/test/test_register.cpp b/buildcc/lib/args/test/test_register.cpp index a91cc92e..cf854e7c 100644 --- a/buildcc/lib/args/test/test_register.cpp +++ b/buildcc/lib/args/test/test_register.cpp @@ -119,7 +119,7 @@ TEST(RegisterTestGroup, Register_Build) { buildcc::Reg::Init(); buildcc::Reg::Toolchain(state).Build( [](buildcc::BaseTarget &target) { (void)target; }, target); - CHECK_TRUE(!buildcc::Reg::GetTaskflow().empty()); + (void)buildcc::Reg::GetTaskflow(); buildcc::Reg::Deinit(); CHECK_THROWS(std::exception, buildcc::Reg::GetTaskflow()); } From 84212c17dab5afebd40a749546f5540f3760942c Mon Sep 17 00:00:00 2001 From: Niket Naidu Date: Thu, 7 Apr 2022 22:56:53 -0700 Subject: [PATCH 39/39] Update test_register.cpp --- buildcc/lib/args/test/test_register.cpp | 43 +++++++++++++++++++++++++ 1 file changed, 43 insertions(+) diff --git a/buildcc/lib/args/test/test_register.cpp b/buildcc/lib/args/test/test_register.cpp index cf854e7c..2403876c 100644 --- a/buildcc/lib/args/test/test_register.cpp +++ b/buildcc/lib/args/test/test_register.cpp @@ -138,6 +138,49 @@ TEST(RegisterTestGroup, Register_Build) { mock().checkExpectations(); } +TEST(RegisterTestGroup, Register_Run_PostCb) { + std::vector av{ + "", + "--config", + "configs/basic_parse.toml", + }; + int argc = av.size(); + + buildcc::ArgToolchain gcc_toolchain; + buildcc::ArgToolchain msvc_toolchain; + buildcc::Args::Init() + .AddToolchain("gcc", "Generic gcc toolchain", gcc_toolchain) + .AddToolchain("msvc", "Generic msvc toolchain", msvc_toolchain) + .Parse(argc, av.data()); + + STRCMP_EQUAL(buildcc::Args::GetProjectRootDir().string().c_str(), "root"); + STRCMP_EQUAL(buildcc::Args::GetProjectBuildDir().string().c_str(), "build"); + CHECK(buildcc::Args::GetLogLevel() == buildcc::env::LogLevel::Trace); + CHECK_TRUE(buildcc::Args::Clean()); + + // Make dummy toolchain and target + buildcc::Project::Init(fs::current_path(), fs::current_path()); + buildcc::Toolchain toolchain(buildcc::ToolchainId::Gcc, "", "", "", "", "", + ""); + buildcc::BaseTarget target("dummyT", buildcc::TargetType::Executable, + toolchain, ""); + + { + buildcc::ArgToolchainState state{false, false}; + + buildcc::Reg::Init(); + buildcc::Reg::Toolchain(state).Build( + [](buildcc::BaseTarget &target) { (void)target; }, target); + + mock().expectOneCall("Build_PostCb"); + buildcc::Reg::Run([]() { mock().actualCall("Build_PostCb"); }); + buildcc::Reg::Deinit(); + } + + buildcc::Project::Deinit(); + mock().checkExpectations(); +} + TEST(RegisterTestGroup, Register_NoBuildAndDep) { std::vector av{ "",