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