diff options
| author | Ed Schouten <ed@FreeBSD.org> | 2009-07-04 13:58:54 +0000 |
|---|---|---|
| committer | Ed Schouten <ed@FreeBSD.org> | 2009-07-04 13:58:54 +0000 |
| commit | 5362a71c02e7d448a8ce98cf00c47e353fba5d04 (patch) | |
| tree | 8ddfe382e1c6d590dc240e76f7cd45cea5c78e24 /lib/Driver | |
| parent | 4ebdf5c4f587daef4e0be499802eac3a7a49bf2f (diff) | |
Notes
Diffstat (limited to 'lib/Driver')
| -rw-r--r-- | lib/Driver/ArgList.cpp | 29 | ||||
| -rw-r--r-- | lib/Driver/Compilation.cpp | 43 | ||||
| -rw-r--r-- | lib/Driver/Driver.cpp | 50 | ||||
| -rw-r--r-- | lib/Driver/HostInfo.cpp | 57 | ||||
| -rw-r--r-- | lib/Driver/Job.cpp | 6 | ||||
| -rw-r--r-- | lib/Driver/ToolChains.cpp | 30 | ||||
| -rw-r--r-- | lib/Driver/ToolChains.h | 7 | ||||
| -rw-r--r-- | lib/Driver/Tools.cpp | 148 | ||||
| -rw-r--r-- | lib/Driver/Tools.h | 34 |
9 files changed, 360 insertions, 44 deletions
diff --git a/lib/Driver/ArgList.cpp b/lib/Driver/ArgList.cpp index 593694cfbbf67..54dd4bb775382 100644 --- a/lib/Driver/ArgList.cpp +++ b/lib/Driver/ArgList.cpp @@ -49,6 +49,35 @@ Arg *ArgList::getLastArg(options::ID Id0, options::ID Id1, bool Claim) const { return Res; } +Arg *ArgList::getLastArg(options::ID Id0, options::ID Id1, options::ID Id2, + bool Claim) const { + Arg *Res = 0; + Arg *A0 = getLastArg(Id0, false); + Arg *A1 = getLastArg(Id1, false); + Arg *A2 = getLastArg(Id2, false); + + int A0Idx = A0 ? A0->getIndex() : -1; + int A1Idx = A1 ? A1->getIndex() : -1; + int A2Idx = A2 ? A2->getIndex() : -1; + + if (A0Idx > A1Idx) { + if (A0Idx > A2Idx) + Res = A0; + else if (A2Idx != -1) + Res = A2; + } else { + if (A1Idx > A2Idx) + Res = A1; + else if (A2Idx != -1) + Res = A2; + } + + if (Claim && Res) + Res->claim(); + + return Res; +} + bool ArgList::hasFlag(options::ID Pos, options::ID Neg, bool Default) const { if (Arg *A = getLastArg(Pos, Neg)) return A->getOption().matches(Pos); diff --git a/lib/Driver/Compilation.cpp b/lib/Driver/Compilation.cpp index 1e044c6b8fdc1..7e29b67769d34 100644 --- a/lib/Driver/Compilation.cpp +++ b/lib/Driver/Compilation.cpp @@ -21,8 +21,8 @@ #include <errno.h> using namespace clang::driver; -Compilation::Compilation(Driver &D, - ToolChain &_DefaultToolChain, +Compilation::Compilation(const Driver &D, + const ToolChain &_DefaultToolChain, InputArgList *_Args) : TheDriver(D), DefaultToolChain(_DefaultToolChain), Args(_Args) { } @@ -105,7 +105,8 @@ bool Compilation::CleanupFileList(const ArgStringList &Files, return Success; } -int Compilation::ExecuteCommand(const Command &C) const { +int Compilation::ExecuteCommand(const Command &C, + const Command *&FailingCommand) const { llvm::sys::Path Prog(C.getExecutable()); const char **Argv = new const char*[C.getArguments().size() + 2]; Argv[0] = C.getExecutable(); @@ -126,49 +127,31 @@ int Compilation::ExecuteCommand(const Command &C) const { getDriver().Diag(clang::diag::err_drv_command_failure) << Error; } + if (Res) + FailingCommand = &C; + delete[] Argv; return Res; } -int Compilation::ExecuteJob(const Job &J) const { +int Compilation::ExecuteJob(const Job &J, + const Command *&FailingCommand) const { if (const Command *C = dyn_cast<Command>(&J)) { - return ExecuteCommand(*C); + return ExecuteCommand(*C, FailingCommand); } else if (const PipedJob *PJ = dyn_cast<PipedJob>(&J)) { // Piped commands with a single job are easy. if (PJ->size() == 1) - return ExecuteCommand(**PJ->begin()); + return ExecuteCommand(**PJ->begin(), FailingCommand); + FailingCommand = *PJ->begin(); getDriver().Diag(clang::diag::err_drv_unsupported_opt) << "-pipe"; return 1; } else { const JobList *Jobs = cast<JobList>(&J); for (JobList::const_iterator it = Jobs->begin(), ie = Jobs->end(); it != ie; ++it) - if (int Res = ExecuteJob(**it)) + if (int Res = ExecuteJob(**it, FailingCommand)) return Res; return 0; } } - -int Compilation::Execute() const { - // Just print if -### was present. - if (getArgs().hasArg(options::OPT__HASH_HASH_HASH)) { - PrintJob(llvm::errs(), Jobs, "\n", true); - return 0; - } - - // If there were errors building the compilation, quit now. - if (getDriver().getDiags().getNumErrors()) - return 1; - - int Res = ExecuteJob(Jobs); - - // Remove temp files. - CleanupFileList(TempFiles); - - // If the compilation failed, remove result files as well. - if (Res != 0 && !getArgs().hasArg(options::OPT_save_temps)) - CleanupFileList(ResultFiles, true); - - return Res; -} diff --git a/lib/Driver/Driver.cpp b/lib/Driver/Driver.cpp index 8c2676b8cd7dd..1b0b5615dfbcb 100644 --- a/lib/Driver/Driver.cpp +++ b/lib/Driver/Driver.cpp @@ -217,6 +217,54 @@ Compilation *Driver::BuildCompilation(int argc, const char **argv) { return C; } +int Driver::ExecuteCompilation(const Compilation &C) const { + // Just print if -### was present. + if (C.getArgs().hasArg(options::OPT__HASH_HASH_HASH)) { + C.PrintJob(llvm::errs(), C.getJobs(), "\n", true); + return 0; + } + + // If there were errors building the compilation, quit now. + if (getDiags().getNumErrors()) + return 1; + + const Command *FailingCommand = 0; + int Res = C.ExecuteJob(C.getJobs(), FailingCommand); + + // Remove temp files. + C.CleanupFileList(C.getTempFiles()); + + // If the compilation failed, remove result files as well. + if (Res != 0 && !C.getArgs().hasArg(options::OPT_save_temps)) + C.CleanupFileList(C.getResultFiles(), true); + + // Print extra information about abnormal failures, if possible. + if (Res) { + // This is ad-hoc, but we don't want to be excessively noisy. If the result + // status was 1, assume the command failed normally. In particular, if it + // was the compiler then assume it gave a reasonable error code. Failures in + // other tools are less common, and they generally have worse diagnostics, + // so always print the diagnostic there. + const Action &Source = FailingCommand->getSource(); + bool IsFriendlyTool = (isa<PreprocessJobAction>(Source) || + isa<PrecompileJobAction>(Source) || + isa<AnalyzeJobAction>(Source) || + isa<CompileJobAction>(Source)); + + if (!IsFriendlyTool || Res != 1) { + // FIXME: See FIXME above regarding result code interpretation. + if (Res < 0) + Diag(clang::diag::err_drv_command_signalled) + << Source.getClassName() << -Res; + else + Diag(clang::diag::err_drv_command_failed) + << Source.getClassName() << Res; + } + } + + return Res; +} + void Driver::PrintOptions(const ArgList &Args) const { unsigned i = 0; for (ArgList::const_iterator it = Args.begin(), ie = Args.end(); @@ -1205,6 +1253,8 @@ const HostInfo *Driver::GetHostInfo(const char *TripleStr) const { return createDarwinHostInfo(*this, Triple); case llvm::Triple::DragonFly: return createDragonFlyHostInfo(*this, Triple); + case llvm::Triple::OpenBSD: + return createOpenBSDHostInfo(*this, Triple); case llvm::Triple::FreeBSD: return createFreeBSDHostInfo(*this, Triple); case llvm::Triple::Linux: diff --git a/lib/Driver/HostInfo.cpp b/lib/Driver/HostInfo.cpp index 831e11b98e42d..602a977135055 100644 --- a/lib/Driver/HostInfo.cpp +++ b/lib/Driver/HostInfo.cpp @@ -234,6 +234,57 @@ ToolChain *UnknownHostInfo::getToolChain(const ArgList &Args, return TC; } +// OpenBSD Host Info + +/// OpenBSDHostInfo - OpenBSD host information implementation. +class OpenBSDHostInfo : public HostInfo { + /// Cache of tool chains we have created. + mutable llvm::StringMap<ToolChain*> ToolChains; + +public: + OpenBSDHostInfo(const Driver &D, const llvm::Triple& Triple) + : HostInfo(D, Triple) {} + ~OpenBSDHostInfo(); + + virtual bool useDriverDriver() const; + + virtual types::ID lookupTypeForExtension(const char *Ext) const { + return types::lookupTypeForExtension(Ext); + } + + virtual ToolChain *getToolChain(const ArgList &Args, + const char *ArchName) const; +}; + +OpenBSDHostInfo::~OpenBSDHostInfo() { + for (llvm::StringMap<ToolChain*>::iterator + it = ToolChains.begin(), ie = ToolChains.end(); it != ie; ++it) + delete it->second; +} + +bool OpenBSDHostInfo::useDriverDriver() const { + return false; +} + +ToolChain *OpenBSDHostInfo::getToolChain(const ArgList &Args, + const char *ArchName) const { + assert(!ArchName && + "Unexpected arch name on platform without driver driver support."); + + std::string Arch = getArchName(); + ArchName = Arch.c_str(); + + ToolChain *&TC = ToolChains[ArchName]; + if (!TC) { + llvm::Triple TCTriple(getTriple()); + TCTriple.setArchName(ArchName); + + TC = new toolchains::OpenBSD(*this, TCTriple); + } + + return TC; +} + // FreeBSD Host Info /// FreeBSDHostInfo - FreeBSD host information implementation. @@ -417,6 +468,12 @@ clang::driver::createDarwinHostInfo(const Driver &D, } const HostInfo * +clang::driver::createOpenBSDHostInfo(const Driver &D, + const llvm::Triple& Triple) { + return new OpenBSDHostInfo(D, Triple); +} + +const HostInfo * clang::driver::createFreeBSDHostInfo(const Driver &D, const llvm::Triple& Triple) { return new FreeBSDHostInfo(D, Triple); diff --git a/lib/Driver/Job.cpp b/lib/Driver/Job.cpp index 222cf15db60f5..1b0ea18453d06 100644 --- a/lib/Driver/Job.cpp +++ b/lib/Driver/Job.cpp @@ -14,8 +14,10 @@ using namespace clang::driver; Job::~Job() {} -Command::Command(const char *_Executable, const ArgStringList &_Arguments) - : Job(CommandClass), Executable(_Executable), Arguments(_Arguments) { +Command::Command(const Action &_Source, const char *_Executable, + const ArgStringList &_Arguments) + : Job(CommandClass), Source(_Source), Executable(_Executable), + Arguments(_Arguments) { } PipedJob::PipedJob() : Job(PipedJobClass) {} diff --git a/lib/Driver/ToolChains.cpp b/lib/Driver/ToolChains.cpp index 436d343dd0211..f663ed49536e2 100644 --- a/lib/Driver/ToolChains.cpp +++ b/lib/Driver/ToolChains.cpp @@ -384,6 +384,36 @@ DerivedArgList *Generic_GCC::TranslateArgs(InputArgList &Args) const { return new DerivedArgList(Args, true); } +/// OpenBSD - OpenBSD tool chain which can call as(1) and ld(1) directly. + +OpenBSD::OpenBSD(const HostInfo &Host, const llvm::Triple& Triple) + : Generic_GCC(Host, Triple) { + getFilePaths().push_back(getHost().getDriver().Dir + "/../lib"); + getFilePaths().push_back("/usr/lib"); +} + +Tool &OpenBSD::SelectTool(const Compilation &C, const JobAction &JA) const { + Action::ActionClass Key; + if (getHost().getDriver().ShouldUseClangCompiler(C, JA, getArchName())) + Key = Action::AnalyzeJobClass; + else + Key = JA.getKind(); + + Tool *&T = Tools[Key]; + if (!T) { + switch (Key) { + case Action::AssembleJobClass: + T = new tools::openbsd::Assemble(*this); break; + case Action::LinkJobClass: + T = new tools::openbsd::Link(*this); break; + default: + T = &Generic_GCC::SelectTool(C, JA); + } + } + + return *T; +} + /// FreeBSD - FreeBSD tool chain which can call as(1) and ld(1) directly. FreeBSD::FreeBSD(const HostInfo &Host, const llvm::Triple& Triple, bool Lib32) diff --git a/lib/Driver/ToolChains.h b/lib/Driver/ToolChains.h index 3ecd1715da969..c921d52864f09 100644 --- a/lib/Driver/ToolChains.h +++ b/lib/Driver/ToolChains.h @@ -107,6 +107,13 @@ public: virtual const char *GetDefaultRelocationModel() const { return "pic"; } }; +class VISIBILITY_HIDDEN OpenBSD : public Generic_GCC { +public: + OpenBSD(const HostInfo &Host, const llvm::Triple& Triple); + + virtual Tool &SelectTool(const Compilation &C, const JobAction &JA) const; +}; + class VISIBILITY_HIDDEN FreeBSD : public Generic_GCC { public: FreeBSD(const HostInfo &Host, const llvm::Triple& Triple, bool Lib32); diff --git a/lib/Driver/Tools.cpp b/lib/Driver/Tools.cpp index bfc247a015ff3..d198a54cf7dd6 100644 --- a/lib/Driver/Tools.cpp +++ b/lib/Driver/Tools.cpp @@ -498,6 +498,18 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, Args.AddLastArg(CmdArgs, options::OPT_fvisibility_EQ); Args.AddLastArg(CmdArgs, options::OPT_fwritable_strings); + // Forward stack protector flags. + if (Arg *A = Args.getLastArg(options::OPT_fno_stack_protector, + options::OPT_fstack_protector_all, + options::OPT_fstack_protector)) { + if (A->getOption().matches(options::OPT_fno_stack_protector)) + CmdArgs.push_back("--stack-protector=0"); + else if (A->getOption().matches(options::OPT_fstack_protector)) + CmdArgs.push_back("--stack-protector=1"); + else + CmdArgs.push_back("--stack-protector=2"); + } + // Forward -f options with positive and negative forms; we translate // these by hand. @@ -616,7 +628,7 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "clang-cc").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); // Explicitly warn that these options are unsupported, even though // we are allowing compilation to continue. @@ -747,7 +759,7 @@ void gcc::Common::ConstructJob(Compilation &C, const JobAction &JA, getToolChain().getHost().getDriver().CCCGenericGCCName.c_str(); const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, GCCName).c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } void gcc::Preprocess::RenderExtraToolArgs(ArgStringList &CmdArgs) const { @@ -1123,7 +1135,7 @@ void darwin::Preprocess::ConstructJob(Compilation &C, const JobAction &JA, const char *CC1Name = getCC1Name(Inputs[0].getType()); const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, CC1Name).c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } void darwin::Compile::ConstructJob(Compilation &C, const JobAction &JA, @@ -1211,7 +1223,7 @@ void darwin::Compile::ConstructJob(Compilation &C, const JobAction &JA, const char *CC1Name = getCC1Name(Inputs[0].getType()); const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, CC1Name).c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } void darwin::Assemble::ConstructJob(Compilation &C, const JobAction &JA, @@ -1264,7 +1276,7 @@ void darwin::Assemble::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "as").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } /// Helper routine for seeing if we should use dsymutil; this is a @@ -1688,7 +1700,7 @@ void darwin::Link::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "ld").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); // Find the first non-empty base input (we want to ignore linker // inputs). @@ -1718,7 +1730,7 @@ void darwin::Link::ConstructJob(Compilation &C, const JobAction &JA, Args.MakeArgString(getToolChain().GetProgramPath(C, "dsymutil").c_str()); ArgStringList CmdArgs; CmdArgs.push_back(Output.getFilename()); - C.getJobs().addCommand(new Command(Exec, CmdArgs)); + C.getJobs().addCommand(new Command(JA, Exec, CmdArgs)); } } } @@ -1744,9 +1756,121 @@ void darwin::Lipo::ConstructJob(Compilation &C, const JobAction &JA, } const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "lipo").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); +} + +void openbsd::Assemble::ConstructJob(Compilation &C, const JobAction &JA, + Job &Dest, 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"); + 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(JA, Exec, CmdArgs)); } +void openbsd::Link::ConstructJob(Compilation &C, const JobAction &JA, + Job &Dest, const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &Args, + const char *LinkingOutput) const { + const Driver &D = getToolChain().getHost().getDriver(); + ArgStringList CmdArgs; + + if (Args.hasArg(options::OPT_static)) { + CmdArgs.push_back("-Bstatic"); + } else { + CmdArgs.push_back("--eh-frame-hdr"); + if (Args.hasArg(options::OPT_shared)) { + CmdArgs.push_back("-Bshareable"); + } else { + CmdArgs.push_back("-dynamic-linker"); + CmdArgs.push_back("/usr/libexec/ld.so"); + } + } + + 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, "crt0.o").c_str())); + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtbegin.o").c_str())); + } else { + 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; + + // Don't try to pass LLVM inputs to a generic gcc. + if (II.getType() == types::TY_LLVMBC) + D.Diag(clang::diag::err_drv_no_linker_llvm_support) + << getToolChain().getTripleString().c_str(); + + 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)) { + + if (Args.hasArg(options::OPT_pthread)) + CmdArgs.push_back("-pthread"); + 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(getToolChain().GetFilePath(C, "crtend.o").c_str())); + else + CmdArgs.push_back(Args.MakeArgString(getToolChain().GetFilePath(C, "crtendS.o").c_str())); + } + + const char *Exec = + Args.MakeArgString(getToolChain().GetProgramPath(C, "ld").c_str()); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); +} void freebsd::Assemble::ConstructJob(Compilation &C, const JobAction &JA, Job &Dest, const InputInfo &Output, @@ -1781,7 +1905,7 @@ void freebsd::Assemble::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "as").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } void freebsd::Link::ConstructJob(Compilation &C, const JobAction &JA, @@ -1892,7 +2016,7 @@ void freebsd::Link::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "ld").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } /// DragonFly Tools @@ -1931,7 +2055,7 @@ void dragonfly::Assemble::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "as").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } void dragonfly::Link::ConstructJob(Compilation &C, const JobAction &JA, @@ -2055,5 +2179,5 @@ void dragonfly::Link::ConstructJob(Compilation &C, const JobAction &JA, const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath(C, "ld").c_str()); - Dest.addCommand(new Command(Exec, CmdArgs)); + Dest.addCommand(new Command(JA, Exec, CmdArgs)); } diff --git a/lib/Driver/Tools.h b/lib/Driver/Tools.h index db108db2b4d7e..ab73496009078 100644 --- a/lib/Driver/Tools.h +++ b/lib/Driver/Tools.h @@ -241,6 +241,40 @@ namespace darwin { }; } + /// openbsd -- Directly call GNU Binutils assembler and linker +namespace openbsd { + class VISIBILITY_HIDDEN Assemble : public Tool { + public: + Assemble(const ToolChain &TC) : Tool("openbsd::Assemble", TC) {} + + virtual bool acceptsPipedInput() const { return true; } + virtual bool canPipeOutput() const { return true; } + virtual bool hasIntegratedCPP() const { return false; } + + virtual void ConstructJob(Compilation &C, const JobAction &JA, + Job &Dest, + const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &TCArgs, + const char *LinkingOutput) const; + }; + class VISIBILITY_HIDDEN Link : public Tool { + public: + Link(const ToolChain &TC) : Tool("openbsd::Link", TC) {} + + virtual bool acceptsPipedInput() const { return true; } + virtual bool canPipeOutput() const { return true; } + virtual bool hasIntegratedCPP() const { return false; } + + virtual void ConstructJob(Compilation &C, const JobAction &JA, + Job &Dest, + const InputInfo &Output, + const InputInfoList &Inputs, + const ArgList &TCArgs, + const char *LinkingOutput) const; + }; +} + /// freebsd -- Directly call GNU Binutils assembler and linker namespace freebsd { class VISIBILITY_HIDDEN Assemble : public Tool { |
