PPCAsmPrinter.cpp revision 9382e29c1ebc6524618b173ed04bc25295d02c6e
1//===-- PPCAsmPrinter.cpp - Print machine instrs to PowerPC assembly --------=// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file was developed by the LLVM research group and is distributed under 6// the University of Illinois Open Source License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file contains a printer that converts from our internal representation 11// of machine-dependent LLVM code to PowerPC assembly language. This printer is 12// the output mechanism used by `llc'. 13// 14// Documentation at http://developer.apple.com/documentation/DeveloperTools/ 15// Reference/Assembler/ASMIntroduction/chapter_1_section_1.html 16// 17//===----------------------------------------------------------------------===// 18 19#define DEBUG_TYPE "asmprinter" 20#include "PPC.h" 21#include "PPCPredicates.h" 22#include "PPCTargetMachine.h" 23#include "PPCSubtarget.h" 24#include "llvm/Constants.h" 25#include "llvm/DerivedTypes.h" 26#include "llvm/Module.h" 27#include "llvm/Assembly/Writer.h" 28#include "llvm/CodeGen/AsmPrinter.h" 29#include "llvm/CodeGen/DwarfWriter.h" 30#include "llvm/CodeGen/MachineDebugInfo.h" 31#include "llvm/CodeGen/MachineFunctionPass.h" 32#include "llvm/CodeGen/MachineInstr.h" 33#include "llvm/Support/Mangler.h" 34#include "llvm/Support/MathExtras.h" 35#include "llvm/Support/CommandLine.h" 36#include "llvm/Support/Debug.h" 37#include "llvm/Support/Compiler.h" 38#include "llvm/Target/TargetAsmInfo.h" 39#include "llvm/Target/MRegisterInfo.h" 40#include "llvm/Target/TargetInstrInfo.h" 41#include "llvm/Target/TargetOptions.h" 42#include "llvm/ADT/Statistic.h" 43#include "llvm/ADT/StringExtras.h" 44#include <iostream> 45#include <set> 46using namespace llvm; 47 48namespace { 49 Statistic<> EmittedInsts("asm-printer", "Number of machine instrs printed"); 50 51 struct VISIBILITY_HIDDEN PPCAsmPrinter : public AsmPrinter { 52 std::set<std::string> FnStubs, GVStubs; 53 const PPCSubtarget &Subtarget; 54 55 // Necessary for external weak linkage support 56 std::set<std::string> ExtWeakSymbols; 57 58 PPCAsmPrinter(std::ostream &O, TargetMachine &TM, const TargetAsmInfo *T) 59 : AsmPrinter(O, TM, T), Subtarget(TM.getSubtarget<PPCSubtarget>()) { 60 } 61 62 virtual const char *getPassName() const { 63 return "PowerPC Assembly Printer"; 64 } 65 66 PPCTargetMachine &getTM() { 67 return static_cast<PPCTargetMachine&>(TM); 68 } 69 70 unsigned enumRegToMachineReg(unsigned enumReg) { 71 switch (enumReg) { 72 default: assert(0 && "Unhandled register!"); break; 73 case PPC::CR0: return 0; 74 case PPC::CR1: return 1; 75 case PPC::CR2: return 2; 76 case PPC::CR3: return 3; 77 case PPC::CR4: return 4; 78 case PPC::CR5: return 5; 79 case PPC::CR6: return 6; 80 case PPC::CR7: return 7; 81 } 82 abort(); 83 } 84 85 /// printInstruction - This method is automatically generated by tablegen 86 /// from the instruction set description. This method returns true if the 87 /// machine instruction was sufficiently described to print it, otherwise it 88 /// returns false. 89 bool printInstruction(const MachineInstr *MI); 90 91 void printMachineInstruction(const MachineInstr *MI); 92 void printOp(const MachineOperand &MO); 93 94 void printOperand(const MachineInstr *MI, unsigned OpNo) { 95 const MachineOperand &MO = MI->getOperand(OpNo); 96 if (MO.isRegister()) { 97 assert(MRegisterInfo::isPhysicalRegister(MO.getReg())&&"Not physreg??"); 98 O << TM.getRegisterInfo()->get(MO.getReg()).Name; 99 } else if (MO.isImmediate()) { 100 O << MO.getImmedValue(); 101 } else { 102 printOp(MO); 103 } 104 } 105 106 bool PrintAsmOperand(const MachineInstr *MI, unsigned OpNo, 107 unsigned AsmVariant, const char *ExtraCode); 108 bool PrintAsmMemoryOperand(const MachineInstr *MI, unsigned OpNo, 109 unsigned AsmVariant, const char *ExtraCode); 110 111 112 void printS5ImmOperand(const MachineInstr *MI, unsigned OpNo) { 113 char value = MI->getOperand(OpNo).getImmedValue(); 114 value = (value << (32-5)) >> (32-5); 115 O << (int)value; 116 } 117 void printU5ImmOperand(const MachineInstr *MI, unsigned OpNo) { 118 unsigned char value = MI->getOperand(OpNo).getImmedValue(); 119 assert(value <= 31 && "Invalid u5imm argument!"); 120 O << (unsigned int)value; 121 } 122 void printU6ImmOperand(const MachineInstr *MI, unsigned OpNo) { 123 unsigned char value = MI->getOperand(OpNo).getImmedValue(); 124 assert(value <= 63 && "Invalid u6imm argument!"); 125 O << (unsigned int)value; 126 } 127 void printS16ImmOperand(const MachineInstr *MI, unsigned OpNo) { 128 O << (short)MI->getOperand(OpNo).getImmedValue(); 129 } 130 void printU16ImmOperand(const MachineInstr *MI, unsigned OpNo) { 131 O << (unsigned short)MI->getOperand(OpNo).getImmedValue(); 132 } 133 void printS16X4ImmOperand(const MachineInstr *MI, unsigned OpNo) { 134 if (MI->getOperand(OpNo).isImmediate()) { 135 O << (short)(MI->getOperand(OpNo).getImmedValue()*4); 136 } else { 137 O << "lo16("; 138 printOp(MI->getOperand(OpNo)); 139 if (TM.getRelocationModel() == Reloc::PIC_) 140 O << "-\"L" << getFunctionNumber() << "$pb\")"; 141 else 142 O << ')'; 143 } 144 } 145 void printBranchOperand(const MachineInstr *MI, unsigned OpNo) { 146 // Branches can take an immediate operand. This is used by the branch 147 // selection pass to print $+8, an eight byte displacement from the PC. 148 if (MI->getOperand(OpNo).isImmediate()) { 149 O << "$+" << MI->getOperand(OpNo).getImmedValue()*4; 150 } else { 151 printOp(MI->getOperand(OpNo)); 152 } 153 } 154 void printCallOperand(const MachineInstr *MI, unsigned OpNo) { 155 const MachineOperand &MO = MI->getOperand(OpNo); 156 if (TM.getRelocationModel() != Reloc::Static) { 157 if (MO.getType() == MachineOperand::MO_GlobalAddress) { 158 GlobalValue *GV = MO.getGlobal(); 159 if (((GV->isExternal() || GV->hasWeakLinkage() || 160 GV->hasLinkOnceLinkage()))) { 161 // Dynamically-resolved functions need a stub for the function. 162 std::string Name = Mang->getValueName(GV); 163 FnStubs.insert(Name); 164 O << "L" << Name << "$stub"; 165 if (GV->hasExternalWeakLinkage()) 166 ExtWeakSymbols.insert(Name); 167 return; 168 } 169 } 170 if (MO.getType() == MachineOperand::MO_ExternalSymbol) { 171 std::string Name(TAI->getGlobalPrefix()); Name += MO.getSymbolName(); 172 FnStubs.insert(Name); 173 O << "L" << Name << "$stub"; 174 return; 175 } 176 } 177 178 printOp(MI->getOperand(OpNo)); 179 } 180 void printAbsAddrOperand(const MachineInstr *MI, unsigned OpNo) { 181 O << (int)MI->getOperand(OpNo).getImmedValue()*4; 182 } 183 void printPICLabel(const MachineInstr *MI, unsigned OpNo) { 184 O << "\"L" << getFunctionNumber() << "$pb\"\n"; 185 O << "\"L" << getFunctionNumber() << "$pb\":"; 186 } 187 void printSymbolHi(const MachineInstr *MI, unsigned OpNo) { 188 if (MI->getOperand(OpNo).isImmediate()) { 189 printS16ImmOperand(MI, OpNo); 190 } else { 191 O << "ha16("; 192 printOp(MI->getOperand(OpNo)); 193 if (TM.getRelocationModel() == Reloc::PIC_) 194 O << "-\"L" << getFunctionNumber() << "$pb\")"; 195 else 196 O << ')'; 197 } 198 } 199 void printSymbolLo(const MachineInstr *MI, unsigned OpNo) { 200 if (MI->getOperand(OpNo).isImmediate()) { 201 printS16ImmOperand(MI, OpNo); 202 } else { 203 O << "lo16("; 204 printOp(MI->getOperand(OpNo)); 205 if (TM.getRelocationModel() == Reloc::PIC_) 206 O << "-\"L" << getFunctionNumber() << "$pb\")"; 207 else 208 O << ')'; 209 } 210 } 211 void printcrbitm(const MachineInstr *MI, unsigned OpNo) { 212 unsigned CCReg = MI->getOperand(OpNo).getReg(); 213 unsigned RegNo = enumRegToMachineReg(CCReg); 214 O << (0x80 >> RegNo); 215 } 216 // The new addressing mode printers. 217 void printMemRegImm(const MachineInstr *MI, unsigned OpNo) { 218 printSymbolLo(MI, OpNo); 219 O << '('; 220 if (MI->getOperand(OpNo+1).isRegister() && 221 MI->getOperand(OpNo+1).getReg() == PPC::R0) 222 O << "0"; 223 else 224 printOperand(MI, OpNo+1); 225 O << ')'; 226 } 227 void printMemRegImmShifted(const MachineInstr *MI, unsigned OpNo) { 228 if (MI->getOperand(OpNo).isImmediate()) 229 printS16X4ImmOperand(MI, OpNo); 230 else 231 printSymbolLo(MI, OpNo); 232 O << '('; 233 if (MI->getOperand(OpNo+1).isRegister() && 234 MI->getOperand(OpNo+1).getReg() == PPC::R0) 235 O << "0"; 236 else 237 printOperand(MI, OpNo+1); 238 O << ')'; 239 } 240 241 void printMemRegReg(const MachineInstr *MI, unsigned OpNo) { 242 // When used as the base register, r0 reads constant zero rather than 243 // the value contained in the register. For this reason, the darwin 244 // assembler requires that we print r0 as 0 (no r) when used as the base. 245 const MachineOperand &MO = MI->getOperand(OpNo); 246 if (MO.getReg() == PPC::R0) 247 O << '0'; 248 else 249 O << TM.getRegisterInfo()->get(MO.getReg()).Name; 250 O << ", "; 251 printOperand(MI, OpNo+1); 252 } 253 254 void printPredicateOperand(const MachineInstr *MI, unsigned OpNo, 255 const char *Modifier); 256 257 virtual bool runOnMachineFunction(MachineFunction &F) = 0; 258 virtual bool doFinalization(Module &M) = 0; 259 }; 260 261 /// DarwinAsmPrinter - PowerPC assembly printer, customized for Darwin/Mac OS 262 /// X 263 struct VISIBILITY_HIDDEN DarwinAsmPrinter : public PPCAsmPrinter { 264 265 DwarfWriter DW; 266 267 DarwinAsmPrinter(std::ostream &O, PPCTargetMachine &TM, 268 const TargetAsmInfo *T) 269 : PPCAsmPrinter(O, TM, T), DW(O, this, T) { 270 } 271 272 virtual const char *getPassName() const { 273 return "Darwin PPC Assembly Printer"; 274 } 275 276 bool runOnMachineFunction(MachineFunction &F); 277 bool doInitialization(Module &M); 278 bool doFinalization(Module &M); 279 280 void getAnalysisUsage(AnalysisUsage &AU) const { 281 AU.setPreservesAll(); 282 AU.addRequired<MachineDebugInfo>(); 283 PPCAsmPrinter::getAnalysisUsage(AU); 284 } 285 286 /// getSectionForFunction - Return the section that we should emit the 287 /// specified function body into. 288 virtual std::string getSectionForFunction(const Function &F) const; 289 }; 290} // end of anonymous namespace 291 292// Include the auto-generated portion of the assembly writer 293#include "PPCGenAsmWriter.inc" 294 295void PPCAsmPrinter::printOp(const MachineOperand &MO) { 296 switch (MO.getType()) { 297 case MachineOperand::MO_Immediate: 298 std::cerr << "printOp() does not handle immediate values\n"; 299 abort(); 300 return; 301 302 case MachineOperand::MO_MachineBasicBlock: 303 printBasicBlockLabel(MO.getMachineBasicBlock()); 304 return; 305 case MachineOperand::MO_JumpTableIndex: 306 O << TAI->getPrivateGlobalPrefix() << "JTI" << getFunctionNumber() 307 << '_' << MO.getJumpTableIndex(); 308 // FIXME: PIC relocation model 309 return; 310 case MachineOperand::MO_ConstantPoolIndex: 311 O << TAI->getPrivateGlobalPrefix() << "CPI" << getFunctionNumber() 312 << '_' << MO.getConstantPoolIndex(); 313 return; 314 case MachineOperand::MO_ExternalSymbol: 315 // Computing the address of an external symbol, not calling it. 316 if (TM.getRelocationModel() != Reloc::Static) { 317 std::string Name(TAI->getGlobalPrefix()); Name += MO.getSymbolName(); 318 GVStubs.insert(Name); 319 O << "L" << Name << "$non_lazy_ptr"; 320 return; 321 } 322 O << TAI->getGlobalPrefix() << MO.getSymbolName(); 323 return; 324 case MachineOperand::MO_GlobalAddress: { 325 // Computing the address of a global symbol, not calling it. 326 GlobalValue *GV = MO.getGlobal(); 327 std::string Name = Mang->getValueName(GV); 328 329 // External or weakly linked global variables need non-lazily-resolved stubs 330 if (TM.getRelocationModel() != Reloc::Static) { 331 if (((GV->isExternal() || GV->hasWeakLinkage() || 332 GV->hasLinkOnceLinkage()))) { 333 GVStubs.insert(Name); 334 O << "L" << Name << "$non_lazy_ptr"; 335 return; 336 } 337 } 338 O << Name; 339 340 if (GV->hasExternalWeakLinkage()) 341 ExtWeakSymbols.insert(Name); 342 return; 343 } 344 345 default: 346 O << "<unknown operand type: " << MO.getType() << ">"; 347 return; 348 } 349} 350 351/// PrintAsmOperand - Print out an operand for an inline asm expression. 352/// 353bool PPCAsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNo, 354 unsigned AsmVariant, 355 const char *ExtraCode) { 356 // Does this asm operand have a single letter operand modifier? 357 if (ExtraCode && ExtraCode[0]) { 358 if (ExtraCode[1] != 0) return true; // Unknown modifier. 359 360 switch (ExtraCode[0]) { 361 default: return true; // Unknown modifier. 362 case 'L': // Write second word of DImode reference. 363 // Verify that this operand has two consecutive registers. 364 if (!MI->getOperand(OpNo).isRegister() || 365 OpNo+1 == MI->getNumOperands() || 366 !MI->getOperand(OpNo+1).isRegister()) 367 return true; 368 ++OpNo; // Return the high-part. 369 break; 370 } 371 } 372 373 printOperand(MI, OpNo); 374 return false; 375} 376 377bool PPCAsmPrinter::PrintAsmMemoryOperand(const MachineInstr *MI, unsigned OpNo, 378 unsigned AsmVariant, 379 const char *ExtraCode) { 380 if (ExtraCode && ExtraCode[0]) 381 return true; // Unknown modifier. 382 printMemRegReg(MI, OpNo); 383 return false; 384} 385 386void PPCAsmPrinter::printPredicateOperand(const MachineInstr *MI, unsigned OpNo, 387 const char *Modifier) { 388 assert(Modifier && "Must specify 'cc' or 'reg' as predicate op modifier!"); 389 unsigned Code = MI->getOperand(OpNo).getImm(); 390 if (!strcmp(Modifier, "cc")) { 391 switch ((PPC::Predicate)Code) { 392 case PPC::PRED_ALWAYS: return; // Don't print anything for always. 393 case PPC::PRED_LT: O << "lt"; return; 394 case PPC::PRED_LE: O << "le"; return; 395 case PPC::PRED_EQ: O << "eq"; return; 396 case PPC::PRED_GE: O << "ge"; return; 397 case PPC::PRED_GT: O << "gt"; return; 398 case PPC::PRED_NE: O << "ne"; return; 399 case PPC::PRED_UN: O << "un"; return; 400 case PPC::PRED_NU: O << "nu"; return; 401 } 402 403 } else { 404 assert(!strcmp(Modifier, "reg") && 405 "Need to specify 'cc' or 'reg' as predicate op modifier!"); 406 // Don't print the register for 'always'. 407 if (Code == PPC::PRED_ALWAYS) return; 408 printOperand(MI, OpNo+1); 409 } 410} 411 412 413/// printMachineInstruction -- Print out a single PowerPC MI in Darwin syntax to 414/// the current output stream. 415/// 416void PPCAsmPrinter::printMachineInstruction(const MachineInstr *MI) { 417 ++EmittedInsts; 418 419 // Check for slwi/srwi mnemonics. 420 if (MI->getOpcode() == PPC::RLWINM) { 421 bool FoundMnemonic = false; 422 unsigned char SH = MI->getOperand(2).getImmedValue(); 423 unsigned char MB = MI->getOperand(3).getImmedValue(); 424 unsigned char ME = MI->getOperand(4).getImmedValue(); 425 if (SH <= 31 && MB == 0 && ME == (31-SH)) { 426 O << "slwi "; FoundMnemonic = true; 427 } 428 if (SH <= 31 && MB == (32-SH) && ME == 31) { 429 O << "srwi "; FoundMnemonic = true; 430 SH = 32-SH; 431 } 432 if (FoundMnemonic) { 433 printOperand(MI, 0); 434 O << ", "; 435 printOperand(MI, 1); 436 O << ", " << (unsigned int)SH << "\n"; 437 return; 438 } 439 } else if (MI->getOpcode() == PPC::OR || MI->getOpcode() == PPC::OR8) { 440 if (MI->getOperand(1).getReg() == MI->getOperand(2).getReg()) { 441 O << "mr "; 442 printOperand(MI, 0); 443 O << ", "; 444 printOperand(MI, 1); 445 O << "\n"; 446 return; 447 } 448 } else if (MI->getOpcode() == PPC::RLDICR) { 449 unsigned char SH = MI->getOperand(2).getImmedValue(); 450 unsigned char ME = MI->getOperand(3).getImmedValue(); 451 // rldicr RA, RS, SH, 63-SH == sldi RA, RS, SH 452 if (63-SH == ME) { 453 O << "sldi "; 454 printOperand(MI, 0); 455 O << ", "; 456 printOperand(MI, 1); 457 O << ", " << (unsigned int)SH << "\n"; 458 return; 459 } 460 } 461 462 if (printInstruction(MI)) 463 return; // Printer was automatically generated 464 465 assert(0 && "Unhandled instruction in asm writer!"); 466 abort(); 467 return; 468} 469 470 471 472std::string DarwinAsmPrinter::getSectionForFunction(const Function &F) const { 473 switch (F.getLinkage()) { 474 default: assert(0 && "Unknown linkage type!"); 475 case Function::ExternalLinkage: 476 case Function::InternalLinkage: return TAI->getTextSection(); 477 case Function::WeakLinkage: 478 case Function::LinkOnceLinkage: 479 return ".section __TEXT,__textcoal_nt,coalesced,pure_instructions"; 480 } 481} 482 483/// runOnMachineFunction - This uses the printMachineInstruction() 484/// method to print assembly for each instruction. 485/// 486bool DarwinAsmPrinter::runOnMachineFunction(MachineFunction &MF) { 487 DW.SetDebugInfo(&getAnalysis<MachineDebugInfo>()); 488 489 SetupMachineFunction(MF); 490 O << "\n\n"; 491 492 // Print out constants referenced by the function 493 EmitConstantPool(MF.getConstantPool()); 494 495 // Print out labels for the function. 496 const Function *F = MF.getFunction(); 497 SwitchToTextSection(getSectionForFunction(*F).c_str(), F); 498 499 switch (F->getLinkage()) { 500 default: assert(0 && "Unknown linkage type!"); 501 case Function::InternalLinkage: // Symbols default to internal. 502 break; 503 case Function::ExternalLinkage: 504 O << "\t.globl\t" << CurrentFnName << "\n"; 505 break; 506 case Function::WeakLinkage: 507 case Function::LinkOnceLinkage: 508 O << "\t.globl\t" << CurrentFnName << "\n"; 509 O << "\t.weak_definition\t" << CurrentFnName << "\n"; 510 break; 511 } 512 EmitAlignment(4, F); 513 O << CurrentFnName << ":\n"; 514 515 // Emit pre-function debug information. 516 DW.BeginFunction(&MF); 517 518 // Print out code for the function. 519 for (MachineFunction::const_iterator I = MF.begin(), E = MF.end(); 520 I != E; ++I) { 521 // Print a label for the basic block. 522 if (I != MF.begin()) { 523 printBasicBlockLabel(I, true); 524 O << '\n'; 525 } 526 for (MachineBasicBlock::const_iterator II = I->begin(), E = I->end(); 527 II != E; ++II) { 528 // Print the assembly for the instruction. 529 O << "\t"; 530 printMachineInstruction(II); 531 } 532 } 533 534 // Print out jump tables referenced by the function. 535 EmitJumpTableInfo(MF.getJumpTableInfo(), MF); 536 537 // Emit post-function debug information. 538 DW.EndFunction(); 539 540 // We didn't modify anything. 541 return false; 542} 543 544 545bool DarwinAsmPrinter::doInitialization(Module &M) { 546 if (Subtarget.isGigaProcessor()) 547 O << "\t.machine ppc970\n"; 548 AsmPrinter::doInitialization(M); 549 550 // Darwin wants symbols to be quoted if they have complex names. 551 Mang->setUseQuotes(true); 552 553 // Prime text sections so they are adjacent. This reduces the likelihood a 554 // large data or debug section causes a branch to exceed 16M limit. 555 SwitchToTextSection(".section __TEXT,__textcoal_nt,coalesced," 556 "pure_instructions"); 557 if (TM.getRelocationModel() == Reloc::PIC_) { 558 SwitchToTextSection(".section __TEXT,__picsymbolstub1,symbol_stubs," 559 "pure_instructions,32"); 560 } else if (TM.getRelocationModel() == Reloc::DynamicNoPIC) { 561 SwitchToTextSection(".section __TEXT,__symbol_stub1,symbol_stubs," 562 "pure_instructions,16"); 563 } 564 SwitchToTextSection(TAI->getTextSection()); 565 566 // Emit initial debug information. 567 DW.BeginModule(&M); 568 return false; 569} 570 571bool DarwinAsmPrinter::doFinalization(Module &M) { 572 const TargetData *TD = TM.getTargetData(); 573 574 // Print out module-level global variables here. 575 for (Module::const_global_iterator I = M.global_begin(), E = M.global_end(); 576 I != E; ++I) { 577 if (!I->hasInitializer()) continue; // External global require no code 578 579 // Check to see if this is a special global used by LLVM, if so, emit it. 580 if (EmitSpecialLLVMGlobal(I)) 581 continue; 582 583 std::string name = Mang->getValueName(I); 584 Constant *C = I->getInitializer(); 585 unsigned Size = TD->getTypeSize(C->getType()); 586 unsigned Align = TD->getPreferredAlignmentLog(I); 587 588 if (C->isNullValue() && /* FIXME: Verify correct */ 589 (I->hasInternalLinkage() || I->hasWeakLinkage() || 590 I->hasLinkOnceLinkage() || 591 (I->hasExternalLinkage() && !I->hasSection()))) { 592 if (Size == 0) Size = 1; // .comm Foo, 0 is undefined, avoid it. 593 if (I->hasExternalLinkage()) { 594 O << "\t.globl " << name << '\n'; 595 O << "\t.zerofill __DATA, __common, " << name << ", " 596 << Size << ", " << Align; 597 } else if (I->hasInternalLinkage()) { 598 SwitchToDataSection("\t.data", I); 599 O << TAI->getLCOMMDirective() << name << "," << Size << "," << Align; 600 } else { 601 SwitchToDataSection("\t.data", I); 602 O << ".comm " << name << "," << Size; 603 } 604 O << "\t\t; '" << I->getName() << "'\n"; 605 } else { 606 switch (I->getLinkage()) { 607 case GlobalValue::LinkOnceLinkage: 608 case GlobalValue::WeakLinkage: 609 O << "\t.globl " << name << '\n' 610 << "\t.weak_definition " << name << '\n'; 611 SwitchToDataSection(".section __DATA,__datacoal_nt,coalesced", I); 612 break; 613 case GlobalValue::AppendingLinkage: 614 // FIXME: appending linkage variables should go into a section of 615 // their name or something. For now, just emit them as external. 616 case GlobalValue::ExternalLinkage: 617 // If external or appending, declare as a global symbol 618 O << "\t.globl " << name << "\n"; 619 // FALL THROUGH 620 case GlobalValue::InternalLinkage: 621 if (I->isConstant()) { 622 const ConstantArray *CVA = dyn_cast<ConstantArray>(C); 623 if (TAI->getCStringSection() && CVA && CVA->isCString()) { 624 SwitchToDataSection(TAI->getCStringSection(), I); 625 break; 626 } 627 } 628 629 SwitchToDataSection("\t.data", I); 630 break; 631 default: 632 std::cerr << "Unknown linkage type!"; 633 abort(); 634 } 635 636 EmitAlignment(Align, I); 637 O << name << ":\t\t\t\t; '" << I->getName() << "'\n"; 638 639 // If the initializer is a extern weak symbol, remember to emit the weak 640 // reference! 641 if (const GlobalValue *GV = dyn_cast<GlobalValue>(C)) 642 if (GV->hasExternalWeakLinkage()) 643 ExtWeakSymbols.insert(Mang->getValueName(GV)); 644 645 EmitGlobalConstant(C); 646 O << '\n'; 647 } 648 } 649 650 if (ExtWeakSymbols.begin() != ExtWeakSymbols.end()) 651 SwitchToDataSection(""); 652 for (std::set<std::string>::iterator i = ExtWeakSymbols.begin(), 653 e = ExtWeakSymbols.end(); i != e; ++i) { 654 O << "\t.weak_reference " << *i << "\n"; 655 } 656 657 bool isPPC64 = TD->getPointerSizeInBits() == 64; 658 659 // Output stubs for dynamically-linked functions 660 if (TM.getRelocationModel() == Reloc::PIC_) { 661 for (std::set<std::string>::iterator i = FnStubs.begin(), e = FnStubs.end(); 662 i != e; ++i) { 663 SwitchToTextSection(".section __TEXT,__picsymbolstub1,symbol_stubs," 664 "pure_instructions,32"); 665 EmitAlignment(4); 666 O << "L" << *i << "$stub:\n"; 667 O << "\t.indirect_symbol " << *i << "\n"; 668 O << "\tmflr r0\n"; 669 O << "\tbcl 20,31,L0$" << *i << "\n"; 670 O << "L0$" << *i << ":\n"; 671 O << "\tmflr r11\n"; 672 O << "\taddis r11,r11,ha16(L" << *i << "$lazy_ptr-L0$" << *i << ")\n"; 673 O << "\tmtlr r0\n"; 674 if (isPPC64) 675 O << "\tldu r12,lo16(L" << *i << "$lazy_ptr-L0$" << *i << ")(r11)\n"; 676 else 677 O << "\tlwzu r12,lo16(L" << *i << "$lazy_ptr-L0$" << *i << ")(r11)\n"; 678 O << "\tmtctr r12\n"; 679 O << "\tbctr\n"; 680 SwitchToDataSection(".lazy_symbol_pointer"); 681 O << "L" << *i << "$lazy_ptr:\n"; 682 O << "\t.indirect_symbol " << *i << "\n"; 683 if (isPPC64) 684 O << "\t.quad dyld_stub_binding_helper\n"; 685 else 686 O << "\t.long dyld_stub_binding_helper\n"; 687 } 688 } else { 689 for (std::set<std::string>::iterator i = FnStubs.begin(), e = FnStubs.end(); 690 i != e; ++i) { 691 SwitchToTextSection(".section __TEXT,__symbol_stub1,symbol_stubs," 692 "pure_instructions,16"); 693 EmitAlignment(4); 694 O << "L" << *i << "$stub:\n"; 695 O << "\t.indirect_symbol " << *i << "\n"; 696 O << "\tlis r11,ha16(L" << *i << "$lazy_ptr)\n"; 697 if (isPPC64) 698 O << "\tldu r12,lo16(L" << *i << "$lazy_ptr)(r11)\n"; 699 else 700 O << "\tlwzu r12,lo16(L" << *i << "$lazy_ptr)(r11)\n"; 701 O << "\tmtctr r12\n"; 702 O << "\tbctr\n"; 703 SwitchToDataSection(".lazy_symbol_pointer"); 704 O << "L" << *i << "$lazy_ptr:\n"; 705 O << "\t.indirect_symbol " << *i << "\n"; 706 if (isPPC64) 707 O << "\t.quad dyld_stub_binding_helper\n"; 708 else 709 O << "\t.long dyld_stub_binding_helper\n"; 710 } 711 } 712 713 O << "\n"; 714 715 // Output stubs for external and common global variables. 716 if (GVStubs.begin() != GVStubs.end()) { 717 SwitchToDataSection(".non_lazy_symbol_pointer"); 718 for (std::set<std::string>::iterator I = GVStubs.begin(), 719 E = GVStubs.end(); I != E; ++I) { 720 O << "L" << *I << "$non_lazy_ptr:\n"; 721 O << "\t.indirect_symbol " << *I << "\n"; 722 if (isPPC64) 723 O << "\t.quad\t0\n"; 724 else 725 O << "\t.long\t0\n"; 726 727 } 728 } 729 730 // Emit initial debug information. 731 DW.EndModule(); 732 733 // Funny Darwin hack: This flag tells the linker that no global symbols 734 // contain code that falls through to other global symbols (e.g. the obvious 735 // implementation of multiple entry points). If this doesn't occur, the 736 // linker can safely perform dead code stripping. Since LLVM never generates 737 // code that does this, it is always safe to set. 738 O << "\t.subsections_via_symbols\n"; 739 740 AsmPrinter::doFinalization(M); 741 return false; // success 742} 743 744 745 746/// createDarwinCodePrinterPass - Returns a pass that prints the PPC assembly 747/// code for a MachineFunction to the given output stream, in a format that the 748/// Darwin assembler can deal with. 749/// 750FunctionPass *llvm::createPPCAsmPrinterPass(std::ostream &o, 751 PPCTargetMachine &tm) { 752 return new DarwinAsmPrinter(o, tm, tm.getTargetAsmInfo()); 753} 754 755