1 //===-- llvm/ADT/Triple.h - Target triple helper class ----------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #ifndef LLVM_ADT_TRIPLE_H
11 #define LLVM_ADT_TRIPLE_H
12 
13 #include "llvm/ADT/Twine.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 
21 namespace 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.
44 class Triple {
45 public:
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     bpf,        // eBPF or extended BPF or 64-bit BPF (little endian)
54     hexagon,    // Hexagon: hexagon
55     mips,       // MIPS: mips, mipsallegrex
56     mipsel,     // MIPSEL: mipsel, mipsallegrexel
57     mips64,     // MIPS64: mips64
58     mips64el,   // MIPS64EL: mips64el
59     msp430,     // MSP430: msp430
60     ppc,        // PPC: powerpc
61     ppc64,      // PPC64: powerpc64, ppu
62     ppc64le,    // PPC64LE: powerpc64le
63     r600,       // R600: AMD GPUs HD2XXX - HD6XXX
64     amdgcn,     // AMDGCN: AMD GCN GPUs
65     sparc,      // Sparc: sparc
66     sparcv9,    // Sparcv9: Sparcv9
67     systemz,    // SystemZ: s390x
68     tce,        // TCE (http://tce.cs.tut.fi/): tce
69     thumb,      // Thumb (little endian): thumb, thumbv.*
70     thumbeb,    // Thumb (big endian): thumbeb
71     x86,        // X86: i[3-9]86
72     x86_64,     // X86-64: amd64, x86_64
73     xcore,      // XCore: xcore
74     nvptx,      // NVPTX: 32-bit
75     nvptx64,    // NVPTX: 64-bit
76     le32,       // le32: generic little-endian 32-bit CPU (PNaCl / Emscripten)
77     le64,       // le64: generic little-endian 64-bit CPU (PNaCl / Emscripten)
78     amdil,      // AMDIL
79     amdil64,    // AMDIL with 64-bit pointers
80     hsail,      // AMD HSAIL
81     hsail64,    // AMD HSAIL with 64-bit pointers
82     spir,       // SPIR: standard portable IR for OpenCL 32-bit version
83     spir64,     // SPIR: standard portable IR for OpenCL 64-bit version
84     kalimba     // Kalimba: generic kalimba
85   };
86   enum SubArchType {
87     NoSubArch,
88 
89     ARMSubArch_v8_1a,
90     ARMSubArch_v8,
91     ARMSubArch_v7,
92     ARMSubArch_v7em,
93     ARMSubArch_v7m,
94     ARMSubArch_v7s,
95     ARMSubArch_v6,
96     ARMSubArch_v6m,
97     ARMSubArch_v6k,
98     ARMSubArch_v6t2,
99     ARMSubArch_v5,
100     ARMSubArch_v5te,
101     ARMSubArch_v4t,
102 
103     KalimbaSubArch_v3,
104     KalimbaSubArch_v4,
105     KalimbaSubArch_v5
106   };
107   enum VendorType {
108     UnknownVendor,
109 
110     Apple,
111     PC,
112     SCEI,
113     BGP,
114     BGQ,
115     Freescale,
116     IBM,
117     ImaginationTechnologies,
118     MipsTechnologies,
119     NVIDIA,
120     CSR
121   };
122   enum OSType {
123     UnknownOS,
124 
125     CloudABI,
126     Darwin,
127     DragonFly,
128     FreeBSD,
129     IOS,
130     KFreeBSD,
131     Linux,
132     Lv2,        // PS3
133     MacOSX,
134     NetBSD,
135     OpenBSD,
136     Solaris,
137     Win32,
138     Haiku,
139     Minix,
140     RTEMS,
141     NaCl,       // Native Client
142     CNK,        // BG/P Compute-Node Kernel
143     Bitrig,
144     AIX,
145     CUDA,       // NVIDIA CUDA
146     NVCL,       // NVIDIA OpenCL
147     AMDHSA,     // AMD HSA Runtime
148     PS4
149   };
150   enum EnvironmentType {
151     UnknownEnvironment,
152 
153     GNU,
154     GNUEABI,
155     GNUEABIHF,
156     GNUX32,
157     CODE16,
158     EABI,
159     EABIHF,
160     Android,
161 
162     MSVC,
163     Itanium,
164     Cygnus,
165   };
166   enum ObjectFormatType {
167     UnknownObjectFormat,
168 
169     COFF,
170     ELF,
171     MachO,
172   };
173 
174 private:
175   std::string Data;
176 
177   /// The parsed arch type.
178   ArchType Arch;
179 
180   /// The parsed subarchitecture type.
181   SubArchType SubArch;
182 
183   /// The parsed vendor type.
184   VendorType Vendor;
185 
186   /// The parsed OS type.
187   OSType OS;
188 
189   /// The parsed Environment type.
190   EnvironmentType Environment;
191 
192   /// The object format type.
193   ObjectFormatType ObjectFormat;
194 
195 public:
196   /// @name Constructors
197   /// @{
198 
199   /// \brief Default constructor is the same as an empty string and leaves all
200   /// triple fields unknown.
Triple()201   Triple() : Data(), Arch(), Vendor(), OS(), Environment(), ObjectFormat() {}
202 
203   explicit Triple(const Twine &Str);
204   Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr);
205   Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr,
206          const Twine &EnvironmentStr);
207 
208   bool operator==(const Triple &Other) const {
209     return Arch == Other.Arch && SubArch == Other.SubArch &&
210            Vendor == Other.Vendor && OS == Other.OS &&
211            Environment == Other.Environment &&
212            ObjectFormat == Other.ObjectFormat;
213   }
214 
215   /// @}
216   /// @name Normalization
217   /// @{
218 
219   /// normalize - Turn an arbitrary machine specification into the canonical
220   /// triple form (or something sensible that the Triple class understands if
221   /// nothing better can reasonably be done).  In particular, it handles the
222   /// common case in which otherwise valid components are in the wrong order.
223   static std::string normalize(StringRef Str);
224 
225   /// \brief Return the normalized form of this triple's string.
normalize()226   std::string normalize() const { return normalize(Data); }
227 
228   /// @}
229   /// @name Typed Component Access
230   /// @{
231 
232   /// getArch - Get the parsed architecture type of this triple.
getArch()233   ArchType getArch() const { return Arch; }
234 
235   /// getSubArch - get the parsed subarchitecture type for this triple.
getSubArch()236   SubArchType getSubArch() const { return SubArch; }
237 
238   /// getVendor - Get the parsed vendor type of this triple.
getVendor()239   VendorType getVendor() const { return Vendor; }
240 
241   /// getOS - Get the parsed operating system type of this triple.
getOS()242   OSType getOS() const { return OS; }
243 
244   /// hasEnvironment - Does this triple have the optional environment
245   /// (fourth) component?
hasEnvironment()246   bool hasEnvironment() const {
247     return getEnvironmentName() != "";
248   }
249 
250   /// getEnvironment - Get the parsed environment type of this triple.
getEnvironment()251   EnvironmentType getEnvironment() const { return Environment; }
252 
253   /// getFormat - Get the object format for this triple.
getObjectFormat()254   ObjectFormatType getObjectFormat() const { return ObjectFormat; }
255 
256   /// getOSVersion - Parse the version number from the OS name component of the
257   /// triple, if present.
258   ///
259   /// For example, "fooos1.2.3" would return (1, 2, 3).
260   ///
261   /// If an entry is not defined, it will be returned as 0.
262   void getOSVersion(unsigned &Major, unsigned &Minor, unsigned &Micro) const;
263 
264   /// getOSMajorVersion - Return just the major version number, this is
265   /// specialized because it is a common query.
getOSMajorVersion()266   unsigned getOSMajorVersion() const {
267     unsigned Maj, Min, Micro;
268     getOSVersion(Maj, Min, Micro);
269     return Maj;
270   }
271 
272   /// getMacOSXVersion - Parse the version number as with getOSVersion and then
273   /// translate generic "darwin" versions to the corresponding OS X versions.
274   /// This may also be called with IOS triples but the OS X version number is
275   /// just set to a constant 10.4.0 in that case.  Returns true if successful.
276   bool getMacOSXVersion(unsigned &Major, unsigned &Minor,
277                         unsigned &Micro) const;
278 
279   /// getiOSVersion - Parse the version number as with getOSVersion.  This should
280   /// only be called with IOS triples.
281   void getiOSVersion(unsigned &Major, unsigned &Minor,
282                      unsigned &Micro) const;
283 
284   /// @}
285   /// @name Direct Component Access
286   /// @{
287 
str()288   const std::string &str() const { return Data; }
289 
getTriple()290   const std::string &getTriple() const { return Data; }
291 
292   /// getArchName - Get the architecture (first) component of the
293   /// triple.
294   StringRef getArchName() const;
295 
296   /// getVendorName - Get the vendor (second) component of the triple.
297   StringRef getVendorName() const;
298 
299   /// getOSName - Get the operating system (third) component of the
300   /// triple.
301   StringRef getOSName() const;
302 
303   /// getEnvironmentName - Get the optional environment (fourth)
304   /// component of the triple, or "" if empty.
305   StringRef getEnvironmentName() const;
306 
307   /// getOSAndEnvironmentName - Get the operating system and optional
308   /// environment components as a single string (separated by a '-'
309   /// if the environment component is present).
310   StringRef getOSAndEnvironmentName() const;
311 
312   /// @}
313   /// @name Convenience Predicates
314   /// @{
315 
316   /// \brief Test whether the architecture is 64-bit
317   ///
318   /// Note that this tests for 64-bit pointer width, and nothing else. Note
319   /// that we intentionally expose only three predicates, 64-bit, 32-bit, and
320   /// 16-bit. The inner details of pointer width for particular architectures
321   /// is not summed up in the triple, and so only a coarse grained predicate
322   /// system is provided.
323   bool isArch64Bit() const;
324 
325   /// \brief Test whether the architecture is 32-bit
326   ///
327   /// Note that this tests for 32-bit pointer width, and nothing else.
328   bool isArch32Bit() const;
329 
330   /// \brief Test whether the architecture is 16-bit
331   ///
332   /// Note that this tests for 16-bit pointer width, and nothing else.
333   bool isArch16Bit() const;
334 
335   /// isOSVersionLT - Helper function for doing comparisons against version
336   /// numbers included in the target triple.
337   bool isOSVersionLT(unsigned Major, unsigned Minor = 0,
338                      unsigned Micro = 0) const {
339     unsigned LHS[3];
340     getOSVersion(LHS[0], LHS[1], LHS[2]);
341 
342     if (LHS[0] != Major)
343       return LHS[0] < Major;
344     if (LHS[1] != Minor)
345       return LHS[1] < Minor;
346     if (LHS[2] != Micro)
347       return LHS[1] < Micro;
348 
349     return false;
350   }
351 
isOSVersionLT(const Triple & Other)352   bool isOSVersionLT(const Triple &Other) const {
353     unsigned RHS[3];
354     Other.getOSVersion(RHS[0], RHS[1], RHS[2]);
355     return isOSVersionLT(RHS[0], RHS[1], RHS[2]);
356   }
357 
358   /// isMacOSXVersionLT - Comparison function for checking OS X version
359   /// compatibility, which handles supporting skewed version numbering schemes
360   /// used by the "darwin" triples.
361   unsigned isMacOSXVersionLT(unsigned Major, unsigned Minor = 0,
362                              unsigned Micro = 0) const {
363     assert(isMacOSX() && "Not an OS X triple!");
364 
365     // If this is OS X, expect a sane version number.
366     if (getOS() == Triple::MacOSX)
367       return isOSVersionLT(Major, Minor, Micro);
368 
369     // Otherwise, compare to the "Darwin" number.
370     assert(Major == 10 && "Unexpected major version");
371     return isOSVersionLT(Minor + 4, Micro, 0);
372   }
373 
374   /// isMacOSX - Is this a Mac OS X triple. For legacy reasons, we support both
375   /// "darwin" and "osx" as OS X triples.
isMacOSX()376   bool isMacOSX() const {
377     return getOS() == Triple::Darwin || getOS() == Triple::MacOSX;
378   }
379 
380   /// Is this an iOS triple.
isiOS()381   bool isiOS() const {
382     return getOS() == Triple::IOS;
383   }
384 
385   /// isOSDarwin - Is this a "Darwin" OS (OS X or iOS).
isOSDarwin()386   bool isOSDarwin() const {
387     return isMacOSX() || isiOS();
388   }
389 
isOSNetBSD()390   bool isOSNetBSD() const {
391     return getOS() == Triple::NetBSD;
392   }
393 
isOSOpenBSD()394   bool isOSOpenBSD() const {
395     return getOS() == Triple::OpenBSD;
396   }
397 
isOSFreeBSD()398   bool isOSFreeBSD() const {
399     return getOS() == Triple::FreeBSD;
400   }
401 
isOSDragonFly()402   bool isOSDragonFly() const { return getOS() == Triple::DragonFly; }
403 
isOSSolaris()404   bool isOSSolaris() const {
405     return getOS() == Triple::Solaris;
406   }
407 
isOSBitrig()408   bool isOSBitrig() const {
409     return getOS() == Triple::Bitrig;
410   }
411 
isWindowsMSVCEnvironment()412   bool isWindowsMSVCEnvironment() const {
413     return getOS() == Triple::Win32 &&
414            (getEnvironment() == Triple::UnknownEnvironment ||
415             getEnvironment() == Triple::MSVC);
416   }
417 
isKnownWindowsMSVCEnvironment()418   bool isKnownWindowsMSVCEnvironment() const {
419     return getOS() == Triple::Win32 && getEnvironment() == Triple::MSVC;
420   }
421 
isWindowsItaniumEnvironment()422   bool isWindowsItaniumEnvironment() const {
423     return getOS() == Triple::Win32 && getEnvironment() == Triple::Itanium;
424   }
425 
isWindowsCygwinEnvironment()426   bool isWindowsCygwinEnvironment() const {
427     return getOS() == Triple::Win32 && getEnvironment() == Triple::Cygnus;
428   }
429 
isWindowsGNUEnvironment()430   bool isWindowsGNUEnvironment() const {
431     return getOS() == Triple::Win32 && getEnvironment() == Triple::GNU;
432   }
433 
434   /// \brief Tests for either Cygwin or MinGW OS
isOSCygMing()435   bool isOSCygMing() const {
436     return isWindowsCygwinEnvironment() || isWindowsGNUEnvironment();
437   }
438 
439   /// \brief Is this a "Windows" OS targeting a "MSVCRT.dll" environment.
isOSMSVCRT()440   bool isOSMSVCRT() const {
441     return isWindowsMSVCEnvironment() || isWindowsGNUEnvironment() ||
442            isWindowsItaniumEnvironment();
443   }
444 
445   /// \brief Tests whether the OS is Windows.
isOSWindows()446   bool isOSWindows() const {
447     return getOS() == Triple::Win32;
448   }
449 
450   /// \brief Tests whether the OS is NaCl (Native Client)
isOSNaCl()451   bool isOSNaCl() const {
452     return getOS() == Triple::NaCl;
453   }
454 
455   /// \brief Tests whether the OS is Linux.
isOSLinux()456   bool isOSLinux() const {
457     return getOS() == Triple::Linux;
458   }
459 
460   /// \brief Tests whether the OS uses the ELF binary format.
isOSBinFormatELF()461   bool isOSBinFormatELF() const {
462     return getObjectFormat() == Triple::ELF;
463   }
464 
465   /// \brief Tests whether the OS uses the COFF binary format.
isOSBinFormatCOFF()466   bool isOSBinFormatCOFF() const {
467     return getObjectFormat() == Triple::COFF;
468   }
469 
470   /// \brief Tests whether the environment is MachO.
isOSBinFormatMachO()471   bool isOSBinFormatMachO() const {
472     return getObjectFormat() == Triple::MachO;
473   }
474 
475   /// \brief Tests whether the target is the PS4 CPU
isPS4CPU()476   bool isPS4CPU() const {
477     return getArch() == Triple::x86_64 &&
478            getVendor() == Triple::SCEI &&
479            getOS() == Triple::PS4;
480   }
481 
482   /// \brief Tests whether the target is the PS4 platform
isPS4()483   bool isPS4() const {
484     return getVendor() == Triple::SCEI &&
485            getOS() == Triple::PS4;
486   }
487 
488   /// @}
489   /// @name Mutators
490   /// @{
491 
492   /// setArch - Set the architecture (first) component of the triple
493   /// to a known type.
494   void setArch(ArchType Kind);
495 
496   /// setVendor - Set the vendor (second) component of the triple to a
497   /// known type.
498   void setVendor(VendorType Kind);
499 
500   /// setOS - Set the operating system (third) component of the triple
501   /// to a known type.
502   void setOS(OSType Kind);
503 
504   /// setEnvironment - Set the environment (fourth) component of the triple
505   /// to a known type.
506   void setEnvironment(EnvironmentType Kind);
507 
508   /// setObjectFormat - Set the object file format
509   void setObjectFormat(ObjectFormatType Kind);
510 
511   /// setTriple - Set all components to the new triple \p Str.
512   void setTriple(const Twine &Str);
513 
514   /// setArchName - Set the architecture (first) component of the
515   /// triple by name.
516   void setArchName(StringRef Str);
517 
518   /// setVendorName - Set the vendor (second) component of the triple
519   /// by name.
520   void setVendorName(StringRef Str);
521 
522   /// setOSName - Set the operating system (third) component of the
523   /// triple by name.
524   void setOSName(StringRef Str);
525 
526   /// setEnvironmentName - Set the optional environment (fourth)
527   /// component of the triple by name.
528   void setEnvironmentName(StringRef Str);
529 
530   /// setOSAndEnvironmentName - Set the operating system and optional
531   /// environment components with a single string.
532   void setOSAndEnvironmentName(StringRef Str);
533 
534   /// @}
535   /// @name Helpers to build variants of a particular triple.
536   /// @{
537 
538   /// \brief Form a triple with a 32-bit variant of the current architecture.
539   ///
540   /// This can be used to move across "families" of architectures where useful.
541   ///
542   /// \returns A new triple with a 32-bit architecture or an unknown
543   ///          architecture if no such variant can be found.
544   llvm::Triple get32BitArchVariant() const;
545 
546   /// \brief Form a triple with a 64-bit variant of the current architecture.
547   ///
548   /// This can be used to move across "families" of architectures where useful.
549   ///
550   /// \returns A new triple with a 64-bit architecture or an unknown
551   ///          architecture if no such variant can be found.
552   llvm::Triple get64BitArchVariant() const;
553 
554   /// Get the (LLVM) name of the minimum ARM CPU for the arch we are targeting.
555   ///
556   /// \param Arch the architecture name (e.g., "armv7s"). If it is an empty
557   /// string then the triple's arch name is used.
558   const char* getARMCPUForArch(StringRef Arch = StringRef()) const;
559 
560   /// @}
561   /// @name Static helpers for IDs.
562   /// @{
563 
564   /// getArchTypeName - Get the canonical name for the \p Kind architecture.
565   static const char *getArchTypeName(ArchType Kind);
566 
567   /// getArchTypePrefix - Get the "prefix" canonical name for the \p Kind
568   /// architecture. This is the prefix used by the architecture specific
569   /// builtins, and is suitable for passing to \see
570   /// Intrinsic::getIntrinsicForGCCBuiltin().
571   ///
572   /// \return - The architecture prefix, or 0 if none is defined.
573   static const char *getArchTypePrefix(ArchType Kind);
574 
575   /// getVendorTypeName - Get the canonical name for the \p Kind vendor.
576   static const char *getVendorTypeName(VendorType Kind);
577 
578   /// getOSTypeName - Get the canonical name for the \p Kind operating system.
579   static const char *getOSTypeName(OSType Kind);
580 
581   /// getEnvironmentTypeName - Get the canonical name for the \p Kind
582   /// environment.
583   static const char *getEnvironmentTypeName(EnvironmentType Kind);
584 
585   /// @}
586   /// @name Static helpers for converting alternate architecture names.
587   /// @{
588 
589   /// getArchTypeForLLVMName - The canonical type for the given LLVM
590   /// architecture name (e.g., "x86").
591   static ArchType getArchTypeForLLVMName(StringRef Str);
592 
593   /// @}
594 };
595 
596 } // End llvm namespace
597 
598 
599 #endif
600