It also uses functors now. The run functions access properties of the
tool through the target. This will allow tool customization without
having to derive from the class, which will be useful for modularization.
40 files changed:
if(sdk.get_platform_jar().empty())
problems.push_back("Android platform not found");
if(sdk.get_platform_jar().empty())
problems.push_back("Android platform not found");
}
Target *AndroidAssetPackagingTool::create_target(const vector<Target *> &sources, const string &)
}
Target *AndroidAssetPackagingTool::create_target(const vector<Target *> &sources, const string &)
-Task *AndroidAssetPackagingTool::run(const Target &tgt) const
+Task *AndroidAssetPackagingTool::_run(const AndroidResourceBundle &res)
- const AndroidResourceBundle &res = dynamic_cast<const AndroidResourceBundle &>(tgt);
+ const AndroidAssetPackagingTool &tool = dynamic_cast<const AndroidAssetPackagingTool &>(*res.get_tool());
ExternalTask::Arguments argv;
ExternalTask::Arguments argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("package");
FS::Path work_dir = res.get_component()->get_package().get_source_directory();
argv.push_back("-I");
argv.push_back("package");
FS::Path work_dir = res.get_component()->get_package().get_source_directory();
argv.push_back("-I");
- argv.push_back(sdk.get_platform_jar().str());
+ argv.push_back(tool.sdk.get_platform_jar().str());
argv.push_back("-F");
argv.push_back(FS::relative(res.get_path(), work_dir).str());
argv.push_back("-F");
argv.push_back(FS::relative(res.get_path(), work_dir).str());
+class AndroidResourceBundle;
class AndroidSdk;
class AndroidAssetPackagingTool: public Tool
class AndroidSdk;
class AndroidAssetPackagingTool: public Tool
AndroidAssetPackagingTool(Builder &, const AndroidSdk &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
AndroidAssetPackagingTool(Builder &, const AndroidSdk &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const AndroidResourceBundle &);
using namespace std;
using namespace Msp;
using namespace std;
using namespace Msp;
-Target *AndroidManifestGenerator::create_target(const vector<Target *> &, const string &)
+AndroidManifestGenerator::AndroidManifestGenerator(Builder &b):
+ Tool(b, "AMG")
- throw logic_error("not implemented");
+ set_run_internal(_run);
-Task *AndroidManifestGenerator::run(const Target &target) const
+Target *AndroidManifestGenerator::create_target(const vector<Target *> &, const string &)
- const AndroidManifestFile &manifest = dynamic_cast<const AndroidManifestFile &>(target);
- return new InternalTask([&manifest]{ return _run(manifest); });
+ throw logic_error("not implemented");
}
bool AndroidManifestGenerator::_run(const AndroidManifestFile &manifest)
}
bool AndroidManifestGenerator::_run(const AndroidManifestFile &manifest)
class AndroidManifestGenerator: public Tool
{
public:
class AndroidManifestGenerator: public Tool
{
public:
- AndroidManifestGenerator(Builder &b): Tool(b, "AMG") { }
+ AndroidManifestGenerator(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const AndroidManifestFile &);
private:
static bool _run(const AndroidManifestFile &);
Tool(b, "APK")
{
set_command("jar");
Tool(b, "APK")
{
set_command("jar");
}
Target *ApkBuilder::create_target(const vector<Target *> &sources, const string &)
}
Target *ApkBuilder::create_target(const vector<Target *> &sources, const string &)
-Task *ApkBuilder::run(const Target &tgt) const
+Task *ApkBuilder::_run(const AndroidPackageFile &apk)
- const AndroidPackageFile &apk = dynamic_cast<const AndroidPackageFile &>(tgt);
+ const ApkBuilder &tool = dynamic_cast<const ApkBuilder &>(*apk.get_tool());
ExternalTask::Arguments argv;
ExternalTask::Arguments argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("u");
FS::Path input_path;
argv.push_back("u");
FS::Path input_path;
task->set_stdin(FS::basename(input_path));
task->set_stdout(FS::relative(apk.get_path(), work_dir));
ChainedTask *chain = new ChainedTask(task);
task->set_stdin(FS::basename(input_path));
task->set_stdout(FS::relative(apk.get_path(), work_dir));
ChainedTask *chain = new ChainedTask(task);
- chain->add_task(jarsigner->run(tgt));
+ chain->add_task(tool.jarsigner->run(apk));
+class AndroidPackageFile;
+
class ApkBuilder: public Tool
{
private:
class ApkBuilder: public Tool
{
private:
Target *create_target(const std::vector<Target *> &, const std::string &) override;
protected:
void do_prepare() override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
protected:
void do_prepare() override;
-public:
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const AndroidPackageFile &);
using namespace std;
using namespace Msp;
using namespace std;
using namespace Msp;
-Target *CompileCommandsGenerator::create_target(const vector<Target *> &, const string &)
+CompileCommandsGenerator::CompileCommandsGenerator(Builder &b):
+ Tool(b, "CCJG")
- throw logic_error("Not implemented");
+ set_run_internal(_run);
-Task *CompileCommandsGenerator::run(const Target &target) const
+Target *CompileCommandsGenerator::create_target(const vector<Target *> &, const string &)
- const CompileCommandsJson &cmds = dynamic_cast<const CompileCommandsJson &>(target);
- return new InternalTask([&cmds]{ return _run(cmds); });
+ throw logic_error("Not implemented");
}
bool CompileCommandsGenerator::_run(const CompileCommandsJson &cmds)
}
bool CompileCommandsGenerator::_run(const CompileCommandsJson &cmds)
class CompileCommandsGenerator: public Tool
{
public:
class CompileCommandsGenerator: public Tool
{
public:
- CompileCommandsGenerator(Builder &b): Tool(b, "CCJG") { }
+ CompileCommandsGenerator(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const CompileCommandsJson &);
private:
static bool _run(const CompileCommandsJson &);
using namespace std;
using namespace Msp;
using namespace std;
using namespace Msp;
+Copy::Copy(Builder &b):
+ Tool(b, "CP")
+{
+ set_run_internal(_run);
+}
+
Target *Copy::create_target(const vector<Target *> &sources, const string &arg)
{
FileTarget &file_tgt = dynamic_cast<FileTarget &>(*sources.front());
Target *Copy::create_target(const vector<Target *> &sources, const string &arg)
{
FileTarget &file_tgt = dynamic_cast<FileTarget &>(*sources.front());
-Task *Copy::run(const Target &target) const
-{
- const InstalledFile &install = dynamic_cast<const InstalledFile &>(target);
- return new InternalTask([&install]{ return _run(install); });
-}
-
bool Copy::_run(const InstalledFile &install)
{
const FileTarget &source = install.get_source();
bool Copy::_run(const InstalledFile &install)
{
const FileTarget &source = install.get_source();
class Copy: public Tool
{
public:
class Copy: public Tool
{
public:
- Copy(Builder &b): Tool(b, "CP") { }
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const InstalledFile &);
private:
static bool _run(const InstalledFile &);
Tool(b, "DATA")
{
set_command("mspdatatool");
Tool(b, "DATA")
{
set_command("mspdatatool");
input_suffixes.push_back(".mdt");
}
input_suffixes.push_back(".mdt");
}
-Task *DataTool::run(const Target &tgt) const
+Task *DataTool::_run(const Target &tgt)
+ const Tool &tool = *tgt.get_tool();
const Component &comp = *tgt.get_component();
FS::Path work_dir = comp.get_package().get_source_directory();
vector<string> argv;
const Component &comp = *tgt.get_component();
FS::Path work_dir = comp.get_package().get_source_directory();
vector<string> argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("-o");
argv.push_back(FS::relative(dynamic_cast<const FileTarget &>(tgt).get_path(), work_dir).str());
argv.push_back("-o");
argv.push_back(FS::relative(dynamic_cast<const FileTarget &>(tgt).get_path(), work_dir).str());
Target *create_source(const Component &, const Msp::FS::Path &) const override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
std::string create_build_signature(const BuildInfo &) const override;
Target *create_source(const Component &, const Msp::FS::Path &) const override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
std::string create_build_signature(const BuildInfo &) const override;
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const Target &);
set_command("ar", true);
input_suffixes.push_back(".o");
processing_unit = COMPONENT;
set_command("ar", true);
input_suffixes.push_back(".o");
processing_unit = COMPONENT;
}
Target *GnuArchiver::create_target(const vector<Target *> &sources, const string &)
}
Target *GnuArchiver::create_target(const vector<Target *> &sources, const string &)
-Task *GnuArchiver::run(const Target &target) const
+Task *GnuArchiver::_run(const StaticLibrary &lib)
- const StaticLibrary &lib = dynamic_cast<const StaticLibrary &>(target);
+ const Tool &tool = *lib.get_tool();
const Component &comp = *lib.get_component();
vector<string> argv;
const Component &comp = *lib.get_component();
vector<string> argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("rc");
FS::Path work_dir = comp.get_package().get_source_directory();
argv.push_back("rc");
FS::Path work_dir = comp.get_package().get_source_directory();
class GnuArchiver: public Tool
{
public:
GnuArchiver(Builder &, const Architecture &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
class GnuArchiver: public Tool
{
public:
GnuArchiver(Builder &, const Architecture &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const StaticLibrary &);
throw invalid_argument("GnuCompiler::GnuCompiler");
set_command((tag=="CXX" ? "g++" : "gcc"), true);
throw invalid_argument("GnuCompiler::GnuCompiler");
set_command((tag=="CXX" ? "g++" : "gcc"), true);
}
Target *GnuCompiler::create_source(const Component &comp, const FS::Path &path) const
}
Target *GnuCompiler::create_source(const Component &comp, const FS::Path &path) const
-Task *GnuCompiler::run(const Target &target) const
+Task *GnuCompiler::_run(const ObjectFile &object)
- const ObjectFile &object = dynamic_cast<const ObjectFile &>(target);
+ const GnuCompiler &tool = dynamic_cast<const GnuCompiler &>(*object.get_tool());
+ const Architecture &arch = *tool.get_architecture();
ExternalTask::Arguments argv;
ExternalTask::Arguments argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("-c");
BuildInfo binfo;
argv.push_back("-c");
BuildInfo binfo;
- target.collect_build_info(binfo);
+ object.collect_build_info(binfo);
- string tag_for_std = (tag=="OBJC" ? "CC" : tag);
+ const std::string &tool_tag = tool.get_tag();
+ string tag_for_std = (tool_tag=="OBJC" ? "CC" : tool_tag);
if(binfo.standards.count(tag_for_std))
argv.push_back("-std="+get_item(binfo.standards, tag_for_std).str());
if(binfo.standards.count(tag_for_std))
argv.push_back("-std="+get_item(binfo.standards, tag_for_std).str());
- if(tag=="OBJC" && binfo.standards.count(tag))
- argv.push_back("-fobjc-std="+get_item(binfo.standards, tag).str());
+ if(tool_tag=="OBJC" && binfo.standards.count(tool_tag))
+ argv.push_back("-fobjc-std="+get_item(binfo.standards, tool_tag).str());
if(binfo.warning_level>=1)
{
if(binfo.warning_level>=1)
{
{
argv.push_back("-Wextra");
argv.push_back("-Wundef");
{
argv.push_back("-Wextra");
argv.push_back("-Wundef");
+ if(tool.version>=0x80000)
argv.push_back("-Wno-cast-function-type");
}
if(binfo.warning_level>=3)
argv.push_back("-Wno-cast-function-type");
}
if(binfo.warning_level>=3)
argv.push_back("-pedantic");
argv.push_back("-Wno-long-long");
argv.push_back("-Wshadow");
argv.push_back("-pedantic");
argv.push_back("-Wno-long-long");
argv.push_back("-Wshadow");
{
argv.push_back("-Wc++-compat");
argv.push_back("-Wstrict-prototypes");
{
argv.push_back("-Wc++-compat");
argv.push_back("-Wstrict-prototypes");
if(binfo.debug)
argv.push_back("-fno-omit-frame-pointer");
}
if(binfo.debug)
argv.push_back("-fno-omit-frame-pointer");
}
- if(binfo.threads && architecture->get_system()!="windows" && architecture->get_system()!="darwin")
+ if(binfo.threads && arch.get_system()!="windows" && arch.get_system()!="darwin")
argv.push_back("-pthread");
argv.push_back("-pthread");
- if(object.is_used_in_shared_library() && architecture->get_system()!="windows")
+ if(object.is_used_in_shared_library() && arch.get_system()!="windows")
- if((architecture->get_type()=="x86" || architecture->get_type()=="ppc") && !architecture->is_native())
- argv.push_back(format("-m%d", architecture->get_bits()));
+ if((arch.get_type()=="x86" || arch.get_type()=="ppc") && !arch.is_native())
+ argv.push_back(format("-m%d", arch.get_bits()));
- string cpu = architecture->get_cpu();
+ string cpu = arch.get_cpu();
if(!cpu.empty())
{
for(unsigned i=0; cpus[i]; i+=2)
if(!cpu.empty())
{
for(unsigned i=0; cpus[i]; i+=2)
argv.push_back("-march="+cpu);
}
argv.push_back("-march="+cpu);
}
- if(!architecture->get_fpu().empty())
+ if(!arch.get_fpu().empty())
- if(architecture->get_type()=="x86")
+ if(arch.get_type()=="x86")
- if(architecture->get_fpu()=="387")
+ if(arch.get_fpu()=="387")
argv.push_back("-mfpmath=387");
argv.push_back("-mfpmath=387");
- else if(!architecture->get_fpu().compare(0, 3, "sse"))
+ else if(!arch.get_fpu().compare(0, 3, "sse"))
argv.push_back("-mfpmath=sse");
argv.push_back("-mfpmath=sse");
- if(architecture->get_fpu()=="sse")
+ if(arch.get_fpu()=="sse")
argv.push_back("-msse2");
argv.push_back("-msse2");
- else if(architecture->get_fpu()=="sse3")
+ else if(arch.get_fpu()=="sse3")
argv.push_back("-msse3");
argv.push_back("-msse3");
- else if(architecture->get_fpu()=="sse4.1")
+ else if(arch.get_fpu()=="sse4.1")
argv.push_back("-msse4.1");
}
argv.push_back("-msse4.1");
}
- else if(architecture->get_type()=="arm")
+ else if(arch.get_type()=="arm")
- argv.push_back("-mfpu="+architecture->get_fpu());
+ argv.push_back("-mfpu="+arch.get_fpu());
argv.push_back("-mfloat-abi=softfp");
}
}
argv.push_back("-mfloat-abi=softfp");
}
}
/**
Common base class for GNU compilers. Turns SourceFiles into ObjectFiles.
/**
Common base class for GNU compilers. Turns SourceFiles into ObjectFiles.
void prepare_syspath();
void prepare_version();
void prepare_version(const std::string &);
void prepare_syspath();
void prepare_version();
void prepare_version(const std::string &);
-public:
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const ObjectFile &);
-Task *GnuLinker::run(const Target &) const
-{
- throw logic_error("GnuLinker should not be run directly");
-}
-
GnuLinker::Linker::Linker(GnuLinker &p, const string &ct):
SubTool(p),
GnuLinker::Linker::Linker(GnuLinker &p, const string &ct):
SubTool(p),
set_command("g++", true);
else
throw invalid_argument("GnuLinker::Linker::Linker");
set_command("g++", true);
else
throw invalid_argument("GnuLinker::Linker::Linker");
}
string GnuLinker::Linker::create_build_signature(const BuildInfo &binfo) const
}
string GnuLinker::Linker::create_build_signature(const BuildInfo &binfo) const
-Task *GnuLinker::Linker::run(const Target &target) const
+Task *GnuLinker::Linker::_run(const Binary &bin)
- const Binary &bin = dynamic_cast<const Binary &>(target);
+ const Linker &tool = dynamic_cast<const Linker &>(*bin.get_tool());
+ const Builder &builder = tool.get_builder();
+ const Architecture &arch = *tool.get_architecture();
ExternalTask::Arguments argv;
ExternalTask::Arguments argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
FS::Path work_dir = bin.get_component()->get_package().get_source_directory();
FS::Path work_dir = bin.get_component()->get_package().get_source_directory();
{
argv.push_back("-shared");
argv.push_back("-fPIC");
{
argv.push_back("-shared");
argv.push_back("-fPIC");
- if(architecture->get_system()!="windows" && !shlib->get_soname().empty())
+ if(arch.get_system()!="windows" && !shlib->get_soname().empty())
- if(architecture->get_system()=="darwin")
+ if(arch.get_system()=="darwin")
{
argv.push_back("-install_name");
argv.push_back(shlib->get_soname());
{
argv.push_back("-install_name");
argv.push_back(shlib->get_soname());
- target.collect_build_info(binfo);
+ bin.collect_build_info(binfo);
const FS::Path &sysroot = binfo.sysroot;
if(!sysroot.empty())
const FS::Path &sysroot = binfo.sysroot;
if(!sysroot.empty())
argv.push_back("-L"+p.str());
if(binfo.strip)
argv.push_back("-s");
argv.push_back("-L"+p.str());
if(binfo.strip)
argv.push_back("-s");
- if(binfo.threads && architecture->get_system()!="windows" && architecture->get_system()!="darwin")
+ if(binfo.threads && arch.get_system()!="windows" && arch.get_system()!="darwin")
argv.push_back("-pthread");
const Architecture &native_arch = builder.get_native_arch();
argv.push_back("-pthread");
const Architecture &native_arch = builder.get_native_arch();
- if(architecture->is_native() && architecture->get_bits()!=native_arch.get_bits())
- argv.push_back(format("-m%d", architecture->get_bits()));
+ if(arch.is_native() && arch.get_bits()!=native_arch.get_bits())
+ argv.push_back(format("-m%d", arch.get_bits()));
argv.push_back("-o");
argv.push_back(relative(bin.get_path(), work_dir).str());
argv.push_back("-o");
argv.push_back(relative(bin.get_path(), work_dir).str());
bool static_link_ok = (binfo.libmode<=BuildInfo::STATIC);
bool static_link_ok = (binfo.libmode<=BuildInfo::STATIC);
- for(Target *d: target.get_dependencies())
+ for(Target *d: bin.get_dependencies())
{
FileTarget *file = dynamic_cast<FileTarget *>(d);
Target *tgt = d->get_real_target();
{
FileTarget *file = dynamic_cast<FileTarget *>(d);
Target *tgt = d->get_real_target();
argv.push_back("-static");
else
{
argv.push_back("-static");
else
{
- if(compiler_tag=="CXX")
+ if(tool.compiler_tag=="CXX")
{
auto i = binfo.libmodes.find("stdc++");
if(i!=binfo.libmodes.end() && i->second<=BuildInfo::STATIC)
argv.push_back("-static-libstdc++");
}
{
auto i = binfo.libmodes.find("stdc++");
if(i!=binfo.libmodes.end() && i->second<=BuildInfo::STATIC)
argv.push_back("-static-libstdc++");
}
- if(architecture->get_system()=="windows")
+ if(arch.get_system()=="windows")
argv.push_back("-Wl,--enable-auto-import");
}
argv.push_back("-Wl,--enable-auto-import");
}
/**
The GNU linker. Turns ObjectFiles into Executables and SharedLibraries. To
create a shared library, specify "shared" as the second argument to
/**
The GNU linker. Turns ObjectFiles into Executables and SharedLibraries. To
create a shared library, specify "shared" as the second argument to
std::string create_build_signature(const BuildInfo &) const override;
private:
void do_prepare() override;
std::string create_build_signature(const BuildInfo &) const override;
private:
void do_prepare() override;
- Task *run(const Target &) const override;
+ static Task *_run(const Binary &);
};
Linker *default_linker = 0;
};
Linker *default_linker = 0;
Target *create_install(Target &) const override;
protected:
void do_prepare() override;
Target *create_install(Target &) const override;
protected:
void do_prepare() override;
-public:
- Task *run(const Target &) const override;
Tool(b, "JSGN")
{
set_command("jarsigner");
Tool(b, "JSGN")
{
set_command("jarsigner");
}
Target *JarSigner::create_target(const vector<Target *> &, const string &)
}
Target *JarSigner::create_target(const vector<Target *> &, const string &)
throw logic_error("not implemented");
}
throw logic_error("not implemented");
}
-Task *JarSigner::run(const Target &tgt) const
+Task *JarSigner::_run(const FileTarget &file)
- const FileTarget &file = dynamic_cast<const FileTarget &>(tgt);
+ const Tool &tool = *file.get_tool();
ExternalTask::Arguments argv;
ExternalTask::Arguments argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
// TODO Make this generic
FS::Path home_dir = Msp::getenv("HOME");
// TODO Make this generic
FS::Path home_dir = Msp::getenv("HOME");
class JarSigner: public Tool
{
public:
JarSigner(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
class JarSigner: public Tool
{
public:
JarSigner(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const FileTarget &);
Tool(b, a, "DLL")
{
set_command("dlltool", true);
Tool(b, a, "DLL")
{
set_command("dlltool", true);
}
Target *MingwDllTool::create_target(const vector<Target *> &sources, const string &)
}
Target *MingwDllTool::create_target(const vector<Target *> &sources, const string &)
-Task *MingwDllTool::run(const Target &target) const
+Task *MingwDllTool::_run(const Target &target)
+ const Tool &tool = *target.get_tool();
+
const ImportLibrary *imp = dynamic_cast<const ImportLibrary *>(&target);
const ExportDefinitions *exp = 0;
if(imp)
const ImportLibrary *imp = dynamic_cast<const ImportLibrary *>(&target);
const ExportDefinitions *exp = 0;
if(imp)
throw invalid_argument("MingwDllTool::run");
vector<string> argv;
throw invalid_argument("MingwDllTool::run");
vector<string> argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
/* dlltool is stupid and puts temporary files in the working directory by
default */
/* dlltool is stupid and puts temporary files in the working directory by
default */
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_install(Target &) const override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_install(Target &) const override;
- Task *run(const Target &) const override;
+
+private:
+ static Task *_run(const Target &);
input_suffixes.push_back(".o");
processing_unit = COMPONENT;
set_command((ms_tools.get_vc_bin_dir()/"lib.exe").str(), false);
input_suffixes.push_back(".o");
processing_unit = COMPONENT;
set_command((ms_tools.get_vc_bin_dir()/"lib.exe").str(), false);
}
Target *MsvcArchiver::create_target(const vector<Target *> &sources, const string &)
}
Target *MsvcArchiver::create_target(const vector<Target *> &sources, const string &)
-Task *MsvcArchiver::run(const Target &target) const
+Task *MsvcArchiver::_run(const StaticLibrary &lib)
- const StaticLibrary &lib = dynamic_cast<const StaticLibrary &>(target);
const Component &comp = *lib.get_component();
const Component &comp = *lib.get_component();
+ const Tool &tool = *lib.get_tool();
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("/NOLOGO");
FS::Path work_dir = comp.get_package().get_source_directory();
argv.push_back("/NOLOGO");
FS::Path work_dir = comp.get_package().get_source_directory();
#include "tool.h"
class MicrosoftTools;
#include "tool.h"
class MicrosoftTools;
class MsvcArchiver: public Tool
{
class MsvcArchiver: public Tool
{
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
+private:
+ static Task *_run(const StaticLibrary &);
throw invalid_argument("MsvcCompiler::MsvcCompiler");
set_command((ms_tools.get_vc_bin_dir()/"cl.exe").str(), false);
throw invalid_argument("MsvcCompiler::MsvcCompiler");
set_command((ms_tools.get_vc_bin_dir()/"cl.exe").str(), false);
}
Target *MsvcCompiler::create_source(const Component &comp, const FS::Path &path) const
}
Target *MsvcCompiler::create_source(const Component &comp, const FS::Path &path) const
setenv("INCLUDE", path);
}
setenv("INCLUDE", path);
}
-Task *MsvcCompiler::run(const Target &target) const
+Task *MsvcCompiler::_run(const ObjectFile &object)
- const ObjectFile &object = dynamic_cast<const ObjectFile &>(target);
+ const Tool &tool = *object.get_tool();
ExternalTask::Arguments argv;
ExternalTask::Arguments argv;
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("/nologo");
argv.push_back("/c");
BuildInfo binfo;
argv.push_back("/nologo");
argv.push_back("/c");
BuildInfo binfo;
- target.collect_build_info(binfo);
+ object.collect_build_info(binfo);
- if(binfo.standards.count(tag))
+ if(binfo.standards.count(tool.get_tag()))
- const BuildInfo::LanguageStandard &std = get_item(binfo.standards, tag);
- if((tag=="CXX" && std.year>2011) || (tag=="CC" && std.year>1999))
+ const BuildInfo::LanguageStandard &std = get_item(binfo.standards, tool.get_tag());
+ if((tool.get_tag()=="CXX" && std.year>2011) || (tool.get_tag()=="CC" && std.year>1999))
argv.push_back("/std:"+std.str());
}
argv.push_back("/std:"+std.str());
}
#include "tool.h"
class MicrosoftTools;
#include "tool.h"
class MicrosoftTools;
class MsvcCompiler: public Tool
{
class MsvcCompiler: public Tool
{
void do_prepare() override;
public:
void do_prepare() override;
public:
- Task *run(const Target &) const override;
+ static Task *_run(const ObjectFile &);
processing_unit = COMPONENT;
set_command((ms_tools.get_vc_bin_dir()/"link.exe").str(), false);
processing_unit = COMPONENT;
set_command((ms_tools.get_vc_bin_dir()/"link.exe").str(), false);
}
Target *MsvcLinker::create_target(const vector<Target *> &sources, const string &arg)
}
Target *MsvcLinker::create_target(const vector<Target *> &sources, const string &arg)
-Task *MsvcLinker::run(const Target &target) const
+Task *MsvcLinker::_run(const Binary &bin)
- const Binary &bin = dynamic_cast<const Binary &>(target);
+ const Tool &tool = *bin.get_tool();
- argv.push_back(executable->get_path().str());
+ argv.push_back(tool.get_executable()->get_path().str());
argv.push_back("/NOLOGO");
FS::Path work_dir = bin.get_component()->get_package().get_source_directory();
argv.push_back("/NOLOGO");
FS::Path work_dir = bin.get_component()->get_package().get_source_directory();
argv.push_back("/DLL");
BuildInfo binfo;
argv.push_back("/DLL");
BuildInfo binfo;
- target.collect_build_info(binfo);
+ bin.collect_build_info(binfo);
/*for(const FS::Path &p: binfo.libpath)
argv.push_back("/LIBPATH:"+p.str());*/
/*for(const FS::Path &p: binfo.libpath)
argv.push_back("/LIBPATH:"+p.str());*/
argv.push_back("/OUT:"+relative(bin.get_path(), work_dir).str());
argv.push_back("/OUT:"+relative(bin.get_path(), work_dir).str());
- for(Target *d: target.get_dependencies())
+ for(Target *d: bin.get_dependencies())
{
FileTarget *file = dynamic_cast<FileTarget *>(d);
Target *tgt = d->get_real_target();
{
FileTarget *file = dynamic_cast<FileTarget *>(d);
Target *tgt = d->get_real_target();
class MicrosoftTools;
class MsvcLinker: public Tool
class MicrosoftTools;
class MsvcLinker: public Tool
void do_prepare() override;
public:
void do_prepare() override;
public:
- Task *run(const Target &) const override;
+ static Task *_run(const Binary &);
using namespace std;
using namespace Msp;
using namespace std;
using namespace Msp;
-Target *PkgConfigGenerator::create_target(const vector<Target *> &, const string &)
+PkgConfigGenerator::PkgConfigGenerator(Builder &b):
+ Tool(b, "PCG")
- throw logic_error("Not implemented");
+ set_run_internal(_run);
-Task *PkgConfigGenerator::run(const Target &target) const
+Target *PkgConfigGenerator::create_target(const vector<Target *> &, const string &)
- const PkgConfigFile &pkgc = dynamic_cast<const PkgConfigFile &>(target);
- return new InternalTask([&pkgc]{ return _run(pkgc); });
+ throw logic_error("Not implemented");
}
bool PkgConfigGenerator::_run(const PkgConfigFile &pkgc)
}
bool PkgConfigGenerator::_run(const PkgConfigFile &pkgc)
class PkgConfigGenerator: public Tool
{
public:
class PkgConfigGenerator: public Tool
{
public:
- PkgConfigGenerator(Builder &b): Tool(b, "PCG") { }
+ PkgConfigGenerator(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const PkgConfigFile &);
private:
static bool _run(const PkgConfigFile &);
SourceGenerator::SourceGenerator(Builder &b, const SourcePackage &p, const string &t):
Tool(b, t),
package(p)
SourceGenerator::SourceGenerator(Builder &b, const SourcePackage &p, const string &t):
Tool(b, t),
package(p)
Target *SourceGenerator::create_source(const Component &comp, const FS::Path &path) const
{
Target *SourceGenerator::create_source(const Component &comp, const FS::Path &path) const
{
-Task *SourceGenerator::run(const Target &target) const
+Task *SourceGenerator::_run(const SourceFile &out_src)
- const SourceFile &out_src = dynamic_cast<const SourceFile &>(target);
const FS::Path &work_dir = out_src.get_package()->get_source_directory();
const FS::Path &work_dir = out_src.get_package()->get_source_directory();
+ const SourceGenerator &tool = dynamic_cast<const SourceGenerator &>(*out_src.get_tool());
- args.push_back(executable->get_path().str());
- args.insert(args.end(), arguments.begin(), arguments.end());
+ args.push_back(tool.get_executable()->get_path().str());
+ args.insert(args.end(), tool.arguments.begin(), tool.arguments.end());
- for(const Target *d: target.get_dependencies())
+ for(const Target *d: out_src.get_dependencies())
if(const TemplateFile *tmpl = dynamic_cast<const TemplateFile *>(d))
args.push_back(FS::relative(tmpl->get_path(), work_dir).str());
if(const TemplateFile *tmpl = dynamic_cast<const TemplateFile *>(d))
args.push_back(FS::relative(tmpl->get_path(), work_dir).str());
- if(!out_argument.empty())
- args.push_back(out_argument);
+ if(!tool.out_argument.empty())
+ args.push_back(tool.out_argument);
args.push_back(FS::relative(out_src.get_path(), work_dir).str());
return new ExternalTask(args, work_dir);
args.push_back(FS::relative(out_src.get_path(), work_dir).str());
return new ExternalTask(args, work_dir);
#include "sourcepackage.h"
#include "tool.h"
#include "sourcepackage.h"
#include "tool.h"
class SourceGenerator: public Tool
{
public:
class SourceGenerator: public Tool
{
public:
Target *create_source(const Component &, const Msp::FS::Path &) const override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_source(const Component &, const Msp::FS::Path &) const override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
+private:
+ static Task *_run(const SourceFile &);
Tool(b, "TAR")
{
processing_unit = COMPONENT;
Tool(b, "TAR")
{
processing_unit = COMPONENT;
+ set_run_internal(&_run);
}
Target *Tar::create_target(const vector<Target *> &sources, const string &arg)
}
Target *Tar::create_target(const vector<Target *> &sources, const string &arg)
-Task *Tar::run(const Target &target) const
-{
- const TarBall &tarball = dynamic_cast<const TarBall &>(target);
- return new InternalTask([&tarball]{ return _run(tarball); });
-}
-
bool Tar::_run(const TarBall &tarball)
{
const FS::Path &pkg_src = tarball.get_package()->get_source_directory();
bool Tar::_run(const TarBall &tarball)
{
const FS::Path &pkg_src = tarball.get_package()->get_source_directory();
Tar(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Tar(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const TarBall &);
private:
static bool _run(const TarBall &);
+void Tool::set_run(function<Task *(const Target &)> f)
+{
+ run_func = move(f);
+}
+
bool Tool::accepts_suffix(const string &suffix, bool aux) const
{
return (any_equals(input_suffixes, suffix) || (aux && any_equals(aux_suffixes, suffix)));
bool Tool::accepts_suffix(const string &suffix, bool aux) const
{
return (any_equals(input_suffixes, suffix) || (aux && any_equals(aux_suffixes, suffix)));
#ifndef TOOL_H_
#define TOOL_H_
#ifndef TOOL_H_
#define TOOL_H_
#include <string>
#include <vector>
#include <msp/fs/path.h>
#include "buildinfo.h"
#include <string>
#include <vector>
#include <msp/fs/path.h>
#include "buildinfo.h"
+#include "internaltask.h"
#include "virtualfilesystem.h"
class Architecture;
#include "virtualfilesystem.h"
class Architecture;
class Component;
class FileTarget;
class Target;
class Component;
class FileTarget;
class Target;
/**
Base class for tools. Tools are used to turn targets into other targets.
/**
Base class for tools. Tools are used to turn targets into other targets.
ProcessingUnit processing_unit = ONE_FILE;
VirtualFileSystem::SearchPath system_path;
BuildInfo build_info;
ProcessingUnit processing_unit = ONE_FILE;
VirtualFileSystem::SearchPath system_path;
BuildInfo build_info;
+ std::function<Task *(const Target &)> run_func;
bool prepared = false;
std::vector<std::string> problems;
bool prepared = false;
std::vector<std::string> problems;
public:
virtual ~Tool() { }
public:
virtual ~Tool() { }
+ Builder &get_builder() const { return builder; }
+
const std::string &get_tag() const { return tag; }
/** Returns the architecture this tool builds for. May return null if the
tool is architecture-agnostic. */
const Architecture *get_architecture() const { return architecture; }
const std::string &get_tag() const { return tag; }
/** Returns the architecture this tool builds for. May return null if the
tool is architecture-agnostic. */
const Architecture *get_architecture() const { return architecture; }
+protected:
+ void set_run(std::function<Task *(const Target &)>);
+
+ template<typename T>
+ void set_run(Task *(*)(const T &));
+
+ template<typename T>
+ void set_run_internal(bool (*)(const T &));
+
+public:
/** Overrides the command used by the tool. The new command should accept
the same command line arguments. Only works on tools that use an external
command. If cross is true and the architecture is not native, a cross
/** Overrides the command used by the tool. The new command should accept
the same command line arguments. Only works on tools that use an external
command. If cross is true and the architecture is not native, a cross
/** Invokes the tool to build a target. This should not be called directly;
use Target::build() instead. */
/** Invokes the tool to build a target. This should not be called directly;
use Target::build() instead. */
- virtual Task *run(const Target &) const = 0;
+ Task *run(const Target &t) const { return run_func(t); }
+template<typename T>
+void Tool::set_run(Task *(*f)(const T &))
+{
+ set_run([f](const Target &t){ return f(dynamic_cast<const T &>(t)); });
+}
+
+template<typename T>
+void Tool::set_run_internal(bool (*f)(const T &))
+{
+ set_run([f](const Target &t){
+ const T &ct = dynamic_cast<const T &>(t);
+ return new InternalTask([f, &ct]{ return f(ct); });
+ });
+}
+
+
void operator>>(const Msp::LexicalConverter &, Tool::ProcessingUnit &);
#endif
void operator>>(const Msp::LexicalConverter &, Tool::ProcessingUnit &);
#endif
using namespace std;
using namespace Msp;
using namespace std;
using namespace Msp;
-Target *VcxProjectGenerator::create_target(const vector<Target *> &, const string &)
+VcxProjectGenerator::VcxProjectGenerator(Builder &b):
+ Tool(b, "VCXG")
- throw logic_error("Not implemented");
+ set_run_internal(_run);
-Task *VcxProjectGenerator::run(const Target &target) const
+Target *VcxProjectGenerator::create_target(const vector<Target *> &, const string &)
- const VcxProjectFile &project = dynamic_cast<const VcxProjectFile &>(target);
- return new InternalTask([&project]{ return _run(project); });
+ throw logic_error("Not implemented");
}
bool VcxProjectGenerator::_run(const VcxProjectFile &project)
}
bool VcxProjectGenerator::_run(const VcxProjectFile &project)
class VcxProjectGenerator: public Tool
{
public:
class VcxProjectGenerator: public Tool
{
public:
- VcxProjectGenerator(Builder &b): Tool(b, "VCXG") { }
+ VcxProjectGenerator(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const VcxProjectFile &);
private:
static bool _run(const VcxProjectFile &);
using namespace std;
using namespace Msp;
using namespace std;
using namespace Msp;
-Target *VsSolutionGenerator::create_target(const vector<Target *> &, const string &)
+VsSolutionGenerator::VsSolutionGenerator(Builder &b):
+ Tool(b, "VSSG")
- throw logic_error("Not implemented");
+ set_run_internal(_run);
-Task *VsSolutionGenerator::run(const Target &target) const
+Target *VsSolutionGenerator::create_target(const vector<Target *> &, const string &)
- const VsSolutionFile &solution = dynamic_cast<const VsSolutionFile &>(target);
- return new InternalTask([&solution]{ return _run(solution); });
+ throw logic_error("Not implemented");
}
bool VsSolutionGenerator::_run(const VsSolutionFile &solution)
}
bool VsSolutionGenerator::_run(const VsSolutionFile &solution)
class VsSolutionGenerator: public Tool
{
public:
class VsSolutionGenerator: public Tool
{
public:
- VsSolutionGenerator(Builder &b): Tool(b, "VSSG") { }
+ VsSolutionGenerator(Builder &);
Target *create_target(const std::vector<Target *> &, const std::string &) override;
Target *create_target(const std::vector<Target *> &, const std::string &) override;
- Task *run(const Target &) const override;
private:
static bool _run(const VsSolutionFile &);
private:
static bool _run(const VsSolutionFile &);