xref: /llvm-project/llvm/lib/TargetParser/Triple.cpp (revision 16e9601e193e026d7f3f27e87f0adb81acf5969b)
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/TargetParser/Triple.h"
10 #include "llvm/ADT/DenseMap.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/SwapByteOrder.h"
16 #include "llvm/Support/VersionTuple.h"
17 #include "llvm/TargetParser/ARMTargetParser.h"
18 #include "llvm/TargetParser/ARMTargetParserCommon.h"
19 #include "llvm/TargetParser/Host.h"
20 #include <cassert>
21 #include <cstring>
22 using namespace llvm;
23 
24 StringRef Triple::getArchTypeName(ArchType Kind) {
25   switch (Kind) {
26   case UnknownArch:    return "unknown";
27 
28   case aarch64:        return "aarch64";
29   case aarch64_32:     return "aarch64_32";
30   case aarch64_be:     return "aarch64_be";
31   case amdgcn:         return "amdgcn";
32   case amdil64:        return "amdil64";
33   case amdil:          return "amdil";
34   case arc:            return "arc";
35   case arm:            return "arm";
36   case armeb:          return "armeb";
37   case avr:            return "avr";
38   case bpfeb:          return "bpfeb";
39   case bpfel:          return "bpfel";
40   case csky:           return "csky";
41   case dxil:           return "dxil";
42   case hexagon:        return "hexagon";
43   case hsail64:        return "hsail64";
44   case hsail:          return "hsail";
45   case kalimba:        return "kalimba";
46   case lanai:          return "lanai";
47   case loongarch32:    return "loongarch32";
48   case loongarch64:    return "loongarch64";
49   case m68k:           return "m68k";
50   case mips64:         return "mips64";
51   case mips64el:       return "mips64el";
52   case mips:           return "mips";
53   case mipsel:         return "mipsel";
54   case msp430:         return "msp430";
55   case nvptx64:        return "nvptx64";
56   case nvptx:          return "nvptx";
57   case ppc64:          return "powerpc64";
58   case ppc64le:        return "powerpc64le";
59   case ppc:            return "powerpc";
60   case ppcle:          return "powerpcle";
61   case r600:           return "r600";
62   case renderscript32: return "renderscript32";
63   case renderscript64: return "renderscript64";
64   case riscv32:        return "riscv32";
65   case riscv64:        return "riscv64";
66   case shave:          return "shave";
67   case sparc:          return "sparc";
68   case sparcel:        return "sparcel";
69   case sparcv9:        return "sparcv9";
70   case spir64:         return "spir64";
71   case spir:           return "spir";
72   case spirv:          return "spirv";
73   case spirv32:        return "spirv32";
74   case spirv64:        return "spirv64";
75   case systemz:        return "s390x";
76   case tce:            return "tce";
77   case tcele:          return "tcele";
78   case thumb:          return "thumb";
79   case thumbeb:        return "thumbeb";
80   case ve:             return "ve";
81   case wasm32:         return "wasm32";
82   case wasm64:         return "wasm64";
83   case x86:            return "i386";
84   case x86_64:         return "x86_64";
85   case xcore:          return "xcore";
86   case xtensa:         return "xtensa";
87   }
88 
89   llvm_unreachable("Invalid ArchType!");
90 }
91 
92 StringRef Triple::getArchName(ArchType Kind, SubArchType SubArch) {
93   switch (Kind) {
94   case Triple::mips:
95     if (SubArch == MipsSubArch_r6)
96       return "mipsisa32r6";
97     break;
98   case Triple::mipsel:
99     if (SubArch == MipsSubArch_r6)
100       return "mipsisa32r6el";
101     break;
102   case Triple::mips64:
103     if (SubArch == MipsSubArch_r6)
104       return "mipsisa64r6";
105     break;
106   case Triple::mips64el:
107     if (SubArch == MipsSubArch_r6)
108       return "mipsisa64r6el";
109     break;
110   case Triple::aarch64:
111     if (SubArch == AArch64SubArch_arm64ec)
112       return "arm64ec";
113     if (SubArch == AArch64SubArch_arm64e)
114       return "arm64e";
115     break;
116   case Triple::spirv:
117     switch (SubArch) {
118     case Triple::SPIRVSubArch_v10:
119       return "spirv1.0";
120     case Triple::SPIRVSubArch_v11:
121       return "spirv1.1";
122     case Triple::SPIRVSubArch_v12:
123       return "spirv1.2";
124     case Triple::SPIRVSubArch_v13:
125       return "spirv1.3";
126     case Triple::SPIRVSubArch_v14:
127       return "spirv1.4";
128     case Triple::SPIRVSubArch_v15:
129       return "spirv1.5";
130     case Triple::SPIRVSubArch_v16:
131       return "spirv1.6";
132     default:
133       break;
134     }
135     break;
136   case Triple::dxil:
137     switch (SubArch) {
138     case Triple::NoSubArch:
139     case Triple::DXILSubArch_v1_0:
140       return "dxilv1.0";
141     case Triple::DXILSubArch_v1_1:
142       return "dxilv1.1";
143     case Triple::DXILSubArch_v1_2:
144       return "dxilv1.2";
145     case Triple::DXILSubArch_v1_3:
146       return "dxilv1.3";
147     case Triple::DXILSubArch_v1_4:
148       return "dxilv1.4";
149     case Triple::DXILSubArch_v1_5:
150       return "dxilv1.5";
151     case Triple::DXILSubArch_v1_6:
152       return "dxilv1.6";
153     case Triple::DXILSubArch_v1_7:
154       return "dxilv1.7";
155     case Triple::DXILSubArch_v1_8:
156       return "dxilv1.8";
157     default:
158       break;
159     }
160     break;
161   default:
162     break;
163   }
164   return getArchTypeName(Kind);
165 }
166 
167 StringRef Triple::getArchTypePrefix(ArchType Kind) {
168   switch (Kind) {
169   default:
170     return StringRef();
171 
172   case aarch64:
173   case aarch64_be:
174   case aarch64_32:  return "aarch64";
175 
176   case arc:         return "arc";
177 
178   case arm:
179   case armeb:
180   case thumb:
181   case thumbeb:     return "arm";
182 
183   case avr:         return "avr";
184 
185   case ppc64:
186   case ppc64le:
187   case ppc:
188   case ppcle:       return "ppc";
189 
190   case m68k:        return "m68k";
191 
192   case mips:
193   case mipsel:
194   case mips64:
195   case mips64el:    return "mips";
196 
197   case hexagon:     return "hexagon";
198 
199   case amdgcn:      return "amdgcn";
200   case r600:        return "r600";
201 
202   case bpfel:
203   case bpfeb:       return "bpf";
204 
205   case sparcv9:
206   case sparcel:
207   case sparc:       return "sparc";
208 
209   case systemz:     return "s390";
210 
211   case x86:
212   case x86_64:      return "x86";
213 
214   case xcore:       return "xcore";
215 
216   // NVPTX intrinsics are namespaced under nvvm.
217   case nvptx:       return "nvvm";
218   case nvptx64:     return "nvvm";
219 
220   case amdil:
221   case amdil64:     return "amdil";
222 
223   case hsail:
224   case hsail64:     return "hsail";
225 
226   case spir:
227   case spir64:      return "spir";
228 
229   case spirv:
230   case spirv32:
231   case spirv64:     return "spv";
232 
233   case kalimba:     return "kalimba";
234   case lanai:       return "lanai";
235   case shave:       return "shave";
236   case wasm32:
237   case wasm64:      return "wasm";
238 
239   case riscv32:
240   case riscv64:     return "riscv";
241 
242   case ve:          return "ve";
243   case csky:        return "csky";
244 
245   case loongarch32:
246   case loongarch64: return "loongarch";
247 
248   case dxil:        return "dx";
249 
250   case xtensa:      return "xtensa";
251   }
252 }
253 
254 StringRef Triple::getVendorTypeName(VendorType Kind) {
255   switch (Kind) {
256   case UnknownVendor: return "unknown";
257 
258   case AMD: return "amd";
259   case Apple: return "apple";
260   case CSR: return "csr";
261   case Freescale: return "fsl";
262   case IBM: return "ibm";
263   case ImaginationTechnologies: return "img";
264   case Intel:
265     return "intel";
266   case Mesa: return "mesa";
267   case MipsTechnologies: return "mti";
268   case NVIDIA: return "nvidia";
269   case OpenEmbedded: return "oe";
270   case PC: return "pc";
271   case SCEI: return "scei";
272   case SUSE: return "suse";
273   }
274 
275   llvm_unreachable("Invalid VendorType!");
276 }
277 
278 StringRef Triple::getOSTypeName(OSType Kind) {
279   switch (Kind) {
280   case UnknownOS: return "unknown";
281 
282   case AIX: return "aix";
283   case AMDHSA: return "amdhsa";
284   case AMDPAL: return "amdpal";
285   case BridgeOS: return "bridgeos";
286   case CUDA: return "cuda";
287   case Darwin: return "darwin";
288   case DragonFly: return "dragonfly";
289   case DriverKit: return "driverkit";
290   case ELFIAMCU: return "elfiamcu";
291   case Emscripten: return "emscripten";
292   case FreeBSD: return "freebsd";
293   case Fuchsia: return "fuchsia";
294   case Haiku: return "haiku";
295   case HermitCore: return "hermit";
296   case Hurd: return "hurd";
297   case IOS: return "ios";
298   case KFreeBSD: return "kfreebsd";
299   case Linux: return "linux";
300   case Lv2: return "lv2";
301   case MacOSX: return "macosx";
302   case Mesa3D: return "mesa3d";
303   case NVCL: return "nvcl";
304   case NaCl: return "nacl";
305   case NetBSD: return "netbsd";
306   case OpenBSD: return "openbsd";
307   case PS4: return "ps4";
308   case PS5: return "ps5";
309   case RTEMS: return "rtems";
310   case Solaris: return "solaris";
311   case Serenity: return "serenity";
312   case TvOS: return "tvos";
313   case UEFI: return "uefi";
314   case WASI: return "wasi";
315   case WatchOS: return "watchos";
316   case Win32: return "windows";
317   case ZOS: return "zos";
318   case ShaderModel: return "shadermodel";
319   case LiteOS: return "liteos";
320   case XROS: return "xros";
321   case Vulkan: return "vulkan";
322   }
323 
324   llvm_unreachable("Invalid OSType");
325 }
326 
327 StringRef Triple::getEnvironmentTypeName(EnvironmentType Kind) {
328   switch (Kind) {
329   case UnknownEnvironment: return "unknown";
330   case Android: return "android";
331   case CODE16: return "code16";
332   case CoreCLR: return "coreclr";
333   case Cygnus: return "cygnus";
334   case EABI: return "eabi";
335   case EABIHF: return "eabihf";
336   case GNU: return "gnu";
337   case GNUT64: return "gnut64";
338   case GNUABI64: return "gnuabi64";
339   case GNUABIN32: return "gnuabin32";
340   case GNUEABI: return "gnueabi";
341   case GNUEABIT64: return "gnueabit64";
342   case GNUEABIHF: return "gnueabihf";
343   case GNUEABIHFT64: return "gnueabihft64";
344   case GNUF32: return "gnuf32";
345   case GNUF64: return "gnuf64";
346   case GNUSF: return "gnusf";
347   case GNUX32: return "gnux32";
348   case GNUILP32: return "gnu_ilp32";
349   case Itanium: return "itanium";
350   case MSVC: return "msvc";
351   case MacABI: return "macabi";
352   case Musl: return "musl";
353   case MuslABIN32:
354     return "muslabin32";
355   case MuslABI64:
356     return "muslabi64";
357   case MuslEABI: return "musleabi";
358   case MuslEABIHF: return "musleabihf";
359   case MuslF32:
360     return "muslf32";
361   case MuslSF:
362     return "muslsf";
363   case MuslX32: return "muslx32";
364   case Simulator: return "simulator";
365   case Pixel: return "pixel";
366   case Vertex: return "vertex";
367   case Geometry: return "geometry";
368   case Hull: return "hull";
369   case Domain: return "domain";
370   case Compute: return "compute";
371   case Library: return "library";
372   case RayGeneration: return "raygeneration";
373   case Intersection: return "intersection";
374   case AnyHit: return "anyhit";
375   case ClosestHit: return "closesthit";
376   case Miss: return "miss";
377   case Callable: return "callable";
378   case Mesh: return "mesh";
379   case Amplification: return "amplification";
380   case OpenCL:
381     return "opencl";
382   case OpenHOS: return "ohos";
383   case PAuthTest:
384     return "pauthtest";
385   case LLVM:
386     return "llvm";
387   }
388 
389   llvm_unreachable("Invalid EnvironmentType!");
390 }
391 
392 StringRef Triple::getObjectFormatTypeName(ObjectFormatType Kind) {
393   switch (Kind) {
394   case UnknownObjectFormat: return "";
395   case COFF: return "coff";
396   case ELF: return "elf";
397   case GOFF: return "goff";
398   case MachO: return "macho";
399   case Wasm: return "wasm";
400   case XCOFF: return "xcoff";
401   case DXContainer: return "dxcontainer";
402   case SPIRV: return "spirv";
403   }
404   llvm_unreachable("unknown object format type");
405 }
406 
407 static Triple::ArchType parseBPFArch(StringRef ArchName) {
408   if (ArchName == "bpf") {
409     if (sys::IsLittleEndianHost)
410       return Triple::bpfel;
411     else
412       return Triple::bpfeb;
413   } else if (ArchName == "bpf_be" || ArchName == "bpfeb") {
414     return Triple::bpfeb;
415   } else if (ArchName == "bpf_le" || ArchName == "bpfel") {
416     return Triple::bpfel;
417   } else {
418     return Triple::UnknownArch;
419   }
420 }
421 
422 Triple::ArchType Triple::getArchTypeForLLVMName(StringRef Name) {
423   Triple::ArchType BPFArch(parseBPFArch(Name));
424   return StringSwitch<Triple::ArchType>(Name)
425     .Case("aarch64", aarch64)
426     .Case("aarch64_be", aarch64_be)
427     .Case("aarch64_32", aarch64_32)
428     .Case("arc", arc)
429     .Case("arm64", aarch64) // "arm64" is an alias for "aarch64"
430     .Case("arm64_32", aarch64_32)
431     .Case("arm", arm)
432     .Case("armeb", armeb)
433     .Case("avr", avr)
434     .StartsWith("bpf", BPFArch)
435     .Case("m68k", m68k)
436     .Case("mips", mips)
437     .Case("mipsel", mipsel)
438     .Case("mips64", mips64)
439     .Case("mips64el", mips64el)
440     .Case("msp430", msp430)
441     .Case("ppc64", ppc64)
442     .Case("ppc32", ppc)
443     .Case("ppc", ppc)
444     .Case("ppc32le", ppcle)
445     .Case("ppcle", ppcle)
446     .Case("ppc64le", ppc64le)
447     .Case("r600", r600)
448     .Case("amdgcn", amdgcn)
449     .Case("riscv32", riscv32)
450     .Case("riscv64", riscv64)
451     .Case("hexagon", hexagon)
452     .Case("sparc", sparc)
453     .Case("sparcel", sparcel)
454     .Case("sparcv9", sparcv9)
455     .Case("s390x", systemz)
456     .Case("systemz", systemz)
457     .Case("tce", tce)
458     .Case("tcele", tcele)
459     .Case("thumb", thumb)
460     .Case("thumbeb", thumbeb)
461     .Case("x86", x86)
462     .Case("i386", x86)
463     .Case("x86-64", x86_64)
464     .Case("xcore", xcore)
465     .Case("nvptx", nvptx)
466     .Case("nvptx64", nvptx64)
467     .Case("amdil", amdil)
468     .Case("amdil64", amdil64)
469     .Case("hsail", hsail)
470     .Case("hsail64", hsail64)
471     .Case("spir", spir)
472     .Case("spir64", spir64)
473     .Case("spirv", spirv)
474     .Case("spirv32", spirv32)
475     .Case("spirv64", spirv64)
476     .Case("kalimba", kalimba)
477     .Case("lanai", lanai)
478     .Case("shave", shave)
479     .Case("wasm32", wasm32)
480     .Case("wasm64", wasm64)
481     .Case("renderscript32", renderscript32)
482     .Case("renderscript64", renderscript64)
483     .Case("ve", ve)
484     .Case("csky", csky)
485     .Case("loongarch32", loongarch32)
486     .Case("loongarch64", loongarch64)
487     .Case("dxil", dxil)
488     .Case("xtensa", xtensa)
489     .Default(UnknownArch);
490 }
491 
492 static Triple::ArchType parseARMArch(StringRef ArchName) {
493   ARM::ISAKind ISA = ARM::parseArchISA(ArchName);
494   ARM::EndianKind ENDIAN = ARM::parseArchEndian(ArchName);
495 
496   Triple::ArchType arch = Triple::UnknownArch;
497   switch (ENDIAN) {
498   case ARM::EndianKind::LITTLE: {
499     switch (ISA) {
500     case ARM::ISAKind::ARM:
501       arch = Triple::arm;
502       break;
503     case ARM::ISAKind::THUMB:
504       arch = Triple::thumb;
505       break;
506     case ARM::ISAKind::AARCH64:
507       arch = Triple::aarch64;
508       break;
509     case ARM::ISAKind::INVALID:
510       break;
511     }
512     break;
513   }
514   case ARM::EndianKind::BIG: {
515     switch (ISA) {
516     case ARM::ISAKind::ARM:
517       arch = Triple::armeb;
518       break;
519     case ARM::ISAKind::THUMB:
520       arch = Triple::thumbeb;
521       break;
522     case ARM::ISAKind::AARCH64:
523       arch = Triple::aarch64_be;
524       break;
525     case ARM::ISAKind::INVALID:
526       break;
527     }
528     break;
529   }
530   case ARM::EndianKind::INVALID: {
531     break;
532   }
533   }
534 
535   ArchName = ARM::getCanonicalArchName(ArchName);
536   if (ArchName.empty())
537     return Triple::UnknownArch;
538 
539   // Thumb only exists in v4+
540   if (ISA == ARM::ISAKind::THUMB &&
541       (ArchName.starts_with("v2") || ArchName.starts_with("v3")))
542     return Triple::UnknownArch;
543 
544   // Thumb only for v6m
545   ARM::ProfileKind Profile = ARM::parseArchProfile(ArchName);
546   unsigned Version = ARM::parseArchVersion(ArchName);
547   if (Profile == ARM::ProfileKind::M && Version == 6) {
548     if (ENDIAN == ARM::EndianKind::BIG)
549       return Triple::thumbeb;
550     else
551       return Triple::thumb;
552   }
553 
554   return arch;
555 }
556 
557 static Triple::ArchType parseArch(StringRef ArchName) {
558   auto AT =
559       StringSwitch<Triple::ArchType>(ArchName)
560           .Cases("i386", "i486", "i586", "i686", Triple::x86)
561           // FIXME: Do we need to support these?
562           .Cases("i786", "i886", "i986", Triple::x86)
563           .Cases("amd64", "x86_64", "x86_64h", Triple::x86_64)
564           .Cases("powerpc", "powerpcspe", "ppc", "ppc32", Triple::ppc)
565           .Cases("powerpcle", "ppcle", "ppc32le", Triple::ppcle)
566           .Cases("powerpc64", "ppu", "ppc64", Triple::ppc64)
567           .Cases("powerpc64le", "ppc64le", Triple::ppc64le)
568           .Case("xscale", Triple::arm)
569           .Case("xscaleeb", Triple::armeb)
570           .Case("aarch64", Triple::aarch64)
571           .Case("aarch64_be", Triple::aarch64_be)
572           .Case("aarch64_32", Triple::aarch64_32)
573           .Case("arc", Triple::arc)
574           .Case("arm64", Triple::aarch64)
575           .Case("arm64_32", Triple::aarch64_32)
576           .Case("arm64e", Triple::aarch64)
577           .Case("arm64ec", Triple::aarch64)
578           .Case("arm", Triple::arm)
579           .Case("armeb", Triple::armeb)
580           .Case("thumb", Triple::thumb)
581           .Case("thumbeb", Triple::thumbeb)
582           .Case("avr", Triple::avr)
583           .Case("m68k", Triple::m68k)
584           .Case("msp430", Triple::msp430)
585           .Cases("mips", "mipseb", "mipsallegrex", "mipsisa32r6", "mipsr6",
586                  Triple::mips)
587           .Cases("mipsel", "mipsallegrexel", "mipsisa32r6el", "mipsr6el",
588                  Triple::mipsel)
589           .Cases("mips64", "mips64eb", "mipsn32", "mipsisa64r6", "mips64r6",
590                  "mipsn32r6", Triple::mips64)
591           .Cases("mips64el", "mipsn32el", "mipsisa64r6el", "mips64r6el",
592                  "mipsn32r6el", Triple::mips64el)
593           .Case("r600", Triple::r600)
594           .Case("amdgcn", Triple::amdgcn)
595           .Case("riscv32", Triple::riscv32)
596           .Case("riscv64", Triple::riscv64)
597           .Case("hexagon", Triple::hexagon)
598           .Cases("s390x", "systemz", Triple::systemz)
599           .Case("sparc", Triple::sparc)
600           .Case("sparcel", Triple::sparcel)
601           .Cases("sparcv9", "sparc64", Triple::sparcv9)
602           .Case("tce", Triple::tce)
603           .Case("tcele", Triple::tcele)
604           .Case("xcore", Triple::xcore)
605           .Case("nvptx", Triple::nvptx)
606           .Case("nvptx64", Triple::nvptx64)
607           .Case("amdil", Triple::amdil)
608           .Case("amdil64", Triple::amdil64)
609           .Case("hsail", Triple::hsail)
610           .Case("hsail64", Triple::hsail64)
611           .Case("spir", Triple::spir)
612           .Case("spir64", Triple::spir64)
613           .Cases("spirv", "spirv1.5", "spirv1.6", Triple::spirv)
614           .Cases("spirv32", "spirv32v1.0", "spirv32v1.1", "spirv32v1.2",
615             "spirv32v1.3", "spirv32v1.4", "spirv32v1.5",
616             "spirv32v1.6", Triple::spirv32)
617           .Cases("spirv64", "spirv64v1.0", "spirv64v1.1", "spirv64v1.2",
618             "spirv64v1.3", "spirv64v1.4", "spirv64v1.5",
619             "spirv64v1.6", Triple::spirv64)
620           .StartsWith("kalimba", Triple::kalimba)
621           .Case("lanai", Triple::lanai)
622           .Case("renderscript32", Triple::renderscript32)
623           .Case("renderscript64", Triple::renderscript64)
624           .Case("shave", Triple::shave)
625           .Case("ve", Triple::ve)
626           .Case("wasm32", Triple::wasm32)
627           .Case("wasm64", Triple::wasm64)
628           .Case("csky", Triple::csky)
629           .Case("loongarch32", Triple::loongarch32)
630           .Case("loongarch64", Triple::loongarch64)
631           .Cases("dxil", "dxilv1.0", "dxilv1.1", "dxilv1.2", "dxilv1.3",
632                  "dxilv1.4", "dxilv1.5", "dxilv1.6", "dxilv1.7", "dxilv1.8",
633                  Triple::dxil)
634           .Case("xtensa", Triple::xtensa)
635           .Default(Triple::UnknownArch);
636 
637   // Some architectures require special parsing logic just to compute the
638   // ArchType result.
639   if (AT == Triple::UnknownArch) {
640     if (ArchName.starts_with("arm") || ArchName.starts_with("thumb") ||
641         ArchName.starts_with("aarch64"))
642       return parseARMArch(ArchName);
643     if (ArchName.starts_with("bpf"))
644       return parseBPFArch(ArchName);
645   }
646 
647   return AT;
648 }
649 
650 static Triple::VendorType parseVendor(StringRef VendorName) {
651   return StringSwitch<Triple::VendorType>(VendorName)
652       .Case("apple", Triple::Apple)
653       .Case("pc", Triple::PC)
654       .Case("scei", Triple::SCEI)
655       .Case("sie", Triple::SCEI)
656       .Case("fsl", Triple::Freescale)
657       .Case("ibm", Triple::IBM)
658       .Case("img", Triple::ImaginationTechnologies)
659       .Case("mti", Triple::MipsTechnologies)
660       .Case("nvidia", Triple::NVIDIA)
661       .Case("csr", Triple::CSR)
662       .Case("amd", Triple::AMD)
663       .Case("mesa", Triple::Mesa)
664       .Case("suse", Triple::SUSE)
665       .Case("oe", Triple::OpenEmbedded)
666       .Case("intel", Triple::Intel)
667       .Default(Triple::UnknownVendor);
668 }
669 
670 static Triple::OSType parseOS(StringRef OSName) {
671   return StringSwitch<Triple::OSType>(OSName)
672     .StartsWith("darwin", Triple::Darwin)
673     .StartsWith("dragonfly", Triple::DragonFly)
674     .StartsWith("freebsd", Triple::FreeBSD)
675     .StartsWith("fuchsia", Triple::Fuchsia)
676     .StartsWith("ios", Triple::IOS)
677     .StartsWith("kfreebsd", Triple::KFreeBSD)
678     .StartsWith("linux", Triple::Linux)
679     .StartsWith("lv2", Triple::Lv2)
680     .StartsWith("macos", Triple::MacOSX)
681     .StartsWith("netbsd", Triple::NetBSD)
682     .StartsWith("openbsd", Triple::OpenBSD)
683     .StartsWith("solaris", Triple::Solaris)
684     .StartsWith("uefi", Triple::UEFI)
685     .StartsWith("win32", Triple::Win32)
686     .StartsWith("windows", Triple::Win32)
687     .StartsWith("zos", Triple::ZOS)
688     .StartsWith("haiku", Triple::Haiku)
689     .StartsWith("rtems", Triple::RTEMS)
690     .StartsWith("nacl", Triple::NaCl)
691     .StartsWith("aix", Triple::AIX)
692     .StartsWith("cuda", Triple::CUDA)
693     .StartsWith("nvcl", Triple::NVCL)
694     .StartsWith("amdhsa", Triple::AMDHSA)
695     .StartsWith("ps4", Triple::PS4)
696     .StartsWith("ps5", Triple::PS5)
697     .StartsWith("elfiamcu", Triple::ELFIAMCU)
698     .StartsWith("tvos", Triple::TvOS)
699     .StartsWith("watchos", Triple::WatchOS)
700     .StartsWith("bridgeos", Triple::BridgeOS)
701     .StartsWith("driverkit", Triple::DriverKit)
702     .StartsWith("xros", Triple::XROS)
703     .StartsWith("visionos", Triple::XROS)
704     .StartsWith("mesa3d", Triple::Mesa3D)
705     .StartsWith("amdpal", Triple::AMDPAL)
706     .StartsWith("hermit", Triple::HermitCore)
707     .StartsWith("hurd", Triple::Hurd)
708     .StartsWith("wasi", Triple::WASI)
709     .StartsWith("emscripten", Triple::Emscripten)
710     .StartsWith("shadermodel", Triple::ShaderModel)
711     .StartsWith("liteos", Triple::LiteOS)
712     .StartsWith("serenity", Triple::Serenity)
713     .StartsWith("vulkan", Triple::Vulkan)
714     .Default(Triple::UnknownOS);
715 }
716 
717 static Triple::EnvironmentType parseEnvironment(StringRef EnvironmentName) {
718   return StringSwitch<Triple::EnvironmentType>(EnvironmentName)
719       .StartsWith("eabihf", Triple::EABIHF)
720       .StartsWith("eabi", Triple::EABI)
721       .StartsWith("gnuabin32", Triple::GNUABIN32)
722       .StartsWith("gnuabi64", Triple::GNUABI64)
723       .StartsWith("gnueabihft64", Triple::GNUEABIHFT64)
724       .StartsWith("gnueabihf", Triple::GNUEABIHF)
725       .StartsWith("gnueabit64", Triple::GNUEABIT64)
726       .StartsWith("gnueabi", Triple::GNUEABI)
727       .StartsWith("gnuf32", Triple::GNUF32)
728       .StartsWith("gnuf64", Triple::GNUF64)
729       .StartsWith("gnusf", Triple::GNUSF)
730       .StartsWith("gnux32", Triple::GNUX32)
731       .StartsWith("gnu_ilp32", Triple::GNUILP32)
732       .StartsWith("code16", Triple::CODE16)
733       .StartsWith("gnut64", Triple::GNUT64)
734       .StartsWith("gnu", Triple::GNU)
735       .StartsWith("android", Triple::Android)
736       .StartsWith("muslabin32", Triple::MuslABIN32)
737       .StartsWith("muslabi64", Triple::MuslABI64)
738       .StartsWith("musleabihf", Triple::MuslEABIHF)
739       .StartsWith("musleabi", Triple::MuslEABI)
740       .StartsWith("muslf32", Triple::MuslF32)
741       .StartsWith("muslsf", Triple::MuslSF)
742       .StartsWith("muslx32", Triple::MuslX32)
743       .StartsWith("musl", Triple::Musl)
744       .StartsWith("msvc", Triple::MSVC)
745       .StartsWith("itanium", Triple::Itanium)
746       .StartsWith("cygnus", Triple::Cygnus)
747       .StartsWith("coreclr", Triple::CoreCLR)
748       .StartsWith("simulator", Triple::Simulator)
749       .StartsWith("macabi", Triple::MacABI)
750       .StartsWith("pixel", Triple::Pixel)
751       .StartsWith("vertex", Triple::Vertex)
752       .StartsWith("geometry", Triple::Geometry)
753       .StartsWith("hull", Triple::Hull)
754       .StartsWith("domain", Triple::Domain)
755       .StartsWith("compute", Triple::Compute)
756       .StartsWith("library", Triple::Library)
757       .StartsWith("raygeneration", Triple::RayGeneration)
758       .StartsWith("intersection", Triple::Intersection)
759       .StartsWith("anyhit", Triple::AnyHit)
760       .StartsWith("closesthit", Triple::ClosestHit)
761       .StartsWith("miss", Triple::Miss)
762       .StartsWith("callable", Triple::Callable)
763       .StartsWith("mesh", Triple::Mesh)
764       .StartsWith("amplification", Triple::Amplification)
765       .StartsWith("opencl", Triple::OpenCL)
766       .StartsWith("ohos", Triple::OpenHOS)
767       .StartsWith("pauthtest", Triple::PAuthTest)
768       .StartsWith("llvm", Triple::LLVM)
769       .Default(Triple::UnknownEnvironment);
770 }
771 
772 static Triple::ObjectFormatType parseFormat(StringRef EnvironmentName) {
773   return StringSwitch<Triple::ObjectFormatType>(EnvironmentName)
774       // "xcoff" must come before "coff" because of the order-dependendent
775       // pattern matching.
776       .EndsWith("xcoff", Triple::XCOFF)
777       .EndsWith("coff", Triple::COFF)
778       .EndsWith("elf", Triple::ELF)
779       .EndsWith("goff", Triple::GOFF)
780       .EndsWith("macho", Triple::MachO)
781       .EndsWith("wasm", Triple::Wasm)
782       .EndsWith("spirv", Triple::SPIRV)
783       .Default(Triple::UnknownObjectFormat);
784 }
785 
786 static Triple::SubArchType parseSubArch(StringRef SubArchName) {
787   if (SubArchName.starts_with("mips") &&
788       (SubArchName.ends_with("r6el") || SubArchName.ends_with("r6")))
789     return Triple::MipsSubArch_r6;
790 
791   if (SubArchName == "powerpcspe")
792     return Triple::PPCSubArch_spe;
793 
794   if (SubArchName == "arm64e")
795     return Triple::AArch64SubArch_arm64e;
796 
797   if (SubArchName == "arm64ec")
798     return Triple::AArch64SubArch_arm64ec;
799 
800   if (SubArchName.starts_with("spirv"))
801     return StringSwitch<Triple::SubArchType>(SubArchName)
802         .EndsWith("v1.0", Triple::SPIRVSubArch_v10)
803         .EndsWith("v1.1", Triple::SPIRVSubArch_v11)
804         .EndsWith("v1.2", Triple::SPIRVSubArch_v12)
805         .EndsWith("v1.3", Triple::SPIRVSubArch_v13)
806         .EndsWith("v1.4", Triple::SPIRVSubArch_v14)
807         .EndsWith("v1.5", Triple::SPIRVSubArch_v15)
808         .EndsWith("v1.6", Triple::SPIRVSubArch_v16)
809         .Default(Triple::NoSubArch);
810 
811   if (SubArchName.starts_with("dxil"))
812     return StringSwitch<Triple::SubArchType>(SubArchName)
813         .EndsWith("v1.0", Triple::DXILSubArch_v1_0)
814         .EndsWith("v1.1", Triple::DXILSubArch_v1_1)
815         .EndsWith("v1.2", Triple::DXILSubArch_v1_2)
816         .EndsWith("v1.3", Triple::DXILSubArch_v1_3)
817         .EndsWith("v1.4", Triple::DXILSubArch_v1_4)
818         .EndsWith("v1.5", Triple::DXILSubArch_v1_5)
819         .EndsWith("v1.6", Triple::DXILSubArch_v1_6)
820         .EndsWith("v1.7", Triple::DXILSubArch_v1_7)
821         .EndsWith("v1.8", Triple::DXILSubArch_v1_8)
822         .Default(Triple::NoSubArch);
823 
824   StringRef ARMSubArch = ARM::getCanonicalArchName(SubArchName);
825 
826   // For now, this is the small part. Early return.
827   if (ARMSubArch.empty())
828     return StringSwitch<Triple::SubArchType>(SubArchName)
829       .EndsWith("kalimba3", Triple::KalimbaSubArch_v3)
830       .EndsWith("kalimba4", Triple::KalimbaSubArch_v4)
831       .EndsWith("kalimba5", Triple::KalimbaSubArch_v5)
832       .Default(Triple::NoSubArch);
833 
834   // ARM sub arch.
835   switch(ARM::parseArch(ARMSubArch)) {
836   case ARM::ArchKind::ARMV4:
837     return Triple::NoSubArch;
838   case ARM::ArchKind::ARMV4T:
839     return Triple::ARMSubArch_v4t;
840   case ARM::ArchKind::ARMV5T:
841     return Triple::ARMSubArch_v5;
842   case ARM::ArchKind::ARMV5TE:
843   case ARM::ArchKind::IWMMXT:
844   case ARM::ArchKind::IWMMXT2:
845   case ARM::ArchKind::XSCALE:
846   case ARM::ArchKind::ARMV5TEJ:
847     return Triple::ARMSubArch_v5te;
848   case ARM::ArchKind::ARMV6:
849     return Triple::ARMSubArch_v6;
850   case ARM::ArchKind::ARMV6K:
851   case ARM::ArchKind::ARMV6KZ:
852     return Triple::ARMSubArch_v6k;
853   case ARM::ArchKind::ARMV6T2:
854     return Triple::ARMSubArch_v6t2;
855   case ARM::ArchKind::ARMV6M:
856     return Triple::ARMSubArch_v6m;
857   case ARM::ArchKind::ARMV7A:
858   case ARM::ArchKind::ARMV7R:
859     return Triple::ARMSubArch_v7;
860   case ARM::ArchKind::ARMV7VE:
861     return Triple::ARMSubArch_v7ve;
862   case ARM::ArchKind::ARMV7K:
863     return Triple::ARMSubArch_v7k;
864   case ARM::ArchKind::ARMV7M:
865     return Triple::ARMSubArch_v7m;
866   case ARM::ArchKind::ARMV7S:
867     return Triple::ARMSubArch_v7s;
868   case ARM::ArchKind::ARMV7EM:
869     return Triple::ARMSubArch_v7em;
870   case ARM::ArchKind::ARMV8A:
871     return Triple::ARMSubArch_v8;
872   case ARM::ArchKind::ARMV8_1A:
873     return Triple::ARMSubArch_v8_1a;
874   case ARM::ArchKind::ARMV8_2A:
875     return Triple::ARMSubArch_v8_2a;
876   case ARM::ArchKind::ARMV8_3A:
877     return Triple::ARMSubArch_v8_3a;
878   case ARM::ArchKind::ARMV8_4A:
879     return Triple::ARMSubArch_v8_4a;
880   case ARM::ArchKind::ARMV8_5A:
881     return Triple::ARMSubArch_v8_5a;
882   case ARM::ArchKind::ARMV8_6A:
883     return Triple::ARMSubArch_v8_6a;
884   case ARM::ArchKind::ARMV8_7A:
885     return Triple::ARMSubArch_v8_7a;
886   case ARM::ArchKind::ARMV8_8A:
887     return Triple::ARMSubArch_v8_8a;
888   case ARM::ArchKind::ARMV8_9A:
889     return Triple::ARMSubArch_v8_9a;
890   case ARM::ArchKind::ARMV9A:
891     return Triple::ARMSubArch_v9;
892   case ARM::ArchKind::ARMV9_1A:
893     return Triple::ARMSubArch_v9_1a;
894   case ARM::ArchKind::ARMV9_2A:
895     return Triple::ARMSubArch_v9_2a;
896   case ARM::ArchKind::ARMV9_3A:
897     return Triple::ARMSubArch_v9_3a;
898   case ARM::ArchKind::ARMV9_4A:
899     return Triple::ARMSubArch_v9_4a;
900   case ARM::ArchKind::ARMV9_5A:
901     return Triple::ARMSubArch_v9_5a;
902   case ARM::ArchKind::ARMV9_6A:
903     return Triple::ARMSubArch_v9_6a;
904   case ARM::ArchKind::ARMV8R:
905     return Triple::ARMSubArch_v8r;
906   case ARM::ArchKind::ARMV8MBaseline:
907     return Triple::ARMSubArch_v8m_baseline;
908   case ARM::ArchKind::ARMV8MMainline:
909     return Triple::ARMSubArch_v8m_mainline;
910   case ARM::ArchKind::ARMV8_1MMainline:
911     return Triple::ARMSubArch_v8_1m_mainline;
912   default:
913     return Triple::NoSubArch;
914   }
915 }
916 
917 static Triple::ObjectFormatType getDefaultFormat(const Triple &T) {
918   switch (T.getArch()) {
919   case Triple::UnknownArch:
920   case Triple::aarch64:
921   case Triple::aarch64_32:
922   case Triple::arm:
923   case Triple::thumb:
924   case Triple::x86:
925   case Triple::x86_64:
926     switch (T.getOS()) {
927     case Triple::Win32:
928     case Triple::UEFI:
929       return Triple::COFF;
930     default:
931       return T.isOSDarwin() ? Triple::MachO : Triple::ELF;
932     }
933   case Triple::aarch64_be:
934   case Triple::amdgcn:
935   case Triple::amdil64:
936   case Triple::amdil:
937   case Triple::arc:
938   case Triple::armeb:
939   case Triple::avr:
940   case Triple::bpfeb:
941   case Triple::bpfel:
942   case Triple::csky:
943   case Triple::hexagon:
944   case Triple::hsail64:
945   case Triple::hsail:
946   case Triple::kalimba:
947   case Triple::lanai:
948   case Triple::loongarch32:
949   case Triple::loongarch64:
950   case Triple::m68k:
951   case Triple::mips64:
952   case Triple::mips64el:
953   case Triple::mips:
954   case Triple::msp430:
955   case Triple::nvptx64:
956   case Triple::nvptx:
957   case Triple::ppc64le:
958   case Triple::ppcle:
959   case Triple::r600:
960   case Triple::renderscript32:
961   case Triple::renderscript64:
962   case Triple::riscv32:
963   case Triple::riscv64:
964   case Triple::shave:
965   case Triple::sparc:
966   case Triple::sparcel:
967   case Triple::sparcv9:
968   case Triple::spir64:
969   case Triple::spir:
970   case Triple::tce:
971   case Triple::tcele:
972   case Triple::thumbeb:
973   case Triple::ve:
974   case Triple::xcore:
975   case Triple::xtensa:
976     return Triple::ELF;
977 
978   case Triple::mipsel:
979     if (T.isOSWindows())
980       return Triple::COFF;
981     return Triple::ELF;
982 
983   case Triple::ppc64:
984   case Triple::ppc:
985     if (T.isOSAIX())
986       return Triple::XCOFF;
987     if (T.isOSDarwin())
988       return Triple::MachO;
989     return Triple::ELF;
990 
991   case Triple::systemz:
992     if (T.isOSzOS())
993       return Triple::GOFF;
994     return Triple::ELF;
995 
996   case Triple::wasm32:
997   case Triple::wasm64:
998     return Triple::Wasm;
999 
1000   case Triple::spirv:
1001   case Triple::spirv32:
1002   case Triple::spirv64:
1003     return Triple::SPIRV;
1004 
1005   case Triple::dxil:
1006     return Triple::DXContainer;
1007   }
1008   llvm_unreachable("unknown architecture");
1009 }
1010 
1011 /// Construct a triple from the string representation provided.
1012 ///
1013 /// This stores the string representation and parses the various pieces into
1014 /// enum members.
1015 Triple::Triple(const Twine &Str)
1016     : Data(Str.str()), Arch(UnknownArch), SubArch(NoSubArch),
1017       Vendor(UnknownVendor), OS(UnknownOS), Environment(UnknownEnvironment),
1018       ObjectFormat(UnknownObjectFormat) {
1019   // Do minimal parsing by hand here.
1020   SmallVector<StringRef, 4> Components;
1021   StringRef(Data).split(Components, '-', /*MaxSplit*/ 3);
1022   if (Components.size() > 0) {
1023     Arch = parseArch(Components[0]);
1024     SubArch = parseSubArch(Components[0]);
1025     if (Components.size() > 1) {
1026       Vendor = parseVendor(Components[1]);
1027       if (Components.size() > 2) {
1028         OS = parseOS(Components[2]);
1029         if (Components.size() > 3) {
1030           Environment = parseEnvironment(Components[3]);
1031           ObjectFormat = parseFormat(Components[3]);
1032         }
1033       }
1034     } else {
1035       Environment =
1036           StringSwitch<Triple::EnvironmentType>(Components[0])
1037               .StartsWith("mipsn32", Triple::GNUABIN32)
1038               .StartsWith("mips64", Triple::GNUABI64)
1039               .StartsWith("mipsisa64", Triple::GNUABI64)
1040               .StartsWith("mipsisa32", Triple::GNU)
1041               .Cases("mips", "mipsel", "mipsr6", "mipsr6el", Triple::GNU)
1042               .Default(UnknownEnvironment);
1043     }
1044   }
1045   if (ObjectFormat == UnknownObjectFormat)
1046     ObjectFormat = getDefaultFormat(*this);
1047 }
1048 
1049 /// Construct a triple from string representations of the architecture,
1050 /// vendor, and OS.
1051 ///
1052 /// This joins each argument into a canonical string representation and parses
1053 /// them into enum members. It leaves the environment unknown and omits it from
1054 /// the string representation.
1055 Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr)
1056     : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr).str()),
1057       Arch(parseArch(ArchStr.str())),
1058       SubArch(parseSubArch(ArchStr.str())),
1059       Vendor(parseVendor(VendorStr.str())),
1060       OS(parseOS(OSStr.str())),
1061       Environment(), ObjectFormat(Triple::UnknownObjectFormat) {
1062   ObjectFormat = getDefaultFormat(*this);
1063 }
1064 
1065 /// Construct a triple from string representations of the architecture,
1066 /// vendor, OS, and environment.
1067 ///
1068 /// This joins each argument into a canonical string representation and parses
1069 /// them into enum members.
1070 Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr,
1071                const Twine &EnvironmentStr)
1072     : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr + Twine('-') +
1073             EnvironmentStr).str()),
1074       Arch(parseArch(ArchStr.str())),
1075       SubArch(parseSubArch(ArchStr.str())),
1076       Vendor(parseVendor(VendorStr.str())),
1077       OS(parseOS(OSStr.str())),
1078       Environment(parseEnvironment(EnvironmentStr.str())),
1079       ObjectFormat(parseFormat(EnvironmentStr.str())) {
1080   if (ObjectFormat == Triple::UnknownObjectFormat)
1081     ObjectFormat = getDefaultFormat(*this);
1082 }
1083 
1084 static VersionTuple parseVersionFromName(StringRef Name);
1085 
1086 static StringRef getDXILArchNameFromShaderModel(StringRef ShaderModelStr) {
1087   VersionTuple Ver =
1088       parseVersionFromName(ShaderModelStr.drop_front(strlen("shadermodel")));
1089   // Default DXIL minor version when Shader Model version is anything other
1090   // than 6.[0...8] or 6.x (which translates to latest current SM version)
1091   const unsigned SMMajor = 6;
1092   if (!Ver.empty()) {
1093     if (Ver.getMajor() == SMMajor) {
1094       if (std::optional<unsigned> SMMinor = Ver.getMinor()) {
1095         switch (*SMMinor) {
1096         case 0:
1097           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_0);
1098         case 1:
1099           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_1);
1100         case 2:
1101           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_2);
1102         case 3:
1103           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_3);
1104         case 4:
1105           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_4);
1106         case 5:
1107           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_5);
1108         case 6:
1109           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_6);
1110         case 7:
1111           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_7);
1112         case 8:
1113           return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_8);
1114         default:
1115           report_fatal_error("Unsupported Shader Model version", false);
1116         }
1117       }
1118     }
1119   } else {
1120     // Special case: DXIL minor version is set to LatestCurrentDXILMinor for
1121     // shadermodel6.x is
1122     if (ShaderModelStr == "shadermodel6.x") {
1123       return Triple::getArchName(Triple::dxil, Triple::LatestDXILSubArch);
1124     }
1125   }
1126   // DXIL version corresponding to Shader Model version other than 6.Minor
1127   // is 1.0
1128   return Triple::getArchName(Triple::dxil, Triple::DXILSubArch_v1_0);
1129 }
1130 
1131 std::string Triple::normalize(StringRef Str, CanonicalForm Form) {
1132   bool IsMinGW32 = false;
1133   bool IsCygwin = false;
1134 
1135   // Parse into components.
1136   SmallVector<StringRef, 4> Components;
1137   Str.split(Components, '-');
1138 
1139   // If the first component corresponds to a known architecture, preferentially
1140   // use it for the architecture.  If the second component corresponds to a
1141   // known vendor, preferentially use it for the vendor, etc.  This avoids silly
1142   // component movement when a component parses as (eg) both a valid arch and a
1143   // valid os.
1144   ArchType Arch = UnknownArch;
1145   if (Components.size() > 0)
1146     Arch = parseArch(Components[0]);
1147   VendorType Vendor = UnknownVendor;
1148   if (Components.size() > 1)
1149     Vendor = parseVendor(Components[1]);
1150   OSType OS = UnknownOS;
1151   if (Components.size() > 2) {
1152     OS = parseOS(Components[2]);
1153     IsCygwin = Components[2].starts_with("cygwin");
1154     IsMinGW32 = Components[2].starts_with("mingw");
1155   }
1156   EnvironmentType Environment = UnknownEnvironment;
1157   if (Components.size() > 3)
1158     Environment = parseEnvironment(Components[3]);
1159   ObjectFormatType ObjectFormat = UnknownObjectFormat;
1160   if (Components.size() > 4)
1161     ObjectFormat = parseFormat(Components[4]);
1162 
1163   // Note which components are already in their final position.  These will not
1164   // be moved.
1165   bool Found[4];
1166   Found[0] = Arch != UnknownArch;
1167   Found[1] = Vendor != UnknownVendor;
1168   Found[2] = OS != UnknownOS;
1169   Found[3] = Environment != UnknownEnvironment;
1170 
1171   // If they are not there already, permute the components into their canonical
1172   // positions by seeing if they parse as a valid architecture, and if so moving
1173   // the component to the architecture position etc.
1174   for (unsigned Pos = 0; Pos != std::size(Found); ++Pos) {
1175     if (Found[Pos])
1176       continue; // Already in the canonical position.
1177 
1178     for (unsigned Idx = 0; Idx != Components.size(); ++Idx) {
1179       // Do not reparse any components that already matched.
1180       if (Idx < std::size(Found) && Found[Idx])
1181         continue;
1182 
1183       // Does this component parse as valid for the target position?
1184       bool Valid = false;
1185       StringRef Comp = Components[Idx];
1186       switch (Pos) {
1187       default: llvm_unreachable("unexpected component type!");
1188       case 0:
1189         Arch = parseArch(Comp);
1190         Valid = Arch != UnknownArch;
1191         break;
1192       case 1:
1193         Vendor = parseVendor(Comp);
1194         Valid = Vendor != UnknownVendor;
1195         break;
1196       case 2:
1197         OS = parseOS(Comp);
1198         IsCygwin = Comp.starts_with("cygwin");
1199         IsMinGW32 = Comp.starts_with("mingw");
1200         Valid = OS != UnknownOS || IsCygwin || IsMinGW32;
1201         break;
1202       case 3:
1203         Environment = parseEnvironment(Comp);
1204         Valid = Environment != UnknownEnvironment;
1205         if (!Valid) {
1206           ObjectFormat = parseFormat(Comp);
1207           Valid = ObjectFormat != UnknownObjectFormat;
1208         }
1209         break;
1210       }
1211       if (!Valid)
1212         continue; // Nope, try the next component.
1213 
1214       // Move the component to the target position, pushing any non-fixed
1215       // components that are in the way to the right.  This tends to give
1216       // good results in the common cases of a forgotten vendor component
1217       // or a wrongly positioned environment.
1218       if (Pos < Idx) {
1219         // Insert left, pushing the existing components to the right.  For
1220         // example, a-b-i386 -> i386-a-b when moving i386 to the front.
1221         StringRef CurrentComponent(""); // The empty component.
1222         // Replace the component we are moving with an empty component.
1223         std::swap(CurrentComponent, Components[Idx]);
1224         // Insert the component being moved at Pos, displacing any existing
1225         // components to the right.
1226         for (unsigned i = Pos; !CurrentComponent.empty(); ++i) {
1227           // Skip over any fixed components.
1228           while (i < std::size(Found) && Found[i])
1229             ++i;
1230           // Place the component at the new position, getting the component
1231           // that was at this position - it will be moved right.
1232           std::swap(CurrentComponent, Components[i]);
1233         }
1234       } else if (Pos > Idx) {
1235         // Push right by inserting empty components until the component at Idx
1236         // reaches the target position Pos.  For example, pc-a -> -pc-a when
1237         // moving pc to the second position.
1238         do {
1239           // Insert one empty component at Idx.
1240           StringRef CurrentComponent(""); // The empty component.
1241           for (unsigned i = Idx; i < Components.size();) {
1242             // Place the component at the new position, getting the component
1243             // that was at this position - it will be moved right.
1244             std::swap(CurrentComponent, Components[i]);
1245             // If it was placed on top of an empty component then we are done.
1246             if (CurrentComponent.empty())
1247               break;
1248             // Advance to the next component, skipping any fixed components.
1249             while (++i < std::size(Found) && Found[i])
1250               ;
1251           }
1252           // The last component was pushed off the end - append it.
1253           if (!CurrentComponent.empty())
1254             Components.push_back(CurrentComponent);
1255 
1256           // Advance Idx to the component's new position.
1257           while (++Idx < std::size(Found) && Found[Idx])
1258             ;
1259         } while (Idx < Pos); // Add more until the final position is reached.
1260       }
1261       assert(Pos < Components.size() && Components[Pos] == Comp &&
1262              "Component moved wrong!");
1263       Found[Pos] = true;
1264       break;
1265     }
1266   }
1267 
1268   // If "none" is in the middle component in a three-component triple, treat it
1269   // as the OS (Components[2]) instead of the vendor (Components[1]).
1270   if (Found[0] && !Found[1] && !Found[2] && Found[3] &&
1271       Components[1] == "none" && Components[2].empty())
1272     std::swap(Components[1], Components[2]);
1273 
1274   // Replace empty components with "unknown" value.
1275   for (StringRef &C : Components)
1276     if (C.empty())
1277       C = "unknown";
1278 
1279   // Special case logic goes here.  At this point Arch, Vendor and OS have the
1280   // correct values for the computed components.
1281   std::string NormalizedEnvironment;
1282   if (Environment == Triple::Android &&
1283       Components[3].starts_with("androideabi")) {
1284     StringRef AndroidVersion = Components[3].drop_front(strlen("androideabi"));
1285     if (AndroidVersion.empty()) {
1286       Components[3] = "android";
1287     } else {
1288       NormalizedEnvironment = Twine("android", AndroidVersion).str();
1289       Components[3] = NormalizedEnvironment;
1290     }
1291   }
1292 
1293   // SUSE uses "gnueabi" to mean "gnueabihf"
1294   if (Vendor == Triple::SUSE && Environment == llvm::Triple::GNUEABI)
1295     Components[3] = "gnueabihf";
1296 
1297   if (OS == Triple::Win32) {
1298     Components.resize(4);
1299     Components[2] = "windows";
1300     if (Environment == UnknownEnvironment) {
1301       if (ObjectFormat == UnknownObjectFormat || ObjectFormat == Triple::COFF)
1302         Components[3] = "msvc";
1303       else
1304         Components[3] = getObjectFormatTypeName(ObjectFormat);
1305     }
1306   } else if (IsMinGW32) {
1307     Components.resize(4);
1308     Components[2] = "windows";
1309     Components[3] = "gnu";
1310   } else if (IsCygwin) {
1311     Components.resize(4);
1312     Components[2] = "windows";
1313     Components[3] = "cygnus";
1314   }
1315   if (IsMinGW32 || IsCygwin ||
1316       (OS == Triple::Win32 && Environment != UnknownEnvironment)) {
1317     if (ObjectFormat != UnknownObjectFormat && ObjectFormat != Triple::COFF) {
1318       Components.resize(5);
1319       Components[4] = getObjectFormatTypeName(ObjectFormat);
1320     }
1321   }
1322 
1323   // Normalize DXIL triple if it does not include DXIL version number.
1324   // Determine DXIL version number using the minor version number of Shader
1325   // Model version specified in target triple, if any. Prior to decoupling DXIL
1326   // version numbering from that of Shader Model DXIL version 1.Y corresponds to
1327   // SM 6.Y. E.g., dxilv1.Y-unknown-shadermodelX.Y-hull
1328   if (Components[0] == "dxil") {
1329     if (Components.size() > 4) {
1330       Components.resize(4);
1331     }
1332     // Add DXIL version only if shadermodel is specified in the triple
1333     if (OS == Triple::ShaderModel) {
1334       Components[0] = getDXILArchNameFromShaderModel(Components[2]);
1335     }
1336   }
1337 
1338   // Canonicalize the components if necessary.
1339   switch (Form) {
1340   case CanonicalForm::ANY:
1341     break;
1342   case CanonicalForm::THREE_IDENT:
1343   case CanonicalForm::FOUR_IDENT:
1344   case CanonicalForm::FIVE_IDENT: {
1345     Components.resize(static_cast<unsigned>(Form), "unknown");
1346     break;
1347   }
1348   }
1349 
1350   // Stick the corrected components back together to form the normalized string.
1351   return join(Components, "-");
1352 }
1353 
1354 StringRef Triple::getArchName() const {
1355   return StringRef(Data).split('-').first;           // Isolate first component
1356 }
1357 
1358 StringRef Triple::getVendorName() const {
1359   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1360   return Tmp.split('-').first;                       // Isolate second component
1361 }
1362 
1363 StringRef Triple::getOSName() const {
1364   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1365   Tmp = Tmp.split('-').second;                       // Strip second component
1366   return Tmp.split('-').first;                       // Isolate third component
1367 }
1368 
1369 StringRef Triple::getEnvironmentName() const {
1370   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1371   Tmp = Tmp.split('-').second;                       // Strip second component
1372   return Tmp.split('-').second;                      // Strip third component
1373 }
1374 
1375 StringRef Triple::getOSAndEnvironmentName() const {
1376   StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
1377   return Tmp.split('-').second;                      // Strip second component
1378 }
1379 
1380 static VersionTuple parseVersionFromName(StringRef Name) {
1381   VersionTuple Version;
1382   Version.tryParse(Name);
1383   return Version.withoutBuild();
1384 }
1385 
1386 VersionTuple Triple::getEnvironmentVersion() const {
1387   return parseVersionFromName(getEnvironmentVersionString());
1388 }
1389 
1390 StringRef Triple::getEnvironmentVersionString() const {
1391   StringRef EnvironmentName = getEnvironmentName();
1392 
1393   // none is a valid environment type - it basically amounts to a freestanding
1394   // environment.
1395   if (EnvironmentName == "none")
1396     return "";
1397 
1398   StringRef EnvironmentTypeName = getEnvironmentTypeName(getEnvironment());
1399   EnvironmentName.consume_front(EnvironmentTypeName);
1400 
1401   if (EnvironmentName.contains("-")) {
1402     // -obj is the suffix
1403     if (getObjectFormat() != Triple::UnknownObjectFormat) {
1404       StringRef ObjectFormatTypeName =
1405           getObjectFormatTypeName(getObjectFormat());
1406       const std::string tmp = (Twine("-") + ObjectFormatTypeName).str();
1407       EnvironmentName.consume_back(tmp);
1408     }
1409   }
1410   return EnvironmentName;
1411 }
1412 
1413 VersionTuple Triple::getOSVersion() const {
1414   StringRef OSName = getOSName();
1415   // Assume that the OS portion of the triple starts with the canonical name.
1416   StringRef OSTypeName = getOSTypeName(getOS());
1417   if (OSName.starts_with(OSTypeName))
1418     OSName = OSName.substr(OSTypeName.size());
1419   else if (getOS() == MacOSX)
1420     OSName.consume_front("macos");
1421   else if (OSName.starts_with("visionos"))
1422     OSName.consume_front("visionos");
1423 
1424   return parseVersionFromName(OSName);
1425 }
1426 
1427 bool Triple::getMacOSXVersion(VersionTuple &Version) const {
1428   Version = getOSVersion();
1429 
1430   switch (getOS()) {
1431   default: llvm_unreachable("unexpected OS for Darwin triple");
1432   case Darwin:
1433     // Default to darwin8, i.e., MacOSX 10.4.
1434     if (Version.getMajor() == 0)
1435       Version = VersionTuple(8);
1436     // Darwin version numbers are skewed from OS X versions.
1437     if (Version.getMajor() < 4) {
1438       return false;
1439     }
1440     if (Version.getMajor() <= 19) {
1441       Version = VersionTuple(10, Version.getMajor() - 4);
1442     } else {
1443       // darwin20+ corresponds to macOS 11+.
1444       Version = VersionTuple(11 + Version.getMajor() - 20);
1445     }
1446     break;
1447   case MacOSX:
1448     // Default to 10.4.
1449     if (Version.getMajor() == 0) {
1450       Version = VersionTuple(10, 4);
1451     } else if (Version.getMajor() < 10) {
1452       return false;
1453     }
1454     break;
1455   case IOS:
1456   case TvOS:
1457   case WatchOS:
1458     // Ignore the version from the triple.  This is only handled because the
1459     // the clang driver combines OS X and IOS support into a common Darwin
1460     // toolchain that wants to know the OS X version number even when targeting
1461     // IOS.
1462     Version = VersionTuple(10, 4);
1463     break;
1464   case XROS:
1465     llvm_unreachable("OSX version isn't relevant for xrOS");
1466   case DriverKit:
1467     llvm_unreachable("OSX version isn't relevant for DriverKit");
1468   }
1469   return true;
1470 }
1471 
1472 VersionTuple Triple::getiOSVersion() const {
1473   switch (getOS()) {
1474   default: llvm_unreachable("unexpected OS for Darwin triple");
1475   case Darwin:
1476   case MacOSX:
1477     // Ignore the version from the triple.  This is only handled because the
1478     // the clang driver combines OS X and IOS support into a common Darwin
1479     // toolchain that wants to know the iOS version number even when targeting
1480     // OS X.
1481     return VersionTuple(5);
1482   case IOS:
1483   case TvOS: {
1484     VersionTuple Version = getOSVersion();
1485     // Default to 5.0 (or 7.0 for arm64).
1486     if (Version.getMajor() == 0)
1487       return (getArch() == aarch64) ? VersionTuple(7) : VersionTuple(5);
1488     return Version;
1489   }
1490   case XROS: {
1491     // xrOS 1 is aligned with iOS 17.
1492     VersionTuple Version = getOSVersion();
1493     return Version.withMajorReplaced(Version.getMajor() + 16);
1494   }
1495   case WatchOS:
1496     llvm_unreachable("conflicting triple info");
1497   case DriverKit:
1498     llvm_unreachable("DriverKit doesn't have an iOS version");
1499   }
1500 }
1501 
1502 VersionTuple Triple::getWatchOSVersion() const {
1503   switch (getOS()) {
1504   default: llvm_unreachable("unexpected OS for Darwin triple");
1505   case Darwin:
1506   case MacOSX:
1507     // Ignore the version from the triple.  This is only handled because the
1508     // the clang driver combines OS X and IOS support into a common Darwin
1509     // toolchain that wants to know the iOS version number even when targeting
1510     // OS X.
1511     return VersionTuple(2);
1512   case WatchOS: {
1513     VersionTuple Version = getOSVersion();
1514     if (Version.getMajor() == 0)
1515       return VersionTuple(2);
1516     return Version;
1517   }
1518   case IOS:
1519     llvm_unreachable("conflicting triple info");
1520   case XROS:
1521     llvm_unreachable("watchOS version isn't relevant for xrOS");
1522   case DriverKit:
1523     llvm_unreachable("DriverKit doesn't have a WatchOS version");
1524   }
1525 }
1526 
1527 VersionTuple Triple::getDriverKitVersion() const {
1528   switch (getOS()) {
1529   default:
1530     llvm_unreachable("unexpected OS for Darwin triple");
1531   case DriverKit:
1532     VersionTuple Version = getOSVersion();
1533     if (Version.getMajor() == 0)
1534       return Version.withMajorReplaced(19);
1535     return Version;
1536   }
1537 }
1538 
1539 VersionTuple Triple::getVulkanVersion() const {
1540   if (getArch() != spirv || getOS() != Vulkan)
1541     llvm_unreachable("invalid Vulkan SPIR-V triple");
1542 
1543   VersionTuple VulkanVersion = getOSVersion();
1544   SubArchType SpirvVersion = getSubArch();
1545 
1546   llvm::DenseMap<VersionTuple, SubArchType> ValidVersionMap = {
1547       // Vulkan 1.2 -> SPIR-V 1.5.
1548       {VersionTuple(1, 2), SPIRVSubArch_v15},
1549       // Vulkan 1.3 -> SPIR-V 1.6.
1550       {VersionTuple(1, 3), SPIRVSubArch_v16}};
1551 
1552   // If Vulkan version is unset, default to 1.2.
1553   if (VulkanVersion == VersionTuple(0))
1554     VulkanVersion = VersionTuple(1, 2);
1555 
1556   if (ValidVersionMap.contains(VulkanVersion) &&
1557       (ValidVersionMap.lookup(VulkanVersion) == SpirvVersion ||
1558        SpirvVersion == NoSubArch))
1559     return VulkanVersion;
1560 
1561   return VersionTuple(0);
1562 }
1563 
1564 VersionTuple Triple::getDXILVersion() const {
1565   if (getArch() != dxil || getOS() != ShaderModel)
1566     llvm_unreachable("invalid DXIL triple");
1567   StringRef Arch = getArchName();
1568   if (getSubArch() == NoSubArch)
1569     Arch = getDXILArchNameFromShaderModel(getOSName());
1570   Arch.consume_front("dxilv");
1571   VersionTuple DXILVersion = parseVersionFromName(Arch);
1572   // FIXME: validate DXIL version against Shader Model version.
1573   // Tracked by https://github.com/llvm/llvm-project/issues/91388
1574   return DXILVersion;
1575 }
1576 
1577 void Triple::setTriple(const Twine &Str) {
1578   *this = Triple(Str);
1579 }
1580 
1581 void Triple::setArch(ArchType Kind, SubArchType SubArch) {
1582   setArchName(getArchName(Kind, SubArch));
1583 }
1584 
1585 void Triple::setVendor(VendorType Kind) {
1586   setVendorName(getVendorTypeName(Kind));
1587 }
1588 
1589 void Triple::setOS(OSType Kind) {
1590   setOSName(getOSTypeName(Kind));
1591 }
1592 
1593 void Triple::setEnvironment(EnvironmentType Kind) {
1594   if (ObjectFormat == getDefaultFormat(*this))
1595     return setEnvironmentName(getEnvironmentTypeName(Kind));
1596 
1597   setEnvironmentName((getEnvironmentTypeName(Kind) + Twine("-") +
1598                       getObjectFormatTypeName(ObjectFormat)).str());
1599 }
1600 
1601 void Triple::setObjectFormat(ObjectFormatType Kind) {
1602   if (Environment == UnknownEnvironment)
1603     return setEnvironmentName(getObjectFormatTypeName(Kind));
1604 
1605   setEnvironmentName((getEnvironmentTypeName(Environment) + Twine("-") +
1606                       getObjectFormatTypeName(Kind)).str());
1607 }
1608 
1609 void Triple::setArchName(StringRef Str) {
1610   // Work around a miscompilation bug for Twines in gcc 4.0.3.
1611   SmallString<64> Triple;
1612   Triple += Str;
1613   Triple += "-";
1614   Triple += getVendorName();
1615   Triple += "-";
1616   Triple += getOSAndEnvironmentName();
1617   setTriple(Triple);
1618 }
1619 
1620 void Triple::setVendorName(StringRef Str) {
1621   setTriple(getArchName() + "-" + Str + "-" + getOSAndEnvironmentName());
1622 }
1623 
1624 void Triple::setOSName(StringRef Str) {
1625   if (hasEnvironment())
1626     setTriple(getArchName() + "-" + getVendorName() + "-" + Str +
1627               "-" + getEnvironmentName());
1628   else
1629     setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
1630 }
1631 
1632 void Triple::setEnvironmentName(StringRef Str) {
1633   setTriple(getArchName() + "-" + getVendorName() + "-" + getOSName() +
1634             "-" + Str);
1635 }
1636 
1637 void Triple::setOSAndEnvironmentName(StringRef Str) {
1638   setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
1639 }
1640 
1641 unsigned Triple::getArchPointerBitWidth(llvm::Triple::ArchType Arch) {
1642   switch (Arch) {
1643   case llvm::Triple::UnknownArch:
1644     return 0;
1645 
1646   case llvm::Triple::avr:
1647   case llvm::Triple::msp430:
1648     return 16;
1649 
1650   case llvm::Triple::aarch64_32:
1651   case llvm::Triple::amdil:
1652   case llvm::Triple::arc:
1653   case llvm::Triple::arm:
1654   case llvm::Triple::armeb:
1655   case llvm::Triple::csky:
1656   case llvm::Triple::dxil:
1657   case llvm::Triple::hexagon:
1658   case llvm::Triple::hsail:
1659   case llvm::Triple::kalimba:
1660   case llvm::Triple::lanai:
1661   case llvm::Triple::loongarch32:
1662   case llvm::Triple::m68k:
1663   case llvm::Triple::mips:
1664   case llvm::Triple::mipsel:
1665   case llvm::Triple::nvptx:
1666   case llvm::Triple::ppc:
1667   case llvm::Triple::ppcle:
1668   case llvm::Triple::r600:
1669   case llvm::Triple::renderscript32:
1670   case llvm::Triple::riscv32:
1671   case llvm::Triple::shave:
1672   case llvm::Triple::sparc:
1673   case llvm::Triple::sparcel:
1674   case llvm::Triple::spir:
1675   case llvm::Triple::spirv32:
1676   case llvm::Triple::tce:
1677   case llvm::Triple::tcele:
1678   case llvm::Triple::thumb:
1679   case llvm::Triple::thumbeb:
1680   case llvm::Triple::wasm32:
1681   case llvm::Triple::x86:
1682   case llvm::Triple::xcore:
1683   case llvm::Triple::xtensa:
1684     return 32;
1685 
1686   case llvm::Triple::aarch64:
1687   case llvm::Triple::aarch64_be:
1688   case llvm::Triple::amdgcn:
1689   case llvm::Triple::amdil64:
1690   case llvm::Triple::bpfeb:
1691   case llvm::Triple::bpfel:
1692   case llvm::Triple::hsail64:
1693   case llvm::Triple::loongarch64:
1694   case llvm::Triple::mips64:
1695   case llvm::Triple::mips64el:
1696   case llvm::Triple::nvptx64:
1697   case llvm::Triple::ppc64:
1698   case llvm::Triple::ppc64le:
1699   case llvm::Triple::renderscript64:
1700   case llvm::Triple::riscv64:
1701   case llvm::Triple::sparcv9:
1702   case llvm::Triple::spirv:
1703   case llvm::Triple::spir64:
1704   case llvm::Triple::spirv64:
1705   case llvm::Triple::systemz:
1706   case llvm::Triple::ve:
1707   case llvm::Triple::wasm64:
1708   case llvm::Triple::x86_64:
1709     return 64;
1710   }
1711   llvm_unreachable("Invalid architecture value");
1712 }
1713 
1714 unsigned Triple::getTrampolineSize() const {
1715   switch (getArch()) {
1716   default:
1717     break;
1718   case Triple::ppc:
1719   case Triple::ppcle:
1720     if (isOSLinux())
1721       return 40;
1722     break;
1723   case Triple::ppc64:
1724   case Triple::ppc64le:
1725     if (isOSLinux())
1726       return 48;
1727     break;
1728   case Triple::aarch64:
1729     return 36;
1730   }
1731   return 32;
1732 }
1733 
1734 bool Triple::isArch64Bit() const {
1735   return getArchPointerBitWidth(getArch()) == 64;
1736 }
1737 
1738 bool Triple::isArch32Bit() const {
1739   return getArchPointerBitWidth(getArch()) == 32;
1740 }
1741 
1742 bool Triple::isArch16Bit() const {
1743   return getArchPointerBitWidth(getArch()) == 16;
1744 }
1745 
1746 Triple Triple::get32BitArchVariant() const {
1747   Triple T(*this);
1748   switch (getArch()) {
1749   case Triple::UnknownArch:
1750   case Triple::amdgcn:
1751   case Triple::avr:
1752   case Triple::bpfeb:
1753   case Triple::bpfel:
1754   case Triple::msp430:
1755   case Triple::systemz:
1756   case Triple::ve:
1757     T.setArch(UnknownArch);
1758     break;
1759 
1760   case Triple::aarch64_32:
1761   case Triple::amdil:
1762   case Triple::arc:
1763   case Triple::arm:
1764   case Triple::armeb:
1765   case Triple::csky:
1766   case Triple::dxil:
1767   case Triple::hexagon:
1768   case Triple::hsail:
1769   case Triple::kalimba:
1770   case Triple::lanai:
1771   case Triple::loongarch32:
1772   case Triple::m68k:
1773   case Triple::mips:
1774   case Triple::mipsel:
1775   case Triple::nvptx:
1776   case Triple::ppc:
1777   case Triple::ppcle:
1778   case Triple::r600:
1779   case Triple::renderscript32:
1780   case Triple::riscv32:
1781   case Triple::shave:
1782   case Triple::sparc:
1783   case Triple::sparcel:
1784   case Triple::spir:
1785   case Triple::spirv32:
1786   case Triple::tce:
1787   case Triple::tcele:
1788   case Triple::thumb:
1789   case Triple::thumbeb:
1790   case Triple::wasm32:
1791   case Triple::x86:
1792   case Triple::xcore:
1793   case Triple::xtensa:
1794     // Already 32-bit.
1795     break;
1796 
1797   case Triple::aarch64:        T.setArch(Triple::arm);     break;
1798   case Triple::aarch64_be:     T.setArch(Triple::armeb);   break;
1799   case Triple::amdil64:        T.setArch(Triple::amdil);   break;
1800   case Triple::hsail64:        T.setArch(Triple::hsail);   break;
1801   case Triple::loongarch64:    T.setArch(Triple::loongarch32); break;
1802   case Triple::mips64:
1803     T.setArch(Triple::mips, getSubArch());
1804     break;
1805   case Triple::mips64el:
1806     T.setArch(Triple::mipsel, getSubArch());
1807     break;
1808   case Triple::nvptx64:        T.setArch(Triple::nvptx);   break;
1809   case Triple::ppc64:          T.setArch(Triple::ppc);     break;
1810   case Triple::ppc64le:        T.setArch(Triple::ppcle);   break;
1811   case Triple::renderscript64: T.setArch(Triple::renderscript32); break;
1812   case Triple::riscv64:        T.setArch(Triple::riscv32); break;
1813   case Triple::sparcv9:        T.setArch(Triple::sparc);   break;
1814   case Triple::spir64:         T.setArch(Triple::spir);    break;
1815   case Triple::spirv:
1816   case Triple::spirv64:
1817     T.setArch(Triple::spirv32, getSubArch());
1818     break;
1819   case Triple::wasm64:         T.setArch(Triple::wasm32);  break;
1820   case Triple::x86_64:         T.setArch(Triple::x86);     break;
1821   }
1822   return T;
1823 }
1824 
1825 Triple Triple::get64BitArchVariant() const {
1826   Triple T(*this);
1827   switch (getArch()) {
1828   case Triple::UnknownArch:
1829   case Triple::arc:
1830   case Triple::avr:
1831   case Triple::csky:
1832   case Triple::dxil:
1833   case Triple::hexagon:
1834   case Triple::kalimba:
1835   case Triple::lanai:
1836   case Triple::m68k:
1837   case Triple::msp430:
1838   case Triple::r600:
1839   case Triple::shave:
1840   case Triple::sparcel:
1841   case Triple::tce:
1842   case Triple::tcele:
1843   case Triple::xcore:
1844   case Triple::xtensa:
1845     T.setArch(UnknownArch);
1846     break;
1847 
1848   case Triple::aarch64:
1849   case Triple::aarch64_be:
1850   case Triple::amdgcn:
1851   case Triple::amdil64:
1852   case Triple::bpfeb:
1853   case Triple::bpfel:
1854   case Triple::hsail64:
1855   case Triple::loongarch64:
1856   case Triple::mips64:
1857   case Triple::mips64el:
1858   case Triple::nvptx64:
1859   case Triple::ppc64:
1860   case Triple::ppc64le:
1861   case Triple::renderscript64:
1862   case Triple::riscv64:
1863   case Triple::sparcv9:
1864   case Triple::spir64:
1865   case Triple::spirv64:
1866   case Triple::systemz:
1867   case Triple::ve:
1868   case Triple::wasm64:
1869   case Triple::x86_64:
1870     // Already 64-bit.
1871     break;
1872 
1873   case Triple::aarch64_32:      T.setArch(Triple::aarch64);    break;
1874   case Triple::amdil:           T.setArch(Triple::amdil64);    break;
1875   case Triple::arm:             T.setArch(Triple::aarch64);    break;
1876   case Triple::armeb:           T.setArch(Triple::aarch64_be); break;
1877   case Triple::hsail:           T.setArch(Triple::hsail64);    break;
1878   case Triple::loongarch32:     T.setArch(Triple::loongarch64);    break;
1879   case Triple::mips:
1880     T.setArch(Triple::mips64, getSubArch());
1881     break;
1882   case Triple::mipsel:
1883     T.setArch(Triple::mips64el, getSubArch());
1884     break;
1885   case Triple::nvptx:           T.setArch(Triple::nvptx64);    break;
1886   case Triple::ppc:             T.setArch(Triple::ppc64);      break;
1887   case Triple::ppcle:           T.setArch(Triple::ppc64le);    break;
1888   case Triple::renderscript32:  T.setArch(Triple::renderscript64);     break;
1889   case Triple::riscv32:         T.setArch(Triple::riscv64);    break;
1890   case Triple::sparc:           T.setArch(Triple::sparcv9);    break;
1891   case Triple::spir:            T.setArch(Triple::spir64);     break;
1892   case Triple::spirv:
1893   case Triple::spirv32:
1894     T.setArch(Triple::spirv64, getSubArch());
1895     break;
1896   case Triple::thumb:           T.setArch(Triple::aarch64);    break;
1897   case Triple::thumbeb:         T.setArch(Triple::aarch64_be); break;
1898   case Triple::wasm32:          T.setArch(Triple::wasm64);     break;
1899   case Triple::x86:             T.setArch(Triple::x86_64);     break;
1900   }
1901   return T;
1902 }
1903 
1904 Triple Triple::getBigEndianArchVariant() const {
1905   Triple T(*this);
1906   // Already big endian.
1907   if (!isLittleEndian())
1908     return T;
1909   switch (getArch()) {
1910   case Triple::UnknownArch:
1911   case Triple::amdgcn:
1912   case Triple::amdil64:
1913   case Triple::amdil:
1914   case Triple::avr:
1915   case Triple::dxil:
1916   case Triple::hexagon:
1917   case Triple::hsail64:
1918   case Triple::hsail:
1919   case Triple::kalimba:
1920   case Triple::loongarch32:
1921   case Triple::loongarch64:
1922   case Triple::msp430:
1923   case Triple::nvptx64:
1924   case Triple::nvptx:
1925   case Triple::r600:
1926   case Triple::renderscript32:
1927   case Triple::renderscript64:
1928   case Triple::riscv32:
1929   case Triple::riscv64:
1930   case Triple::shave:
1931   case Triple::spir64:
1932   case Triple::spir:
1933   case Triple::spirv:
1934   case Triple::spirv32:
1935   case Triple::spirv64:
1936   case Triple::wasm32:
1937   case Triple::wasm64:
1938   case Triple::x86:
1939   case Triple::x86_64:
1940   case Triple::xcore:
1941   case Triple::ve:
1942   case Triple::csky:
1943   case Triple::xtensa:
1944 
1945   // ARM is intentionally unsupported here, changing the architecture would
1946   // drop any arch suffixes.
1947   case Triple::arm:
1948   case Triple::thumb:
1949     T.setArch(UnknownArch);
1950     break;
1951 
1952   case Triple::aarch64: T.setArch(Triple::aarch64_be); break;
1953   case Triple::bpfel:   T.setArch(Triple::bpfeb);      break;
1954   case Triple::mips64el:
1955     T.setArch(Triple::mips64, getSubArch());
1956     break;
1957   case Triple::mipsel:
1958     T.setArch(Triple::mips, getSubArch());
1959     break;
1960   case Triple::ppcle:   T.setArch(Triple::ppc);        break;
1961   case Triple::ppc64le: T.setArch(Triple::ppc64);      break;
1962   case Triple::sparcel: T.setArch(Triple::sparc);      break;
1963   case Triple::tcele:   T.setArch(Triple::tce);        break;
1964   default:
1965     llvm_unreachable("getBigEndianArchVariant: unknown triple.");
1966   }
1967   return T;
1968 }
1969 
1970 Triple Triple::getLittleEndianArchVariant() const {
1971   Triple T(*this);
1972   if (isLittleEndian())
1973     return T;
1974 
1975   switch (getArch()) {
1976   case Triple::UnknownArch:
1977   case Triple::lanai:
1978   case Triple::sparcv9:
1979   case Triple::systemz:
1980   case Triple::m68k:
1981 
1982   // ARM is intentionally unsupported here, changing the architecture would
1983   // drop any arch suffixes.
1984   case Triple::armeb:
1985   case Triple::thumbeb:
1986     T.setArch(UnknownArch);
1987     break;
1988 
1989   case Triple::aarch64_be: T.setArch(Triple::aarch64);  break;
1990   case Triple::bpfeb:      T.setArch(Triple::bpfel);    break;
1991   case Triple::mips64:
1992     T.setArch(Triple::mips64el, getSubArch());
1993     break;
1994   case Triple::mips:
1995     T.setArch(Triple::mipsel, getSubArch());
1996     break;
1997   case Triple::ppc:        T.setArch(Triple::ppcle);    break;
1998   case Triple::ppc64:      T.setArch(Triple::ppc64le);  break;
1999   case Triple::sparc:      T.setArch(Triple::sparcel);  break;
2000   case Triple::tce:        T.setArch(Triple::tcele);    break;
2001   default:
2002     llvm_unreachable("getLittleEndianArchVariant: unknown triple.");
2003   }
2004   return T;
2005 }
2006 
2007 bool Triple::isLittleEndian() const {
2008   switch (getArch()) {
2009   case Triple::aarch64:
2010   case Triple::aarch64_32:
2011   case Triple::amdgcn:
2012   case Triple::amdil64:
2013   case Triple::amdil:
2014   case Triple::arm:
2015   case Triple::avr:
2016   case Triple::bpfel:
2017   case Triple::csky:
2018   case Triple::dxil:
2019   case Triple::hexagon:
2020   case Triple::hsail64:
2021   case Triple::hsail:
2022   case Triple::kalimba:
2023   case Triple::loongarch32:
2024   case Triple::loongarch64:
2025   case Triple::mips64el:
2026   case Triple::mipsel:
2027   case Triple::msp430:
2028   case Triple::nvptx64:
2029   case Triple::nvptx:
2030   case Triple::ppcle:
2031   case Triple::ppc64le:
2032   case Triple::r600:
2033   case Triple::renderscript32:
2034   case Triple::renderscript64:
2035   case Triple::riscv32:
2036   case Triple::riscv64:
2037   case Triple::shave:
2038   case Triple::sparcel:
2039   case Triple::spir64:
2040   case Triple::spir:
2041   case Triple::spirv:
2042   case Triple::spirv32:
2043   case Triple::spirv64:
2044   case Triple::tcele:
2045   case Triple::thumb:
2046   case Triple::ve:
2047   case Triple::wasm32:
2048   case Triple::wasm64:
2049   case Triple::x86:
2050   case Triple::x86_64:
2051   case Triple::xcore:
2052   case Triple::xtensa:
2053     return true;
2054   default:
2055     return false;
2056   }
2057 }
2058 
2059 bool Triple::isCompatibleWith(const Triple &Other) const {
2060   // On MinGW, C code is usually built with a "w64" vendor, while Rust
2061   // often uses a "pc" vendor.
2062   bool IgnoreVendor = isWindowsGNUEnvironment();
2063 
2064   // ARM and Thumb triples are compatible, if subarch, vendor and OS match.
2065   if ((getArch() == Triple::thumb && Other.getArch() == Triple::arm) ||
2066       (getArch() == Triple::arm && Other.getArch() == Triple::thumb) ||
2067       (getArch() == Triple::thumbeb && Other.getArch() == Triple::armeb) ||
2068       (getArch() == Triple::armeb && Other.getArch() == Triple::thumbeb)) {
2069     if (getVendor() == Triple::Apple)
2070       return getSubArch() == Other.getSubArch() &&
2071              getVendor() == Other.getVendor() && getOS() == Other.getOS();
2072     else
2073       return getSubArch() == Other.getSubArch() &&
2074              (getVendor() == Other.getVendor() || IgnoreVendor) &&
2075              getOS() == Other.getOS() &&
2076              getEnvironment() == Other.getEnvironment() &&
2077              getObjectFormat() == Other.getObjectFormat();
2078   }
2079 
2080   // If vendor is apple, ignore the version number (the environment field)
2081   // and the object format.
2082   if (getVendor() == Triple::Apple)
2083     return getArch() == Other.getArch() && getSubArch() == Other.getSubArch() &&
2084            (getVendor() == Other.getVendor() || IgnoreVendor) &&
2085            getOS() == Other.getOS();
2086 
2087   return getArch() == Other.getArch() && getSubArch() == Other.getSubArch() &&
2088          (getVendor() == Other.getVendor() || IgnoreVendor) &&
2089          getOS() == Other.getOS() &&
2090          getEnvironment() == Other.getEnvironment() &&
2091          getObjectFormat() == Other.getObjectFormat();
2092 }
2093 
2094 std::string Triple::merge(const Triple &Other) const {
2095   // If vendor is apple, pick the triple with the larger version number.
2096   if (getVendor() == Triple::Apple)
2097     if (Other.isOSVersionLT(*this))
2098       return str();
2099 
2100   return Other.str();
2101 }
2102 
2103 bool Triple::isMacOSXVersionLT(unsigned Major, unsigned Minor,
2104                                unsigned Micro) const {
2105   assert(isMacOSX() && "Not an OS X triple!");
2106 
2107   // If this is OS X, expect a sane version number.
2108   if (getOS() == Triple::MacOSX)
2109     return isOSVersionLT(Major, Minor, Micro);
2110 
2111   // Otherwise, compare to the "Darwin" number.
2112   if (Major == 10) {
2113     return isOSVersionLT(Minor + 4, Micro, 0);
2114   } else {
2115     assert(Major >= 11 && "Unexpected major version");
2116     return isOSVersionLT(Major - 11 + 20, Minor, Micro);
2117   }
2118 }
2119 
2120 VersionTuple Triple::getMinimumSupportedOSVersion() const {
2121   if (getVendor() != Triple::Apple || getArch() != Triple::aarch64)
2122     return VersionTuple();
2123   switch (getOS()) {
2124   case Triple::MacOSX:
2125     // ARM64 slice is supported starting from macOS 11.0+.
2126     return VersionTuple(11, 0, 0);
2127   case Triple::IOS:
2128     // ARM64 slice is supported starting from Mac Catalyst 14 (macOS 11).
2129     // ARM64 simulators are supported for iOS 14+.
2130     if (isMacCatalystEnvironment() || isSimulatorEnvironment())
2131       return VersionTuple(14, 0, 0);
2132     // ARM64e slice is supported starting from iOS 14.
2133     if (isArm64e())
2134       return VersionTuple(14, 0, 0);
2135     break;
2136   case Triple::TvOS:
2137     // ARM64 simulators are supported for tvOS 14+.
2138     if (isSimulatorEnvironment())
2139       return VersionTuple(14, 0, 0);
2140     break;
2141   case Triple::WatchOS:
2142     // ARM64 simulators are supported for watchOS 7+.
2143     if (isSimulatorEnvironment())
2144       return VersionTuple(7, 0, 0);
2145     break;
2146   case Triple::DriverKit:
2147     return VersionTuple(20, 0, 0);
2148   default:
2149     break;
2150   }
2151   return VersionTuple();
2152 }
2153 
2154 VersionTuple Triple::getCanonicalVersionForOS(OSType OSKind,
2155                                               const VersionTuple &Version) {
2156   switch (OSKind) {
2157   case MacOSX:
2158     // macOS 10.16 is canonicalized to macOS 11.
2159     if (Version == VersionTuple(10, 16))
2160       return VersionTuple(11, 0);
2161     [[fallthrough]];
2162   default:
2163     return Version;
2164   }
2165 }
2166 
2167 // HLSL triple environment orders are relied on in the front end
2168 static_assert(Triple::Vertex - Triple::Pixel == 1,
2169               "incorrect HLSL stage order");
2170 static_assert(Triple::Geometry - Triple::Pixel == 2,
2171               "incorrect HLSL stage order");
2172 static_assert(Triple::Hull - Triple::Pixel == 3,
2173               "incorrect HLSL stage order");
2174 static_assert(Triple::Domain - Triple::Pixel == 4,
2175               "incorrect HLSL stage order");
2176 static_assert(Triple::Compute - Triple::Pixel == 5,
2177               "incorrect HLSL stage order");
2178 static_assert(Triple::Library - Triple::Pixel == 6,
2179               "incorrect HLSL stage order");
2180 static_assert(Triple::RayGeneration - Triple::Pixel == 7,
2181               "incorrect HLSL stage order");
2182 static_assert(Triple::Intersection - Triple::Pixel == 8,
2183               "incorrect HLSL stage order");
2184 static_assert(Triple::AnyHit - Triple::Pixel == 9,
2185               "incorrect HLSL stage order");
2186 static_assert(Triple::ClosestHit - Triple::Pixel == 10,
2187               "incorrect HLSL stage order");
2188 static_assert(Triple::Miss - Triple::Pixel == 11,
2189               "incorrect HLSL stage order");
2190 static_assert(Triple::Callable - Triple::Pixel == 12,
2191               "incorrect HLSL stage order");
2192 static_assert(Triple::Mesh - Triple::Pixel == 13,
2193               "incorrect HLSL stage order");
2194 static_assert(Triple::Amplification - Triple::Pixel == 14,
2195               "incorrect HLSL stage order");
2196