1 //===--- PPC.cpp - Implement PPC target feature support -------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements PPC TargetInfo objects. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "PPC.h" 14 #include "clang/Basic/Diagnostic.h" 15 #include "clang/Basic/MacroBuilder.h" 16 #include "clang/Basic/TargetBuiltins.h" 17 18 using namespace clang; 19 using namespace clang::targets; 20 21 const Builtin::Info PPCTargetInfo::BuiltinInfo[] = { 22 #define BUILTIN(ID, TYPE, ATTRS) \ 23 {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, nullptr}, 24 #define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) \ 25 {#ID, TYPE, ATTRS, HEADER, ALL_LANGUAGES, nullptr}, 26 #include "clang/Basic/BuiltinsPPC.def" 27 }; 28 29 /// handleTargetFeatures - Perform initialization based on the user 30 /// configured set of features. 31 bool PPCTargetInfo::handleTargetFeatures(std::vector<std::string> &Features, 32 DiagnosticsEngine &Diags) { 33 FloatABI = HardFloat; 34 for (const auto &Feature : Features) { 35 if (Feature == "+altivec") { 36 HasAltivec = true; 37 } else if (Feature == "+vsx") { 38 HasVSX = true; 39 } else if (Feature == "+bpermd") { 40 HasBPERMD = true; 41 } else if (Feature == "+extdiv") { 42 HasExtDiv = true; 43 } else if (Feature == "+power8-vector") { 44 HasP8Vector = true; 45 } else if (Feature == "+crypto") { 46 HasP8Crypto = true; 47 } else if (Feature == "+direct-move") { 48 HasDirectMove = true; 49 } else if (Feature == "+htm") { 50 HasHTM = true; 51 } else if (Feature == "+float128") { 52 HasFloat128 = true; 53 } else if (Feature == "+power9-vector") { 54 HasP9Vector = true; 55 } else if (Feature == "+power10-vector") { 56 HasP10Vector = true; 57 } else if (Feature == "+pcrelative-memops") { 58 HasPCRelativeMemops = true; 59 } else if (Feature == "+prefix-instrs") { 60 HasPrefixInstrs = true; 61 } else if (Feature == "+spe" || Feature == "+efpu2") { 62 HasStrictFP = false; 63 HasSPE = true; 64 LongDoubleWidth = LongDoubleAlign = 64; 65 LongDoubleFormat = &llvm::APFloat::IEEEdouble(); 66 } else if (Feature == "-hard-float") { 67 FloatABI = SoftFloat; 68 } else if (Feature == "+paired-vector-memops") { 69 PairedVectorMemops = true; 70 } else if (Feature == "+mma") { 71 HasMMA = true; 72 } else if (Feature == "+rop-protect") { 73 HasROPProtect = true; 74 } else if (Feature == "+privileged") { 75 HasPrivileged = true; 76 } 77 // TODO: Finish this list and add an assert that we've handled them 78 // all. 79 } 80 81 return true; 82 } 83 84 static void defineXLCompatMacros(MacroBuilder &Builder) { 85 Builder.defineMacro("__popcntb", "__builtin_ppc_popcntb"); 86 Builder.defineMacro("__eieio", "__builtin_ppc_eieio"); 87 Builder.defineMacro("__iospace_eieio", "__builtin_ppc_iospace_eieio"); 88 Builder.defineMacro("__isync", "__builtin_ppc_isync"); 89 Builder.defineMacro("__lwsync", "__builtin_ppc_lwsync"); 90 Builder.defineMacro("__iospace_lwsync", "__builtin_ppc_iospace_lwsync"); 91 Builder.defineMacro("__sync", "__builtin_ppc_sync"); 92 Builder.defineMacro("__iospace_sync", "__builtin_ppc_iospace_sync"); 93 Builder.defineMacro("__dcbfl", "__builtin_ppc_dcbfl"); 94 Builder.defineMacro("__dcbflp", "__builtin_ppc_dcbflp"); 95 Builder.defineMacro("__dcbst", "__builtin_ppc_dcbst"); 96 Builder.defineMacro("__dcbt", "__builtin_ppc_dcbt"); 97 Builder.defineMacro("__dcbtst", "__builtin_ppc_dcbtst"); 98 Builder.defineMacro("__dcbz", "__builtin_ppc_dcbz"); 99 Builder.defineMacro("__icbt", "__builtin_ppc_icbt"); 100 Builder.defineMacro("__compare_and_swap", "__builtin_ppc_compare_and_swap"); 101 Builder.defineMacro("__compare_and_swaplp", 102 "__builtin_ppc_compare_and_swaplp"); 103 Builder.defineMacro("__fetch_and_add", "__builtin_ppc_fetch_and_add"); 104 Builder.defineMacro("__fetch_and_addlp", "__builtin_ppc_fetch_and_addlp"); 105 Builder.defineMacro("__fetch_and_and", "__builtin_ppc_fetch_and_and"); 106 Builder.defineMacro("__fetch_and_andlp", "__builtin_ppc_fetch_and_andlp"); 107 Builder.defineMacro("__fetch_and_or", "__builtin_ppc_fetch_and_or"); 108 Builder.defineMacro("__fetch_and_orlp", "__builtin_ppc_fetch_and_orlp"); 109 Builder.defineMacro("__fetch_and_swap", "__builtin_ppc_fetch_and_swap"); 110 Builder.defineMacro("__fetch_and_swaplp", "__builtin_ppc_fetch_and_swaplp"); 111 Builder.defineMacro("__ldarx", "__builtin_ppc_ldarx"); 112 Builder.defineMacro("__lwarx", "__builtin_ppc_lwarx"); 113 Builder.defineMacro("__stdcx", "__builtin_ppc_stdcx"); 114 Builder.defineMacro("__stwcx", "__builtin_ppc_stwcx"); 115 } 116 117 /// PPCTargetInfo::getTargetDefines - Return a set of the PowerPC-specific 118 /// #defines that are not tied to a specific subtarget. 119 void PPCTargetInfo::getTargetDefines(const LangOptions &Opts, 120 MacroBuilder &Builder) const { 121 122 defineXLCompatMacros(Builder); 123 124 // Target identification. 125 Builder.defineMacro("__ppc__"); 126 Builder.defineMacro("__PPC__"); 127 Builder.defineMacro("_ARCH_PPC"); 128 Builder.defineMacro("__powerpc__"); 129 Builder.defineMacro("__POWERPC__"); 130 if (PointerWidth == 64) { 131 Builder.defineMacro("_ARCH_PPC64"); 132 Builder.defineMacro("__powerpc64__"); 133 Builder.defineMacro("__ppc64__"); 134 Builder.defineMacro("__PPC64__"); 135 } 136 137 // Target properties. 138 if (getTriple().getArch() == llvm::Triple::ppc64le || 139 getTriple().getArch() == llvm::Triple::ppcle) { 140 Builder.defineMacro("_LITTLE_ENDIAN"); 141 } else { 142 if (!getTriple().isOSNetBSD() && 143 !getTriple().isOSOpenBSD()) 144 Builder.defineMacro("_BIG_ENDIAN"); 145 } 146 147 // ABI options. 148 if (ABI == "elfv1") 149 Builder.defineMacro("_CALL_ELF", "1"); 150 if (ABI == "elfv2") 151 Builder.defineMacro("_CALL_ELF", "2"); 152 153 // This typically is only for a new enough linker (bfd >= 2.16.2 or gold), but 154 // our support post-dates this and it should work on all 64-bit ppc linux 155 // platforms. It is guaranteed to work on all elfv2 platforms. 156 if (getTriple().getOS() == llvm::Triple::Linux && PointerWidth == 64) 157 Builder.defineMacro("_CALL_LINUX", "1"); 158 159 // Subtarget options. 160 if (!getTriple().isOSAIX()){ 161 Builder.defineMacro("__NATURAL_ALIGNMENT__"); 162 } 163 Builder.defineMacro("__REGISTER_PREFIX__", ""); 164 165 // FIXME: Should be controlled by command line option. 166 if (LongDoubleWidth == 128) { 167 Builder.defineMacro("__LONG_DOUBLE_128__"); 168 Builder.defineMacro("__LONGDOUBLE128"); 169 if (Opts.PPCIEEELongDouble) 170 Builder.defineMacro("__LONG_DOUBLE_IEEE128__"); 171 else 172 Builder.defineMacro("__LONG_DOUBLE_IBM128__"); 173 } 174 175 // Define this for elfv2 (64-bit only) or 64-bit darwin. 176 if (ABI == "elfv2" || 177 (getTriple().getOS() == llvm::Triple::Darwin && PointerWidth == 64)) 178 Builder.defineMacro("__STRUCT_PARM_ALIGN__", "16"); 179 180 if (ArchDefs & ArchDefineName) 181 Builder.defineMacro(Twine("_ARCH_", StringRef(CPU).upper())); 182 if (ArchDefs & ArchDefinePpcgr) 183 Builder.defineMacro("_ARCH_PPCGR"); 184 if (ArchDefs & ArchDefinePpcsq) 185 Builder.defineMacro("_ARCH_PPCSQ"); 186 if (ArchDefs & ArchDefine440) 187 Builder.defineMacro("_ARCH_440"); 188 if (ArchDefs & ArchDefine603) 189 Builder.defineMacro("_ARCH_603"); 190 if (ArchDefs & ArchDefine604) 191 Builder.defineMacro("_ARCH_604"); 192 if (ArchDefs & ArchDefinePwr4) 193 Builder.defineMacro("_ARCH_PWR4"); 194 if (ArchDefs & ArchDefinePwr5) 195 Builder.defineMacro("_ARCH_PWR5"); 196 if (ArchDefs & ArchDefinePwr5x) 197 Builder.defineMacro("_ARCH_PWR5X"); 198 if (ArchDefs & ArchDefinePwr6) 199 Builder.defineMacro("_ARCH_PWR6"); 200 if (ArchDefs & ArchDefinePwr6x) 201 Builder.defineMacro("_ARCH_PWR6X"); 202 if (ArchDefs & ArchDefinePwr7) 203 Builder.defineMacro("_ARCH_PWR7"); 204 if (ArchDefs & ArchDefinePwr8) 205 Builder.defineMacro("_ARCH_PWR8"); 206 if (ArchDefs & ArchDefinePwr9) 207 Builder.defineMacro("_ARCH_PWR9"); 208 if (ArchDefs & ArchDefinePwr10) 209 Builder.defineMacro("_ARCH_PWR10"); 210 if (ArchDefs & ArchDefineA2) 211 Builder.defineMacro("_ARCH_A2"); 212 if (ArchDefs & ArchDefineE500) 213 Builder.defineMacro("__NO_LWSYNC__"); 214 if (ArchDefs & ArchDefineFuture) 215 Builder.defineMacro("_ARCH_PWR_FUTURE"); 216 217 if (HasAltivec) { 218 Builder.defineMacro("__VEC__", "10206"); 219 Builder.defineMacro("__ALTIVEC__"); 220 } 221 if (HasSPE) { 222 Builder.defineMacro("__SPE__"); 223 Builder.defineMacro("__NO_FPRS__"); 224 } 225 if (HasVSX) 226 Builder.defineMacro("__VSX__"); 227 if (HasP8Vector) 228 Builder.defineMacro("__POWER8_VECTOR__"); 229 if (HasP8Crypto) 230 Builder.defineMacro("__CRYPTO__"); 231 if (HasHTM) 232 Builder.defineMacro("__HTM__"); 233 if (HasFloat128) 234 Builder.defineMacro("__FLOAT128__"); 235 if (HasP9Vector) 236 Builder.defineMacro("__POWER9_VECTOR__"); 237 if (HasMMA) 238 Builder.defineMacro("__MMA__"); 239 if (HasROPProtect) 240 Builder.defineMacro("__ROP_PROTECT__"); 241 if (HasPrivileged) 242 Builder.defineMacro("__PRIVILEGED__"); 243 if (HasP10Vector) 244 Builder.defineMacro("__POWER10_VECTOR__"); 245 if (HasPCRelativeMemops) 246 Builder.defineMacro("__PCREL__"); 247 248 Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_1"); 249 Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_2"); 250 Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4"); 251 if (PointerWidth == 64) 252 Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_8"); 253 254 // We have support for the bswap intrinsics so we can define this. 255 Builder.defineMacro("__HAVE_BSWAP__", "1"); 256 257 // FIXME: The following are not yet generated here by Clang, but are 258 // generated by GCC: 259 // 260 // _SOFT_FLOAT_ 261 // __RECIP_PRECISION__ 262 // __APPLE_ALTIVEC__ 263 // __RECIP__ 264 // __RECIPF__ 265 // __RSQRTE__ 266 // __RSQRTEF__ 267 // _SOFT_DOUBLE_ 268 // __NO_LWSYNC__ 269 // __CMODEL_MEDIUM__ 270 // __CMODEL_LARGE__ 271 // _CALL_SYSV 272 // _CALL_DARWIN 273 } 274 275 // Handle explicit options being passed to the compiler here: if we've 276 // explicitly turned off vsx and turned on any of: 277 // - power8-vector 278 // - direct-move 279 // - float128 280 // - power9-vector 281 // - paired-vector-memops 282 // - mma 283 // - power10-vector 284 // then go ahead and error since the customer has expressed an incompatible 285 // set of options. 286 static bool ppcUserFeaturesCheck(DiagnosticsEngine &Diags, 287 const std::vector<std::string> &FeaturesVec) { 288 289 // vsx was not explicitly turned off. 290 if (llvm::find(FeaturesVec, "-vsx") == FeaturesVec.end()) 291 return true; 292 293 auto FindVSXSubfeature = [&](StringRef Feature, StringRef Option) { 294 if (llvm::find(FeaturesVec, Feature) != FeaturesVec.end()) { 295 Diags.Report(diag::err_opt_not_valid_with_opt) << Option << "-mno-vsx"; 296 return true; 297 } 298 return false; 299 }; 300 301 bool Found = FindVSXSubfeature("+power8-vector", "-mpower8-vector"); 302 Found |= FindVSXSubfeature("+direct-move", "-mdirect-move"); 303 Found |= FindVSXSubfeature("+float128", "-mfloat128"); 304 Found |= FindVSXSubfeature("+power9-vector", "-mpower9-vector"); 305 Found |= FindVSXSubfeature("+paired-vector-memops", "-mpaired-vector-memops"); 306 Found |= FindVSXSubfeature("+mma", "-mmma"); 307 Found |= FindVSXSubfeature("+power10-vector", "-mpower10-vector"); 308 309 // Return false if any vsx subfeatures was found. 310 return !Found; 311 } 312 313 bool PPCTargetInfo::initFeatureMap( 314 llvm::StringMap<bool> &Features, DiagnosticsEngine &Diags, StringRef CPU, 315 const std::vector<std::string> &FeaturesVec) const { 316 Features["altivec"] = llvm::StringSwitch<bool>(CPU) 317 .Case("7400", true) 318 .Case("g4", true) 319 .Case("7450", true) 320 .Case("g4+", true) 321 .Case("970", true) 322 .Case("g5", true) 323 .Case("pwr6", true) 324 .Case("pwr7", true) 325 .Case("pwr8", true) 326 .Case("pwr9", true) 327 .Case("ppc64", true) 328 .Case("ppc64le", true) 329 .Default(false); 330 331 Features["power9-vector"] = (CPU == "pwr9"); 332 Features["crypto"] = llvm::StringSwitch<bool>(CPU) 333 .Case("ppc64le", true) 334 .Case("pwr9", true) 335 .Case("pwr8", true) 336 .Default(false); 337 Features["power8-vector"] = llvm::StringSwitch<bool>(CPU) 338 .Case("ppc64le", true) 339 .Case("pwr9", true) 340 .Case("pwr8", true) 341 .Default(false); 342 Features["bpermd"] = llvm::StringSwitch<bool>(CPU) 343 .Case("ppc64le", true) 344 .Case("pwr9", true) 345 .Case("pwr8", true) 346 .Case("pwr7", true) 347 .Default(false); 348 Features["extdiv"] = llvm::StringSwitch<bool>(CPU) 349 .Case("ppc64le", true) 350 .Case("pwr9", true) 351 .Case("pwr8", true) 352 .Case("pwr7", true) 353 .Default(false); 354 Features["direct-move"] = llvm::StringSwitch<bool>(CPU) 355 .Case("ppc64le", true) 356 .Case("pwr9", true) 357 .Case("pwr8", true) 358 .Default(false); 359 Features["vsx"] = llvm::StringSwitch<bool>(CPU) 360 .Case("ppc64le", true) 361 .Case("pwr9", true) 362 .Case("pwr8", true) 363 .Case("pwr7", true) 364 .Default(false); 365 Features["htm"] = llvm::StringSwitch<bool>(CPU) 366 .Case("ppc64le", true) 367 .Case("pwr9", true) 368 .Case("pwr8", true) 369 .Default(false); 370 371 // ROP Protect is off by default. 372 Features["rop-protect"] = false; 373 // Privileged instructions are off by default. 374 Features["privileged"] = false; 375 376 Features["spe"] = llvm::StringSwitch<bool>(CPU) 377 .Case("8548", true) 378 .Case("e500", true) 379 .Default(false); 380 381 // Power10 includes all the same features as Power9 plus any features specific 382 // to the Power10 core. 383 if (CPU == "pwr10" || CPU == "power10") { 384 initFeatureMap(Features, Diags, "pwr9", FeaturesVec); 385 addP10SpecificFeatures(Features); 386 } 387 388 // Future CPU should include all of the features of Power 10 as well as any 389 // additional features (yet to be determined) specific to it. 390 if (CPU == "future") { 391 initFeatureMap(Features, Diags, "pwr10", FeaturesVec); 392 addFutureSpecificFeatures(Features); 393 } 394 395 if (!ppcUserFeaturesCheck(Diags, FeaturesVec)) 396 return false; 397 398 if (!(ArchDefs & ArchDefinePwr9) && (ArchDefs & ArchDefinePpcgr) && 399 llvm::find(FeaturesVec, "+float128") != FeaturesVec.end()) { 400 // We have __float128 on PPC but not power 9 and above. 401 Diags.Report(diag::err_opt_not_valid_with_opt) << "-mfloat128" << CPU; 402 return false; 403 } 404 405 if (!(ArchDefs & ArchDefinePwr10) && 406 llvm::find(FeaturesVec, "+mma") != FeaturesVec.end()) { 407 // We have MMA on PPC but not power 10 and above. 408 Diags.Report(diag::err_opt_not_valid_with_opt) << "-mmma" << CPU; 409 return false; 410 } 411 412 if (!(ArchDefs & ArchDefinePwr8) && 413 llvm::find(FeaturesVec, "+rop-protect") != FeaturesVec.end()) { 414 // We can turn on ROP Protect on Power 8 and above. 415 Diags.Report(diag::err_opt_not_valid_with_opt) << "-mrop-protect" << CPU; 416 return false; 417 } 418 419 if (!(ArchDefs & ArchDefinePwr8) && 420 llvm::find(FeaturesVec, "+privileged") != FeaturesVec.end()) { 421 Diags.Report(diag::err_opt_not_valid_with_opt) << "-mprivileged" << CPU; 422 return false; 423 } 424 425 return TargetInfo::initFeatureMap(Features, Diags, CPU, FeaturesVec); 426 } 427 428 // Add any Power10 specific features. 429 void PPCTargetInfo::addP10SpecificFeatures( 430 llvm::StringMap<bool> &Features) const { 431 Features["htm"] = false; // HTM was removed for P10. 432 Features["paired-vector-memops"] = true; 433 Features["mma"] = true; 434 Features["power10-vector"] = true; 435 Features["pcrelative-memops"] = true; 436 Features["prefix-instrs"] = true; 437 return; 438 } 439 440 // Add features specific to the "Future" CPU. 441 void PPCTargetInfo::addFutureSpecificFeatures( 442 llvm::StringMap<bool> &Features) const { 443 return; 444 } 445 446 bool PPCTargetInfo::hasFeature(StringRef Feature) const { 447 return llvm::StringSwitch<bool>(Feature) 448 .Case("powerpc", true) 449 .Case("altivec", HasAltivec) 450 .Case("vsx", HasVSX) 451 .Case("power8-vector", HasP8Vector) 452 .Case("crypto", HasP8Crypto) 453 .Case("direct-move", HasDirectMove) 454 .Case("htm", HasHTM) 455 .Case("bpermd", HasBPERMD) 456 .Case("extdiv", HasExtDiv) 457 .Case("float128", HasFloat128) 458 .Case("power9-vector", HasP9Vector) 459 .Case("paired-vector-memops", PairedVectorMemops) 460 .Case("power10-vector", HasP10Vector) 461 .Case("pcrelative-memops", HasPCRelativeMemops) 462 .Case("prefix-instrs", HasPrefixInstrs) 463 .Case("spe", HasSPE) 464 .Case("mma", HasMMA) 465 .Case("rop-protect", HasROPProtect) 466 .Case("privileged", HasPrivileged) 467 .Default(false); 468 } 469 470 void PPCTargetInfo::setFeatureEnabled(llvm::StringMap<bool> &Features, 471 StringRef Name, bool Enabled) const { 472 if (Enabled) { 473 if (Name == "efpu2") 474 Features["spe"] = true; 475 // If we're enabling any of the vsx based features then enable vsx and 476 // altivec. We'll diagnose any problems later. 477 bool FeatureHasVSX = llvm::StringSwitch<bool>(Name) 478 .Case("vsx", true) 479 .Case("direct-move", true) 480 .Case("power8-vector", true) 481 .Case("power9-vector", true) 482 .Case("paired-vector-memops", true) 483 .Case("power10-vector", true) 484 .Case("float128", true) 485 .Case("mma", true) 486 .Default(false); 487 if (FeatureHasVSX) 488 Features["vsx"] = Features["altivec"] = true; 489 if (Name == "power9-vector") 490 Features["power8-vector"] = true; 491 else if (Name == "power10-vector") 492 Features["power8-vector"] = Features["power9-vector"] = true; 493 if (Name == "pcrel") 494 Features["pcrelative-memops"] = true; 495 else if (Name == "prefixed") 496 Features["prefix-instrs"] = true; 497 else 498 Features[Name] = true; 499 } else { 500 if (Name == "spe") 501 Features["efpu2"] = false; 502 // If we're disabling altivec or vsx go ahead and disable all of the vsx 503 // features. 504 if ((Name == "altivec") || (Name == "vsx")) 505 Features["vsx"] = Features["direct-move"] = Features["power8-vector"] = 506 Features["float128"] = Features["power9-vector"] = 507 Features["paired-vector-memops"] = Features["mma"] = 508 Features["power10-vector"] = false; 509 if (Name == "power8-vector") 510 Features["power9-vector"] = Features["paired-vector-memops"] = 511 Features["mma"] = Features["power10-vector"] = false; 512 else if (Name == "power9-vector") 513 Features["paired-vector-memops"] = Features["mma"] = 514 Features["power10-vector"] = false; 515 if (Name == "pcrel") 516 Features["pcrelative-memops"] = false; 517 else if (Name == "prefixed") 518 Features["prefix-instrs"] = false; 519 else 520 Features[Name] = false; 521 } 522 } 523 524 const char *const PPCTargetInfo::GCCRegNames[] = { 525 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", 526 "r9", "r10", "r11", "r12", "r13", "r14", "r15", "r16", "r17", 527 "r18", "r19", "r20", "r21", "r22", "r23", "r24", "r25", "r26", 528 "r27", "r28", "r29", "r30", "r31", "f0", "f1", "f2", "f3", 529 "f4", "f5", "f6", "f7", "f8", "f9", "f10", "f11", "f12", 530 "f13", "f14", "f15", "f16", "f17", "f18", "f19", "f20", "f21", 531 "f22", "f23", "f24", "f25", "f26", "f27", "f28", "f29", "f30", 532 "f31", "mq", "lr", "ctr", "ap", "cr0", "cr1", "cr2", "cr3", 533 "cr4", "cr5", "cr6", "cr7", "xer", "v0", "v1", "v2", "v3", 534 "v4", "v5", "v6", "v7", "v8", "v9", "v10", "v11", "v12", 535 "v13", "v14", "v15", "v16", "v17", "v18", "v19", "v20", "v21", 536 "v22", "v23", "v24", "v25", "v26", "v27", "v28", "v29", "v30", 537 "v31", "vrsave", "vscr", "spe_acc", "spefscr", "sfp" 538 }; 539 540 ArrayRef<const char *> PPCTargetInfo::getGCCRegNames() const { 541 return llvm::makeArrayRef(GCCRegNames); 542 } 543 544 const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = { 545 // While some of these aliases do map to different registers 546 // they still share the same register name. 547 {{"0"}, "r0"}, {{"1"}, "r1"}, {{"2"}, "r2"}, {{"3"}, "r3"}, 548 {{"4"}, "r4"}, {{"5"}, "r5"}, {{"6"}, "r6"}, {{"7"}, "r7"}, 549 {{"8"}, "r8"}, {{"9"}, "r9"}, {{"10"}, "r10"}, {{"11"}, "r11"}, 550 {{"12"}, "r12"}, {{"13"}, "r13"}, {{"14"}, "r14"}, {{"15"}, "r15"}, 551 {{"16"}, "r16"}, {{"17"}, "r17"}, {{"18"}, "r18"}, {{"19"}, "r19"}, 552 {{"20"}, "r20"}, {{"21"}, "r21"}, {{"22"}, "r22"}, {{"23"}, "r23"}, 553 {{"24"}, "r24"}, {{"25"}, "r25"}, {{"26"}, "r26"}, {{"27"}, "r27"}, 554 {{"28"}, "r28"}, {{"29"}, "r29"}, {{"30"}, "r30"}, {{"31"}, "r31"}, 555 {{"fr0"}, "f0"}, {{"fr1"}, "f1"}, {{"fr2"}, "f2"}, {{"fr3"}, "f3"}, 556 {{"fr4"}, "f4"}, {{"fr5"}, "f5"}, {{"fr6"}, "f6"}, {{"fr7"}, "f7"}, 557 {{"fr8"}, "f8"}, {{"fr9"}, "f9"}, {{"fr10"}, "f10"}, {{"fr11"}, "f11"}, 558 {{"fr12"}, "f12"}, {{"fr13"}, "f13"}, {{"fr14"}, "f14"}, {{"fr15"}, "f15"}, 559 {{"fr16"}, "f16"}, {{"fr17"}, "f17"}, {{"fr18"}, "f18"}, {{"fr19"}, "f19"}, 560 {{"fr20"}, "f20"}, {{"fr21"}, "f21"}, {{"fr22"}, "f22"}, {{"fr23"}, "f23"}, 561 {{"fr24"}, "f24"}, {{"fr25"}, "f25"}, {{"fr26"}, "f26"}, {{"fr27"}, "f27"}, 562 {{"fr28"}, "f28"}, {{"fr29"}, "f29"}, {{"fr30"}, "f30"}, {{"fr31"}, "f31"}, 563 {{"cc"}, "cr0"}, 564 }; 565 566 ArrayRef<TargetInfo::GCCRegAlias> PPCTargetInfo::getGCCRegAliases() const { 567 return llvm::makeArrayRef(GCCRegAliases); 568 } 569 570 // PPC ELFABIv2 DWARF Definitoin "Table 2.26. Mappings of Common Registers". 571 // vs0 ~ vs31 is mapping to 32 - 63, 572 // vs32 ~ vs63 is mapping to 77 - 108. 573 const TargetInfo::AddlRegName GCCAddlRegNames[] = { 574 // Table of additional register names to use in user input. 575 {{"vs0"}, 32}, {{"vs1"}, 33}, {{"vs2"}, 34}, {{"vs3"}, 35}, 576 {{"vs4"}, 36}, {{"vs5"}, 37}, {{"vs6"}, 38}, {{"vs7"}, 39}, 577 {{"vs8"}, 40}, {{"vs9"}, 41}, {{"vs10"}, 42}, {{"vs11"}, 43}, 578 {{"vs12"}, 44}, {{"vs13"}, 45}, {{"vs14"}, 46}, {{"vs15"}, 47}, 579 {{"vs16"}, 48}, {{"vs17"}, 49}, {{"vs18"}, 50}, {{"vs19"}, 51}, 580 {{"vs20"}, 52}, {{"vs21"}, 53}, {{"vs22"}, 54}, {{"vs23"}, 55}, 581 {{"vs24"}, 56}, {{"vs25"}, 57}, {{"vs26"}, 58}, {{"vs27"}, 59}, 582 {{"vs28"}, 60}, {{"vs29"}, 61}, {{"vs30"}, 62}, {{"vs31"}, 63}, 583 {{"vs32"}, 77}, {{"vs33"}, 78}, {{"vs34"}, 79}, {{"vs35"}, 80}, 584 {{"vs36"}, 81}, {{"vs37"}, 82}, {{"vs38"}, 83}, {{"vs39"}, 84}, 585 {{"vs40"}, 85}, {{"vs41"}, 86}, {{"vs42"}, 87}, {{"vs43"}, 88}, 586 {{"vs44"}, 89}, {{"vs45"}, 90}, {{"vs46"}, 91}, {{"vs47"}, 92}, 587 {{"vs48"}, 93}, {{"vs49"}, 94}, {{"vs50"}, 95}, {{"vs51"}, 96}, 588 {{"vs52"}, 97}, {{"vs53"}, 98}, {{"vs54"}, 99}, {{"vs55"}, 100}, 589 {{"vs56"}, 101}, {{"vs57"}, 102}, {{"vs58"}, 103}, {{"vs59"}, 104}, 590 {{"vs60"}, 105}, {{"vs61"}, 106}, {{"vs62"}, 107}, {{"vs63"}, 108}, 591 }; 592 593 ArrayRef<TargetInfo::AddlRegName> PPCTargetInfo::getGCCAddlRegNames() const { 594 if (ABI == "elfv2") 595 return llvm::makeArrayRef(GCCAddlRegNames); 596 else 597 return TargetInfo::getGCCAddlRegNames(); 598 } 599 600 static constexpr llvm::StringLiteral ValidCPUNames[] = { 601 {"generic"}, {"440"}, {"450"}, {"601"}, {"602"}, 602 {"603"}, {"603e"}, {"603ev"}, {"604"}, {"604e"}, 603 {"620"}, {"630"}, {"g3"}, {"7400"}, {"g4"}, 604 {"7450"}, {"g4+"}, {"750"}, {"8548"}, {"970"}, 605 {"g5"}, {"a2"}, {"e500"}, {"e500mc"}, {"e5500"}, 606 {"power3"}, {"pwr3"}, {"power4"}, {"pwr4"}, {"power5"}, 607 {"pwr5"}, {"power5x"}, {"pwr5x"}, {"power6"}, {"pwr6"}, 608 {"power6x"}, {"pwr6x"}, {"power7"}, {"pwr7"}, {"power8"}, 609 {"pwr8"}, {"power9"}, {"pwr9"}, {"power10"}, {"pwr10"}, 610 {"powerpc"}, {"ppc"}, {"ppc32"}, {"powerpc64"}, {"ppc64"}, 611 {"powerpc64le"}, {"ppc64le"}, {"future"}}; 612 613 bool PPCTargetInfo::isValidCPUName(StringRef Name) const { 614 return llvm::find(ValidCPUNames, Name) != std::end(ValidCPUNames); 615 } 616 617 void PPCTargetInfo::fillValidCPUList(SmallVectorImpl<StringRef> &Values) const { 618 Values.append(std::begin(ValidCPUNames), std::end(ValidCPUNames)); 619 } 620 621 void PPCTargetInfo::adjust(DiagnosticsEngine &Diags, LangOptions &Opts) { 622 if (HasAltivec) 623 Opts.AltiVec = 1; 624 TargetInfo::adjust(Diags, Opts); 625 if (LongDoubleFormat != &llvm::APFloat::IEEEdouble()) 626 LongDoubleFormat = Opts.PPCIEEELongDouble 627 ? &llvm::APFloat::IEEEquad() 628 : &llvm::APFloat::PPCDoubleDouble(); 629 Opts.IEEE128 = 1; 630 } 631 632 ArrayRef<Builtin::Info> PPCTargetInfo::getTargetBuiltins() const { 633 return llvm::makeArrayRef(BuiltinInfo, clang::PPC::LastTSBuiltin - 634 Builtin::FirstTSBuiltin); 635 } 636