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