12 #include "clang/Config/config.h" 17 #include "llvm/Support/FileSystem.h" 18 #include "llvm/Support/Path.h" 19 #include "llvm/Option/ArgList.h" 24 using namespace clang;
30 const llvm::Triple &TargetTriple,
32 return (TargetTriple.getArchName() +
"-" +
33 TargetTriple.getOSAndEnvironmentName()).str();
38 if (
const Arg* A = Args.getLastArg(options::OPT_fuse_ld_EQ)) {
39 StringRef UseLinker = A->getValue();
40 if (!UseLinker.empty()) {
41 if (llvm::sys::path::is_absolute(UseLinker) &&
42 llvm::sys::fs::can_execute(UseLinker))
46 if (UseLinker !=
"lld" && UseLinker !=
"ld")
48 << A->getAsString(Args);
59 const char *LinkingOutput)
const {
62 const char *
Linker = Args.MakeArgString(getLinkerPath(Args));
63 ArgStringList CmdArgs;
65 if (Args.hasArg(options::OPT_s))
66 CmdArgs.push_back(
"--strip-all");
68 Args.AddAllArgs(CmdArgs, options::OPT_L);
69 Args.AddAllArgs(CmdArgs, options::OPT_u);
72 if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles))
73 CmdArgs.push_back(Args.MakeArgString(ToolChain.
GetFilePath(
"crt1.o")));
77 if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nodefaultlibs)) {
81 if (Args.hasArg(options::OPT_pthread)) {
82 CmdArgs.push_back(
"-lpthread");
83 CmdArgs.push_back(
"--shared-memory");
86 CmdArgs.push_back(
"-lc");
90 CmdArgs.push_back(
"-o");
93 C.
addCommand(std::make_unique<Command>(JA, *
this, Linker, CmdArgs, Inputs));
96 if (Arg *A = Args.getLastArg(options::OPT_O_Group)) {
97 auto WasmOptPath = getToolChain().GetProgramPath(
"wasm-opt");
98 if (WasmOptPath !=
"wasm-opt") {
100 if (A->getOption().matches(options::OPT_O4) ||
101 A->getOption().matches(options::OPT_Ofast))
103 else if (A->getOption().matches(options::OPT_O0))
105 else if (A->getOption().matches(options::OPT_O))
106 OOpt = A->getValue();
109 const char *WasmOpt = Args.MakeArgString(WasmOptPath);
110 ArgStringList CmdArgs;
112 CmdArgs.push_back(Args.MakeArgString(llvm::Twine(
"-O") + OOpt));
113 CmdArgs.push_back(
"-o");
115 C.
addCommand(std::make_unique<Command>(JA, *
this, WasmOpt, CmdArgs, Inputs));
126 return Dir +
"/llvm-lto/" LLVM_VERSION_STRING;
129 WebAssembly::WebAssembly(
const Driver &D,
const llvm::Triple &Triple,
130 const llvm::opt::ArgList &Args)
133 assert(Triple.isArch32Bit() != Triple.isArch64Bit());
135 getProgramPaths().push_back(getDriver().getInstalledDir());
137 auto SysRoot = getDriver().SysRoot;
138 if (getTriple().getOS() == llvm::Triple::UnknownOS) {
143 getFilePaths().push_back(SysRoot +
"/lib");
145 const std::string MultiarchTriple =
152 getFilePaths().push_back(Dir);
154 getFilePaths().push_back(SysRoot +
"/lib/" + MultiarchTriple);
158 bool WebAssembly::IsMathErrnoDefault()
const {
return false; }
160 bool WebAssembly::IsObjCNonFragileABIDefault()
const {
return true; }
162 bool WebAssembly::UseObjCMixedDispatch()
const {
return true; }
164 bool WebAssembly::isPICDefault()
const {
return false; }
166 bool WebAssembly::isPIEDefault()
const {
return false; }
168 bool WebAssembly::isPICDefaultForced()
const {
return false; }
170 bool WebAssembly::IsIntegratedAssemblerDefault()
const {
return true; }
172 bool WebAssembly::hasBlocksRuntime()
const {
return false; }
175 bool WebAssembly::SupportsProfiling()
const {
return false; }
177 bool WebAssembly::HasNativeLLVMSupport()
const {
return true; }
179 void WebAssembly::addClangTargetOptions(
const ArgList &DriverArgs,
180 ArgStringList &CC1Args,
182 if (!DriverArgs.hasFlag(clang::driver::options::OPT_fuse_init_array,
183 options::OPT_fno_use_init_array,
true))
184 CC1Args.push_back(
"-fno-use-init-array");
187 if (DriverArgs.hasFlag(options::OPT_pthread, options::OPT_no_pthread,
189 if (DriverArgs.hasFlag(options::OPT_mno_atomics, options::OPT_matomics,
191 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
194 if (DriverArgs.hasFlag(options::OPT_mno_bulk_memory,
195 options::OPT_mbulk_memory,
false))
196 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
198 <<
"-mno-bulk-memory";
199 if (DriverArgs.hasFlag(options::OPT_mno_mutable_globals,
200 options::OPT_mmutable_globals,
false))
201 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
203 <<
"-mno-mutable-globals";
204 if (DriverArgs.hasFlag(options::OPT_mno_sign_ext, options::OPT_msign_ext,
206 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
209 CC1Args.push_back(
"-target-feature");
210 CC1Args.push_back(
"+atomics");
211 CC1Args.push_back(
"-target-feature");
212 CC1Args.push_back(
"+bulk-memory");
213 CC1Args.push_back(
"-target-feature");
214 CC1Args.push_back(
"+mutable-globals");
215 CC1Args.push_back(
"-target-feature");
216 CC1Args.push_back(
"+sign-ext");
219 if (DriverArgs.getLastArg(options::OPT_fwasm_exceptions)) {
221 if (DriverArgs.hasFlag(options::OPT_mno_exception_handing,
222 options::OPT_mexception_handing,
false))
223 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
224 <<
"-fwasm-exceptions" 225 <<
"-mno-exception-handling";
227 if (DriverArgs.hasFlag(options::OPT_mno_reference_types,
228 options::OPT_mexception_handing,
false))
229 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
230 <<
"-fwasm-exceptions" 231 <<
"-mno-reference-types";
234 for (
const Arg *A : DriverArgs.filtered(options::OPT_mllvm)) {
235 if (StringRef(A->getValue(0)) ==
"-enable-emscripten-cxx-exceptions")
236 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
237 <<
"-fwasm-exceptions" 238 <<
"-mllvm -enable-emscripten-cxx-exceptions";
241 CC1Args.push_back(
"-target-feature");
242 CC1Args.push_back(
"+exception-handling");
243 CC1Args.push_back(
"-target-feature");
244 CC1Args.push_back(
"+reference-types");
253 WebAssembly::GetCXXStdlibType(
const ArgList &Args)
const {
254 if (Arg *A = Args.getLastArg(options::OPT_stdlib_EQ)) {
255 StringRef
Value = A->getValue();
256 if (Value !=
"libc++")
257 getDriver().Diag(diag::err_drv_invalid_stdlib_name)
258 << A->getAsString(Args);
263 void WebAssembly::AddClangSystemIncludeArgs(
const ArgList &DriverArgs,
264 ArgStringList &CC1Args)
const {
265 if (DriverArgs.hasArg(clang::driver::options::OPT_nostdinc))
268 const Driver &D = getDriver();
270 if (!DriverArgs.hasArg(options::OPT_nobuiltininc)) {
272 llvm::sys::path::append(P,
"include");
273 addSystemInclude(DriverArgs, CC1Args, P);
276 if (DriverArgs.hasArg(options::OPT_nostdlibinc))
280 StringRef CIncludeDirs(C_INCLUDE_DIRS);
281 if (CIncludeDirs !=
"") {
283 CIncludeDirs.split(dirs,
":");
284 for (StringRef dir : dirs) {
286 llvm::sys::path::is_absolute(dir) ? StringRef(D.
SysRoot) :
"";
287 addExternCSystemInclude(DriverArgs, CC1Args, Prefix + dir);
292 if (getTriple().getOS() != llvm::Triple::UnknownOS) {
293 const std::string MultiarchTriple =
295 addSystemInclude(DriverArgs, CC1Args, D.
SysRoot +
"/include/" + MultiarchTriple);
297 addSystemInclude(DriverArgs, CC1Args, D.
SysRoot +
"/include");
300 void WebAssembly::AddClangCXXStdlibIncludeArgs(
const ArgList &DriverArgs,
301 ArgStringList &CC1Args)
const {
302 if (!DriverArgs.hasArg(options::OPT_nostdlibinc) &&
303 !DriverArgs.hasArg(options::OPT_nostdincxx)) {
304 if (getTriple().getOS() != llvm::Triple::UnknownOS) {
305 const std::string MultiarchTriple =
307 addSystemInclude(DriverArgs, CC1Args,
308 getDriver().SysRoot +
"/include/" + MultiarchTriple +
311 addSystemInclude(DriverArgs, CC1Args,
312 getDriver().SysRoot +
"/include/c++/v1");
316 void WebAssembly::AddCXXStdlibLibArgs(
const llvm::opt::ArgList &Args,
317 llvm::opt::ArgStringList &CmdArgs)
const {
319 switch (GetCXXStdlibType(Args)) {
321 CmdArgs.push_back(
"-lc++");
322 CmdArgs.push_back(
"-lc++abi");
325 llvm_unreachable(
"invalid stdlib name");
331 if (getTriple().isOSEmscripten()) {
332 Res |= SanitizerKind::Vptr | SanitizerKind::Leak | SanitizerKind::Address;
337 Tool *WebAssembly::buildLinker()
const {
bool isUsingLTO() const
Returns true if we are performing any kind of LTO.
DiagnosticBuilder Diag(unsigned DiagID) const
Driver - Encapsulate logic for constructing compilation processes from a set of gcc-driver-like comma...
Defines version macros and version-related utility functions for Clang.
void addCommand(std::unique_ptr< Command > C)
Dataflow Directional Tag Classes.
std::string SysRoot
sysroot, if present
Compilation - A set of tasks to perform for a single driver invocation.
std::string ResourceDir
The path to the compiler resource directory.