#include <msp/core/environ.h>
#include <msp/fs/utils.h>
-#include <msp/strings/format.h>
#include <msp/strings/utils.h>
#include "builder.h"
#include "component.h"
#include "executable.h"
-#include "externaltask.h"
#include "importlibrary.h"
#include "microsofttools.h"
#include "msvclinker.h"
using namespace Msp;
MsvcLinker::MsvcLinker(Builder &b, const Architecture &a, const MicrosoftTools &m):
- Tool(b, a, "LINK"),
+ Tool(b, &a, "LINK"),
ms_tools(m)
{
input_suffixes.push_back(".o");
processing_unit = COMPONENT;
set_command((ms_tools.get_vc_bin_dir()/"link.exe").str(), false);
+ set_run_external(_run);
}
-Target *MsvcLinker::create_target(const list<Target *> &sources, const string &arg)
+Target *MsvcLinker::create_target(const vector<Target *> &sources, const string &arg)
{
if(sources.empty())
throw invalid_argument("MsvcLinker::create_target");
- list<ObjectFile *> objs;
+ vector<ObjectFile *> objs;
+ objs.reserve(sources.size());
for(Target *s: sources)
- {
- if(ObjectFile *obj = dynamic_cast<ObjectFile *>(s))
- objs.push_back(obj);
- else
- throw invalid_argument("MsvcLinker::create_target");
- }
+ objs.push_back(&dynamic_cast<ObjectFile &>(*s));
const Component &comp = *objs.front()->get_component();
Binary *bin = 0;
return result;
}
-void MsvcLinker::do_prepare()
+void MsvcLinker::do_prepare(ToolData &tool) const
{
- string arch_dir = (architecture->get_bits()==64 ? "x64" : "x86");
+ const std::string &tool_tag = static_cast<Tool &>(tool).get_tag();
+ const Architecture &arch = *static_cast<Tool &>(tool).get_architecture();
+ string arch_dir = (arch.get_bits()==64 ? "x64" : "x86");
const FS::Path &vc_base_dir = ms_tools.get_vc_base_dir();
- system_path.push_back(vc_base_dir/"lib"/arch_dir);
+ tool.system_path.push_back(vc_base_dir/"lib"/arch_dir);
const FS::Path &win_sdk_dir = ms_tools.get_windows_sdk_dir();
const string &win_sdk_ver = ms_tools.get_windows_sdk_version();
- system_path.push_back(win_sdk_dir/"lib"/win_sdk_ver/"ucrt"/arch_dir);
- system_path.push_back(win_sdk_dir/"lib"/win_sdk_ver/"um"/arch_dir);
+ tool.system_path.push_back(win_sdk_dir/"lib"/win_sdk_ver/"ucrt"/arch_dir);
+ tool.system_path.push_back(win_sdk_dir/"lib"/win_sdk_ver/"um"/arch_dir);
string path;
- for(const FS::Path &p: system_path)
+ for(const FS::Path &p: tool.system_path)
{
append(path, ";", p.str());
- builder.get_logger().log("tools", format("Got %s system path: %s", tag, p));
+ builder.get_logger().log("tools", "Got %s system path: %s", tool_tag, p);
}
setenv("LIB", path);
}
-Task *MsvcLinker::run(const Target &target) const
+ExternalTask::Arguments MsvcLinker::_run(const Binary &bin, FS::Path &work_dir)
{
- const Binary &bin = dynamic_cast<const Binary &>(target);
+ const Tool &tool = *bin.get_tool();
vector<string> argv;
- 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();
-
if(dynamic_cast<const SharedLibrary *>(&bin))
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());*/
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();
argv.push_back("/SUBSYSTEM:CONSOLE");
- return new ExternalTask(argv, work_dir);
+ return argv;
}