From ae1871ca0ffcac3e8bd337f8d8bb4e7fd6c59295 Mon Sep 17 00:00:00 2001 From: Bent Bisballe Nyeng Date: Sun, 10 Jul 2022 17:24:16 +0200 Subject: Make tools abstraction around compiler options to better support tool agnostic arguments. --- test/ctor.cc | 18 +++++ test/tools_test.cc | 212 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 230 insertions(+) create mode 100644 test/tools_test.cc (limited to 'test') diff --git a/test/ctor.cc b/test/ctor.cc index c24ded7..9b690a2 100644 --- a/test/ctor.cc +++ b/test/ctor.cc @@ -60,6 +60,23 @@ BuildConfigurations ctorTestConfigs(const Settings& settings) .ldflags = { "-pthread" }, }, }, + { + .type = TargetType::UnitTest, + .target = "tools_test", + .sources = { + "tools_test.cc", + "testmain.cc", + "../src/tools.cc", + }, + //.depends = { "libctor_nomain.a" }, + .flags = { + .cxxflags = { + "-std=c++20", "-O3", "-Wall", "-Werror", + "-I../src", "-Iuunit", + "-DOUTPUT=\"tools\"", + }, + }, + }, { .type = TargetType::UnitTestLib, .target = "libctor_nomain.a", @@ -75,6 +92,7 @@ BuildConfigurations ctorTestConfigs(const Settings& settings) "../src/task_fn.cc", "../src/task_ld.cc", "../src/task_so.cc", + "../src/tools.cc", "../src/util.cc", "../src/externals_manual.cc", }, diff --git a/test/tools_test.cc b/test/tools_test.cc new file mode 100644 index 0000000..3e9de1b --- /dev/null +++ b/test/tools_test.cc @@ -0,0 +1,212 @@ +#include + +#include +#include + +#include + +using namespace std::string_literals; + +namespace +{ +std::ostream& operator<<(std::ostream& stream, const ToolChain& tool_chain) +{ + switch(tool_chain) + { + case ToolChain::gcc: + stream << "ToolChain::gcc"; + break; + case ToolChain::clang: + stream << "ToolChain::clang"; + break; + } + return stream; +} + +std::ostream& operator<<(std::ostream& stream, const std::vector& vs) +{ + bool first{true}; + stream << "{ "; + for(const auto& v : vs) + { + if(!first) + { + stream << ", "; + } + stream << "'" << v << "'"; + first = false; + } + stream << " }"; + + return stream; +} + +std::ostream& operator<<(std::ostream& stream, opt o) +{ + // Adding to this enum should also imply adding to the unit-tests below + switch(o) + { + case opt::output: stream << "opt::output"; break; + case opt::debug: stream << "opt::debug"; break; + case opt::strip: stream << "opt::strip"; break; + case opt::warn_all: stream << "opt::warn_all"; break; + case opt::warnings_as_errors: stream << "opt::warnings_as_errors"; break; + case opt::generate_dep_tree: stream << "opt::generate_dep_tree"; break; + case opt::no_link: stream << "opt::no_link"; break; + case opt::include_path: stream << "opt::include_path"; break; + case opt::library_path: stream << "opt::library_path"; break; + case opt::link: stream << "opt::link"; break; + case opt::cpp_std: stream << "opt::cpp_std"; break; + case opt::build_shared: stream << "opt::build_shared"; break; + case opt::threads: stream << "opt::threads"; break; + case opt::optimization: stream << "opt::optimization"; break; + case opt::position_independent_code: stream << "opt::position_independent_code"; break; + case opt::position_independent_executable: stream << "opt::position_independent_executable"; break; + case opt::custom: stream << "opt::custom"; break; + } + + return stream; +} + +std::ostream& operator<<(std::ostream& stream, const std::pair& vs) +{ + stream << "{ " << vs.first << ", " << vs.second << " }"; + + return stream; +} +} + +// Controllable getConfiguration stub: +namespace +{ +std::string conf_host_cxx{}; +std::string conf_build_cxx{}; +} +const std::string& getConfiguration(const std::string& key, + const std::string& defval) +{ + if(key == cfg::host_cxx) + { + return conf_host_cxx; + } + + if(key == cfg::build_cxx) + { + return conf_build_cxx; + } + + assert(false); // bad key + + static std::string res{}; + return res; +} + +class ToolsTest + : public uUnit +{ +public: + ToolsTest() + { + uTEST(ToolsTest::getToolChain_test); + uTEST(ToolsTest::getOption_toolchain_test); + uTEST(ToolsTest::getOption_str_test); + } + + void getToolChain_test() + { + // host + conf_host_cxx = "/usr/bin/g++"; + uASSERT_EQUAL(ToolChain::gcc, getToolChain(OutputSystem::Host)); + + conf_host_cxx = "/usr/bin/g++-10"; + uASSERT_EQUAL(ToolChain::gcc, getToolChain(OutputSystem::Host)); + + conf_host_cxx = "/usr/bin/x86_64-pc-linux-gnu-g++-9.3.0"; + uASSERT_EQUAL(ToolChain::gcc, getToolChain(OutputSystem::Host)); + + conf_host_cxx = "/usr/bin/clang++"; + uASSERT_EQUAL(ToolChain::clang, getToolChain(OutputSystem::Host)); + + conf_host_cxx = "/usr/bin/clang++-10"; + uASSERT_EQUAL(ToolChain::clang, getToolChain(OutputSystem::Host)); + + conf_host_cxx = "/usr/lib/llvm/12/bin/i686-pc-linux-gnu-clang++-12"; + uASSERT_EQUAL(ToolChain::clang, getToolChain(OutputSystem::Host)); + + // build + conf_build_cxx = "/usr/bin/g++"; + uASSERT_EQUAL(ToolChain::gcc, getToolChain(OutputSystem::Build)); + + conf_build_cxx = "/usr/bin/g++-10"; + uASSERT_EQUAL(ToolChain::gcc, getToolChain(OutputSystem::Build)); + + conf_build_cxx = "/usr/bin/x86_64-pc-linux-gnu-g++-9.3.0"; + uASSERT_EQUAL(ToolChain::gcc, getToolChain(OutputSystem::Build)); + + conf_build_cxx = "/usr/bin/clang++"; + uASSERT_EQUAL(ToolChain::clang, getToolChain(OutputSystem::Build)); + + conf_build_cxx = "/usr/bin/clang++-10"; + uASSERT_EQUAL(ToolChain::clang, getToolChain(OutputSystem::Build)); + + conf_build_cxx = "/usr/lib/llvm/12/bin/i686-pc-linux-gnu-clang++-12"; + uASSERT_EQUAL(ToolChain::clang, getToolChain(OutputSystem::Build)); + } + + void getOption_toolchain_test() + { + using sv = std::vector; + + uUnit::assert_equal(sv{ "-o", "foo" }, getOption(ToolChain::clang, opt::output, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-g" }, getOption(ToolChain::clang, opt::debug), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-s" }, getOption(ToolChain::clang, opt::strip), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Wall" }, getOption(ToolChain::clang, opt::warn_all), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Werror" }, getOption(ToolChain::clang, opt::warnings_as_errors), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-MMD" }, getOption(ToolChain::clang, opt::generate_dep_tree), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-c" }, getOption(ToolChain::clang, opt::no_link), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Ifoo" }, getOption(ToolChain::clang, opt::include_path, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Lfoo" }, getOption(ToolChain::clang, opt::library_path, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-lfoo" }, getOption(ToolChain::clang, opt::link, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-std=foo" }, getOption(ToolChain::clang, opt::cpp_std, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-shared" }, getOption(ToolChain::clang, opt::build_shared), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-pthread" }, getOption(ToolChain::clang, opt::threads), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Ofoo" }, getOption(ToolChain::clang, opt::optimization, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-fPIC" }, getOption(ToolChain::clang, opt::position_independent_code), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-fPIE" }, getOption(ToolChain::clang, opt::position_independent_executable), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-foo" }, getOption(ToolChain::clang, opt::custom, "-foo"), __FILE__, __LINE__); + + uUnit::assert_equal(sv{ "-o", "foo" }, getOption(ToolChain::gcc, opt::output, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-g" }, getOption(ToolChain::gcc, opt::debug), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-s" }, getOption(ToolChain::gcc, opt::strip), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Wall" }, getOption(ToolChain::gcc, opt::warn_all), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Werror" }, getOption(ToolChain::gcc, opt::warnings_as_errors), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-MMD" }, getOption(ToolChain::gcc, opt::generate_dep_tree), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-c" }, getOption(ToolChain::gcc, opt::no_link), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Ifoo" }, getOption(ToolChain::gcc, opt::include_path, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Lfoo" }, getOption(ToolChain::gcc, opt::library_path, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-lfoo" }, getOption(ToolChain::gcc, opt::link, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-std=foo" }, getOption(ToolChain::gcc, opt::cpp_std, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-shared" }, getOption(ToolChain::gcc, opt::build_shared), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-pthread" }, getOption(ToolChain::gcc, opt::threads), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-Ofoo" }, getOption(ToolChain::gcc, opt::optimization, "foo"), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-fPIC" }, getOption(ToolChain::gcc, opt::position_independent_code), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-fPIE" }, getOption(ToolChain::gcc, opt::position_independent_executable), __FILE__, __LINE__); + uUnit::assert_equal(sv{ "-foo" }, getOption(ToolChain::gcc, opt::custom, "-foo"), __FILE__, __LINE__); + } + + void getOption_str_test() + { + using p = std::pair; + uUnit::assert_equal(p{ opt::include_path, "foo" }, getOption("-Ifoo", ToolChain::gcc), __FILE__, __LINE__); + uUnit::assert_equal(p{ opt::library_path, "foo" }, getOption("-Lfoo", ToolChain::gcc), __FILE__, __LINE__); + + uUnit::assert_equal(p{ opt::include_path, "foo" }, getOption("-Ifoo", ToolChain::clang), __FILE__, __LINE__); + uUnit::assert_equal(p{ opt::library_path, "foo" }, getOption("-Lfoo", ToolChain::clang), __FILE__, __LINE__); + } + + + +}; + +// Registers the fixture into the 'registry' +static ToolsTest test; -- cgit v1.2.3