1 //===- llvm/CodeGen/AsmPrinter.h - AsmPrinter Framework ---------*- C++ -*-===// 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 contains a class to be used as the base class for target specific 10 // asm writers. This class primarily handles common functionality used by 11 // all asm writers. 12 // 13 //===----------------------------------------------------------------------===// 14 15 #ifndef LLVM_CODEGEN_ASMPRINTER_H 16 #define LLVM_CODEGEN_ASMPRINTER_H 17 18 #include "llvm/ADT/MapVector.h" 19 #include "llvm/ADT/SmallVector.h" 20 #include "llvm/CodeGen/AsmPrinterHandler.h" 21 #include "llvm/CodeGen/DwarfStringPoolEntry.h" 22 #include "llvm/CodeGen/MachineFunctionPass.h" 23 #include "llvm/IR/InlineAsm.h" 24 #include "llvm/IR/LLVMContext.h" 25 #include "llvm/Support/ErrorHandling.h" 26 #include "llvm/Support/SourceMgr.h" 27 #include <cstdint> 28 #include <memory> 29 #include <utility> 30 #include <vector> 31 32 namespace llvm { 33 34 class BasicBlock; 35 class BlockAddress; 36 class Constant; 37 class ConstantArray; 38 class DataLayout; 39 class DIE; 40 class DIEAbbrev; 41 class DwarfDebug; 42 class GCMetadataPrinter; 43 class GCStrategy; 44 class GlobalIndirectSymbol; 45 class GlobalObject; 46 class GlobalValue; 47 class GlobalVariable; 48 class MachineBasicBlock; 49 class MachineConstantPoolValue; 50 class MachineDominatorTree; 51 class MachineFunction; 52 class MachineInstr; 53 class MachineJumpTableInfo; 54 class MachineLoopInfo; 55 class MachineModuleInfo; 56 class MachineOptimizationRemarkEmitter; 57 class MCAsmInfo; 58 class MCCFIInstruction; 59 class MCContext; 60 class MCExpr; 61 class MCInst; 62 class MCSection; 63 class MCStreamer; 64 class MCSubtargetInfo; 65 class MCSymbol; 66 class MCTargetOptions; 67 class MDNode; 68 class Module; 69 class PseudoProbeHandler; 70 class raw_ostream; 71 class StackMaps; 72 class StringRef; 73 class TargetLoweringObjectFile; 74 class TargetMachine; 75 class Twine; 76 77 namespace remarks { 78 class RemarkStreamer; 79 } 80 81 /// This class is intended to be used as a driving class for all asm writers. 82 class AsmPrinter : public MachineFunctionPass { 83 public: 84 /// Target machine description. 85 TargetMachine &TM; 86 87 /// Target Asm Printer information. 88 const MCAsmInfo *MAI; 89 90 /// This is the context for the output file that we are streaming. This owns 91 /// all of the global MC-related objects for the generated translation unit. 92 MCContext &OutContext; 93 94 /// This is the MCStreamer object for the file we are generating. This 95 /// contains the transient state for the current translation unit that we are 96 /// generating (such as the current section etc). 97 std::unique_ptr<MCStreamer> OutStreamer; 98 99 /// The current machine function. 100 MachineFunction *MF = nullptr; 101 102 /// This is a pointer to the current MachineModuleInfo. 103 MachineModuleInfo *MMI = nullptr; 104 105 /// This is a pointer to the current MachineDominatorTree. 106 MachineDominatorTree *MDT = nullptr; 107 108 /// This is a pointer to the current MachineLoopInfo. 109 MachineLoopInfo *MLI = nullptr; 110 111 /// Optimization remark emitter. 112 MachineOptimizationRemarkEmitter *ORE; 113 114 /// The symbol for the entry in __patchable_function_entires. 115 MCSymbol *CurrentPatchableFunctionEntrySym = nullptr; 116 117 /// The symbol for the current function. This is recalculated at the beginning 118 /// of each call to runOnMachineFunction(). 119 MCSymbol *CurrentFnSym = nullptr; 120 121 /// The symbol for the current function descriptor on AIX. This is created 122 /// at the beginning of each call to SetupMachineFunction(). 123 MCSymbol *CurrentFnDescSym = nullptr; 124 125 /// The symbol used to represent the start of the current function for the 126 /// purpose of calculating its size (e.g. using the .size directive). By 127 /// default, this is equal to CurrentFnSym. 128 MCSymbol *CurrentFnSymForSize = nullptr; 129 130 /// Map a basic block section ID to the begin and end symbols of that section 131 /// which determine the section's range. 132 struct MBBSectionRange { 133 MCSymbol *BeginLabel, *EndLabel; 134 }; 135 136 MapVector<unsigned, MBBSectionRange> MBBSectionRanges; 137 138 /// Map global GOT equivalent MCSymbols to GlobalVariables and keep track of 139 /// its number of uses by other globals. 140 using GOTEquivUsePair = std::pair<const GlobalVariable *, unsigned>; 141 MapVector<const MCSymbol *, GOTEquivUsePair> GlobalGOTEquivs; 142 143 /// struct HandlerInfo and Handlers permit users or target extended 144 /// AsmPrinter to add their own handlers. 145 struct HandlerInfo { 146 std::unique_ptr<AsmPrinterHandler> Handler; 147 const char *TimerName; 148 const char *TimerDescription; 149 const char *TimerGroupName; 150 const char *TimerGroupDescription; 151 152 HandlerInfo(std::unique_ptr<AsmPrinterHandler> Handler, 153 const char *TimerName, const char *TimerDescription, 154 const char *TimerGroupName, const char *TimerGroupDescription) 155 : Handler(std::move(Handler)), TimerName(TimerName), 156 TimerDescription(TimerDescription), TimerGroupName(TimerGroupName), 157 TimerGroupDescription(TimerGroupDescription) {} 158 }; 159 160 private: 161 MCSymbol *CurrentFnEnd = nullptr; 162 163 /// Map a basic block section ID to the exception symbol associated with that 164 /// section. Map entries are assigned and looked up via 165 /// AsmPrinter::getMBBExceptionSym. 166 DenseMap<unsigned, MCSymbol *> MBBSectionExceptionSyms; 167 168 // The symbol used to represent the start of the current BB section of the 169 // function. This is used to calculate the size of the BB section. 170 MCSymbol *CurrentSectionBeginSym = nullptr; 171 172 // The garbage collection metadata printer table. 173 void *GCMetadataPrinters = nullptr; // Really a DenseMap. 174 175 /// Emit comments in assembly output if this is true. 176 bool VerboseAsm; 177 178 static char ID; 179 180 protected: 181 MCSymbol *CurrentFnBegin = nullptr; 182 183 /// A vector of all debug/EH info emitters we should use. This vector 184 /// maintains ownership of the emitters. 185 std::vector<HandlerInfo> Handlers; 186 size_t NumUserHandlers = 0; 187 188 public: 189 struct SrcMgrDiagInfo { 190 SourceMgr SrcMgr; 191 std::vector<const MDNode *> LocInfos; 192 LLVMContext::InlineAsmDiagHandlerTy DiagHandler; 193 void *DiagContext; 194 }; 195 196 private: 197 /// If generated on the fly this own the instance. 198 std::unique_ptr<MachineDominatorTree> OwnedMDT; 199 200 /// If generated on the fly this own the instance. 201 std::unique_ptr<MachineLoopInfo> OwnedMLI; 202 203 /// Structure for generating diagnostics for inline assembly. Only initialised 204 /// when necessary. 205 mutable std::unique_ptr<SrcMgrDiagInfo> DiagInfo; 206 207 /// If the target supports dwarf debug info, this pointer is non-null. 208 DwarfDebug *DD = nullptr; 209 210 /// A handler that supports pseudo probe emission with embedded inline 211 /// context. 212 PseudoProbeHandler *PP = nullptr; 213 214 /// If the current module uses dwarf CFI annotations strictly for debugging. 215 bool isCFIMoveForDebugging = false; 216 217 protected: 218 explicit AsmPrinter(TargetMachine &TM, std::unique_ptr<MCStreamer> Streamer); 219 220 public: 221 ~AsmPrinter() override; 222 223 DwarfDebug *getDwarfDebug() { return DD; } 224 DwarfDebug *getDwarfDebug() const { return DD; } 225 226 uint16_t getDwarfVersion() const; 227 void setDwarfVersion(uint16_t Version); 228 229 bool isDwarf64() const; 230 231 /// Returns 4 for DWARF32 and 8 for DWARF64. 232 unsigned int getDwarfOffsetByteSize() const; 233 234 /// Returns 4 for DWARF32 and 12 for DWARF64. 235 unsigned int getUnitLengthFieldByteSize() const; 236 237 bool isPositionIndependent() const; 238 239 /// Return true if assembly output should contain comments. 240 bool isVerbose() const { return VerboseAsm; } 241 242 /// Return a unique ID for the current function. 243 unsigned getFunctionNumber() const; 244 245 /// Return symbol for the function pseudo stack if the stack frame is not a 246 /// register based. 247 virtual const MCSymbol *getFunctionFrameSymbol() const { return nullptr; } 248 249 MCSymbol *getFunctionBegin() const { return CurrentFnBegin; } 250 MCSymbol *getFunctionEnd() const { return CurrentFnEnd; } 251 252 // Return the exception symbol associated with the MBB section containing a 253 // given basic block. 254 MCSymbol *getMBBExceptionSym(const MachineBasicBlock &MBB); 255 256 /// Return information about object file lowering. 257 const TargetLoweringObjectFile &getObjFileLowering() const; 258 259 /// Return information about data layout. 260 const DataLayout &getDataLayout() const; 261 262 /// Return the pointer size from the TargetMachine 263 unsigned getPointerSize() const; 264 265 /// Return information about subtarget. 266 const MCSubtargetInfo &getSubtargetInfo() const; 267 268 void EmitToStreamer(MCStreamer &S, const MCInst &Inst); 269 270 /// Emits inital debug location directive. 271 void emitInitialRawDwarfLocDirective(const MachineFunction &MF); 272 273 /// Return the current section we are emitting to. 274 const MCSection *getCurrentSection() const; 275 276 void getNameWithPrefix(SmallVectorImpl<char> &Name, 277 const GlobalValue *GV) const; 278 279 MCSymbol *getSymbol(const GlobalValue *GV) const; 280 281 /// Similar to getSymbol() but preferred for references. On ELF, this uses a 282 /// local symbol if a reference to GV is guaranteed to be resolved to the 283 /// definition in the same module. 284 MCSymbol *getSymbolPreferLocal(const GlobalValue &GV) const; 285 286 //===------------------------------------------------------------------===// 287 // XRay instrumentation implementation. 288 //===------------------------------------------------------------------===// 289 public: 290 // This describes the kind of sled we're storing in the XRay table. 291 enum class SledKind : uint8_t { 292 FUNCTION_ENTER = 0, 293 FUNCTION_EXIT = 1, 294 TAIL_CALL = 2, 295 LOG_ARGS_ENTER = 3, 296 CUSTOM_EVENT = 4, 297 TYPED_EVENT = 5, 298 }; 299 300 // The table will contain these structs that point to the sled, the function 301 // containing the sled, and what kind of sled (and whether they should always 302 // be instrumented). We also use a version identifier that the runtime can use 303 // to decide what to do with the sled, depending on the version of the sled. 304 struct XRayFunctionEntry { 305 const MCSymbol *Sled; 306 const MCSymbol *Function; 307 SledKind Kind; 308 bool AlwaysInstrument; 309 const class Function *Fn; 310 uint8_t Version; 311 312 void emit(int, MCStreamer *) const; 313 }; 314 315 // All the sleds to be emitted. 316 SmallVector<XRayFunctionEntry, 4> Sleds; 317 318 // Helper function to record a given XRay sled. 319 void recordSled(MCSymbol *Sled, const MachineInstr &MI, SledKind Kind, 320 uint8_t Version = 0); 321 322 /// Emit a table with all XRay instrumentation points. 323 void emitXRayTable(); 324 325 void emitPatchableFunctionEntries(); 326 327 //===------------------------------------------------------------------===// 328 // MachineFunctionPass Implementation. 329 //===------------------------------------------------------------------===// 330 331 /// Record analysis usage. 332 void getAnalysisUsage(AnalysisUsage &AU) const override; 333 334 /// Set up the AsmPrinter when we are working on a new module. If your pass 335 /// overrides this, it must make sure to explicitly call this implementation. 336 bool doInitialization(Module &M) override; 337 338 /// Shut down the asmprinter. If you override this in your pass, you must make 339 /// sure to call it explicitly. 340 bool doFinalization(Module &M) override; 341 342 /// Emit the specified function out to the OutStreamer. 343 bool runOnMachineFunction(MachineFunction &MF) override { 344 SetupMachineFunction(MF); 345 emitFunctionBody(); 346 return false; 347 } 348 349 //===------------------------------------------------------------------===// 350 // Coarse grained IR lowering routines. 351 //===------------------------------------------------------------------===// 352 353 /// This should be called when a new MachineFunction is being processed from 354 /// runOnMachineFunction. 355 virtual void SetupMachineFunction(MachineFunction &MF); 356 357 /// This method emits the body and trailer for a function. 358 void emitFunctionBody(); 359 360 void emitCFIInstruction(const MachineInstr &MI); 361 362 void emitFrameAlloc(const MachineInstr &MI); 363 364 void emitStackSizeSection(const MachineFunction &MF); 365 366 void emitBBAddrMapSection(const MachineFunction &MF); 367 368 void emitPseudoProbe(const MachineInstr &MI); 369 370 void emitRemarksSection(remarks::RemarkStreamer &RS); 371 372 enum CFIMoveType { CFI_M_None, CFI_M_EH, CFI_M_Debug }; 373 CFIMoveType needsCFIMoves() const; 374 375 /// Returns false if needsCFIMoves() == CFI_M_EH for any function 376 /// in the module. 377 bool needsOnlyDebugCFIMoves() const { return isCFIMoveForDebugging; } 378 379 bool needsSEHMoves(); 380 381 /// Print to the current output stream assembly representations of the 382 /// constants in the constant pool MCP. This is used to print out constants 383 /// which have been "spilled to memory" by the code generator. 384 virtual void emitConstantPool(); 385 386 /// Print assembly representations of the jump tables used by the current 387 /// function to the current output stream. 388 virtual void emitJumpTableInfo(); 389 390 /// Emit the specified global variable to the .s file. 391 virtual void emitGlobalVariable(const GlobalVariable *GV); 392 393 /// Check to see if the specified global is a special global used by LLVM. If 394 /// so, emit it and return true, otherwise do nothing and return false. 395 bool emitSpecialLLVMGlobal(const GlobalVariable *GV); 396 397 /// `llvm.global_ctors` and `llvm.global_dtors` are arrays of Structor 398 /// structs. 399 /// 400 /// Priority - init priority 401 /// Func - global initialization or global clean-up function 402 /// ComdatKey - associated data 403 struct Structor { 404 int Priority = 0; 405 Constant *Func = nullptr; 406 GlobalValue *ComdatKey = nullptr; 407 408 Structor() = default; 409 }; 410 411 /// This method gathers an array of Structors and then sorts them out by 412 /// Priority. 413 /// @param List The initializer of `llvm.global_ctors` or `llvm.global_dtors` 414 /// array. 415 /// @param[out] Structors Sorted Structor structs by Priority. 416 void preprocessXXStructorList(const DataLayout &DL, const Constant *List, 417 SmallVector<Structor, 8> &Structors); 418 419 /// This method emits `llvm.global_ctors` or `llvm.global_dtors` list. 420 virtual void emitXXStructorList(const DataLayout &DL, const Constant *List, 421 bool IsCtor); 422 423 /// Emit an alignment directive to the specified power of two boundary. If a 424 /// global value is specified, and if that global has an explicit alignment 425 /// requested, it will override the alignment request if required for 426 /// correctness. 427 void emitAlignment(Align Alignment, const GlobalObject *GV = nullptr) const; 428 429 /// Lower the specified LLVM Constant to an MCExpr. 430 virtual const MCExpr *lowerConstant(const Constant *CV); 431 432 /// Print a general LLVM constant to the .s file. 433 void emitGlobalConstant(const DataLayout &DL, const Constant *CV); 434 435 /// Unnamed constant global variables solely contaning a pointer to 436 /// another globals variable act like a global variable "proxy", or GOT 437 /// equivalents, i.e., it's only used to hold the address of the latter. One 438 /// optimization is to replace accesses to these proxies by using the GOT 439 /// entry for the final global instead. Hence, we select GOT equivalent 440 /// candidates among all the module global variables, avoid emitting them 441 /// unnecessarily and finally replace references to them by pc relative 442 /// accesses to GOT entries. 443 void computeGlobalGOTEquivs(Module &M); 444 445 /// Constant expressions using GOT equivalent globals may not be 446 /// eligible for PC relative GOT entry conversion, in such cases we need to 447 /// emit the proxies we previously omitted in EmitGlobalVariable. 448 void emitGlobalGOTEquivs(); 449 450 /// Emit the stack maps. 451 void emitStackMaps(StackMaps &SM); 452 453 //===------------------------------------------------------------------===// 454 // Overridable Hooks 455 //===------------------------------------------------------------------===// 456 457 void addAsmPrinterHandler(HandlerInfo Handler) { 458 Handlers.insert(Handlers.begin(), std::move(Handler)); 459 NumUserHandlers++; 460 } 461 462 // Targets can, or in the case of EmitInstruction, must implement these to 463 // customize output. 464 465 /// This virtual method can be overridden by targets that want to emit 466 /// something at the start of their file. 467 virtual void emitStartOfAsmFile(Module &) {} 468 469 /// This virtual method can be overridden by targets that want to emit 470 /// something at the end of their file. 471 virtual void emitEndOfAsmFile(Module &) {} 472 473 /// Targets can override this to emit stuff before the first basic block in 474 /// the function. 475 virtual void emitFunctionBodyStart() {} 476 477 /// Targets can override this to emit stuff after the last basic block in the 478 /// function. 479 virtual void emitFunctionBodyEnd() {} 480 481 /// Targets can override this to emit stuff at the start of a basic block. 482 /// By default, this method prints the label for the specified 483 /// MachineBasicBlock, an alignment (if present) and a comment describing it 484 /// if appropriate. 485 virtual void emitBasicBlockStart(const MachineBasicBlock &MBB); 486 487 /// Targets can override this to emit stuff at the end of a basic block. 488 virtual void emitBasicBlockEnd(const MachineBasicBlock &MBB); 489 490 /// Targets should implement this to emit instructions. 491 virtual void emitInstruction(const MachineInstr *) { 492 llvm_unreachable("EmitInstruction not implemented"); 493 } 494 495 /// Return the symbol for the specified constant pool entry. 496 virtual MCSymbol *GetCPISymbol(unsigned CPID) const; 497 498 virtual void emitFunctionEntryLabel(); 499 500 virtual void emitFunctionDescriptor() { 501 llvm_unreachable("Function descriptor is target-specific."); 502 } 503 504 virtual void emitMachineConstantPoolValue(MachineConstantPoolValue *MCPV); 505 506 /// Targets can override this to change how global constants that are part of 507 /// a C++ static/global constructor list are emitted. 508 virtual void emitXXStructor(const DataLayout &DL, const Constant *CV) { 509 emitGlobalConstant(DL, CV); 510 } 511 512 /// Return true if the basic block has exactly one predecessor and the control 513 /// transfer mechanism between the predecessor and this block is a 514 /// fall-through. 515 virtual bool 516 isBlockOnlyReachableByFallthrough(const MachineBasicBlock *MBB) const; 517 518 /// Targets can override this to customize the output of IMPLICIT_DEF 519 /// instructions in verbose mode. 520 virtual void emitImplicitDef(const MachineInstr *MI) const; 521 522 /// Emit N NOP instructions. 523 void emitNops(unsigned N); 524 525 //===------------------------------------------------------------------===// 526 // Symbol Lowering Routines. 527 //===------------------------------------------------------------------===// 528 529 MCSymbol *createTempSymbol(const Twine &Name) const; 530 531 /// Return the MCSymbol for a private symbol with global value name as its 532 /// base, with the specified suffix. 533 MCSymbol *getSymbolWithGlobalValueBase(const GlobalValue *GV, 534 StringRef Suffix) const; 535 536 /// Return the MCSymbol for the specified ExternalSymbol. 537 MCSymbol *GetExternalSymbolSymbol(StringRef Sym) const; 538 539 /// Return the symbol for the specified jump table entry. 540 MCSymbol *GetJTISymbol(unsigned JTID, bool isLinkerPrivate = false) const; 541 542 /// Return the symbol for the specified jump table .set 543 /// FIXME: privatize to AsmPrinter. 544 MCSymbol *GetJTSetSymbol(unsigned UID, unsigned MBBID) const; 545 546 /// Return the MCSymbol used to satisfy BlockAddress uses of the specified 547 /// basic block. 548 MCSymbol *GetBlockAddressSymbol(const BlockAddress *BA) const; 549 MCSymbol *GetBlockAddressSymbol(const BasicBlock *BB) const; 550 551 //===------------------------------------------------------------------===// 552 // Emission Helper Routines. 553 //===------------------------------------------------------------------===// 554 555 /// This is just convenient handler for printing offsets. 556 void printOffset(int64_t Offset, raw_ostream &OS) const; 557 558 /// Emit a byte directive and value. 559 void emitInt8(int Value) const; 560 561 /// Emit a short directive and value. 562 void emitInt16(int Value) const; 563 564 /// Emit a long directive and value. 565 void emitInt32(int Value) const; 566 567 /// Emit a long long directive and value. 568 void emitInt64(uint64_t Value) const; 569 570 /// Emit something like ".long Hi-Lo" where the size in bytes of the directive 571 /// is specified by Size and Hi/Lo specify the labels. This implicitly uses 572 /// .set if it is available. 573 void emitLabelDifference(const MCSymbol *Hi, const MCSymbol *Lo, 574 unsigned Size) const; 575 576 /// Emit something like ".uleb128 Hi-Lo". 577 void emitLabelDifferenceAsULEB128(const MCSymbol *Hi, 578 const MCSymbol *Lo) const; 579 580 /// Emit something like ".long Label+Offset" where the size in bytes of the 581 /// directive is specified by Size and Label specifies the label. This 582 /// implicitly uses .set if it is available. 583 void emitLabelPlusOffset(const MCSymbol *Label, uint64_t Offset, 584 unsigned Size, bool IsSectionRelative = false) const; 585 586 /// Emit something like ".long Label" where the size in bytes of the directive 587 /// is specified by Size and Label specifies the label. 588 void emitLabelReference(const MCSymbol *Label, unsigned Size, 589 bool IsSectionRelative = false) const { 590 emitLabelPlusOffset(Label, 0, Size, IsSectionRelative); 591 } 592 593 //===------------------------------------------------------------------===// 594 // Dwarf Emission Helper Routines 595 //===------------------------------------------------------------------===// 596 597 /// Emit the specified signed leb128 value. 598 void emitSLEB128(int64_t Value, const char *Desc = nullptr) const; 599 600 /// Emit the specified unsigned leb128 value. 601 void emitULEB128(uint64_t Value, const char *Desc = nullptr, 602 unsigned PadTo = 0) const; 603 604 /// Emit a .byte 42 directive that corresponds to an encoding. If verbose 605 /// assembly output is enabled, we output comments describing the encoding. 606 /// Desc is a string saying what the encoding is specifying (e.g. "LSDA"). 607 void emitEncodingByte(unsigned Val, const char *Desc = nullptr) const; 608 609 /// Return the size of the encoding in bytes. 610 unsigned GetSizeOfEncodedValue(unsigned Encoding) const; 611 612 /// Emit reference to a ttype global with a specified encoding. 613 virtual void emitTTypeReference(const GlobalValue *GV, unsigned Encoding); 614 615 /// Emit a reference to a symbol for use in dwarf. Different object formats 616 /// represent this in different ways. Some use a relocation others encode 617 /// the label offset in its section. 618 void emitDwarfSymbolReference(const MCSymbol *Label, 619 bool ForceOffset = false) const; 620 621 /// Emit the 4- or 8-byte offset of a string from the start of its section. 622 /// 623 /// When possible, emit a DwarfStringPool section offset without any 624 /// relocations, and without using the symbol. Otherwise, defers to \a 625 /// emitDwarfSymbolReference(). 626 /// 627 /// The length of the emitted value depends on the DWARF format. 628 void emitDwarfStringOffset(DwarfStringPoolEntry S) const; 629 630 /// Emit the 4-or 8-byte offset of a string from the start of its section. 631 void emitDwarfStringOffset(DwarfStringPoolEntryRef S) const { 632 emitDwarfStringOffset(S.getEntry()); 633 } 634 635 /// Emit something like ".long Label + Offset" or ".quad Label + Offset" 636 /// depending on the DWARF format. 637 void emitDwarfOffset(const MCSymbol *Label, uint64_t Offset) const; 638 639 /// Emit 32- or 64-bit value depending on the DWARF format. 640 void emitDwarfLengthOrOffset(uint64_t Value) const; 641 642 /// Emit a special value of 0xffffffff if producing 64-bit debugging info. 643 void maybeEmitDwarf64Mark() const; 644 645 /// Emit a unit length field. The actual format, DWARF32 or DWARF64, is chosen 646 /// according to the settings. 647 void emitDwarfUnitLength(uint64_t Length, const Twine &Comment) const; 648 649 /// Emit a unit length field. The actual format, DWARF32 or DWARF64, is chosen 650 /// according to the settings. 651 void emitDwarfUnitLength(const MCSymbol *Hi, const MCSymbol *Lo, 652 const Twine &Comment) const; 653 654 /// Emit reference to a call site with a specified encoding 655 void emitCallSiteOffset(const MCSymbol *Hi, const MCSymbol *Lo, 656 unsigned Encoding) const; 657 /// Emit an integer value corresponding to the call site encoding 658 void emitCallSiteValue(uint64_t Value, unsigned Encoding) const; 659 660 /// Get the value for DW_AT_APPLE_isa. Zero if no isa encoding specified. 661 virtual unsigned getISAEncoding() { return 0; } 662 663 /// Emit the directive and value for debug thread local expression 664 /// 665 /// \p Value - The value to emit. 666 /// \p Size - The size of the integer (in bytes) to emit. 667 virtual void emitDebugValue(const MCExpr *Value, unsigned Size) const; 668 669 //===------------------------------------------------------------------===// 670 // Dwarf Lowering Routines 671 //===------------------------------------------------------------------===// 672 673 /// Emit frame instruction to describe the layout of the frame. 674 void emitCFIInstruction(const MCCFIInstruction &Inst) const; 675 676 /// Emit Dwarf abbreviation table. 677 template <typename T> void emitDwarfAbbrevs(const T &Abbrevs) const { 678 // For each abbreviation. 679 for (const auto &Abbrev : Abbrevs) 680 emitDwarfAbbrev(*Abbrev); 681 682 // Mark end of abbreviations. 683 emitULEB128(0, "EOM(3)"); 684 } 685 686 void emitDwarfAbbrev(const DIEAbbrev &Abbrev) const; 687 688 /// Recursively emit Dwarf DIE tree. 689 void emitDwarfDIE(const DIE &Die) const; 690 691 //===------------------------------------------------------------------===// 692 // Inline Asm Support 693 //===------------------------------------------------------------------===// 694 695 // These are hooks that targets can override to implement inline asm 696 // support. These should probably be moved out of AsmPrinter someday. 697 698 /// Print information related to the specified machine instr that is 699 /// independent of the operand, and may be independent of the instr itself. 700 /// This can be useful for portably encoding the comment character or other 701 /// bits of target-specific knowledge into the asmstrings. The syntax used is 702 /// ${:comment}. Targets can override this to add support for their own 703 /// strange codes. 704 virtual void PrintSpecial(const MachineInstr *MI, raw_ostream &OS, 705 const char *Code) const; 706 707 /// Print the MachineOperand as a symbol. Targets with complex handling of 708 /// symbol references should override the base implementation. 709 virtual void PrintSymbolOperand(const MachineOperand &MO, raw_ostream &OS); 710 711 /// Print the specified operand of MI, an INLINEASM instruction, using the 712 /// specified assembler variant. Targets should override this to format as 713 /// appropriate. This method can return true if the operand is erroneous. 714 virtual bool PrintAsmOperand(const MachineInstr *MI, unsigned OpNo, 715 const char *ExtraCode, raw_ostream &OS); 716 717 /// Print the specified operand of MI, an INLINEASM instruction, using the 718 /// specified assembler variant as an address. Targets should override this to 719 /// format as appropriate. This method can return true if the operand is 720 /// erroneous. 721 virtual bool PrintAsmMemoryOperand(const MachineInstr *MI, unsigned OpNo, 722 const char *ExtraCode, raw_ostream &OS); 723 724 /// Let the target do anything it needs to do before emitting inlineasm. 725 /// \p StartInfo - the subtarget info before parsing inline asm 726 virtual void emitInlineAsmStart() const; 727 728 /// Let the target do anything it needs to do after emitting inlineasm. 729 /// This callback can be used restore the original mode in case the 730 /// inlineasm contains directives to switch modes. 731 /// \p StartInfo - the original subtarget info before inline asm 732 /// \p EndInfo - the final subtarget info after parsing the inline asm, 733 /// or NULL if the value is unknown. 734 virtual void emitInlineAsmEnd(const MCSubtargetInfo &StartInfo, 735 const MCSubtargetInfo *EndInfo) const; 736 737 /// This emits visibility information about symbol, if this is supported by 738 /// the target. 739 void emitVisibility(MCSymbol *Sym, unsigned Visibility, 740 bool IsDefinition = true) const; 741 742 /// This emits linkage information about \p GVSym based on \p GV, if this is 743 /// supported by the target. 744 virtual void emitLinkage(const GlobalValue *GV, MCSymbol *GVSym) const; 745 746 /// Return the alignment for the specified \p GV. 747 static Align getGVAlignment(const GlobalObject *GV, const DataLayout &DL, 748 Align InAlign = Align(1)); 749 750 private: 751 /// Private state for PrintSpecial() 752 // Assign a unique ID to this machine instruction. 753 mutable const MachineInstr *LastMI = nullptr; 754 mutable unsigned LastFn = 0; 755 mutable unsigned Counter = ~0U; 756 757 /// This method emits the header for the current function. 758 virtual void emitFunctionHeader(); 759 760 /// This method emits a comment next to header for the current function. 761 virtual void emitFunctionHeaderComment(); 762 763 /// Emit a blob of inline asm to the output streamer. 764 void 765 emitInlineAsm(StringRef Str, const MCSubtargetInfo &STI, 766 const MCTargetOptions &MCOptions, 767 const MDNode *LocMDNode = nullptr, 768 InlineAsm::AsmDialect AsmDialect = InlineAsm::AD_ATT) const; 769 770 /// This method formats and emits the specified machine instruction that is an 771 /// inline asm. 772 void emitInlineAsm(const MachineInstr *MI) const; 773 774 /// Add inline assembly info to the diagnostics machinery, so we can 775 /// emit file and position info. Returns SrcMgr memory buffer position. 776 unsigned addInlineAsmDiagBuffer(StringRef AsmStr, 777 const MDNode *LocMDNode) const; 778 779 //===------------------------------------------------------------------===// 780 // Internal Implementation Details 781 //===------------------------------------------------------------------===// 782 783 void emitJumpTableEntry(const MachineJumpTableInfo *MJTI, 784 const MachineBasicBlock *MBB, unsigned uid) const; 785 void emitLLVMUsedList(const ConstantArray *InitList); 786 /// Emit llvm.ident metadata in an '.ident' directive. 787 void emitModuleIdents(Module &M); 788 /// Emit bytes for llvm.commandline metadata. 789 void emitModuleCommandLines(Module &M); 790 791 GCMetadataPrinter *GetOrCreateGCPrinter(GCStrategy &S); 792 /// Emit GlobalAlias or GlobalIFunc. 793 void emitGlobalIndirectSymbol(Module &M, const GlobalIndirectSymbol &GIS); 794 795 /// This method decides whether the specified basic block requires a label. 796 bool shouldEmitLabelForBasicBlock(const MachineBasicBlock &MBB) const; 797 }; 798 799 } // end namespace llvm 800 801 #endif // LLVM_CODEGEN_ASMPRINTER_H 802