1//===-- llvm/TargetParser/Triple.h - Target triple helper class--*- 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#ifndef LLVM_TARGETPARSER_TRIPLE_H
10#define LLVM_TARGETPARSER_TRIPLE_H
11
12#include "llvm/ADT/Twine.h"
13#include "llvm/Support/VersionTuple.h"
14
15// Some system headers or GCC predefined macros conflict with identifiers in
16// this file.  Undefine them here.
17#undef NetBSD
18#undef mips
19#undef sparc
20
21namespace llvm {
22
23/// Triple - Helper class for working with autoconf configuration names. For
24/// historical reasons, we also call these 'triples' (they used to contain
25/// exactly three fields).
26///
27/// Configuration names are strings in the canonical form:
28///   ARCHITECTURE-VENDOR-OPERATING_SYSTEM
29/// or
30///   ARCHITECTURE-VENDOR-OPERATING_SYSTEM-ENVIRONMENT
31///
32/// This class is used for clients which want to support arbitrary
33/// configuration names, but also want to implement certain special
34/// behavior for particular configurations. This class isolates the mapping
35/// from the components of the configuration name to well known IDs.
36///
37/// At its core the Triple class is designed to be a wrapper for a triple
38/// string; the constructor does not change or normalize the triple string.
39/// Clients that need to handle the non-canonical triples that users often
40/// specify should use the normalize method.
41///
42/// See autoconf/config.guess for a glimpse into what configuration names
43/// look like in practice.
44class Triple {
45public:
46  enum ArchType {
47    UnknownArch,
48
49    arm,            // ARM (little endian): arm, armv.*, xscale
50    armeb,          // ARM (big endian): armeb
51    aarch64,        // AArch64 (little endian): aarch64
52    aarch64_be,     // AArch64 (big endian): aarch64_be
53    aarch64_32,     // AArch64 (little endian) ILP32: aarch64_32
54    arc,            // ARC: Synopsys ARC
55    avr,            // AVR: Atmel AVR microcontroller
56    bpfel,          // eBPF or extended BPF or 64-bit BPF (little endian)
57    bpfeb,          // eBPF or extended BPF or 64-bit BPF (big endian)
58    csky,           // CSKY: csky
59    dxil,           // DXIL 32-bit DirectX bytecode
60    hexagon,        // Hexagon: hexagon
61    loongarch32,    // LoongArch (32-bit): loongarch32
62    loongarch64,    // LoongArch (64-bit): loongarch64
63    m68k,           // M68k: Motorola 680x0 family
64    mips,           // MIPS: mips, mipsallegrex, mipsr6
65    mipsel,         // MIPSEL: mipsel, mipsallegrexe, mipsr6el
66    mips64,         // MIPS64: mips64, mips64r6, mipsn32, mipsn32r6
67    mips64el,       // MIPS64EL: mips64el, mips64r6el, mipsn32el, mipsn32r6el
68    msp430,         // MSP430: msp430
69    ppc,            // PPC: powerpc
70    ppcle,          // PPCLE: powerpc (little endian)
71    ppc64,          // PPC64: powerpc64, ppu
72    ppc64le,        // PPC64LE: powerpc64le
73    r600,           // R600: AMD GPUs HD2XXX - HD6XXX
74    amdgcn,         // AMDGCN: AMD GCN GPUs
75    riscv32,        // RISC-V (32-bit): riscv32
76    riscv64,        // RISC-V (64-bit): riscv64
77    sparc,          // Sparc: sparc
78    sparcv9,        // Sparcv9: Sparcv9
79    sparcel,        // Sparc: (endianness = little). NB: 'Sparcle' is a CPU variant
80    systemz,        // SystemZ: s390x
81    tce,            // TCE (http://tce.cs.tut.fi/): tce
82    tcele,          // TCE little endian (http://tce.cs.tut.fi/): tcele
83    thumb,          // Thumb (little endian): thumb, thumbv.*
84    thumbeb,        // Thumb (big endian): thumbeb
85    x86,            // X86: i[3-9]86
86    x86_64,         // X86-64: amd64, x86_64
87    xcore,          // XCore: xcore
88    xtensa,         // Tensilica: Xtensa
89    nvptx,          // NVPTX: 32-bit
90    nvptx64,        // NVPTX: 64-bit
91    le32,           // le32: generic little-endian 32-bit CPU (PNaCl)
92    le64,           // le64: generic little-endian 64-bit CPU (PNaCl)
93    amdil,          // AMDIL
94    amdil64,        // AMDIL with 64-bit pointers
95    hsail,          // AMD HSAIL
96    hsail64,        // AMD HSAIL with 64-bit pointers
97    spir,           // SPIR: standard portable IR for OpenCL 32-bit version
98    spir64,         // SPIR: standard portable IR for OpenCL 64-bit version
99    spirv,          // SPIR-V with logical memory layout.
100    spirv32,        // SPIR-V with 32-bit pointers
101    spirv64,        // SPIR-V with 64-bit pointers
102    kalimba,        // Kalimba: generic kalimba
103    shave,          // SHAVE: Movidius vector VLIW processors
104    lanai,          // Lanai: Lanai 32-bit
105    wasm32,         // WebAssembly with 32-bit pointers
106    wasm64,         // WebAssembly with 64-bit pointers
107    renderscript32, // 32-bit RenderScript
108    renderscript64, // 64-bit RenderScript
109    ve,             // NEC SX-Aurora Vector Engine
110    LastArchType = ve
111  };
112  enum SubArchType {
113    NoSubArch,
114
115    ARMSubArch_v9_5a,
116    ARMSubArch_v9_4a,
117    ARMSubArch_v9_3a,
118    ARMSubArch_v9_2a,
119    ARMSubArch_v9_1a,
120    ARMSubArch_v9,
121    ARMSubArch_v8_9a,
122    ARMSubArch_v8_8a,
123    ARMSubArch_v8_7a,
124    ARMSubArch_v8_6a,
125    ARMSubArch_v8_5a,
126    ARMSubArch_v8_4a,
127    ARMSubArch_v8_3a,
128    ARMSubArch_v8_2a,
129    ARMSubArch_v8_1a,
130    ARMSubArch_v8,
131    ARMSubArch_v8r,
132    ARMSubArch_v8m_baseline,
133    ARMSubArch_v8m_mainline,
134    ARMSubArch_v8_1m_mainline,
135    ARMSubArch_v7,
136    ARMSubArch_v7em,
137    ARMSubArch_v7m,
138    ARMSubArch_v7s,
139    ARMSubArch_v7k,
140    ARMSubArch_v7ve,
141    ARMSubArch_v6,
142    ARMSubArch_v6m,
143    ARMSubArch_v6k,
144    ARMSubArch_v6t2,
145    ARMSubArch_v5,
146    ARMSubArch_v5te,
147    ARMSubArch_v4t,
148
149    AArch64SubArch_arm64e,
150    AArch64SubArch_arm64ec,
151
152    KalimbaSubArch_v3,
153    KalimbaSubArch_v4,
154    KalimbaSubArch_v5,
155
156    MipsSubArch_r6,
157
158    PPCSubArch_spe,
159
160    // SPIR-V sub-arch corresponds to its version.
161    SPIRVSubArch_v10,
162    SPIRVSubArch_v11,
163    SPIRVSubArch_v12,
164    SPIRVSubArch_v13,
165    SPIRVSubArch_v14,
166    SPIRVSubArch_v15,
167    SPIRVSubArch_v16,
168  };
169  enum VendorType {
170    UnknownVendor,
171
172    Apple,
173    PC,
174    SCEI,
175    Freescale,
176    IBM,
177    ImaginationTechnologies,
178    MipsTechnologies,
179    NVIDIA,
180    CSR,
181    AMD,
182    Mesa,
183    SUSE,
184    OpenEmbedded,
185    LastVendorType = OpenEmbedded
186  };
187  enum OSType {
188    UnknownOS,
189
190    Darwin,
191    DragonFly,
192    FreeBSD,
193    Fuchsia,
194    IOS,
195    KFreeBSD,
196    Linux,
197    Lv2,        // PS3
198    MacOSX,
199    NetBSD,
200    OpenBSD,
201    Solaris,
202    UEFI,
203    Win32,
204    ZOS,
205    Haiku,
206    RTEMS,
207    NaCl,       // Native Client
208    AIX,
209    CUDA,       // NVIDIA CUDA
210    NVCL,       // NVIDIA OpenCL
211    AMDHSA,     // AMD HSA Runtime
212    PS4,
213    PS5,
214    ELFIAMCU,
215    TvOS,       // Apple tvOS
216    WatchOS,    // Apple watchOS
217    DriverKit,  // Apple DriverKit
218    XROS,       // Apple XROS
219    Mesa3D,
220    AMDPAL,     // AMD PAL Runtime
221    HermitCore, // HermitCore Unikernel/Multikernel
222    Hurd,       // GNU/Hurd
223    WASI,       // Experimental WebAssembly OS
224    Emscripten,
225    ShaderModel, // DirectX ShaderModel
226    LiteOS,
227    Serenity,
228    Vulkan,      // Vulkan SPIR-V
229    LastOSType = Vulkan
230  };
231  enum EnvironmentType {
232    UnknownEnvironment,
233
234    GNU,
235    GNUABIN32,
236    GNUABI64,
237    GNUEABI,
238    GNUEABIHF,
239    GNUF32,
240    GNUF64,
241    GNUSF,
242    GNUX32,
243    GNUILP32,
244    CODE16,
245    EABI,
246    EABIHF,
247    Android,
248    Musl,
249    MuslEABI,
250    MuslEABIHF,
251    MuslX32,
252
253    MSVC,
254    Itanium,
255    Cygnus,
256    CoreCLR,
257    Simulator, // Simulator variants of other systems, e.g., Apple's iOS
258    MacABI, // Mac Catalyst variant of Apple's iOS deployment target.
259
260    // Shader Stages
261    // The order of these values matters, and must be kept in sync with the
262    // language options enum in Clang. The ordering is enforced in
263    // static_asserts in Triple.cpp and in Clang.
264    Pixel,
265    Vertex,
266    Geometry,
267    Hull,
268    Domain,
269    Compute,
270    Library,
271    RayGeneration,
272    Intersection,
273    AnyHit,
274    ClosestHit,
275    Miss,
276    Callable,
277    Mesh,
278    Amplification,
279
280    OpenHOS,
281
282    LastEnvironmentType = OpenHOS
283  };
284  enum ObjectFormatType {
285    UnknownObjectFormat,
286
287    COFF,
288    DXContainer,
289    ELF,
290    GOFF,
291    MachO,
292    SPIRV,
293    Wasm,
294    XCOFF,
295  };
296
297private:
298  std::string Data;
299
300  /// The parsed arch type.
301  ArchType Arch{};
302
303  /// The parsed subarchitecture type.
304  SubArchType SubArch{};
305
306  /// The parsed vendor type.
307  VendorType Vendor{};
308
309  /// The parsed OS type.
310  OSType OS{};
311
312  /// The parsed Environment type.
313  EnvironmentType Environment{};
314
315  /// The object format type.
316  ObjectFormatType ObjectFormat{};
317
318public:
319  /// @name Constructors
320  /// @{
321
322  /// Default constructor is the same as an empty string and leaves all
323  /// triple fields unknown.
324  Triple() = default;
325
326  explicit Triple(const Twine &Str);
327  Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr);
328  Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr,
329         const Twine &EnvironmentStr);
330
331  bool operator==(const Triple &Other) const {
332    return Arch == Other.Arch && SubArch == Other.SubArch &&
333           Vendor == Other.Vendor && OS == Other.OS &&
334           Environment == Other.Environment &&
335           ObjectFormat == Other.ObjectFormat;
336  }
337
338  bool operator!=(const Triple &Other) const {
339    return !(*this == Other);
340  }
341
342  /// @}
343  /// @name Normalization
344  /// @{
345
346  /// Turn an arbitrary machine specification into the canonical triple form (or
347  /// something sensible that the Triple class understands if nothing better can
348  /// reasonably be done).  In particular, it handles the common case in which
349  /// otherwise valid components are in the wrong order.
350  static std::string normalize(StringRef Str);
351
352  /// Return the normalized form of this triple's string.
353  std::string normalize() const { return normalize(Data); }
354
355  /// @}
356  /// @name Typed Component Access
357  /// @{
358
359  /// Get the parsed architecture type of this triple.
360  ArchType getArch() const { return Arch; }
361
362  /// get the parsed subarchitecture type for this triple.
363  SubArchType getSubArch() const { return SubArch; }
364
365  /// Get the parsed vendor type of this triple.
366  VendorType getVendor() const { return Vendor; }
367
368  /// Get the parsed operating system type of this triple.
369  OSType getOS() const { return OS; }
370
371  /// Does this triple have the optional environment (fourth) component?
372  bool hasEnvironment() const {
373    return getEnvironmentName() != "";
374  }
375
376  /// Get the parsed environment type of this triple.
377  EnvironmentType getEnvironment() const { return Environment; }
378
379  /// Parse the version number from the OS name component of the
380  /// triple, if present.
381  ///
382  /// For example, "fooos1.2.3" would return (1, 2, 3).
383  VersionTuple getEnvironmentVersion() const;
384
385  /// Get the object format for this triple.
386  ObjectFormatType getObjectFormat() const { return ObjectFormat; }
387
388  /// Parse the version number from the OS name component of the triple, if
389  /// present.
390  ///
391  /// For example, "fooos1.2.3" would return (1, 2, 3).
392  VersionTuple getOSVersion() const;
393
394  /// Return just the major version number, this is specialized because it is a
395  /// common query.
396  unsigned getOSMajorVersion() const { return getOSVersion().getMajor(); }
397
398  /// Parse the version number as with getOSVersion and then translate generic
399  /// "darwin" versions to the corresponding OS X versions.  This may also be
400  /// called with IOS triples but the OS X version number is just set to a
401  /// constant 10.4.0 in that case.  Returns true if successful.
402  bool getMacOSXVersion(VersionTuple &Version) const;
403
404  /// Parse the version number as with getOSVersion.  This should only be called
405  /// with IOS or generic triples.
406  VersionTuple getiOSVersion() const;
407
408  /// Parse the version number as with getOSVersion.  This should only be called
409  /// with WatchOS or generic triples.
410  VersionTuple getWatchOSVersion() const;
411
412  /// Parse the version number as with getOSVersion.
413  VersionTuple getDriverKitVersion() const;
414
415  /// Parse the Vulkan version number from the OSVersion and SPIR-V version
416  /// (SubArch).  This should only be called with Vulkan SPIR-V triples.
417  VersionTuple getVulkanVersion() const;
418
419  /// @}
420  /// @name Direct Component Access
421  /// @{
422
423  const std::string &str() const { return Data; }
424
425  const std::string &getTriple() const { return Data; }
426
427  /// Get the architecture (first) component of the triple.
428  StringRef getArchName() const;
429
430  /// Get the vendor (second) component of the triple.
431  StringRef getVendorName() const;
432
433  /// Get the operating system (third) component of the triple.
434  StringRef getOSName() const;
435
436  /// Get the optional environment (fourth) component of the triple, or "" if
437  /// empty.
438  StringRef getEnvironmentName() const;
439
440  /// Get the operating system and optional environment components as a single
441  /// string (separated by a '-' if the environment component is present).
442  StringRef getOSAndEnvironmentName() const;
443
444  /// Get the version component of the environment component as a single
445  /// string (the version after the environment).
446  ///
447  /// For example, "fooos1.2.3" would return "1.2.3".
448  StringRef getEnvironmentVersionString() const;
449
450  /// @}
451  /// @name Convenience Predicates
452  /// @{
453
454  /// Test whether the architecture is 64-bit
455  ///
456  /// Note that this tests for 64-bit pointer width, and nothing else. Note
457  /// that we intentionally expose only three predicates, 64-bit, 32-bit, and
458  /// 16-bit. The inner details of pointer width for particular architectures
459  /// is not summed up in the triple, and so only a coarse grained predicate
460  /// system is provided.
461  bool isArch64Bit() const;
462
463  /// Test whether the architecture is 32-bit
464  ///
465  /// Note that this tests for 32-bit pointer width, and nothing else.
466  bool isArch32Bit() const;
467
468  /// Test whether the architecture is 16-bit
469  ///
470  /// Note that this tests for 16-bit pointer width, and nothing else.
471  bool isArch16Bit() const;
472
473  /// Helper function for doing comparisons against version numbers included in
474  /// the target triple.
475  bool isOSVersionLT(unsigned Major, unsigned Minor = 0,
476                     unsigned Micro = 0) const {
477    if (Minor == 0) {
478      return getOSVersion() < VersionTuple(Major);
479    }
480    if (Micro == 0) {
481      return getOSVersion() < VersionTuple(Major, Minor);
482    }
483    return getOSVersion() < VersionTuple(Major, Minor, Micro);
484  }
485
486  bool isOSVersionLT(const Triple &Other) const {
487    return getOSVersion() < Other.getOSVersion();
488  }
489
490  /// Comparison function for checking OS X version compatibility, which handles
491  /// supporting skewed version numbering schemes used by the "darwin" triples.
492  bool isMacOSXVersionLT(unsigned Major, unsigned Minor = 0,
493                         unsigned Micro = 0) const;
494
495  /// Is this a Mac OS X triple. For legacy reasons, we support both "darwin"
496  /// and "osx" as OS X triples.
497  bool isMacOSX() const {
498    return getOS() == Triple::Darwin || getOS() == Triple::MacOSX;
499  }
500
501  /// Is this an iOS triple.
502  /// Note: This identifies tvOS as a variant of iOS. If that ever
503  /// changes, i.e., if the two operating systems diverge or their version
504  /// numbers get out of sync, that will need to be changed.
505  /// watchOS has completely different version numbers so it is not included.
506  bool isiOS() const {
507    return getOS() == Triple::IOS || isTvOS();
508  }
509
510  /// Is this an Apple tvOS triple.
511  bool isTvOS() const {
512    return getOS() == Triple::TvOS;
513  }
514
515  /// Is this an Apple watchOS triple.
516  bool isWatchOS() const {
517    return getOS() == Triple::WatchOS;
518  }
519
520  bool isWatchABI() const {
521    return getSubArch() == Triple::ARMSubArch_v7k;
522  }
523
524  /// Is this an Apple XROS triple.
525  bool isXROS() const { return getOS() == Triple::XROS; }
526
527  /// Is this an Apple DriverKit triple.
528  bool isDriverKit() const { return getOS() == Triple::DriverKit; }
529
530  bool isOSzOS() const { return getOS() == Triple::ZOS; }
531
532  /// Is this a "Darwin" OS (macOS, iOS, tvOS, watchOS, XROS, or DriverKit).
533  bool isOSDarwin() const {
534    return isMacOSX() || isiOS() || isWatchOS() || isDriverKit() || isXROS();
535  }
536
537  bool isSimulatorEnvironment() const {
538    return getEnvironment() == Triple::Simulator;
539  }
540
541  bool isMacCatalystEnvironment() const {
542    return getEnvironment() == Triple::MacABI;
543  }
544
545  /// Returns true for targets that run on a macOS machine.
546  bool isTargetMachineMac() const {
547    return isMacOSX() || (isOSDarwin() && (isSimulatorEnvironment() ||
548                                           isMacCatalystEnvironment()));
549  }
550
551  bool isOSNetBSD() const {
552    return getOS() == Triple::NetBSD;
553  }
554
555  bool isOSOpenBSD() const {
556    return getOS() == Triple::OpenBSD;
557  }
558
559  bool isOSFreeBSD() const {
560    return getOS() == Triple::FreeBSD;
561  }
562
563  bool isOSFuchsia() const {
564    return getOS() == Triple::Fuchsia;
565  }
566
567  bool isOSDragonFly() const { return getOS() == Triple::DragonFly; }
568
569  bool isOSSolaris() const {
570    return getOS() == Triple::Solaris;
571  }
572
573  bool isOSIAMCU() const {
574    return getOS() == Triple::ELFIAMCU;
575  }
576
577  bool isOSUnknown() const { return getOS() == Triple::UnknownOS; }
578
579  bool isGNUEnvironment() const {
580    EnvironmentType Env = getEnvironment();
581    return Env == Triple::GNU || Env == Triple::GNUABIN32 ||
582           Env == Triple::GNUABI64 || Env == Triple::GNUEABI ||
583           Env == Triple::GNUEABIHF || Env == Triple::GNUF32 ||
584           Env == Triple::GNUF64 || Env == Triple::GNUSF ||
585           Env == Triple::GNUX32;
586  }
587
588  /// Tests whether the OS is Haiku.
589  bool isOSHaiku() const {
590    return getOS() == Triple::Haiku;
591  }
592
593  /// Tests whether the OS is UEFI.
594  bool isUEFI() const {
595    return getOS() == Triple::UEFI;
596  }
597
598  /// Tests whether the OS is Windows.
599  bool isOSWindows() const {
600    return getOS() == Triple::Win32;
601  }
602
603  /// Checks if the environment is MSVC.
604  bool isKnownWindowsMSVCEnvironment() const {
605    return isOSWindows() && getEnvironment() == Triple::MSVC;
606  }
607
608  /// Checks if the environment could be MSVC.
609  bool isWindowsMSVCEnvironment() const {
610    return isKnownWindowsMSVCEnvironment() ||
611           (isOSWindows() && getEnvironment() == Triple::UnknownEnvironment);
612  }
613
614  // Checks if we're using the Windows Arm64EC ABI.
615  bool isWindowsArm64EC() const {
616    return getArch() == Triple::aarch64 &&
617           getSubArch() == Triple::AArch64SubArch_arm64ec;
618  }
619
620  bool isWindowsCoreCLREnvironment() const {
621    return isOSWindows() && getEnvironment() == Triple::CoreCLR;
622  }
623
624  bool isWindowsItaniumEnvironment() const {
625    return isOSWindows() && getEnvironment() == Triple::Itanium;
626  }
627
628  bool isWindowsCygwinEnvironment() const {
629    return isOSWindows() && getEnvironment() == Triple::Cygnus;
630  }
631
632  bool isWindowsGNUEnvironment() const {
633    return isOSWindows() && getEnvironment() == Triple::GNU;
634  }
635
636  /// Tests for either Cygwin or MinGW OS
637  bool isOSCygMing() const {
638    return isWindowsCygwinEnvironment() || isWindowsGNUEnvironment();
639  }
640
641  /// Is this a "Windows" OS targeting a "MSVCRT.dll" environment.
642  bool isOSMSVCRT() const {
643    return isWindowsMSVCEnvironment() || isWindowsGNUEnvironment() ||
644           isWindowsItaniumEnvironment();
645  }
646
647  /// Tests whether the OS is NaCl (Native Client)
648  bool isOSNaCl() const {
649    return getOS() == Triple::NaCl;
650  }
651
652  /// Tests whether the OS is Linux.
653  bool isOSLinux() const {
654    return getOS() == Triple::Linux;
655  }
656
657  /// Tests whether the OS is kFreeBSD.
658  bool isOSKFreeBSD() const {
659    return getOS() == Triple::KFreeBSD;
660  }
661
662  /// Tests whether the OS is Hurd.
663  bool isOSHurd() const {
664    return getOS() == Triple::Hurd;
665  }
666
667  /// Tests whether the OS is WASI.
668  bool isOSWASI() const {
669    return getOS() == Triple::WASI;
670  }
671
672  /// Tests whether the OS is Emscripten.
673  bool isOSEmscripten() const {
674    return getOS() == Triple::Emscripten;
675  }
676
677  /// Tests whether the OS uses glibc.
678  bool isOSGlibc() const {
679    return (getOS() == Triple::Linux || getOS() == Triple::KFreeBSD ||
680            getOS() == Triple::Hurd) &&
681           !isAndroid();
682  }
683
684  /// Tests whether the OS is AIX.
685  bool isOSAIX() const {
686    return getOS() == Triple::AIX;
687  }
688
689  bool isOSSerenity() const {
690    return getOS() == Triple::Serenity;
691  }
692
693  /// Tests whether the OS uses the ELF binary format.
694  bool isOSBinFormatELF() const {
695    return getObjectFormat() == Triple::ELF;
696  }
697
698  /// Tests whether the OS uses the COFF binary format.
699  bool isOSBinFormatCOFF() const {
700    return getObjectFormat() == Triple::COFF;
701  }
702
703  /// Tests whether the OS uses the GOFF binary format.
704  bool isOSBinFormatGOFF() const { return getObjectFormat() == Triple::GOFF; }
705
706  /// Tests whether the environment is MachO.
707  bool isOSBinFormatMachO() const {
708    return getObjectFormat() == Triple::MachO;
709  }
710
711  /// Tests whether the OS uses the Wasm binary format.
712  bool isOSBinFormatWasm() const {
713    return getObjectFormat() == Triple::Wasm;
714  }
715
716  /// Tests whether the OS uses the XCOFF binary format.
717  bool isOSBinFormatXCOFF() const {
718    return getObjectFormat() == Triple::XCOFF;
719  }
720
721  /// Tests whether the OS uses the DXContainer binary format.
722  bool isOSBinFormatDXContainer() const {
723    return getObjectFormat() == Triple::DXContainer;
724  }
725
726  /// Tests whether the target is the PS4 platform.
727  bool isPS4() const {
728    return getArch() == Triple::x86_64 &&
729           getVendor() == Triple::SCEI &&
730           getOS() == Triple::PS4;
731  }
732
733  /// Tests whether the target is the PS5 platform.
734  bool isPS5() const {
735    return getArch() == Triple::x86_64 &&
736      getVendor() == Triple::SCEI &&
737      getOS() == Triple::PS5;
738  }
739
740  /// Tests whether the target is the PS4 or PS5 platform.
741  bool isPS() const { return isPS4() || isPS5(); }
742
743  /// Tests whether the target is Android
744  bool isAndroid() const { return getEnvironment() == Triple::Android; }
745
746  bool isAndroidVersionLT(unsigned Major) const {
747    assert(isAndroid() && "Not an Android triple!");
748
749    VersionTuple Version = getEnvironmentVersion();
750
751    // 64-bit targets did not exist before API level 21 (Lollipop).
752    if (isArch64Bit() && Version.getMajor() < 21)
753      return VersionTuple(21) < VersionTuple(Major);
754
755    return Version < VersionTuple(Major);
756  }
757
758  /// Tests whether the environment is musl-libc
759  bool isMusl() const {
760    return getEnvironment() == Triple::Musl ||
761           getEnvironment() == Triple::MuslEABI ||
762           getEnvironment() == Triple::MuslEABIHF ||
763           getEnvironment() == Triple::MuslX32 ||
764           getEnvironment() == Triple::OpenHOS || isOSLiteOS();
765  }
766
767  /// Tests whether the target is OHOS
768  /// LiteOS default enviroment is also OHOS, but omited on triple.
769  bool isOHOSFamily() const { return isOpenHOS() || isOSLiteOS(); }
770
771  bool isOpenHOS() const { return getEnvironment() == Triple::OpenHOS; }
772
773  bool isOSLiteOS() const { return getOS() == Triple::LiteOS; }
774
775  /// Tests whether the target is DXIL.
776  bool isDXIL() const {
777    return getArch() == Triple::dxil;
778  }
779
780  bool isShaderModelOS() const {
781    return getOS() == Triple::ShaderModel;
782  }
783
784  bool isVulkanOS() const { return getOS() == Triple::Vulkan; }
785
786  bool isShaderStageEnvironment() const {
787    EnvironmentType Env = getEnvironment();
788    return Env == Triple::Pixel || Env == Triple::Vertex ||
789           Env == Triple::Geometry || Env == Triple::Hull ||
790           Env == Triple::Domain || Env == Triple::Compute ||
791           Env == Triple::Library || Env == Triple::RayGeneration ||
792           Env == Triple::Intersection || Env == Triple::AnyHit ||
793           Env == Triple::ClosestHit || Env == Triple::Miss ||
794           Env == Triple::Callable || Env == Triple::Mesh ||
795           Env == Triple::Amplification;
796  }
797
798  /// Tests whether the target is SPIR (32- or 64-bit).
799  bool isSPIR() const {
800    return getArch() == Triple::spir || getArch() == Triple::spir64;
801  }
802
803  /// Tests whether the target is SPIR-V (32/64-bit/Logical).
804  bool isSPIRV() const {
805    return getArch() == Triple::spirv32 || getArch() == Triple::spirv64 ||
806           getArch() == Triple::spirv;
807  }
808
809  /// Tests whether the target is SPIR-V Logical
810  bool isSPIRVLogical() const {
811    return getArch() == Triple::spirv;
812  }
813
814  /// Tests whether the target is NVPTX (32- or 64-bit).
815  bool isNVPTX() const {
816    return getArch() == Triple::nvptx || getArch() == Triple::nvptx64;
817  }
818
819  /// Tests whether the target is AMDGCN
820  bool isAMDGCN() const { return getArch() == Triple::amdgcn; }
821
822  bool isAMDGPU() const {
823    return getArch() == Triple::r600 || getArch() == Triple::amdgcn;
824  }
825
826  /// Tests whether the target is Thumb (little and big endian).
827  bool isThumb() const {
828    return getArch() == Triple::thumb || getArch() == Triple::thumbeb;
829  }
830
831  /// Tests whether the target is ARM (little and big endian).
832  bool isARM() const {
833    return getArch() == Triple::arm || getArch() == Triple::armeb;
834  }
835
836  /// Tests whether the target supports the EHABI exception
837  /// handling standard.
838  bool isTargetEHABICompatible() const {
839    return (isARM() || isThumb()) &&
840           (getEnvironment() == Triple::EABI ||
841            getEnvironment() == Triple::GNUEABI ||
842            getEnvironment() == Triple::MuslEABI ||
843            getEnvironment() == Triple::EABIHF ||
844            getEnvironment() == Triple::GNUEABIHF ||
845            getEnvironment() == Triple::OpenHOS ||
846            getEnvironment() == Triple::MuslEABIHF || isAndroid()) &&
847           isOSBinFormatELF();
848  }
849
850  /// Tests whether the target is T32.
851  bool isArmT32() const {
852    switch (getSubArch()) {
853    case Triple::ARMSubArch_v8m_baseline:
854    case Triple::ARMSubArch_v7s:
855    case Triple::ARMSubArch_v7k:
856    case Triple::ARMSubArch_v7ve:
857    case Triple::ARMSubArch_v6:
858    case Triple::ARMSubArch_v6m:
859    case Triple::ARMSubArch_v6k:
860    case Triple::ARMSubArch_v6t2:
861    case Triple::ARMSubArch_v5:
862    case Triple::ARMSubArch_v5te:
863    case Triple::ARMSubArch_v4t:
864      return false;
865    default:
866      return true;
867    }
868  }
869
870  /// Tests whether the target is an M-class.
871  bool isArmMClass() const {
872    switch (getSubArch()) {
873    case Triple::ARMSubArch_v6m:
874    case Triple::ARMSubArch_v7m:
875    case Triple::ARMSubArch_v7em:
876    case Triple::ARMSubArch_v8m_mainline:
877    case Triple::ARMSubArch_v8m_baseline:
878    case Triple::ARMSubArch_v8_1m_mainline:
879      return true;
880    default:
881      return false;
882    }
883  }
884
885  /// Tests whether the target is AArch64 (little and big endian).
886  bool isAArch64() const {
887    return getArch() == Triple::aarch64 || getArch() == Triple::aarch64_be ||
888           getArch() == Triple::aarch64_32;
889  }
890
891  /// Tests whether the target is AArch64 and pointers are the size specified by
892  /// \p PointerWidth.
893  bool isAArch64(int PointerWidth) const {
894    assert(PointerWidth == 64 || PointerWidth == 32);
895    if (!isAArch64())
896      return false;
897    return getArch() == Triple::aarch64_32 ||
898                   getEnvironment() == Triple::GNUILP32
899               ? PointerWidth == 32
900               : PointerWidth == 64;
901  }
902
903  /// Tests whether the target is 32-bit LoongArch.
904  bool isLoongArch32() const { return getArch() == Triple::loongarch32; }
905
906  /// Tests whether the target is 64-bit LoongArch.
907  bool isLoongArch64() const { return getArch() == Triple::loongarch64; }
908
909  /// Tests whether the target is LoongArch (32- and 64-bit).
910  bool isLoongArch() const { return isLoongArch32() || isLoongArch64(); }
911
912  /// Tests whether the target is MIPS 32-bit (little and big endian).
913  bool isMIPS32() const {
914    return getArch() == Triple::mips || getArch() == Triple::mipsel;
915  }
916
917  /// Tests whether the target is MIPS 64-bit (little and big endian).
918  bool isMIPS64() const {
919    return getArch() == Triple::mips64 || getArch() == Triple::mips64el;
920  }
921
922  /// Tests whether the target is MIPS (little and big endian, 32- or 64-bit).
923  bool isMIPS() const {
924    return isMIPS32() || isMIPS64();
925  }
926
927  /// Tests whether the target is PowerPC (32- or 64-bit LE or BE).
928  bool isPPC() const {
929    return getArch() == Triple::ppc || getArch() == Triple::ppc64 ||
930           getArch() == Triple::ppcle || getArch() == Triple::ppc64le;
931  }
932
933  /// Tests whether the target is 32-bit PowerPC (little and big endian).
934  bool isPPC32() const {
935    return getArch() == Triple::ppc || getArch() == Triple::ppcle;
936  }
937
938  /// Tests whether the target is 64-bit PowerPC (little and big endian).
939  bool isPPC64() const {
940    return getArch() == Triple::ppc64 || getArch() == Triple::ppc64le;
941  }
942
943  /// Tests whether the target 64-bit PowerPC big endian ABI is ELFv2.
944  bool isPPC64ELFv2ABI() const {
945    return (getArch() == Triple::ppc64 &&
946            ((getOS() == Triple::FreeBSD &&
947              (getOSMajorVersion() >= 13 || getOSVersion().empty())) ||
948             getOS() == Triple::OpenBSD || isMusl()));
949  }
950
951  /// Tests whether the target 32-bit PowerPC uses Secure PLT.
952  bool isPPC32SecurePlt() const {
953    return ((getArch() == Triple::ppc || getArch() == Triple::ppcle) &&
954            ((getOS() == Triple::FreeBSD &&
955              (getOSMajorVersion() >= 13 || getOSVersion().empty())) ||
956             getOS() == Triple::NetBSD || getOS() == Triple::OpenBSD ||
957             isMusl()));
958  }
959
960  /// Tests whether the target is 32-bit RISC-V.
961  bool isRISCV32() const { return getArch() == Triple::riscv32; }
962
963  /// Tests whether the target is 64-bit RISC-V.
964  bool isRISCV64() const { return getArch() == Triple::riscv64; }
965
966  /// Tests whether the target is RISC-V (32- and 64-bit).
967  bool isRISCV() const { return isRISCV32() || isRISCV64(); }
968
969  /// Tests whether the target is 32-bit SPARC (little and big endian).
970  bool isSPARC32() const {
971    return getArch() == Triple::sparc || getArch() == Triple::sparcel;
972  }
973
974  /// Tests whether the target is 64-bit SPARC (big endian).
975  bool isSPARC64() const { return getArch() == Triple::sparcv9; }
976
977  /// Tests whether the target is SPARC.
978  bool isSPARC() const { return isSPARC32() || isSPARC64(); }
979
980  /// Tests whether the target is SystemZ.
981  bool isSystemZ() const {
982    return getArch() == Triple::systemz;
983  }
984
985  /// Tests whether the target is x86 (32- or 64-bit).
986  bool isX86() const {
987    return getArch() == Triple::x86 || getArch() == Triple::x86_64;
988  }
989
990  /// Tests whether the target is VE
991  bool isVE() const {
992    return getArch() == Triple::ve;
993  }
994
995  /// Tests whether the target is wasm (32- and 64-bit).
996  bool isWasm() const {
997    return getArch() == Triple::wasm32 || getArch() == Triple::wasm64;
998  }
999
1000  // Tests whether the target is CSKY
1001  bool isCSKY() const {
1002    return getArch() == Triple::csky;
1003  }
1004
1005  /// Tests whether the target is the Apple "arm64e" AArch64 subarch.
1006  bool isArm64e() const {
1007    return getArch() == Triple::aarch64 &&
1008           getSubArch() == Triple::AArch64SubArch_arm64e;
1009  }
1010
1011  /// Tests whether the target is X32.
1012  bool isX32() const {
1013    EnvironmentType Env = getEnvironment();
1014    return Env == Triple::GNUX32 || Env == Triple::MuslX32;
1015  }
1016
1017  /// Tests whether the target is eBPF.
1018  bool isBPF() const {
1019    return getArch() == Triple::bpfel || getArch() == Triple::bpfeb;
1020  }
1021
1022  /// Tests whether the target supports comdat
1023  bool supportsCOMDAT() const {
1024    return !(isOSBinFormatMachO() || isOSBinFormatXCOFF() ||
1025             isOSBinFormatDXContainer());
1026  }
1027
1028  /// Tests whether the target uses emulated TLS as default.
1029  ///
1030  /// Note: Android API level 29 (10) introduced ELF TLS.
1031  bool hasDefaultEmulatedTLS() const {
1032    return (isAndroid() && isAndroidVersionLT(29)) || isOSOpenBSD() ||
1033           isWindowsCygwinEnvironment() || isOHOSFamily();
1034  }
1035
1036  /// True if the target supports both general-dynamic and TLSDESC, and TLSDESC
1037  /// is enabled by default.
1038  bool hasDefaultTLSDESC() const {
1039    // TODO: Improve check for other platforms, like Android, and RISC-V
1040    return false;
1041  }
1042
1043  /// Tests whether the target uses -data-sections as default.
1044  bool hasDefaultDataSections() const {
1045    return isOSBinFormatXCOFF() || isWasm();
1046  }
1047
1048  /// Tests if the environment supports dllimport/export annotations.
1049  bool hasDLLImportExport() const { return isOSWindows() || isPS(); }
1050
1051  /// @}
1052  /// @name Mutators
1053  /// @{
1054
1055  /// Set the architecture (first) component of the triple to a known type.
1056  void setArch(ArchType Kind, SubArchType SubArch = NoSubArch);
1057
1058  /// Set the vendor (second) component of the triple to a known type.
1059  void setVendor(VendorType Kind);
1060
1061  /// Set the operating system (third) component of the triple to a known type.
1062  void setOS(OSType Kind);
1063
1064  /// Set the environment (fourth) component of the triple to a known type.
1065  void setEnvironment(EnvironmentType Kind);
1066
1067  /// Set the object file format.
1068  void setObjectFormat(ObjectFormatType Kind);
1069
1070  /// Set all components to the new triple \p Str.
1071  void setTriple(const Twine &Str);
1072
1073  /// Set the architecture (first) component of the triple by name.
1074  void setArchName(StringRef Str);
1075
1076  /// Set the vendor (second) component of the triple by name.
1077  void setVendorName(StringRef Str);
1078
1079  /// Set the operating system (third) component of the triple by name.
1080  void setOSName(StringRef Str);
1081
1082  /// Set the optional environment (fourth) component of the triple by name.
1083  void setEnvironmentName(StringRef Str);
1084
1085  /// Set the operating system and optional environment components with a single
1086  /// string.
1087  void setOSAndEnvironmentName(StringRef Str);
1088
1089  /// @}
1090  /// @name Helpers to build variants of a particular triple.
1091  /// @{
1092
1093  /// Form a triple with a 32-bit variant of the current architecture.
1094  ///
1095  /// This can be used to move across "families" of architectures where useful.
1096  ///
1097  /// \returns A new triple with a 32-bit architecture or an unknown
1098  ///          architecture if no such variant can be found.
1099  llvm::Triple get32BitArchVariant() const;
1100
1101  /// Form a triple with a 64-bit variant of the current architecture.
1102  ///
1103  /// This can be used to move across "families" of architectures where useful.
1104  ///
1105  /// \returns A new triple with a 64-bit architecture or an unknown
1106  ///          architecture if no such variant can be found.
1107  llvm::Triple get64BitArchVariant() const;
1108
1109  /// Form a triple with a big endian variant of the current architecture.
1110  ///
1111  /// This can be used to move across "families" of architectures where useful.
1112  ///
1113  /// \returns A new triple with a big endian architecture or an unknown
1114  ///          architecture if no such variant can be found.
1115  llvm::Triple getBigEndianArchVariant() const;
1116
1117  /// Form a triple with a little endian variant of the current architecture.
1118  ///
1119  /// This can be used to move across "families" of architectures where useful.
1120  ///
1121  /// \returns A new triple with a little endian architecture or an unknown
1122  ///          architecture if no such variant can be found.
1123  llvm::Triple getLittleEndianArchVariant() const;
1124
1125  /// Tests whether the target triple is little endian.
1126  ///
1127  /// \returns true if the triple is little endian, false otherwise.
1128  bool isLittleEndian() const;
1129
1130  /// Test whether target triples are compatible.
1131  bool isCompatibleWith(const Triple &Other) const;
1132
1133  /// Merge target triples.
1134  std::string merge(const Triple &Other) const;
1135
1136  /// Some platforms have different minimum supported OS versions that
1137  /// varies by the architecture specified in the triple. This function
1138  /// returns the minimum supported OS version for this triple if one an exists,
1139  /// or an invalid version tuple if this triple doesn't have one.
1140  VersionTuple getMinimumSupportedOSVersion() const;
1141
1142  /// @}
1143  /// @name Static helpers for IDs.
1144  /// @{
1145
1146  /// Get the canonical name for the \p Kind architecture.
1147  static StringRef getArchTypeName(ArchType Kind);
1148
1149  /// Get the architecture name based on \p Kind and \p SubArch.
1150  static StringRef getArchName(ArchType Kind, SubArchType SubArch = NoSubArch);
1151
1152  /// Get the "prefix" canonical name for the \p Kind architecture. This is the
1153  /// prefix used by the architecture specific builtins, and is suitable for
1154  /// passing to \see Intrinsic::getIntrinsicForClangBuiltin().
1155  ///
1156  /// \return - The architecture prefix, or 0 if none is defined.
1157  static StringRef getArchTypePrefix(ArchType Kind);
1158
1159  /// Get the canonical name for the \p Kind vendor.
1160  static StringRef getVendorTypeName(VendorType Kind);
1161
1162  /// Get the canonical name for the \p Kind operating system.
1163  static StringRef getOSTypeName(OSType Kind);
1164
1165  /// Get the canonical name for the \p Kind environment.
1166  static StringRef getEnvironmentTypeName(EnvironmentType Kind);
1167
1168  /// Get the name for the \p Object format.
1169  static StringRef getObjectFormatTypeName(ObjectFormatType ObjectFormat);
1170
1171  /// @}
1172  /// @name Static helpers for converting alternate architecture names.
1173  /// @{
1174
1175  /// The canonical type for the given LLVM architecture name (e.g., "x86").
1176  static ArchType getArchTypeForLLVMName(StringRef Str);
1177
1178  /// @}
1179
1180  /// Returns a canonicalized OS version number for the specified OS.
1181  static VersionTuple getCanonicalVersionForOS(OSType OSKind,
1182                                               const VersionTuple &Version);
1183};
1184
1185} // End llvm namespace
1186
1187
1188#endif
1189