1 //===--- Triple.cpp - Target triple helper class --------------------------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
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"
18 const char *Triple::getArchTypeName(ArchType Kind) {
20 case UnknownArch: return "unknown";
22 case aarch64: return "aarch64";
23 case aarch64_be: return "aarch64_be";
24 case arm: return "arm";
25 case armeb: return "armeb";
26 case bpf: return "bpf";
27 case hexagon: return "hexagon";
28 case mips: return "mips";
29 case mipsel: return "mipsel";
30 case mips64: return "mips64";
31 case mips64el: return "mips64el";
32 case msp430: return "msp430";
33 case ppc64: return "powerpc64";
34 case ppc64le: return "powerpc64le";
35 case ppc: return "powerpc";
36 case r600: return "r600";
37 case amdgcn: return "amdgcn";
38 case sparc: return "sparc";
39 case sparcv9: return "sparcv9";
40 case systemz: return "s390x";
41 case tce: return "tce";
42 case thumb: return "thumb";
43 case thumbeb: return "thumbeb";
44 case x86: return "i386";
45 case x86_64: return "x86_64";
46 case xcore: return "xcore";
47 case nvptx: return "nvptx";
48 case nvptx64: return "nvptx64";
49 case le32: return "le32";
50 case le64: return "le64";
51 case amdil: return "amdil";
52 case amdil64: return "amdil64";
53 case hsail: return "hsail";
54 case hsail64: return "hsail64";
55 case spir: return "spir";
56 case spir64: return "spir64";
57 case kalimba: return "kalimba";
60 llvm_unreachable("Invalid ArchType!");
63 const char *Triple::getArchTypePrefix(ArchType Kind) {
69 case aarch64_be: return "aarch64";
74 case thumbeb: return "arm";
78 case ppc: return "ppc";
83 case mips64el: return "mips";
85 case hexagon: return "hexagon";
88 case r600: return "amdgpu";
90 case bpf: return "bpf";
93 case sparc: return "sparc";
95 case systemz: return "systemz";
98 case x86_64: return "x86";
100 case xcore: return "xcore";
102 case nvptx: return "nvptx";
103 case nvptx64: return "nvptx";
105 case le32: return "le32";
106 case le64: return "le64";
109 case amdil64: return "amdil";
112 case hsail64: return "hsail";
115 case spir64: return "spir";
116 case kalimba: return "kalimba";
120 const char *Triple::getVendorTypeName(VendorType Kind) {
122 case UnknownVendor: return "unknown";
124 case Apple: return "apple";
125 case PC: return "pc";
126 case SCEI: return "scei";
127 case BGP: return "bgp";
128 case BGQ: return "bgq";
129 case Freescale: return "fsl";
130 case IBM: return "ibm";
131 case ImaginationTechnologies: return "img";
132 case MipsTechnologies: return "mti";
133 case NVIDIA: return "nvidia";
134 case CSR: return "csr";
137 llvm_unreachable("Invalid VendorType!");
140 const char *Triple::getOSTypeName(OSType Kind) {
142 case UnknownOS: return "unknown";
144 case CloudABI: return "cloudabi";
145 case Darwin: return "darwin";
146 case DragonFly: return "dragonfly";
147 case FreeBSD: return "freebsd";
148 case IOS: return "ios";
149 case KFreeBSD: return "kfreebsd";
150 case Linux: return "linux";
151 case Lv2: return "lv2";
152 case MacOSX: return "macosx";
153 case NetBSD: return "netbsd";
154 case OpenBSD: return "openbsd";
155 case Solaris: return "solaris";
156 case Win32: return "windows";
157 case Haiku: return "haiku";
158 case Minix: return "minix";
159 case RTEMS: return "rtems";
160 case NaCl: return "nacl";
161 case CNK: return "cnk";
162 case Bitrig: return "bitrig";
163 case AIX: return "aix";
164 case CUDA: return "cuda";
165 case NVCL: return "nvcl";
166 case AMDHSA: return "amdhsa";
167 case PS4: return "ps4";
170 llvm_unreachable("Invalid OSType");
173 const char *Triple::getEnvironmentTypeName(EnvironmentType Kind) {
175 case UnknownEnvironment: return "unknown";
176 case GNU: return "gnu";
177 case GNUEABIHF: return "gnueabihf";
178 case GNUEABI: return "gnueabi";
179 case GNUX32: return "gnux32";
180 case CODE16: return "code16";
181 case EABI: return "eabi";
182 case EABIHF: return "eabihf";
183 case Android: return "android";
184 case MSVC: return "msvc";
185 case Itanium: return "itanium";
186 case Cygnus: return "cygnus";
189 llvm_unreachable("Invalid EnvironmentType!");
192 Triple::ArchType Triple::getArchTypeForLLVMName(StringRef Name) {
193 return StringSwitch<Triple::ArchType>(Name)
194 .Case("aarch64", aarch64)
195 .Case("aarch64_be", aarch64_be)
196 .Case("arm64", aarch64) // "arm64" is an alias for "aarch64"
198 .Case("armeb", armeb)
201 .Case("mipsel", mipsel)
202 .Case("mips64", mips64)
203 .Case("mips64el", mips64el)
204 .Case("msp430", msp430)
205 .Case("ppc64", ppc64)
208 .Case("ppc64le", ppc64le)
210 .Case("amdgcn", amdgcn)
211 .Case("hexagon", hexagon)
212 .Case("sparc", sparc)
213 .Case("sparcv9", sparcv9)
214 .Case("systemz", systemz)
216 .Case("thumb", thumb)
217 .Case("thumbeb", thumbeb)
219 .Case("x86-64", x86_64)
220 .Case("xcore", xcore)
221 .Case("nvptx", nvptx)
222 .Case("nvptx64", nvptx64)
225 .Case("amdil", amdil)
226 .Case("amdil64", amdil64)
227 .Case("hsail", hsail)
228 .Case("hsail64", hsail64)
230 .Case("spir64", spir64)
231 .Case("kalimba", kalimba)
232 .Default(UnknownArch);
235 static Triple::ArchType parseARMArch(StringRef ArchName) {
236 size_t offset = StringRef::npos;
237 Triple::ArchType arch = Triple::UnknownArch;
238 bool isThumb = ArchName.startswith("thumb");
240 if (ArchName.equals("arm"))
242 if (ArchName.equals("armeb"))
243 return Triple::armeb;
244 if (ArchName.equals("thumb"))
245 return Triple::thumb;
246 if (ArchName.equals("thumbeb"))
247 return Triple::thumbeb;
248 if (ArchName.equals("arm64") || ArchName.equals("aarch64"))
249 return Triple::aarch64;
250 if (ArchName.equals("aarch64_be"))
251 return Triple::aarch64_be;
253 if (ArchName.startswith("armv")) {
255 if (ArchName.endswith("eb")) {
256 arch = Triple::armeb;
257 ArchName = ArchName.substr(0, ArchName.size() - 2);
260 } else if (ArchName.startswith("armebv")) {
262 arch = Triple::armeb;
263 } else if (ArchName.startswith("thumbv")) {
265 if (ArchName.endswith("eb")) {
266 arch = Triple::thumbeb;
267 ArchName = ArchName.substr(0, ArchName.size() - 2);
269 arch = Triple::thumb;
270 } else if (ArchName.startswith("thumbebv")) {
272 arch = Triple::thumbeb;
274 return StringSwitch<Triple::ArchType>(ArchName.substr(offset))
275 .Cases("v2", "v2a", isThumb ? Triple::UnknownArch : arch)
276 .Cases("v3", "v3m", isThumb ? Triple::UnknownArch : arch)
277 .Cases("v4", "v4t", arch)
278 .Cases("v5", "v5e", "v5t", "v5te", "v5tej", arch)
279 .Cases("v6", "v6j", "v6k", "v6m", "v6sm", arch)
280 .Cases("v6t2", "v6z", "v6zk", arch)
281 .Cases("v7", "v7a", "v7em", "v7l", arch)
282 .Cases("v7m", "v7r", "v7s", arch)
283 .Cases("v8", "v8a", arch)
284 .Default(Triple::UnknownArch);
287 static Triple::ArchType parseArch(StringRef ArchName) {
288 Triple::ArchType ARMArch(parseARMArch(ArchName));
290 return StringSwitch<Triple::ArchType>(ArchName)
291 .Cases("i386", "i486", "i586", "i686", Triple::x86)
292 // FIXME: Do we need to support these?
293 .Cases("i786", "i886", "i986", Triple::x86)
294 .Cases("amd64", "x86_64", "x86_64h", Triple::x86_64)
295 .Case("powerpc", Triple::ppc)
296 .Cases("powerpc64", "ppu", Triple::ppc64)
297 .Case("powerpc64le", Triple::ppc64le)
298 .Case("xscale", Triple::arm)
299 .Case("xscaleeb", Triple::armeb)
300 .StartsWith("arm", ARMArch)
301 .StartsWith("thumb", ARMArch)
302 .StartsWith("aarch64", ARMArch)
303 .Case("msp430", Triple::msp430)
304 .Cases("mips", "mipseb", "mipsallegrex", Triple::mips)
305 .Cases("mipsel", "mipsallegrexel", Triple::mipsel)
306 .Cases("mips64", "mips64eb", Triple::mips64)
307 .Case("mips64el", Triple::mips64el)
308 .Case("r600", Triple::r600)
309 .Case("amdgcn", Triple::amdgcn)
310 .Case("bpf", Triple::bpf)
311 .Case("hexagon", Triple::hexagon)
312 .Case("s390x", Triple::systemz)
313 .Case("sparc", Triple::sparc)
314 .Cases("sparcv9", "sparc64", Triple::sparcv9)
315 .Case("tce", Triple::tce)
316 .Case("xcore", Triple::xcore)
317 .Case("nvptx", Triple::nvptx)
318 .Case("nvptx64", Triple::nvptx64)
319 .Case("le32", Triple::le32)
320 .Case("le64", Triple::le64)
321 .Case("amdil", Triple::amdil)
322 .Case("amdil64", Triple::amdil64)
323 .Case("hsail", Triple::hsail)
324 .Case("hsail64", Triple::hsail64)
325 .Case("spir", Triple::spir)
326 .Case("spir64", Triple::spir64)
327 .StartsWith("kalimba", Triple::kalimba)
328 .Default(Triple::UnknownArch);
331 static Triple::VendorType parseVendor(StringRef VendorName) {
332 return StringSwitch<Triple::VendorType>(VendorName)
333 .Case("apple", Triple::Apple)
334 .Case("pc", Triple::PC)
335 .Case("scei", Triple::SCEI)
336 .Case("bgp", Triple::BGP)
337 .Case("bgq", Triple::BGQ)
338 .Case("fsl", Triple::Freescale)
339 .Case("ibm", Triple::IBM)
340 .Case("img", Triple::ImaginationTechnologies)
341 .Case("mti", Triple::MipsTechnologies)
342 .Case("nvidia", Triple::NVIDIA)
343 .Case("csr", Triple::CSR)
344 .Default(Triple::UnknownVendor);
347 static Triple::OSType parseOS(StringRef OSName) {
348 return StringSwitch<Triple::OSType>(OSName)
349 .StartsWith("cloudabi", Triple::CloudABI)
350 .StartsWith("darwin", Triple::Darwin)
351 .StartsWith("dragonfly", Triple::DragonFly)
352 .StartsWith("freebsd", Triple::FreeBSD)
353 .StartsWith("ios", Triple::IOS)
354 .StartsWith("kfreebsd", Triple::KFreeBSD)
355 .StartsWith("linux", Triple::Linux)
356 .StartsWith("lv2", Triple::Lv2)
357 .StartsWith("macosx", Triple::MacOSX)
358 .StartsWith("netbsd", Triple::NetBSD)
359 .StartsWith("openbsd", Triple::OpenBSD)
360 .StartsWith("solaris", Triple::Solaris)
361 .StartsWith("win32", Triple::Win32)
362 .StartsWith("windows", Triple::Win32)
363 .StartsWith("haiku", Triple::Haiku)
364 .StartsWith("minix", Triple::Minix)
365 .StartsWith("rtems", Triple::RTEMS)
366 .StartsWith("nacl", Triple::NaCl)
367 .StartsWith("cnk", Triple::CNK)
368 .StartsWith("bitrig", Triple::Bitrig)
369 .StartsWith("aix", Triple::AIX)
370 .StartsWith("cuda", Triple::CUDA)
371 .StartsWith("nvcl", Triple::NVCL)
372 .StartsWith("amdhsa", Triple::AMDHSA)
373 .StartsWith("ps4", Triple::PS4)
374 .Default(Triple::UnknownOS);
377 static Triple::EnvironmentType parseEnvironment(StringRef EnvironmentName) {
378 return StringSwitch<Triple::EnvironmentType>(EnvironmentName)
379 .StartsWith("eabihf", Triple::EABIHF)
380 .StartsWith("eabi", Triple::EABI)
381 .StartsWith("gnueabihf", Triple::GNUEABIHF)
382 .StartsWith("gnueabi", Triple::GNUEABI)
383 .StartsWith("gnux32", Triple::GNUX32)
384 .StartsWith("code16", Triple::CODE16)
385 .StartsWith("gnu", Triple::GNU)
386 .StartsWith("android", Triple::Android)
387 .StartsWith("msvc", Triple::MSVC)
388 .StartsWith("itanium", Triple::Itanium)
389 .StartsWith("cygnus", Triple::Cygnus)
390 .Default(Triple::UnknownEnvironment);
393 static Triple::ObjectFormatType parseFormat(StringRef EnvironmentName) {
394 return StringSwitch<Triple::ObjectFormatType>(EnvironmentName)
395 .EndsWith("coff", Triple::COFF)
396 .EndsWith("elf", Triple::ELF)
397 .EndsWith("macho", Triple::MachO)
398 .Default(Triple::UnknownObjectFormat);
401 static Triple::SubArchType parseSubArch(StringRef SubArchName) {
402 if (SubArchName.endswith("eb"))
403 SubArchName = SubArchName.substr(0, SubArchName.size() - 2);
405 return StringSwitch<Triple::SubArchType>(SubArchName)
406 .EndsWith("v8", Triple::ARMSubArch_v8)
407 .EndsWith("v8a", Triple::ARMSubArch_v8)
408 .EndsWith("v7", Triple::ARMSubArch_v7)
409 .EndsWith("v7a", Triple::ARMSubArch_v7)
410 .EndsWith("v7em", Triple::ARMSubArch_v7em)
411 .EndsWith("v7l", Triple::ARMSubArch_v7)
412 .EndsWith("v7m", Triple::ARMSubArch_v7m)
413 .EndsWith("v7r", Triple::ARMSubArch_v7)
414 .EndsWith("v7s", Triple::ARMSubArch_v7s)
415 .EndsWith("v6", Triple::ARMSubArch_v6)
416 .EndsWith("v6m", Triple::ARMSubArch_v6m)
417 .EndsWith("v6sm", Triple::ARMSubArch_v6m)
418 .EndsWith("v6k", Triple::ARMSubArch_v6k)
419 .EndsWith("v6t2", Triple::ARMSubArch_v6t2)
420 .EndsWith("v5", Triple::ARMSubArch_v5)
421 .EndsWith("v5e", Triple::ARMSubArch_v5)
422 .EndsWith("v5t", Triple::ARMSubArch_v5)
423 .EndsWith("v5te", Triple::ARMSubArch_v5te)
424 .EndsWith("v4t", Triple::ARMSubArch_v4t)
425 .EndsWith("kalimba3", Triple::KalimbaSubArch_v3)
426 .EndsWith("kalimba4", Triple::KalimbaSubArch_v4)
427 .EndsWith("kalimba5", Triple::KalimbaSubArch_v5)
428 .Default(Triple::NoSubArch);
431 static const char *getObjectFormatTypeName(Triple::ObjectFormatType Kind) {
433 case Triple::UnknownObjectFormat: return "";
434 case Triple::COFF: return "coff";
435 case Triple::ELF: return "elf";
436 case Triple::MachO: return "macho";
438 llvm_unreachable("unknown object format type");
441 static Triple::ObjectFormatType getDefaultFormat(const Triple &T) {
442 switch (T.getArch()) {
445 case Triple::hexagon:
449 case Triple::mips64el:
453 case Triple::sparcv9:
454 case Triple::systemz:
456 case Triple::ppc64le:
462 return Triple::MachO;
467 return Triple::MachO;
468 else if (T.isOSWindows())
473 /// \brief Construct a triple from the string representation provided.
475 /// This stores the string representation and parses the various pieces into
477 Triple::Triple(const Twine &Str)
479 Arch(parseArch(getArchName())),
480 SubArch(parseSubArch(getArchName())),
481 Vendor(parseVendor(getVendorName())),
482 OS(parseOS(getOSName())),
483 Environment(parseEnvironment(getEnvironmentName())),
484 ObjectFormat(parseFormat(getEnvironmentName())) {
485 if (ObjectFormat == Triple::UnknownObjectFormat)
486 ObjectFormat = getDefaultFormat(*this);
489 /// \brief Construct a triple from string representations of the architecture,
492 /// This joins each argument into a canonical string representation and parses
493 /// them into enum members. It leaves the environment unknown and omits it from
494 /// the string representation.
495 Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr)
496 : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr).str()),
497 Arch(parseArch(ArchStr.str())),
498 SubArch(parseSubArch(ArchStr.str())),
499 Vendor(parseVendor(VendorStr.str())),
500 OS(parseOS(OSStr.str())),
501 Environment(), ObjectFormat(Triple::UnknownObjectFormat) {
502 ObjectFormat = getDefaultFormat(*this);
505 /// \brief Construct a triple from string representations of the architecture,
506 /// vendor, OS, and environment.
508 /// This joins each argument into a canonical string representation and parses
509 /// them into enum members.
510 Triple::Triple(const Twine &ArchStr, const Twine &VendorStr, const Twine &OSStr,
511 const Twine &EnvironmentStr)
512 : Data((ArchStr + Twine('-') + VendorStr + Twine('-') + OSStr + Twine('-') +
513 EnvironmentStr).str()),
514 Arch(parseArch(ArchStr.str())),
515 SubArch(parseSubArch(ArchStr.str())),
516 Vendor(parseVendor(VendorStr.str())),
517 OS(parseOS(OSStr.str())),
518 Environment(parseEnvironment(EnvironmentStr.str())),
519 ObjectFormat(parseFormat(EnvironmentStr.str())) {
520 if (ObjectFormat == Triple::UnknownObjectFormat)
521 ObjectFormat = getDefaultFormat(*this);
524 std::string Triple::normalize(StringRef Str) {
525 bool IsMinGW32 = false;
526 bool IsCygwin = false;
528 // Parse into components.
529 SmallVector<StringRef, 4> Components;
530 Str.split(Components, "-");
532 // If the first component corresponds to a known architecture, preferentially
533 // use it for the architecture. If the second component corresponds to a
534 // known vendor, preferentially use it for the vendor, etc. This avoids silly
535 // component movement when a component parses as (eg) both a valid arch and a
537 ArchType Arch = UnknownArch;
538 if (Components.size() > 0)
539 Arch = parseArch(Components[0]);
540 VendorType Vendor = UnknownVendor;
541 if (Components.size() > 1)
542 Vendor = parseVendor(Components[1]);
543 OSType OS = UnknownOS;
544 if (Components.size() > 2) {
545 OS = parseOS(Components[2]);
546 IsCygwin = Components[2].startswith("cygwin");
547 IsMinGW32 = Components[2].startswith("mingw");
549 EnvironmentType Environment = UnknownEnvironment;
550 if (Components.size() > 3)
551 Environment = parseEnvironment(Components[3]);
552 ObjectFormatType ObjectFormat = UnknownObjectFormat;
553 if (Components.size() > 4)
554 ObjectFormat = parseFormat(Components[4]);
556 // Note which components are already in their final position. These will not
559 Found[0] = Arch != UnknownArch;
560 Found[1] = Vendor != UnknownVendor;
561 Found[2] = OS != UnknownOS;
562 Found[3] = Environment != UnknownEnvironment;
564 // If they are not there already, permute the components into their canonical
565 // positions by seeing if they parse as a valid architecture, and if so moving
566 // the component to the architecture position etc.
567 for (unsigned Pos = 0; Pos != array_lengthof(Found); ++Pos) {
569 continue; // Already in the canonical position.
571 for (unsigned Idx = 0; Idx != Components.size(); ++Idx) {
572 // Do not reparse any components that already matched.
573 if (Idx < array_lengthof(Found) && Found[Idx])
576 // Does this component parse as valid for the target position?
578 StringRef Comp = Components[Idx];
580 default: llvm_unreachable("unexpected component type!");
582 Arch = parseArch(Comp);
583 Valid = Arch != UnknownArch;
586 Vendor = parseVendor(Comp);
587 Valid = Vendor != UnknownVendor;
591 IsCygwin = Comp.startswith("cygwin");
592 IsMinGW32 = Comp.startswith("mingw");
593 Valid = OS != UnknownOS || IsCygwin || IsMinGW32;
596 Environment = parseEnvironment(Comp);
597 Valid = Environment != UnknownEnvironment;
599 ObjectFormat = parseFormat(Comp);
600 Valid = ObjectFormat != UnknownObjectFormat;
605 continue; // Nope, try the next component.
607 // Move the component to the target position, pushing any non-fixed
608 // components that are in the way to the right. This tends to give
609 // good results in the common cases of a forgotten vendor component
610 // or a wrongly positioned environment.
612 // Insert left, pushing the existing components to the right. For
613 // example, a-b-i386 -> i386-a-b when moving i386 to the front.
614 StringRef CurrentComponent(""); // The empty component.
615 // Replace the component we are moving with an empty component.
616 std::swap(CurrentComponent, Components[Idx]);
617 // Insert the component being moved at Pos, displacing any existing
618 // components to the right.
619 for (unsigned i = Pos; !CurrentComponent.empty(); ++i) {
620 // Skip over any fixed components.
621 while (i < array_lengthof(Found) && Found[i])
623 // Place the component at the new position, getting the component
624 // that was at this position - it will be moved right.
625 std::swap(CurrentComponent, Components[i]);
627 } else if (Pos > Idx) {
628 // Push right by inserting empty components until the component at Idx
629 // reaches the target position Pos. For example, pc-a -> -pc-a when
630 // moving pc to the second position.
632 // Insert one empty component at Idx.
633 StringRef CurrentComponent(""); // The empty component.
634 for (unsigned i = Idx; i < Components.size();) {
635 // Place the component at the new position, getting the component
636 // that was at this position - it will be moved right.
637 std::swap(CurrentComponent, Components[i]);
638 // If it was placed on top of an empty component then we are done.
639 if (CurrentComponent.empty())
641 // Advance to the next component, skipping any fixed components.
642 while (++i < array_lengthof(Found) && Found[i])
645 // The last component was pushed off the end - append it.
646 if (!CurrentComponent.empty())
647 Components.push_back(CurrentComponent);
649 // Advance Idx to the component's new position.
650 while (++Idx < array_lengthof(Found) && Found[Idx])
652 } while (Idx < Pos); // Add more until the final position is reached.
654 assert(Pos < Components.size() && Components[Pos] == Comp &&
655 "Component moved wrong!");
661 // Special case logic goes here. At this point Arch, Vendor and OS have the
662 // correct values for the computed components.
664 if (OS == Triple::Win32) {
665 Components.resize(4);
666 Components[2] = "windows";
667 if (Environment == UnknownEnvironment) {
668 if (ObjectFormat == UnknownObjectFormat || ObjectFormat == Triple::COFF)
669 Components[3] = "msvc";
671 Components[3] = getObjectFormatTypeName(ObjectFormat);
673 } else if (IsMinGW32) {
674 Components.resize(4);
675 Components[2] = "windows";
676 Components[3] = "gnu";
677 } else if (IsCygwin) {
678 Components.resize(4);
679 Components[2] = "windows";
680 Components[3] = "cygnus";
682 if (IsMinGW32 || IsCygwin ||
683 (OS == Triple::Win32 && Environment != UnknownEnvironment)) {
684 if (ObjectFormat != UnknownObjectFormat && ObjectFormat != Triple::COFF) {
685 Components.resize(5);
686 Components[4] = getObjectFormatTypeName(ObjectFormat);
690 // Stick the corrected components back together to form the normalized string.
691 std::string Normalized;
692 for (unsigned i = 0, e = Components.size(); i != e; ++i) {
693 if (i) Normalized += '-';
694 Normalized += Components[i];
699 StringRef Triple::getArchName() const {
700 return StringRef(Data).split('-').first; // Isolate first component
703 StringRef Triple::getVendorName() const {
704 StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
705 return Tmp.split('-').first; // Isolate second component
708 StringRef Triple::getOSName() const {
709 StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
710 Tmp = Tmp.split('-').second; // Strip second component
711 return Tmp.split('-').first; // Isolate third component
714 StringRef Triple::getEnvironmentName() const {
715 StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
716 Tmp = Tmp.split('-').second; // Strip second component
717 return Tmp.split('-').second; // Strip third component
720 StringRef Triple::getOSAndEnvironmentName() const {
721 StringRef Tmp = StringRef(Data).split('-').second; // Strip first component
722 return Tmp.split('-').second; // Strip second component
725 static unsigned EatNumber(StringRef &Str) {
726 assert(!Str.empty() && Str[0] >= '0' && Str[0] <= '9' && "Not a number");
730 // Consume the leading digit.
731 Result = Result*10 + (Str[0] - '0');
735 } while (!Str.empty() && Str[0] >= '0' && Str[0] <= '9');
740 void Triple::getOSVersion(unsigned &Major, unsigned &Minor,
741 unsigned &Micro) const {
742 StringRef OSName = getOSName();
744 // For Android, we care about the Android version rather than the Linux
746 if (getEnvironment() == Android) {
747 OSName = getEnvironmentName().substr(strlen("android"));
748 if (OSName.startswith("eabi"))
749 OSName = OSName.substr(strlen("eabi"));
752 // Assume that the OS portion of the triple starts with the canonical name.
753 StringRef OSTypeName = getOSTypeName(getOS());
754 if (OSName.startswith(OSTypeName))
755 OSName = OSName.substr(OSTypeName.size());
757 // Any unset version defaults to 0.
758 Major = Minor = Micro = 0;
760 // Parse up to three components.
761 unsigned *Components[3] = { &Major, &Minor, &Micro };
762 for (unsigned i = 0; i != 3; ++i) {
763 if (OSName.empty() || OSName[0] < '0' || OSName[0] > '9')
766 // Consume the leading number.
767 *Components[i] = EatNumber(OSName);
769 // Consume the separator, if present.
770 if (OSName.startswith("."))
771 OSName = OSName.substr(1);
775 bool Triple::getMacOSXVersion(unsigned &Major, unsigned &Minor,
776 unsigned &Micro) const {
777 getOSVersion(Major, Minor, Micro);
780 default: llvm_unreachable("unexpected OS for Darwin triple");
782 // Default to darwin8, i.e., MacOSX 10.4.
785 // Darwin version numbers are skewed from OS X versions.
802 // Ignore the version from the triple. This is only handled because the
803 // the clang driver combines OS X and IOS support into a common Darwin
804 // toolchain that wants to know the OS X version number even when targeting
814 void Triple::getiOSVersion(unsigned &Major, unsigned &Minor,
815 unsigned &Micro) const {
817 default: llvm_unreachable("unexpected OS for Darwin triple");
820 // Ignore the version from the triple. This is only handled because the
821 // the clang driver combines OS X and IOS support into a common Darwin
822 // toolchain that wants to know the iOS version number even when targeting
829 getOSVersion(Major, Minor, Micro);
830 // Default to 5.0 (or 7.0 for arm64).
832 Major = (getArch() == aarch64) ? 7 : 5;
837 void Triple::setTriple(const Twine &Str) {
841 void Triple::setArch(ArchType Kind) {
842 setArchName(getArchTypeName(Kind));
845 void Triple::setVendor(VendorType Kind) {
846 setVendorName(getVendorTypeName(Kind));
849 void Triple::setOS(OSType Kind) {
850 setOSName(getOSTypeName(Kind));
853 void Triple::setEnvironment(EnvironmentType Kind) {
854 if (ObjectFormat == getDefaultFormat(*this))
855 return setEnvironmentName(getEnvironmentTypeName(Kind));
857 setEnvironmentName((getEnvironmentTypeName(Kind) + Twine("-") +
858 getObjectFormatTypeName(ObjectFormat)).str());
861 void Triple::setObjectFormat(ObjectFormatType Kind) {
862 if (Environment == UnknownEnvironment)
863 return setEnvironmentName(getObjectFormatTypeName(Kind));
865 setEnvironmentName((getEnvironmentTypeName(Environment) + Twine("-") +
866 getObjectFormatTypeName(Kind)).str());
869 void Triple::setArchName(StringRef Str) {
870 // Work around a miscompilation bug for Twines in gcc 4.0.3.
871 SmallString<64> Triple;
874 Triple += getVendorName();
876 Triple += getOSAndEnvironmentName();
880 void Triple::setVendorName(StringRef Str) {
881 setTriple(getArchName() + "-" + Str + "-" + getOSAndEnvironmentName());
884 void Triple::setOSName(StringRef Str) {
885 if (hasEnvironment())
886 setTriple(getArchName() + "-" + getVendorName() + "-" + Str +
887 "-" + getEnvironmentName());
889 setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
892 void Triple::setEnvironmentName(StringRef Str) {
893 setTriple(getArchName() + "-" + getVendorName() + "-" + getOSName() +
897 void Triple::setOSAndEnvironmentName(StringRef Str) {
898 setTriple(getArchName() + "-" + getVendorName() + "-" + Str);
901 static unsigned getArchPointerBitWidth(llvm::Triple::ArchType Arch) {
903 case llvm::Triple::UnknownArch:
906 case llvm::Triple::msp430:
909 case llvm::Triple::arm:
910 case llvm::Triple::armeb:
911 case llvm::Triple::hexagon:
912 case llvm::Triple::le32:
913 case llvm::Triple::mips:
914 case llvm::Triple::mipsel:
915 case llvm::Triple::nvptx:
916 case llvm::Triple::ppc:
917 case llvm::Triple::r600:
918 case llvm::Triple::sparc:
919 case llvm::Triple::tce:
920 case llvm::Triple::thumb:
921 case llvm::Triple::thumbeb:
922 case llvm::Triple::x86:
923 case llvm::Triple::xcore:
924 case llvm::Triple::amdil:
925 case llvm::Triple::hsail:
926 case llvm::Triple::spir:
927 case llvm::Triple::kalimba:
930 case llvm::Triple::aarch64:
931 case llvm::Triple::aarch64_be:
932 case llvm::Triple::amdgcn:
933 case llvm::Triple::bpf:
934 case llvm::Triple::le64:
935 case llvm::Triple::mips64:
936 case llvm::Triple::mips64el:
937 case llvm::Triple::nvptx64:
938 case llvm::Triple::ppc64:
939 case llvm::Triple::ppc64le:
940 case llvm::Triple::sparcv9:
941 case llvm::Triple::systemz:
942 case llvm::Triple::x86_64:
943 case llvm::Triple::amdil64:
944 case llvm::Triple::hsail64:
945 case llvm::Triple::spir64:
948 llvm_unreachable("Invalid architecture value");
951 bool Triple::isArch64Bit() const {
952 return getArchPointerBitWidth(getArch()) == 64;
955 bool Triple::isArch32Bit() const {
956 return getArchPointerBitWidth(getArch()) == 32;
959 bool Triple::isArch16Bit() const {
960 return getArchPointerBitWidth(getArch()) == 16;
963 Triple Triple::get32BitArchVariant() const {
966 case Triple::UnknownArch:
967 case Triple::aarch64:
968 case Triple::aarch64_be:
972 case Triple::systemz:
973 case Triple::ppc64le:
974 T.setArch(UnknownArch);
982 case Triple::hexagon:
983 case Triple::kalimba:
993 case Triple::thumbeb:
999 case Triple::le64: T.setArch(Triple::le32); break;
1000 case Triple::mips64: T.setArch(Triple::mips); break;
1001 case Triple::mips64el: T.setArch(Triple::mipsel); break;
1002 case Triple::nvptx64: T.setArch(Triple::nvptx); break;
1003 case Triple::ppc64: T.setArch(Triple::ppc); break;
1004 case Triple::sparcv9: T.setArch(Triple::sparc); break;
1005 case Triple::x86_64: T.setArch(Triple::x86); break;
1006 case Triple::amdil64: T.setArch(Triple::amdil); break;
1007 case Triple::hsail64: T.setArch(Triple::hsail); break;
1008 case Triple::spir64: T.setArch(Triple::spir); break;
1013 Triple Triple::get64BitArchVariant() const {
1015 switch (getArch()) {
1016 case Triple::UnknownArch:
1019 case Triple::hexagon:
1020 case Triple::kalimba:
1021 case Triple::msp430:
1025 case Triple::thumbeb:
1027 T.setArch(UnknownArch);
1030 case Triple::aarch64:
1031 case Triple::aarch64_be:
1034 case Triple::amdil64:
1035 case Triple::amdgcn:
1036 case Triple::hsail64:
1037 case Triple::spir64:
1038 case Triple::mips64:
1039 case Triple::mips64el:
1040 case Triple::nvptx64:
1042 case Triple::ppc64le:
1043 case Triple::sparcv9:
1044 case Triple::systemz:
1045 case Triple::x86_64:
1049 case Triple::le32: T.setArch(Triple::le64); break;
1050 case Triple::mips: T.setArch(Triple::mips64); break;
1051 case Triple::mipsel: T.setArch(Triple::mips64el); break;
1052 case Triple::nvptx: T.setArch(Triple::nvptx64); break;
1053 case Triple::ppc: T.setArch(Triple::ppc64); break;
1054 case Triple::sparc: T.setArch(Triple::sparcv9); break;
1055 case Triple::x86: T.setArch(Triple::x86_64); break;
1056 case Triple::amdil: T.setArch(Triple::amdil64); break;
1057 case Triple::hsail: T.setArch(Triple::hsail64); break;
1058 case Triple::spir: T.setArch(Triple::spir64); break;
1063 // FIXME: tblgen this.
1064 const char *Triple::getARMCPUForArch(StringRef MArch) const {
1066 MArch = getArchName();
1069 case llvm::Triple::FreeBSD:
1070 case llvm::Triple::NetBSD:
1071 if (MArch == "armv6")
1072 return "arm1176jzf-s";
1074 case llvm::Triple::Win32:
1075 // FIXME: this is invalid for WindowsCE
1081 const char *result = nullptr;
1082 size_t offset = StringRef::npos;
1083 if (MArch.startswith("arm"))
1085 if (MArch.startswith("thumb"))
1087 if (offset != StringRef::npos && MArch.substr(offset, 2) == "eb")
1089 if (MArch.endswith("eb"))
1090 MArch = MArch.substr(0, MArch.size() - 2);
1091 if (offset != StringRef::npos)
1092 result = llvm::StringSwitch<const char *>(MArch.substr(offset))
1093 .Cases("v2", "v2a", "arm2")
1095 .Case("v3m", "arm7m")
1096 .Case("v4", "strongarm")
1097 .Case("v4t", "arm7tdmi")
1098 .Cases("v5", "v5t", "arm10tdmi")
1099 .Cases("v5e", "v5te", "arm1022e")
1100 .Case("v5tej", "arm926ej-s")
1101 .Case("v6", "arm1136jf-s")
1102 .Case("v6j", "arm1136j-s")
1103 .Cases("v6k", "v6z", "v6zk", "arm1176jzf-s")
1104 .Case("v6t2", "arm1156t2-s")
1105 .Cases("v6m", "v6-m", "v6sm", "v6s-m", "cortex-m0")
1106 .Cases("v7", "v7a", "v7-a", "v7l", "v7-l", "cortex-a8")
1107 .Cases("v7s", "v7-s", "swift")
1108 .Cases("v7r", "v7-r", "cortex-r4")
1109 .Cases("v7m", "v7-m", "cortex-m3")
1110 .Cases("v7em", "v7e-m", "cortex-m4")
1111 .Cases("v8", "v8a", "v8-a", "cortex-a53")
1114 result = llvm::StringSwitch<const char *>(MArch)
1115 .Case("ep9312", "ep9312")
1116 .Case("iwmmxt", "iwmmxt")
1117 .Case("xscale", "xscale")
1123 // If all else failed, return the most base CPU with thumb interworking
1124 // supported by LLVM.
1125 // FIXME: Should warn once that we're falling back.
1127 case llvm::Triple::NetBSD:
1128 switch (getEnvironment()) {
1129 case llvm::Triple::GNUEABIHF:
1130 case llvm::Triple::GNUEABI:
1131 case llvm::Triple::EABIHF:
1132 case llvm::Triple::EABI:
1133 return "arm926ej-s";
1138 switch (getEnvironment()) {
1139 case llvm::Triple::EABIHF:
1140 case llvm::Triple::GNUEABIHF:
1141 return "arm1176jzf-s";