1 //===--- Ananas.cpp - Ananas ToolChain Implementations ------*- C++ -*-===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
10 #include "CommonArgs.h"
11 #include "clang/Driver/Compilation.h"
12 #include "clang/Driver/Driver.h"
13 #include "clang/Driver/InputInfo.h"
14 #include "clang/Driver/Options.h"
15 #include "llvm/ADT/SmallString.h"
16 #include "llvm/Option/ArgList.h"
17 #include "llvm/Support/Path.h"
19 using namespace clang::driver
;
20 using namespace clang::driver::tools
;
21 using namespace clang::driver::toolchains
;
22 using namespace clang
;
23 using namespace llvm::opt
;
25 void ananas::Assembler::ConstructJob(Compilation
&C
, const JobAction
&JA
,
26 const InputInfo
&Output
,
27 const InputInfoList
&Inputs
,
29 const char *LinkingOutput
) const {
30 claimNoWarnArgs(Args
);
31 ArgStringList CmdArgs
;
33 Args
.AddAllArgValues(CmdArgs
, options::OPT_Wa_COMMA
, options::OPT_Xassembler
);
35 CmdArgs
.push_back("-o");
36 CmdArgs
.push_back(Output
.getFilename());
38 for (const auto &II
: Inputs
)
39 CmdArgs
.push_back(II
.getFilename());
41 const char *Exec
= Args
.MakeArgString(getToolChain().GetProgramPath("as"));
42 C
.addCommand(std::make_unique
<Command
>(JA
, *this,
43 ResponseFileSupport::AtFileCurCP(),
44 Exec
, CmdArgs
, Inputs
, Output
));
47 void ananas::Linker::ConstructJob(Compilation
&C
, const JobAction
&JA
,
48 const InputInfo
&Output
,
49 const InputInfoList
&Inputs
,
51 const char *LinkingOutput
) const {
52 const ToolChain
&ToolChain
= getToolChain();
53 const Driver
&D
= ToolChain
.getDriver();
54 ArgStringList CmdArgs
;
56 // Silence warning for "clang -g foo.o -o foo"
57 Args
.ClaimAllArgs(options::OPT_g_Group
);
58 // and "clang -emit-llvm foo.o -o foo"
59 Args
.ClaimAllArgs(options::OPT_emit_llvm
);
60 // and for "clang -w foo.o -o foo". Other warning options are already
61 // handled somewhere else.
62 Args
.ClaimAllArgs(options::OPT_w
);
64 if (!D
.SysRoot
.empty())
65 CmdArgs
.push_back(Args
.MakeArgString("--sysroot=" + D
.SysRoot
));
67 if (Args
.hasArg(options::OPT_static
)) {
68 CmdArgs
.push_back("-Bstatic");
70 if (Args
.hasArg(options::OPT_rdynamic
))
71 CmdArgs
.push_back("-export-dynamic");
72 if (Args
.hasArg(options::OPT_shared
)) {
73 CmdArgs
.push_back("-Bshareable");
74 } else if (!Args
.hasArg(options::OPT_r
)) {
75 Args
.AddAllArgs(CmdArgs
, options::OPT_pie
);
76 CmdArgs
.push_back("-dynamic-linker");
77 CmdArgs
.push_back("/lib/ld-ananas.so");
81 if (Output
.isFilename()) {
82 CmdArgs
.push_back("-o");
83 CmdArgs
.push_back(Output
.getFilename());
85 assert(Output
.isNothing() && "Invalid output.");
88 if (!Args
.hasArg(options::OPT_nostdlib
, options::OPT_nostartfiles
,
90 if (!Args
.hasArg(options::OPT_shared
)) {
91 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crt0.o")));
93 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crti.o")));
94 if (Args
.hasArg(options::OPT_shared
) || Args
.hasArg(options::OPT_pie
)) {
95 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crtbeginS.o")));
97 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crtbegin.o")));
101 Args
.AddAllArgs(CmdArgs
, options::OPT_L
);
102 ToolChain
.AddFilePathLibArgs(Args
, CmdArgs
);
103 Args
.AddAllArgs(CmdArgs
,
104 {options::OPT_T_Group
, options::OPT_e
, options::OPT_s
,
105 options::OPT_t
, options::OPT_Z_Flag
, options::OPT_r
});
107 if (D
.isUsingLTO()) {
108 assert(!Inputs
.empty() && "Must have at least one input.");
109 addLTOOptions(ToolChain
, Args
, CmdArgs
, Output
, Inputs
[0],
110 D
.getLTOMode() == LTOK_Thin
);
113 AddLinkerInputs(ToolChain
, Inputs
, Args
, CmdArgs
, JA
);
115 if (!Args
.hasArg(options::OPT_nostdlib
, options::OPT_nodefaultlibs
,
117 if (ToolChain
.ShouldLinkCXXStdlib(Args
))
118 ToolChain
.AddCXXStdlibLibArgs(Args
, CmdArgs
);
119 CmdArgs
.push_back("-lc");
122 if (!Args
.hasArg(options::OPT_nostdlib
, options::OPT_nostartfiles
,
124 if (Args
.hasArg(options::OPT_shared
) || Args
.hasArg(options::OPT_pie
))
125 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crtendS.o")));
127 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crtend.o")));
128 CmdArgs
.push_back(Args
.MakeArgString(ToolChain
.GetFilePath("crtn.o")));
131 const char *Exec
= Args
.MakeArgString(ToolChain
.GetLinkerPath());
132 C
.addCommand(std::make_unique
<Command
>(JA
, *this,
133 ResponseFileSupport::AtFileCurCP(),
134 Exec
, CmdArgs
, Inputs
, Output
));
137 // Ananas - Ananas tool chain which can call as(1) and ld(1) directly.
139 Ananas::Ananas(const Driver
&D
, const llvm::Triple
&Triple
, const ArgList
&Args
)
140 : Generic_ELF(D
, Triple
, Args
) {
141 getFilePaths().push_back(getDriver().SysRoot
+ "/usr/lib");
144 Tool
*Ananas::buildAssembler() const {
145 return new tools::ananas::Assembler(*this);
148 Tool
*Ananas::buildLinker() const { return new tools::ananas::Linker(*this); }