diff options
Diffstat (limited to 'src/task_cc.cc')
-rw-r--r-- | src/task_cc.cc | 235 |
1 files changed, 172 insertions, 63 deletions
diff --git a/src/task_cc.cc b/src/task_cc.cc index c4343b6..9628455 100644 --- a/src/task_cc.cc +++ b/src/task_cc.cc @@ -6,49 +6,51 @@ #include <iostream> #include <fstream> #include <cassert> +#include <algorithm> -#include "libctor.h" +#include "ctor.h" #include "execute.h" #include "util.h" #include "tools.h" - -TaskCC::TaskCC(const BuildConfiguration& config, const Settings& settings, - const std::string& sourceDir, const Source& source) - : Task(config, settings, sourceDir) - , config(config) - , settings(settings) - , sourceDir(sourceDir) +#include "deps.h" + +TaskCC::TaskCC(const ctor::build_configuration& config_, const ctor::settings& settings_, + const std::string& sourceDir_, const ctor::source& source) + : Task(config_, settings_, sourceDir_) + , sourceFile(sourceDir_) + , config(config_) + , settings(settings_) + , sourceDir(sourceDir_) , _source(source) { - sourceFile = sourceDir; sourceFile /= source.file; std::filesystem::path base = sourceFile.parent_path(); - std::filesystem::create_directories(std::filesystem::path(settings.builddir) / base); base /= cleanUp(config.target); base += "-"; base += sourceFile.stem(); - target_type = TargetType::Object; + target_type = ctor::target_type::object; + output_system = config.system; source_language = source.language; - if(source_language == Language::Auto) + if(source_language == ctor::language::automatic) { source_language = languageFromExtension(sourceFile); } switch(source_language) { - case Language::C: + case ctor::language::c: base += "_c"; break; - case Language::Cpp: + case ctor::language::cpp: base += "_cc"; break; - case Language::Asm: + case ctor::language::assembler: base += "_asm"; break; - case Language::Auto: + case ctor::language::automatic: assert(0 && "This should never happen"); break; } @@ -56,36 +58,38 @@ TaskCC::TaskCC(const BuildConfiguration& config, const Settings& settings, if(source.output.empty()) { _targetFile = base; - _targetFile += ".o"; } else { _targetFile = source.output; } + auto toolchain = getToolChain(config.system); + _targetFile = extension(toolchain, target_type, config.system, _targetFile); + depsFile = targetFile().parent_path() / targetFile().stem(); depsFile += ".d"; flagsFile = targetFile().parent_path() / targetFile().stem(); flagsFile += ".flags"; + + std::filesystem::create_directories(targetFile().parent_path()); } -int TaskCC::registerDepTasksInner(const std::set<std::shared_ptr<Task>>& tasks) +int TaskCC::registerDepTasksInner(const std::vector<std::shared_ptr<Task>>& tasks) { for(const auto& task : tasks) { if(*task == _source.file) { - dependsTasks.insert(task); + if(std::find(dependsTasks.begin(), dependsTasks.end(), task) == dependsTasks.end()) + { + dependsTasks.push_back(task); + } } } return 0; } -std::string TaskCC::name() const -{ - return {}; -} - bool TaskCC::dirtyInner() { if(!std::filesystem::exists(sourceFile)) @@ -128,7 +132,8 @@ bool TaskCC::dirtyInner() } } - auto depList = readDeps(depsFile.string()); + auto toolchain = getToolChain(config.system); + auto depList = readDeps(depsFile.string(), toolchain); for(const auto& dep : depList) { if(!std::filesystem::exists(dep) || @@ -167,25 +172,59 @@ int TaskCC::runInner() if(settings.verbose == 0) { + std::string output; switch(sourceLanguage()) { - case Language::C: - std::cout << "CC "; + case ctor::language::c: + output = "CC "; break; - case Language::Cpp: - std::cout << "CXX "; + case ctor::language::cpp: + output = "CXX "; break; - case Language::Auto: - case Language::Asm: + case ctor::language::automatic: + case ctor::language::assembler: // Only c/c++ handled by this task type. break; } - std::cout << - sourceFile.lexically_normal().string() << " => " << - targetFile().lexically_normal().string() << "\n"; + output += sourceFile.lexically_normal().string() + " => " + + targetFile().lexically_normal().string() + '\n'; + std::cout << output << std::flush; + } + + auto toolchain = getToolChain(config.system); + const auto& cfg = ctor::get_configuration(); + switch(sourceLanguage()) + { + case ctor::language::c: + { + auto cflags = cfg.getenv("CFLAGS"); + if(!cflags.empty()) + { + append(args, c_option(toolchain, ctor::c_opt::custom, cflags)); + } + } + break; + case ctor::language::cpp: + { + auto cxxflags = cfg.getenv("CXXFLAGS"); + if(!cxxflags.empty()) + { + append(args, cxx_option(toolchain, ctor::cxx_opt::custom, cxxflags)); + } + } + break; + case ctor::language::automatic: + case ctor::language::assembler: + // Only c/c++ handled by this task type. + break; + } + auto res = execute(settings, compiler(), args, cfg.env); + if(res != 0) + { + std::filesystem::remove(targetFile()); } - return execute(compiler(), args, settings.verbose > 0); + return res; } int TaskCC::clean() @@ -256,17 +295,29 @@ std::string TaskCC::source() const std::vector<std::string> TaskCC::flags() const { + std::vector<std::string> flags; + auto toolchain = getToolChain(config.system); + switch(sourceLanguage()) { - case Language::C: - return config.flags.cflags; - case Language::Cpp: - return config.flags.cxxflags; + case ctor::language::c: + for(const auto& flag : config.flags.cflags) + { + append(flags, to_strings(toolchain, flag)); + } + return flags; + case ctor::language::cpp: + for(const auto& flag : config.flags.cxxflags) + { + append(flags, to_strings(toolchain, flag)); + } + return flags; default: std::cerr << "Unknown CC target type\n"; exit(1); break; } + } std::string TaskCC::flagsString() const @@ -281,44 +332,102 @@ std::string TaskCC::flagsString() const std::vector<std::string> TaskCC::getCompilerArgs() const { - auto tool_chain = getToolChain(config.system); - + auto toolchain = getToolChain(config.system); auto compiler_flags = flags(); std::vector<std::string> args; - append(args, getOption(tool_chain, opt::generate_dep_tree)); - if(std::filesystem::path(config.target).extension() == ".so") + switch(sourceLanguage()) { - // Add -fPIC arg to all contained object files - append(args, getOption(tool_chain, opt::position_independent_code)); - } + case ctor::language::c: + { + append(args, c_option(toolchain, ctor::c_opt::generate_dep_tree, depsFile.string())); - append(args, getOption(tool_chain, opt::no_link)); - args.push_back(sourceFile.string()); - append(args, getOption(tool_chain, opt::output, targetFile().string())); + if(std::filesystem::path(config.target).extension() == ".so") + { + // Add -fPIC arg to all contained object files + append(args, c_option(toolchain, + ctor::c_opt::position_independent_code)); + } - for(const auto& flag : compiler_flags) - { - auto option = getOption(flag); - switch(option.first) + append(args, c_option(toolchain, ctor::c_opt::no_link)); + args.push_back(sourceFile.string()); + append(args, c_option(toolchain, + ctor::c_opt::output, targetFile().string())); + + // Relative include paths has to be altered to be relative to sourceDir + for(const auto& flag : compiler_flags) + { + auto option = c_option(flag, toolchain); + switch(option.opt) + { + case ctor::c_opt::include_path: + { + std::filesystem::path path(option.arg); + if(path.is_relative()) + { + path = (sourceDir / path).lexically_normal(); + append(args, c_option(toolchain, + ctor::c_opt::include_path, path.string())); + continue; + } + } + break; + default: + break; + } + + args.push_back(flag); + } + } + break; + + case ctor::language::cpp: { - // Relative include paths has to be altered to be relative to sourceDir - case opt::include_path: + append(args, cxx_option(toolchain, ctor::cxx_opt::generate_dep_tree, depsFile.string())); + + if(std::filesystem::path(config.target).extension() == ".so") { - std::filesystem::path path(option.second); - if(path.is_relative()) + // Add -fPIC arg to all contained object files + append(args, cxx_option(toolchain, + ctor::cxx_opt::position_independent_code)); + } + + append(args, cxx_option(toolchain, ctor::cxx_opt::no_link)); + args.push_back(sourceFile.string()); + append(args, cxx_option(toolchain, + ctor::cxx_opt::output, targetFile().string())); + + // Relative include paths has to be altered to be relative to sourceDir + for(const auto& flag : compiler_flags) + { + auto option = cxx_option(flag, toolchain); + switch(option.opt) { - path = (sourceDir / path).lexically_normal(); - append(args, getOption(tool_chain, opt::include_path, path.string())); + case ctor::cxx_opt::include_path: + { + std::filesystem::path path(option.arg); + if(path.is_relative()) + { + path = (sourceDir / path).lexically_normal(); + append(args, cxx_option(toolchain, + ctor::cxx_opt::include_path, path.string())); + continue; + } + } + break; + default: + break; } + + args.push_back(flag); } - continue; - default: - break; + } + break; - args.push_back(flag); + default: + break; } return args; |