Skip to content

Commit

Permalink
Support separate linking with ldc2
Browse files Browse the repository at this point in the history
This is basically #1548 with an augmented set of compiler flags being
included in the linking command lines.
  • Loading branch information
kinke committed Aug 17, 2019
1 parent 4cc1733 commit c8fe948
Show file tree
Hide file tree
Showing 2 changed files with 36 additions and 7 deletions.
35 changes: 34 additions & 1 deletion source/dub/compilers/ldc.d
Original file line number Diff line number Diff line change
Expand Up @@ -232,7 +232,20 @@ config /etc/ldc2.conf (x86_64-pc-linux-gnu)

void invokeLinker(in BuildSettings settings, in BuildPlatform platform, string[] objects, void delegate(int, string) output_callback)
{
assert(false, "Separate linking not implemented for LDC");
import std.string;
auto tpath = NativePath(settings.targetPath) ~ getTargetFileName(settings, platform);
auto args = ["-of"~tpath.toNativeString()];
args ~= objects;
args ~= settings.sourceFiles;
version(linux) args ~= "-L--no-as-needed"; // avoids linker errors due to libraries being specified in the wrong order
args ~= lflagsToDFlags(settings.lflags);
args ~= settings.dflags.filter!(f => isLinkerDFlag(f)).array;

auto res_file = getTempFile("dub-build", ".lnk");
std.file.write(res_file.toNativeString(), escapeArgs(args).join("\n"));

logDiagnostic("%s %s", platform.compilerBinary, escapeArgs(args).join(" "));
invokeTool([platform.compilerBinary, "@"~res_file.toNativeString()], output_callback);
}

string[] lflagsToDFlags(in string[] lflags) const
Expand All @@ -245,6 +258,26 @@ config /etc/ldc2.conf (x86_64-pc-linux-gnu)
return args.map!(s => s.canFind(' ') ? "\""~s~"\"" : s);
}

private static bool isLinkerDFlag(string arg)
{
switch (arg) {
case "-g", "-gc", "-m32", "-m64", "-shared", "-lib",
"-disable-linker-strip-dead", "-static":
return true;
default:
return arg.startsWith("-L")
|| arg.startsWith("-Xcc=")
|| arg.startsWith("-defaultlib=")
|| arg.startsWith("-flto")
|| arg.startsWith("-fsanitize=")
|| arg.startsWith("-link-")
|| arg.startsWith("-linker=")
|| arg.startsWith("-march=")
|| arg.startsWith("-mscrtlib=")
|| arg.startsWith("-mtriple=");
}
}

private static bool generatesCOFF(in BuildPlatform platform)
{
import std.string : splitLines, strip;
Expand Down
8 changes: 2 additions & 6 deletions source/dub/generators/build.d
Original file line number Diff line number Diff line change
Expand Up @@ -476,12 +476,8 @@ class BuildGenerator : ProjectGenerator {
settings.compiler.prepareBuildSettings(lbuildsettings, BuildSetting.commandLineSeparate|BuildSetting.sourceFiles);
settings.compiler.invokeLinker(lbuildsettings, settings.platform, objs, settings.linkCallback);

/*
NOTE: for DMD experimental separate compile/link is used, but this is not yet implemented
on the other compilers. Later this should be integrated somehow in the build process
(either in the dub.json, or using a command line flag)
*/
} else if (generate_binary && (settings.buildMode == BuildMode.allAtOnce || settings.compiler.name != "dmd" || is_static_library)) {
// NOTE: separate compile/link is not yet enabled for GDC.
} else if (generate_binary && (settings.buildMode == BuildMode.allAtOnce || settings.compiler.name == "gdc" || is_static_library)) {
// don't include symbols of dependencies (will be included by the top level target)
if (is_static_library) buildsettings.sourceFiles = buildsettings.sourceFiles.filter!(f => !f.isLinkerFile()).array;

Expand Down

0 comments on commit c8fe948

Please sign in to comment.