106f32e7eSjoerg //===--- OSTargets.h - Declare OS target feature support --------*- C++ -*-===//
206f32e7eSjoerg //
306f32e7eSjoerg // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
406f32e7eSjoerg // See https://llvm.org/LICENSE.txt for license information.
506f32e7eSjoerg // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
606f32e7eSjoerg //
706f32e7eSjoerg //===----------------------------------------------------------------------===//
806f32e7eSjoerg //
906f32e7eSjoerg // This file declares OS specific TargetInfo types.
1006f32e7eSjoerg //===----------------------------------------------------------------------===//
1106f32e7eSjoerg 
1206f32e7eSjoerg #ifndef LLVM_CLANG_LIB_BASIC_TARGETS_OSTARGETS_H
1306f32e7eSjoerg #define LLVM_CLANG_LIB_BASIC_TARGETS_OSTARGETS_H
1406f32e7eSjoerg 
1506f32e7eSjoerg #include "Targets.h"
1606f32e7eSjoerg 
1706f32e7eSjoerg namespace clang {
1806f32e7eSjoerg namespace targets {
1906f32e7eSjoerg 
2006f32e7eSjoerg template <typename TgtInfo>
2106f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY OSTargetInfo : public TgtInfo {
2206f32e7eSjoerg protected:
2306f32e7eSjoerg   virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
2406f32e7eSjoerg                             MacroBuilder &Builder) const = 0;
2506f32e7eSjoerg 
2606f32e7eSjoerg public:
OSTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)2706f32e7eSjoerg   OSTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
2806f32e7eSjoerg       : TgtInfo(Triple, Opts) {}
2906f32e7eSjoerg 
getTargetDefines(const LangOptions & Opts,MacroBuilder & Builder)3006f32e7eSjoerg   void getTargetDefines(const LangOptions &Opts,
3106f32e7eSjoerg                         MacroBuilder &Builder) const override {
3206f32e7eSjoerg     TgtInfo::getTargetDefines(Opts, Builder);
3306f32e7eSjoerg     getOSDefines(Opts, TgtInfo::getTriple(), Builder);
3406f32e7eSjoerg   }
3506f32e7eSjoerg };
3606f32e7eSjoerg 
3706f32e7eSjoerg // CloudABI Target
3806f32e7eSjoerg template <typename Target>
3906f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY CloudABITargetInfo : public OSTargetInfo<Target> {
4006f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)4106f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
4206f32e7eSjoerg                     MacroBuilder &Builder) const override {
4306f32e7eSjoerg     Builder.defineMacro("__CloudABI__");
4406f32e7eSjoerg     Builder.defineMacro("__ELF__");
4506f32e7eSjoerg 
4606f32e7eSjoerg     // CloudABI uses ISO/IEC 10646:2012 for wchar_t, char16_t and char32_t.
4706f32e7eSjoerg     Builder.defineMacro("__STDC_ISO_10646__", "201206L");
4806f32e7eSjoerg     Builder.defineMacro("__STDC_UTF_16__");
4906f32e7eSjoerg     Builder.defineMacro("__STDC_UTF_32__");
5006f32e7eSjoerg   }
5106f32e7eSjoerg 
5206f32e7eSjoerg public:
CloudABITargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)5306f32e7eSjoerg   CloudABITargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
5406f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {}
5506f32e7eSjoerg };
5606f32e7eSjoerg 
5706f32e7eSjoerg // Ananas target
5806f32e7eSjoerg template <typename Target>
5906f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY AnanasTargetInfo : public OSTargetInfo<Target> {
6006f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)6106f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
6206f32e7eSjoerg                     MacroBuilder &Builder) const override {
6306f32e7eSjoerg     // Ananas defines
6406f32e7eSjoerg     Builder.defineMacro("__Ananas__");
6506f32e7eSjoerg     Builder.defineMacro("__ELF__");
6606f32e7eSjoerg   }
6706f32e7eSjoerg 
6806f32e7eSjoerg public:
AnanasTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)6906f32e7eSjoerg   AnanasTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
7006f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {}
7106f32e7eSjoerg };
7206f32e7eSjoerg 
7306f32e7eSjoerg void getDarwinDefines(MacroBuilder &Builder, const LangOptions &Opts,
7406f32e7eSjoerg                       const llvm::Triple &Triple, StringRef &PlatformName,
7506f32e7eSjoerg                       VersionTuple &PlatformMinVersion);
7606f32e7eSjoerg 
7706f32e7eSjoerg template <typename Target>
7806f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY DarwinTargetInfo : public OSTargetInfo<Target> {
7906f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)8006f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
8106f32e7eSjoerg                     MacroBuilder &Builder) const override {
8206f32e7eSjoerg     getDarwinDefines(Builder, Opts, Triple, this->PlatformName,
8306f32e7eSjoerg                      this->PlatformMinVersion);
8406f32e7eSjoerg   }
8506f32e7eSjoerg 
8606f32e7eSjoerg public:
DarwinTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)8706f32e7eSjoerg   DarwinTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
8806f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
89*13fbcb42Sjoerg     // By default, no TLS, and we list permitted architecture/OS
9006f32e7eSjoerg     // combinations.
9106f32e7eSjoerg     this->TLSSupported = false;
9206f32e7eSjoerg 
9306f32e7eSjoerg     if (Triple.isMacOSX())
9406f32e7eSjoerg       this->TLSSupported = !Triple.isMacOSXVersionLT(10, 7);
9506f32e7eSjoerg     else if (Triple.isiOS()) {
9606f32e7eSjoerg       // 64-bit iOS supported it from 8 onwards, 32-bit device from 9 onwards,
9706f32e7eSjoerg       // 32-bit simulator from 10 onwards.
9806f32e7eSjoerg       if (Triple.isArch64Bit())
9906f32e7eSjoerg         this->TLSSupported = !Triple.isOSVersionLT(8);
10006f32e7eSjoerg       else if (Triple.isArch32Bit()) {
10106f32e7eSjoerg         if (!Triple.isSimulatorEnvironment())
10206f32e7eSjoerg           this->TLSSupported = !Triple.isOSVersionLT(9);
10306f32e7eSjoerg         else
10406f32e7eSjoerg           this->TLSSupported = !Triple.isOSVersionLT(10);
10506f32e7eSjoerg       }
10606f32e7eSjoerg     } else if (Triple.isWatchOS()) {
10706f32e7eSjoerg       if (!Triple.isSimulatorEnvironment())
10806f32e7eSjoerg         this->TLSSupported = !Triple.isOSVersionLT(2);
10906f32e7eSjoerg       else
11006f32e7eSjoerg         this->TLSSupported = !Triple.isOSVersionLT(3);
11106f32e7eSjoerg     }
11206f32e7eSjoerg 
11306f32e7eSjoerg     this->MCountName = "\01mcount";
11406f32e7eSjoerg   }
11506f32e7eSjoerg 
getStaticInitSectionSpecifier()11606f32e7eSjoerg   const char *getStaticInitSectionSpecifier() const override {
11706f32e7eSjoerg     // FIXME: We should return 0 when building kexts.
11806f32e7eSjoerg     return "__TEXT,__StaticInit,regular,pure_instructions";
11906f32e7eSjoerg   }
12006f32e7eSjoerg 
12106f32e7eSjoerg   /// Darwin does not support protected visibility.  Darwin's "default"
12206f32e7eSjoerg   /// is very similar to ELF's "protected";  Darwin requires a "weak"
12306f32e7eSjoerg   /// attribute on declarations that can be dynamically replaced.
hasProtectedVisibility()12406f32e7eSjoerg   bool hasProtectedVisibility() const override { return false; }
12506f32e7eSjoerg 
getExnObjectAlignment()12606f32e7eSjoerg   unsigned getExnObjectAlignment() const override {
12706f32e7eSjoerg     // Older versions of libc++abi guarantee an alignment of only 8-bytes for
12806f32e7eSjoerg     // exception objects because of a bug in __cxa_exception that was
12906f32e7eSjoerg     // eventually fixed in r319123.
13006f32e7eSjoerg     llvm::VersionTuple MinVersion;
13106f32e7eSjoerg     const llvm::Triple &T = this->getTriple();
13206f32e7eSjoerg 
13306f32e7eSjoerg     // Compute the earliest OS versions that have the fix to libc++abi.
13406f32e7eSjoerg     switch (T.getOS()) {
13506f32e7eSjoerg     case llvm::Triple::Darwin:
13606f32e7eSjoerg     case llvm::Triple::MacOSX: // Earliest supporting version is 10.14.
13706f32e7eSjoerg       MinVersion = llvm::VersionTuple(10U, 14U);
13806f32e7eSjoerg       break;
13906f32e7eSjoerg     case llvm::Triple::IOS:
14006f32e7eSjoerg     case llvm::Triple::TvOS: // Earliest supporting version is 12.0.0.
14106f32e7eSjoerg       MinVersion = llvm::VersionTuple(12U);
14206f32e7eSjoerg       break;
14306f32e7eSjoerg     case llvm::Triple::WatchOS: // Earliest supporting version is 5.0.0.
14406f32e7eSjoerg       MinVersion = llvm::VersionTuple(5U);
14506f32e7eSjoerg       break;
14606f32e7eSjoerg     default:
147*13fbcb42Sjoerg       // Conservatively return 8 bytes if OS is unknown.
148*13fbcb42Sjoerg       return 64;
14906f32e7eSjoerg     }
15006f32e7eSjoerg 
15106f32e7eSjoerg     unsigned Major, Minor, Micro;
15206f32e7eSjoerg     T.getOSVersion(Major, Minor, Micro);
15306f32e7eSjoerg     if (llvm::VersionTuple(Major, Minor, Micro) < MinVersion)
15406f32e7eSjoerg       return 64;
15506f32e7eSjoerg     return OSTargetInfo<Target>::getExnObjectAlignment();
15606f32e7eSjoerg   }
15706f32e7eSjoerg 
getLeastIntTypeByWidth(unsigned BitWidth,bool IsSigned)15806f32e7eSjoerg   TargetInfo::IntType getLeastIntTypeByWidth(unsigned BitWidth,
15906f32e7eSjoerg                                              bool IsSigned) const final {
16006f32e7eSjoerg     // Darwin uses `long long` for `int_least64_t` and `int_fast64_t`.
16106f32e7eSjoerg     return BitWidth == 64
16206f32e7eSjoerg                ? (IsSigned ? TargetInfo::SignedLongLong
16306f32e7eSjoerg                            : TargetInfo::UnsignedLongLong)
16406f32e7eSjoerg                : TargetInfo::getLeastIntTypeByWidth(BitWidth, IsSigned);
16506f32e7eSjoerg   }
16606f32e7eSjoerg };
16706f32e7eSjoerg 
16806f32e7eSjoerg // DragonFlyBSD Target
16906f32e7eSjoerg template <typename Target>
17006f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY DragonFlyBSDTargetInfo
17106f32e7eSjoerg     : public OSTargetInfo<Target> {
17206f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)17306f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
17406f32e7eSjoerg                     MacroBuilder &Builder) const override {
17506f32e7eSjoerg     // DragonFly defines; list based off of gcc output
17606f32e7eSjoerg     Builder.defineMacro("__DragonFly__");
17706f32e7eSjoerg     Builder.defineMacro("__DragonFly_cc_version", "100001");
17806f32e7eSjoerg     Builder.defineMacro("__ELF__");
17906f32e7eSjoerg     Builder.defineMacro("__KPRINTF_ATTRIBUTE__");
18006f32e7eSjoerg     Builder.defineMacro("__tune_i386__");
18106f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
18206f32e7eSjoerg   }
18306f32e7eSjoerg 
18406f32e7eSjoerg public:
DragonFlyBSDTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)18506f32e7eSjoerg   DragonFlyBSDTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
18606f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
18706f32e7eSjoerg     switch (Triple.getArch()) {
18806f32e7eSjoerg     default:
18906f32e7eSjoerg     case llvm::Triple::x86:
19006f32e7eSjoerg     case llvm::Triple::x86_64:
19106f32e7eSjoerg       this->MCountName = ".mcount";
19206f32e7eSjoerg       break;
19306f32e7eSjoerg     }
19406f32e7eSjoerg   }
19506f32e7eSjoerg };
19606f32e7eSjoerg 
19706f32e7eSjoerg #ifndef FREEBSD_CC_VERSION
19806f32e7eSjoerg #define FREEBSD_CC_VERSION 0U
19906f32e7eSjoerg #endif
20006f32e7eSjoerg 
20106f32e7eSjoerg // FreeBSD Target
20206f32e7eSjoerg template <typename Target>
20306f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY FreeBSDTargetInfo : public OSTargetInfo<Target> {
20406f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)20506f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
20606f32e7eSjoerg                     MacroBuilder &Builder) const override {
20706f32e7eSjoerg     // FreeBSD defines; list based off of gcc output
20806f32e7eSjoerg 
20906f32e7eSjoerg     unsigned Release = Triple.getOSMajorVersion();
21006f32e7eSjoerg     if (Release == 0U)
21106f32e7eSjoerg       Release = 8U;
21206f32e7eSjoerg     unsigned CCVersion = FREEBSD_CC_VERSION;
21306f32e7eSjoerg     if (CCVersion == 0U)
21406f32e7eSjoerg       CCVersion = Release * 100000U + 1U;
21506f32e7eSjoerg 
21606f32e7eSjoerg     Builder.defineMacro("__FreeBSD__", Twine(Release));
21706f32e7eSjoerg     Builder.defineMacro("__FreeBSD_cc_version", Twine(CCVersion));
21806f32e7eSjoerg     Builder.defineMacro("__KPRINTF_ATTRIBUTE__");
21906f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
22006f32e7eSjoerg     Builder.defineMacro("__ELF__");
22106f32e7eSjoerg 
22206f32e7eSjoerg     // On FreeBSD, wchar_t contains the number of the code point as
22306f32e7eSjoerg     // used by the character set of the locale. These character sets are
22406f32e7eSjoerg     // not necessarily a superset of ASCII.
22506f32e7eSjoerg     //
22606f32e7eSjoerg     // FIXME: This is wrong; the macro refers to the numerical values
22706f32e7eSjoerg     // of wchar_t *literals*, which are not locale-dependent. However,
22806f32e7eSjoerg     // FreeBSD systems apparently depend on us getting this wrong, and
22906f32e7eSjoerg     // setting this to 1 is conforming even if all the basic source
23006f32e7eSjoerg     // character literals have the same encoding as char and wchar_t.
23106f32e7eSjoerg     Builder.defineMacro("__STDC_MB_MIGHT_NEQ_WC__", "1");
23206f32e7eSjoerg   }
23306f32e7eSjoerg 
23406f32e7eSjoerg public:
FreeBSDTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)23506f32e7eSjoerg   FreeBSDTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
23606f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
23706f32e7eSjoerg     switch (Triple.getArch()) {
23806f32e7eSjoerg     default:
23906f32e7eSjoerg     case llvm::Triple::x86:
24006f32e7eSjoerg     case llvm::Triple::x86_64:
24106f32e7eSjoerg       this->MCountName = ".mcount";
24206f32e7eSjoerg       break;
24306f32e7eSjoerg     case llvm::Triple::mips:
24406f32e7eSjoerg     case llvm::Triple::mipsel:
24506f32e7eSjoerg     case llvm::Triple::ppc:
246*13fbcb42Sjoerg     case llvm::Triple::ppcle:
24706f32e7eSjoerg     case llvm::Triple::ppc64:
24806f32e7eSjoerg     case llvm::Triple::ppc64le:
24906f32e7eSjoerg       this->MCountName = "_mcount";
25006f32e7eSjoerg       break;
25106f32e7eSjoerg     case llvm::Triple::arm:
25206f32e7eSjoerg       this->MCountName = "__mcount";
25306f32e7eSjoerg       break;
254*13fbcb42Sjoerg     case llvm::Triple::riscv32:
255*13fbcb42Sjoerg     case llvm::Triple::riscv64:
256*13fbcb42Sjoerg       break;
25706f32e7eSjoerg     }
25806f32e7eSjoerg   }
25906f32e7eSjoerg };
26006f32e7eSjoerg 
26106f32e7eSjoerg // GNU/kFreeBSD Target
26206f32e7eSjoerg template <typename Target>
26306f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY KFreeBSDTargetInfo : public OSTargetInfo<Target> {
26406f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)26506f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
26606f32e7eSjoerg                     MacroBuilder &Builder) const override {
26706f32e7eSjoerg     // GNU/kFreeBSD defines; list based off of gcc output
26806f32e7eSjoerg 
26906f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
27006f32e7eSjoerg     Builder.defineMacro("__FreeBSD_kernel__");
27106f32e7eSjoerg     Builder.defineMacro("__GLIBC__");
27206f32e7eSjoerg     Builder.defineMacro("__ELF__");
27306f32e7eSjoerg     if (Opts.POSIXThreads)
27406f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
27506f32e7eSjoerg     if (Opts.CPlusPlus)
27606f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
27706f32e7eSjoerg   }
27806f32e7eSjoerg 
27906f32e7eSjoerg public:
KFreeBSDTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)28006f32e7eSjoerg   KFreeBSDTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
28106f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {}
28206f32e7eSjoerg };
28306f32e7eSjoerg 
28406f32e7eSjoerg // Haiku Target
28506f32e7eSjoerg template <typename Target>
28606f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY HaikuTargetInfo : public OSTargetInfo<Target> {
28706f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)28806f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
28906f32e7eSjoerg                     MacroBuilder &Builder) const override {
29006f32e7eSjoerg     // Haiku defines; list based off of gcc output
29106f32e7eSjoerg     Builder.defineMacro("__HAIKU__");
29206f32e7eSjoerg     Builder.defineMacro("__ELF__");
29306f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
29406f32e7eSjoerg     if (this->HasFloat128)
29506f32e7eSjoerg       Builder.defineMacro("__FLOAT128__");
29606f32e7eSjoerg   }
29706f32e7eSjoerg 
29806f32e7eSjoerg public:
HaikuTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)29906f32e7eSjoerg   HaikuTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
30006f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
30106f32e7eSjoerg     this->SizeType = TargetInfo::UnsignedLong;
30206f32e7eSjoerg     this->IntPtrType = TargetInfo::SignedLong;
30306f32e7eSjoerg     this->PtrDiffType = TargetInfo::SignedLong;
30406f32e7eSjoerg     this->ProcessIDType = TargetInfo::SignedLong;
30506f32e7eSjoerg     this->TLSSupported = false;
30606f32e7eSjoerg     switch (Triple.getArch()) {
30706f32e7eSjoerg     default:
30806f32e7eSjoerg       break;
30906f32e7eSjoerg     case llvm::Triple::x86:
31006f32e7eSjoerg     case llvm::Triple::x86_64:
31106f32e7eSjoerg       this->HasFloat128 = true;
31206f32e7eSjoerg       break;
31306f32e7eSjoerg     }
31406f32e7eSjoerg   }
31506f32e7eSjoerg };
31606f32e7eSjoerg 
31706f32e7eSjoerg // Hurd target
31806f32e7eSjoerg template <typename Target>
31906f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY HurdTargetInfo : public OSTargetInfo<Target> {
32006f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)32106f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
32206f32e7eSjoerg                     MacroBuilder &Builder) const override {
32306f32e7eSjoerg     // Hurd defines; list based off of gcc output.
32406f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
32506f32e7eSjoerg     Builder.defineMacro("__GNU__");
32606f32e7eSjoerg     Builder.defineMacro("__gnu_hurd__");
32706f32e7eSjoerg     Builder.defineMacro("__MACH__");
32806f32e7eSjoerg     Builder.defineMacro("__GLIBC__");
32906f32e7eSjoerg     Builder.defineMacro("__ELF__");
33006f32e7eSjoerg     if (Opts.POSIXThreads)
33106f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
33206f32e7eSjoerg     if (Opts.CPlusPlus)
33306f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
33406f32e7eSjoerg   }
33506f32e7eSjoerg public:
HurdTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)33606f32e7eSjoerg   HurdTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
33706f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {}
33806f32e7eSjoerg };
33906f32e7eSjoerg 
34006f32e7eSjoerg // Minix Target
34106f32e7eSjoerg template <typename Target>
34206f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY MinixTargetInfo : public OSTargetInfo<Target> {
34306f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)34406f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
34506f32e7eSjoerg                     MacroBuilder &Builder) const override {
34606f32e7eSjoerg     // Minix defines
34706f32e7eSjoerg 
34806f32e7eSjoerg     Builder.defineMacro("__minix", "3");
34906f32e7eSjoerg     Builder.defineMacro("_EM_WSIZE", "4");
35006f32e7eSjoerg     Builder.defineMacro("_EM_PSIZE", "4");
35106f32e7eSjoerg     Builder.defineMacro("_EM_SSIZE", "2");
35206f32e7eSjoerg     Builder.defineMacro("_EM_LSIZE", "4");
35306f32e7eSjoerg     Builder.defineMacro("_EM_FSIZE", "4");
35406f32e7eSjoerg     Builder.defineMacro("_EM_DSIZE", "8");
35506f32e7eSjoerg     Builder.defineMacro("__ELF__");
35606f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
35706f32e7eSjoerg   }
35806f32e7eSjoerg 
35906f32e7eSjoerg public:
MinixTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)36006f32e7eSjoerg   MinixTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
36106f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {}
36206f32e7eSjoerg };
36306f32e7eSjoerg 
36406f32e7eSjoerg // Linux target
36506f32e7eSjoerg template <typename Target>
36606f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY LinuxTargetInfo : public OSTargetInfo<Target> {
36706f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)36806f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
36906f32e7eSjoerg                     MacroBuilder &Builder) const override {
37006f32e7eSjoerg     // Linux defines; list based off of gcc output
37106f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
37206f32e7eSjoerg     DefineStd(Builder, "linux", Opts);
37306f32e7eSjoerg     Builder.defineMacro("__ELF__");
37406f32e7eSjoerg     if (Triple.isAndroid()) {
37506f32e7eSjoerg       Builder.defineMacro("__ANDROID__", "1");
37606f32e7eSjoerg       unsigned Maj, Min, Rev;
37706f32e7eSjoerg       Triple.getEnvironmentVersion(Maj, Min, Rev);
37806f32e7eSjoerg       this->PlatformName = "android";
37906f32e7eSjoerg       this->PlatformMinVersion = VersionTuple(Maj, Min, Rev);
380*13fbcb42Sjoerg       if (Maj) {
381*13fbcb42Sjoerg         Builder.defineMacro("__ANDROID_MIN_SDK_VERSION__", Twine(Maj));
382*13fbcb42Sjoerg         // This historical but ambiguous name for the minSdkVersion macro. Keep
383*13fbcb42Sjoerg         // defined for compatibility.
384*13fbcb42Sjoerg         Builder.defineMacro("__ANDROID_API__", "__ANDROID_MIN_SDK_VERSION__");
385*13fbcb42Sjoerg       }
38606f32e7eSjoerg     } else {
38706f32e7eSjoerg         Builder.defineMacro("__gnu_linux__");
38806f32e7eSjoerg     }
38906f32e7eSjoerg     if (Opts.POSIXThreads)
39006f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
39106f32e7eSjoerg     if (Opts.CPlusPlus)
39206f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
39306f32e7eSjoerg     if (this->HasFloat128)
39406f32e7eSjoerg       Builder.defineMacro("__FLOAT128__");
39506f32e7eSjoerg   }
39606f32e7eSjoerg 
39706f32e7eSjoerg public:
LinuxTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)39806f32e7eSjoerg   LinuxTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
39906f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
40006f32e7eSjoerg     this->WIntType = TargetInfo::UnsignedInt;
40106f32e7eSjoerg 
40206f32e7eSjoerg     switch (Triple.getArch()) {
40306f32e7eSjoerg     default:
40406f32e7eSjoerg       break;
40506f32e7eSjoerg     case llvm::Triple::mips:
40606f32e7eSjoerg     case llvm::Triple::mipsel:
40706f32e7eSjoerg     case llvm::Triple::mips64:
40806f32e7eSjoerg     case llvm::Triple::mips64el:
40906f32e7eSjoerg     case llvm::Triple::ppc:
410*13fbcb42Sjoerg     case llvm::Triple::ppcle:
41106f32e7eSjoerg     case llvm::Triple::ppc64:
41206f32e7eSjoerg     case llvm::Triple::ppc64le:
41306f32e7eSjoerg       this->MCountName = "_mcount";
41406f32e7eSjoerg       break;
41506f32e7eSjoerg     case llvm::Triple::x86:
41606f32e7eSjoerg     case llvm::Triple::x86_64:
41706f32e7eSjoerg       this->HasFloat128 = true;
41806f32e7eSjoerg       break;
41906f32e7eSjoerg     }
42006f32e7eSjoerg   }
42106f32e7eSjoerg 
getStaticInitSectionSpecifier()42206f32e7eSjoerg   const char *getStaticInitSectionSpecifier() const override {
42306f32e7eSjoerg     return ".text.startup";
42406f32e7eSjoerg   }
42506f32e7eSjoerg };
42606f32e7eSjoerg 
42706f32e7eSjoerg // NetBSD Target
42806f32e7eSjoerg template <typename Target>
42906f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY NetBSDTargetInfo : public OSTargetInfo<Target> {
43006f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)43106f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
43206f32e7eSjoerg                     MacroBuilder &Builder) const override {
43306f32e7eSjoerg     // NetBSD defines; list based off of gcc output
43406f32e7eSjoerg     Builder.defineMacro("__NetBSD__");
43506f32e7eSjoerg     Builder.defineMacro("__unix__");
43606f32e7eSjoerg     Builder.defineMacro("__ELF__");
43706f32e7eSjoerg     if (Opts.POSIXThreads)
43806f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
43906f32e7eSjoerg   }
44006f32e7eSjoerg 
44106f32e7eSjoerg public:
NetBSDTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)44206f32e7eSjoerg   NetBSDTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
44306f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
44406f32e7eSjoerg     this->MCountName = "__mcount";
44506f32e7eSjoerg   }
44606f32e7eSjoerg };
44706f32e7eSjoerg 
44806f32e7eSjoerg // OpenBSD Target
44906f32e7eSjoerg template <typename Target>
45006f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY OpenBSDTargetInfo : public OSTargetInfo<Target> {
45106f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)45206f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
45306f32e7eSjoerg                     MacroBuilder &Builder) const override {
45406f32e7eSjoerg     // OpenBSD defines; list based off of gcc output
45506f32e7eSjoerg 
45606f32e7eSjoerg     Builder.defineMacro("__OpenBSD__");
45706f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
45806f32e7eSjoerg     Builder.defineMacro("__ELF__");
45906f32e7eSjoerg     if (Opts.POSIXThreads)
46006f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
46106f32e7eSjoerg     if (this->HasFloat128)
46206f32e7eSjoerg       Builder.defineMacro("__FLOAT128__");
46306f32e7eSjoerg   }
46406f32e7eSjoerg 
46506f32e7eSjoerg public:
OpenBSDTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)46606f32e7eSjoerg   OpenBSDTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
46706f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
468*13fbcb42Sjoerg     this->WCharType = this->WIntType = this->SignedInt;
469*13fbcb42Sjoerg     this->IntMaxType = TargetInfo::SignedLongLong;
470*13fbcb42Sjoerg     this->Int64Type = TargetInfo::SignedLongLong;
47106f32e7eSjoerg     switch (Triple.getArch()) {
47206f32e7eSjoerg     case llvm::Triple::x86:
47306f32e7eSjoerg     case llvm::Triple::x86_64:
47406f32e7eSjoerg       this->HasFloat128 = true;
47506f32e7eSjoerg       LLVM_FALLTHROUGH;
47606f32e7eSjoerg     default:
47706f32e7eSjoerg       this->MCountName = "__mcount";
47806f32e7eSjoerg       break;
47906f32e7eSjoerg     case llvm::Triple::mips64:
48006f32e7eSjoerg     case llvm::Triple::mips64el:
48106f32e7eSjoerg     case llvm::Triple::ppc:
482*13fbcb42Sjoerg     case llvm::Triple::ppc64:
483*13fbcb42Sjoerg     case llvm::Triple::ppc64le:
48406f32e7eSjoerg     case llvm::Triple::sparcv9:
48506f32e7eSjoerg       this->MCountName = "_mcount";
48606f32e7eSjoerg       break;
487*13fbcb42Sjoerg     case llvm::Triple::riscv32:
488*13fbcb42Sjoerg     case llvm::Triple::riscv64:
489*13fbcb42Sjoerg       break;
49006f32e7eSjoerg     }
49106f32e7eSjoerg   }
49206f32e7eSjoerg };
49306f32e7eSjoerg 
49406f32e7eSjoerg // PSP Target
49506f32e7eSjoerg template <typename Target>
49606f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY PSPTargetInfo : public OSTargetInfo<Target> {
49706f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)49806f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
49906f32e7eSjoerg                     MacroBuilder &Builder) const override {
50006f32e7eSjoerg     // PSP defines; list based on the output of the pspdev gcc toolchain.
50106f32e7eSjoerg     Builder.defineMacro("PSP");
50206f32e7eSjoerg     Builder.defineMacro("_PSP");
50306f32e7eSjoerg     Builder.defineMacro("__psp__");
50406f32e7eSjoerg     Builder.defineMacro("__ELF__");
50506f32e7eSjoerg   }
50606f32e7eSjoerg 
50706f32e7eSjoerg public:
PSPTargetInfo(const llvm::Triple & Triple)50806f32e7eSjoerg   PSPTargetInfo(const llvm::Triple &Triple) : OSTargetInfo<Target>(Triple) {}
50906f32e7eSjoerg };
51006f32e7eSjoerg 
51106f32e7eSjoerg // PS3 PPU Target
51206f32e7eSjoerg template <typename Target>
51306f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY PS3PPUTargetInfo : public OSTargetInfo<Target> {
51406f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)51506f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
51606f32e7eSjoerg                     MacroBuilder &Builder) const override {
51706f32e7eSjoerg     // PS3 PPU defines.
51806f32e7eSjoerg     Builder.defineMacro("__PPC__");
51906f32e7eSjoerg     Builder.defineMacro("__PPU__");
52006f32e7eSjoerg     Builder.defineMacro("__CELLOS_LV2__");
52106f32e7eSjoerg     Builder.defineMacro("__ELF__");
52206f32e7eSjoerg     Builder.defineMacro("__LP32__");
52306f32e7eSjoerg     Builder.defineMacro("_ARCH_PPC64");
52406f32e7eSjoerg     Builder.defineMacro("__powerpc64__");
52506f32e7eSjoerg   }
52606f32e7eSjoerg 
52706f32e7eSjoerg public:
PS3PPUTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)52806f32e7eSjoerg   PS3PPUTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
52906f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
53006f32e7eSjoerg     this->LongWidth = this->LongAlign = 32;
53106f32e7eSjoerg     this->PointerWidth = this->PointerAlign = 32;
53206f32e7eSjoerg     this->IntMaxType = TargetInfo::SignedLongLong;
53306f32e7eSjoerg     this->Int64Type = TargetInfo::SignedLongLong;
53406f32e7eSjoerg     this->SizeType = TargetInfo::UnsignedInt;
53506f32e7eSjoerg     this->resetDataLayout("E-m:e-p:32:32-i64:64-n32:64");
53606f32e7eSjoerg   }
53706f32e7eSjoerg };
53806f32e7eSjoerg 
53906f32e7eSjoerg template <typename Target>
54006f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY PS4OSTargetInfo : public OSTargetInfo<Target> {
54106f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)54206f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
54306f32e7eSjoerg                     MacroBuilder &Builder) const override {
54406f32e7eSjoerg     Builder.defineMacro("__FreeBSD__", "9");
54506f32e7eSjoerg     Builder.defineMacro("__FreeBSD_cc_version", "900001");
54606f32e7eSjoerg     Builder.defineMacro("__KPRINTF_ATTRIBUTE__");
54706f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
54806f32e7eSjoerg     Builder.defineMacro("__ELF__");
549*13fbcb42Sjoerg     Builder.defineMacro("__SCE__");
55006f32e7eSjoerg     Builder.defineMacro("__ORBIS__");
55106f32e7eSjoerg   }
55206f32e7eSjoerg 
55306f32e7eSjoerg public:
PS4OSTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)55406f32e7eSjoerg   PS4OSTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
55506f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
55606f32e7eSjoerg     this->WCharType = TargetInfo::UnsignedShort;
55706f32e7eSjoerg 
55806f32e7eSjoerg     // On PS4, TLS variable cannot be aligned to more than 32 bytes (256 bits).
55906f32e7eSjoerg     this->MaxTLSAlign = 256;
56006f32e7eSjoerg 
56106f32e7eSjoerg     // On PS4, do not honor explicit bit field alignment,
56206f32e7eSjoerg     // as in "__attribute__((aligned(2))) int b : 1;".
56306f32e7eSjoerg     this->UseExplicitBitFieldAlignment = false;
56406f32e7eSjoerg 
56506f32e7eSjoerg     switch (Triple.getArch()) {
56606f32e7eSjoerg     default:
56706f32e7eSjoerg     case llvm::Triple::x86_64:
56806f32e7eSjoerg       this->MCountName = ".mcount";
56906f32e7eSjoerg       this->NewAlign = 256;
57006f32e7eSjoerg       break;
57106f32e7eSjoerg     }
57206f32e7eSjoerg   }
57306f32e7eSjoerg   TargetInfo::CallingConvCheckResult
checkCallingConvention(CallingConv CC)57406f32e7eSjoerg   checkCallingConvention(CallingConv CC) const override {
57506f32e7eSjoerg     return (CC == CC_C) ? TargetInfo::CCCR_OK : TargetInfo::CCCR_Error;
57606f32e7eSjoerg   }
57706f32e7eSjoerg };
57806f32e7eSjoerg 
57906f32e7eSjoerg // RTEMS Target
58006f32e7eSjoerg template <typename Target>
58106f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY RTEMSTargetInfo : public OSTargetInfo<Target> {
58206f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)58306f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
58406f32e7eSjoerg                     MacroBuilder &Builder) const override {
58506f32e7eSjoerg     // RTEMS defines; list based off of gcc output
58606f32e7eSjoerg 
58706f32e7eSjoerg     Builder.defineMacro("__rtems__");
58806f32e7eSjoerg     Builder.defineMacro("__ELF__");
58906f32e7eSjoerg     if (Opts.CPlusPlus)
59006f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
59106f32e7eSjoerg   }
59206f32e7eSjoerg 
59306f32e7eSjoerg public:
RTEMSTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)59406f32e7eSjoerg   RTEMSTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
59506f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
59606f32e7eSjoerg     switch (Triple.getArch()) {
59706f32e7eSjoerg     default:
59806f32e7eSjoerg     case llvm::Triple::x86:
59906f32e7eSjoerg       // this->MCountName = ".mcount";
60006f32e7eSjoerg       break;
60106f32e7eSjoerg     case llvm::Triple::mips:
60206f32e7eSjoerg     case llvm::Triple::mipsel:
60306f32e7eSjoerg     case llvm::Triple::ppc:
60406f32e7eSjoerg     case llvm::Triple::ppc64:
60506f32e7eSjoerg     case llvm::Triple::ppc64le:
60606f32e7eSjoerg       // this->MCountName = "_mcount";
60706f32e7eSjoerg       break;
60806f32e7eSjoerg     case llvm::Triple::arm:
60906f32e7eSjoerg       // this->MCountName = "__mcount";
61006f32e7eSjoerg       break;
61106f32e7eSjoerg     }
61206f32e7eSjoerg   }
61306f32e7eSjoerg };
61406f32e7eSjoerg 
61506f32e7eSjoerg // Solaris target
61606f32e7eSjoerg template <typename Target>
61706f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY SolarisTargetInfo : public OSTargetInfo<Target> {
61806f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)61906f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
62006f32e7eSjoerg                     MacroBuilder &Builder) const override {
62106f32e7eSjoerg     DefineStd(Builder, "sun", Opts);
62206f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
62306f32e7eSjoerg     Builder.defineMacro("__ELF__");
62406f32e7eSjoerg     Builder.defineMacro("__svr4__");
62506f32e7eSjoerg     Builder.defineMacro("__SVR4");
62606f32e7eSjoerg     // Solaris headers require _XOPEN_SOURCE to be set to 600 for C99 and
62706f32e7eSjoerg     // newer, but to 500 for everything else.  feature_test.h has a check to
62806f32e7eSjoerg     // ensure that you are not using C99 with an old version of X/Open or C89
62906f32e7eSjoerg     // with a new version.
63006f32e7eSjoerg     if (Opts.C99)
63106f32e7eSjoerg       Builder.defineMacro("_XOPEN_SOURCE", "600");
63206f32e7eSjoerg     else
63306f32e7eSjoerg       Builder.defineMacro("_XOPEN_SOURCE", "500");
63406f32e7eSjoerg     if (Opts.CPlusPlus) {
63506f32e7eSjoerg       Builder.defineMacro("__C99FEATURES__");
63606f32e7eSjoerg       Builder.defineMacro("_FILE_OFFSET_BITS", "64");
63706f32e7eSjoerg     }
63806f32e7eSjoerg     // GCC restricts the next two to C++.
63906f32e7eSjoerg     Builder.defineMacro("_LARGEFILE_SOURCE");
64006f32e7eSjoerg     Builder.defineMacro("_LARGEFILE64_SOURCE");
64106f32e7eSjoerg     Builder.defineMacro("__EXTENSIONS__");
64206f32e7eSjoerg     if (Opts.POSIXThreads)
64306f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
64406f32e7eSjoerg     if (this->HasFloat128)
64506f32e7eSjoerg       Builder.defineMacro("__FLOAT128__");
64606f32e7eSjoerg   }
64706f32e7eSjoerg 
64806f32e7eSjoerg public:
SolarisTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)64906f32e7eSjoerg   SolarisTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
65006f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
65106f32e7eSjoerg     if (this->PointerWidth == 64) {
65206f32e7eSjoerg       this->WCharType = this->WIntType = this->SignedInt;
65306f32e7eSjoerg     } else {
65406f32e7eSjoerg       this->WCharType = this->WIntType = this->SignedLong;
65506f32e7eSjoerg     }
65606f32e7eSjoerg     switch (Triple.getArch()) {
65706f32e7eSjoerg     default:
65806f32e7eSjoerg       break;
65906f32e7eSjoerg     case llvm::Triple::x86:
66006f32e7eSjoerg     case llvm::Triple::x86_64:
66106f32e7eSjoerg       this->HasFloat128 = true;
66206f32e7eSjoerg       break;
66306f32e7eSjoerg     }
66406f32e7eSjoerg   }
66506f32e7eSjoerg };
66606f32e7eSjoerg 
66706f32e7eSjoerg // AIX Target
66806f32e7eSjoerg template <typename Target>
66906f32e7eSjoerg class AIXTargetInfo : public OSTargetInfo<Target> {
67006f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)67106f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
67206f32e7eSjoerg                     MacroBuilder &Builder) const override {
67306f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
67406f32e7eSjoerg     Builder.defineMacro("_IBMR2");
67506f32e7eSjoerg     Builder.defineMacro("_POWER");
67606f32e7eSjoerg 
67706f32e7eSjoerg     Builder.defineMacro("_AIX");
67806f32e7eSjoerg 
679*13fbcb42Sjoerg     if (Opts.EnableAIXExtendedAltivecABI)
680*13fbcb42Sjoerg       Builder.defineMacro("__EXTABI__");
681*13fbcb42Sjoerg 
68206f32e7eSjoerg     unsigned Major, Minor, Micro;
68306f32e7eSjoerg     Triple.getOSVersion(Major, Minor, Micro);
68406f32e7eSjoerg 
68506f32e7eSjoerg     // Define AIX OS-Version Macros.
68606f32e7eSjoerg     // Includes logic for legacy versions of AIX; no specific intent to support.
68706f32e7eSjoerg     std::pair<int, int> OsVersion = {Major, Minor};
68806f32e7eSjoerg     if (OsVersion >= std::make_pair(3, 2)) Builder.defineMacro("_AIX32");
68906f32e7eSjoerg     if (OsVersion >= std::make_pair(4, 1)) Builder.defineMacro("_AIX41");
69006f32e7eSjoerg     if (OsVersion >= std::make_pair(4, 3)) Builder.defineMacro("_AIX43");
69106f32e7eSjoerg     if (OsVersion >= std::make_pair(5, 0)) Builder.defineMacro("_AIX50");
69206f32e7eSjoerg     if (OsVersion >= std::make_pair(5, 1)) Builder.defineMacro("_AIX51");
69306f32e7eSjoerg     if (OsVersion >= std::make_pair(5, 2)) Builder.defineMacro("_AIX52");
69406f32e7eSjoerg     if (OsVersion >= std::make_pair(5, 3)) Builder.defineMacro("_AIX53");
69506f32e7eSjoerg     if (OsVersion >= std::make_pair(6, 1)) Builder.defineMacro("_AIX61");
69606f32e7eSjoerg     if (OsVersion >= std::make_pair(7, 1)) Builder.defineMacro("_AIX71");
69706f32e7eSjoerg     if (OsVersion >= std::make_pair(7, 2)) Builder.defineMacro("_AIX72");
69806f32e7eSjoerg 
69906f32e7eSjoerg     // FIXME: Do not define _LONG_LONG when -fno-long-long is specified.
70006f32e7eSjoerg     Builder.defineMacro("_LONG_LONG");
70106f32e7eSjoerg 
70206f32e7eSjoerg     if (Opts.POSIXThreads) {
70306f32e7eSjoerg       Builder.defineMacro("_THREAD_SAFE");
70406f32e7eSjoerg     }
70506f32e7eSjoerg 
70606f32e7eSjoerg     if (this->PointerWidth == 64) {
70706f32e7eSjoerg       Builder.defineMacro("__64BIT__");
70806f32e7eSjoerg     }
70906f32e7eSjoerg 
71006f32e7eSjoerg     // Define _WCHAR_T when it is a fundamental type
71106f32e7eSjoerg     // (i.e., for C++ without -fno-wchar).
71206f32e7eSjoerg     if (Opts.CPlusPlus && Opts.WChar) {
71306f32e7eSjoerg       Builder.defineMacro("_WCHAR_T");
71406f32e7eSjoerg     }
71506f32e7eSjoerg   }
71606f32e7eSjoerg 
71706f32e7eSjoerg public:
AIXTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)71806f32e7eSjoerg   AIXTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
71906f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
720*13fbcb42Sjoerg     this->TheCXXABI.set(TargetCXXABI::XL);
721*13fbcb42Sjoerg 
72206f32e7eSjoerg     if (this->PointerWidth == 64) {
72306f32e7eSjoerg       this->WCharType = this->UnsignedInt;
72406f32e7eSjoerg     } else {
72506f32e7eSjoerg       this->WCharType = this->UnsignedShort;
72606f32e7eSjoerg     }
72706f32e7eSjoerg     this->UseZeroLengthBitfieldAlignment = true;
72806f32e7eSjoerg   }
72906f32e7eSjoerg 
73006f32e7eSjoerg   // AIX sets FLT_EVAL_METHOD to be 1.
getFloatEvalMethod()73106f32e7eSjoerg   unsigned getFloatEvalMethod() const override { return 1; }
hasInt128Type()73206f32e7eSjoerg   bool hasInt128Type() const override { return false; }
733*13fbcb42Sjoerg 
defaultsToAIXPowerAlignment()734*13fbcb42Sjoerg   bool defaultsToAIXPowerAlignment() const override { return true; }
735*13fbcb42Sjoerg };
736*13fbcb42Sjoerg 
737*13fbcb42Sjoerg // z/OS target
738*13fbcb42Sjoerg template <typename Target>
739*13fbcb42Sjoerg class LLVM_LIBRARY_VISIBILITY ZOSTargetInfo : public OSTargetInfo<Target> {
740*13fbcb42Sjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)741*13fbcb42Sjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
742*13fbcb42Sjoerg                     MacroBuilder &Builder) const override {
743*13fbcb42Sjoerg     // FIXME: _LONG_LONG should not be defined under -std=c89.
744*13fbcb42Sjoerg     Builder.defineMacro("_LONG_LONG");
745*13fbcb42Sjoerg     Builder.defineMacro("_OPEN_DEFAULT");
746*13fbcb42Sjoerg     // _UNIX03_WITHDRAWN is required to build libcxx.
747*13fbcb42Sjoerg     Builder.defineMacro("_UNIX03_WITHDRAWN");
748*13fbcb42Sjoerg     Builder.defineMacro("__370__");
749*13fbcb42Sjoerg     Builder.defineMacro("__BFP__");
750*13fbcb42Sjoerg     // FIXME: __BOOL__ should not be defined under -std=c89.
751*13fbcb42Sjoerg     Builder.defineMacro("__BOOL__");
752*13fbcb42Sjoerg     Builder.defineMacro("__LONGNAME__");
753*13fbcb42Sjoerg     Builder.defineMacro("__MVS__");
754*13fbcb42Sjoerg     Builder.defineMacro("__THW_370__");
755*13fbcb42Sjoerg     Builder.defineMacro("__THW_BIG_ENDIAN__");
756*13fbcb42Sjoerg     Builder.defineMacro("__TOS_390__");
757*13fbcb42Sjoerg     Builder.defineMacro("__TOS_MVS__");
758*13fbcb42Sjoerg     Builder.defineMacro("__XPLINK__");
759*13fbcb42Sjoerg 
760*13fbcb42Sjoerg     if (this->PointerWidth == 64)
761*13fbcb42Sjoerg       Builder.defineMacro("__64BIT__");
762*13fbcb42Sjoerg 
763*13fbcb42Sjoerg     if (Opts.CPlusPlus) {
764*13fbcb42Sjoerg       Builder.defineMacro("__DLL__");
765*13fbcb42Sjoerg       // _XOPEN_SOURCE=600 is required to build libcxx.
766*13fbcb42Sjoerg       Builder.defineMacro("_XOPEN_SOURCE", "600");
767*13fbcb42Sjoerg     }
768*13fbcb42Sjoerg 
769*13fbcb42Sjoerg     if (Opts.GNUMode) {
770*13fbcb42Sjoerg       Builder.defineMacro("_MI_BUILTIN");
771*13fbcb42Sjoerg       Builder.defineMacro("_EXT");
772*13fbcb42Sjoerg     }
773*13fbcb42Sjoerg 
774*13fbcb42Sjoerg     if (Opts.CPlusPlus && Opts.WChar) {
775*13fbcb42Sjoerg       // Macro __wchar_t is defined so that the wchar_t data
776*13fbcb42Sjoerg       // type is not declared as a typedef in system headers.
777*13fbcb42Sjoerg       Builder.defineMacro("__wchar_t");
778*13fbcb42Sjoerg     }
779*13fbcb42Sjoerg 
780*13fbcb42Sjoerg     this->PlatformName = llvm::Triple::getOSTypeName(Triple.getOS());
781*13fbcb42Sjoerg   }
782*13fbcb42Sjoerg 
783*13fbcb42Sjoerg public:
ZOSTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)784*13fbcb42Sjoerg   ZOSTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
785*13fbcb42Sjoerg       : OSTargetInfo<Target>(Triple, Opts) {
786*13fbcb42Sjoerg     this->WCharType = TargetInfo::UnsignedInt;
787*13fbcb42Sjoerg     this->MaxAlignedAttribute = 128;
788*13fbcb42Sjoerg     this->UseBitFieldTypeAlignment = false;
789*13fbcb42Sjoerg     this->UseZeroLengthBitfieldAlignment = true;
790*13fbcb42Sjoerg     this->UseLeadingZeroLengthBitfield = false;
791*13fbcb42Sjoerg     this->ZeroLengthBitfieldBoundary = 32;
792*13fbcb42Sjoerg     this->MinGlobalAlign = 0;
793*13fbcb42Sjoerg     this->DefaultAlignForAttributeAligned = 128;
794*13fbcb42Sjoerg   }
79506f32e7eSjoerg };
79606f32e7eSjoerg 
79706f32e7eSjoerg void addWindowsDefines(const llvm::Triple &Triple, const LangOptions &Opts,
79806f32e7eSjoerg                        MacroBuilder &Builder);
79906f32e7eSjoerg 
80006f32e7eSjoerg // Windows target
80106f32e7eSjoerg template <typename Target>
80206f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY WindowsTargetInfo : public OSTargetInfo<Target> {
80306f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)80406f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
80506f32e7eSjoerg                     MacroBuilder &Builder) const override {
80606f32e7eSjoerg     addWindowsDefines(Triple, Opts, Builder);
80706f32e7eSjoerg   }
80806f32e7eSjoerg 
80906f32e7eSjoerg public:
WindowsTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)81006f32e7eSjoerg   WindowsTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
81106f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
81206f32e7eSjoerg     this->WCharType = TargetInfo::UnsignedShort;
81306f32e7eSjoerg     this->WIntType = TargetInfo::UnsignedShort;
81406f32e7eSjoerg   }
81506f32e7eSjoerg };
81606f32e7eSjoerg 
81706f32e7eSjoerg template <typename Target>
81806f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY NaClTargetInfo : public OSTargetInfo<Target> {
81906f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)82006f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
82106f32e7eSjoerg                     MacroBuilder &Builder) const override {
82206f32e7eSjoerg     if (Opts.POSIXThreads)
82306f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
82406f32e7eSjoerg     if (Opts.CPlusPlus)
82506f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
82606f32e7eSjoerg 
82706f32e7eSjoerg     DefineStd(Builder, "unix", Opts);
82806f32e7eSjoerg     Builder.defineMacro("__ELF__");
82906f32e7eSjoerg     Builder.defineMacro("__native_client__");
83006f32e7eSjoerg   }
83106f32e7eSjoerg 
83206f32e7eSjoerg public:
NaClTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)83306f32e7eSjoerg   NaClTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
83406f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
83506f32e7eSjoerg     this->LongAlign = 32;
83606f32e7eSjoerg     this->LongWidth = 32;
83706f32e7eSjoerg     this->PointerAlign = 32;
83806f32e7eSjoerg     this->PointerWidth = 32;
83906f32e7eSjoerg     this->IntMaxType = TargetInfo::SignedLongLong;
84006f32e7eSjoerg     this->Int64Type = TargetInfo::SignedLongLong;
84106f32e7eSjoerg     this->DoubleAlign = 64;
84206f32e7eSjoerg     this->LongDoubleWidth = 64;
84306f32e7eSjoerg     this->LongDoubleAlign = 64;
84406f32e7eSjoerg     this->LongLongWidth = 64;
84506f32e7eSjoerg     this->LongLongAlign = 64;
84606f32e7eSjoerg     this->SizeType = TargetInfo::UnsignedInt;
84706f32e7eSjoerg     this->PtrDiffType = TargetInfo::SignedInt;
84806f32e7eSjoerg     this->IntPtrType = TargetInfo::SignedInt;
84906f32e7eSjoerg     // RegParmMax is inherited from the underlying architecture.
85006f32e7eSjoerg     this->LongDoubleFormat = &llvm::APFloat::IEEEdouble();
85106f32e7eSjoerg     if (Triple.getArch() == llvm::Triple::arm) {
85206f32e7eSjoerg       // Handled in ARM's setABI().
85306f32e7eSjoerg     } else if (Triple.getArch() == llvm::Triple::x86) {
85406f32e7eSjoerg       this->resetDataLayout("e-m:e-p:32:32-p270:32:32-p271:32:32-p272:64:64-"
85506f32e7eSjoerg                             "i64:64-n8:16:32-S128");
85606f32e7eSjoerg     } else if (Triple.getArch() == llvm::Triple::x86_64) {
85706f32e7eSjoerg       this->resetDataLayout("e-m:e-p:32:32-p270:32:32-p271:32:32-p272:64:64-"
85806f32e7eSjoerg                             "i64:64-n8:16:32:64-S128");
85906f32e7eSjoerg     } else if (Triple.getArch() == llvm::Triple::mipsel) {
86006f32e7eSjoerg       // Handled on mips' setDataLayout.
86106f32e7eSjoerg     } else {
86206f32e7eSjoerg       assert(Triple.getArch() == llvm::Triple::le32);
86306f32e7eSjoerg       this->resetDataLayout("e-p:32:32-i64:64");
86406f32e7eSjoerg     }
86506f32e7eSjoerg   }
86606f32e7eSjoerg };
86706f32e7eSjoerg 
86806f32e7eSjoerg // Fuchsia Target
86906f32e7eSjoerg template <typename Target>
87006f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY FuchsiaTargetInfo : public OSTargetInfo<Target> {
87106f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)87206f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
87306f32e7eSjoerg                     MacroBuilder &Builder) const override {
87406f32e7eSjoerg     Builder.defineMacro("__Fuchsia__");
87506f32e7eSjoerg     Builder.defineMacro("__ELF__");
87606f32e7eSjoerg     if (Opts.POSIXThreads)
87706f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
87806f32e7eSjoerg     // Required by the libc++ locale support.
87906f32e7eSjoerg     if (Opts.CPlusPlus)
88006f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
88106f32e7eSjoerg   }
88206f32e7eSjoerg 
88306f32e7eSjoerg public:
FuchsiaTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)88406f32e7eSjoerg   FuchsiaTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
88506f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
88606f32e7eSjoerg     this->MCountName = "__mcount";
887*13fbcb42Sjoerg     this->TheCXXABI.set(TargetCXXABI::Fuchsia);
88806f32e7eSjoerg   }
88906f32e7eSjoerg };
89006f32e7eSjoerg 
89106f32e7eSjoerg // WebAssembly target
89206f32e7eSjoerg template <typename Target>
89306f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY WebAssemblyOSTargetInfo
89406f32e7eSjoerg     : public OSTargetInfo<Target> {
89506f32e7eSjoerg protected:
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)89606f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
897*13fbcb42Sjoerg                     MacroBuilder &Builder) const override {
89806f32e7eSjoerg     // A common platform macro.
89906f32e7eSjoerg     if (Opts.POSIXThreads)
90006f32e7eSjoerg       Builder.defineMacro("_REENTRANT");
90106f32e7eSjoerg     // Follow g++ convention and predefine _GNU_SOURCE for C++.
90206f32e7eSjoerg     if (Opts.CPlusPlus)
90306f32e7eSjoerg       Builder.defineMacro("_GNU_SOURCE");
90406f32e7eSjoerg     // Indicate that we have __float128.
90506f32e7eSjoerg     Builder.defineMacro("__FLOAT128__");
90606f32e7eSjoerg   }
90706f32e7eSjoerg 
90806f32e7eSjoerg public:
WebAssemblyOSTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)90906f32e7eSjoerg   explicit WebAssemblyOSTargetInfo(const llvm::Triple &Triple,
91006f32e7eSjoerg                                    const TargetOptions &Opts)
91106f32e7eSjoerg       : OSTargetInfo<Target>(Triple, Opts) {
91206f32e7eSjoerg     this->MCountName = "__mcount";
91306f32e7eSjoerg     this->TheCXXABI.set(TargetCXXABI::WebAssembly);
91406f32e7eSjoerg     this->HasFloat128 = true;
91506f32e7eSjoerg   }
91606f32e7eSjoerg };
91706f32e7eSjoerg 
91806f32e7eSjoerg // WASI target
91906f32e7eSjoerg template <typename Target>
92006f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY WASITargetInfo
92106f32e7eSjoerg     : public WebAssemblyOSTargetInfo<Target> {
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)92206f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
92306f32e7eSjoerg                     MacroBuilder &Builder) const final {
92406f32e7eSjoerg     WebAssemblyOSTargetInfo<Target>::getOSDefines(Opts, Triple, Builder);
92506f32e7eSjoerg     Builder.defineMacro("__wasi__");
92606f32e7eSjoerg   }
92706f32e7eSjoerg 
92806f32e7eSjoerg public:
WASITargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)92906f32e7eSjoerg   explicit WASITargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
93006f32e7eSjoerg       : WebAssemblyOSTargetInfo<Target>(Triple, Opts) {}
93106f32e7eSjoerg };
93206f32e7eSjoerg 
93306f32e7eSjoerg // Emscripten target
93406f32e7eSjoerg template <typename Target>
93506f32e7eSjoerg class LLVM_LIBRARY_VISIBILITY EmscriptenTargetInfo
93606f32e7eSjoerg     : public WebAssemblyOSTargetInfo<Target> {
getOSDefines(const LangOptions & Opts,const llvm::Triple & Triple,MacroBuilder & Builder)93706f32e7eSjoerg   void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
93806f32e7eSjoerg                     MacroBuilder &Builder) const final {
93906f32e7eSjoerg     WebAssemblyOSTargetInfo<Target>::getOSDefines(Opts, Triple, Builder);
94006f32e7eSjoerg     Builder.defineMacro("__EMSCRIPTEN__");
941*13fbcb42Sjoerg     if (Opts.POSIXThreads)
942*13fbcb42Sjoerg       Builder.defineMacro("__EMSCRIPTEN_PTHREADS__");
94306f32e7eSjoerg   }
94406f32e7eSjoerg 
94506f32e7eSjoerg public:
EmscriptenTargetInfo(const llvm::Triple & Triple,const TargetOptions & Opts)94606f32e7eSjoerg   explicit EmscriptenTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
94706f32e7eSjoerg       : WebAssemblyOSTargetInfo<Target>(Triple, Opts) {}
94806f32e7eSjoerg };
94906f32e7eSjoerg 
95006f32e7eSjoerg } // namespace targets
95106f32e7eSjoerg } // namespace clang
95206f32e7eSjoerg #endif // LLVM_CLANG_LIB_BASIC_TARGETS_OSTARGETS_H
953