Targets.cpp revision 09e95f0f2829673cfb8a02d4533f004a5cb6d6c0
1//===--- Targets.cpp - Implement -arch option and targets -----------------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file implements construction of a TargetInfo object from a 11// target triple. 12// 13//===----------------------------------------------------------------------===// 14 15#include "clang/Basic/Builtins.h" 16#include "clang/Basic/TargetBuiltins.h" 17#include "clang/Basic/TargetInfo.h" 18#include "clang/Basic/LangOptions.h" 19#include "llvm/ADT/APFloat.h" 20#include "llvm/ADT/SmallString.h" 21#include "llvm/ADT/StringRef.h" 22#include "llvm/ADT/STLExtras.h" 23#include "llvm/ADT/Triple.h" 24#include "llvm/MC/MCSectionMachO.h" 25using namespace clang; 26 27//===----------------------------------------------------------------------===// 28// Common code shared among targets. 29//===----------------------------------------------------------------------===// 30 31static void Define(std::vector<char> &Buf, const llvm::StringRef &Macro, 32 const llvm::StringRef &Val = "1") { 33 const char *Def = "#define "; 34 Buf.insert(Buf.end(), Def, Def+strlen(Def)); 35 Buf.insert(Buf.end(), Macro.begin(), Macro.end()); 36 Buf.push_back(' '); 37 Buf.insert(Buf.end(), Val.begin(), Val.end()); 38 Buf.push_back('\n'); 39} 40 41/// DefineStd - Define a macro name and standard variants. For example if 42/// MacroName is "unix", then this will define "__unix", "__unix__", and "unix" 43/// when in GNU mode. 44static void DefineStd(std::vector<char> &Buf, const char *MacroName, 45 const LangOptions &Opts) { 46 assert(MacroName[0] != '_' && "Identifier should be in the user's namespace"); 47 48 // If in GNU mode (e.g. -std=gnu99 but not -std=c99) define the raw identifier 49 // in the user's namespace. 50 if (Opts.GNUMode) 51 Define(Buf, MacroName); 52 53 // Define __unix. 54 llvm::SmallString<20> TmpStr; 55 TmpStr = "__"; 56 TmpStr += MacroName; 57 Define(Buf, TmpStr.str()); 58 59 // Define __unix__. 60 TmpStr += "__"; 61 Define(Buf, TmpStr.str()); 62} 63 64//===----------------------------------------------------------------------===// 65// Defines specific to certain operating systems. 66//===----------------------------------------------------------------------===// 67 68namespace { 69template<typename TgtInfo> 70class OSTargetInfo : public TgtInfo { 71protected: 72 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 73 std::vector<char> &Defines) const=0; 74public: 75 OSTargetInfo(const std::string& triple) : TgtInfo(triple) {} 76 virtual void getTargetDefines(const LangOptions &Opts, 77 std::vector<char> &Defines) const { 78 TgtInfo::getTargetDefines(Opts, Defines); 79 getOSDefines(Opts, TgtInfo::getTriple(), Defines); 80 } 81 82}; 83} // end anonymous namespace 84 85 86static void getDarwinDefines(std::vector<char> &Defs, const LangOptions &Opts) { 87 Define(Defs, "__APPLE_CC__", "5621"); 88 Define(Defs, "__APPLE__"); 89 Define(Defs, "__MACH__"); 90 Define(Defs, "OBJC_NEW_PROPERTIES"); 91 92 // __weak is always defined, for use in blocks and with objc pointers. 93 Define(Defs, "__weak", "__attribute__((objc_gc(weak)))"); 94 95 // Darwin defines __strong even in C mode (just to nothing). 96 if (!Opts.ObjC1 || Opts.getGCMode() == LangOptions::NonGC) 97 Define(Defs, "__strong", ""); 98 else 99 Define(Defs, "__strong", "__attribute__((objc_gc(strong)))"); 100 101 if (Opts.Static) 102 Define(Defs, "__STATIC__"); 103 else 104 Define(Defs, "__DYNAMIC__"); 105 106 if (Opts.POSIXThreads) 107 Define(Defs, "_REENTRANT", "1"); 108} 109 110static void getDarwinOSXDefines(std::vector<char> &Defs, 111 const llvm::Triple &Triple) { 112 if (Triple.getOS() != llvm::Triple::Darwin) 113 return; 114 115 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5. 116 unsigned Maj, Min, Rev; 117 Triple.getDarwinNumber(Maj, Min, Rev); 118 119 char MacOSXStr[] = "1000"; 120 if (Maj >= 4 && Maj <= 13) { // 10.0-10.9 121 // darwin7 -> 1030, darwin8 -> 1040, darwin9 -> 1050, etc. 122 MacOSXStr[2] = '0' + Maj-4; 123 } 124 125 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049" 126 // Cap 10.4.11 -> darwin8.11 -> "1049" 127 MacOSXStr[3] = std::min(Min, 9U)+'0'; 128 Define(Defs, "__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", MacOSXStr); 129} 130 131static void getDarwinIPhoneOSDefines(std::vector<char> &Defs, 132 const llvm::Triple &Triple) { 133 if (Triple.getOS() != llvm::Triple::Darwin) 134 return; 135 136 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5. 137 unsigned Maj, Min, Rev; 138 Triple.getDarwinNumber(Maj, Min, Rev); 139 140 // When targetting iPhone OS, interpret the minor version and 141 // revision as the iPhone OS version 142 char iPhoneOSStr[] = "10000"; 143 if (Min >= 2 && Min <= 9) { // iPhone OS 2.0-9.0 144 // darwin9.2.0 -> 20000, darwin9.3.0 -> 30000, etc. 145 iPhoneOSStr[0] = '0' + Min; 146 } 147 148 // Handle minor version: 2.2 -> darwin9.2.2 -> 20200 149 iPhoneOSStr[2] = std::min(Rev, 9U)+'0'; 150 Define(Defs, "__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__", 151 iPhoneOSStr); 152} 153 154/// GetDarwinLanguageOptions - Set the default language options for darwin. 155static void GetDarwinLanguageOptions(LangOptions &Opts, 156 const llvm::Triple &Triple) { 157 Opts.NeXTRuntime = true; 158 159 if (Triple.getOS() != llvm::Triple::Darwin) 160 return; 161 162 unsigned MajorVersion = Triple.getDarwinMajorNumber(); 163 164 // Blocks and stack protectors default to on for 10.6 (darwin10) and beyond. 165 if (MajorVersion > 9) { 166 Opts.Blocks = 1; 167 Opts.setStackProtectorMode(LangOptions::SSPOn); 168 } 169 170 // Non-fragile ABI (in 64-bit mode) default to on for 10.5 (darwin9) and 171 // beyond. 172 if (MajorVersion >= 9 && Opts.ObjC1 && 173 Triple.getArch() == llvm::Triple::x86_64) 174 Opts.ObjCNonFragileABI = 1; 175} 176 177namespace { 178template<typename Target> 179class DarwinTargetInfo : public OSTargetInfo<Target> { 180protected: 181 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 182 std::vector<char> &Defines) const { 183 getDarwinDefines(Defines, Opts); 184 getDarwinOSXDefines(Defines, Triple); 185 } 186 187 /// getDefaultLangOptions - Allow the target to specify default settings for 188 /// various language options. These may be overridden by command line 189 /// options. 190 virtual void getDefaultLangOptions(LangOptions &Opts) { 191 TargetInfo::getDefaultLangOptions(Opts); 192 GetDarwinLanguageOptions(Opts, TargetInfo::getTriple()); 193 } 194public: 195 DarwinTargetInfo(const std::string& triple) : 196 OSTargetInfo<Target>(triple) { 197 this->TLSSupported = false; 198 } 199 200 virtual const char *getUnicodeStringSection() const { 201 return "__TEXT,__ustring"; 202 } 203 204 virtual std::string isValidSectionSpecifier(const llvm::StringRef &SR) const { 205 // Let MCSectionMachO validate this. 206 llvm::StringRef Segment, Section; 207 unsigned TAA, StubSize; 208 return llvm::MCSectionMachO::ParseSectionSpecifier(SR, Segment, Section, 209 TAA, StubSize); 210 } 211}; 212 213 214// DragonFlyBSD Target 215template<typename Target> 216class DragonFlyBSDTargetInfo : public OSTargetInfo<Target> { 217protected: 218 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 219 std::vector<char> &Defs) const { 220 // DragonFly defines; list based off of gcc output 221 Define(Defs, "__DragonFly__"); 222 Define(Defs, "__DragonFly_cc_version", "100001"); 223 Define(Defs, "__ELF__"); 224 Define(Defs, "__KPRINTF_ATTRIBUTE__"); 225 Define(Defs, "__tune_i386__"); 226 DefineStd(Defs, "unix", Opts); 227 } 228public: 229 DragonFlyBSDTargetInfo(const std::string &triple) 230 : OSTargetInfo<Target>(triple) {} 231}; 232 233// FreeBSD Target 234template<typename Target> 235class FreeBSDTargetInfo : public OSTargetInfo<Target> { 236protected: 237 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 238 std::vector<char> &Defs) const { 239 // FreeBSD defines; list based off of gcc output 240 241 // FIXME: Move version number handling to llvm::Triple. 242 const char *FreeBSD = strstr(Triple.getTriple().c_str(), 243 "-freebsd"); 244 FreeBSD += strlen("-freebsd"); 245 char release[] = "X"; 246 release[0] = FreeBSD[0]; 247 char version[] = "X00001"; 248 version[0] = FreeBSD[0]; 249 250 Define(Defs, "__FreeBSD__", release); 251 Define(Defs, "__FreeBSD_cc_version", version); 252 Define(Defs, "__KPRINTF_ATTRIBUTE__"); 253 DefineStd(Defs, "unix", Opts); 254 Define(Defs, "__ELF__", "1"); 255 } 256public: 257 FreeBSDTargetInfo(const std::string &triple) 258 : OSTargetInfo<Target>(triple) { 259 this->UserLabelPrefix = ""; 260 } 261}; 262 263// Linux target 264template<typename Target> 265class LinuxTargetInfo : public OSTargetInfo<Target> { 266protected: 267 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 268 std::vector<char> &Defs) const { 269 // Linux defines; list based off of gcc output 270 DefineStd(Defs, "unix", Opts); 271 DefineStd(Defs, "linux", Opts); 272 Define(Defs, "__gnu_linux__"); 273 Define(Defs, "__ELF__", "1"); 274 if (Opts.POSIXThreads) 275 Define(Defs, "_REENTRANT", "1"); 276 } 277public: 278 LinuxTargetInfo(const std::string& triple) 279 : OSTargetInfo<Target>(triple) { 280 this->UserLabelPrefix = ""; 281 } 282}; 283 284// NetBSD Target 285template<typename Target> 286class NetBSDTargetInfo : public OSTargetInfo<Target> { 287protected: 288 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 289 std::vector<char> &Defs) const { 290 // NetBSD defines; list based off of gcc output 291 Define(Defs, "__NetBSD__", "1"); 292 Define(Defs, "__unix__", "1"); 293 Define(Defs, "__ELF__", "1"); 294 if (Opts.POSIXThreads) 295 Define(Defs, "_POSIX_THREADS", "1"); 296 } 297public: 298 NetBSDTargetInfo(const std::string &triple) 299 : OSTargetInfo<Target>(triple) { 300 this->UserLabelPrefix = ""; 301 } 302}; 303 304// OpenBSD Target 305template<typename Target> 306class OpenBSDTargetInfo : public OSTargetInfo<Target> { 307protected: 308 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 309 std::vector<char> &Defs) const { 310 // OpenBSD defines; list based off of gcc output 311 312 Define(Defs, "__OpenBSD__", "1"); 313 DefineStd(Defs, "unix", Opts); 314 Define(Defs, "__ELF__", "1"); 315 if (Opts.POSIXThreads) 316 Define(Defs, "_POSIX_THREADS", "1"); 317 } 318public: 319 OpenBSDTargetInfo(const std::string &triple) 320 : OSTargetInfo<Target>(triple) {} 321}; 322 323// AuroraUX target 324template<typename Target> 325class AuroraUXTargetInfo : public OSTargetInfo<Target> { 326protected: 327 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 328 std::vector<char> &Defs) const { 329 DefineStd(Defs, "sun", Opts); 330 DefineStd(Defs, "unix", Opts); 331 Define(Defs, "__ELF__"); 332 Define(Defs, "__svr4__"); 333 Define(Defs, "__SVR4"); 334 } 335public: 336 AuroraUXTargetInfo(const std::string& triple) 337 : OSTargetInfo<Target>(triple) { 338 this->UserLabelPrefix = ""; 339 this->WCharType = this->SignedLong; 340 // FIXME: WIntType should be SignedLong 341 } 342}; 343 344// Solaris target 345template<typename Target> 346class SolarisTargetInfo : public OSTargetInfo<Target> { 347protected: 348 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 349 std::vector<char> &Defs) const { 350 DefineStd(Defs, "sun", Opts); 351 DefineStd(Defs, "unix", Opts); 352 Define(Defs, "__ELF__"); 353 Define(Defs, "__svr4__"); 354 Define(Defs, "__SVR4"); 355 } 356public: 357 SolarisTargetInfo(const std::string& triple) 358 : OSTargetInfo<Target>(triple) { 359 this->UserLabelPrefix = ""; 360 this->WCharType = this->SignedLong; 361 // FIXME: WIntType should be SignedLong 362 } 363}; 364} // end anonymous namespace. 365 366//===----------------------------------------------------------------------===// 367// Specific target implementations. 368//===----------------------------------------------------------------------===// 369 370namespace { 371// PPC abstract base class 372class PPCTargetInfo : public TargetInfo { 373 static const Builtin::Info BuiltinInfo[]; 374 static const char * const GCCRegNames[]; 375 static const TargetInfo::GCCRegAlias GCCRegAliases[]; 376 377public: 378 PPCTargetInfo(const std::string& triple) : TargetInfo(triple) {} 379 380 virtual void getTargetBuiltins(const Builtin::Info *&Records, 381 unsigned &NumRecords) const { 382 Records = BuiltinInfo; 383 NumRecords = clang::PPC::LastTSBuiltin-Builtin::FirstTSBuiltin; 384 } 385 386 virtual void getTargetDefines(const LangOptions &Opts, 387 std::vector<char> &Defines) const; 388 389 virtual const char *getVAListDeclaration() const { 390 return "typedef char* __builtin_va_list;"; 391 // This is the right definition for ABI/V4: System V.4/eabi. 392 /*return "typedef struct __va_list_tag {" 393 " unsigned char gpr;" 394 " unsigned char fpr;" 395 " unsigned short reserved;" 396 " void* overflow_arg_area;" 397 " void* reg_save_area;" 398 "} __builtin_va_list[1];";*/ 399 } 400 virtual void getGCCRegNames(const char * const *&Names, 401 unsigned &NumNames) const; 402 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 403 unsigned &NumAliases) const; 404 virtual bool validateAsmConstraint(const char *&Name, 405 TargetInfo::ConstraintInfo &Info) const { 406 switch (*Name) { 407 default: return false; 408 case 'O': // Zero 409 return true; 410 case 'b': // Base register 411 case 'f': // Floating point register 412 Info.setAllowsRegister(); 413 return true; 414 } 415 } 416 virtual void getDefaultLangOptions(LangOptions &Opts) { 417 TargetInfo::getDefaultLangOptions(Opts); 418 Opts.CharIsSigned = false; 419 } 420 virtual const char *getClobbers() const { 421 return ""; 422 } 423}; 424 425const Builtin::Info PPCTargetInfo::BuiltinInfo[] = { 426#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false }, 427#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false }, 428#include "clang/Basic/BuiltinsPPC.def" 429}; 430 431 432/// PPCTargetInfo::getTargetDefines - Return a set of the PowerPC-specific 433/// #defines that are not tied to a specific subtarget. 434void PPCTargetInfo::getTargetDefines(const LangOptions &Opts, 435 std::vector<char> &Defs) const { 436 // Target identification. 437 Define(Defs, "__ppc__"); 438 Define(Defs, "_ARCH_PPC"); 439 Define(Defs, "__POWERPC__"); 440 if (PointerWidth == 64) { 441 Define(Defs, "_ARCH_PPC64"); 442 Define(Defs, "_LP64"); 443 Define(Defs, "__LP64__"); 444 Define(Defs, "__ppc64__"); 445 } else { 446 Define(Defs, "__ppc__"); 447 } 448 449 // Target properties. 450 Define(Defs, "_BIG_ENDIAN"); 451 Define(Defs, "__BIG_ENDIAN__"); 452 453 // Subtarget options. 454 Define(Defs, "__NATURAL_ALIGNMENT__"); 455 Define(Defs, "__REGISTER_PREFIX__", ""); 456 457 // FIXME: Should be controlled by command line option. 458 Define(Defs, "__LONG_DOUBLE_128__"); 459} 460 461 462const char * const PPCTargetInfo::GCCRegNames[] = { 463 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 464 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", 465 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23", 466 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31", 467 "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7", 468 "f8", "f9", "f10", "f11", "f12", "f13", "f14", "f15", 469 "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23", 470 "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31", 471 "mq", "lr", "ctr", "ap", 472 "cr0", "cr1", "cr2", "cr3", "cr4", "cr5", "cr6", "cr7", 473 "xer", 474 "v0", "v1", "v2", "v3", "v4", "v5", "v6", "v7", 475 "v8", "v9", "v10", "v11", "v12", "v13", "v14", "v15", 476 "v16", "v17", "v18", "v19", "v20", "v21", "v22", "v23", 477 "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31", 478 "vrsave", "vscr", 479 "spe_acc", "spefscr", 480 "sfp" 481}; 482 483void PPCTargetInfo::getGCCRegNames(const char * const *&Names, 484 unsigned &NumNames) const { 485 Names = GCCRegNames; 486 NumNames = llvm::array_lengthof(GCCRegNames); 487} 488 489const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = { 490 // While some of these aliases do map to different registers 491 // they still share the same register name. 492 { { "0" }, "r0" }, 493 { { "1"}, "r1" }, 494 { { "2" }, "r2" }, 495 { { "3" }, "r3" }, 496 { { "4" }, "r4" }, 497 { { "5" }, "r5" }, 498 { { "6" }, "r6" }, 499 { { "7" }, "r7" }, 500 { { "8" }, "r8" }, 501 { { "9" }, "r9" }, 502 { { "10" }, "r10" }, 503 { { "11" }, "r11" }, 504 { { "12" }, "r12" }, 505 { { "13" }, "r13" }, 506 { { "14" }, "r14" }, 507 { { "15" }, "r15" }, 508 { { "16" }, "r16" }, 509 { { "17" }, "r17" }, 510 { { "18" }, "r18" }, 511 { { "19" }, "r19" }, 512 { { "20" }, "r20" }, 513 { { "21" }, "r21" }, 514 { { "22" }, "r22" }, 515 { { "23" }, "r23" }, 516 { { "24" }, "r24" }, 517 { { "25" }, "r25" }, 518 { { "26" }, "r26" }, 519 { { "27" }, "r27" }, 520 { { "28" }, "r28" }, 521 { { "29" }, "r29" }, 522 { { "30" }, "r30" }, 523 { { "31" }, "r31" }, 524 { { "fr0" }, "f0" }, 525 { { "fr1" }, "f1" }, 526 { { "fr2" }, "f2" }, 527 { { "fr3" }, "f3" }, 528 { { "fr4" }, "f4" }, 529 { { "fr5" }, "f5" }, 530 { { "fr6" }, "f6" }, 531 { { "fr7" }, "f7" }, 532 { { "fr8" }, "f8" }, 533 { { "fr9" }, "f9" }, 534 { { "fr10" }, "f10" }, 535 { { "fr11" }, "f11" }, 536 { { "fr12" }, "f12" }, 537 { { "fr13" }, "f13" }, 538 { { "fr14" }, "f14" }, 539 { { "fr15" }, "f15" }, 540 { { "fr16" }, "f16" }, 541 { { "fr17" }, "f17" }, 542 { { "fr18" }, "f18" }, 543 { { "fr19" }, "f19" }, 544 { { "fr20" }, "f20" }, 545 { { "fr21" }, "f21" }, 546 { { "fr22" }, "f22" }, 547 { { "fr23" }, "f23" }, 548 { { "fr24" }, "f24" }, 549 { { "fr25" }, "f25" }, 550 { { "fr26" }, "f26" }, 551 { { "fr27" }, "f27" }, 552 { { "fr28" }, "f28" }, 553 { { "fr29" }, "f29" }, 554 { { "fr30" }, "f30" }, 555 { { "fr31" }, "f31" }, 556 { { "cc" }, "cr0" }, 557}; 558 559void PPCTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases, 560 unsigned &NumAliases) const { 561 Aliases = GCCRegAliases; 562 NumAliases = llvm::array_lengthof(GCCRegAliases); 563} 564} // end anonymous namespace. 565 566namespace { 567class PPC32TargetInfo : public PPCTargetInfo { 568public: 569 PPC32TargetInfo(const std::string& triple) : PPCTargetInfo(triple) { 570 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 571 "i64:64:64-f32:32:32-f64:64:64-v128:128:128"; 572 } 573}; 574} // end anonymous namespace. 575 576namespace { 577class PPC64TargetInfo : public PPCTargetInfo { 578public: 579 PPC64TargetInfo(const std::string& triple) : PPCTargetInfo(triple) { 580 LongWidth = LongAlign = PointerWidth = PointerAlign = 64; 581 IntMaxType = SignedLong; 582 UIntMaxType = UnsignedLong; 583 Int64Type = SignedLong; 584 DescriptionString = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 585 "i64:64:64-f32:32:32-f64:64:64-v128:128:128"; 586 } 587}; 588} // end anonymous namespace. 589 590namespace { 591// Namespace for x86 abstract base class 592const Builtin::Info BuiltinInfo[] = { 593#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false }, 594#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false }, 595#include "clang/Basic/BuiltinsX86.def" 596}; 597 598const char *GCCRegNames[] = { 599 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp", 600 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)", 601 "argp", "flags", "fspr", "dirflag", "frame", 602 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7", 603 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7", 604 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", 605 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15" 606}; 607 608const TargetInfo::GCCRegAlias GCCRegAliases[] = { 609 { { "al", "ah", "eax", "rax" }, "ax" }, 610 { { "bl", "bh", "ebx", "rbx" }, "bx" }, 611 { { "cl", "ch", "ecx", "rcx" }, "cx" }, 612 { { "dl", "dh", "edx", "rdx" }, "dx" }, 613 { { "esi", "rsi" }, "si" }, 614 { { "edi", "rdi" }, "di" }, 615 { { "esp", "rsp" }, "sp" }, 616 { { "ebp", "rbp" }, "bp" }, 617}; 618 619// X86 target abstract base class; x86-32 and x86-64 are very close, so 620// most of the implementation can be shared. 621class X86TargetInfo : public TargetInfo { 622 enum X86SSEEnum { 623 NoMMXSSE, MMX, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42 624 } SSELevel; 625public: 626 X86TargetInfo(const std::string& triple) 627 : TargetInfo(triple), SSELevel(NoMMXSSE) { 628 LongDoubleFormat = &llvm::APFloat::x87DoubleExtended; 629 } 630 virtual void getTargetBuiltins(const Builtin::Info *&Records, 631 unsigned &NumRecords) const { 632 Records = BuiltinInfo; 633 NumRecords = clang::X86::LastTSBuiltin-Builtin::FirstTSBuiltin; 634 } 635 virtual void getGCCRegNames(const char * const *&Names, 636 unsigned &NumNames) const { 637 Names = GCCRegNames; 638 NumNames = llvm::array_lengthof(GCCRegNames); 639 } 640 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 641 unsigned &NumAliases) const { 642 Aliases = GCCRegAliases; 643 NumAliases = llvm::array_lengthof(GCCRegAliases); 644 } 645 virtual bool validateAsmConstraint(const char *&Name, 646 TargetInfo::ConstraintInfo &info) const; 647 virtual std::string convertConstraint(const char Constraint) const; 648 virtual const char *getClobbers() const { 649 return "~{dirflag},~{fpsr},~{flags}"; 650 } 651 virtual void getTargetDefines(const LangOptions &Opts, 652 std::vector<char> &Defines) const; 653 virtual bool setFeatureEnabled(llvm::StringMap<bool> &Features, 654 const std::string &Name, 655 bool Enabled) const; 656 virtual void getDefaultFeatures(const std::string &CPU, 657 llvm::StringMap<bool> &Features) const; 658 virtual void HandleTargetFeatures(const llvm::StringMap<bool> &Features); 659}; 660 661void X86TargetInfo::getDefaultFeatures(const std::string &CPU, 662 llvm::StringMap<bool> &Features) const { 663 // FIXME: This should not be here. 664 Features["3dnow"] = false; 665 Features["3dnowa"] = false; 666 Features["mmx"] = false; 667 Features["sse"] = false; 668 Features["sse2"] = false; 669 Features["sse3"] = false; 670 Features["ssse3"] = false; 671 Features["sse41"] = false; 672 Features["sse42"] = false; 673 674 // LLVM does not currently recognize this. 675 // Features["sse4a"] = false; 676 677 // FIXME: This *really* should not be here. 678 679 // X86_64 always has SSE2. 680 if (PointerWidth == 64) 681 Features["sse2"] = Features["sse"] = Features["mmx"] = true; 682 683 if (CPU == "generic" || CPU == "i386" || CPU == "i486" || CPU == "i586" || 684 CPU == "pentium" || CPU == "i686" || CPU == "pentiumpro") 685 ; 686 else if (CPU == "pentium-mmx" || CPU == "pentium2") 687 setFeatureEnabled(Features, "mmx", true); 688 else if (CPU == "pentium3") 689 setFeatureEnabled(Features, "sse", true); 690 else if (CPU == "pentium-m" || CPU == "pentium4" || CPU == "x86-64") 691 setFeatureEnabled(Features, "sse2", true); 692 else if (CPU == "yonah" || CPU == "prescott" || CPU == "nocona") 693 setFeatureEnabled(Features, "sse3", true); 694 else if (CPU == "core2") 695 setFeatureEnabled(Features, "ssse3", true); 696 else if (CPU == "penryn") { 697 setFeatureEnabled(Features, "sse4", true); 698 Features["sse42"] = false; 699 } else if (CPU == "atom") 700 setFeatureEnabled(Features, "sse3", true); 701 else if (CPU == "corei7") 702 setFeatureEnabled(Features, "sse4", true); 703 else if (CPU == "k6" || CPU == "winchip-c6") 704 setFeatureEnabled(Features, "mmx", true); 705 else if (CPU == "k6-2" || CPU == "k6-3" || CPU == "athlon" || 706 CPU == "athlon-tbird" || CPU == "winchip2" || CPU == "c3") { 707 setFeatureEnabled(Features, "mmx", true); 708 setFeatureEnabled(Features, "3dnow", true); 709 } else if (CPU == "athlon-4" || CPU == "athlon-xp" || CPU == "athlon-mp") { 710 setFeatureEnabled(Features, "sse", true); 711 setFeatureEnabled(Features, "3dnowa", true); 712 } else if (CPU == "k8" || CPU == "opteron" || CPU == "athlon64" || 713 CPU == "athlon-fx") { 714 setFeatureEnabled(Features, "sse2", true); 715 setFeatureEnabled(Features, "3dnowa", true); 716 } else if (CPU == "c3-2") 717 setFeatureEnabled(Features, "sse", true); 718} 719 720bool X86TargetInfo::setFeatureEnabled(llvm::StringMap<bool> &Features, 721 const std::string &Name, 722 bool Enabled) const { 723 // FIXME: This *really* should not be here. 724 if (!Features.count(Name) && Name != "sse4") 725 return false; 726 727 if (Enabled) { 728 if (Name == "mmx") 729 Features["mmx"] = true; 730 else if (Name == "sse") 731 Features["mmx"] = Features["sse"] = true; 732 else if (Name == "sse2") 733 Features["mmx"] = Features["sse"] = Features["sse2"] = true; 734 else if (Name == "sse3") 735 Features["mmx"] = Features["sse"] = Features["sse2"] = 736 Features["sse3"] = true; 737 else if (Name == "ssse3") 738 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] = 739 Features["ssse3"] = true; 740 else if (Name == "sse4") 741 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] = 742 Features["ssse3"] = Features["sse41"] = Features["sse42"] = true; 743 else if (Name == "3dnow") 744 Features["3dnowa"] = true; 745 else if (Name == "3dnowa") 746 Features["3dnow"] = Features["3dnowa"] = true; 747 } else { 748 if (Name == "mmx") 749 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] = 750 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false; 751 else if (Name == "sse") 752 Features["sse"] = Features["sse2"] = Features["sse3"] = 753 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false; 754 else if (Name == "sse2") 755 Features["sse2"] = Features["sse3"] = Features["ssse3"] = 756 Features["sse41"] = Features["sse42"] = false; 757 else if (Name == "sse3") 758 Features["sse3"] = Features["ssse3"] = Features["sse41"] = 759 Features["sse42"] = false; 760 else if (Name == "ssse3") 761 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false; 762 else if (Name == "sse4") 763 Features["sse41"] = Features["sse42"] = false; 764 else if (Name == "3dnow") 765 Features["3dnow"] = Features["3dnowa"] = false; 766 else if (Name == "3dnowa") 767 Features["3dnowa"] = false; 768 } 769 770 return true; 771} 772 773/// HandleTargetOptions - Perform initialization based on the user 774/// configured set of features. 775void X86TargetInfo::HandleTargetFeatures(const llvm::StringMap<bool>&Features) { 776 if (Features.lookup("sse42")) 777 SSELevel = SSE42; 778 else if (Features.lookup("sse41")) 779 SSELevel = SSE41; 780 else if (Features.lookup("ssse3")) 781 SSELevel = SSSE3; 782 else if (Features.lookup("sse3")) 783 SSELevel = SSE3; 784 else if (Features.lookup("sse2")) 785 SSELevel = SSE2; 786 else if (Features.lookup("sse")) 787 SSELevel = SSE1; 788 else if (Features.lookup("mmx")) 789 SSELevel = MMX; 790} 791 792/// X86TargetInfo::getTargetDefines - Return a set of the X86-specific #defines 793/// that are not tied to a specific subtarget. 794void X86TargetInfo::getTargetDefines(const LangOptions &Opts, 795 std::vector<char> &Defs) const { 796 // Target identification. 797 if (PointerWidth == 64) { 798 Define(Defs, "_LP64"); 799 Define(Defs, "__LP64__"); 800 Define(Defs, "__amd64__"); 801 Define(Defs, "__amd64"); 802 Define(Defs, "__x86_64"); 803 Define(Defs, "__x86_64__"); 804 } else { 805 DefineStd(Defs, "i386", Opts); 806 } 807 808 // Target properties. 809 Define(Defs, "__LITTLE_ENDIAN__"); 810 811 // Subtarget options. 812 Define(Defs, "__nocona"); 813 Define(Defs, "__nocona__"); 814 Define(Defs, "__tune_nocona__"); 815 Define(Defs, "__REGISTER_PREFIX__", ""); 816 817 // Define __NO_MATH_INLINES on linux/x86 so that we don't get inline 818 // functions in glibc header files that use FP Stack inline asm which the 819 // backend can't deal with (PR879). 820 Define(Defs, "__NO_MATH_INLINES"); 821 822 // Each case falls through to the previous one here. 823 switch (SSELevel) { 824 case SSE42: 825 Define(Defs, "__SSE4_2__"); 826 case SSE41: 827 Define(Defs, "__SSE4_1__"); 828 case SSSE3: 829 Define(Defs, "__SSSE3__"); 830 case SSE3: 831 Define(Defs, "__SSE3__"); 832 case SSE2: 833 Define(Defs, "__SSE2__"); 834 Define(Defs, "__SSE2_MATH__"); // -mfp-math=sse always implied. 835 case SSE1: 836 Define(Defs, "__SSE__"); 837 Define(Defs, "__SSE_MATH__"); // -mfp-math=sse always implied. 838 case MMX: 839 Define(Defs, "__MMX__"); 840 case NoMMXSSE: 841 break; 842 } 843} 844 845 846bool 847X86TargetInfo::validateAsmConstraint(const char *&Name, 848 TargetInfo::ConstraintInfo &Info) const { 849 switch (*Name) { 850 default: return false; 851 case 'a': // eax. 852 case 'b': // ebx. 853 case 'c': // ecx. 854 case 'd': // edx. 855 case 'S': // esi. 856 case 'D': // edi. 857 case 'A': // edx:eax. 858 case 't': // top of floating point stack. 859 case 'u': // second from top of floating point stack. 860 case 'q': // Any register accessible as [r]l: a, b, c, and d. 861 case 'y': // Any MMX register. 862 case 'x': // Any SSE register. 863 case 'Q': // Any register accessible as [r]h: a, b, c, and d. 864 case 'e': // 32-bit signed integer constant for use with zero-extending 865 // x86_64 instructions. 866 case 'Z': // 32-bit unsigned integer constant for use with zero-extending 867 // x86_64 instructions. 868 case 'N': // unsigned 8-bit integer constant for use with in and out 869 // instructions. 870 case 'R': // "legacy" registers: ax, bx, cx, dx, di, si, sp, bp. 871 Info.setAllowsRegister(); 872 return true; 873 } 874} 875 876std::string 877X86TargetInfo::convertConstraint(const char Constraint) const { 878 switch (Constraint) { 879 case 'a': return std::string("{ax}"); 880 case 'b': return std::string("{bx}"); 881 case 'c': return std::string("{cx}"); 882 case 'd': return std::string("{dx}"); 883 case 'S': return std::string("{si}"); 884 case 'D': return std::string("{di}"); 885 case 't': // top of floating point stack. 886 return std::string("{st}"); 887 case 'u': // second from top of floating point stack. 888 return std::string("{st(1)}"); // second from top of floating point stack. 889 default: 890 return std::string(1, Constraint); 891 } 892} 893} // end anonymous namespace 894 895namespace { 896// X86-32 generic target 897class X86_32TargetInfo : public X86TargetInfo { 898public: 899 X86_32TargetInfo(const std::string& triple) : X86TargetInfo(triple) { 900 DoubleAlign = LongLongAlign = 32; 901 LongDoubleWidth = 96; 902 LongDoubleAlign = 32; 903 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 904 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-" 905 "a0:0:64-f80:32:32"; 906 SizeType = UnsignedInt; 907 PtrDiffType = SignedInt; 908 IntPtrType = SignedInt; 909 RegParmMax = 3; 910 } 911 virtual const char *getVAListDeclaration() const { 912 return "typedef char* __builtin_va_list;"; 913 } 914 915 int getEHDataRegisterNumber(unsigned RegNo) const { 916 if (RegNo == 0) return 0; 917 if (RegNo == 1) return 2; 918 return -1; 919 } 920}; 921} // end anonymous namespace 922 923namespace { 924class OpenBSDI386TargetInfo : public OpenBSDTargetInfo<X86_32TargetInfo> { 925public: 926 OpenBSDI386TargetInfo(const std::string& triple) : 927 OpenBSDTargetInfo<X86_32TargetInfo>(triple) { 928 SizeType = UnsignedLong; 929 IntPtrType = SignedLong; 930 PtrDiffType = SignedLong; 931 } 932}; 933} // end anonymous namespace 934 935namespace { 936class DarwinI386TargetInfo : public DarwinTargetInfo<X86_32TargetInfo> { 937public: 938 DarwinI386TargetInfo(const std::string& triple) : 939 DarwinTargetInfo<X86_32TargetInfo>(triple) { 940 LongDoubleWidth = 128; 941 LongDoubleAlign = 128; 942 SizeType = UnsignedLong; 943 IntPtrType = SignedLong; 944 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 945 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-" 946 "a0:0:64-f80:128:128"; 947 } 948 949}; 950} // end anonymous namespace 951 952namespace { 953// x86-32 Windows target 954class WindowsX86_32TargetInfo : public X86_32TargetInfo { 955public: 956 WindowsX86_32TargetInfo(const std::string& triple) 957 : X86_32TargetInfo(triple) { 958 TLSSupported = false; 959 WCharType = UnsignedShort; 960 WCharWidth = WCharAlign = 16; 961 DoubleAlign = LongLongAlign = 64; 962 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 963 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-" 964 "a0:0:64-f80:32:32"; 965 } 966 virtual void getTargetDefines(const LangOptions &Opts, 967 std::vector<char> &Defines) const { 968 X86_32TargetInfo::getTargetDefines(Opts, Defines); 969 // This list is based off of the the list of things MingW defines 970 Define(Defines, "_WIN32"); 971 DefineStd(Defines, "WIN32", Opts); 972 DefineStd(Defines, "WINNT", Opts); 973 Define(Defines, "_X86_"); 974 } 975}; 976} // end anonymous namespace 977 978namespace { 979 980/// GetWindowsVisualStudioLanguageOptions - Set the default language options for Windows. 981static void GetWindowsVisualStudioLanguageOptions(LangOptions &Opts) { 982 Opts.Microsoft = true; 983} 984 985// x86-32 Windows Visual Studio target 986class VisualStudioWindowsX86_32TargetInfo : public WindowsX86_32TargetInfo { 987public: 988 VisualStudioWindowsX86_32TargetInfo(const std::string& triple) 989 : WindowsX86_32TargetInfo(triple) { 990 } 991 virtual void getTargetDefines(const LangOptions &Opts, 992 std::vector<char> &Defines) const { 993 WindowsX86_32TargetInfo::getTargetDefines(Opts, Defines); 994 // The value of the following reflects processor type. 995 // 300=386, 400=486, 500=Pentium, 600=Blend (default) 996 // We lost the original triple, so we use the default. 997 Define(Defines, "_M_IX86", "600"); 998 } 999 virtual void getDefaultLangOptions(LangOptions &Opts) { 1000 WindowsX86_32TargetInfo::getDefaultLangOptions(Opts); 1001 GetWindowsVisualStudioLanguageOptions(Opts); 1002 } 1003}; 1004} // end anonymous namespace 1005 1006namespace { 1007// x86-32 MinGW target 1008class MinGWX86_32TargetInfo : public WindowsX86_32TargetInfo { 1009public: 1010 MinGWX86_32TargetInfo(const std::string& triple) 1011 : WindowsX86_32TargetInfo(triple) { 1012 } 1013 virtual void getTargetDefines(const LangOptions &Opts, 1014 std::vector<char> &Defines) const { 1015 WindowsX86_32TargetInfo::getTargetDefines(Opts, Defines); 1016 Define(Defines, "__MSVCRT__"); 1017 Define(Defines, "__MINGW32__"); 1018 Define(Defines, "__declspec", "__declspec"); 1019 } 1020}; 1021} // end anonymous namespace 1022 1023namespace { 1024// x86-32 Cygwin target 1025class CygwinX86_32TargetInfo : public X86_32TargetInfo { 1026public: 1027 CygwinX86_32TargetInfo(const std::string& triple) 1028 : X86_32TargetInfo(triple) { 1029 TLSSupported = false; 1030 WCharType = UnsignedShort; 1031 WCharWidth = WCharAlign = 16; 1032 DoubleAlign = LongLongAlign = 64; 1033 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 1034 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-" 1035 "a0:0:64-f80:32:32"; 1036 } 1037 virtual void getTargetDefines(const LangOptions &Opts, 1038 std::vector<char> &Defines) const { 1039 X86_32TargetInfo::getTargetDefines(Opts, Defines); 1040 Define(Defines, "__CYGWIN__"); 1041 Define(Defines, "__CYGWIN32__"); 1042 DefineStd(Defines, "unix", Opts); 1043 } 1044}; 1045} // end anonymous namespace 1046 1047namespace { 1048// x86-64 generic target 1049class X86_64TargetInfo : public X86TargetInfo { 1050public: 1051 X86_64TargetInfo(const std::string &triple) : X86TargetInfo(triple) { 1052 LongWidth = LongAlign = PointerWidth = PointerAlign = 64; 1053 LongDoubleWidth = 128; 1054 LongDoubleAlign = 128; 1055 IntMaxType = SignedLong; 1056 UIntMaxType = UnsignedLong; 1057 Int64Type = SignedLong; 1058 RegParmMax = 6; 1059 1060 DescriptionString = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 1061 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-" 1062 "a0:0:64-s0:64:64-f80:128:128"; 1063 } 1064 virtual const char *getVAListDeclaration() const { 1065 return "typedef struct __va_list_tag {" 1066 " unsigned gp_offset;" 1067 " unsigned fp_offset;" 1068 " void* overflow_arg_area;" 1069 " void* reg_save_area;" 1070 "} __va_list_tag;" 1071 "typedef __va_list_tag __builtin_va_list[1];"; 1072 } 1073 1074 int getEHDataRegisterNumber(unsigned RegNo) const { 1075 if (RegNo == 0) return 0; 1076 if (RegNo == 1) return 1; 1077 return -1; 1078 } 1079}; 1080} // end anonymous namespace 1081 1082namespace { 1083// x86-64 Windows target 1084class WindowsX86_64TargetInfo : public X86_64TargetInfo { 1085public: 1086 WindowsX86_64TargetInfo(const std::string& triple) 1087 : X86_64TargetInfo(triple) { 1088 TLSSupported = false; 1089 WCharType = UnsignedShort; 1090 WCharWidth = WCharAlign = 16; 1091 LongWidth = LongAlign = 32; 1092 DoubleAlign = LongLongAlign = 64; 1093 } 1094 virtual void getTargetDefines(const LangOptions &Opts, 1095 std::vector<char> &Defines) const { 1096 X86_64TargetInfo::getTargetDefines(Opts, Defines); 1097 Define(Defines, "_WIN64"); 1098 DefineStd(Defines, "WIN64", Opts); 1099 } 1100}; 1101} // end anonymous namespace 1102 1103namespace { 1104// x86-64 Windows Visual Studio target 1105class VisualStudioWindowsX86_64TargetInfo : public WindowsX86_64TargetInfo { 1106public: 1107 VisualStudioWindowsX86_64TargetInfo(const std::string& triple) 1108 : WindowsX86_64TargetInfo(triple) { 1109 } 1110 virtual void getTargetDefines(const LangOptions &Opts, 1111 std::vector<char> &Defines) const { 1112 WindowsX86_64TargetInfo::getTargetDefines(Opts, Defines); 1113 Define(Defines, "_M_X64"); 1114 } 1115 virtual const char *getVAListDeclaration() const { 1116 return "typedef char* va_list;"; 1117 } 1118}; 1119} // end anonymous namespace 1120 1121namespace { 1122// x86-64 MinGW target 1123class MinGWX86_64TargetInfo : public WindowsX86_64TargetInfo { 1124public: 1125 MinGWX86_64TargetInfo(const std::string& triple) 1126 : WindowsX86_64TargetInfo(triple) { 1127 } 1128 virtual void getTargetDefines(const LangOptions &Opts, 1129 std::vector<char> &Defines) const { 1130 WindowsX86_64TargetInfo::getTargetDefines(Opts, Defines); 1131 Define(Defines, "__MSVCRT__"); 1132 Define(Defines, "__MINGW64__"); 1133 Define(Defines, "__declspec"); 1134 } 1135}; 1136} // end anonymous namespace 1137 1138namespace { 1139class DarwinX86_64TargetInfo : public DarwinTargetInfo<X86_64TargetInfo> { 1140public: 1141 DarwinX86_64TargetInfo(const std::string& triple) 1142 : DarwinTargetInfo<X86_64TargetInfo>(triple) { 1143 Int64Type = SignedLongLong; 1144 } 1145}; 1146} // end anonymous namespace 1147 1148namespace { 1149class OpenBSDX86_64TargetInfo : public OpenBSDTargetInfo<X86_64TargetInfo> { 1150public: 1151 OpenBSDX86_64TargetInfo(const std::string& triple) 1152 : OpenBSDTargetInfo<X86_64TargetInfo>(triple) { 1153 IntMaxType = SignedLongLong; 1154 UIntMaxType = UnsignedLongLong; 1155 Int64Type = SignedLongLong; 1156 } 1157}; 1158} // end anonymous namespace 1159 1160namespace { 1161class ARMTargetInfo : public TargetInfo { 1162 enum { 1163 Armv4t, 1164 Armv5, 1165 Armv6, 1166 Armv7a, 1167 XScale 1168 } ArmArch; 1169 1170 static const TargetInfo::GCCRegAlias GCCRegAliases[]; 1171 static const char * const GCCRegNames[]; 1172 1173 std::string ABI; 1174 bool IsThumb; 1175 1176public: 1177 ARMTargetInfo(const std::string &TripleStr) 1178 : TargetInfo(TripleStr), ABI("aapcs-linux"), IsThumb(false) 1179 { 1180 llvm::Triple Triple(TripleStr); 1181 1182 SizeType = UnsignedInt; 1183 PtrDiffType = SignedInt; 1184 1185 // FIXME: This shouldn't be done this way, we should use features to 1186 // indicate the arch. See lib/Driver/Tools.cpp. 1187 llvm::StringRef Version(""), Arch = Triple.getArchName(); 1188 if (Arch.startswith("arm")) 1189 Version = Arch.substr(3); 1190 else if (Arch.startswith("thumb")) 1191 Version = Arch.substr(5); 1192 if (Version == "v7") 1193 ArmArch = Armv7a; 1194 else if (Version.empty() || Version == "v6" || Version == "v6t2") 1195 ArmArch = Armv6; 1196 else if (Version == "v5") 1197 ArmArch = Armv5; 1198 else if (Version == "v4t") 1199 ArmArch = Armv4t; 1200 else if (Arch == "xscale" || Arch == "thumbv5e") 1201 ArmArch = XScale; 1202 else 1203 ArmArch = Armv6; 1204 1205 if (Arch.startswith("thumb")) 1206 IsThumb = true; 1207 1208 if (IsThumb) { 1209 DescriptionString = ("e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-" 1210 "i64:64:64-f32:32:32-f64:64:64-" 1211 "v64:64:64-v128:128:128-a0:0:32"); 1212 } else { 1213 DescriptionString = ("e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 1214 "i64:64:64-f32:32:32-f64:64:64-" 1215 "v64:64:64-v128:128:128-a0:0:64"); 1216 } 1217 } 1218 virtual const char *getABI() const { return ABI.c_str(); } 1219 virtual bool setABI(const std::string &Name) { 1220 ABI = Name; 1221 1222 // The defaults (above) are for AAPCS, check if we need to change them. 1223 // 1224 // FIXME: We need support for -meabi... we could just mangle it into the 1225 // name. 1226 if (Name == "apcs-gnu") { 1227 DoubleAlign = LongLongAlign = 32; 1228 SizeType = UnsignedLong; 1229 1230 if (IsThumb) { 1231 DescriptionString = ("e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-" 1232 "i64:32:32-f32:32:32-f64:32:32-" 1233 "v64:64:64-v128:128:128-a0:0:32"); 1234 } else { 1235 DescriptionString = ("e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 1236 "i64:32:32-f32:32:32-f64:32:32-" 1237 "v64:64:64-v128:128:128-a0:0:64"); 1238 } 1239 1240 // FIXME: Override "preferred align" for double and long long. 1241 } else if (Name == "aapcs") { 1242 // FIXME: Enumerated types are variable width in straight AAPCS. 1243 } else if (Name == "aapcs-linux") { 1244 ; 1245 } else 1246 return false; 1247 1248 return true; 1249 } 1250 virtual void getTargetDefines(const LangOptions &Opts, 1251 std::vector<char> &Defs) const { 1252 // Target identification. 1253 Define(Defs, "__arm"); 1254 Define(Defs, "__arm__"); 1255 1256 // Target properties. 1257 Define(Defs, "__LITTLE_ENDIAN__"); 1258 1259 // Subtarget options. 1260 // 1261 // FIXME: Neither THUMB_INTERWORK nor SOFTFP is not being set correctly 1262 // here. 1263 if (ArmArch == Armv7a) { 1264 Define(Defs, "__ARM_ARCH_7A__"); 1265 Define(Defs, "__THUMB_INTERWORK__"); 1266 } else if (ArmArch == Armv6) { 1267 Define(Defs, "__ARM_ARCH_6K__"); 1268 Define(Defs, "__THUMB_INTERWORK__"); 1269 } else if (ArmArch == Armv5) { 1270 Define(Defs, "__ARM_ARCH_5TEJ__"); 1271 Define(Defs, "__THUMB_INTERWORK__"); 1272 Define(Defs, "__SOFTFP__"); 1273 } else if (ArmArch == Armv4t) { 1274 Define(Defs, "__ARM_ARCH_4T__"); 1275 Define(Defs, "__SOFTFP__"); 1276 } else if (ArmArch == XScale) { 1277 Define(Defs, "__ARM_ARCH_5TE__"); 1278 Define(Defs, "__XSCALE__"); 1279 Define(Defs, "__SOFTFP__"); 1280 } 1281 1282 Define(Defs, "__ARMEL__"); 1283 1284 if (IsThumb) { 1285 Define(Defs, "__THUMBEL__"); 1286 Define(Defs, "__thumb__"); 1287 if (ArmArch == Armv7a) 1288 Define(Defs, "__thumb2__"); 1289 } 1290 1291 // Note, this is always on in gcc, even though it doesn't make sense. 1292 Define(Defs, "__APCS_32__"); 1293 // FIXME: This should be conditional on VFP instruction support. 1294 Define(Defs, "__VFP_FP__"); 1295 1296 Define(Defs, "__USING_SJLJ_EXCEPTIONS__"); 1297 } 1298 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1299 unsigned &NumRecords) const { 1300 // FIXME: Implement. 1301 Records = 0; 1302 NumRecords = 0; 1303 } 1304 virtual const char *getVAListDeclaration() const { 1305 return "typedef char* __builtin_va_list;"; 1306 } 1307 virtual void getGCCRegNames(const char * const *&Names, 1308 unsigned &NumNames) const; 1309 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1310 unsigned &NumAliases) const; 1311 virtual bool validateAsmConstraint(const char *&Name, 1312 TargetInfo::ConstraintInfo &Info) const { 1313 // FIXME: Check if this is complete 1314 switch (*Name) { 1315 default: 1316 case 'l': // r0-r7 1317 case 'h': // r8-r15 1318 case 'w': // VFP Floating point register single precision 1319 case 'P': // VFP Floating point register double precision 1320 Info.setAllowsRegister(); 1321 return true; 1322 } 1323 return false; 1324 } 1325 virtual const char *getClobbers() const { 1326 // FIXME: Is this really right? 1327 return ""; 1328 } 1329}; 1330 1331const char * const ARMTargetInfo::GCCRegNames[] = { 1332 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 1333 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15" 1334}; 1335 1336void ARMTargetInfo::getGCCRegNames(const char * const *&Names, 1337 unsigned &NumNames) const { 1338 Names = GCCRegNames; 1339 NumNames = llvm::array_lengthof(GCCRegNames); 1340} 1341 1342const TargetInfo::GCCRegAlias ARMTargetInfo::GCCRegAliases[] = { 1343 1344 { { "a1" }, "r0" }, 1345 { { "a2" }, "r1" }, 1346 { { "a3" }, "r2" }, 1347 { { "a4" }, "r3" }, 1348 { { "v1" }, "r4" }, 1349 { { "v2" }, "r5" }, 1350 { { "v3" }, "r6" }, 1351 { { "v4" }, "r7" }, 1352 { { "v5" }, "r8" }, 1353 { { "v6", "rfp" }, "r9" }, 1354 { { "sl" }, "r10" }, 1355 { { "fp" }, "r11" }, 1356 { { "ip" }, "r12" }, 1357 { { "sp" }, "r13" }, 1358 { { "lr" }, "r14" }, 1359 { { "pc" }, "r15" }, 1360}; 1361 1362void ARMTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases, 1363 unsigned &NumAliases) const { 1364 Aliases = GCCRegAliases; 1365 NumAliases = llvm::array_lengthof(GCCRegAliases); 1366} 1367} // end anonymous namespace. 1368 1369 1370namespace { 1371class DarwinARMTargetInfo : 1372 public DarwinTargetInfo<ARMTargetInfo> { 1373protected: 1374 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple, 1375 std::vector<char> &Defines) const { 1376 getDarwinDefines(Defines, Opts); 1377 getDarwinIPhoneOSDefines(Defines, Triple); 1378 } 1379 1380public: 1381 DarwinARMTargetInfo(const std::string& triple) 1382 : DarwinTargetInfo<ARMTargetInfo>(triple) {} 1383}; 1384} // end anonymous namespace. 1385 1386namespace { 1387class SparcV8TargetInfo : public TargetInfo { 1388 static const TargetInfo::GCCRegAlias GCCRegAliases[]; 1389 static const char * const GCCRegNames[]; 1390public: 1391 SparcV8TargetInfo(const std::string& triple) : TargetInfo(triple) { 1392 // FIXME: Support Sparc quad-precision long double? 1393 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 1394 "i64:64:64-f32:32:32-f64:64:64-v64:64:64"; 1395 } 1396 virtual void getTargetDefines(const LangOptions &Opts, 1397 std::vector<char> &Defines) const { 1398 DefineStd(Defines, "sparc", Opts); 1399 Define(Defines, "__sparcv8"); 1400 Define(Defines, "__REGISTER_PREFIX__", ""); 1401 } 1402 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1403 unsigned &NumRecords) const { 1404 // FIXME: Implement! 1405 } 1406 virtual const char *getVAListDeclaration() const { 1407 return "typedef void* __builtin_va_list;"; 1408 } 1409 virtual void getGCCRegNames(const char * const *&Names, 1410 unsigned &NumNames) const; 1411 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1412 unsigned &NumAliases) const; 1413 virtual bool validateAsmConstraint(const char *&Name, 1414 TargetInfo::ConstraintInfo &info) const { 1415 // FIXME: Implement! 1416 return false; 1417 } 1418 virtual const char *getClobbers() const { 1419 // FIXME: Implement! 1420 return ""; 1421 } 1422}; 1423 1424const char * const SparcV8TargetInfo::GCCRegNames[] = { 1425 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 1426 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", 1427 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23", 1428 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31" 1429}; 1430 1431void SparcV8TargetInfo::getGCCRegNames(const char * const *&Names, 1432 unsigned &NumNames) const { 1433 Names = GCCRegNames; 1434 NumNames = llvm::array_lengthof(GCCRegNames); 1435} 1436 1437const TargetInfo::GCCRegAlias SparcV8TargetInfo::GCCRegAliases[] = { 1438 { { "g0" }, "r0" }, 1439 { { "g1" }, "r1" }, 1440 { { "g2" }, "r2" }, 1441 { { "g3" }, "r3" }, 1442 { { "g4" }, "r4" }, 1443 { { "g5" }, "r5" }, 1444 { { "g6" }, "r6" }, 1445 { { "g7" }, "r7" }, 1446 { { "o0" }, "r8" }, 1447 { { "o1" }, "r9" }, 1448 { { "o2" }, "r10" }, 1449 { { "o3" }, "r11" }, 1450 { { "o4" }, "r12" }, 1451 { { "o5" }, "r13" }, 1452 { { "o6", "sp" }, "r14" }, 1453 { { "o7" }, "r15" }, 1454 { { "l0" }, "r16" }, 1455 { { "l1" }, "r17" }, 1456 { { "l2" }, "r18" }, 1457 { { "l3" }, "r19" }, 1458 { { "l4" }, "r20" }, 1459 { { "l5" }, "r21" }, 1460 { { "l6" }, "r22" }, 1461 { { "l7" }, "r23" }, 1462 { { "i0" }, "r24" }, 1463 { { "i1" }, "r25" }, 1464 { { "i2" }, "r26" }, 1465 { { "i3" }, "r27" }, 1466 { { "i4" }, "r28" }, 1467 { { "i5" }, "r29" }, 1468 { { "i6", "fp" }, "r30" }, 1469 { { "i7" }, "r31" }, 1470}; 1471 1472void SparcV8TargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases, 1473 unsigned &NumAliases) const { 1474 Aliases = GCCRegAliases; 1475 NumAliases = llvm::array_lengthof(GCCRegAliases); 1476} 1477} // end anonymous namespace. 1478 1479namespace { 1480class AuroraUXSparcV8TargetInfo : public AuroraUXTargetInfo<SparcV8TargetInfo> { 1481public: 1482 AuroraUXSparcV8TargetInfo(const std::string& triple) : 1483 AuroraUXTargetInfo<SparcV8TargetInfo>(triple) { 1484 SizeType = UnsignedInt; 1485 PtrDiffType = SignedInt; 1486 } 1487}; 1488class SolarisSparcV8TargetInfo : public SolarisTargetInfo<SparcV8TargetInfo> { 1489public: 1490 SolarisSparcV8TargetInfo(const std::string& triple) : 1491 SolarisTargetInfo<SparcV8TargetInfo>(triple) { 1492 SizeType = UnsignedInt; 1493 PtrDiffType = SignedInt; 1494 } 1495}; 1496} // end anonymous namespace. 1497 1498namespace { 1499 class PIC16TargetInfo : public TargetInfo{ 1500 public: 1501 PIC16TargetInfo(const std::string& triple) : TargetInfo(triple) { 1502 TLSSupported = false; 1503 IntWidth = 16; 1504 LongWidth = LongLongWidth = 32; 1505 IntMaxTWidth = 32; 1506 PointerWidth = 16; 1507 IntAlign = 8; 1508 LongAlign = LongLongAlign = 8; 1509 PointerAlign = 8; 1510 SizeType = UnsignedInt; 1511 IntMaxType = SignedLong; 1512 UIntMaxType = UnsignedLong; 1513 IntPtrType = SignedShort; 1514 PtrDiffType = SignedInt; 1515 FloatWidth = 32; 1516 FloatAlign = 32; 1517 DoubleWidth = 32; 1518 DoubleAlign = 32; 1519 LongDoubleWidth = 32; 1520 LongDoubleAlign = 32; 1521 FloatFormat = &llvm::APFloat::IEEEsingle; 1522 DoubleFormat = &llvm::APFloat::IEEEsingle; 1523 LongDoubleFormat = &llvm::APFloat::IEEEsingle; 1524 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8-f32:32:32"; 1525 1526 } 1527 virtual uint64_t getPointerWidthV(unsigned AddrSpace) const { return 16; } 1528 virtual uint64_t getPointerAlignV(unsigned AddrSpace) const { return 8; } 1529 virtual void getTargetDefines(const LangOptions &Opts, 1530 std::vector<char> &Defines) const { 1531 Define(Defines, "__pic16"); 1532 Define(Defines, "rom", "__attribute__((address_space(1)))"); 1533 Define(Defines, "ram", "__attribute__((address_space(0)))"); 1534 Define(Defines, "_section(SectName)", 1535 "__attribute__((section(SectName)))"); 1536 Define(Defines, "near", 1537 "__attribute__((section(\"Address=NEAR\")))"); 1538 Define(Defines, "_address(Addr)", 1539 "__attribute__((section(\"Address=\"#Addr)))"); 1540 Define(Defines, "_CONFIG(conf)", "asm(\"CONFIG \"#conf)"); 1541 Define(Defines, "_interrupt", 1542 "__attribute__((section(\"interrupt=0x4\"))) \ 1543 __attribute__((used))"); 1544 } 1545 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1546 unsigned &NumRecords) const {} 1547 virtual const char *getVAListDeclaration() const { 1548 return ""; 1549 } 1550 virtual const char *getClobbers() const { 1551 return ""; 1552 } 1553 virtual void getGCCRegNames(const char * const *&Names, 1554 unsigned &NumNames) const {} 1555 virtual bool validateAsmConstraint(const char *&Name, 1556 TargetInfo::ConstraintInfo &info) const { 1557 return true; 1558 } 1559 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1560 unsigned &NumAliases) const {} 1561 virtual bool useGlobalsForAutomaticVariables() const {return true;} 1562 }; 1563} 1564 1565namespace { 1566 class MSP430TargetInfo : public TargetInfo { 1567 static const char * const GCCRegNames[]; 1568 public: 1569 MSP430TargetInfo(const std::string& triple) : TargetInfo(triple) { 1570 TLSSupported = false; 1571 IntWidth = 16; 1572 LongWidth = LongLongWidth = 32; 1573 IntMaxTWidth = 32; 1574 PointerWidth = 16; 1575 IntAlign = 8; 1576 LongAlign = LongLongAlign = 8; 1577 PointerAlign = 8; 1578 SizeType = UnsignedInt; 1579 IntMaxType = SignedLong; 1580 UIntMaxType = UnsignedLong; 1581 IntPtrType = SignedShort; 1582 PtrDiffType = SignedInt; 1583 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8"; 1584 } 1585 virtual void getTargetDefines(const LangOptions &Opts, 1586 std::vector<char> &Defines) const { 1587 Define(Defines, "MSP430"); 1588 Define(Defines, "__MSP430__"); 1589 // FIXME: defines for different 'flavours' of MCU 1590 } 1591 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1592 unsigned &NumRecords) const { 1593 // FIXME: Implement. 1594 Records = 0; 1595 NumRecords = 0; 1596 } 1597 virtual void getGCCRegNames(const char * const *&Names, 1598 unsigned &NumNames) const; 1599 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1600 unsigned &NumAliases) const { 1601 // No aliases. 1602 Aliases = 0; 1603 NumAliases = 0; 1604 } 1605 virtual bool validateAsmConstraint(const char *&Name, 1606 TargetInfo::ConstraintInfo &info) const { 1607 // No target constraints for now. 1608 return false; 1609 } 1610 virtual const char *getClobbers() const { 1611 // FIXME: Is this really right? 1612 return ""; 1613 } 1614 virtual const char *getVAListDeclaration() const { 1615 // FIXME: implement 1616 return "typedef char* __builtin_va_list;"; 1617 } 1618 }; 1619 1620 const char * const MSP430TargetInfo::GCCRegNames[] = { 1621 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 1622 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15" 1623 }; 1624 1625 void MSP430TargetInfo::getGCCRegNames(const char * const *&Names, 1626 unsigned &NumNames) const { 1627 Names = GCCRegNames; 1628 NumNames = llvm::array_lengthof(GCCRegNames); 1629 } 1630} 1631 1632 1633namespace { 1634 class SystemZTargetInfo : public TargetInfo { 1635 static const char * const GCCRegNames[]; 1636 public: 1637 SystemZTargetInfo(const std::string& triple) : TargetInfo(triple) { 1638 TLSSupported = false; 1639 IntWidth = IntAlign = 32; 1640 LongWidth = LongLongWidth = LongAlign = LongLongAlign = 64; 1641 PointerWidth = PointerAlign = 64; 1642 DescriptionString = "E-p:64:64:64-i8:8:16-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-f128:128:128-a0:16:16"; 1643 } 1644 virtual void getTargetDefines(const LangOptions &Opts, 1645 std::vector<char> &Defines) const { 1646 Define(Defines, "__s390__"); 1647 Define(Defines, "__s390x__"); 1648 } 1649 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1650 unsigned &NumRecords) const { 1651 // FIXME: Implement. 1652 Records = 0; 1653 NumRecords = 0; 1654 } 1655 1656 virtual void getDefaultLangOptions(LangOptions &Opts) { 1657 TargetInfo::getDefaultLangOptions(Opts); 1658 Opts.CharIsSigned = false; 1659 } 1660 1661 virtual void getGCCRegNames(const char * const *&Names, 1662 unsigned &NumNames) const; 1663 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1664 unsigned &NumAliases) const { 1665 // No aliases. 1666 Aliases = 0; 1667 NumAliases = 0; 1668 } 1669 virtual bool validateAsmConstraint(const char *&Name, 1670 TargetInfo::ConstraintInfo &info) const { 1671 // FIXME: implement 1672 return true; 1673 } 1674 virtual const char *getClobbers() const { 1675 // FIXME: Is this really right? 1676 return ""; 1677 } 1678 virtual const char *getVAListDeclaration() const { 1679 // FIXME: implement 1680 return "typedef char* __builtin_va_list;"; 1681 } 1682 }; 1683 1684 const char * const SystemZTargetInfo::GCCRegNames[] = { 1685 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 1686 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15" 1687 }; 1688 1689 void SystemZTargetInfo::getGCCRegNames(const char * const *&Names, 1690 unsigned &NumNames) const { 1691 Names = GCCRegNames; 1692 NumNames = llvm::array_lengthof(GCCRegNames); 1693 } 1694} 1695 1696namespace { 1697 class BlackfinTargetInfo : public TargetInfo { 1698 static const char * const GCCRegNames[]; 1699 public: 1700 BlackfinTargetInfo(const std::string& triple) : TargetInfo(triple) { 1701 TLSSupported = false; 1702 DoubleAlign = 32; 1703 LongLongAlign = 32; 1704 LongDoubleAlign = 32; 1705 DescriptionString = "e-p:32:32-i64:32-f64:32"; 1706 } 1707 1708 virtual void getTargetDefines(const LangOptions &Opts, 1709 std::vector<char> &Defines) const { 1710 DefineStd(Defines, "bfin", Opts); 1711 DefineStd(Defines, "BFIN", Opts); 1712 Define(Defines, "__ADSPBLACKFIN__"); 1713 // FIXME: This one is really dependent on -mcpu 1714 Define(Defines, "__ADSPLPBLACKFIN__"); 1715 // FIXME: Add cpu-dependent defines and __SILICON_REVISION__ 1716 } 1717 1718 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1719 unsigned &NumRecords) const { 1720 // FIXME: Implement. 1721 Records = 0; 1722 NumRecords = 0; 1723 } 1724 1725 virtual void getGCCRegNames(const char * const *&Names, 1726 unsigned &NumNames) const; 1727 1728 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1729 unsigned &NumAliases) const { 1730 // No aliases. 1731 Aliases = 0; 1732 NumAliases = 0; 1733 } 1734 1735 virtual bool validateAsmConstraint(const char *&Name, 1736 TargetInfo::ConstraintInfo &Info) const { 1737 if (strchr("adzDWeABbvfcCtukxywZY", Name[0])) { 1738 Info.setAllowsRegister(); 1739 return true; 1740 } 1741 return false; 1742 } 1743 1744 virtual const char *getClobbers() const { 1745 return ""; 1746 } 1747 1748 virtual const char *getVAListDeclaration() const { 1749 return "typedef char* __builtin_va_list;"; 1750 } 1751 }; 1752 1753 const char * const BlackfinTargetInfo::GCCRegNames[] = { 1754 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 1755 "p0", "p1", "p2", "p3", "p4", "p5", "sp", "fp", 1756 "i0", "i1", "i2", "i3", "b0", "b1", "b2", "b3", 1757 "l0", "l1", "l2", "l3", "m0", "m1", "m2", "m3", 1758 "a0", "a1", "cc", 1759 "rets", "reti", "retx", "retn", "rete", "astat", "seqstat", "usp", 1760 "argp", "lt0", "lt1", "lc0", "lc1", "lb0", "lb1" 1761 }; 1762 1763 void BlackfinTargetInfo::getGCCRegNames(const char * const *&Names, 1764 unsigned &NumNames) const { 1765 Names = GCCRegNames; 1766 NumNames = llvm::array_lengthof(GCCRegNames); 1767 } 1768} 1769 1770namespace { 1771 1772 // LLVM and Clang cannot be used directly to output native binaries for 1773 // target, but is used to compile C code to llvm bitcode with correct 1774 // type and alignment information. 1775 // 1776 // TCE uses the llvm bitcode as input and uses it for generating customized 1777 // target processor and program binary. TCE co-design environment is 1778 // publicly available in http://tce.cs.tut.fi 1779 1780 class TCETargetInfo : public TargetInfo{ 1781 public: 1782 TCETargetInfo(const std::string& triple) : TargetInfo(triple) { 1783 TLSSupported = false; 1784 IntWidth = 32; 1785 LongWidth = LongLongWidth = 32; 1786 IntMaxTWidth = 32; 1787 PointerWidth = 32; 1788 IntAlign = 32; 1789 LongAlign = LongLongAlign = 32; 1790 PointerAlign = 32; 1791 SizeType = UnsignedInt; 1792 IntMaxType = SignedLong; 1793 UIntMaxType = UnsignedLong; 1794 IntPtrType = SignedInt; 1795 PtrDiffType = SignedInt; 1796 FloatWidth = 32; 1797 FloatAlign = 32; 1798 DoubleWidth = 32; 1799 DoubleAlign = 32; 1800 LongDoubleWidth = 32; 1801 LongDoubleAlign = 32; 1802 FloatFormat = &llvm::APFloat::IEEEsingle; 1803 DoubleFormat = &llvm::APFloat::IEEEsingle; 1804 LongDoubleFormat = &llvm::APFloat::IEEEsingle; 1805 DescriptionString = "E-p:32:32:32-a0:32:32" 1806 "-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64" 1807 "-f32:32:32-f64:32:64"; 1808 } 1809 1810 virtual void getTargetDefines(const LangOptions &Opts, 1811 std::vector<char> &Defines) const { 1812 DefineStd(Defines, "tce", Opts); 1813 Define(Defines, "__TCE__"); 1814 Define(Defines, "__TCE_V1__"); 1815 } 1816 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1817 unsigned &NumRecords) const {} 1818 virtual const char *getClobbers() const { 1819 return ""; 1820 } 1821 virtual const char *getVAListDeclaration() const { 1822 return "typedef void* __builtin_va_list;"; 1823 } 1824 virtual void getGCCRegNames(const char * const *&Names, 1825 unsigned &NumNames) const {} 1826 virtual bool validateAsmConstraint(const char *&Name, 1827 TargetInfo::ConstraintInfo &info) const { 1828 return true; 1829 } 1830 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1831 unsigned &NumAliases) const {} 1832 }; 1833} 1834 1835//===----------------------------------------------------------------------===// 1836// Driver code 1837//===----------------------------------------------------------------------===// 1838 1839/// CreateTargetInfo - Return the target info object for the specified target 1840/// triple. 1841TargetInfo* TargetInfo::CreateTargetInfo(const std::string &T) { 1842 llvm::Triple Triple(T); 1843 llvm::Triple::OSType os = Triple.getOS(); 1844 1845 switch (Triple.getArch()) { 1846 default: 1847 return NULL; 1848 1849 case llvm::Triple::arm: 1850 case llvm::Triple::thumb: 1851 switch (os) { 1852 case llvm::Triple::Darwin: 1853 return new DarwinARMTargetInfo(T); 1854 case llvm::Triple::FreeBSD: 1855 return new FreeBSDTargetInfo<ARMTargetInfo>(T); 1856 default: 1857 return new ARMTargetInfo(T); 1858 } 1859 1860 case llvm::Triple::bfin: 1861 return new BlackfinTargetInfo(T); 1862 1863 case llvm::Triple::msp430: 1864 return new MSP430TargetInfo(T); 1865 1866 case llvm::Triple::pic16: 1867 return new PIC16TargetInfo(T); 1868 1869 case llvm::Triple::ppc: 1870 if (os == llvm::Triple::Darwin) 1871 return new DarwinTargetInfo<PPCTargetInfo>(T); 1872 return new PPC32TargetInfo(T); 1873 1874 case llvm::Triple::ppc64: 1875 if (os == llvm::Triple::Darwin) 1876 return new DarwinTargetInfo<PPC64TargetInfo>(T); 1877 return new PPC64TargetInfo(T); 1878 1879 case llvm::Triple::sparc: 1880 if (os == llvm::Triple::AuroraUX) 1881 return new AuroraUXSparcV8TargetInfo(T); 1882 if (os == llvm::Triple::Solaris) 1883 return new SolarisSparcV8TargetInfo(T); 1884 return new SparcV8TargetInfo(T); 1885 1886 case llvm::Triple::systemz: 1887 return new SystemZTargetInfo(T); 1888 1889 case llvm::Triple::tce: 1890 return new TCETargetInfo(T); 1891 1892 case llvm::Triple::x86: 1893 switch (os) { 1894 case llvm::Triple::AuroraUX: 1895 return new AuroraUXTargetInfo<X86_32TargetInfo>(T); 1896 case llvm::Triple::Darwin: 1897 return new DarwinI386TargetInfo(T); 1898 case llvm::Triple::Linux: 1899 return new LinuxTargetInfo<X86_32TargetInfo>(T); 1900 case llvm::Triple::DragonFly: 1901 return new DragonFlyBSDTargetInfo<X86_32TargetInfo>(T); 1902 case llvm::Triple::NetBSD: 1903 return new NetBSDTargetInfo<X86_32TargetInfo>(T); 1904 case llvm::Triple::OpenBSD: 1905 return new OpenBSDI386TargetInfo(T); 1906 case llvm::Triple::FreeBSD: 1907 return new FreeBSDTargetInfo<X86_32TargetInfo>(T); 1908 case llvm::Triple::Solaris: 1909 return new SolarisTargetInfo<X86_32TargetInfo>(T); 1910 case llvm::Triple::Cygwin: 1911 return new CygwinX86_32TargetInfo(T); 1912 case llvm::Triple::MinGW32: 1913 return new MinGWX86_32TargetInfo(T); 1914 case llvm::Triple::Win32: 1915 return new VisualStudioWindowsX86_32TargetInfo(T); 1916 default: 1917 return new X86_32TargetInfo(T); 1918 } 1919 1920 case llvm::Triple::x86_64: 1921 switch (os) { 1922 case llvm::Triple::AuroraUX: 1923 return new AuroraUXTargetInfo<X86_64TargetInfo>(T); 1924 case llvm::Triple::Darwin: 1925 return new DarwinX86_64TargetInfo(T); 1926 case llvm::Triple::Linux: 1927 return new LinuxTargetInfo<X86_64TargetInfo>(T); 1928 case llvm::Triple::NetBSD: 1929 return new NetBSDTargetInfo<X86_64TargetInfo>(T); 1930 case llvm::Triple::OpenBSD: 1931 return new OpenBSDX86_64TargetInfo(T); 1932 case llvm::Triple::FreeBSD: 1933 return new FreeBSDTargetInfo<X86_64TargetInfo>(T); 1934 case llvm::Triple::Solaris: 1935 return new SolarisTargetInfo<X86_64TargetInfo>(T); 1936 case llvm::Triple::MinGW64: 1937 return new MinGWX86_64TargetInfo(T); 1938 case llvm::Triple::Win32: // This is what Triple.h supports now. 1939 return new VisualStudioWindowsX86_64TargetInfo(T); 1940 default: 1941 return new X86_64TargetInfo(T); 1942 } 1943 } 1944} 1945