1 //===--- Triple.cpp - Target triple helper class --------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "llvm/ADT/Triple.h"
10 #include "llvm/ADT/STLExtras.h"
11 #include "llvm/ADT/SmallString.h"
12 #include "llvm/ADT/StringSwitch.h"
13 #include "llvm/Support/ErrorHandling.h"
14 #include "llvm/Support/Host.h"
15 #include "llvm/Support/SwapByteOrder.h"
16 #include "llvm/Support/TargetParser.h"
17 #include <cassert>
18 #include <cstring>
19 using namespace llvm;
20 
21 StringRef Triple::getArchTypeName(ArchType Kind) {
22   switch (Kind) {
23   case UnknownArch:    return "unknown";
24 
25   case aarch64:        return "aarch64";
26   case aarch64_32:     return "aarch64_32";
27   case aarch64_be:     return "aarch64_be";
28   case amdgcn:         return "amdgcn";
29   case amdil64:        return "amdil64";
30   case amdil:          return "amdil";
31   case arc:            return "arc";
32   case arm:            return "arm";
33   case armeb:          return "armeb";
34   case avr:            return "avr";
35   case bpfeb:          return "bpfeb";
36   case bpfel:          return "bpfel";
37   case hexagon:        return "hexagon";
38   case hsail64:        return "hsail64";
39   case hsail:          return "hsail";
40   case kalimba:        return "kalimba";
41   case lanai:          return "lanai";
42   case le32:           return "le32";
43   case le64:           return "le64";
44   case mips64:         return "mips64";
45   case mips64el:       return "mips64el";
46   case mips:           return "mips";
47   case mipsel:         return "mipsel";
48   case msp430:         return "msp430";
49   case nvptx64:        return "nvptx64";
50   case nvptx:          return "nvptx";
51   case ppc64:          return "powerpc64";
52   case ppc64le:        return "powerpc64le";
53   case ppc:            return "powerpc";
54   case r600:           return "r600";
55   case renderscript32: return "renderscript32";
56   case renderscript64: return "renderscript64";
57   case riscv32:        return "riscv32";
58   case riscv64:        return "riscv64";
59   case shave:          return "shave";
60   case sparc:          return "sparc";
61   case sparcel:        return "sparcel";
62   case sparcv9:        return "sparcv9";
63   case spir64:         return "spir64";
64   case spir:           return "spir";
65   case systemz:        return "s390x";
66   case tce:            return "tce";
67   case tcele:          return "tcele";
68   case thumb:          return "thumb";
69   case thumbeb:        return "thumbeb";
70   case ve:             return "ve";
71   case wasm32:         return "wasm32";
72   case wasm64:         return "wasm64";
73   case x86:            return "i386";
74   case x86_64:         return "x86_64";
75   case xcore:          return "xcore";
76   }
77 
78   llvm_unreachable("Invalid ArchType!");
79 }
80 
81 StringRef Triple::getArchTypePrefix(ArchType Kind) {
82   switch (Kind) {
83   default:
84     return StringRef();
85 
86   case aarch64:
87   case aarch64_be:
88   case aarch64_32:  return "aarch64";
89 
90   case arc:         return "arc";
91 
92   case arm:
93   case armeb:
94   case thumb:
95   case thumbeb:     return "arm";
96 
97   case avr:         return "avr";
98 
99   case ppc64:
100   case ppc64le:
101   case ppc:         return "ppc";
102 
103   case mips:
104   case mipsel:
105   case mips64:
106   case mips64el:    return "mips";
107 
108   case hexagon:     return "hexagon";
109 
110   case amdgcn:      return "amdgcn";
111   case r600:        return "r600";
112 
113   case bpfel:
114   case bpfeb:       return "bpf";
115 
116   case sparcv9:
117   case sparcel:
118   case sparc:       return "sparc";
119 
120   case systemz:     return "s390";
121 
122   case x86:
123   case x86_64:      return "x86";
124 
125   case xcore:       return "xcore";
126 
127   // NVPTX intrinsics are namespaced under nvvm.
128   case nvptx:       return "nvvm";
129   case nvptx64:     return "nvvm";
130 
131   case le32:        return "le32";
132   case le64:        return "le64";
133 
134   case amdil:
135   case amdil64:     return "amdil";
136 
137   case hsail:
138   case hsail64:     return "hsail";
139 
140   case spir:
141   case spir64:      return "spir";
142   case kalimba:     return "kalimba";
143   case lanai:       return "lanai";
144   case shave:       return "shave";
145   case wasm32:
146   case wasm64:      return "wasm";
147 
148   case riscv32:
149   case riscv64:     return "riscv";
150 
151   case ve:          return "ve";
152   }
153 }
154 
155 StringRef Triple::getVendorTypeName(VendorType Kind) {
156   switch (Kind) {
157   case UnknownVendor: return "unknown";
158 
159   case AMD: return "amd";
160   case Apple: return "apple";
161   case BGP: return "bgp";
162   case BGQ: return "bgq";
163   case CSR: return "csr";
164   case Freescale: return "fsl";
165   case IBM: return "ibm";
166   case ImaginationTechnologies: return "img";
167   case Mesa: return "mesa";
168   case MipsTechnologies: return "mti";
169   case Myriad: return "myriad";
170   case NVIDIA: return "nvidia";
171   case OpenEmbedded: return "oe";
172   case PC: return "pc";
173   case SCEI: return "scei";
174   case SUSE: return "suse";
175   }
176 
177   llvm_unreachable("Invalid VendorType!");
178 }
179 
180 StringRef Triple::getOSTypeName(OSType Kind) {
181   switch (Kind) {
182   case UnknownOS: return "unknown";
183 
184   case AIX: return "aix";
185   case AMDHSA: return "amdhsa";
186   case AMDPAL: return "amdpal";
187   case Ananas: return "ananas";
188   case CNK: return "cnk";
189   case CUDA: return "cuda";
190   case CloudABI: return "cloudabi";
191   case Contiki: return "contiki";
192   case Darwin: return "darwin";
193   case DragonFly: return "dragonfly";
194   case ELFIAMCU: return "elfiamcu";
195   case Emscripten: return "emscripten";
196   case FreeBSD: return "freebsd";
197   case Fuchsia: return "fuchsia";
198   case Haiku: return "haiku";
199   case HermitCore: return "hermit";
200   case Hurd: return "hurd";
201   case IOS: return "ios";
202   case KFreeBSD: return "kfreebsd";
203   case Linux: return "linux";
204   case Lv2: return "lv2";
205   case MacOSX: return "macosx";
206   case Mesa3D: return "mesa3d";
207   case Minix: return "minix";
208   case NVCL: return "nvcl";
209   case NaCl: return "nacl";
210   case NetBSD: return "netbsd";
211   case OpenBSD: return "openbsd";
212   case PS4: return "ps4";
213   case RTEMS: return "rtems";
214   case Solaris: return "solaris";
215   case TvOS: return "tvos";
216   case WASI: return "wasi";
217   case WatchOS: return "watchos";
218   case Win32: return "windows";
219   }
220 
221   llvm_unreachable("Invalid OSType");
222 }
223 
224 StringRef Triple::getEnvironmentTypeName(EnvironmentType Kind) {
225   switch (Kind) {
226   case UnknownEnvironment: return "unknown";
227   case Android: return "android";
228   case CODE16: return "code16";
229   case CoreCLR: return "coreclr";
230   case Cygnus: return "cygnus";
231   case EABI: return "eabi";
232   case EABIHF: return "eabihf";
233   case GNU: return "gnu";
234   case GNUABI64: return "gnuabi64";
235   case GNUABIN32: return "gnuabin32";
236   case GNUEABI: return "gnueabi";
237   case GNUEABIHF: return "gnueabihf";
238   case GNUX32: return "gnux32";
239   case Itanium: return "itanium";
240   case MSVC: return "msvc";
241   case MacABI: return "macabi";
242   case Musl: return "musl";
243   case MuslEABI: return "musleabi";
244   case MuslEABIHF: return "musleabihf";
245   case Simulator: return "simulator";
246   }
247 
248   llvm_unreachable("Invalid EnvironmentType!");
249 }
250 
251 static Triple::ArchType parseBPFArch(StringRef ArchName) {
252   if (ArchName.equals("bpf")) {
253     if (sys::IsLittleEndianHost)
254       return Triple::bpfel;
255     else
256       return Triple::bpfeb;
257   } else if (ArchName.equals("bpf_be") || ArchName.equals("bpfeb")) {
258     return Triple::bpfeb;
259   } else if (ArchName.equals("bpf_le") || ArchName.equals("bpfel")) {
260     return Triple::bpfel;
261   } else {
262     return Triple::UnknownArch;
263   }
264 }
265 
266 Triple::ArchType Triple::getArchTypeForLLVMName(StringRef Name) {
267   Triple::ArchType BPFArch(parseBPFArch(Name));
268   return StringSwitch<Triple::ArchType>(Name)
269     .Case("aarch64", aarch64)
270     .Case("aarch64_be", aarch64_be)
271     .Case("aarch64_32", aarch64_32)
272     .Case("arc", arc)
273     .Case("arm64", aarch64) // "arm64" is an alias for "aarch64"
274     .Case("arm64_32", aarch64_32)
275     .Case("arm", arm)
276     .Case("armeb", armeb)
277     .Case("avr", avr)
278     .StartsWith("bpf", BPFArch)
279     .Case("mips", mips)
280     .Case("mipsel", mipsel)
281     .Case("mips64", mips64)
282     .Case("mips64el", mips64el)
283     .Case("msp430", msp430)
284     .Case("ppc64", ppc64)
285     .Case("ppc32", ppc)
286     .Case("ppc", ppc)
287     .Case("ppc64le", ppc64le)
288     .Case("r600", r600)
289     .Case("amdgcn", amdgcn)
290     .Case("riscv32", riscv32)
291     .Case("riscv64", riscv64)
292     .Case("hexagon", hexagon)
293     .Case("sparc", sparc)
294     .Case("sparcel", sparcel)
295     .Case("sparcv9", sparcv9)
296     .Case("systemz", systemz)
297     .Case("tce", tce)
298     .Case("tcele", tcele)
299     .Case("thumb", thumb)
300     .Case("thumbeb", thumbeb)
301     .Case("x86", x86)
302     .Case("x86-64", x86_64)
303     .Case("xcore", xcore)
304     .Case("nvptx", nvptx)
305     .Case("nvptx64", nvptx64)
306     .Case("le32", le32)
307     .Case("le64", le64)
308     .Case("amdil", amdil)
309     .Case("amdil64", amdil64)
310     .Case("hsail", hsail)
311     .Case("hsail64", hsail64)
312     .Case("spir", spir)
313     .Case("spir64", spir64)
314     .Case("kalimba", kalimba)
315     .Case("lanai", lanai)
316     .Case("shave", shave)
317     .Case("wasm32", wasm32)
318     .Case("wasm64", wasm64)
319     .Case("renderscript32", renderscript32)
320     .Case("renderscript64", renderscript64)
321     .Case("ve", ve)
322     .Default(UnknownArch);
323 }
324 
325 static Triple::ArchType parseARMArch(StringRef ArchName) {
326   ARM::ISAKind ISA = ARM::parseArchISA(ArchName);
327   ARM::EndianKind ENDIAN = ARM::parseArchEndian(ArchName);
328 
329   Triple::ArchType arch = Triple::UnknownArch;
330   switch (ENDIAN) {
331   case ARM::EndianKind::LITTLE: {
332     switch (ISA) {
333     case ARM::ISAKind::ARM:
334       arch = Triple::arm;
335       break;
336     case ARM::ISAKind::THUMB:
337       arch = Triple::thumb;
338       break;
339     case ARM::ISAKind::AARCH64:
340       arch = Triple::aarch64;
341       break;
342     case ARM::ISAKind::INVALID:
343       break;
344     }
345     break;
346   }
347   case ARM::EndianKind::BIG: {
348     switch (ISA) {
349     case ARM::ISAKind::ARM:
350       arch = Triple::armeb;
351       break;
352     case ARM::ISAKind::THUMB:
353       arch = Triple::thumbeb;
354       break;
355     case ARM::ISAKind::AARCH64:
356       arch = Triple::aarch64_be;
357       break;
358     case ARM::ISAKind::INVALID:
359       break;
360     }
361     break;
362   }
363   case ARM::EndianKind::INVALID: {
364     break;
365   }
366   }
367 
368   ArchName = ARM::getCanonicalArchName(ArchName);
369   if (ArchName.empty())
370     return Triple::UnknownArch;
371 
372   // Thumb only exists in v4+
373   if (ISA == ARM::ISAKind::THUMB &&
374       (ArchName.startswith("v2") || ArchName.startswith("v3")))
375     return Triple::UnknownArch;
376 
377   // Thumb only for v6m
378   ARM::ProfileKind Profile = ARM::parseArchProfile(ArchName);
379   unsigned Version = ARM::parseArchVersion(ArchName);
380   if (Profile == ARM::ProfileKind::M && Version == 6) {
381     if (ENDIAN == ARM::EndianKind::BIG)
382       return Triple::thumbeb;
383     else
384       return Triple::thumb;
385   }
386 
387   return arch;
388 }
389 
390 static Triple::ArchType parseArch(StringRef ArchName) {
391   auto AT = StringSwitch<Triple::ArchType>(ArchName)
392     .Cases("i386", "i486", "i586", "i686", Triple::x86)
393     // FIXME: Do we need to support these?
394     .Cases("i786", "i886", "i986", Triple::x86)
395     .Cases("amd64", "x86_64", "x86_64h", Triple::x86_64)
396     .Cases("powerpc", "powerpcspe", "ppc", "ppc32", Triple::ppc)
397     .Cases("powerpc64", "ppu", "ppc64", Triple::ppc64)
398     .Cases("powerpc64le", "ppc64le", Triple::ppc64le)
399     .Case("xscale", Triple::arm)
400     .Case("xscaleeb", Triple::armeb)
401     .Case("aarch64", Triple::aarch64)
402     .Case("aarch64_be", Triple::aarch64_be)
403     .Case("aarch64_32", Triple::aarch64_32)
404     .Case("arc", Triple::arc)
405     .Case("arm64", Triple::aarch64)
406     .Case("arm64_32", Triple::aarch64_32)
407     .Case("arm", Triple::arm)
408     .Case("armeb", Triple::armeb)
409     .Case("thumb", Triple::thumb)
410     .Case("thumbeb", Triple::thumbeb)
411     .Case("avr", Triple::avr)
412     .Case("msp430", Triple::msp430)
413     .Cases("mips", "mipseb", "mipsallegrex", "mipsisa32r6",
414            "mipsr6", Triple::mips)
415     .Cases("mipsel", "mipsallegrexel", "mipsisa32r6el", "mipsr6el",
416            Triple::mipsel)
417     .Cases("mips64", "mips64eb", "mipsn32", "mipsisa64r6",
418            "mips64r6", "mipsn32r6", Triple::mips64)
419     .Cases("mips64el", "mipsn32el", "mipsisa64r6el", "mips64r6el",
420            "mipsn32r6el", Triple::mips64el)
421     .Case("r600", Triple::r600)
422     .Case("amdgcn", Triple::amdgcn)
423     .Case("riscv32", Triple::riscv32)
424     .Case("riscv64", Triple::riscv64)
425     .Case("hexagon", Triple::hexagon)
426     .Cases("s390x", "systemz", Triple::systemz)
427     .Case("sparc", Triple::sparc)
428     .Case("sparcel", Triple::sparcel)
429     .Cases("sparcv9", "sparc64", Triple::sparcv9)
430     .Case("tce", Triple::tce)
431     .Case("tcele", Triple::tcele)
432     .Case("xcore", Triple::xcore)
433     .Case("nvptx", Triple::nvptx)
434     .Case("nvptx64", Triple::nvptx64)
435     .Case("le32", Triple::le32)
436     .Case("le64", Triple::le64)
437     .Case("amdil", Triple::amdil)
438     .Case("amdil64", Triple::amdil64)
439     .Case("hsail", Triple::hsail)
440     .Case("hsail64", Triple::hsail64)
441     .Case("spir", Triple::spir)
442     .Case("spir64", Triple::spir64)
443     .StartsWith("kalimba", Triple::kalimba)
444     .Case("lanai", Triple::lanai)
445     .Case("renderscript32", Triple::renderscript32)
446     .Case("renderscript64", Triple::renderscript64)
447     .Case("shave", Triple::shave)
448     .Case("ve", Triple::ve)
449     .Case("wasm32", Triple::wasm32)
450     .Case("wasm64", Triple::wasm64)
451     .Default(Triple::UnknownArch);
452 
453   // Some architectures require special parsing logic just to compute the
454   // ArchType result.
455   if (AT == Triple::UnknownArch) {
456     if (ArchName.startswith("arm") || ArchName.startswith("thumb") ||
457         ArchName.startswith("aarch64"))
458       return parseARMArch(ArchName);
459     if (ArchName.startswith("bpf"))
460       return parseBPFArch(ArchName);
461   }
462 
463   return AT;
464 }
465 
466 static Triple::VendorType parseVendor(StringRef VendorName) {
467   return StringSwitch<Triple::VendorType>(VendorName)
468     .Case("apple", Triple::Apple)
469     .Case("pc", Triple::PC)
470     .Case("scei", Triple::SCEI)
471     .Case("bgp", Triple::BGP)
472     .Case("bgq", Triple::BGQ)
473     .Case("fsl", Triple::Freescale)
474     .Case("ibm", Triple::IBM)
475     .Case("img", Triple::ImaginationTechnologies)
476     .Case("mti", Triple::MipsTechnologies)
477     .Case("nvidia", Triple::NVIDIA)
478     .Case("csr", Triple::CSR)
479     .Case("myriad", Triple::Myriad)
480     .Case("amd", Triple::AMD)
481     .Case("mesa", Triple::Mesa)
482     .Case("suse", Triple::SUSE)
483     .Case("oe", Triple::OpenEmbedded)
484     .Default(Triple::UnknownVendor);
485 }
486 
487 static Triple::OSType parseOS(StringRef OSName) {
488   return StringSwitch<Triple::OSType>(OSName)
489     .StartsWith("ananas", Triple::Ananas)
490     .StartsWith("cloudabi", Triple::CloudABI)
491     .StartsWith("darwin", Triple::Darwin)
492     .StartsWith("dragonfly", Triple::DragonFly)
493     .StartsWith("freebsd", Triple::FreeBSD)
494     .StartsWith("fuchsia", Triple::Fuchsia)
495     .StartsWith("ios", Triple::IOS)
496     .StartsWith("kfreebsd", Triple::KFreeBSD)
497     .StartsWith("linux", Triple::Linux)
498     .StartsWith("lv2", Triple::Lv2)
499     .StartsWith("macos", Triple::MacOSX)
500     .StartsWith("netbsd", Triple::NetBSD)
501     .StartsWith("openbsd", Triple::OpenBSD)
502     .StartsWith("solaris", Triple::Solaris)
503     .StartsWith("win32", Triple::Win32)
504     .StartsWith("windows", Triple::Win32)
505     .StartsWith("haiku", Triple::Haiku)
506     .StartsWith("minix", Triple::Minix)
507     .StartsWith("rtems", Triple::RTEMS)
508     .StartsWith("nacl", Triple::NaCl)
509     .StartsWith("cnk", Triple::CNK)
510     .StartsWith("aix", Triple::AIX)
511     .StartsWith("cuda", Triple::CUDA)
512     .StartsWith("nvcl", Triple::NVCL)
513     .StartsWith("amdhsa", Triple::AMDHSA)
514     .StartsWith("ps4", Triple::PS4)
515     .StartsWith("elfiamcu", Triple::ELFIAMCU)
516     .StartsWith("tvos", Triple::TvOS)
517     .StartsWith("watchos", Triple::WatchOS)
518     .StartsWith("mesa3d", Triple::Mesa3D)
519     .StartsWith("contiki", Triple::Contiki)
520     .StartsWith("amdpal", Triple::AMDPAL)
521     .StartsWith("hermit", Triple::HermitCore)
522     .StartsWith("hurd", Triple::Hurd)
523     .StartsWith("wasi", Triple::WASI)
524     .StartsWith("emscripten", Triple::Emscripten)
525     .Default(Triple::UnknownOS);
526 }
527 
528 static Triple::EnvironmentType parseEnvironment(StringRef EnvironmentName) {
529   return StringSwitch<Triple::EnvironmentType>(EnvironmentName)
530     .StartsWith("eabihf", Triple::EABIHF)
531     .StartsWith("eabi", Triple::EABI)
532     .StartsWith("gnuabin32", Triple::GNUABIN32)
533     .StartsWith("gnuabi64", Triple::GNUABI64)
534     .StartsWith("gnueabihf", Triple::GNUEABIHF)
535     .StartsWith("gnueabi", Triple::GNUEABI)
536     .StartsWith("gnux32", Triple::GNUX32)
537     .StartsWith("code16", Triple::CODE16)
538     .StartsWith("gnu", Triple::GNU)
539     .StartsWith("android", Triple::Android)
540     .StartsWith("musleabihf", Triple::MuslEABIHF)
541     .StartsWith("musleabi", Triple::MuslEABI)
542     .StartsWith("musl", Triple::Musl)
543     .StartsWith("msvc", Triple::MSVC)
544     .StartsWith("itanium", Triple::Itanium)
545     .StartsWith("cygnus", Triple::Cygnus)
546     .StartsWith("coreclr", Triple::CoreCLR)
547     .StartsWith("simulator", Triple::Simulator)
548     .StartsWith("macabi", Triple::MacABI)
549     .Default(Triple::UnknownEnvironment);
550 }
551 
552 static Triple::ObjectFormatType parseFormat(StringRef EnvironmentName) {
553   return StringSwitch<Triple::ObjectFormatType>(EnvironmentName)
554     // "xcoff" must come before "coff" because of the order-dependendent
555     // pattern matching.
556     .EndsWith("xcoff", Triple::XCOFF)
557     .EndsWith("coff", Triple::COFF)
558     .EndsWith("elf", Triple::ELF)
559     .EndsWith("macho", Triple::MachO)
560     .EndsWith("wasm", Triple::Wasm)
561     .Default(Triple::UnknownObjectFormat);
562 }
563 
564 static Triple::SubArchType parseSubArch(StringRef SubArchName) {
565   if (SubArchName.startswith("mips") &&
566       (SubArchName.endswith("r6el") || SubArchName.endswith("r6")))
567     return Triple::MipsSubArch_r6;
568 
569   if (SubArchName == "powerpcspe")
570     return Triple::PPCSubArch_spe;
571 
572   StringRef ARMSubArch = ARM::getCanonicalArchName(SubArchName);
573 
574   // For now, this is the small part. Early return.
575   if (ARMSubArch.empty())
576     return StringSwitch<Triple::SubArchType>(SubArchName)
577       .EndsWith("kalimba3", Triple::KalimbaSubArch_v3)
578       .EndsWith("kalimba4", Triple::KalimbaSubArch_v4)
579       .EndsWith("kalimba5", Triple::KalimbaSubArch_v5)
580       .Default(Triple::NoSubArch);
581 
582   // ARM sub arch.
583   switch(ARM::parseArch(ARMSubArch)) {
584   case ARM::ArchKind::ARMV4:
585     return Triple::NoSubArch;
586   case ARM::ArchKind::ARMV4T:
587     return Triple::ARMSubArch_v4t;
588   case ARM::ArchKind::ARMV5T:
589     return Triple::ARMSubArch_v5;
590   case ARM::ArchKind::ARMV5TE:
591   case ARM::ArchKind::IWMMXT:
592   case ARM::ArchKind::IWMMXT2:
593   case ARM::ArchKind::XSCALE:
594   case ARM::ArchKind::ARMV5TEJ:
595     return Triple::ARMSubArch_v5te;
596   case ARM::ArchKind::ARMV6:
597     return Triple::ARMSubArch_v6;
598   case ARM::ArchKind::ARMV6K:
599   case ARM::ArchKind::ARMV6KZ:
600     return Triple::ARMSubArch_v6k;
601   case ARM::ArchKind::ARMV6T2:
602     return Triple::ARMSubArch_v6t2;
603   case ARM::ArchKind::ARMV6M:
604     return Triple::ARMSubArch_v6m;
605   case ARM::ArchKind::ARMV7A:
606   case ARM::ArchKind::ARMV7R:
607     return Triple::ARMSubArch_v7;
608   case ARM::ArchKind::ARMV7VE:
609     return Triple::ARMSubArch_v7ve;
610   case ARM::ArchKind::ARMV7K:
611     return Triple::ARMSubArch_v7k;
612   case ARM::ArchKind::ARMV7M:
613     return Triple::ARMSubArch_v7m;
614   case ARM::ArchKind::ARMV7S:
615     return Triple::ARMSubArch_v7s;
616   case ARM::ArchKind::ARMV7EM:
617     return Triple::ARMSubArch_v7em;
618   case ARM::ArchKind::ARMV8A:
619     return Triple::ARMSubArch_v8;
620   case ARM::ArchKind::ARMV8_1A:
621     return Triple::ARMSubArch_v8_1a;
622   case ARM::ArchKind::ARMV8_2A:
623     return Triple::ARMSubArch_v8_2a;
624   case ARM::ArchKind::ARMV8_3A:
625     return Triple::ARMSubArch_v8_3a;
626   case ARM::ArchKind::ARMV8_4A:
627     return Triple::ARMSubArch_v8_4a;
628   case ARM::ArchKind::ARMV8_5A:
629     return Triple::ARMSubArch_v8_5a;
630   case ARM::ArchKind::ARMV8R:
631     return Triple::ARMSubArch_v8r;
632   case ARM::ArchKind::ARMV8MBaseline:
633     return Triple::ARMSubArch_v8m_baseline;
634   case ARM::ArchKind::ARMV8MMainline:
635     return Triple::ARMSubArch_v8m_mainline;
636   case ARM::ArchKind::ARMV8_1MMainline:
637     return Triple::ARMSubArch_v8_1m_mainline;
638   default:
639     return Triple::NoSubArch;
640   }
641 }
642 
643 static StringRef getObjectFormatTypeName(Triple::ObjectFormatType Kind) {
644   switch (Kind) {
645   case Triple::UnknownObjectFormat: return "";
646   case Triple::COFF:  return "coff";
647   case Triple::ELF:   return "elf";
648   case Triple::MachO: return "macho";
649   case Triple::Wasm:  return "wasm";
650   case Triple::XCOFF: return "xcoff";
651   }
652   llvm_unreachable("unknown object format type");
653 }
654 
655 static Triple::ObjectFormatType getDefaultFormat(const Triple &T) {
656   switch (T.getArch()) {
657   case Triple::UnknownArch:
658   case Triple::aarch64:
659   case Triple::aarch64_32:
660   case Triple::arm:
661   case Triple::thumb:
662   case Triple::x86:
663   case Triple::x86_64:
664     if (T.isOSDarwin())
665       return Triple::MachO;
666     else if (T.isOSWindows())
667       return Triple::COFF;
668     return Triple::ELF;
669 
670   case Triple::aarch64_be:
671   case Triple::amdgcn:
672   case Triple::amdil64:
673   case Triple::amdil:
674   case Triple::arc:
675   case Triple::armeb:
676   case Triple::avr:
677   case Triple::bpfeb:
678   case Triple::bpfel:
679   case Triple::hexagon:
680   case Triple::hsail64:
681   case Triple::hsail:
682   case Triple::kalimba:
683   case Triple::lanai:
684   case Triple::le32:
685   case Triple::le64:
686   case Triple::mips64:
687   case Triple::mips64el:
688   case Triple::mips:
689   case Triple::mipsel:
690   case Triple::msp430:
691   case Triple::nvptx64:
692   case Triple::nvptx:
693   case Triple::ppc64le:
694   case Triple::r600:
695   case Triple::renderscript32:
696   case Triple::renderscript64:
697   case Triple::riscv32:
698   case Triple::riscv64:
699   case Triple::shave:
700   case Triple::sparc:
701   case Triple::sparcel:
702   case Triple::sparcv9:
703   case Triple::spir64:
704   case Triple::spir:
705   case Triple::systemz:
706   case Triple::tce:
707   case Triple::tcele:
708   case Triple::thumbeb:
709   case Triple::ve:
710   case Triple::xcore:
711     return Triple::ELF;
712 
713   case Triple::ppc64:
714   case Triple::ppc:
715     if (T.isOSDarwin())
716       return Triple::MachO;
717     else if (T.isOSAIX())
718       return Triple::XCOFF;
719     return Triple::ELF;
720 
721   case Triple::wasm32:
722   case Triple::wasm64:
723     return Triple::Wasm;
724   }
725   llvm_unreachable("unknown architecture");
726 }
727 
728 /// Construct a triple from the string representation provided.
729 ///
730 /// This stores the string representation and parses the various pieces into
731 /// enum members.
732 Triple::Triple(const Twine &Str)
733     : Data(Str.str()), Arch(UnknownArch), SubArch(NoSubArch),
734       Vendor(UnknownVendor), OS(UnknownOS), Environment(UnknownEnvironment),
735       ObjectFormat(UnknownObjectFormat) {
736   // Do minimal parsing by hand here.
737   SmallVector<StringRef, 4> Components;
738   StringRef(Data).split(Components, '-', /*MaxSplit*/ 3);
739   if (Components.size() > 0) {
740     Arch = parseArch(Components[0]);
741     SubArch = parseSubArch(Components[0]);
742     if (Components.size() > 1) {
743       Vendor = parseVendor(Components[1]);
744       if (Components.size() > 2) {
745         OS = parseOS(Components[2]);
746         if (Components.size() > 3) {
747           Environment = parseEnvironment(Components[3]);
748           ObjectFormat = parseFormat(Components[3]);
749         }
750       }
751     } else {
752       Environment =
753           StringSwitch<Triple::EnvironmentType>(Components[0])
754               .StartsWith("mipsn32", Triple::GNUABIN32)
755               .StartsWith("mips64", Triple::GNUABI64)
756               .StartsWith("mipsisa64", Triple::GNUABI64)
757               .StartsWith("mipsisa32", Triple::GNU)
758               .Cases("mips", "mipsel", "mipsr6", "mipsr6el", Triple::GNU)
759               .Default(UnknownEnvironment);
760     }
761   }
762   if (ObjectFormat == UnknownObjectFormat)
763     ObjectFormat = getDefaultFormat(*this);
764 }
765 
766 /// Construct a triple from string representations of the architecture,
767 /// vendor, and OS.
768 ///
769 /// This joins each argument into a canonical string representation and parses
770 /// them into enum members. It leaves the environment unknown and omits it from
771 /// the string representation.
772 Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr)
773     : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr).str()),
774       Arch(parseArch(ArchStr.str())),
775       SubArch(parseSubArch(ArchStr.str())),
776       Vendor(parseVendor(VendorStr.str())),
777       OS(parseOS(OSStr.str())),
778       Environment(), ObjectFormat(Triple::UnknownObjectFormat) {
779   ObjectFormat = getDefaultFormat(*this);
780 }
781 
782 /// Construct a triple from string representations of the architecture,
783 /// vendor, OS, and environment.
784 ///
785 /// This joins each argument into a canonical string representation and parses
786 /// them into enum members.
787 Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr,
788                const Twine &EnvironmentStr)
789     : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr + Twine('-') +
790             EnvironmentStr).str()),
791       Arch(parseArch(ArchStr.str())),
792       SubArch(parseSubArch(ArchStr.str())),
793       Vendor(parseVendor(VendorStr.str())),
794       OS(parseOS(OSStr.str())),
795       Environment(parseEnvironment(EnvironmentStr.str())),
796       ObjectFormat(parseFormat(EnvironmentStr.str())) {
797   if (ObjectFormat == Triple::UnknownObjectFormat)
798     ObjectFormat = getDefaultFormat(*this);
799 }
800 
801 std::string Triple::normalize(StringRef Str) {
802   bool IsMinGW32 = false;
803   bool IsCygwin = false;
804 
805   // Parse into components.
806   SmallVector<StringRef, 4> Components;
807   Str.split(Components, '-');
808 
809   // If the first component corresponds to a known architecture, preferentially
810   // use it for the architecture.  If the second component corresponds to a
811   // known vendor, preferentially use it for the vendor, etc.  This avoids silly
812   // component movement when a component parses as (eg) both a valid arch and a
813   // valid os.
814   ArchType Arch = UnknownArch;
815   if (Components.size() > 0)
816     Arch = parseArch(Components[0]);
817   VendorType Vendor = UnknownVendor;
818   if (Components.size() > 1)
819     Vendor = parseVendor(Components[1]);
820   OSType OS = UnknownOS;
821   if (Components.size() > 2) {
822     OS = parseOS(Components[2]);
823     IsCygwin = Components[2].startswith("cygwin");
824     IsMinGW32 = Components[2].startswith("mingw");
825   }
826   EnvironmentType Environment = UnknownEnvironment;
827   if (Components.size() > 3)
828     Environment = parseEnvironment(Components[3]);
829   ObjectFormatType ObjectFormat = UnknownObjectFormat;
830   if (Components.size() > 4)
831     ObjectFormat = parseFormat(Components[4]);
832 
833   // Note which components are already in their final position.  These will not
834   // be moved.
835   bool Found[4];
836   Found[0] = Arch != UnknownArch;
837   Found[1] = Vendor != UnknownVendor;
838   Found[2] = OS != UnknownOS;
839   Found[3] = Environment != UnknownEnvironment;
840 
841   // If they are not there already, permute the components into their canonical
842   // positions by seeing if they parse as a valid architecture, and if so moving
843   // the component to the architecture position etc.
844   for (unsigned Pos = 0; Pos != array_lengthof(Found); ++Pos) {
845     if (Found[Pos])
846       continue; // Already in the canonical position.
847 
848     for (unsigned Idx = 0; Idx != Components.size(); ++Idx) {
849       // Do not reparse any components that already matched.
850       if (Idx < array_lengthof(Found) && Found[Idx])
851         continue;
852 
853       // Does this component parse as valid for the target position?
854       bool Valid = false;
855       StringRef Comp = Components[Idx];
856       switch (Pos) {
857       default: llvm_unreachable("unexpected component type!");
858       case 0:
859         Arch = parseArch(Comp);
860         Valid = Arch != UnknownArch;
861         break;
862       case 1:
863         Vendor = parseVendor(Comp);
864         Valid = Vendor != UnknownVendor;
865         break;
866       case 2:
867         OS = parseOS(Comp);
868         IsCygwin = Comp.startswith("cygwin");
869         IsMinGW32 = Comp.startswith("mingw");
870         Valid = OS != UnknownOS || IsCygwin || IsMinGW32;
871         break;
872       case 3:
873         Environment = parseEnvironment(Comp);
874         Valid = Environment != UnknownEnvironment;
875         if (!Valid) {
876           ObjectFormat = parseFormat(Comp);
877           Valid = ObjectFormat != UnknownObjectFormat;
878         }
879         break;
880       }
881       if (!Valid)
882         continue; // Nope, try the next component.
883 
884       // Move the component to the target position, pushing any non-fixed
885       // components that are in the way to the right.  This tends to give
886       // good results in the common cases of a forgotten vendor component
887       // or a wrongly positioned environment.
888       if (Pos < Idx) {
889         // Insert left, pushing the existing components to the right.  For
890         // example, a-b-i386 -> i386-a-b when moving i386 to the front.
891         StringRef CurrentComponent(""); // The empty component.
892         // Replace the component we are moving with an empty component.
893         std::swap(CurrentComponent, Components[Idx]);
894         // Insert the component being moved at Pos, displacing any existing
895         // components to the right.
896         for (unsigned i = Pos; !CurrentComponent.empty(); ++i) {
897           // Skip over any fixed components.
898           while (i < array_lengthof(Found) && Found[i])
899             ++i;
900           // Place the component at the new position, getting the component
901           // that was at this position - it will be moved right.
902           std::swap(CurrentComponent, Components[i]);
903         }
904       } else if (Pos > Idx) {
905         // Push right by inserting empty components until the component at Idx
906         // reaches the target position Pos.  For example, pc-a -> -pc-a when
907         // moving pc to the second position.
908         do {
909           // Insert one empty component at Idx.
910           StringRef CurrentComponent(""); // The empty component.
911           for (unsigned i = Idx; i < Components.size();) {
912             // Place the component at the new position, getting the component
913             // that was at this position - it will be moved right.
914             std::swap(CurrentComponent, Components[i]);
915             // If it was placed on top of an empty component then we are done.
916             if (CurrentComponent.empty())
917               break;
918             // Advance to the next component, skipping any fixed components.
919             while (++i < array_lengthof(Found) && Found[i])
920               ;
921           }
922           // The last component was pushed off the end - append it.
923           if (!CurrentComponent.empty())
924             Components.push_back(CurrentComponent);
925 
926           // Advance Idx to the component's new position.
927           while (++Idx < array_lengthof(Found) && Found[Idx])
928             ;
929         } while (Idx < Pos); // Add more until the final position is reached.
930       }
931       assert(Pos < Components.size() && Components[Pos] == Comp &&
932              "Component moved wrong!");
933       Found[Pos] = true;
934       break;
935     }
936   }
937 
938   // Replace empty components with "unknown" value.
939   for (unsigned i = 0, e = Components.size(); i < e; ++i) {
940     if (Components[i].empty())
941       Components[i] = "unknown";
942   }
943 
944   // Special case logic goes here.  At this point Arch, Vendor and OS have the
945   // correct values for the computed components.
946   std::string NormalizedEnvironment;
947   if (Environment == Triple::Android && Components[3].startswith("androideabi")) {
948     StringRef AndroidVersion = Components[3].drop_front(strlen("androideabi"));
949     if (AndroidVersion.empty()) {
950       Components[3] = "android";
951     } else {
952       NormalizedEnvironment = Twine("android", AndroidVersion).str();
953       Components[3] = NormalizedEnvironment;
954     }
955   }
956 
957   // SUSE uses "gnueabi" to mean "gnueabihf"
958   if (Vendor == Triple::SUSE && Environment == llvm::Triple::GNUEABI)
959     Components[3] = "gnueabihf";
960 
961   if (OS == Triple::Win32) {
962     Components.resize(4);
963     Components[2] = "windows";
964     if (Environment == UnknownEnvironment) {
965       if (ObjectFormat == UnknownObjectFormat || ObjectFormat == Triple::COFF)
966         Components[3] = "msvc";
967       else
968         Components[3] = getObjectFormatTypeName(ObjectFormat);
969     }
970   } else if (IsMinGW32) {
971     Components.resize(4);
972     Components[2] = "windows";
973     Components[3] = "gnu";
974   } else if (IsCygwin) {
975     Components.resize(4);
976     Components[2] = "windows";
977     Components[3] = "cygnus";
978   }
979   if (IsMinGW32 || IsCygwin ||
980       (OS == Triple::Win32 && Environment != UnknownEnvironment)) {
981     if (ObjectFormat != UnknownObjectFormat && ObjectFormat != Triple::COFF) {
982       Components.resize(5);
983       Components[4] = getObjectFormatTypeName(ObjectFormat);
984     }
985   }
986 
987   // Stick the corrected components back together to form the normalized string.
988   std::string Normalized;
989   for (unsigned i = 0, e = Components.size(); i != e; ++i) {
990     if (i) Normalized += '-';
991     Normalized += Components[i];
992   }
993   return Normalized;
994 }
995 
996 StringRef Triple::getArchName() const {
997   return StringRef(Data).split('-').first;           // Isolate first component
998 }
999 
1000 StringRef Triple::getVendorName() const {
1001   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1002   return Tmp.split('-').first;                       // Isolate second component
1003 }
1004 
1005 StringRef Triple::getOSName() const {
1006   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1007   Tmp = Tmp.split('-').second;                       // Strip second component
1008   return Tmp.split('-').first;                       // Isolate third component
1009 }
1010 
1011 StringRef Triple::getEnvironmentName() const {
1012   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1013   Tmp = Tmp.split('-').second;                       // Strip second component
1014   return Tmp.split('-').second;                      // Strip third component
1015 }
1016 
1017 StringRef Triple::getOSAndEnvironmentName() const {
1018   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1019   return Tmp.split('-').second;                      // Strip second component
1020 }
1021 
1022 static unsigned EatNumber(StringRef &Str) {
1023   assert(!Str.empty() && Str[0] >= '0' && Str[0] <= '9' && "Not a number");
1024   unsigned Result = 0;
1025 
1026   do {
1027     // Consume the leading digit.
1028     Result = Result*10 + (Str[0] - '0');
1029 
1030     // Eat the digit.
1031     Str = Str.substr(1);
1032   } while (!Str.empty() && Str[0] >= '0' && Str[0] <= '9');
1033 
1034   return Result;
1035 }
1036 
1037 static void parseVersionFromName(StringRef Name, unsigned &Major,
1038                                  unsigned &Minor, unsigned &Micro) {
1039   // Any unset version defaults to 0.
1040   Major = Minor = Micro = 0;
1041 
1042   // Parse up to three components.
1043   unsigned *Components[3] = {&Major, &Minor, &Micro};
1044   for (unsigned i = 0; i != 3; ++i) {
1045     if (Name.empty() || Name[0] < '0' || Name[0] > '9')
1046       break;
1047 
1048     // Consume the leading number.
1049     *Components[i] = EatNumber(Name);
1050 
1051     // Consume the separator, if present.
1052     if (Name.startswith("."))
1053       Name = Name.substr(1);
1054   }
1055 }
1056 
1057 void Triple::getEnvironmentVersion(unsigned &Major, unsigned &Minor,
1058                                    unsigned &Micro) const {
1059   StringRef EnvironmentName = getEnvironmentName();
1060   StringRef EnvironmentTypeName = getEnvironmentTypeName(getEnvironment());
1061   if (EnvironmentName.startswith(EnvironmentTypeName))
1062     EnvironmentName = EnvironmentName.substr(EnvironmentTypeName.size());
1063 
1064   parseVersionFromName(EnvironmentName, Major, Minor, Micro);
1065 }
1066 
1067 void Triple::getOSVersion(unsigned &Major, unsigned &Minor,
1068                           unsigned &Micro) const {
1069   StringRef OSName = getOSName();
1070   // Assume that the OS portion of the triple starts with the canonical name.
1071   StringRef OSTypeName = getOSTypeName(getOS());
1072   if (OSName.startswith(OSTypeName))
1073     OSName = OSName.substr(OSTypeName.size());
1074   else if (getOS() == MacOSX)
1075     OSName.consume_front("macos");
1076 
1077   parseVersionFromName(OSName, Major, Minor, Micro);
1078 }
1079 
1080 bool Triple::getMacOSXVersion(unsigned &Major, unsigned &Minor,
1081                               unsigned &Micro) const {
1082   getOSVersion(Major, Minor, Micro);
1083 
1084   switch (getOS()) {
1085   default: llvm_unreachable("unexpected OS for Darwin triple");
1086   case Darwin:
1087     // Default to darwin8, i.e., MacOSX 10.4.
1088     if (Major == 0)
1089       Major = 8;
1090     // Darwin version numbers are skewed from OS X versions.
1091     if (Major < 4)
1092       return false;
1093     Micro = 0;
1094     Minor = Major - 4;
1095     Major = 10;
1096     break;
1097   case MacOSX:
1098     // Default to 10.4.
1099     if (Major == 0) {
1100       Major = 10;
1101       Minor = 4;
1102     }
1103     if (Major != 10)
1104       return false;
1105     break;
1106   case IOS:
1107   case TvOS:
1108   case WatchOS:
1109     // Ignore the version from the triple.  This is only handled because the
1110     // the clang driver combines OS X and IOS support into a common Darwin
1111     // toolchain that wants to know the OS X version number even when targeting
1112     // IOS.
1113     Major = 10;
1114     Minor = 4;
1115     Micro = 0;
1116     break;
1117   }
1118   return true;
1119 }
1120 
1121 void Triple::getiOSVersion(unsigned &Major, unsigned &Minor,
1122                            unsigned &Micro) const {
1123   switch (getOS()) {
1124   default: llvm_unreachable("unexpected OS for Darwin triple");
1125   case Darwin:
1126   case MacOSX:
1127     // Ignore the version from the triple.  This is only handled because the
1128     // the clang driver combines OS X and IOS support into a common Darwin
1129     // toolchain that wants to know the iOS version number even when targeting
1130     // OS X.
1131     Major = 5;
1132     Minor = 0;
1133     Micro = 0;
1134     break;
1135   case IOS:
1136   case TvOS:
1137     getOSVersion(Major, Minor, Micro);
1138     // Default to 5.0 (or 7.0 for arm64).
1139     if (Major == 0)
1140       Major = (getArch() == aarch64) ? 7 : 5;
1141     break;
1142   case WatchOS:
1143     llvm_unreachable("conflicting triple info");
1144   }
1145 }
1146 
1147 void Triple::getWatchOSVersion(unsigned &Major, unsigned &Minor,
1148                                unsigned &Micro) const {
1149   switch (getOS()) {
1150   default: llvm_unreachable("unexpected OS for Darwin triple");
1151   case Darwin:
1152   case MacOSX:
1153     // Ignore the version from the triple.  This is only handled because the
1154     // the clang driver combines OS X and IOS support into a common Darwin
1155     // toolchain that wants to know the iOS version number even when targeting
1156     // OS X.
1157     Major = 2;
1158     Minor = 0;
1159     Micro = 0;
1160     break;
1161   case WatchOS:
1162     getOSVersion(Major, Minor, Micro);
1163     if (Major == 0)
1164       Major = 2;
1165     break;
1166   case IOS:
1167     llvm_unreachable("conflicting triple info");
1168   }
1169 }
1170 
1171 void Triple::setTriple(const Twine &Str) {
1172   *this = Triple(Str);
1173 }
1174 
1175 void Triple::setArch(ArchType Kind) {
1176   setArchName(getArchTypeName(Kind));
1177 }
1178 
1179 void Triple::setVendor(VendorType Kind) {
1180   setVendorName(getVendorTypeName(Kind));
1181 }
1182 
1183 void Triple::setOS(OSType Kind) {
1184   setOSName(getOSTypeName(Kind));
1185 }
1186 
1187 void Triple::setEnvironment(EnvironmentType Kind) {
1188   if (ObjectFormat == getDefaultFormat(*this))
1189     return setEnvironmentName(getEnvironmentTypeName(Kind));
1190 
1191   setEnvironmentName((getEnvironmentTypeName(Kind) + Twine("-") +
1192                       getObjectFormatTypeName(ObjectFormat)).str());
1193 }
1194 
1195 void Triple::setObjectFormat(ObjectFormatType Kind) {
1196   if (Environment == UnknownEnvironment)
1197     return setEnvironmentName(getObjectFormatTypeName(Kind));
1198 
1199   setEnvironmentName((getEnvironmentTypeName(Environment) + Twine("-") +
1200                       getObjectFormatTypeName(Kind)).str());
1201 }
1202 
1203 void Triple::setArchName(StringRef Str) {
1204   // Work around a miscompilation bug for Twines in gcc 4.0.3.
1205   SmallString<64> Triple;
1206   Triple += Str;
1207   Triple += "-";
1208   Triple += getVendorName();
1209   Triple += "-";
1210   Triple += getOSAndEnvironmentName();
1211   setTriple(Triple);
1212 }
1213 
1214 void Triple::setVendorName(StringRef Str) {
1215   setTriple(getArchName() + "-" + Str + "-" + getOSAndEnvironmentName());
1216 }
1217 
1218 void Triple::setOSName(StringRef Str) {
1219   if (hasEnvironment())
1220     setTriple(getArchName() + "-" + getVendorName() + "-" + Str +
1221               "-" + getEnvironmentName());
1222   else
1223     setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
1224 }
1225 
1226 void Triple::setEnvironmentName(StringRef Str) {
1227   setTriple(getArchName() + "-" + getVendorName() + "-" + getOSName() +
1228             "-" + Str);
1229 }
1230 
1231 void Triple::setOSAndEnvironmentName(StringRef Str) {
1232   setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
1233 }
1234 
1235 static unsigned getArchPointerBitWidth(llvm::Triple::ArchType Arch) {
1236   switch (Arch) {
1237   case llvm::Triple::UnknownArch:
1238     return 0;
1239 
1240   case llvm::Triple::avr:
1241   case llvm::Triple::msp430:
1242     return 16;
1243 
1244   case llvm::Triple::aarch64_32:
1245   case llvm::Triple::amdil:
1246   case llvm::Triple::arc:
1247   case llvm::Triple::arm:
1248   case llvm::Triple::armeb:
1249   case llvm::Triple::hexagon:
1250   case llvm::Triple::hsail:
1251   case llvm::Triple::kalimba:
1252   case llvm::Triple::lanai:
1253   case llvm::Triple::le32:
1254   case llvm::Triple::mips:
1255   case llvm::Triple::mipsel:
1256   case llvm::Triple::nvptx:
1257   case llvm::Triple::ppc:
1258   case llvm::Triple::r600:
1259   case llvm::Triple::renderscript32:
1260   case llvm::Triple::riscv32:
1261   case llvm::Triple::shave:
1262   case llvm::Triple::sparc:
1263   case llvm::Triple::sparcel:
1264   case llvm::Triple::spir:
1265   case llvm::Triple::tce:
1266   case llvm::Triple::tcele:
1267   case llvm::Triple::thumb:
1268   case llvm::Triple::thumbeb:
1269   case llvm::Triple::wasm32:
1270   case llvm::Triple::x86:
1271   case llvm::Triple::xcore:
1272     return 32;
1273 
1274   case llvm::Triple::aarch64:
1275   case llvm::Triple::aarch64_be:
1276   case llvm::Triple::amdgcn:
1277   case llvm::Triple::amdil64:
1278   case llvm::Triple::bpfeb:
1279   case llvm::Triple::bpfel:
1280   case llvm::Triple::hsail64:
1281   case llvm::Triple::le64:
1282   case llvm::Triple::mips64:
1283   case llvm::Triple::mips64el:
1284   case llvm::Triple::nvptx64:
1285   case llvm::Triple::ppc64:
1286   case llvm::Triple::ppc64le:
1287   case llvm::Triple::renderscript64:
1288   case llvm::Triple::riscv64:
1289   case llvm::Triple::sparcv9:
1290   case llvm::Triple::spir64:
1291   case llvm::Triple::systemz:
1292   case llvm::Triple::ve:
1293   case llvm::Triple::wasm64:
1294   case llvm::Triple::x86_64:
1295     return 64;
1296   }
1297   llvm_unreachable("Invalid architecture value");
1298 }
1299 
1300 bool Triple::isArch64Bit() const {
1301   return getArchPointerBitWidth(getArch()) == 64;
1302 }
1303 
1304 bool Triple::isArch32Bit() const {
1305   return getArchPointerBitWidth(getArch()) == 32;
1306 }
1307 
1308 bool Triple::isArch16Bit() const {
1309   return getArchPointerBitWidth(getArch()) == 16;
1310 }
1311 
1312 Triple Triple::get32BitArchVariant() const {
1313   Triple T(*this);
1314   switch (getArch()) {
1315   case Triple::UnknownArch:
1316   case Triple::amdgcn:
1317   case Triple::avr:
1318   case Triple::bpfeb:
1319   case Triple::bpfel:
1320   case Triple::msp430:
1321   case Triple::ppc64le:
1322   case Triple::systemz:
1323   case Triple::ve:
1324     T.setArch(UnknownArch);
1325     break;
1326 
1327   case Triple::aarch64_32:
1328   case Triple::amdil:
1329   case Triple::arc:
1330   case Triple::arm:
1331   case Triple::armeb:
1332   case Triple::hexagon:
1333   case Triple::hsail:
1334   case Triple::kalimba:
1335   case Triple::lanai:
1336   case Triple::le32:
1337   case Triple::mips:
1338   case Triple::mipsel:
1339   case Triple::nvptx:
1340   case Triple::ppc:
1341   case Triple::r600:
1342   case Triple::renderscript32:
1343   case Triple::riscv32:
1344   case Triple::shave:
1345   case Triple::sparc:
1346   case Triple::sparcel:
1347   case Triple::spir:
1348   case Triple::tce:
1349   case Triple::tcele:
1350   case Triple::thumb:
1351   case Triple::thumbeb:
1352   case Triple::wasm32:
1353   case Triple::x86:
1354   case Triple::xcore:
1355     // Already 32-bit.
1356     break;
1357 
1358   case Triple::aarch64:        T.setArch(Triple::arm);     break;
1359   case Triple::aarch64_be:     T.setArch(Triple::armeb);   break;
1360   case Triple::amdil64:        T.setArch(Triple::amdil);   break;
1361   case Triple::hsail64:        T.setArch(Triple::hsail);   break;
1362   case Triple::le64:           T.setArch(Triple::le32);    break;
1363   case Triple::mips64:         T.setArch(Triple::mips);    break;
1364   case Triple::mips64el:       T.setArch(Triple::mipsel);  break;
1365   case Triple::nvptx64:        T.setArch(Triple::nvptx);   break;
1366   case Triple::ppc64:          T.setArch(Triple::ppc);     break;
1367   case Triple::renderscript64: T.setArch(Triple::renderscript32); break;
1368   case Triple::riscv64:        T.setArch(Triple::riscv32); break;
1369   case Triple::sparcv9:        T.setArch(Triple::sparc);   break;
1370   case Triple::spir64:         T.setArch(Triple::spir);    break;
1371   case Triple::wasm64:         T.setArch(Triple::wasm32);  break;
1372   case Triple::x86_64:         T.setArch(Triple::x86);     break;
1373   }
1374   return T;
1375 }
1376 
1377 Triple Triple::get64BitArchVariant() const {
1378   Triple T(*this);
1379   switch (getArch()) {
1380   case Triple::UnknownArch:
1381   case Triple::arc:
1382   case Triple::avr:
1383   case Triple::hexagon:
1384   case Triple::kalimba:
1385   case Triple::lanai:
1386   case Triple::msp430:
1387   case Triple::r600:
1388   case Triple::shave:
1389   case Triple::sparcel:
1390   case Triple::tce:
1391   case Triple::tcele:
1392   case Triple::xcore:
1393     T.setArch(UnknownArch);
1394     break;
1395 
1396   case Triple::aarch64:
1397   case Triple::aarch64_be:
1398   case Triple::amdgcn:
1399   case Triple::amdil64:
1400   case Triple::bpfeb:
1401   case Triple::bpfel:
1402   case Triple::hsail64:
1403   case Triple::le64:
1404   case Triple::mips64:
1405   case Triple::mips64el:
1406   case Triple::nvptx64:
1407   case Triple::ppc64:
1408   case Triple::ppc64le:
1409   case Triple::renderscript64:
1410   case Triple::riscv64:
1411   case Triple::sparcv9:
1412   case Triple::spir64:
1413   case Triple::systemz:
1414   case Triple::ve:
1415   case Triple::wasm64:
1416   case Triple::x86_64:
1417     // Already 64-bit.
1418     break;
1419 
1420   case Triple::aarch64_32:      T.setArch(Triple::aarch64);    break;
1421   case Triple::amdil:           T.setArch(Triple::amdil64);    break;
1422   case Triple::arm:             T.setArch(Triple::aarch64);    break;
1423   case Triple::armeb:           T.setArch(Triple::aarch64_be); break;
1424   case Triple::hsail:           T.setArch(Triple::hsail64);    break;
1425   case Triple::le32:            T.setArch(Triple::le64);       break;
1426   case Triple::mips:            T.setArch(Triple::mips64);     break;
1427   case Triple::mipsel:          T.setArch(Triple::mips64el);   break;
1428   case Triple::nvptx:           T.setArch(Triple::nvptx64);    break;
1429   case Triple::ppc:             T.setArch(Triple::ppc64);      break;
1430   case Triple::renderscript32:  T.setArch(Triple::renderscript64);     break;
1431   case Triple::riscv32:         T.setArch(Triple::riscv64);    break;
1432   case Triple::sparc:           T.setArch(Triple::sparcv9);    break;
1433   case Triple::spir:            T.setArch(Triple::spir64);     break;
1434   case Triple::thumb:           T.setArch(Triple::aarch64);    break;
1435   case Triple::thumbeb:         T.setArch(Triple::aarch64_be); break;
1436   case Triple::wasm32:          T.setArch(Triple::wasm64);     break;
1437   case Triple::x86:             T.setArch(Triple::x86_64);     break;
1438   }
1439   return T;
1440 }
1441 
1442 Triple Triple::getBigEndianArchVariant() const {
1443   Triple T(*this);
1444   // Already big endian.
1445   if (!isLittleEndian())
1446     return T;
1447   switch (getArch()) {
1448   case Triple::UnknownArch:
1449   case Triple::amdgcn:
1450   case Triple::amdil64:
1451   case Triple::amdil:
1452   case Triple::avr:
1453   case Triple::hexagon:
1454   case Triple::hsail64:
1455   case Triple::hsail:
1456   case Triple::kalimba:
1457   case Triple::le32:
1458   case Triple::le64:
1459   case Triple::msp430:
1460   case Triple::nvptx64:
1461   case Triple::nvptx:
1462   case Triple::r600:
1463   case Triple::renderscript32:
1464   case Triple::renderscript64:
1465   case Triple::riscv32:
1466   case Triple::riscv64:
1467   case Triple::shave:
1468   case Triple::spir64:
1469   case Triple::spir:
1470   case Triple::wasm32:
1471   case Triple::wasm64:
1472   case Triple::x86:
1473   case Triple::x86_64:
1474   case Triple::xcore:
1475   case Triple::ve:
1476 
1477   // ARM is intentionally unsupported here, changing the architecture would
1478   // drop any arch suffixes.
1479   case Triple::arm:
1480   case Triple::thumb:
1481     T.setArch(UnknownArch);
1482     break;
1483 
1484   case Triple::aarch64: T.setArch(Triple::aarch64_be); break;
1485   case Triple::bpfel:   T.setArch(Triple::bpfeb);      break;
1486   case Triple::mips64el:T.setArch(Triple::mips64);     break;
1487   case Triple::mipsel:  T.setArch(Triple::mips);       break;
1488   case Triple::ppc64le: T.setArch(Triple::ppc64);      break;
1489   case Triple::sparcel: T.setArch(Triple::sparc);      break;
1490   case Triple::tcele:   T.setArch(Triple::tce);        break;
1491   default:
1492     llvm_unreachable("getBigEndianArchVariant: unknown triple.");
1493   }
1494   return T;
1495 }
1496 
1497 Triple Triple::getLittleEndianArchVariant() const {
1498   Triple T(*this);
1499   if (isLittleEndian())
1500     return T;
1501 
1502   switch (getArch()) {
1503   case Triple::UnknownArch:
1504   case Triple::lanai:
1505   case Triple::ppc:
1506   case Triple::sparcv9:
1507   case Triple::systemz:
1508 
1509   // ARM is intentionally unsupported here, changing the architecture would
1510   // drop any arch suffixes.
1511   case Triple::armeb:
1512   case Triple::thumbeb:
1513     T.setArch(UnknownArch);
1514     break;
1515 
1516   case Triple::aarch64_be: T.setArch(Triple::aarch64);  break;
1517   case Triple::bpfeb:      T.setArch(Triple::bpfel);    break;
1518   case Triple::mips64:     T.setArch(Triple::mips64el); break;
1519   case Triple::mips:       T.setArch(Triple::mipsel);   break;
1520   case Triple::ppc64:      T.setArch(Triple::ppc64le);  break;
1521   case Triple::sparc:      T.setArch(Triple::sparcel);  break;
1522   case Triple::tce:        T.setArch(Triple::tcele);    break;
1523   default:
1524     llvm_unreachable("getLittleEndianArchVariant: unknown triple.");
1525   }
1526   return T;
1527 }
1528 
1529 bool Triple::isLittleEndian() const {
1530   switch (getArch()) {
1531   case Triple::aarch64:
1532   case Triple::aarch64_32:
1533   case Triple::amdgcn:
1534   case Triple::amdil64:
1535   case Triple::amdil:
1536   case Triple::arm:
1537   case Triple::avr:
1538   case Triple::bpfel:
1539   case Triple::hexagon:
1540   case Triple::hsail64:
1541   case Triple::hsail:
1542   case Triple::kalimba:
1543   case Triple::le32:
1544   case Triple::le64:
1545   case Triple::mips64el:
1546   case Triple::mipsel:
1547   case Triple::msp430:
1548   case Triple::nvptx64:
1549   case Triple::nvptx:
1550   case Triple::ppc64le:
1551   case Triple::r600:
1552   case Triple::renderscript32:
1553   case Triple::renderscript64:
1554   case Triple::riscv32:
1555   case Triple::riscv64:
1556   case Triple::shave:
1557   case Triple::sparcel:
1558   case Triple::spir64:
1559   case Triple::spir:
1560   case Triple::tcele:
1561   case Triple::thumb:
1562   case Triple::ve:
1563   case Triple::wasm32:
1564   case Triple::wasm64:
1565   case Triple::x86:
1566   case Triple::x86_64:
1567   case Triple::xcore:
1568     return true;
1569   default:
1570     return false;
1571   }
1572 }
1573 
1574 bool Triple::isCompatibleWith(const Triple &Other) const {
1575   // ARM and Thumb triples are compatible, if subarch, vendor and OS match.
1576   if ((getArch() == Triple::thumb && Other.getArch() == Triple::arm) ||
1577       (getArch() == Triple::arm && Other.getArch() == Triple::thumb) ||
1578       (getArch() == Triple::thumbeb && Other.getArch() == Triple::armeb) ||
1579       (getArch() == Triple::armeb && Other.getArch() == Triple::thumbeb)) {
1580     if (getVendor() == Triple::Apple)
1581       return getSubArch() == Other.getSubArch() &&
1582              getVendor() == Other.getVendor() && getOS() == Other.getOS();
1583     else
1584       return getSubArch() == Other.getSubArch() &&
1585              getVendor() == Other.getVendor() && getOS() == Other.getOS() &&
1586              getEnvironment() == Other.getEnvironment() &&
1587              getObjectFormat() == Other.getObjectFormat();
1588   }
1589 
1590   // If vendor is apple, ignore the version number.
1591   if (getVendor() == Triple::Apple)
1592     return getArch() == Other.getArch() && getSubArch() == Other.getSubArch() &&
1593            getVendor() == Other.getVendor() && getOS() == Other.getOS();
1594 
1595   return *this == Other;
1596 }
1597 
1598 std::string Triple::merge(const Triple &Other) const {
1599   // If vendor is apple, pick the triple with the larger version number.
1600   if (getVendor() == Triple::Apple)
1601     if (Other.isOSVersionLT(*this))
1602       return str();
1603 
1604   return Other.str();
1605 }
1606 
1607 StringRef Triple::getARMCPUForArch(StringRef MArch) const {
1608   if (MArch.empty())
1609     MArch = getArchName();
1610   MArch = ARM::getCanonicalArchName(MArch);
1611 
1612   // Some defaults are forced.
1613   switch (getOS()) {
1614   case llvm::Triple::FreeBSD:
1615   case llvm::Triple::NetBSD:
1616     if (!MArch.empty() && MArch == "v6")
1617       return "arm1176jzf-s";
1618     break;
1619   case llvm::Triple::Win32:
1620     // FIXME: this is invalid for WindowsCE
1621     return "cortex-a9";
1622   case llvm::Triple::IOS:
1623   case llvm::Triple::MacOSX:
1624   case llvm::Triple::TvOS:
1625   case llvm::Triple::WatchOS:
1626     if (MArch == "v7k")
1627       return "cortex-a7";
1628     break;
1629   default:
1630     break;
1631   }
1632 
1633   if (MArch.empty())
1634     return StringRef();
1635 
1636   StringRef CPU = ARM::getDefaultCPU(MArch);
1637   if (!CPU.empty() && !CPU.equals("invalid"))
1638     return CPU;
1639 
1640   // If no specific architecture version is requested, return the minimum CPU
1641   // required by the OS and environment.
1642   switch (getOS()) {
1643   case llvm::Triple::NetBSD:
1644     switch (getEnvironment()) {
1645     case llvm::Triple::EABI:
1646     case llvm::Triple::EABIHF:
1647     case llvm::Triple::GNUEABI:
1648     case llvm::Triple::GNUEABIHF:
1649       return "arm926ej-s";
1650     default:
1651       return "strongarm";
1652     }
1653   case llvm::Triple::NaCl:
1654   case llvm::Triple::OpenBSD:
1655     return "cortex-a8";
1656   default:
1657     switch (getEnvironment()) {
1658     case llvm::Triple::EABIHF:
1659     case llvm::Triple::GNUEABIHF:
1660     case llvm::Triple::MuslEABIHF:
1661       return "arm1176jzf-s";
1662     default:
1663       return "arm7tdmi";
1664     }
1665   }
1666 
1667   llvm_unreachable("invalid arch name");
1668 }
1669