clang  20.0.0git
PPCLinux.cpp
Go to the documentation of this file.
1 //===-- PPCLinux.cpp - PowerPC ToolChain Implementations --------*- C++ -*-===//
2 //
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
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "PPCLinux.h"
10 #include "clang/Driver/Driver.h"
12 #include "clang/Driver/Options.h"
13 #include "llvm/Support/FileSystem.h"
14 #include "llvm/Support/Path.h"
15 
16 using namespace clang::driver;
17 using namespace clang::driver::toolchains;
18 using namespace llvm::opt;
19 using namespace llvm::sys;
20 
21 // Glibc older than 2.32 doesn't fully support IEEE float128. Here we check
22 // glibc version by looking at dynamic linker name.
23 static bool GlibcSupportsFloat128(const std::string &Linker) {
25 
26  // Resolve potential symlinks to linker.
27  if (fs::real_path(Linker, Path))
28  return false;
29  llvm::StringRef LinkerName =
30  path::filename(llvm::StringRef(Path.data(), Path.size()));
31 
32  // Since glibc 2.34, the installed .so file is not symlink anymore. But we can
33  // still safely assume it's newer than 2.32.
34  if (LinkerName.starts_with("ld64.so"))
35  return true;
36 
37  if (!LinkerName.starts_with("ld-2."))
38  return false;
39  unsigned Minor = (LinkerName[5] - '0') * 10 + (LinkerName[6] - '0');
40  if (Minor < 32)
41  return false;
42 
43  return true;
44 }
45 
47  const llvm::Triple &Triple,
48  const llvm::opt::ArgList &Args)
49  : Linux(D, Triple, Args) {
50  if (Arg *A = Args.getLastArg(options::OPT_mabi_EQ)) {
51  StringRef ABIName = A->getValue();
52 
53  if ((ABIName == "ieeelongdouble" &&
54  !SupportIEEEFloat128(D, Triple, Args)) ||
55  (ABIName == "ibmlongdouble" && !supportIBMLongDouble(D, Args)))
56  D.Diag(diag::warn_drv_unsupported_float_abi_by_lib) << ABIName;
57  }
58 }
59 
60 void PPCLinuxToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
61  ArgStringList &CC1Args) const {
62  if (!DriverArgs.hasArg(clang::driver::options::OPT_nostdinc) &&
63  !DriverArgs.hasArg(options::OPT_nobuiltininc)) {
64  const Driver &D = getDriver();
65  SmallString<128> P(D.ResourceDir);
66  llvm::sys::path::append(P, "include", "ppc_wrappers");
67  addSystemInclude(DriverArgs, CC1Args, P);
68  }
69 
70  Linux::AddClangSystemIncludeArgs(DriverArgs, CC1Args);
71 }
72 
73 bool PPCLinuxToolChain::supportIBMLongDouble(
74  const Driver &D, const llvm::opt::ArgList &Args) const {
75  if (Args.hasArg(options::OPT_nostdlib, options::OPT_nostdlibxx))
76  return true;
77 
79  if (StdLib == CST_Libstdcxx)
80  return true;
81 
82  return StdLib == CST_Libcxx && !defaultToIEEELongDouble();
83 }
84 
85 bool PPCLinuxToolChain::SupportIEEEFloat128(
86  const Driver &D, const llvm::Triple &Triple,
87  const llvm::opt::ArgList &Args) const {
88  if (!Triple.isLittleEndian() || !Triple.isPPC64())
89  return false;
90 
91  if (Args.hasArg(options::OPT_nostdlib, options::OPT_nostdlibxx))
92  return true;
93 
95  bool HasUnsupportedCXXLib =
96  (StdLib == CST_Libcxx && !defaultToIEEELongDouble()) ||
97  (StdLib == CST_Libstdcxx &&
99 
100  std::string Linker = Linux::getDynamicLinker(Args);
101  return GlibcSupportsFloat128((Twine(D.DyldPrefix) + Linker).str()) &&
102  !(D.CCCIsCXX() && HasUnsupportedCXXLib);
103 }
StringRef P
const Decl * D
IndirectLocalPath & Path
static bool GlibcSupportsFloat128(const std::string &Linker)
Definition: PPCLinux.cpp:23
Driver - Encapsulate logic for constructing compilation processes from a set of gcc-driver-like comma...
Definition: Driver.h:77
const Driver & getDriver() const
Definition: ToolChain.h:269
static void addSystemInclude(const llvm::opt::ArgList &DriverArgs, llvm::opt::ArgStringList &CC1Args, const Twine &Path)
Utility function to add a system include directory to CC1 arguments.
Definition: ToolChain.cpp:1287
bool defaultToIEEELongDouble() const
Check whether use IEEE binary128 as long double format by default.
Definition: ToolChain.cpp:196
virtual CXXStdlibType GetCXXStdlibType(const llvm::opt::ArgList &Args) const
Definition: ToolChain.cpp:1261
const GCCVersion & getVersion() const
Get the detected GCC version string.
Definition: Gnu.h:252
GCCInstallationDetector GCCInstallation
Definition: Gnu.h:294
void AddClangSystemIncludeArgs(const llvm::opt::ArgList &DriverArgs, llvm::opt::ArgStringList &CC1Args) const override
Add the clang cc1 arguments for system include paths.
Definition: Linux.cpp:635
std::string getDynamicLinker(const llvm::opt::ArgList &Args) const override
Definition: Linux.cpp:451
void AddClangSystemIncludeArgs(const llvm::opt::ArgList &DriverArgs, llvm::opt::ArgStringList &CC1Args) const override
Add the clang cc1 arguments for system include paths.
Definition: PPCLinux.cpp:60
PPCLinuxToolChain(const Driver &D, const llvm::Triple &Triple, const llvm::opt::ArgList &Args)
Definition: PPCLinux.cpp:46
bool isOlderThan(int RHSMajor, int RHSMinor, int RHSPatch, StringRef RHSPatchSuffix=StringRef()) const
Generic_GCC - A tool chain using the 'gcc' command to perform all subcommands; this relies on gcc tra...
Definition: Gnu.cpp:2216