Targets.cpp revision c345a80ada9bbdc1e72b94c78bd0505438b6e162
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// FIXME: Layering violation 16#include "clang/AST/Builtins.h" 17#include "clang/AST/TargetBuiltins.h" 18#include "clang/Basic/TargetInfo.h" 19#include "clang/Basic/LangOptions.h" 20#include "llvm/ADT/STLExtras.h" 21#include "llvm/ADT/APFloat.h" 22#include "llvm/ADT/SmallString.h" 23using namespace clang; 24 25//===----------------------------------------------------------------------===// 26// Common code shared among targets. 27//===----------------------------------------------------------------------===// 28 29static void Define(std::vector<char> &Buf, const char *Macro, 30 const char *Val = "1") { 31 const char *Def = "#define "; 32 Buf.insert(Buf.end(), Def, Def+strlen(Def)); 33 Buf.insert(Buf.end(), Macro, Macro+strlen(Macro)); 34 Buf.push_back(' '); 35 Buf.insert(Buf.end(), Val, Val+strlen(Val)); 36 Buf.push_back('\n'); 37} 38 39/// DefineStd - Define a macro name and standard variants. For example if 40/// MacroName is "unix", then this will define "__unix", "__unix__", and "unix" 41/// when in GNU mode. 42static void DefineStd(std::vector<char> &Buf, const char *MacroName, 43 const LangOptions &Opts) { 44 assert(MacroName[0] != '_' && "Identifier should be in the user's namespace"); 45 46 // If in GNU mode (e.g. -std=gnu99 but not -std=c99) define the raw identifier 47 // in the user's namespace. 48 if (Opts.GNUMode) 49 Define(Buf, MacroName); 50 51 // Define __unix. 52 llvm::SmallString<20> TmpStr; 53 TmpStr = "__"; 54 TmpStr += MacroName; 55 Define(Buf, TmpStr.c_str()); 56 57 // Define __unix__. 58 TmpStr += "__"; 59 Define(Buf, TmpStr.c_str()); 60} 61 62//===----------------------------------------------------------------------===// 63// Defines specific to certain operating systems. 64//===----------------------------------------------------------------------===// 65 66static void getSolarisDefines(std::vector<char> &Defs) { 67 Define(Defs, "__SUN__"); 68 Define(Defs, "__SOLARIS__"); 69} 70 71static void getFreeBSDDefines(const LangOptions &Opts, bool is64Bit, 72 const char *Triple, std::vector<char> &Defs) { 73 // FreeBSD defines; list based off of gcc output 74 75 const char *FreeBSD = strstr(Triple, "-freebsd"); 76 FreeBSD += strlen("-freebsd"); 77 char release[] = "X"; 78 release[0] = FreeBSD[0]; 79 char version[] = "X00001"; 80 version[0] = FreeBSD[0]; 81 82 Define(Defs, "__FreeBSD__", release); 83 Define(Defs, "__FreeBSD_cc_version", version); 84 Define(Defs, "__KPRINTF_ATTRIBUTE__"); 85 DefineStd(Defs, "unix", Opts); 86 Define(Defs, "__ELF__", "1"); 87 if (is64Bit) { 88 Define(Defs, "__LP64__"); 89 } 90} 91 92static void getDragonFlyDefines(const LangOptions &Opts, 93 std::vector<char> &Defs) { 94 // DragonFly defines; list based off of gcc output 95 Define(Defs, "__DragonFly__"); 96 Define(Defs, "__DragonFly_cc_version", "100001"); 97 Define(Defs, "__ELF__"); 98 Define(Defs, "__KPRINTF_ATTRIBUTE__"); 99 Define(Defs, "__tune_i386__"); 100 DefineStd(Defs, "unix", Opts); 101} 102 103static void getLinuxDefines(const LangOptions &Opts, std::vector<char> &Defs) { 104 // Linux defines; list based off of gcc output 105 DefineStd(Defs, "unix", Opts); 106 DefineStd(Defs, "linux", Opts); 107 Define(Defs, "__gnu_linux__"); 108 Define(Defs, "__ELF__", "1"); 109} 110 111/// getDarwinNumber - Parse the 'darwin number' out of the specific targe 112/// triple. For example, if we have darwin8.5 return 8,5,4. If any entry is 113/// not defined, return 0's. Return true if we have -darwin in the string or 114/// false otherwise. 115static bool getDarwinNumber(const char *Triple, unsigned &Maj, unsigned &Min) { 116 Maj = Min = 0; 117 const char *Darwin = strstr(Triple, "-darwin"); 118 if (Darwin == 0) return false; 119 120 Darwin += strlen("-darwin"); 121 if (Darwin[0] < '0' || Darwin[0] > '9') 122 return true; 123 124 Maj = Darwin[0]-'0'; 125 ++Darwin; 126 127 // Handle "darwin11". 128 if (Maj == 1 && Darwin[0] >= '0' && Darwin[0] <= '9') { 129 Maj = 10+Darwin[0]-'0'; 130 ++Darwin; 131 } 132 133 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049" 134 if (Darwin[0] == '.' && Darwin[1] >= '0' && Darwin[1] <= '9' && 135 Darwin[2] == '\0') 136 Min = Darwin[1]-'0'; 137 138 return true; 139} 140 141static void getDarwinDefines(std::vector<char> &Defs, const char *Triple) { 142 Define(Defs, "__APPLE__"); 143 Define(Defs, "__MACH__"); 144 Define(Defs, "OBJC_NEW_PROPERTIES"); 145 146 // FIXME: OBJC_ZEROCOST_EXCEPTIONS when using zero cost eh. 147 148 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5. 149 unsigned Maj, Min; 150 if (getDarwinNumber(Triple, Maj, Min)) { 151 char DarwinStr[] = "1000"; 152 if (Maj >= 4 && Maj <= 13) { // 10.0-10.9 153 // darwin7 -> 1030, darwin8 -> 1040, darwin9 -> 1050, etc. 154 DarwinStr[2] = '0' + Maj-4; 155 } 156 157 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049" 158 DarwinStr[3] = Min+'0'; 159 Define(Defs, "__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", DarwinStr); 160 } 161} 162 163/// GetDarwinLanguageOptions - Set the default language options for darwin. 164static void GetDarwinLanguageOptions(LangOptions &Opts, 165 const char *Triple) { 166 Opts.NeXTRuntime = true; 167 168 unsigned Maj, Min; 169 if (!getDarwinNumber(Triple, Maj, Min)) 170 return; 171 172 // Blocks default to on for 10.6 (darwin10) and beyond. 173 // As does nonfragile-abi for 64bit mode 174 if (Maj > 9) 175 Opts.Blocks = 1; 176 177 if (Maj >= 9 && Opts.ObjC1 && !strncmp(Triple, "x86_64", 6)) 178 Opts.ObjCNonFragileABI = 1; 179} 180 181 182//===----------------------------------------------------------------------===// 183// Specific target implementations. 184//===----------------------------------------------------------------------===// 185 186namespace { 187// PPC abstract base class 188class PPCTargetInfo : public TargetInfo { 189 static const Builtin::Info BuiltinInfo[]; 190 static const char * const GCCRegNames[]; 191 static const TargetInfo::GCCRegAlias GCCRegAliases[]; 192 193public: 194 PPCTargetInfo(const std::string& triple) : TargetInfo(triple) { 195 CharIsSigned = false; 196 } 197 virtual void getTargetBuiltins(const Builtin::Info *&Records, 198 unsigned &NumRecords) const { 199 Records = BuiltinInfo; 200 NumRecords = clang::PPC::LastTSBuiltin-Builtin::FirstTSBuiltin; 201 } 202 203 virtual void getTargetDefines(const LangOptions &Opts, 204 std::vector<char> &Defines) const; 205 206 virtual const char *getVAListDeclaration() const { 207 return "typedef char* __builtin_va_list;"; 208 // This is the right definition for ABI/V4: System V.4/eabi. 209 /*return "typedef struct __va_list_tag {" 210 " unsigned char gpr;" 211 " unsigned char fpr;" 212 " unsigned short reserved;" 213 " void* overflow_arg_area;" 214 " void* reg_save_area;" 215 "} __builtin_va_list[1];";*/ 216 } 217 virtual const char *getTargetPrefix() const { 218 return "ppc"; 219 } 220 virtual void getGCCRegNames(const char * const *&Names, 221 unsigned &NumNames) const; 222 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 223 unsigned &NumAliases) const; 224 virtual bool validateAsmConstraint(const char *&Name, 225 TargetInfo::ConstraintInfo &info) const { 226 switch (*Name) { 227 default: return false; 228 case 'O': // Zero 229 return true; 230 case 'b': // Base register 231 case 'f': // Floating point register 232 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister); 233 return true; 234 } 235 } 236 virtual const char *getClobbers() const { 237 return ""; 238 } 239}; 240 241const Builtin::Info PPCTargetInfo::BuiltinInfo[] = { 242#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false }, 243#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false }, 244#include "clang/AST/PPCBuiltins.def" 245}; 246 247 248/// PPCTargetInfo::getTargetDefines - Return a set of the PowerPC-specific 249/// #defines that are not tied to a specific subtarget. 250void PPCTargetInfo::getTargetDefines(const LangOptions &Opts, 251 std::vector<char> &Defs) const { 252 // Target identification. 253 Define(Defs, "__ppc__"); 254 Define(Defs, "_ARCH_PPC"); 255 Define(Defs, "__POWERPC__"); 256 if (PointerWidth == 64) { 257 Define(Defs, "_ARCH_PPC64"); 258 Define(Defs, "_LP64"); 259 Define(Defs, "__LP64__"); 260 Define(Defs, "__ppc64__"); 261 } else { 262 Define(Defs, "__ppc__"); 263 } 264 265 // Target properties. 266 Define(Defs, "_BIG_ENDIAN"); 267 Define(Defs, "__BIG_ENDIAN__"); 268 269 // Subtarget options. 270 Define(Defs, "__NATURAL_ALIGNMENT__"); 271 Define(Defs, "__REGISTER_PREFIX__", ""); 272 273 // FIXME: Should be controlled by command line option. 274 Define(Defs, "__LONG_DOUBLE_128__"); 275} 276 277 278const char * const PPCTargetInfo::GCCRegNames[] = { 279 "0", "1", "2", "3", "4", "5", "6", "7", 280 "8", "9", "10", "11", "12", "13", "14", "15", 281 "16", "17", "18", "19", "20", "21", "22", "23", 282 "24", "25", "26", "27", "28", "29", "30", "31", 283 "0", "1", "2", "3", "4", "5", "6", "7", 284 "8", "9", "10", "11", "12", "13", "14", "15", 285 "16", "17", "18", "19", "20", "21", "22", "23", 286 "24", "25", "26", "27", "28", "29", "30", "31", 287 "mq", "lr", "ctr", "ap", 288 "0", "1", "2", "3", "4", "5", "6", "7", 289 "xer", 290 "0", "1", "2", "3", "4", "5", "6", "7", 291 "8", "9", "10", "11", "12", "13", "14", "15", 292 "16", "17", "18", "19", "20", "21", "22", "23", 293 "24", "25", "26", "27", "28", "29", "30", "31", 294 "vrsave", "vscr", 295 "spe_acc", "spefscr", 296 "sfp" 297}; 298 299void PPCTargetInfo::getGCCRegNames(const char * const *&Names, 300 unsigned &NumNames) const { 301 Names = GCCRegNames; 302 NumNames = llvm::array_lengthof(GCCRegNames); 303} 304 305const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = { 306 // While some of these aliases do map to different registers 307 // they still share the same register name. 308 { { "cc", "cr0", "fr0", "r0", "v0"}, "0" }, 309 { { "cr1", "fr1", "r1", "sp", "v1"}, "1" }, 310 { { "cr2", "fr2", "r2", "toc", "v2"}, "2" }, 311 { { "cr3", "fr3", "r3", "v3"}, "3" }, 312 { { "cr4", "fr4", "r4", "v4"}, "4" }, 313 { { "cr5", "fr5", "r5", "v5"}, "5" }, 314 { { "cr6", "fr6", "r6", "v6"}, "6" }, 315 { { "cr7", "fr7", "r7", "v7"}, "7" }, 316 { { "fr8", "r8", "v8"}, "8" }, 317 { { "fr9", "r9", "v9"}, "9" }, 318 { { "fr10", "r10", "v10"}, "10" }, 319 { { "fr11", "r11", "v11"}, "11" }, 320 { { "fr12", "r12", "v12"}, "12" }, 321 { { "fr13", "r13", "v13"}, "13" }, 322 { { "fr14", "r14", "v14"}, "14" }, 323 { { "fr15", "r15", "v15"}, "15" }, 324 { { "fr16", "r16", "v16"}, "16" }, 325 { { "fr17", "r17", "v17"}, "17" }, 326 { { "fr18", "r18", "v18"}, "18" }, 327 { { "fr19", "r19", "v19"}, "19" }, 328 { { "fr20", "r20", "v20"}, "20" }, 329 { { "fr21", "r21", "v21"}, "21" }, 330 { { "fr22", "r22", "v22"}, "22" }, 331 { { "fr23", "r23", "v23"}, "23" }, 332 { { "fr24", "r24", "v24"}, "24" }, 333 { { "fr25", "r25", "v25"}, "25" }, 334 { { "fr26", "r26", "v26"}, "26" }, 335 { { "fr27", "r27", "v27"}, "27" }, 336 { { "fr28", "r28", "v28"}, "28" }, 337 { { "fr29", "r29", "v29"}, "29" }, 338 { { "fr30", "r30", "v30"}, "30" }, 339 { { "fr31", "r31", "v31"}, "31" }, 340}; 341 342void PPCTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases, 343 unsigned &NumAliases) const { 344 Aliases = GCCRegAliases; 345 NumAliases = llvm::array_lengthof(GCCRegAliases); 346} 347} // end anonymous namespace. 348 349namespace { 350class PPC32TargetInfo : public PPCTargetInfo { 351public: 352 PPC32TargetInfo(const std::string& triple) : PPCTargetInfo(triple) { 353 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 354 "i64:64:64-f32:32:32-f64:64:64-v128:128:128"; 355 } 356}; 357} // end anonymous namespace. 358 359namespace { 360class PPC64TargetInfo : public PPCTargetInfo { 361public: 362 PPC64TargetInfo(const std::string& triple) : PPCTargetInfo(triple) { 363 LongWidth = LongAlign = PointerWidth = PointerAlign = 64; 364 DescriptionString = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 365 "i64:64:64-f32:32:32-f64:64:64-v128:128:128"; 366 } 367}; 368} // end anonymous namespace. 369 370 371namespace { 372class DarwinPPCTargetInfo : public PPC32TargetInfo { 373public: 374 DarwinPPCTargetInfo(const std::string& triple) : PPC32TargetInfo(triple) {} 375 virtual void getTargetDefines(const LangOptions &Opts, 376 std::vector<char> &Defines) const { 377 PPC32TargetInfo::getTargetDefines(Opts, Defines); 378 getDarwinDefines(Defines, getTargetTriple()); 379 } 380 381 /// getDefaultLangOptions - Allow the target to specify default settings for 382 /// various language options. These may be overridden by command line 383 /// options. 384 virtual void getDefaultLangOptions(LangOptions &Opts) { 385 GetDarwinLanguageOptions(Opts, getTargetTriple()); 386 } 387}; 388} // end anonymous namespace. 389 390namespace { 391class DarwinPPC64TargetInfo : public PPC64TargetInfo { 392public: 393 DarwinPPC64TargetInfo(const std::string& triple) : PPC64TargetInfo(triple) {} 394 virtual void getTargetDefines(const LangOptions &Opts, 395 std::vector<char> &Defines) const { 396 PPC64TargetInfo::getTargetDefines(Opts, Defines); 397 getDarwinDefines(Defines, getTargetTriple()); 398 } 399 400 /// getDefaultLangOptions - Allow the target to specify default settings for 401 /// various language options. These may be overridden by command line 402 /// options. 403 virtual void getDefaultLangOptions(LangOptions &Opts) { 404 GetDarwinLanguageOptions(Opts, getTargetTriple()); 405 } 406}; 407} // end anonymous namespace. 408 409namespace { 410// Namespace for x86 abstract base class 411const Builtin::Info BuiltinInfo[] = { 412#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false }, 413#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false }, 414#include "clang/AST/X86Builtins.def" 415}; 416 417const char *GCCRegNames[] = { 418 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp", 419 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)", 420 "argp", "flags", "fspr", "dirflag", "frame", 421 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7", 422 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7", 423 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", 424 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15" 425}; 426 427const TargetInfo::GCCRegAlias GCCRegAliases[] = { 428 { { "al", "ah", "eax", "rax" }, "ax" }, 429 { { "bl", "bh", "ebx", "rbx" }, "bx" }, 430 { { "cl", "ch", "ecx", "rcx" }, "cx" }, 431 { { "dl", "dh", "edx", "rdx" }, "dx" }, 432 { { "esi", "rsi" }, "si" }, 433 { { "edi", "rdi" }, "di" }, 434 { { "esp", "rsp" }, "sp" }, 435 { { "ebp", "rbp" }, "bp" }, 436}; 437 438// X86 target abstract base class; x86-32 and x86-64 are very close, so 439// most of the implementation can be shared. 440class X86TargetInfo : public TargetInfo { 441 enum X86SSEEnum { 442 NoMMXSSE, MMX, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42 443 } SSELevel; 444public: 445 X86TargetInfo(const std::string& triple) 446 : TargetInfo(triple), 447 // FIXME: hard coding to SSE2 for now. This should change to NoMMXSSE so 448 // that the driver controls this. 449 SSELevel(SSE2) { 450 LongDoubleFormat = &llvm::APFloat::x87DoubleExtended; 451 } 452 virtual void getTargetBuiltins(const Builtin::Info *&Records, 453 unsigned &NumRecords) const { 454 Records = BuiltinInfo; 455 NumRecords = clang::X86::LastTSBuiltin-Builtin::FirstTSBuiltin; 456 } 457 virtual const char *getTargetPrefix() const { 458 return "x86"; 459 } 460 virtual void getGCCRegNames(const char * const *&Names, 461 unsigned &NumNames) const { 462 Names = GCCRegNames; 463 NumNames = llvm::array_lengthof(GCCRegNames); 464 } 465 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 466 unsigned &NumAliases) const { 467 Aliases = GCCRegAliases; 468 NumAliases = llvm::array_lengthof(GCCRegAliases); 469 } 470 virtual bool validateAsmConstraint(const char *&Name, 471 TargetInfo::ConstraintInfo &info) const; 472 virtual std::string convertConstraint(const char Constraint) const; 473 virtual const char *getClobbers() const { 474 return "~{dirflag},~{fpsr},~{flags}"; 475 } 476 virtual void getTargetDefines(const LangOptions &Opts, 477 std::vector<char> &Defines) const; 478 479 virtual int HandleTargetFeatures(std::string *StrArray, unsigned NumStrs, 480 std::string &ErrorReason); 481}; 482 483/// HandleTargetOptions - Handle target-specific options like -msse2 and 484/// friends. An array of arguments is passed in: if they are all valid, this 485/// should handle them and return -1. If there is an error, the index of the 486/// invalid argument should be returned along with an optional error string. 487int X86TargetInfo::HandleTargetFeatures(std::string *StrArray, unsigned NumStrs, 488 std::string &ErrorReason) { 489 for (unsigned i = 0; i != NumStrs; ++i) { 490 const std::string &Feature = StrArray[i]; 491 if (Feature.size() < 2) return i; 492 // Ignore explicitly disabled features. 493 if (Feature[0] == '-') continue; 494 495 // Feature strings are of the form "+feature". 496 if (Feature[0] != '+') return i; 497 498 // The set of supported subtarget features is defined in 499 // lib/Target/X86/X86.td. Here we recognize and map onto our internal 500 // state. 501 if (Feature == "+mmx") 502 SSELevel = std::max(SSELevel, MMX); 503 else if (Feature == "+sse") 504 SSELevel = std::max(SSELevel, SSE1); 505 else if (Feature == "+sse2") 506 SSELevel = std::max(SSELevel, SSE2); 507 else if (Feature == "+sse3") 508 SSELevel = std::max(SSELevel, SSE3); 509 else if (Feature == "+ssse3") 510 SSELevel = std::max(SSELevel, SSSE3); 511 else if (Feature == "+sse41") 512 SSELevel = std::max(SSELevel, SSE41); 513 else if (Feature == "+sse42") 514 SSELevel = std::max(SSELevel, SSE42); 515 else if (Feature == "+64bit" || Feature == "+slow-bt-mem") 516 // Ignore these features. 517 continue; 518 else 519 return i; 520 } 521 return -1; 522} 523 524/// X86TargetInfo::getTargetDefines - Return a set of the X86-specific #defines 525/// that are not tied to a specific subtarget. 526void X86TargetInfo::getTargetDefines(const LangOptions &Opts, 527 std::vector<char> &Defs) const { 528 // Target identification. 529 if (PointerWidth == 64) { 530 Define(Defs, "_LP64"); 531 Define(Defs, "__LP64__"); 532 Define(Defs, "__amd64__"); 533 Define(Defs, "__amd64"); 534 Define(Defs, "__x86_64"); 535 Define(Defs, "__x86_64__"); 536 Define(Defs, "__SSE3__"); 537 } else { 538 DefineStd(Defs, "i386", Opts); 539 } 540 541 // Target properties. 542 Define(Defs, "__LITTLE_ENDIAN__"); 543 544 // Subtarget options. 545 Define(Defs, "__nocona"); 546 Define(Defs, "__nocona__"); 547 Define(Defs, "__tune_nocona__"); 548 Define(Defs, "__REGISTER_PREFIX__", ""); 549 550 // Each case falls through to the previous one here. 551 switch (SSELevel) { 552 case SSE42: 553 Define(Defs, "__SSE4_2__"); 554 case SSE41: 555 Define(Defs, "__SSE4_1__"); 556 case SSSE3: 557 Define(Defs, "__SSSE3__"); 558 case SSE3: 559 Define(Defs, "__SSE3__"); 560 case SSE2: 561 Define(Defs, "__SSE2__"); 562 Define(Defs, "__SSE2_MATH__"); // -mfp-math=sse always implied. 563 case SSE1: 564 Define(Defs, "__SSE__"); 565 Define(Defs, "__SSE_MATH__"); // -mfp-math=sse always implied. 566 case MMX: 567 Define(Defs, "__MMX__"); 568 case NoMMXSSE: 569 break; 570 } 571} 572 573 574bool 575X86TargetInfo::validateAsmConstraint(const char *&Name, 576 TargetInfo::ConstraintInfo &info) const { 577 switch (*Name) { 578 default: return false; 579 case 'a': // eax. 580 case 'b': // ebx. 581 case 'c': // ecx. 582 case 'd': // edx. 583 case 'S': // esi. 584 case 'D': // edi. 585 case 'A': // edx:eax. 586 case 't': // top of floating point stack. 587 case 'u': // second from top of floating point stack. 588 case 'q': // Any register accessible as [r]l: a, b, c, and d. 589 case 'y': // Any MMX register. 590 case 'x': // Any SSE register. 591 case 'Q': // Any register accessible as [r]h: a, b, c, and d. 592 case 'e': // 32-bit signed integer constant for use with zero-extending 593 // x86_64 instructions. 594 case 'Z': // 32-bit unsigned integer constant for use with zero-extending 595 // x86_64 instructions. 596 case 'N': // unsigned 8-bit integer constant for use with in and out 597 // instructions. 598 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister); 599 return true; 600 } 601} 602 603std::string 604X86TargetInfo::convertConstraint(const char Constraint) const { 605 switch (Constraint) { 606 case 'a': return std::string("{ax}"); 607 case 'b': return std::string("{bx}"); 608 case 'c': return std::string("{cx}"); 609 case 'd': return std::string("{dx}"); 610 case 'S': return std::string("{si}"); 611 case 'D': return std::string("{di}"); 612 case 't': // top of floating point stack. 613 return std::string("{st}"); 614 case 'u': // second from top of floating point stack. 615 return std::string("{st(1)}"); // second from top of floating point stack. 616 default: 617 return std::string(1, Constraint); 618 } 619} 620} // end anonymous namespace 621 622namespace { 623// X86-32 generic target 624class X86_32TargetInfo : public X86TargetInfo { 625public: 626 X86_32TargetInfo(const std::string& triple) : X86TargetInfo(triple) { 627 DoubleAlign = LongLongAlign = 32; 628 LongDoubleWidth = 96; 629 LongDoubleAlign = 32; 630 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 631 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-" 632 "a0:0:64-f80:32:32"; 633 } 634 virtual const char *getVAListDeclaration() const { 635 return "typedef char* __builtin_va_list;"; 636 } 637}; 638} // end anonymous namespace 639 640namespace { 641// x86-32 Darwin (OS X) target 642class DarwinI386TargetInfo : public X86_32TargetInfo { 643public: 644 DarwinI386TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) { 645 LongDoubleWidth = 128; 646 LongDoubleAlign = 128; 647 PtrDiffType = SignedInt; 648 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 649 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-" 650 "a0:0:64-f80:128:128"; 651 } 652 virtual void getTargetDefines(const LangOptions &Opts, 653 std::vector<char> &Defines) const { 654 X86_32TargetInfo::getTargetDefines(Opts, Defines); 655 getDarwinDefines(Defines, getTargetTriple()); 656 } 657 /// getDefaultLangOptions - Allow the target to specify default settings for 658 /// various language options. These may be overridden by command line 659 /// options. 660 virtual void getDefaultLangOptions(LangOptions &Opts) { 661 GetDarwinLanguageOptions(Opts, getTargetTriple()); 662 } 663}; 664} // end anonymous namespace 665 666namespace { 667// x86-32 FreeBSD target 668class FreeBSDX86_32TargetInfo : public X86_32TargetInfo { 669public: 670 FreeBSDX86_32TargetInfo(const std::string& triple) : 671 X86_32TargetInfo(triple) { 672 SizeType = UnsignedInt; 673 PtrDiffType = SignedInt; 674 } 675 virtual void getTargetDefines(const LangOptions &Opts, 676 std::vector<char> &Defines) const { 677 X86_32TargetInfo::getTargetDefines(Opts, Defines); 678 getFreeBSDDefines(Opts, 0, getTargetTriple(), Defines); 679 } 680}; 681} // end anonymous namespace 682 683namespace { 684// x86-32 DragonFly target 685class DragonFlyX86_32TargetInfo : public X86_32TargetInfo { 686public: 687 DragonFlyX86_32TargetInfo(const std::string& triple) : 688 X86_32TargetInfo(triple) { 689 SizeType = UnsignedInt; 690 PtrDiffType = SignedInt; 691 } 692 virtual void getTargetDefines(const LangOptions &Opts, 693 std::vector<char> &Defines) const { 694 X86_32TargetInfo::getTargetDefines(Opts, Defines); 695 getDragonFlyDefines(Opts, Defines); 696 } 697}; 698} // end anonymous namespace 699 700namespace { 701// x86-32 Linux target 702class LinuxX86_32TargetInfo : public X86_32TargetInfo { 703public: 704 LinuxX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) { 705 UserLabelPrefix = ""; 706 SizeType = UnsignedInt; 707 PtrDiffType = SignedInt; 708 IntPtrType = SignedInt; 709 } 710 virtual void getTargetDefines(const LangOptions &Opts, 711 std::vector<char> &Defines) const { 712 X86_32TargetInfo::getTargetDefines(Opts, Defines); 713 getLinuxDefines(Opts, Defines); 714 } 715}; 716} // end anonymous namespace 717 718namespace { 719// x86-32 Windows target 720class WindowsX86_32TargetInfo : public X86_32TargetInfo { 721public: 722 WindowsX86_32TargetInfo(const std::string& triple) 723 : X86_32TargetInfo(triple) { 724 // FIXME: Fix wchar_t. 725 // FIXME: We should probably enable -fms-extensions by default for 726 // this target. 727 SizeType = UnsignedInt; 728 PtrDiffType = SignedInt; 729 } 730 virtual void getTargetDefines(const LangOptions &Opts, 731 std::vector<char> &Defines) const { 732 X86_32TargetInfo::getTargetDefines(Opts, Defines); 733 // This list is based off of the the list of things MingW defines 734 Define(Defines, "_WIN32"); 735 DefineStd(Defines, "WIN32", Opts); 736 DefineStd(Defines, "WINNT", Opts); 737 Define(Defines, "_X86_"); 738 Define(Defines, "__MSVCRT__"); 739 } 740}; 741} // end anonymous namespace 742 743namespace { 744// x86-64 generic target 745class X86_64TargetInfo : public X86TargetInfo { 746public: 747 X86_64TargetInfo(const std::string &triple) : X86TargetInfo(triple) { 748 LongWidth = LongAlign = PointerWidth = PointerAlign = 64; 749 DoubleAlign = LongLongAlign = 64; 750 LongDoubleWidth = 128; 751 LongDoubleAlign = 128; 752 IntMaxType = SignedLong; 753 UIntMaxType = UnsignedLong; 754 755 DescriptionString = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 756 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-" 757 "a0:0:64-f80:128:128"; 758 } 759 virtual const char *getVAListDeclaration() const { 760 return "typedef struct __va_list_tag {" 761 " unsigned gp_offset;" 762 " unsigned fp_offset;" 763 " void* overflow_arg_area;" 764 " void* reg_save_area;" 765 "} __builtin_va_list[1];"; 766 } 767}; 768} // end anonymous namespace 769 770namespace { 771// x86-64 FreeBSD target 772class FreeBSDX86_64TargetInfo : public X86_64TargetInfo { 773public: 774 FreeBSDX86_64TargetInfo(const std::string &triple) 775 : X86_64TargetInfo(triple) {} 776 virtual void getTargetDefines(const LangOptions &Opts, 777 std::vector<char> &Defines) const { 778 X86_64TargetInfo::getTargetDefines(Opts, Defines); 779 getFreeBSDDefines(Opts, 1, getTargetTriple(), Defines); 780 } 781}; 782} // end anonymous namespace 783 784namespace { 785// x86-64 Linux target 786class LinuxX86_64TargetInfo : public X86_64TargetInfo { 787public: 788 LinuxX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) { 789 UserLabelPrefix = ""; 790 } 791 virtual void getTargetDefines(const LangOptions &Opts, 792 std::vector<char> &Defines) const { 793 X86_64TargetInfo::getTargetDefines(Opts, Defines); 794 getLinuxDefines(Opts, Defines); 795 } 796}; 797} // end anonymous namespace 798 799namespace { 800// x86-64 Darwin (OS X) target 801class DarwinX86_64TargetInfo : public X86_64TargetInfo { 802public: 803 DarwinX86_64TargetInfo(const std::string& triple) : 804 X86_64TargetInfo(triple) {} 805 806 virtual void getTargetDefines(const LangOptions &Opts, 807 std::vector<char> &Defines) const { 808 X86_64TargetInfo::getTargetDefines(Opts, Defines); 809 getDarwinDefines(Defines, getTargetTriple()); 810 } 811 812 /// getDefaultLangOptions - Allow the target to specify default settings for 813 /// various language options. These may be overridden by command line 814 /// options. 815 virtual void getDefaultLangOptions(LangOptions &Opts) { 816 GetDarwinLanguageOptions(Opts, getTargetTriple()); 817 } 818}; 819} // end anonymous namespace. 820 821namespace { 822class ARMTargetInfo : public TargetInfo { 823public: 824 ARMTargetInfo(const std::string& triple) : TargetInfo(triple) { 825 // FIXME: Are the defaults correct for ARM? 826 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 827 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:64"; 828 } 829 virtual void getTargetDefines(const LangOptions &Opts, 830 std::vector<char> &Defs) const { 831 // Target identification. 832 Define(Defs, "__arm"); 833 Define(Defs, "__arm__"); 834 835 // Target properties. 836 Define(Defs, "__LITTLE_ENDIAN__"); 837 838 // Subtarget options. [hard coded to v6 for now] 839 Define(Defs, "__ARM_ARCH_6K__"); 840 Define(Defs, "__ARMEL__"); 841 Define(Defs, "__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__", "20000"); 842 } 843 virtual void getTargetBuiltins(const Builtin::Info *&Records, 844 unsigned &NumRecords) const { 845 // FIXME: Implement. 846 Records = 0; 847 NumRecords = 0; 848 } 849 virtual const char *getVAListDeclaration() const { 850 return "typedef char* __builtin_va_list;"; 851 } 852 virtual const char *getTargetPrefix() const { 853 return "arm"; 854 } 855 virtual void getGCCRegNames(const char * const *&Names, 856 unsigned &NumNames) const { 857 // FIXME: Implement. 858 Names = 0; 859 NumNames = 0; 860 } 861 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 862 unsigned &NumAliases) const { 863 // FIXME: Implement. 864 Aliases = 0; 865 NumAliases = 0; 866 } 867 virtual bool validateAsmConstraint(const char *&Name, 868 TargetInfo::ConstraintInfo &info) const { 869 // FIXME: Check if this is complete 870 switch (*Name) { 871 default: 872 case 'l': // r0-r7 873 case 'h': // r8-r15 874 case 'w': // VFP Floating point register single precision 875 case 'P': // VFP Floating point register double precision 876 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister); 877 return true; 878 } 879 return false; 880 } 881 virtual const char *getClobbers() const { 882 // FIXME: Is this really right? 883 return ""; 884 } 885}; 886} // end anonymous namespace. 887 888 889namespace { 890class DarwinARMTargetInfo : public ARMTargetInfo { 891public: 892 DarwinARMTargetInfo(const std::string& triple) : ARMTargetInfo(triple) {} 893 894 virtual void getTargetDefines(const LangOptions &Opts, 895 std::vector<char> &Defines) const { 896 ARMTargetInfo::getTargetDefines(Opts, Defines); 897 getDarwinDefines(Defines, getTargetTriple()); 898 } 899}; 900} // end anonymous namespace. 901 902namespace { 903class SparcV8TargetInfo : public TargetInfo { 904 static const TargetInfo::GCCRegAlias GCCRegAliases[]; 905 static const char * const GCCRegNames[]; 906public: 907 SparcV8TargetInfo(const std::string& triple) : TargetInfo(triple) { 908 // FIXME: Support Sparc quad-precision long double? 909 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-" 910 "i64:64:64-f32:32:32-f64:64:64-v64:64:64"; 911 } 912 virtual void getTargetDefines(const LangOptions &Opts, 913 std::vector<char> &Defines) const { 914 // FIXME: This is missing a lot of important defines; some of the 915 // missing stuff is likely to break system headers. 916 Define(Defines, "__sparc"); 917 Define(Defines, "__sparc__"); 918 Define(Defines, "__sparcv8"); 919 } 920 virtual void getTargetBuiltins(const Builtin::Info *&Records, 921 unsigned &NumRecords) const { 922 // FIXME: Implement! 923 } 924 virtual const char *getVAListDeclaration() const { 925 return "typedef void* __builtin_va_list;"; 926 } 927 virtual const char *getTargetPrefix() const { 928 return "sparc"; 929 } 930 virtual void getGCCRegNames(const char * const *&Names, 931 unsigned &NumNames) const; 932 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 933 unsigned &NumAliases) const; 934 virtual bool validateAsmConstraint(const char *&Name, 935 TargetInfo::ConstraintInfo &info) const { 936 // FIXME: Implement! 937 return false; 938 } 939 virtual const char *getClobbers() const { 940 // FIXME: Implement! 941 return ""; 942 } 943}; 944 945const char * const SparcV8TargetInfo::GCCRegNames[] = { 946 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 947 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", 948 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23", 949 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31" 950}; 951 952void SparcV8TargetInfo::getGCCRegNames(const char * const *&Names, 953 unsigned &NumNames) const { 954 Names = GCCRegNames; 955 NumNames = llvm::array_lengthof(GCCRegNames); 956} 957 958const TargetInfo::GCCRegAlias SparcV8TargetInfo::GCCRegAliases[] = { 959 { { "g0" }, "r0" }, 960 { { "g1" }, "r1" }, 961 { { "g2" }, "r2" }, 962 { { "g3" }, "r3" }, 963 { { "g4" }, "r4" }, 964 { { "g5" }, "r5" }, 965 { { "g6" }, "r6" }, 966 { { "g7" }, "r7" }, 967 { { "o0" }, "r8" }, 968 { { "o1" }, "r9" }, 969 { { "o2" }, "r10" }, 970 { { "o3" }, "r11" }, 971 { { "o4" }, "r12" }, 972 { { "o5" }, "r13" }, 973 { { "o6", "sp" }, "r14" }, 974 { { "o7" }, "r15" }, 975 { { "l0" }, "r16" }, 976 { { "l1" }, "r17" }, 977 { { "l2" }, "r18" }, 978 { { "l3" }, "r19" }, 979 { { "l4" }, "r20" }, 980 { { "l5" }, "r21" }, 981 { { "l6" }, "r22" }, 982 { { "l7" }, "r23" }, 983 { { "i0" }, "r24" }, 984 { { "i1" }, "r25" }, 985 { { "i2" }, "r26" }, 986 { { "i3" }, "r27" }, 987 { { "i4" }, "r28" }, 988 { { "i5" }, "r29" }, 989 { { "i6", "fp" }, "r30" }, 990 { { "i7" }, "r31" }, 991}; 992 993void SparcV8TargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases, 994 unsigned &NumAliases) const { 995 Aliases = GCCRegAliases; 996 NumAliases = llvm::array_lengthof(GCCRegAliases); 997} 998} // end anonymous namespace. 999 1000namespace { 1001class SolarisSparcV8TargetInfo : public SparcV8TargetInfo { 1002public: 1003 SolarisSparcV8TargetInfo(const std::string& triple) : 1004 SparcV8TargetInfo(triple) { 1005 SizeType = UnsignedInt; 1006 PtrDiffType = SignedInt; 1007 } 1008 1009 virtual void getTargetDefines(const LangOptions &Opts, 1010 std::vector<char> &Defines) const { 1011 SparcV8TargetInfo::getTargetDefines(Opts, Defines); 1012 getSolarisDefines(Defines); 1013 } 1014}; 1015} // end anonymous namespace. 1016 1017namespace { 1018 class PIC16TargetInfo : public TargetInfo{ 1019 public: 1020 PIC16TargetInfo(const std::string& triple) : TargetInfo(triple) { 1021 IntWidth = 16; 1022 LongWidth = LongLongWidth = 32; 1023 PointerWidth = 16; 1024 IntAlign = 8; 1025 LongAlign = LongLongAlign = 8; 1026 PointerAlign = 8; 1027 SizeType = UnsignedInt; 1028 IntMaxType = SignedLong; 1029 UIntMaxType = UnsignedLong; 1030 IntPtrType = SignedShort; 1031 PtrDiffType = SignedInt; 1032 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8"; 1033 } 1034 virtual uint64_t getPointerWidthV(unsigned AddrSpace) const { return 16; } 1035 virtual uint64_t getPointerAlignV(unsigned AddrSpace) const { return 8; } 1036 virtual void getTargetDefines(const LangOptions &Opts, 1037 std::vector<char> &Defines) const { 1038 Define(Defines, "__pic16"); 1039 } 1040 virtual void getTargetBuiltins(const Builtin::Info *&Records, 1041 unsigned &NumRecords) const {} 1042 virtual const char *getVAListDeclaration() const { return "";} 1043 virtual const char *getClobbers() const {return "";} 1044 virtual const char *getTargetPrefix() const {return "";} 1045 virtual void getGCCRegNames(const char * const *&Names, 1046 unsigned &NumNames) const {} 1047 virtual bool validateAsmConstraint(const char *&Name, 1048 TargetInfo::ConstraintInfo &info) const { 1049 return true; 1050 } 1051 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases, 1052 unsigned &NumAliases) const {} 1053 virtual bool useGlobalsForAutomaticVariables() const {return true;} 1054 }; 1055} 1056 1057//===----------------------------------------------------------------------===// 1058// Driver code 1059//===----------------------------------------------------------------------===// 1060 1061static inline bool IsX86(const std::string& TT) { 1062 return (TT.size() >= 5 && TT[0] == 'i' && TT[2] == '8' && TT[3] == '6' && 1063 TT[4] == '-' && TT[1] - '3' < 6); 1064} 1065 1066/// CreateTargetInfo - Return the target info object for the specified target 1067/// triple. 1068TargetInfo* TargetInfo::CreateTargetInfo(const std::string &T) { 1069 // OS detection; this isn't really anywhere near complete. 1070 // Additions and corrections are welcome. 1071 bool isDarwin = T.find("-darwin") != std::string::npos; 1072 bool isDragonFly = T.find("-dragonfly") != std::string::npos; 1073 bool isFreeBSD = T.find("-freebsd") != std::string::npos; 1074 bool isSolaris = T.find("-solaris") != std::string::npos; 1075 bool isLinux = T.find("-linux") != std::string::npos; 1076 bool isWindows = T.find("-windows") != std::string::npos || 1077 T.find("-win32") != std::string::npos || 1078 T.find("-mingw") != std::string::npos; 1079 1080 if (T.find("ppc-") == 0 || T.find("powerpc-") == 0) { 1081 if (isDarwin) 1082 return new DarwinPPCTargetInfo(T); 1083 return new PPC32TargetInfo(T); 1084 } 1085 1086 if (T.find("ppc64-") == 0 || T.find("powerpc64-") == 0) { 1087 if (isDarwin) 1088 return new DarwinPPC64TargetInfo(T); 1089 return new PPC64TargetInfo(T); 1090 } 1091 1092 if (T.find("armv6-") == 0 || T.find("arm-") == 0) { 1093 if (isDarwin) 1094 return new DarwinARMTargetInfo(T); 1095 return new ARMTargetInfo(T); 1096 } 1097 1098 if (T.find("sparc-") == 0) { 1099 if (isSolaris) 1100 return new SolarisSparcV8TargetInfo(T); 1101 return new SparcV8TargetInfo(T); 1102 } 1103 1104 if (T.find("x86_64-") == 0 || T.find("amd64-") == 0) { 1105 if (isDarwin) 1106 return new DarwinX86_64TargetInfo(T); 1107 if (isLinux) 1108 return new LinuxX86_64TargetInfo(T); 1109 if (isFreeBSD) 1110 return new FreeBSDX86_64TargetInfo(T); 1111 return new X86_64TargetInfo(T); 1112 } 1113 1114 if (T.find("pic16-") == 0) 1115 return new PIC16TargetInfo(T); 1116 1117 if (IsX86(T)) { 1118 if (isDarwin) 1119 return new DarwinI386TargetInfo(T); 1120 if (isLinux) 1121 return new LinuxX86_32TargetInfo(T); 1122 if (isDragonFly) 1123 return new DragonFlyX86_32TargetInfo(T); 1124 if (isFreeBSD) 1125 return new FreeBSDX86_32TargetInfo(T); 1126 if (isWindows) 1127 return new WindowsX86_32TargetInfo(T); 1128 return new X86_32TargetInfo(T); 1129 } 1130 1131 return NULL; 1132} 1133 1134