1//===--- Triple.cpp - Target triple helper class --------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "llvm/TargetParser/Triple.h"
10#include "llvm/ADT/DenseMap.h"
11#include "llvm/ADT/StringExtras.h"
12#include "llvm/ADT/StringSwitch.h"
13#include "llvm/Support/CodeGen.h"
14#include "llvm/Support/ErrorHandling.h"
15#include "llvm/Support/SwapByteOrder.h"
16#include "llvm/Support/VersionTuple.h"
17#include "llvm/TargetParser/AMDGPUTargetParser.h"
18#include "llvm/TargetParser/ARMTargetParser.h"
19#include "llvm/TargetParser/ARMTargetParserCommon.h"
20#include "llvm/TargetParser/Host.h"
21#include "llvm/TargetParser/TargetParser.h"
22#include <cassert>
23#include <cstring>
24using namespace llvm;
25
26bool Triple::operator==(const Triple &Other) const {
27 return Arch == Other.Arch && SubArch == Other.SubArch &&
28 Vendor == Other.Vendor && OS == Other.OS &&
29 Environment == Other.Environment && ObjectFormat == Other.ObjectFormat;
30}
31
32bool Triple::operator<(const Triple &Other) const {
33 return std::tie(args: Arch, args: SubArch, args: Vendor, args: OS, args: Environment, args: ObjectFormat, args: Data) <
34 std::tie(args: Other.Arch, args: Other.SubArch, args: Other.Vendor, args: Other.OS,
35 args: Other.Environment, args: Other.ObjectFormat, args: Other.Data);
36}
37
38StringRef Triple::getArchTypeName(ArchType Kind) {
39 switch (Kind) {
40 case UnknownArch:
41 return "unknown";
42
43 case aarch64:
44 return "aarch64";
45 case aarch64_32:
46 return "aarch64_32";
47 case aarch64_be:
48 return "aarch64_be";
49 case amdgpu:
50 return "amdgpu";
51 case amdil64:
52 return "amdil64";
53 case amdil:
54 return "amdil";
55 case arc:
56 return "arc";
57 case arm:
58 return "arm";
59 case armeb:
60 return "armeb";
61 case avr:
62 return "avr";
63 case bpfeb:
64 return "bpfeb";
65 case bpfel:
66 return "bpfel";
67 case csky:
68 return "csky";
69 case dxil:
70 return "dxil";
71 case hexagon:
72 return "hexagon";
73 case hsail64:
74 return "hsail64";
75 case hsail:
76 return "hsail";
77 case kalimba:
78 return "kalimba";
79 case lanai:
80 return "lanai";
81 case loongarch32:
82 return "loongarch32";
83 case loongarch64:
84 return "loongarch64";
85 case m68k:
86 return "m68k";
87 case mips64:
88 return "mips64";
89 case mips64el:
90 return "mips64el";
91 case mips:
92 return "mips";
93 case mipsel:
94 return "mipsel";
95 case msp430:
96 return "msp430";
97 case nvptx64:
98 return "nvptx64";
99 case nvptx:
100 return "nvptx";
101 case ppc64:
102 return "powerpc64";
103 case ppc64le:
104 return "powerpc64le";
105 case ppc:
106 return "powerpc";
107 case ppcle:
108 return "powerpcle";
109 case r600:
110 return "r600";
111 case renderscript32:
112 return "renderscript32";
113 case renderscript64:
114 return "renderscript64";
115 case riscv32:
116 return "riscv32";
117 case riscv64:
118 return "riscv64";
119 case riscv32be:
120 return "riscv32be";
121 case riscv64be:
122 return "riscv64be";
123 case shave:
124 return "shave";
125 case sparc:
126 return "sparc";
127 case sparcel:
128 return "sparcel";
129 case sparcv9:
130 return "sparcv9";
131 case spir64:
132 return "spir64";
133 case spir:
134 return "spir";
135 case spirv:
136 return "spirv";
137 case spirv32:
138 return "spirv32";
139 case spirv64:
140 return "spirv64";
141 case systemz:
142 return "s390x";
143 case tce:
144 return "tce";
145 case tcele:
146 return "tcele";
147 case tcele64:
148 return "tcele64";
149 case thumb:
150 return "thumb";
151 case thumbeb:
152 return "thumbeb";
153 case ve:
154 return "ve";
155 case wasm32:
156 return "wasm32";
157 case wasm64:
158 return "wasm64";
159 case x86:
160 return "i386";
161 case x86_64:
162 return "x86_64";
163 case xcore:
164 return "xcore";
165 case xtensa:
166 return "xtensa";
167 }
168
169 llvm_unreachable("Invalid ArchType!");
170}
171
172StringRef Triple::getArchName(ArchType Kind, SubArchType SubArch) {
173 switch (Kind) {
174 case Triple::mips:
175 if (SubArch == MipsSubArch_r6)
176 return "mipsisa32r6";
177 break;
178 case Triple::mipsel:
179 if (SubArch == MipsSubArch_r6)
180 return "mipsisa32r6el";
181 break;
182 case Triple::mips64:
183 if (SubArch == MipsSubArch_r6)
184 return "mipsisa64r6";
185 break;
186 case Triple::mips64el:
187 if (SubArch == MipsSubArch_r6)
188 return "mipsisa64r6el";
189 break;
190 case Triple::aarch64:
191 if (SubArch == AArch64SubArch_arm64ec)
192 return "arm64ec";
193 if (SubArch == AArch64SubArch_arm64e)
194 return "arm64e";
195 if (SubArch == AArch64SubArch_lfi)
196 return "aarch64_lfi";
197 break;
198 case Triple::x86_64:
199 if (SubArch == X86_64SubArch_lfi)
200 return "x86_64_lfi";
201 break;
202 case Triple::spirv:
203 switch (SubArch) {
204 case Triple::SPIRVSubArch_v10:
205 return "spirv1.0";
206 case Triple::SPIRVSubArch_v11:
207 return "spirv1.1";
208 case Triple::SPIRVSubArch_v12:
209 return "spirv1.2";
210 case Triple::SPIRVSubArch_v13:
211 return "spirv1.3";
212 case Triple::SPIRVSubArch_v14:
213 return "spirv1.4";
214 case Triple::SPIRVSubArch_v15:
215 return "spirv1.5";
216 case Triple::SPIRVSubArch_v16:
217 return "spirv1.6";
218 default:
219 break;
220 }
221 break;
222 case Triple::dxil:
223 switch (SubArch) {
224 case Triple::NoSubArch:
225 case Triple::DXILSubArch_v1_0:
226 return "dxilv1.0";
227 case Triple::DXILSubArch_v1_1:
228 return "dxilv1.1";
229 case Triple::DXILSubArch_v1_2:
230 return "dxilv1.2";
231 case Triple::DXILSubArch_v1_3:
232 return "dxilv1.3";
233 case Triple::DXILSubArch_v1_4:
234 return "dxilv1.4";
235 case Triple::DXILSubArch_v1_5:
236 return "dxilv1.5";
237 case Triple::DXILSubArch_v1_6:
238 return "dxilv1.6";
239 case Triple::DXILSubArch_v1_7:
240 return "dxilv1.7";
241 case Triple::DXILSubArch_v1_8:
242 return "dxilv1.8";
243 case Triple::DXILSubArch_v1_9:
244 return "dxilv1.9";
245 default:
246 break;
247 }
248 break;
249 case Triple::amdgpu:
250 return AMDGPU::getSubArchName(SubArch);
251 default:
252 break;
253 }
254 return getArchTypeName(Kind);
255}
256
257StringRef Triple::getArchTypePrefix(ArchType Kind) {
258 switch (Kind) {
259 default:
260 return StringRef();
261
262 case aarch64:
263 case aarch64_be:
264 case aarch64_32:
265 return "aarch64";
266
267 case arc:
268 return "arc";
269
270 case arm:
271 case armeb:
272 case thumb:
273 case thumbeb:
274 return "arm";
275
276 case avr:
277 return "avr";
278
279 case ppc64:
280 case ppc64le:
281 case ppc:
282 case ppcle:
283 return "ppc";
284
285 case m68k:
286 return "m68k";
287
288 case mips:
289 case mipsel:
290 case mips64:
291 case mips64el:
292 return "mips";
293
294 case hexagon:
295 return "hexagon";
296
297 // Intrinsics use amdgcn prefix.
298 case amdgpu:
299 return "amdgcn";
300 case r600:
301 return "r600";
302
303 case bpfel:
304 case bpfeb:
305 return "bpf";
306
307 case sparcv9:
308 case sparcel:
309 case sparc:
310 return "sparc";
311
312 case systemz:
313 return "s390";
314
315 case x86:
316 case x86_64:
317 return "x86";
318
319 case xcore:
320 return "xcore";
321
322 // NVPTX intrinsics are namespaced under nvvm.
323 case nvptx:
324 return "nvvm";
325 case nvptx64:
326 return "nvvm";
327
328 case amdil:
329 case amdil64:
330 return "amdil";
331
332 case hsail:
333 case hsail64:
334 return "hsail";
335
336 case spir:
337 case spir64:
338 return "spir";
339
340 case spirv:
341 case spirv32:
342 case spirv64:
343 return "spv";
344
345 case kalimba:
346 return "kalimba";
347 case lanai:
348 return "lanai";
349 case shave:
350 return "shave";
351 case wasm32:
352 case wasm64:
353 return "wasm";
354
355 case riscv32:
356 case riscv64:
357 case riscv32be:
358 case riscv64be:
359 return "riscv";
360
361 case ve:
362 return "ve";
363 case csky:
364 return "csky";
365
366 case loongarch32:
367 case loongarch64:
368 return "loongarch";
369
370 case dxil:
371 return "dx";
372
373 case xtensa:
374 return "xtensa";
375 }
376}
377
378StringRef Triple::getVendorTypeName(VendorType Kind) {
379 switch (Kind) {
380 case UnknownVendor:
381 return "unknown";
382#define TRIPLE_VENDOR(Enum, Name) \
383 case Enum: \
384 return Name;
385#include "llvm/TargetParser/TripleName.def"
386 }
387
388 llvm_unreachable("Invalid VendorType!");
389}
390
391StringRef Triple::getOSTypeName(OSType Kind) {
392 switch (Kind) {
393 case UnknownOS:
394 return "unknown";
395#define TRIPLE_OS(Enum, Name, CMakeName) \
396 case Enum: \
397 return Name;
398#include "llvm/TargetParser/TripleName.def"
399 }
400
401 llvm_unreachable("Invalid OSType");
402}
403
404StringRef Triple::getEnvironmentTypeName(EnvironmentType Kind) {
405 switch (Kind) {
406 case UnknownEnvironment:
407 return "unknown";
408#define TRIPLE_ENV(Enum, Name, CMakeOverride) \
409 case Enum: \
410 return Name;
411#include "llvm/TargetParser/TripleName.def"
412 }
413
414 llvm_unreachable("Invalid EnvironmentType!");
415}
416
417StringRef Triple::getObjectFormatTypeName(ObjectFormatType Kind) {
418 switch (Kind) {
419 case UnknownObjectFormat:
420 return "";
421 case COFF:
422 return "coff";
423 case ELF:
424 return "elf";
425 case GOFF:
426 return "goff";
427 case MachO:
428 return "macho";
429 case Wasm:
430 return "wasm";
431 case XCOFF:
432 return "xcoff";
433 case DXContainer:
434 return "dxcontainer";
435 case SPIRV:
436 return "spirv";
437 }
438 llvm_unreachable("unknown object format type");
439}
440
441static Triple::ArchType parseBPFArch(StringRef ArchName) {
442 if (ArchName == "bpf") {
443 if (sys::IsLittleEndianHost)
444 return Triple::bpfel;
445 else
446 return Triple::bpfeb;
447 } else if (ArchName == "bpf_be" || ArchName == "bpfeb") {
448 return Triple::bpfeb;
449 } else if (ArchName == "bpf_le" || ArchName == "bpfel") {
450 return Triple::bpfel;
451 } else {
452 return Triple::UnknownArch;
453 }
454}
455
456Triple::ArchType Triple::getArchTypeForLLVMName(StringRef Name) {
457 Triple::ArchType BPFArch(parseBPFArch(ArchName: Name));
458 return StringSwitch<Triple::ArchType>(Name)
459 .Case(S: "aarch64", Value: aarch64)
460 .Case(S: "aarch64_be", Value: aarch64_be)
461 .Case(S: "aarch64_32", Value: aarch64_32)
462 .Case(S: "arc", Value: arc)
463 .Case(S: "arm64", Value: aarch64) // "arm64" is an alias for "aarch64"
464 .Case(S: "arm64_32", Value: aarch64_32)
465 .Case(S: "arm", Value: arm)
466 .Case(S: "armeb", Value: armeb)
467 .Case(S: "avr", Value: avr)
468 .StartsWith(S: "bpf", Value: BPFArch)
469 .Case(S: "m68k", Value: m68k)
470 .Case(S: "mips", Value: mips)
471 .Case(S: "mipsel", Value: mipsel)
472 .Case(S: "mips64", Value: mips64)
473 .Case(S: "mips64el", Value: mips64el)
474 .Case(S: "msp430", Value: msp430)
475 .Case(S: "ppc64", Value: ppc64)
476 .Case(S: "ppc32", Value: ppc)
477 .Case(S: "ppc", Value: ppc)
478 .Case(S: "ppc32le", Value: ppcle)
479 .Case(S: "ppcle", Value: ppcle)
480 .Case(S: "ppc64le", Value: ppc64le)
481 .Case(S: "amdgpu", Value: amdgpu)
482 .Case(S: "amdgcn", Value: amdgpu) // Legacy name
483 .Case(S: "r600", Value: r600)
484 .Case(S: "riscv32", Value: riscv32)
485 .Case(S: "riscv64", Value: riscv64)
486 .Case(S: "riscv32be", Value: riscv32be)
487 .Case(S: "riscv64be", Value: riscv64be)
488 .Case(S: "hexagon", Value: hexagon)
489 .Case(S: "sparc", Value: sparc)
490 .Case(S: "sparcel", Value: sparcel)
491 .Case(S: "sparcv9", Value: sparcv9)
492 .Case(S: "s390x", Value: systemz)
493 .Case(S: "systemz", Value: systemz)
494 .Case(S: "tce", Value: tce)
495 .Case(S: "tcele", Value: tcele)
496 .Case(S: "tcele64", Value: tcele64)
497 .Case(S: "thumb", Value: thumb)
498 .Case(S: "thumbeb", Value: thumbeb)
499 .Case(S: "x86", Value: x86)
500 .Case(S: "i386", Value: x86)
501 .Case(S: "x86-64", Value: x86_64)
502 .Case(S: "xcore", Value: xcore)
503 .Case(S: "nvptx", Value: nvptx)
504 .Case(S: "nvptx64", Value: nvptx64)
505 .Case(S: "amdil", Value: amdil)
506 .Case(S: "amdil64", Value: amdil64)
507 .Case(S: "hsail", Value: hsail)
508 .Case(S: "hsail64", Value: hsail64)
509 .Case(S: "spir", Value: spir)
510 .Case(S: "spir64", Value: spir64)
511 .Case(S: "spirv", Value: spirv)
512 .Case(S: "spirv32", Value: spirv32)
513 .Case(S: "spirv64", Value: spirv64)
514 .Case(S: "kalimba", Value: kalimba)
515 .Case(S: "lanai", Value: lanai)
516 .Case(S: "shave", Value: shave)
517 .Case(S: "wasm32", Value: wasm32)
518 .Case(S: "wasm64", Value: wasm64)
519 .Case(S: "renderscript32", Value: renderscript32)
520 .Case(S: "renderscript64", Value: renderscript64)
521 .Case(S: "ve", Value: ve)
522 .Case(S: "csky", Value: csky)
523 .Case(S: "loongarch32", Value: loongarch32)
524 .Case(S: "loongarch64", Value: loongarch64)
525 .Case(S: "dxil", Value: dxil)
526 .Case(S: "xtensa", Value: xtensa)
527 .Default(Value: UnknownArch);
528}
529
530static Triple::ArchType parseARMArch(StringRef ArchName) {
531 ARM::ISAKind ISA = ARM::parseArchISA(Arch: ArchName);
532 ARM::EndianKind ENDIAN = ARM::parseArchEndian(Arch: ArchName);
533
534 Triple::ArchType arch = Triple::UnknownArch;
535 switch (ENDIAN) {
536 case ARM::EndianKind::LITTLE: {
537 switch (ISA) {
538 case ARM::ISAKind::ARM:
539 arch = Triple::arm;
540 break;
541 case ARM::ISAKind::THUMB:
542 arch = Triple::thumb;
543 break;
544 case ARM::ISAKind::AARCH64:
545 arch = Triple::aarch64;
546 break;
547 case ARM::ISAKind::INVALID:
548 break;
549 }
550 break;
551 }
552 case ARM::EndianKind::BIG: {
553 switch (ISA) {
554 case ARM::ISAKind::ARM:
555 arch = Triple::armeb;
556 break;
557 case ARM::ISAKind::THUMB:
558 arch = Triple::thumbeb;
559 break;
560 case ARM::ISAKind::AARCH64:
561 arch = Triple::aarch64_be;
562 break;
563 case ARM::ISAKind::INVALID:
564 break;
565 }
566 break;
567 }
568 case ARM::EndianKind::INVALID: {
569 break;
570 }
571 }
572
573 ArchName = ARM::getCanonicalArchName(Arch: ArchName);
574 if (ArchName.empty())
575 return Triple::UnknownArch;
576
577 // Thumb only exists in v4+
578 if (ISA == ARM::ISAKind::THUMB &&
579 (ArchName.starts_with(Prefix: "v2") || ArchName.starts_with(Prefix: "v3")))
580 return Triple::UnknownArch;
581
582 // Thumb only for v6m
583 ARM::ProfileKind Profile = ARM::parseArchProfile(Arch: ArchName);
584 unsigned Version = ARM::parseArchVersion(Arch: ArchName);
585 if (Profile == ARM::ProfileKind::M && Version == 6) {
586 if (ENDIAN == ARM::EndianKind::BIG)
587 return Triple::thumbeb;
588 else
589 return Triple::thumb;
590 }
591
592 return arch;
593}
594
595Triple::ArchType Triple::parseArch(StringRef ArchName) {
596 auto AT =
597 StringSwitch<Triple::ArchType>(ArchName)
598 .Cases(CaseStrings: {"i386", "i486", "i586", "i686"}, Value: Triple::x86)
599 // FIXME: Do we need to support these?
600 .Cases(CaseStrings: {"i786", "i886", "i986"}, Value: Triple::x86)
601 .Cases(CaseStrings: {"amd64", "x86_64", "x86_64h", "x86_64_lfi"}, Value: Triple::x86_64)
602 .Cases(CaseStrings: {"powerpc", "powerpcspe", "ppc", "ppc32"}, Value: Triple::ppc)
603 .Cases(CaseStrings: {"powerpcle", "ppcle", "ppc32le"}, Value: Triple::ppcle)
604 .Cases(CaseStrings: {"powerpc64", "ppu", "ppc64"}, Value: Triple::ppc64)
605 .Cases(CaseStrings: {"powerpc64le", "ppc64le"}, Value: Triple::ppc64le)
606 .Case(S: "xscale", Value: Triple::arm)
607 .Case(S: "xscaleeb", Value: Triple::armeb)
608 .Case(S: "aarch64", Value: Triple::aarch64)
609 .Case(S: "aarch64_be", Value: Triple::aarch64_be)
610 .Case(S: "aarch64_32", Value: Triple::aarch64_32)
611 .Case(S: "aarch64_lfi", Value: Triple::aarch64)
612 .Case(S: "arc", Value: Triple::arc)
613 .Case(S: "arm64", Value: Triple::aarch64)
614 .Case(S: "arm64_32", Value: Triple::aarch64_32)
615 .Case(S: "arm64e", Value: Triple::aarch64)
616 .Case(S: "arm64ec", Value: Triple::aarch64)
617 .Case(S: "arm", Value: Triple::arm)
618 .Case(S: "armeb", Value: Triple::armeb)
619 .Case(S: "thumb", Value: Triple::thumb)
620 .Case(S: "thumbeb", Value: Triple::thumbeb)
621 .Case(S: "avr", Value: Triple::avr)
622 .Case(S: "m68k", Value: Triple::m68k)
623 .Case(S: "msp430", Value: Triple::msp430)
624 .Cases(CaseStrings: {"mips", "mipseb", "mipsallegrex", "mipsisa32r6", "mipsr6"},
625 Value: Triple::mips)
626 .Cases(CaseStrings: {"mipsel", "mipsallegrexel", "mipsisa32r6el", "mipsr6el"},
627 Value: Triple::mipsel)
628 .Cases(CaseStrings: {"mips64", "mips64eb", "mipsn32", "mipsisa64r6", "mips64r6",
629 "mipsn32r6"},
630 Value: Triple::mips64)
631 .Cases(CaseStrings: {"mips64el", "mipsn32el", "mipsisa64r6el", "mips64r6el",
632 "mipsn32r6el"},
633 Value: Triple::mips64el)
634 .StartsWith(S: "amdgpu", Value: Triple::amdgpu)
635 .Case(S: "amdgcn", Value: Triple::amdgpu)
636 .Case(S: "r600", Value: Triple::r600)
637 .Case(S: "riscv32", Value: Triple::riscv32)
638 .Case(S: "riscv64", Value: Triple::riscv64)
639 .Case(S: "riscv32be", Value: Triple::riscv32be)
640 .Case(S: "riscv64be", Value: Triple::riscv64be)
641 .Case(S: "hexagon", Value: Triple::hexagon)
642 .Cases(CaseStrings: {"s390x", "systemz"}, Value: Triple::systemz)
643 .Case(S: "sparc", Value: Triple::sparc)
644 .Case(S: "sparcel", Value: Triple::sparcel)
645 .Cases(CaseStrings: {"sparcv9", "sparc64"}, Value: Triple::sparcv9)
646 .Case(S: "tce", Value: Triple::tce)
647 .Case(S: "tcele", Value: Triple::tcele)
648 .Case(S: "tcele64", Value: Triple::tcele64)
649 .Case(S: "xcore", Value: Triple::xcore)
650 .Case(S: "nvptx", Value: Triple::nvptx)
651 .Case(S: "nvptx64", Value: Triple::nvptx64)
652 .Case(S: "amdil", Value: Triple::amdil)
653 .Case(S: "amdil64", Value: Triple::amdil64)
654 .Case(S: "hsail", Value: Triple::hsail)
655 .Case(S: "hsail64", Value: Triple::hsail64)
656 .Case(S: "spir", Value: Triple::spir)
657 .Case(S: "spir64", Value: Triple::spir64)
658 .Cases(CaseStrings: {"spirv", "spirv1.5", "spirv1.6"}, Value: Triple::spirv)
659 .Cases(CaseStrings: {"spirv32", "spirv32v1.0", "spirv32v1.1", "spirv32v1.2",
660 "spirv32v1.3", "spirv32v1.4", "spirv32v1.5", "spirv32v1.6"},
661 Value: Triple::spirv32)
662 .Cases(CaseStrings: {"spirv64", "spirv64v1.0", "spirv64v1.1", "spirv64v1.2",
663 "spirv64v1.3", "spirv64v1.4", "spirv64v1.5", "spirv64v1.6"},
664 Value: Triple::spirv64)
665 .StartsWith(S: "kalimba", Value: Triple::kalimba)
666 .Case(S: "lanai", Value: Triple::lanai)
667 .Case(S: "renderscript32", Value: Triple::renderscript32)
668 .Case(S: "renderscript64", Value: Triple::renderscript64)
669 .Case(S: "shave", Value: Triple::shave)
670 .Case(S: "ve", Value: Triple::ve)
671 .Case(S: "wasm32", Value: Triple::wasm32)
672 .Case(S: "wasm64", Value: Triple::wasm64)
673 .Case(S: "csky", Value: Triple::csky)
674 .Case(S: "loongarch32", Value: Triple::loongarch32)
675 .Case(S: "loongarch64", Value: Triple::loongarch64)
676 .Cases(CaseStrings: {"dxil", "dxilv1.0", "dxilv1.1", "dxilv1.2", "dxilv1.3",
677 "dxilv1.4", "dxilv1.5", "dxilv1.6", "dxilv1.7", "dxilv1.8",
678 "dxilv1.9"},
679 Value: Triple::dxil)
680 .Case(S: "xtensa", Value: Triple::xtensa)
681 .Default(Value: Triple::UnknownArch);
682
683 // Some architectures require special parsing logic just to compute the
684 // ArchType result.
685 if (AT == Triple::UnknownArch) {
686 if (ArchName.starts_with(Prefix: "arm") || ArchName.starts_with(Prefix: "thumb") ||
687 ArchName.starts_with(Prefix: "aarch64"))
688 return parseARMArch(ArchName);
689 if (ArchName.starts_with(Prefix: "bpf"))
690 return parseBPFArch(ArchName);
691 }
692
693 return AT;
694}
695
696static Triple::VendorType parseVendor(StringRef VendorName) {
697 return StringSwitch<Triple::VendorType>(VendorName)
698#define TRIPLE_VENDOR(Enum, Name) .Case(Name, Triple::Enum)
699#define TRIPLE_VENDOR_ALIAS(Enum, AliasName) .Case(AliasName, Triple::Enum)
700#include "llvm/TargetParser/TripleName.def"
701 .Default(Value: Triple::UnknownVendor);
702}
703
704static Triple::OSType parseOS(StringRef OSName) {
705 return StringSwitch<Triple::OSType>(OSName)
706#define TRIPLE_OS(Enum, Name, CMakeName) .StartsWith(Name, Triple::Enum)
707#define TRIPLE_OS_ALIAS(Enum, AliasName) .StartsWith(AliasName, Triple::Enum)
708#include "llvm/TargetParser/TripleName.def"
709 .Default(Value: Triple::UnknownOS);
710}
711
712static Triple::EnvironmentType parseEnvironment(StringRef EnvironmentName) {
713 return StringSwitch<Triple::EnvironmentType>(EnvironmentName)
714#define TRIPLE_ENV(Enum, Name, CMakeOverride) .StartsWith(Name, Triple::Enum)
715#include "llvm/TargetParser/TripleName.def"
716 .Default(Value: Triple::UnknownEnvironment);
717}
718
719static Triple::ObjectFormatType parseFormat(StringRef EnvironmentName) {
720 return StringSwitch<Triple::ObjectFormatType>(EnvironmentName)
721 // "xcoff" must come before "coff" because of the order-dependendent
722 // pattern matching.
723 .EndsWith(S: "xcoff", Value: Triple::XCOFF)
724 .EndsWith(S: "coff", Value: Triple::COFF)
725 .EndsWith(S: "elf", Value: Triple::ELF)
726 .EndsWith(S: "goff", Value: Triple::GOFF)
727 .EndsWith(S: "macho", Value: Triple::MachO)
728 .EndsWith(S: "wasm", Value: Triple::Wasm)
729 .EndsWith(S: "spirv", Value: Triple::SPIRV)
730 .Default(Value: Triple::UnknownObjectFormat);
731}
732
733Triple::SubArchType Triple::parseSubArch(StringRef SubArchName) {
734 if (SubArchName.starts_with(Prefix: "mips") &&
735 (SubArchName.ends_with(Suffix: "r6el") || SubArchName.ends_with(Suffix: "r6")))
736 return Triple::MipsSubArch_r6;
737
738 if (SubArchName == "powerpcspe")
739 return Triple::PPCSubArch_spe;
740
741 if (SubArchName == "arm64e")
742 return Triple::AArch64SubArch_arm64e;
743
744 if (SubArchName == "arm64ec")
745 return Triple::AArch64SubArch_arm64ec;
746
747 if (SubArchName == "aarch64_lfi")
748 return Triple::AArch64SubArch_lfi;
749
750 if (SubArchName == "x86_64_lfi")
751 return Triple::X86_64SubArch_lfi;
752
753 if (SubArchName.starts_with(Prefix: "spirv"))
754 return StringSwitch<Triple::SubArchType>(SubArchName)
755 .EndsWith(S: "v1.0", Value: Triple::SPIRVSubArch_v10)
756 .EndsWith(S: "v1.1", Value: Triple::SPIRVSubArch_v11)
757 .EndsWith(S: "v1.2", Value: Triple::SPIRVSubArch_v12)
758 .EndsWith(S: "v1.3", Value: Triple::SPIRVSubArch_v13)
759 .EndsWith(S: "v1.4", Value: Triple::SPIRVSubArch_v14)
760 .EndsWith(S: "v1.5", Value: Triple::SPIRVSubArch_v15)
761 .EndsWith(S: "v1.6", Value: Triple::SPIRVSubArch_v16)
762 .Default(Value: Triple::NoSubArch);
763
764 if (SubArchName.starts_with(Prefix: "dxil"))
765 return StringSwitch<Triple::SubArchType>(SubArchName)
766 .EndsWith(S: "v1.0", Value: Triple::DXILSubArch_v1_0)
767 .EndsWith(S: "v1.1", Value: Triple::DXILSubArch_v1_1)
768 .EndsWith(S: "v1.2", Value: Triple::DXILSubArch_v1_2)
769 .EndsWith(S: "v1.3", Value: Triple::DXILSubArch_v1_3)
770 .EndsWith(S: "v1.4", Value: Triple::DXILSubArch_v1_4)
771 .EndsWith(S: "v1.5", Value: Triple::DXILSubArch_v1_5)
772 .EndsWith(S: "v1.6", Value: Triple::DXILSubArch_v1_6)
773 .EndsWith(S: "v1.7", Value: Triple::DXILSubArch_v1_7)
774 .EndsWith(S: "v1.8", Value: Triple::DXILSubArch_v1_8)
775 .EndsWith(S: "v1.9", Value: Triple::DXILSubArch_v1_9)
776 .Default(Value: Triple::NoSubArch);
777
778 if (SubArchName.consume_front(Prefix: "amdgpu")) {
779 return StringSwitch<Triple::SubArchType>(SubArchName)
780 .Case(S: "6", Value: Triple::AMDGPUSubArch6)
781 .Case(S: "6.00", Value: Triple::AMDGPUSubArch600)
782 .Case(S: "6.01", Value: Triple::AMDGPUSubArch601)
783 .Case(S: "6.02", Value: Triple::AMDGPUSubArch602)
784 .Case(S: "7", Value: Triple::AMDGPUSubArch7)
785 .Case(S: "7.00", Value: Triple::AMDGPUSubArch700)
786 .Case(S: "7.01", Value: Triple::AMDGPUSubArch701)
787 .Case(S: "7.02", Value: Triple::AMDGPUSubArch702)
788 .Case(S: "7.03", Value: Triple::AMDGPUSubArch703)
789 .Case(S: "7.04", Value: Triple::AMDGPUSubArch704)
790 .Case(S: "7.05", Value: Triple::AMDGPUSubArch705)
791 .Case(S: "8", Value: Triple::AMDGPUSubArch8)
792 .Case(S: "8.01", Value: Triple::AMDGPUSubArch801)
793 .Case(S: "8.02", Value: Triple::AMDGPUSubArch802)
794 .Case(S: "8.03", Value: Triple::AMDGPUSubArch803)
795 .Case(S: "8.05", Value: Triple::AMDGPUSubArch805)
796 .Case(S: "8.10", Value: Triple::AMDGPUSubArch810)
797 .Case(S: "9", Value: Triple::AMDGPUSubArch9)
798 .Case(S: "9.00", Value: Triple::AMDGPUSubArch900)
799 .Case(S: "9.02", Value: Triple::AMDGPUSubArch902)
800 .Case(S: "9.04", Value: Triple::AMDGPUSubArch904)
801 .Case(S: "9.06", Value: Triple::AMDGPUSubArch906)
802 .Case(S: "9.08", Value: Triple::AMDGPUSubArch908)
803 .Case(S: "9.09", Value: Triple::AMDGPUSubArch909)
804 .Case(S: "9.0a", Value: Triple::AMDGPUSubArch90A)
805 .Case(S: "9.0c", Value: Triple::AMDGPUSubArch90C)
806 .Case(S: "9.4", Value: Triple::AMDGPUSubArch9_4)
807 .Case(S: "9.5", Value: Triple::AMDGPUSubArch9_4)
808 .Case(S: "9.42", Value: Triple::AMDGPUSubArch942)
809 .Case(S: "9.50", Value: Triple::AMDGPUSubArch950)
810 .Case(S: "10", Value: Triple::AMDGPUSubArch10_1)
811 .Case(S: "10.1", Value: Triple::AMDGPUSubArch10_1)
812 .Case(S: "10.10", Value: Triple::AMDGPUSubArch1010)
813 .Case(S: "10.11", Value: Triple::AMDGPUSubArch1011)
814 .Case(S: "10.12", Value: Triple::AMDGPUSubArch1012)
815 .Case(S: "10.13", Value: Triple::AMDGPUSubArch1013)
816 .Case(S: "10.3", Value: Triple::AMDGPUSubArch10_3)
817 .Case(S: "10.30", Value: Triple::AMDGPUSubArch1030)
818 .Case(S: "10.31", Value: Triple::AMDGPUSubArch1031)
819 .Case(S: "10.32", Value: Triple::AMDGPUSubArch1032)
820 .Case(S: "10.33", Value: Triple::AMDGPUSubArch1033)
821 .Case(S: "10.34", Value: Triple::AMDGPUSubArch1034)
822 .Case(S: "10.35", Value: Triple::AMDGPUSubArch1035)
823 .Case(S: "10.36", Value: Triple::AMDGPUSubArch1036)
824 .Case(S: "11", Value: Triple::AMDGPUSubArch11)
825 .Case(S: "11.00", Value: Triple::AMDGPUSubArch1100)
826 .Case(S: "11.01", Value: Triple::AMDGPUSubArch1101)
827 .Case(S: "11.02", Value: Triple::AMDGPUSubArch1102)
828 .Case(S: "11.03", Value: Triple::AMDGPUSubArch1103)
829 .Case(S: "11.50", Value: Triple::AMDGPUSubArch1150)
830 .Case(S: "11.51", Value: Triple::AMDGPUSubArch1151)
831 .Case(S: "11.52", Value: Triple::AMDGPUSubArch1152)
832 .Case(S: "11.53", Value: Triple::AMDGPUSubArch1153)
833 .Case(S: "11.54", Value: Triple::AMDGPUSubArch1154)
834 .Case(S: "11.7", Value: Triple::AMDGPUSubArch11_7)
835 .Case(S: "11.70", Value: Triple::AMDGPUSubArch1170)
836 .Case(S: "11.71", Value: Triple::AMDGPUSubArch1171)
837 .Case(S: "11.72", Value: Triple::AMDGPUSubArch1172)
838 .Case(S: "12", Value: Triple::AMDGPUSubArch12)
839 .Case(S: "12.00", Value: Triple::AMDGPUSubArch1200)
840 .Case(S: "12.01", Value: Triple::AMDGPUSubArch1201)
841 .Case(S: "12.5", Value: Triple::AMDGPUSubArch12_5)
842 .Case(S: "12.50", Value: Triple::AMDGPUSubArch1250)
843 .Case(S: "12.50s", Value: Triple::AMDGPUSubArch1250S)
844 .Case(S: "12.51", Value: Triple::AMDGPUSubArch1251)
845 .Case(S: "13", Value: Triple::AMDGPUSubArch13)
846 .Case(S: "13.10", Value: Triple::AMDGPUSubArch1310)
847 .Default(Value: Triple::NoSubArch);
848 }
849
850 StringRef ARMSubArch = ARM::getCanonicalArchName(Arch: SubArchName);
851
852 // For now, this is the small part. Early return.
853 if (ARMSubArch.empty())
854 return StringSwitch<Triple::SubArchType>(SubArchName)
855 .EndsWith(S: "kalimba3", Value: Triple::KalimbaSubArch_v3)
856 .EndsWith(S: "kalimba4", Value: Triple::KalimbaSubArch_v4)
857 .EndsWith(S: "kalimba5", Value: Triple::KalimbaSubArch_v5)
858 .Default(Value: Triple::NoSubArch);
859
860 // ARM sub arch.
861 switch (ARM::parseArch(Arch: ARMSubArch)) {
862 case ARM::ArchKind::ARMV4:
863 return Triple::NoSubArch;
864 case ARM::ArchKind::ARMV4T:
865 return Triple::ARMSubArch_v4t;
866 case ARM::ArchKind::ARMV5T:
867 return Triple::ARMSubArch_v5;
868 case ARM::ArchKind::ARMV5TE:
869 case ARM::ArchKind::IWMMXT:
870 case ARM::ArchKind::IWMMXT2:
871 case ARM::ArchKind::XSCALE:
872 case ARM::ArchKind::ARMV5TEJ:
873 return Triple::ARMSubArch_v5te;
874 case ARM::ArchKind::ARMV6:
875 return Triple::ARMSubArch_v6;
876 case ARM::ArchKind::ARMV6K:
877 case ARM::ArchKind::ARMV6KZ:
878 return Triple::ARMSubArch_v6k;
879 case ARM::ArchKind::ARMV6T2:
880 return Triple::ARMSubArch_v6t2;
881 case ARM::ArchKind::ARMV6M:
882 return Triple::ARMSubArch_v6m;
883 case ARM::ArchKind::ARMV7A:
884 case ARM::ArchKind::ARMV7R:
885 return Triple::ARMSubArch_v7;
886 case ARM::ArchKind::ARMV7VE:
887 return Triple::ARMSubArch_v7ve;
888 case ARM::ArchKind::ARMV7K:
889 return Triple::ARMSubArch_v7k;
890 case ARM::ArchKind::ARMV7M:
891 return Triple::ARMSubArch_v7m;
892 case ARM::ArchKind::ARMV7S:
893 return Triple::ARMSubArch_v7s;
894 case ARM::ArchKind::ARMV7EM:
895 return Triple::ARMSubArch_v7em;
896 case ARM::ArchKind::ARMV8A:
897 return Triple::ARMSubArch_v8;
898 case ARM::ArchKind::ARMV8_1A:
899 return Triple::ARMSubArch_v8_1a;
900 case ARM::ArchKind::ARMV8_2A:
901 return Triple::ARMSubArch_v8_2a;
902 case ARM::ArchKind::ARMV8_3A:
903 return Triple::ARMSubArch_v8_3a;
904 case ARM::ArchKind::ARMV8_4A:
905 return Triple::ARMSubArch_v8_4a;
906 case ARM::ArchKind::ARMV8_5A:
907 return Triple::ARMSubArch_v8_5a;
908 case ARM::ArchKind::ARMV8_6A:
909 return Triple::ARMSubArch_v8_6a;
910 case ARM::ArchKind::ARMV8_7A:
911 return Triple::ARMSubArch_v8_7a;
912 case ARM::ArchKind::ARMV8_8A:
913 return Triple::ARMSubArch_v8_8a;
914 case ARM::ArchKind::ARMV8_9A:
915 return Triple::ARMSubArch_v8_9a;
916 case ARM::ArchKind::ARMV9A:
917 return Triple::ARMSubArch_v9;
918 case ARM::ArchKind::ARMV9_1A:
919 return Triple::ARMSubArch_v9_1a;
920 case ARM::ArchKind::ARMV9_2A:
921 return Triple::ARMSubArch_v9_2a;
922 case ARM::ArchKind::ARMV9_3A:
923 return Triple::ARMSubArch_v9_3a;
924 case ARM::ArchKind::ARMV9_4A:
925 return Triple::ARMSubArch_v9_4a;
926 case ARM::ArchKind::ARMV9_5A:
927 return Triple::ARMSubArch_v9_5a;
928 case ARM::ArchKind::ARMV9_6A:
929 return Triple::ARMSubArch_v9_6a;
930 case ARM::ArchKind::ARMV9_7A:
931 return Triple::ARMSubArch_v9_7a;
932 case ARM::ArchKind::ARMV8R:
933 return Triple::ARMSubArch_v8r;
934 case ARM::ArchKind::ARMV8MBaseline:
935 return Triple::ARMSubArch_v8m_baseline;
936 case ARM::ArchKind::ARMV8MMainline:
937 return Triple::ARMSubArch_v8m_mainline;
938 case ARM::ArchKind::ARMV8_1MMainline:
939 return Triple::ARMSubArch_v8_1m_mainline;
940 default:
941 return Triple::NoSubArch;
942 }
943}
944
945static Triple::ObjectFormatType getDefaultFormat(const Triple &T) {
946 switch (T.getArch()) {
947 case Triple::UnknownArch:
948 case Triple::aarch64:
949 case Triple::aarch64_32:
950 case Triple::arm:
951 case Triple::thumb:
952 case Triple::x86:
953 case Triple::x86_64:
954 switch (T.getOS()) {
955 case Triple::Win32:
956 case Triple::UEFI:
957 return Triple::COFF;
958 default:
959 return T.isOSDarwin() ? Triple::MachO : Triple::ELF;
960 }
961 case Triple::aarch64_be:
962 case Triple::amdgpu:
963 case Triple::amdil64:
964 case Triple::amdil:
965 case Triple::arc:
966 case Triple::armeb:
967 case Triple::avr:
968 case Triple::bpfeb:
969 case Triple::bpfel:
970 case Triple::csky:
971 case Triple::hexagon:
972 case Triple::hsail64:
973 case Triple::hsail:
974 case Triple::kalimba:
975 case Triple::lanai:
976 case Triple::loongarch32:
977 case Triple::loongarch64:
978 case Triple::m68k:
979 case Triple::mips64:
980 case Triple::mips64el:
981 case Triple::mips:
982 case Triple::msp430:
983 case Triple::nvptx64:
984 case Triple::nvptx:
985 case Triple::ppc64le:
986 case Triple::ppcle:
987 case Triple::r600:
988 case Triple::renderscript32:
989 case Triple::renderscript64:
990 case Triple::riscv32:
991 case Triple::riscv64:
992 case Triple::riscv32be:
993 case Triple::riscv64be:
994 case Triple::shave:
995 case Triple::sparc:
996 case Triple::sparcel:
997 case Triple::sparcv9:
998 case Triple::spir64:
999 case Triple::spir:
1000 case Triple::tce:
1001 case Triple::tcele:
1002 case Triple::tcele64:
1003 case Triple::thumbeb:
1004 case Triple::ve:
1005 case Triple::xcore:
1006 case Triple::xtensa:
1007 return Triple::ELF;
1008
1009 case Triple::mipsel:
1010 if (T.isOSWindows())
1011 return Triple::COFF;
1012 return Triple::ELF;
1013
1014 case Triple::ppc64:
1015 case Triple::ppc:
1016 if (T.isOSAIX())
1017 return Triple::XCOFF;
1018 if (T.isOSDarwin())
1019 return Triple::MachO;
1020 return Triple::ELF;
1021
1022 case Triple::systemz:
1023 if (T.isOSzOS())
1024 return Triple::GOFF;
1025 return Triple::ELF;
1026
1027 case Triple::wasm32:
1028 case Triple::wasm64:
1029 return Triple::Wasm;
1030
1031 case Triple::spirv:
1032 case Triple::spirv32:
1033 case Triple::spirv64:
1034 return Triple::SPIRV;
1035
1036 case Triple::dxil:
1037 return Triple::DXContainer;
1038 }
1039 llvm_unreachable("unknown architecture");
1040}
1041
1042/// Construct a triple from the string representation provided.
1043///
1044/// This stores the string representation and parses the various pieces into
1045/// enum members.
1046Triple::Triple(std::string &&Str) : Data(std::move(Str)) {
1047 // Do minimal parsing by hand here.
1048 SmallVector<StringRef, 4> Components;
1049 StringRef(Data).split(A&: Components, Separator: '-', /*MaxSplit*/ 3);
1050 if (Components.size() > 0) {
1051 Arch = parseArch(ArchName: Components[0]);
1052 SubArch = parseSubArch(SubArchName: Components[0]);
1053 if (Components.size() > 1) {
1054 Vendor = parseVendor(VendorName: Components[1]);
1055 if (Components.size() > 2) {
1056 OS = parseOS(OSName: Components[2]);
1057 if (Components.size() > 3) {
1058 Environment = parseEnvironment(EnvironmentName: Components[3]);
1059 ObjectFormat = parseFormat(EnvironmentName: Components[3]);
1060 }
1061 }
1062 } else {
1063 Environment =
1064 StringSwitch<Triple::EnvironmentType>(Components[0])
1065 .StartsWith(S: "mipsn32", Value: Triple::GNUABIN32)
1066 .StartsWith(S: "mips64", Value: Triple::GNUABI64)
1067 .StartsWith(S: "mipsisa64", Value: Triple::GNUABI64)
1068 .StartsWith(S: "mipsisa32", Value: Triple::GNU)
1069 .Cases(CaseStrings: {"mips", "mipsel", "mipsr6", "mipsr6el"}, Value: Triple::GNU)
1070 .Default(Value: UnknownEnvironment);
1071 }
1072 }
1073 if (ObjectFormat == UnknownObjectFormat)
1074 ObjectFormat = getDefaultFormat(T: *this);
1075}
1076
1077Triple::Triple(const Twine &Str) : Triple(Str.str()) {}
1078
1079/// Construct a triple from string representations of the architecture,
1080/// vendor, and OS.
1081///
1082/// This joins each argument into a canonical string representation and parses
1083/// them into enum members. It leaves the environment unknown and omits it from
1084/// the string representation.
1085Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr)
1086 : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr).str()),
1087 Arch(parseArch(ArchName: ArchStr.str())), SubArch(parseSubArch(SubArchName: ArchStr.str())),
1088 Vendor(parseVendor(VendorName: VendorStr.str())), OS(parseOS(OSName: OSStr.str())),
1089 Environment(), ObjectFormat(Triple::UnknownObjectFormat) {
1090 ObjectFormat = getDefaultFormat(T: *this);
1091}
1092
1093/// Construct a triple from string representations of the architecture,
1094/// vendor, OS, and environment.
1095///
1096/// This joins each argument into a canonical string representation and parses
1097/// them into enum members.
1098Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr,
1099 const Twine &EnvironmentStr)
1100 : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr + Twine('-') +
1101 EnvironmentStr)
1102 .str()),
1103 Arch(parseArch(ArchName: ArchStr.str())), SubArch(parseSubArch(SubArchName: ArchStr.str())),
1104 Vendor(parseVendor(VendorName: VendorStr.str())), OS(parseOS(OSName: OSStr.str())),
1105 Environment(parseEnvironment(EnvironmentName: EnvironmentStr.str())),
1106 ObjectFormat(parseFormat(EnvironmentName: EnvironmentStr.str())) {
1107 if (ObjectFormat == Triple::UnknownObjectFormat)
1108 ObjectFormat = getDefaultFormat(T: *this);
1109}
1110
1111Triple::Triple(ArchType A, SubArchType SA, VendorType V, OSType OS)
1112 : Data((getArchName(Kind: A, SubArch: SA) + Twine('-') + getVendorTypeName(Kind: V) +
1113 Twine('-') + getOSTypeName(Kind: OS))
1114 .str()),
1115 Arch(A), SubArch(SA), Vendor(V), OS(OS),
1116 ObjectFormat(getDefaultFormat(T: *this)) {}
1117
1118Triple::Triple(ArchType A, SubArchType SA, VendorType V, OSType OS,
1119 EnvironmentType E)
1120 : Data((getArchName(Kind: A, SubArch: SA) + Twine('-') + getVendorTypeName(Kind: V) +
1121 Twine('-') + getOSTypeName(Kind: OS) + Twine('-') +
1122 getEnvironmentTypeName(Kind: E))
1123 .str()),
1124 Arch(A), SubArch(SA), Vendor(V), OS(OS), Environment(E),
1125 ObjectFormat(getDefaultFormat(T: *this)) {}
1126
1127Triple::Triple(ArchType A, SubArchType SA, VendorType V, OSType OS,
1128 EnvironmentType E, ObjectFormatType OF)
1129 : Data((getArchName(Kind: A, SubArch: SA) + Twine('-') + getVendorTypeName(Kind: V) +
1130 Twine('-') + getOSTypeName(Kind: OS) + Twine('-') +
1131 getEnvironmentTypeName(Kind: E) + Twine('-') +
1132 getObjectFormatTypeName(Kind: OF))
1133 .str()),
1134 Arch(A), SubArch(SA), Vendor(V), OS(OS), Environment(E),
1135 ObjectFormat(OF) {}
1136
1137static VersionTuple parseVersionFromName(StringRef Name);
1138
1139static StringRef getDXILArchNameFromShaderModel(StringRef ShaderModelStr) {
1140 VersionTuple Ver =
1141 parseVersionFromName(Name: ShaderModelStr.drop_front(N: strlen(s: "shadermodel")));
1142 // Default DXIL minor version when Shader Model version is anything other
1143 // than 6.[0...9] or 6.x (which translates to latest current SM version)
1144 const unsigned SMMajor = 6;
1145 if (!Ver.empty()) {
1146 if (Ver.getMajor() == SMMajor) {
1147 if (std::optional<unsigned> SMMinor = Ver.getMinor()) {
1148 switch (*SMMinor) {
1149 case 0:
1150 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_0);
1151 case 1:
1152 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_1);
1153 case 2:
1154 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_2);
1155 case 3:
1156 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_3);
1157 case 4:
1158 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_4);
1159 case 5:
1160 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_5);
1161 case 6:
1162 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_6);
1163 case 7:
1164 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_7);
1165 case 8:
1166 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_8);
1167 case 9:
1168 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_9);
1169 default:
1170 report_fatal_error(reason: "Unsupported Shader Model version", gen_crash_diag: false);
1171 }
1172 }
1173 }
1174 } else {
1175 // Special case: DXIL minor version is set to LatestCurrentDXILMinor for
1176 // shadermodel6.x is
1177 if (ShaderModelStr == "shadermodel6.x") {
1178 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::LatestDXILSubArch);
1179 }
1180 }
1181 // DXIL version corresponding to Shader Model version other than 6.Minor
1182 // is 1.0
1183 return Triple::getArchName(Kind: Triple::dxil, SubArch: Triple::DXILSubArch_v1_0);
1184}
1185
1186std::string Triple::normalize(StringRef Str, CanonicalForm Form) {
1187 bool IsMinGW32 = false;
1188 bool IsCygwin = false;
1189
1190 // Parse into components.
1191 SmallVector<StringRef, 4> Components;
1192 Str.split(A&: Components, Separator: '-');
1193
1194 // If the first component corresponds to a known architecture, preferentially
1195 // use it for the architecture. If the second component corresponds to a
1196 // known vendor, preferentially use it for the vendor, etc. This avoids silly
1197 // component movement when a component parses as (eg) both a valid arch and a
1198 // valid os.
1199 ArchType Arch = UnknownArch;
1200 if (Components.size() > 0)
1201 Arch = parseArch(ArchName: Components[0]);
1202 VendorType Vendor = UnknownVendor;
1203 if (Components.size() > 1)
1204 Vendor = parseVendor(VendorName: Components[1]);
1205 OSType OS = UnknownOS;
1206 if (Components.size() > 2) {
1207 OS = parseOS(OSName: Components[2]);
1208 IsCygwin = Components[2].starts_with(Prefix: "cygwin") ||
1209 Components[2].starts_with(Prefix: "msys");
1210 IsMinGW32 = Components[2].starts_with(Prefix: "mingw");
1211 }
1212 EnvironmentType Environment = UnknownEnvironment;
1213 if (Components.size() > 3)
1214 Environment = parseEnvironment(EnvironmentName: Components[3]);
1215 ObjectFormatType ObjectFormat = UnknownObjectFormat;
1216 if (Components.size() > 4)
1217 ObjectFormat = parseFormat(EnvironmentName: Components[4]);
1218
1219 // Note which components are already in their final position. These will not
1220 // be moved.
1221 bool Found[4];
1222 Found[0] = Arch != UnknownArch;
1223 Found[1] = Vendor != UnknownVendor;
1224 Found[2] = OS != UnknownOS;
1225 Found[3] = Environment != UnknownEnvironment;
1226
1227 // If they are not there already, permute the components into their canonical
1228 // positions by seeing if they parse as a valid architecture, and if so moving
1229 // the component to the architecture position etc.
1230 for (unsigned Pos = 0; Pos != std::size(Found); ++Pos) {
1231 if (Found[Pos])
1232 continue; // Already in the canonical position.
1233
1234 for (unsigned Idx = 0; Idx != Components.size(); ++Idx) {
1235 // Do not reparse any components that already matched.
1236 if (Idx < std::size(Found) && Found[Idx])
1237 continue;
1238
1239 // Does this component parse as valid for the target position?
1240 bool Valid = false;
1241 StringRef Comp = Components[Idx];
1242 switch (Pos) {
1243 default:
1244 llvm_unreachable("unexpected component type!");
1245 case 0:
1246 Arch = parseArch(ArchName: Comp);
1247 Valid = Arch != UnknownArch;
1248 break;
1249 case 1:
1250 Vendor = parseVendor(VendorName: Comp);
1251 Valid = Vendor != UnknownVendor;
1252 break;
1253 case 2:
1254 OS = parseOS(OSName: Comp);
1255 IsCygwin = Comp.starts_with(Prefix: "cygwin") || Comp.starts_with(Prefix: "msys");
1256 IsMinGW32 = Comp.starts_with(Prefix: "mingw");
1257 Valid = OS != UnknownOS || IsCygwin || IsMinGW32;
1258 break;
1259 case 3:
1260 Environment = parseEnvironment(EnvironmentName: Comp);
1261 Valid = Environment != UnknownEnvironment;
1262 if (!Valid) {
1263 ObjectFormat = parseFormat(EnvironmentName: Comp);
1264 Valid = ObjectFormat != UnknownObjectFormat;
1265 }
1266 break;
1267 }
1268 if (!Valid)
1269 continue; // Nope, try the next component.
1270
1271 // Move the component to the target position, pushing any non-fixed
1272 // components that are in the way to the right. This tends to give
1273 // good results in the common cases of a forgotten vendor component
1274 // or a wrongly positioned environment.
1275 if (Pos < Idx) {
1276 // Insert left, pushing the existing components to the right. For
1277 // example, a-b-i386 -> i386-a-b when moving i386 to the front.
1278 StringRef CurrentComponent(""); // The empty component.
1279 // Replace the component we are moving with an empty component.
1280 std::swap(a&: CurrentComponent, b&: Components[Idx]);
1281 // Insert the component being moved at Pos, displacing any existing
1282 // components to the right.
1283 for (unsigned i = Pos; !CurrentComponent.empty(); ++i) {
1284 // Skip over any fixed components.
1285 while (i < std::size(Found) && Found[i])
1286 ++i;
1287 // Place the component at the new position, getting the component
1288 // that was at this position - it will be moved right.
1289 std::swap(a&: CurrentComponent, b&: Components[i]);
1290 }
1291 } else if (Pos > Idx) {
1292 // Push right by inserting empty components until the component at Idx
1293 // reaches the target position Pos. For example, pc-a -> -pc-a when
1294 // moving pc to the second position.
1295 do {
1296 // Insert one empty component at Idx.
1297 StringRef CurrentComponent(""); // The empty component.
1298 for (unsigned i = Idx; i < Components.size();) {
1299 // Place the component at the new position, getting the component
1300 // that was at this position - it will be moved right.
1301 std::swap(a&: CurrentComponent, b&: Components[i]);
1302 // If it was placed on top of an empty component then we are done.
1303 if (CurrentComponent.empty())
1304 break;
1305 // Advance to the next component, skipping any fixed components.
1306 while (++i < std::size(Found) && Found[i])
1307 ;
1308 }
1309 // The last component was pushed off the end - append it.
1310 if (!CurrentComponent.empty())
1311 Components.push_back(Elt: CurrentComponent);
1312
1313 // Advance Idx to the component's new position.
1314 while (++Idx < std::size(Found) && Found[Idx])
1315 ;
1316 } while (Idx < Pos); // Add more until the final position is reached.
1317 }
1318 assert(Pos < Components.size() && Components[Pos] == Comp &&
1319 "Component moved wrong!");
1320 Found[Pos] = true;
1321 break;
1322 }
1323 }
1324
1325 // If "none" is in the middle component in a three-component triple, treat it
1326 // as the OS (Components[2]) instead of the vendor (Components[1]).
1327 if (Found[0] && !Found[1] && !Found[2] && Found[3] &&
1328 Components[1] == "none" && Components[2].empty())
1329 std::swap(a&: Components[1], b&: Components[2]);
1330
1331 // Replace empty components with "unknown" value.
1332 for (StringRef &C : Components)
1333 if (C.empty())
1334 C = "unknown";
1335
1336 // Special case logic goes here. At this point Arch, Vendor and OS have the
1337 // correct values for the computed components.
1338 std::string NormalizedEnvironment;
1339 if (Environment == Triple::Android &&
1340 Components[3].starts_with(Prefix: "androideabi")) {
1341 StringRef AndroidVersion = Components[3].drop_front(N: strlen(s: "androideabi"));
1342 if (AndroidVersion.empty()) {
1343 Components[3] = "android";
1344 } else {
1345 NormalizedEnvironment = Twine("android", AndroidVersion).str();
1346 Components[3] = NormalizedEnvironment;
1347 }
1348 }
1349
1350 // SUSE uses "gnueabi" to mean "gnueabihf"
1351 if (Vendor == Triple::SUSE && Environment == llvm::Triple::GNUEABI)
1352 Components[3] = "gnueabihf";
1353
1354 if (OS == Triple::Win32) {
1355 Components.resize(N: 4);
1356 Components[2] = "windows";
1357 if (Environment == UnknownEnvironment) {
1358 if (ObjectFormat == UnknownObjectFormat || ObjectFormat == Triple::COFF)
1359 Components[3] = "msvc";
1360 else
1361 Components[3] = getObjectFormatTypeName(Kind: ObjectFormat);
1362 }
1363 } else if (IsMinGW32) {
1364 Components.resize(N: 4);
1365 Components[2] = "windows";
1366 Components[3] = "gnu";
1367 } else if (IsCygwin) {
1368 Components.resize(N: 4);
1369 Components[2] = "windows";
1370 Components[3] = "cygnus";
1371 }
1372 if (IsMinGW32 || IsCygwin ||
1373 (OS == Triple::Win32 && Environment != UnknownEnvironment)) {
1374 if (ObjectFormat != UnknownObjectFormat && ObjectFormat != Triple::COFF) {
1375 Components.resize(N: 5);
1376 Components[4] = getObjectFormatTypeName(Kind: ObjectFormat);
1377 }
1378 }
1379
1380 // Normalize DXIL triple if it does not include DXIL version number.
1381 // Determine DXIL version number using the minor version number of Shader
1382 // Model version specified in target triple, if any. Prior to decoupling DXIL
1383 // version numbering from that of Shader Model DXIL version 1.Y corresponds to
1384 // SM 6.Y. E.g., dxilv1.Y-unknown-shadermodelX.Y-hull
1385 if (Components[0] == "dxil") {
1386 if (Components.size() > 4) {
1387 Components.resize(N: 4);
1388 }
1389 // Add DXIL version only if shadermodel is specified in the triple
1390 if (OS == Triple::ShaderModel) {
1391 Components[0] = getDXILArchNameFromShaderModel(ShaderModelStr: Components[2]);
1392 }
1393 }
1394
1395 // Currently the firmware OS is an Apple specific concept.
1396 if ((Components.size() > 2) && (Components[2] == "firmware") &&
1397 (Components[1] != "apple"))
1398 llvm::reportFatalUsageError(
1399 reason: "the firmware target os is only supported for the apple vendor");
1400
1401 // Canonicalize the components if necessary.
1402 switch (Form) {
1403 case CanonicalForm::ANY:
1404 break;
1405 case CanonicalForm::THREE_IDENT:
1406 case CanonicalForm::FOUR_IDENT:
1407 case CanonicalForm::FIVE_IDENT: {
1408 Components.resize(N: static_cast<unsigned>(Form), NV: "unknown");
1409 break;
1410 }
1411 }
1412
1413 // Stick the corrected components back together to form the normalized string.
1414 return join(R&: Components, Separator: "-");
1415}
1416
1417StringRef Triple::getArchName() const {
1418 return StringRef(Data).split(Separator: '-').first; // Isolate first component
1419}
1420
1421StringRef Triple::getVendorName() const {
1422 StringRef Tmp = StringRef(Data).split(Separator: '-').second; // Strip first component
1423 return Tmp.split(Separator: '-').first; // Isolate second component
1424}
1425
1426StringRef Triple::getOSName() const {
1427 StringRef Tmp = StringRef(Data).split(Separator: '-').second; // Strip first component
1428 Tmp = Tmp.split(Separator: '-').second; // Strip second component
1429 return Tmp.split(Separator: '-').first; // Isolate third component
1430}
1431
1432StringRef Triple::getEnvironmentName() const {
1433 StringRef Tmp = StringRef(Data).split(Separator: '-').second; // Strip first component
1434 Tmp = Tmp.split(Separator: '-').second; // Strip second component
1435 return Tmp.split(Separator: '-').second; // Strip third component
1436}
1437
1438StringRef Triple::getOSAndEnvironmentName() const {
1439 StringRef Tmp = StringRef(Data).split(Separator: '-').second; // Strip first component
1440 return Tmp.split(Separator: '-').second; // Strip second component
1441}
1442
1443static VersionTuple parseVersionFromName(StringRef Name) {
1444 VersionTuple Version;
1445 Version.tryParse(string: Name);
1446 return Version.withoutBuild();
1447}
1448
1449VersionTuple Triple::getEnvironmentVersion() const {
1450 return parseVersionFromName(Name: getEnvironmentVersionString());
1451}
1452
1453StringRef Triple::getEnvironmentVersionString() const {
1454 StringRef EnvironmentName = getEnvironmentName();
1455
1456 // none is a valid environment type - it basically amounts to a freestanding
1457 // environment.
1458 if (EnvironmentName == "none")
1459 return "";
1460
1461 StringRef EnvironmentTypeName = getEnvironmentTypeName(Kind: getEnvironment());
1462 EnvironmentName.consume_front(Prefix: EnvironmentTypeName);
1463
1464 if (EnvironmentName.contains(Other: "-")) {
1465 // -obj is the suffix
1466 if (getObjectFormat() != Triple::UnknownObjectFormat) {
1467 StringRef ObjectFormatTypeName =
1468 getObjectFormatTypeName(Kind: getObjectFormat());
1469 const std::string tmp = (Twine("-") + ObjectFormatTypeName).str();
1470 EnvironmentName.consume_back(Suffix: tmp);
1471 }
1472 }
1473 return EnvironmentName;
1474}
1475
1476VersionTuple Triple::getOSVersion() const {
1477 StringRef OSName = getOSName();
1478 // Assume that the OS portion of the triple starts with the canonical name.
1479 StringRef OSTypeName = getOSTypeName(Kind: getOS());
1480 if (OSName.starts_with(Prefix: OSTypeName))
1481 OSName = OSName.substr(Start: OSTypeName.size());
1482 else if (getOS() == MacOSX)
1483 OSName.consume_front(Prefix: "macos");
1484 else if (OSName.starts_with(Prefix: "visionos"))
1485 OSName.consume_front(Prefix: "visionos");
1486
1487 return parseVersionFromName(Name: OSName);
1488}
1489
1490bool Triple::getMacOSXVersion(VersionTuple &Version) const {
1491 Version = getOSVersion();
1492
1493 switch (getOS()) {
1494 default:
1495 llvm_unreachable("unexpected OS for Darwin triple");
1496 case Darwin:
1497 // Default to darwin8, i.e., MacOSX 10.4.
1498 if (Version.getMajor() == 0)
1499 Version = VersionTuple(8);
1500 // Darwin version numbers are skewed from OS X versions.
1501 if (Version.getMajor() < 4) {
1502 return false;
1503 }
1504 if (Version.getMajor() <= 19) {
1505 Version = VersionTuple(10, Version.getMajor() - 4);
1506 } else if (Version.getMajor() < 25) {
1507 // darwin20-24 corresponds to macOS 11-15.
1508 Version = VersionTuple(11 + Version.getMajor() - 20);
1509 } else if ((Version.getMajor() == 25) || (Version.getMajor() == 26)) {
1510 // darwin25-26 corresponds to macOS 26-27.
1511 Version = VersionTuple(Version.getMajor() + 1);
1512 } else {
1513 // Starting with darwin27, it naturally corresponds to the same macOS
1514 // version.
1515 }
1516 break;
1517 case MacOSX:
1518 // Default to 10.4.
1519 if (Version.getMajor() == 0) {
1520 Version = VersionTuple(10, 4);
1521 } else if (Version.getMajor() < 10) {
1522 return false;
1523 }
1524 break;
1525 case IOS:
1526 case TvOS:
1527 case WatchOS:
1528 // Ignore the version from the triple. This is only handled because the
1529 // the clang driver combines OS X and IOS support into a common Darwin
1530 // toolchain that wants to know the OS X version number even when targeting
1531 // IOS.
1532 Version = VersionTuple(10, 4);
1533 break;
1534 case XROS:
1535 llvm_unreachable("OSX version isn't relevant for xrOS");
1536 case DriverKit:
1537 llvm_unreachable("OSX version isn't relevant for DriverKit");
1538 case Firmware:
1539 llvm_unreachable("OSX version isn't relevant for Firmware");
1540 }
1541 return true;
1542}
1543
1544VersionTuple Triple::getiOSVersion() const {
1545 switch (getOS()) {
1546 default:
1547 llvm_unreachable("unexpected OS for Darwin triple");
1548 case Darwin:
1549 case MacOSX:
1550 // Ignore the version from the triple. This is only handled because the
1551 // the clang driver combines OS X and IOS support into a common Darwin
1552 // toolchain that wants to know the iOS version number even when targeting
1553 // OS X.
1554 return VersionTuple(5);
1555 case IOS:
1556 case TvOS: {
1557 VersionTuple Version = getOSVersion();
1558 // Default to 5.0 (or 7.0 for arm64).
1559 if (Version.getMajor() == 0)
1560 return (getArch() == aarch64) ? VersionTuple(7) : VersionTuple(5);
1561 if (Version.getMajor() == 19)
1562 // tvOS 19 corresponds to ios26.
1563 return VersionTuple(26);
1564 return getCanonicalVersionForOS(OSKind: OSType::IOS, Version,
1565 IsInValidRange: isValidVersionForOS(OSKind: OSType::IOS, Version));
1566 }
1567 case XROS: {
1568 VersionTuple Version = getOSVersion();
1569 // xrOS 1 is aligned with iOS 17.
1570 if (Version.getMajor() < 3)
1571 return Version.withMajorReplaced(NewMajor: Version.getMajor() + 16);
1572 // visionOS 3 corresponds to ios 26+.
1573 if (Version.getMajor() == 3)
1574 return VersionTuple(26);
1575 return getCanonicalVersionForOS(OSKind: OSType::XROS, Version,
1576 IsInValidRange: isValidVersionForOS(OSKind: OSType::XROS, Version));
1577 }
1578 case WatchOS: {
1579 VersionTuple Version = getOSVersion();
1580 // watchOS 12 corresponds to ios 26.
1581 if (Version.getMajor() == 12)
1582 return VersionTuple(26);
1583 return getCanonicalVersionForOS(
1584 OSKind: OSType::WatchOS, Version,
1585 IsInValidRange: isValidVersionForOS(OSKind: OSType::WatchOS, Version));
1586 }
1587 case BridgeOS:
1588 llvm_unreachable("conflicting triple info");
1589 case DriverKit:
1590 llvm_unreachable("DriverKit doesn't have an iOS version");
1591 case Firmware:
1592 llvm_unreachable("iOS version isn't relevant for Firmware");
1593 }
1594}
1595
1596VersionTuple Triple::getWatchOSVersion() const {
1597 switch (getOS()) {
1598 default:
1599 llvm_unreachable("unexpected OS for Darwin triple");
1600 case Darwin:
1601 case MacOSX:
1602 // Ignore the version from the triple. This is only handled because the
1603 // the clang driver combines OS X and IOS support into a common Darwin
1604 // toolchain that wants to know the iOS version number even when targeting
1605 // OS X.
1606 return VersionTuple(2);
1607 case WatchOS: {
1608 VersionTuple Version = getOSVersion();
1609 if (Version.getMajor() == 0)
1610 return VersionTuple(2);
1611 return Version;
1612 }
1613 case IOS:
1614 llvm_unreachable("conflicting triple info");
1615 case XROS:
1616 llvm_unreachable("watchOS version isn't relevant for xrOS");
1617 case DriverKit:
1618 llvm_unreachable("DriverKit doesn't have a WatchOS version");
1619 case Firmware:
1620 llvm_unreachable("watchOS version isn't relevant for Firmware");
1621 }
1622}
1623
1624VersionTuple Triple::getDriverKitVersion() const {
1625 switch (getOS()) {
1626 default:
1627 llvm_unreachable("unexpected OS for Darwin triple");
1628 case DriverKit:
1629 VersionTuple Version = getOSVersion();
1630 if (Version.getMajor() == 0)
1631 return Version.withMajorReplaced(NewMajor: 19);
1632 return Version;
1633 }
1634}
1635
1636VersionTuple Triple::getVulkanVersion() const {
1637 if (getArch() != spirv || getOS() != Vulkan)
1638 llvm_unreachable("invalid Vulkan SPIR-V triple");
1639
1640 VersionTuple VulkanVersion = getOSVersion();
1641 SubArchType SpirvVersion = getSubArch();
1642
1643 llvm::DenseMap<VersionTuple, SubArchType> ValidVersionMap = {
1644 // Vulkan 1.2 -> SPIR-V 1.5.
1645 {VersionTuple(1, 2), SPIRVSubArch_v15},
1646 // Vulkan 1.3 -> SPIR-V 1.6.
1647 {VersionTuple(1, 3), SPIRVSubArch_v16}};
1648
1649 // If Vulkan version is unset, default to 1.2.
1650 if (VulkanVersion == VersionTuple(0))
1651 VulkanVersion = VersionTuple(1, 2);
1652
1653 if (ValidVersionMap.contains(Val: VulkanVersion) &&
1654 (ValidVersionMap.lookup(Val: VulkanVersion) == SpirvVersion ||
1655 SpirvVersion == NoSubArch))
1656 return VulkanVersion;
1657
1658 return VersionTuple(0);
1659}
1660
1661VersionTuple Triple::getDXILVersion() const {
1662 if (getArch() != dxil || getOS() != ShaderModel)
1663 llvm_unreachable("invalid DXIL triple");
1664 StringRef Arch = getArchName();
1665 if (getSubArch() == NoSubArch)
1666 Arch = getDXILArchNameFromShaderModel(ShaderModelStr: getOSName());
1667 Arch.consume_front(Prefix: "dxilv");
1668 VersionTuple DXILVersion = parseVersionFromName(Name: Arch);
1669 // FIXME: validate DXIL version against Shader Model version.
1670 // Tracked by https://github.com/llvm/llvm-project/issues/91388
1671 return DXILVersion;
1672}
1673
1674void Triple::setTriple(const Twine &Str) { *this = Triple(Str); }
1675
1676void Triple::setArch(ArchType Kind, SubArchType SubArch) {
1677 setArchName(getArchName(Kind, SubArch));
1678}
1679
1680void Triple::setVendor(VendorType Kind) {
1681 setVendorName(getVendorTypeName(Kind));
1682}
1683
1684void Triple::setOS(OSType Kind) { setOSName(getOSTypeName(Kind)); }
1685
1686void Triple::setEnvironment(EnvironmentType Kind) {
1687 if (ObjectFormat == getDefaultFormat(T: *this))
1688 return setEnvironmentName(getEnvironmentTypeName(Kind));
1689
1690 setEnvironmentName((getEnvironmentTypeName(Kind) + Twine("-") +
1691 getObjectFormatTypeName(Kind: ObjectFormat))
1692 .str());
1693}
1694
1695void Triple::setObjectFormat(ObjectFormatType Kind) {
1696 if (Environment == UnknownEnvironment)
1697 return setEnvironmentName(getObjectFormatTypeName(Kind));
1698
1699 setEnvironmentName((getEnvironmentTypeName(Kind: Environment) + Twine("-") +
1700 getObjectFormatTypeName(Kind))
1701 .str());
1702}
1703
1704void Triple::setArchName(StringRef Str) {
1705 setTriple(Str + "-" + getVendorName() + "-" + getOSAndEnvironmentName());
1706}
1707
1708void Triple::setVendorName(StringRef Str) {
1709 setTriple(getArchName() + "-" + Str + "-" + getOSAndEnvironmentName());
1710}
1711
1712void Triple::setOSName(StringRef Str) {
1713 if (hasEnvironment())
1714 setTriple(getArchName() + "-" + getVendorName() + "-" + Str + "-" +
1715 getEnvironmentName());
1716 else
1717 setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
1718}
1719
1720void Triple::setEnvironmentName(StringRef Str) {
1721 setTriple(getArchName() + "-" + getVendorName() + "-" + getOSName() + "-" +
1722 Str);
1723}
1724
1725void Triple::setOSAndEnvironmentName(StringRef Str) {
1726 setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
1727}
1728
1729unsigned Triple::getArchPointerBitWidth(llvm::Triple::ArchType Arch) {
1730 switch (Arch) {
1731 case llvm::Triple::UnknownArch:
1732 return 0;
1733
1734 case llvm::Triple::avr:
1735 case llvm::Triple::msp430:
1736 return 16;
1737
1738 case llvm::Triple::aarch64_32:
1739 case llvm::Triple::amdil:
1740 case llvm::Triple::arc:
1741 case llvm::Triple::arm:
1742 case llvm::Triple::armeb:
1743 case llvm::Triple::csky:
1744 case llvm::Triple::dxil:
1745 case llvm::Triple::hexagon:
1746 case llvm::Triple::hsail:
1747 case llvm::Triple::kalimba:
1748 case llvm::Triple::lanai:
1749 case llvm::Triple::loongarch32:
1750 case llvm::Triple::m68k:
1751 case llvm::Triple::mips:
1752 case llvm::Triple::mipsel:
1753 case llvm::Triple::nvptx:
1754 case llvm::Triple::ppc:
1755 case llvm::Triple::ppcle:
1756 case llvm::Triple::r600:
1757 case llvm::Triple::renderscript32:
1758 case llvm::Triple::riscv32:
1759 case llvm::Triple::riscv32be:
1760 case llvm::Triple::shave:
1761 case llvm::Triple::sparc:
1762 case llvm::Triple::sparcel:
1763 case llvm::Triple::spir:
1764 case llvm::Triple::spirv32:
1765 case llvm::Triple::tce:
1766 case llvm::Triple::tcele:
1767 case llvm::Triple::thumb:
1768 case llvm::Triple::thumbeb:
1769 case llvm::Triple::wasm32:
1770 case llvm::Triple::x86:
1771 case llvm::Triple::xcore:
1772 case llvm::Triple::xtensa:
1773 return 32;
1774
1775 case llvm::Triple::aarch64:
1776 case llvm::Triple::aarch64_be:
1777 case llvm::Triple::amdgpu:
1778 case llvm::Triple::amdil64:
1779 case llvm::Triple::bpfeb:
1780 case llvm::Triple::bpfel:
1781 case llvm::Triple::hsail64:
1782 case llvm::Triple::loongarch64:
1783 case llvm::Triple::mips64:
1784 case llvm::Triple::mips64el:
1785 case llvm::Triple::nvptx64:
1786 case llvm::Triple::ppc64:
1787 case llvm::Triple::ppc64le:
1788 case llvm::Triple::renderscript64:
1789 case llvm::Triple::riscv64:
1790 case llvm::Triple::riscv64be:
1791 case llvm::Triple::sparcv9:
1792 case llvm::Triple::spirv:
1793 case llvm::Triple::spir64:
1794 case llvm::Triple::spirv64:
1795 case llvm::Triple::tcele64:
1796 case llvm::Triple::systemz:
1797 case llvm::Triple::ve:
1798 case llvm::Triple::wasm64:
1799 case llvm::Triple::x86_64:
1800 return 64;
1801 }
1802 llvm_unreachable("Invalid architecture value");
1803}
1804
1805unsigned Triple::getTrampolineSize() const {
1806 switch (getArch()) {
1807 default:
1808 break;
1809 case Triple::ppc:
1810 case Triple::ppcle:
1811 if (isOSLinux())
1812 return 40;
1813 break;
1814 case Triple::ppc64:
1815 case Triple::ppc64le:
1816 if (isOSLinux())
1817 return 48;
1818 break;
1819 }
1820 return 32;
1821}
1822
1823bool Triple::isArch64Bit() const {
1824 return getArchPointerBitWidth(Arch: getArch()) == 64;
1825}
1826
1827bool Triple::isArch32Bit() const {
1828 return getArchPointerBitWidth(Arch: getArch()) == 32;
1829}
1830
1831bool Triple::isArch16Bit() const {
1832 return getArchPointerBitWidth(Arch: getArch()) == 16;
1833}
1834
1835Triple Triple::get32BitArchVariant() const {
1836 Triple T(*this);
1837 switch (getArch()) {
1838 case Triple::UnknownArch:
1839 case Triple::amdgpu:
1840 case Triple::avr:
1841 case Triple::bpfeb:
1842 case Triple::bpfel:
1843 case Triple::msp430:
1844 case Triple::systemz:
1845 case Triple::ve:
1846 T.setArch(Kind: UnknownArch);
1847 break;
1848
1849 case Triple::aarch64_32:
1850 case Triple::amdil:
1851 case Triple::arc:
1852 case Triple::arm:
1853 case Triple::armeb:
1854 case Triple::csky:
1855 case Triple::dxil:
1856 case Triple::hexagon:
1857 case Triple::hsail:
1858 case Triple::kalimba:
1859 case Triple::lanai:
1860 case Triple::loongarch32:
1861 case Triple::m68k:
1862 case Triple::mips:
1863 case Triple::mipsel:
1864 case Triple::nvptx:
1865 case Triple::ppc:
1866 case Triple::ppcle:
1867 case Triple::r600:
1868 case Triple::renderscript32:
1869 case Triple::riscv32:
1870 case Triple::riscv32be:
1871 case Triple::shave:
1872 case Triple::sparc:
1873 case Triple::sparcel:
1874 case Triple::spir:
1875 case Triple::spirv32:
1876 case Triple::tce:
1877 case Triple::tcele:
1878 case Triple::thumb:
1879 case Triple::thumbeb:
1880 case Triple::wasm32:
1881 case Triple::x86:
1882 case Triple::xcore:
1883 case Triple::xtensa:
1884 // Already 32-bit.
1885 break;
1886
1887 case Triple::aarch64:
1888 T.setArch(Kind: Triple::arm);
1889 break;
1890 case Triple::aarch64_be:
1891 T.setArch(Kind: Triple::armeb);
1892 break;
1893 case Triple::amdil64:
1894 T.setArch(Kind: Triple::amdil);
1895 break;
1896 case Triple::hsail64:
1897 T.setArch(Kind: Triple::hsail);
1898 break;
1899 case Triple::loongarch64:
1900 T.setArch(Kind: Triple::loongarch32);
1901 break;
1902 case Triple::mips64:
1903 T.setArch(Kind: Triple::mips, SubArch: getSubArch());
1904 break;
1905 case Triple::mips64el:
1906 T.setArch(Kind: Triple::mipsel, SubArch: getSubArch());
1907 break;
1908 case Triple::nvptx64:
1909 T.setArch(Kind: Triple::nvptx);
1910 break;
1911 case Triple::ppc64:
1912 T.setArch(Kind: Triple::ppc);
1913 break;
1914 case Triple::ppc64le:
1915 T.setArch(Kind: Triple::ppcle);
1916 break;
1917 case Triple::renderscript64:
1918 T.setArch(Kind: Triple::renderscript32);
1919 break;
1920 case Triple::riscv64:
1921 T.setArch(Kind: Triple::riscv32);
1922 break;
1923 case Triple::riscv64be:
1924 T.setArch(Kind: Triple::riscv32be);
1925 break;
1926 case Triple::sparcv9:
1927 T.setArch(Kind: Triple::sparc);
1928 break;
1929 case Triple::spir64:
1930 T.setArch(Kind: Triple::spir);
1931 break;
1932 case Triple::spirv:
1933 case Triple::spirv64:
1934 T.setArch(Kind: Triple::spirv32, SubArch: getSubArch());
1935 break;
1936 case Triple::tcele64:
1937 T.setArch(Kind: Triple::tcele);
1938 break;
1939 case Triple::wasm64:
1940 T.setArch(Kind: Triple::wasm32);
1941 break;
1942 case Triple::x86_64:
1943 T.setArch(Kind: Triple::x86);
1944 break;
1945 }
1946 return T;
1947}
1948
1949Triple Triple::get64BitArchVariant() const {
1950 Triple T(*this);
1951 switch (getArch()) {
1952 case Triple::UnknownArch:
1953 case Triple::arc:
1954 case Triple::avr:
1955 case Triple::csky:
1956 case Triple::dxil:
1957 case Triple::hexagon:
1958 case Triple::kalimba:
1959 case Triple::lanai:
1960 case Triple::m68k:
1961 case Triple::msp430:
1962 case Triple::r600:
1963 case Triple::shave:
1964 case Triple::sparcel:
1965 case Triple::tce:
1966 case Triple::xcore:
1967 case Triple::xtensa:
1968 T.setArch(Kind: UnknownArch);
1969 break;
1970
1971 case Triple::aarch64:
1972 case Triple::aarch64_be:
1973 case Triple::amdgpu:
1974 case Triple::amdil64:
1975 case Triple::bpfeb:
1976 case Triple::bpfel:
1977 case Triple::hsail64:
1978 case Triple::loongarch64:
1979 case Triple::mips64:
1980 case Triple::mips64el:
1981 case Triple::nvptx64:
1982 case Triple::ppc64:
1983 case Triple::ppc64le:
1984 case Triple::renderscript64:
1985 case Triple::riscv64:
1986 case Triple::riscv64be:
1987 case Triple::sparcv9:
1988 case Triple::spir64:
1989 case Triple::spirv64:
1990 case Triple::systemz:
1991 case Triple::tcele64:
1992 case Triple::ve:
1993 case Triple::wasm64:
1994 case Triple::x86_64:
1995 // Already 64-bit.
1996 break;
1997
1998 case Triple::aarch64_32:
1999 T.setArch(Kind: Triple::aarch64);
2000 break;
2001 case Triple::amdil:
2002 T.setArch(Kind: Triple::amdil64);
2003 break;
2004 case Triple::arm:
2005 T.setArch(Kind: Triple::aarch64);
2006 break;
2007 case Triple::armeb:
2008 T.setArch(Kind: Triple::aarch64_be);
2009 break;
2010 case Triple::hsail:
2011 T.setArch(Kind: Triple::hsail64);
2012 break;
2013 case Triple::loongarch32:
2014 T.setArch(Kind: Triple::loongarch64);
2015 break;
2016 case Triple::mips:
2017 T.setArch(Kind: Triple::mips64, SubArch: getSubArch());
2018 break;
2019 case Triple::mipsel:
2020 T.setArch(Kind: Triple::mips64el, SubArch: getSubArch());
2021 break;
2022 case Triple::nvptx:
2023 T.setArch(Kind: Triple::nvptx64);
2024 break;
2025 case Triple::ppc:
2026 T.setArch(Kind: Triple::ppc64);
2027 break;
2028 case Triple::ppcle:
2029 T.setArch(Kind: Triple::ppc64le);
2030 break;
2031 case Triple::renderscript32:
2032 T.setArch(Kind: Triple::renderscript64);
2033 break;
2034 case Triple::riscv32:
2035 T.setArch(Kind: Triple::riscv64);
2036 break;
2037 case Triple::riscv32be:
2038 T.setArch(Kind: Triple::riscv64be);
2039 break;
2040 case Triple::sparc:
2041 T.setArch(Kind: Triple::sparcv9);
2042 break;
2043 case Triple::spir:
2044 T.setArch(Kind: Triple::spir64);
2045 break;
2046 case Triple::spirv:
2047 case Triple::spirv32:
2048 T.setArch(Kind: Triple::spirv64, SubArch: getSubArch());
2049 break;
2050 case Triple::tcele:
2051 T.setArch(Kind: Triple::tcele64);
2052 break;
2053 case Triple::thumb:
2054 T.setArch(Kind: Triple::aarch64);
2055 break;
2056 case Triple::thumbeb:
2057 T.setArch(Kind: Triple::aarch64_be);
2058 break;
2059 case Triple::wasm32:
2060 T.setArch(Kind: Triple::wasm64);
2061 break;
2062 case Triple::x86:
2063 T.setArch(Kind: Triple::x86_64);
2064 break;
2065 }
2066 return T;
2067}
2068
2069Triple Triple::getBigEndianArchVariant() const {
2070 Triple T(*this);
2071 // Already big endian.
2072 if (!isLittleEndian())
2073 return T;
2074 switch (getArch()) {
2075 case Triple::UnknownArch:
2076 case Triple::amdgpu:
2077 case Triple::amdil64:
2078 case Triple::amdil:
2079 case Triple::avr:
2080 case Triple::dxil:
2081 case Triple::hexagon:
2082 case Triple::hsail64:
2083 case Triple::hsail:
2084 case Triple::kalimba:
2085 case Triple::loongarch32:
2086 case Triple::loongarch64:
2087 case Triple::msp430:
2088 case Triple::nvptx64:
2089 case Triple::nvptx:
2090 case Triple::r600:
2091 case Triple::renderscript32:
2092 case Triple::renderscript64:
2093 case Triple::shave:
2094 case Triple::spir64:
2095 case Triple::spir:
2096 case Triple::spirv:
2097 case Triple::spirv32:
2098 case Triple::spirv64:
2099 case Triple::tcele64:
2100 case Triple::wasm32:
2101 case Triple::wasm64:
2102 case Triple::x86:
2103 case Triple::x86_64:
2104 case Triple::xcore:
2105 case Triple::ve:
2106 case Triple::csky:
2107 case Triple::xtensa:
2108
2109 // ARM is intentionally unsupported here, changing the architecture would
2110 // drop any arch suffixes.
2111 case Triple::arm:
2112 case Triple::thumb:
2113 T.setArch(Kind: UnknownArch);
2114 break;
2115
2116 case Triple::aarch64:
2117 T.setArch(Kind: Triple::aarch64_be);
2118 break;
2119 case Triple::bpfel:
2120 T.setArch(Kind: Triple::bpfeb);
2121 break;
2122 case Triple::mips64el:
2123 T.setArch(Kind: Triple::mips64, SubArch: getSubArch());
2124 break;
2125 case Triple::mipsel:
2126 T.setArch(Kind: Triple::mips, SubArch: getSubArch());
2127 break;
2128 case Triple::ppcle:
2129 T.setArch(Kind: Triple::ppc);
2130 break;
2131 case Triple::ppc64le:
2132 T.setArch(Kind: Triple::ppc64);
2133 break;
2134 case Triple::riscv32:
2135 T.setArch(Kind: Triple::riscv32be);
2136 break;
2137 case Triple::riscv64:
2138 T.setArch(Kind: Triple::riscv64be);
2139 break;
2140 case Triple::sparcel:
2141 T.setArch(Kind: Triple::sparc);
2142 break;
2143 case Triple::tcele:
2144 T.setArch(Kind: Triple::tce);
2145 break;
2146 default:
2147 llvm_unreachable("getBigEndianArchVariant: unknown triple.");
2148 }
2149 return T;
2150}
2151
2152Triple Triple::getLittleEndianArchVariant() const {
2153 Triple T(*this);
2154 if (isLittleEndian())
2155 return T;
2156
2157 switch (getArch()) {
2158 case Triple::UnknownArch:
2159 case Triple::lanai:
2160 case Triple::sparcv9:
2161 case Triple::systemz:
2162 case Triple::m68k:
2163
2164 // ARM is intentionally unsupported here, changing the architecture would
2165 // drop any arch suffixes.
2166 case Triple::armeb:
2167 case Triple::thumbeb:
2168 T.setArch(Kind: UnknownArch);
2169 break;
2170
2171 case Triple::aarch64_be:
2172 T.setArch(Kind: Triple::aarch64);
2173 break;
2174 case Triple::bpfeb:
2175 T.setArch(Kind: Triple::bpfel);
2176 break;
2177 case Triple::mips64:
2178 T.setArch(Kind: Triple::mips64el, SubArch: getSubArch());
2179 break;
2180 case Triple::mips:
2181 T.setArch(Kind: Triple::mipsel, SubArch: getSubArch());
2182 break;
2183 case Triple::ppc:
2184 T.setArch(Kind: Triple::ppcle);
2185 break;
2186 case Triple::ppc64:
2187 T.setArch(Kind: Triple::ppc64le);
2188 break;
2189 case Triple::riscv32be:
2190 T.setArch(Kind: Triple::riscv32);
2191 break;
2192 case Triple::riscv64be:
2193 T.setArch(Kind: Triple::riscv64);
2194 break;
2195 case Triple::sparc:
2196 T.setArch(Kind: Triple::sparcel);
2197 break;
2198 case Triple::tce:
2199 T.setArch(Kind: Triple::tcele);
2200 break;
2201 default:
2202 llvm_unreachable("getLittleEndianArchVariant: unknown triple.");
2203 }
2204 return T;
2205}
2206
2207bool Triple::isLittleEndian() const {
2208 switch (getArch()) {
2209 case Triple::aarch64:
2210 case Triple::aarch64_32:
2211 case Triple::amdgpu:
2212 case Triple::amdil64:
2213 case Triple::amdil:
2214 case Triple::arm:
2215 case Triple::avr:
2216 case Triple::bpfel:
2217 case Triple::csky:
2218 case Triple::dxil:
2219 case Triple::hexagon:
2220 case Triple::hsail64:
2221 case Triple::hsail:
2222 case Triple::kalimba:
2223 case Triple::loongarch32:
2224 case Triple::loongarch64:
2225 case Triple::mips64el:
2226 case Triple::mipsel:
2227 case Triple::msp430:
2228 case Triple::nvptx64:
2229 case Triple::nvptx:
2230 case Triple::ppcle:
2231 case Triple::ppc64le:
2232 case Triple::r600:
2233 case Triple::renderscript32:
2234 case Triple::renderscript64:
2235 case Triple::riscv32:
2236 case Triple::riscv64:
2237 case Triple::shave:
2238 case Triple::sparcel:
2239 case Triple::spir64:
2240 case Triple::spir:
2241 case Triple::spirv:
2242 case Triple::spirv32:
2243 case Triple::spirv64:
2244 case Triple::tcele:
2245 case Triple::tcele64:
2246 case Triple::thumb:
2247 case Triple::ve:
2248 case Triple::wasm32:
2249 case Triple::wasm64:
2250 case Triple::x86:
2251 case Triple::x86_64:
2252 case Triple::xcore:
2253 case Triple::xtensa:
2254 return true;
2255 default:
2256 return false;
2257 }
2258}
2259
2260unsigned Triple::getDefaultWCharSize() const {
2261 if (getArch() == Triple::xcore)
2262 return 1;
2263 if (isOSWindowsOrUEFI() || isPS())
2264 return 2;
2265 if (isOSAIX() && isArch32Bit())
2266 return 2;
2267 return 4;
2268}
2269
2270bool Triple::isCompatibleWith(const Triple &Other) const {
2271 // On MinGW, C code is usually built with a "w64" vendor, while Rust
2272 // often uses a "pc" vendor.
2273 bool IgnoreVendor = isWindowsGNUEnvironment();
2274
2275 // ARM and Thumb triples are compatible, if subarch, vendor and OS match.
2276 if ((getArch() == Triple::thumb && Other.getArch() == Triple::arm) ||
2277 (getArch() == Triple::arm && Other.getArch() == Triple::thumb) ||
2278 (getArch() == Triple::thumbeb && Other.getArch() == Triple::armeb) ||
2279 (getArch() == Triple::armeb && Other.getArch() == Triple::thumbeb)) {
2280 if (getVendor() == Triple::Apple)
2281 return getSubArch() == Other.getSubArch() &&
2282 getVendor() == Other.getVendor() && getOS() == Other.getOS();
2283 else
2284 return getSubArch() == Other.getSubArch() &&
2285 (getVendor() == Other.getVendor() || IgnoreVendor) &&
2286 getOS() == Other.getOS() &&
2287 getEnvironment() == Other.getEnvironment() &&
2288 getObjectFormat() == Other.getObjectFormat();
2289 }
2290
2291 if (getArch() == Triple::amdgpu && Other.getArch() == Triple::amdgpu) {
2292 if (getOS() != Other.getOS() || getVendor() != Other.getVendor() ||
2293 getEnvironment() != Other.getEnvironment() ||
2294 getObjectFormat() != Other.getObjectFormat())
2295 return false;
2296 return AMDGPU::isSubArchCompatible(A: *this, B: Other);
2297 }
2298
2299 // If vendor is apple, ignore the version number (the environment field)
2300 // and the object format.
2301 if (getVendor() == Triple::Apple)
2302 return getArch() == Other.getArch() && getSubArch() == Other.getSubArch() &&
2303 (getVendor() == Other.getVendor() || IgnoreVendor) &&
2304 getOS() == Other.getOS();
2305
2306 return getArch() == Other.getArch() && getSubArch() == Other.getSubArch() &&
2307 (getVendor() == Other.getVendor() || IgnoreVendor) &&
2308 getOS() == Other.getOS() &&
2309 getEnvironment() == Other.getEnvironment() &&
2310 getObjectFormat() == Other.getObjectFormat();
2311}
2312
2313std::string Triple::merge(const Triple &Other) const {
2314 // If vendor is apple, pick the triple with the larger version number.
2315 if (getVendor() == Triple::Apple && Other.isOSVersionLT(Other: *this))
2316 return str();
2317
2318 if (isAMDGCN() && Other.isAMDGCN() && getOS() == Other.getOS() &&
2319 getVendor() == Other.getVendor())
2320 return AMDGPU::mergeSubArch(A: *this, B: Other);
2321
2322 return Other.str();
2323}
2324
2325bool Triple::isMacOSXVersionLT(unsigned Major, unsigned Minor,
2326 unsigned Micro) const {
2327 assert(isMacOSX() && "Not an OS X triple!");
2328
2329 // If this is OS X, expect a sane version number.
2330 if (getOS() == Triple::MacOSX)
2331 return isOSVersionLT(Major, Minor, Micro);
2332
2333 // Otherwise, compare to the "Darwin" number.
2334 if (Major == 10)
2335 return isOSVersionLT(Major: Minor + 4, Minor: Micro, Micro: 0);
2336 assert(Major >= 11 && "Unexpected major version");
2337 if (Major < 25)
2338 return isOSVersionLT(Major: Major - 11 + 20, Minor, Micro);
2339 return isOSVersionLT(Major: Major + 1, Minor, Micro);
2340}
2341
2342VersionTuple Triple::getMinimumSupportedOSVersion() const {
2343 if (getVendor() != Triple::Apple || getArch() != Triple::aarch64)
2344 return VersionTuple();
2345 switch (getOS()) {
2346 case Triple::MacOSX:
2347 // ARM64 slice is supported starting from macOS 11.0+.
2348 return VersionTuple(11, 0, 0);
2349 case Triple::IOS:
2350 // ARM64 slice is supported starting from Mac Catalyst 14 (macOS 11).
2351 // ARM64 simulators are supported for iOS 14+.
2352 if (isMacCatalystEnvironment() || isSimulatorEnvironment())
2353 return VersionTuple(14, 0, 0);
2354 // ARM64e slice is supported starting from iOS 14.
2355 if (isArm64e())
2356 return VersionTuple(14, 0, 0);
2357 break;
2358 case Triple::TvOS:
2359 // ARM64 simulators are supported for tvOS 14+.
2360 if (isSimulatorEnvironment())
2361 return VersionTuple(14, 0, 0);
2362 break;
2363 case Triple::WatchOS:
2364 // ARM64 simulators are supported for watchOS 7+.
2365 if (isSimulatorEnvironment())
2366 return VersionTuple(7, 0, 0);
2367 // ARM64/ARM64e slices are supported starting from watchOS 26.
2368 // ARM64_32 is older though.
2369 assert(getArch() != Triple::aarch64_32);
2370 return VersionTuple(26, 0, 0);
2371 case Triple::DriverKit:
2372 return VersionTuple(20, 0, 0);
2373 default:
2374 break;
2375 }
2376 return VersionTuple();
2377}
2378
2379VersionTuple Triple::getCanonicalVersionForOS(OSType OSKind,
2380 const VersionTuple &Version,
2381 bool IsInValidRange) {
2382 const unsigned MacOSRangeBump = 10;
2383 const unsigned IOSRangeBump = 7;
2384 const unsigned XROSRangeBump = 23;
2385 const unsigned WatchOSRangeBump = 14;
2386 switch (OSKind) {
2387 case MacOSX: {
2388 // macOS 10.16 is canonicalized to macOS 11.
2389 if (Version == VersionTuple(10, 16))
2390 return VersionTuple(11, 0);
2391 // macOS 16 is canonicalized to macOS 26.
2392 if (Version == VersionTuple(16, 0))
2393 return VersionTuple(26, 0);
2394 if (!IsInValidRange)
2395 return Version.withMajorReplaced(NewMajor: Version.getMajor() + MacOSRangeBump);
2396 break;
2397 }
2398 case IOS:
2399 case TvOS: {
2400 // Both iOS & tvOS 19.0 canonicalize to 26.
2401 if (Version == VersionTuple(19, 0))
2402 return VersionTuple(26, 0);
2403 if (!IsInValidRange)
2404 return Version.withMajorReplaced(NewMajor: Version.getMajor() + IOSRangeBump);
2405 break;
2406 }
2407 case XROS: {
2408 // visionOS3 is canonicalized to 26.
2409 if (Version == VersionTuple(3, 0))
2410 return VersionTuple(26, 0);
2411 if (!IsInValidRange)
2412 return Version.withMajorReplaced(NewMajor: Version.getMajor() + XROSRangeBump);
2413 break;
2414 }
2415 case WatchOS: {
2416 // watchOS 12 is canonicalized to 26.
2417 if (Version == VersionTuple(12, 0))
2418 return VersionTuple(26, 0);
2419 if (!IsInValidRange)
2420 return Version.withMajorReplaced(NewMajor: Version.getMajor() + WatchOSRangeBump);
2421 break;
2422 }
2423 case DriverKit: {
2424 // DriverKit26 is canonicalized to 27.
2425 if (Version.getMajor() == 26U)
2426 return Version.withMajorReplaced(NewMajor: 27);
2427 break;
2428 }
2429 default:
2430 return Version;
2431 }
2432
2433 return Version;
2434}
2435
2436bool Triple::isValidVersionForOS(OSType OSKind, const VersionTuple &Version) {
2437 /// This constant is used to capture gaps in versioning.
2438 const VersionTuple CommonVersion(26);
2439 auto IsValid = [&](const VersionTuple &StartingVersion) {
2440 return !((Version > StartingVersion) && (Version < CommonVersion));
2441 };
2442 switch (OSKind) {
2443 case WatchOS: {
2444 const VersionTuple StartingWatchOS(12);
2445 return IsValid(StartingWatchOS);
2446 }
2447 case IOS:
2448 case TvOS: {
2449 const VersionTuple StartingIOS(19);
2450 return IsValid(StartingIOS);
2451 }
2452 case MacOSX: {
2453 const VersionTuple StartingMacOS(16);
2454 return IsValid(StartingMacOS);
2455 }
2456 case XROS: {
2457 const VersionTuple StartingXROS(3);
2458 return IsValid(StartingXROS);
2459 }
2460 default:
2461 return true;
2462 }
2463
2464 llvm_unreachable("unexpected or invalid os version");
2465}
2466
2467ExceptionHandling Triple::getDefaultExceptionHandling() const {
2468 if (isOSBinFormatCOFF()) {
2469 if (getArch() == Triple::x86 &&
2470 (isOSCygMing() || isWindowsItaniumEnvironment()))
2471 return ExceptionHandling::DwarfCFI;
2472 return ExceptionHandling::WinEH;
2473 }
2474
2475 if (isOSBinFormatXCOFF())
2476 return ExceptionHandling::AIX;
2477 if (isOSBinFormatGOFF())
2478 return ExceptionHandling::ZOS;
2479
2480 if (isARM() || isThumb()) {
2481 if (isOSBinFormatELF()) {
2482 return getOS() == Triple::NetBSD ? ExceptionHandling::DwarfCFI
2483 : ExceptionHandling::ARM;
2484 }
2485
2486 return isOSDarwin() && !isWatchABI() ? ExceptionHandling::SjLj
2487 : ExceptionHandling::DwarfCFI;
2488 }
2489
2490 if (isAArch64() || isX86() || isPPC() || isMIPS() || isSPARC() || isBPF() ||
2491 isRISCV() || isLoongArch())
2492 return ExceptionHandling::DwarfCFI;
2493
2494 switch (getArch()) {
2495 case Triple::arc:
2496 case Triple::csky:
2497 case Triple::hexagon:
2498 case Triple::lanai:
2499 case Triple::m68k:
2500 case Triple::msp430:
2501 case Triple::systemz:
2502 case Triple::xcore:
2503 case Triple::xtensa:
2504 return ExceptionHandling::DwarfCFI;
2505 default:
2506 break;
2507 }
2508
2509 // Explicitly none targets.
2510 if (isWasm() || isAMDGPU() || isNVPTX() || isSPIROrSPIRV())
2511 return ExceptionHandling::None;
2512
2513 // Default to none.
2514 return ExceptionHandling::None;
2515}
2516
2517static FloatABI::ABIType getARMDefaultFloatABI(const Triple &T) {
2518 Triple::EnvironmentType Env = T.getEnvironment();
2519 bool IsHard =
2520 Env == Triple::GNUEABIHF || Env == Triple::GNUEABIHFT64 ||
2521 Env == Triple::MuslEABIHF || Env == Triple::EABIHF ||
2522 (T.isOSBinFormatMachO() && T.getSubArch() == Triple::ARMSubArch_v7em) ||
2523 T.isOSWindows() || ARM::computeTargetABI(TT: T, ABIName: "") == ARM::ARM_ABI_AAPCS16;
2524 return IsHard ? FloatABI::Hard : FloatABI::Soft;
2525}
2526
2527FloatABI::ABIType Triple::getDefaultFloatABI() const {
2528 if (isARM() || isThumb())
2529 return getARMDefaultFloatABI(T: *this);
2530
2531 // MIPS defaults to hard float, except on FreeBSD which uses soft float.
2532 if (isMIPS())
2533 return isOSFreeBSD() ? FloatABI::Soft : FloatABI::Hard;
2534
2535 if (isCSKY() || isAVR() || getArch() == msp430)
2536 return FloatABI::Soft;
2537
2538 // Most targets use hard float unless soft float is explicitly requested.
2539 return FloatABI::Hard;
2540}
2541
2542LongDoubleFormat Triple::getDefaultLongDoubleFormat() const {
2543 switch (getArch()) {
2544 case loongarch64:
2545 case riscv32:
2546 case riscv64:
2547 case riscv32be:
2548 case riscv64be:
2549 case sparc:
2550 case sparcel:
2551 case sparcv9:
2552 case systemz:
2553 case ve:
2554 case wasm32:
2555 case wasm64:
2556 return LongDoubleFormat::IEEEquad;
2557 case ppc:
2558 case ppcle:
2559 case ppc64:
2560 case ppc64le:
2561 // PowerPC uses IBM double-double, except on a handful of OSes that use
2562 // plain IEEE double. NetBSD only switches to IEEE double on 32-bit PowerPC.
2563 if (isOSAIX() || isOSFreeBSD() || isOSOpenBSD() || isMusl() ||
2564 (isOSNetBSD() && isPPC32()))
2565 return LongDoubleFormat::IEEEdouble;
2566 return LongDoubleFormat::PPCDoubleDouble;
2567 case x86:
2568 case x86_64:
2569 // Android and OHOS use IEEE double on 32-bit and IEEE quad on 64-bit.
2570 if (isAndroid() || isOHOSFamily())
2571 return isX86_64() ? LongDoubleFormat::IEEEquad
2572 : LongDoubleFormat::IEEEdouble;
2573 // Windows-MSVC and UEFI use IEEE double. MinGW and Cygwin keep x87.
2574 if (isWindowsMSVCEnvironment() || isUEFI())
2575 return LongDoubleFormat::IEEEdouble;
2576 return LongDoubleFormat::X87DoubleExtended;
2577 case aarch64:
2578 case aarch64_be:
2579 case aarch64_32:
2580 // AArch64 uses IEEE quad, except on Windows and Darwin.
2581 if (isOSWindows() || isOSDarwin())
2582 return LongDoubleFormat::IEEEdouble;
2583 return LongDoubleFormat::IEEEquad;
2584 case mips64:
2585 case mips64el:
2586 return LongDoubleFormat::IEEEquad;
2587 case avr:
2588 case tce:
2589 case tcele:
2590 // AVR and 32-bit OpenASIP use IEEE single precision.
2591 return LongDoubleFormat::IEEEsingle;
2592 case tcele64:
2593 // 64-bit OpenASIP uses IEEE double, unlike its 32-bit variants.
2594 return LongDoubleFormat::IEEEdouble;
2595 default:
2596 return LongDoubleFormat::IEEEdouble;
2597 }
2598}
2599
2600// HLSL triple environment orders are relied on in the front end
2601static_assert(Triple::Vertex - Triple::Pixel == 1,
2602 "incorrect HLSL stage order");
2603static_assert(Triple::Geometry - Triple::Pixel == 2,
2604 "incorrect HLSL stage order");
2605static_assert(Triple::Hull - Triple::Pixel == 3, "incorrect HLSL stage order");
2606static_assert(Triple::Domain - Triple::Pixel == 4,
2607 "incorrect HLSL stage order");
2608static_assert(Triple::Compute - Triple::Pixel == 5,
2609 "incorrect HLSL stage order");
2610static_assert(Triple::Library - Triple::Pixel == 6,
2611 "incorrect HLSL stage order");
2612static_assert(Triple::RayGeneration - Triple::Pixel == 7,
2613 "incorrect HLSL stage order");
2614static_assert(Triple::Intersection - Triple::Pixel == 8,
2615 "incorrect HLSL stage order");
2616static_assert(Triple::AnyHit - Triple::Pixel == 9,
2617 "incorrect HLSL stage order");
2618static_assert(Triple::ClosestHit - Triple::Pixel == 10,
2619 "incorrect HLSL stage order");
2620static_assert(Triple::Miss - Triple::Pixel == 11, "incorrect HLSL stage order");
2621static_assert(Triple::Callable - Triple::Pixel == 12,
2622 "incorrect HLSL stage order");
2623static_assert(Triple::Mesh - Triple::Pixel == 13, "incorrect HLSL stage order");
2624static_assert(Triple::Amplification - Triple::Pixel == 14,
2625 "incorrect HLSL stage order");
2626