diff options
Diffstat (limited to 'lib/Driver/Tools.cpp')
-rw-r--r-- | lib/Driver/Tools.cpp | 156 |
1 files changed, 156 insertions, 0 deletions
diff --git a/lib/Driver/Tools.cpp b/lib/Driver/Tools.cpp index 83100248db..c8622284fc 100644 --- a/lib/Driver/Tools.cpp +++ b/lib/Driver/Tools.cpp @@ -1826,3 +1826,159 @@ void freebsd::Link::ConstructJob(Compilation &C, const JobAction &JA, Args.MakeArgString(getToolChain().GetProgramPath(C, "ld").c_str()); Dest.addCommand(new Command(Exec, CmdArgs)); } + +/// DragonFly Tools + +// For now, DragonFly Assemble does just about the same as for +// FreeBSD, but this may change soon. +void dragonfly::Assemble::ConstructJob(Compilation &C, const JobAction &JA, + Job &Dest, const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &Args, + const char *LinkingOutput) const { + ArgStringList CmdArgs; + + // When building 32-bit code on DragonFly/pc64, we have to explicitly + // instruct as in the base system to assemble 32-bit code. + if (getToolChain().getArchName() == "i386") + CmdArgs.push_back("--32"); + + Args.AddAllArgValues(CmdArgs, options::OPT_Wa_COMMA, + options::OPT_Xassembler); + + CmdArgs.push_back("-o"); + if (Output.isPipe()) + CmdArgs.push_back("-"); + else + CmdArgs.push_back(Output.getFilename()); + + for (InputInfoList::const_iterator + it = Inputs.begin(), ie = Inputs.end(); it != ie; ++it) { + const InputInfo &II = *it; + if (II.isPipe()) + CmdArgs.push_back("-"); + else + CmdArgs.push_back(II.getFilename()); + } + + const char *Exec = + Args.MakeArgString(getToolChain().GetProgramPath(C, "as").c_str()); + Dest.addCommand(new Command(Exec, CmdArgs)); +} + +void dragonfly::Link::ConstructJob(Compilation &C, const JobAction &JA, + Job &Dest, const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &Args, + const char *LinkingOutput) const { + ArgStringList CmdArgs; + + if (Args.hasArg(options::OPT_static)) { + CmdArgs.push_back("-Bstatic"); + } else { + if (Args.hasArg(options::OPT_shared)) + CmdArgs.push_back("-Bshareable"); + else { + CmdArgs.push_back("-dynamic-linker"); + CmdArgs.push_back("/usr/libexec/ld-elf.so.2"); + } + } + + // When building 32-bit code on DragonFly/pc64, we have to explicitly + // instruct ld in the base system to link 32-bit code. + if (getToolChain().getArchName() == "i386") { + CmdArgs.push_back("-m"); + CmdArgs.push_back("elf_i386"); + } + + if (Output.isPipe()) { + CmdArgs.push_back("-o"); + CmdArgs.push_back("-"); + } else if (Output.isFilename()) { + CmdArgs.push_back("-o"); + CmdArgs.push_back(Output.getFilename()); + } else { + assert(Output.isNothing() && "Invalid output."); + } + + if (!Args.hasArg(options::OPT_nostdlib) && + !Args.hasArg(options::OPT_nostartfiles)) { + if (!Args.hasArg(options::OPT_shared)) { + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crt1.o").c_str())); + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crti.o").c_str())); + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtbegin.o").c_str())); + } else { + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crti.o").c_str())); + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtbeginS.o").c_str())); + } + } + + Args.AddAllArgs(CmdArgs, options::OPT_L); + Args.AddAllArgs(CmdArgs, options::OPT_T_Group); + Args.AddAllArgs(CmdArgs, options::OPT_e); + + for (InputInfoList::const_iterator + it = Inputs.begin(), ie = Inputs.end(); it != ie; ++it) { + const InputInfo &II = *it; + if (II.isPipe()) + CmdArgs.push_back("-"); + else if (II.isFilename()) + CmdArgs.push_back(II.getFilename()); + else + II.getInputArg().renderAsInput(Args, CmdArgs); + } + + if (!Args.hasArg(options::OPT_nostdlib) && + !Args.hasArg(options::OPT_nodefaultlibs)) { + // FIXME: GCC passes on -lgcc, -lgcc_pic and a whole lot of + // rpaths + CmdArgs.push_back("-L/usr/lib/gcc41"); + + if (!Args.hasArg(options::OPT_static)) { + CmdArgs.push_back("-rpath"); + CmdArgs.push_back("/usr/lib/gcc41"); + + CmdArgs.push_back("-rpath-link"); + CmdArgs.push_back("/usr/lib/gcc41"); + + CmdArgs.push_back("-rpath"); + CmdArgs.push_back("/usr/lib"); + + CmdArgs.push_back("-rpath-link"); + CmdArgs.push_back("/usr/lib"); + } + + if (Args.hasArg(options::OPT_shared)) { + CmdArgs.push_back("-lgcc_pic"); + } else { + CmdArgs.push_back("-lgcc"); + } + + + if (Args.hasArg(options::OPT_pthread)) + CmdArgs.push_back("-lthread_xu"); + + if (!Args.hasArg(options::OPT_nolibc)) { + CmdArgs.push_back("-lc"); + } + + if (Args.hasArg(options::OPT_shared)) { + CmdArgs.push_back("-lgcc_pic"); + } else { + CmdArgs.push_back("-lgcc"); + } + } + + if (!Args.hasArg(options::OPT_nostdlib) && + !Args.hasArg(options::OPT_nostartfiles)) { + if (!Args.hasArg(options::OPT_shared)) + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtend.o").c_str())); + else + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtendS.o").c_str())); + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtn.o").c_str())); + } + + const char *Exec = + Args.MakeArgString(getToolChain().GetProgramPath(C, "ld").c_str()); + Dest.addCommand(new Command(Exec, CmdArgs)); +} |