From: David Chisnall Date: Wed, 15 Feb 2012 13:39:01 +0000 (+0000) Subject: First pass at Solaris toolchain support. This version compiles and links hello X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=31c4690047f5f362ecf886f1586844b1aef0c4d2;p=clang First pass at Solaris toolchain support. This version compiles and links hello world on Solaris 11 for both x86 and x86-64 using the built-in assembler and Solaris (not GNU) ld, however it currently relies on a hard-coded GCC location to find crtbegin.o and crtend.o, as well as libgcc and libgcc_eh. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@150580 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Driver/Driver.cpp b/lib/Driver/Driver.cpp index b494ed1239..4209c9598e 100644 --- a/lib/Driver/Driver.cpp +++ b/lib/Driver/Driver.cpp @@ -1663,6 +1663,9 @@ const ToolChain &Driver::getToolChain(const ArgList &Args, else TC = new toolchains::Linux(*this, Target); break; + case llvm::Triple::Solaris: + TC = new toolchains::Solaris(*this, Target); + break; case llvm::Triple::Win32: TC = new toolchains::Windows(*this, Target); break; diff --git a/lib/Driver/ToolChains.cpp b/lib/Driver/ToolChains.cpp index 703c7aa3d5..2a5bdbc553 100644 --- a/lib/Driver/ToolChains.cpp +++ b/lib/Driver/ToolChains.cpp @@ -1755,6 +1755,41 @@ Tool &AuroraUX::SelectTool(const Compilation &C, const JobAction &JA, return *T; } +/// Solaris - Solaris tool chain which can call as(1) and ld(1) directly. + +Solaris::Solaris(const Driver &D, const llvm::Triple& Triple) + : Generic_GCC(D, Triple) { + + getProgramPaths().push_back(getDriver().getInstalledDir()); + if (getDriver().getInstalledDir() != getDriver().Dir) + getProgramPaths().push_back(getDriver().Dir); + + getFilePaths().push_back(getDriver().Dir + "/../lib"); + getFilePaths().push_back("/usr/lib"); +} + +Tool &Solaris::SelectTool(const Compilation &C, const JobAction &JA, + const ActionList &Inputs) const { + Action::ActionClass Key; + if (getDriver().ShouldUseClangCompiler(C, JA, getTriple())) + Key = Action::AnalyzeJobClass; + else + Key = JA.getKind(); + + Tool *&T = Tools[Key]; + if (!T) { + switch (Key) { + case Action::AssembleJobClass: + T = new tools::solaris::Assemble(*this); break; + case Action::LinkJobClass: + T = new tools::solaris::Link(*this); break; + default: + T = &Generic_GCC::SelectTool(C, JA, Inputs); + } + } + + return *T; +} /// Linux toolchain (very bare-bones at the moment). diff --git a/lib/Driver/ToolChains.h b/lib/Driver/ToolChains.h index c454db553b..605fefb0c8 100644 --- a/lib/Driver/ToolChains.h +++ b/lib/Driver/ToolChains.h @@ -449,6 +449,17 @@ public: const ActionList &Inputs) const; }; +class LLVM_LIBRARY_VISIBILITY Solaris : public Generic_GCC { +public: + Solaris(const Driver &D, const llvm::Triple& Triple); + + virtual Tool &SelectTool(const Compilation &C, const JobAction &JA, + const ActionList &Inputs) const; + + virtual bool IsIntegratedAssemblerDefault() const { return true; } +}; + + class LLVM_LIBRARY_VISIBILITY OpenBSD : public Generic_ELF { public: OpenBSD(const Driver &D, const llvm::Triple& Triple); diff --git a/lib/Driver/Tools.cpp b/lib/Driver/Tools.cpp index c963654de5..629ba07b1d 100644 --- a/lib/Driver/Tools.cpp +++ b/lib/Driver/Tools.cpp @@ -4170,6 +4170,126 @@ void darwin::VerifyDebug::ConstructJob(Compilation &C, const JobAction &JA, C.addCommand(new Command(JA, *this, Exec, CmdArgs)); } +void solaris::Assemble::ConstructJob(Compilation &C, const JobAction &JA, + const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &Args, + const char *LinkingOutput) const { + ArgStringList CmdArgs; + + Args.AddAllArgValues(CmdArgs, options::OPT_Wa_COMMA, + options::OPT_Xassembler); + + CmdArgs.push_back("-o"); + CmdArgs.push_back(Output.getFilename()); + + for (InputInfoList::const_iterator + it = Inputs.begin(), ie = Inputs.end(); it != ie; ++it) { + const InputInfo &II = *it; + CmdArgs.push_back(II.getFilename()); + } + + const char *Exec = + Args.MakeArgString(getToolChain().GetProgramPath("as")); + C.addCommand(new Command(JA, *this, Exec, CmdArgs)); +} + + +void solaris::Link::ConstructJob(Compilation &C, const JobAction &JA, + const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &Args, + const char *LinkingOutput) const { + // FIXME: Find a real GCC, don't hard-code versions here + std::string GCCLibPath = "/usr/gcc/4.5/lib/gcc/"; + const llvm::Triple &T = getToolChain().getTriple(); + std::string LibPath = "/usr/lib/"; + llvm::Triple::ArchType Arch = T.getArch(); + switch (Arch) { + case llvm::Triple::x86: + GCCLibPath += ("i386-" + T.getVendorName() + "-" + + T.getOSName()).str() + "/4.5.2/"; + break; + case llvm::Triple::x86_64: + GCCLibPath += ("i386-" + T.getVendorName() + "-" + + T.getOSName()).str(); + GCCLibPath += "/4.5.2/amd64/"; + LibPath += "amd64/"; + break; + default: + assert(0 && "Unsupported architecture"); + } + + ArgStringList CmdArgs; + + if ((!Args.hasArg(options::OPT_nostdlib)) && + (!Args.hasArg(options::OPT_shared))) { + CmdArgs.push_back("-e"); + CmdArgs.push_back("_start"); + } + + if (Args.hasArg(options::OPT_static)) { + CmdArgs.push_back("-Bstatic"); + CmdArgs.push_back("-dn"); + } else { + CmdArgs.push_back("-Bdynamic"); + if (Args.hasArg(options::OPT_shared)) { + CmdArgs.push_back("-shared"); + } else { + CmdArgs.push_back("--dynamic-linker"); + CmdArgs.push_back(Args.MakeArgString(LibPath + "ld.so.1")); + } + } + + 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(LibPath + "crt1.o")); + CmdArgs.push_back(Args.MakeArgString(LibPath + "crti.o")); + CmdArgs.push_back(Args.MakeArgString(GCCLibPath + "crtbegin.o")); + } else { + CmdArgs.push_back(Args.MakeArgString(LibPath + "crti.o")); + } + CmdArgs.push_back(Args.MakeArgString(LibPath + "crtn.o")); + } + + CmdArgs.push_back(Args.MakeArgString("-L" + GCCLibPath)); + + Args.AddAllArgs(CmdArgs, options::OPT_L); + Args.AddAllArgs(CmdArgs, options::OPT_T_Group); + Args.AddAllArgs(CmdArgs, options::OPT_e); + + AddLinkerInputs(getToolChain(), Inputs, Args, CmdArgs); + + if (!Args.hasArg(options::OPT_nostdlib) && + !Args.hasArg(options::OPT_nodefaultlibs)) { + CmdArgs.push_back("-lgcc"); + CmdArgs.push_back("-lgcc_eh"); + if (!Args.hasArg(options::OPT_shared)) + CmdArgs.push_back("-lc"); + + } + + if (!Args.hasArg(options::OPT_nostdlib) && + !Args.hasArg(options::OPT_nostartfiles)) { + if (!Args.hasArg(options::OPT_shared)) + CmdArgs.push_back(Args.MakeArgString(GCCLibPath + "crtend.o")); + } + + addProfileRT(getToolChain(), Args, CmdArgs, getToolChain().getTriple()); + + const char *Exec = + Args.MakeArgString(getToolChain().GetProgramPath("ld")); + C.addCommand(new Command(JA, *this, Exec, CmdArgs)); +} + void auroraux::Assemble::ConstructJob(Compilation &C, const JobAction &JA, const InputInfo &Output, const InputInfoList &Inputs, diff --git a/lib/Driver/Tools.h b/lib/Driver/Tools.h index e607acb685..c810bf34bf 100644 --- a/lib/Driver/Tools.h +++ b/lib/Driver/Tools.h @@ -483,6 +483,35 @@ namespace minix { }; } // end namespace minix + /// solaris -- Directly call Solaris assembler and linker +namespace solaris { + class LLVM_LIBRARY_VISIBILITY Assemble : public Tool { + public: + Assemble(const ToolChain &TC) : Tool("solaris::Assemble", "assembler", + TC) {} + + virtual bool hasIntegratedCPP() const { return false; } + + virtual void ConstructJob(Compilation &C, const JobAction &JA, + const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &TCArgs, + const char *LinkingOutput) const; + }; + class LLVM_LIBRARY_VISIBILITY Link : public Tool { + public: + Link(const ToolChain &TC) : Tool("solaris::Link", "linker", TC) {} + + virtual bool hasIntegratedCPP() const { return false; } + + virtual void ConstructJob(Compilation &C, const JobAction &JA, + const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &TCArgs, + const char *LinkingOutput) const; + }; +} // end namespace auroraux + /// auroraux -- Directly call GNU Binutils assembler and linker namespace auroraux { class LLVM_LIBRARY_VISIBILITY Assemble : public Tool {