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