21 #include "llvm/Config/config.h" 53 bool UseRelocs =
false;
74 if (MinInsnLength == 1)
76 if (AddrDelta % MinInsnLength != 0) {
80 return AddrDelta / MinInsnLength;
110 .addLineEntry(LineEntry, Section);
137 static inline const MCExpr *
153 unsigned FileNum = 1;
154 unsigned LastLine = 1;
158 unsigned Discriminator = 0;
163 int64_t LineDelta =
static_cast<int64_t
>(LineEntry.getLine()) - LastLine;
165 if (FileNum != LineEntry.getFileNum()) {
166 FileNum = LineEntry.getFileNum();
170 if (Column != LineEntry.getColumn()) {
171 Column = LineEntry.getColumn();
175 if (Discriminator != LineEntry.getDiscriminator() &&
177 Discriminator = LineEntry.getDiscriminator();
184 if (Isa != LineEntry.getIsa()) {
185 Isa = LineEntry.getIsa();
190 Flags = LineEntry.getFlags();
198 MCOS->
EmitIntValue(dwarf::DW_LNS_set_epilogue_begin, 1);
200 MCSymbol *Label = LineEntry.getLabel();
210 LastLine = LineEntry.getLine();
241 if (LineTables.empty())
253 for (
const auto &CUIDTablePair : LineTables) {
254 CUIDTablePair.second.EmitCU(MCOS, Params, LineStr);
263 if (Header.MCDwarfFiles.empty())
267 MCOS.
EmitLabel(Header.Emit(&MCOS, Params,
None, NoLineStr).second);
270 std::pair<MCSymbol *, MCSymbol *>
273 static const char StandardOpcodeLengths[] = {
297 assert(!isa<MCSymbolRefExpr>(Expr));
319 LineStrings.
write((uint8_t *)Data.
data());
333 void MCDwarfLineTableHeader::emitV2FileDirTables(
MCStreamer *MCOS)
const {
335 for (
auto &Dir : MCDwarfDirs) {
342 for (
unsigned i = 1; i < MCDwarfFiles.size(); i++) {
354 bool EmitMD5,
bool HasSource,
368 Cksum->
Bytes.size()));
381 void MCDwarfLineTableHeader::emitV5FileDirTables(
390 : dwarf::DW_FORM_string);
394 CompilationDir.
empty() ? CtxCompilationDir :
StringRef(CompilationDir);
397 LineStr->
emitRef(MCOS, CompDir);
398 for (
const auto &Dir : MCDwarfDirs)
404 for (
const auto &Dir : MCDwarfDirs) {
413 uint64_t Entries = 2;
421 : dwarf::DW_FORM_string);
431 : dwarf::DW_FORM_string);
439 HasAllMD5, HasSource, LineStr);
440 for (
unsigned i = 1; i < MCDwarfFiles.size(); ++i)
444 std::pair<MCSymbol *, MCSymbol *>
471 unsigned PreHeaderLengthBytes = 4 + 2;
474 if (LineTableVersion >= 5) {
477 PreHeaderLengthBytes += 2;
487 (PreHeaderLengthBytes + 4)),
495 if (LineTableVersion >= 4)
503 for (
char Length : StandardOpcodeLengths)
508 if (LineTableVersion >= 5)
511 emitV2FileDirTables(MCOS);
517 return std::make_pair(LineStartSym, LineEndSym);
523 MCSymbol *LineEndSym = Header.Emit(MCOS, Params, LineStr).second;
526 for (
const auto &LineSec : MCLineSections.getMCLineEntries())
538 unsigned FileNumber) {
539 return Header.tryGetFile(Directory, FileName, Checksum, Source, FileNumber);
547 unsigned FileNumber) {
548 if (Directory == CompilationDir)
550 if (FileName.
empty()) {
551 FileName =
"<stdin>";
557 if (MCDwarfFiles.empty()) {
558 trackMD5Usage(Checksum);
559 HasSource = (Source !=
None);
561 if (FileNumber == 0) {
564 FileNumber = MCDwarfFiles.empty() ? 1 : MCDwarfFiles.size();
566 auto IterBool = SourceIdMap.
insert(
569 if (!IterBool.second)
570 return IterBool.first->second;
573 if (FileNumber >= MCDwarfFiles.size())
574 MCDwarfFiles.resize(FileNumber + 1);
580 if (!File.
Name.empty())
581 return make_error<StringError>(
"file number already allocated",
585 if (HasSource != (Source !=
None))
586 return make_error<StringError>(
"inconsistent use of embedded source",
589 if (Directory.
empty()) {
592 if (!tFileName.
empty()) {
594 if (!Directory.
empty())
595 FileName = tFileName;
602 if (Directory.
empty()) {
607 for (
unsigned End = MCDwarfDirs.size(); DirIndex < End; DirIndex++) {
608 if (Directory == MCDwarfDirs[DirIndex])
611 if (DirIndex >= MCDwarfDirs.size())
612 MCDwarfDirs.push_back(Directory);
620 File.
Name = FileName;
623 trackMD5Usage(Checksum);
634 int64_t LineDelta, uint64_t AddrDelta) {
650 int64_t LineDelta, uint64_t AddrDelta,
652 uint64_t Temp, Opcode;
653 bool NeedCopy =
false;
656 uint64_t MaxSpecialAddrDelta =
SpecialAddr(Params, 255);
665 if (AddrDelta == MaxSpecialAddrDelta)
666 OS <<
char(dwarf::DW_LNS_const_add_pc);
667 else if (AddrDelta) {
668 OS << char(dwarf::DW_LNS_advance_pc);
671 OS << char(dwarf::DW_LNS_extended_op);
673 OS << char(dwarf::DW_LNE_end_sequence);
684 OS <<
char(dwarf::DW_LNS_advance_line);
693 if (LineDelta == 0 && AddrDelta == 0) {
694 OS <<
char(dwarf::DW_LNS_copy);
702 if (AddrDelta < 256 + MaxSpecialAddrDelta) {
711 Opcode = Temp + (AddrDelta - MaxSpecialAddrDelta) * Params.
DWARF2LineRange;
713 OS <<
char(dwarf::DW_LNS_const_add_pc);
720 OS <<
char(dwarf::DW_LNS_advance_pc);
724 OS << char(dwarf::DW_LNS_copy);
726 assert(Temp <= 255 &&
"Buggy special opcode encoding.");
733 int64_t LineDelta, uint64_t AddrDelta,
737 OS <<
char(dwarf::DW_LNS_advance_line);
747 if (AddrDelta > 60000) {
751 OS <<
char(dwarf::DW_LNS_extended_op);
753 OS << char(dwarf::DW_LNE_set_address);
758 std::vector<uint8_t> FillData;
759 FillData.insert(FillData.begin(), AddrSize, 0);
760 OS.
write(reinterpret_cast<char *>(FillData.data()), AddrSize);
762 OS <<
char(dwarf::DW_LNS_fixed_advance_pc);
772 OS <<
char(dwarf::DW_LNS_extended_op);
774 OS << char(dwarf::DW_LNE_end_sequence);
776 OS <<
char(dwarf::DW_LNS_copy);
799 ? dwarf::DW_FORM_sec_offset
800 : dwarf::DW_FORM_data4);
804 ? dwarf::DW_FORM_sec_offset
805 : dwarf::DW_FORM_data4);
807 EmitAbbrev(MCOS, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr);
808 EmitAbbrev(MCOS, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr);
810 EmitAbbrev(MCOS, dwarf::DW_AT_name, dwarf::DW_FORM_string);
812 EmitAbbrev(MCOS, dwarf::DW_AT_comp_dir, dwarf::DW_FORM_string);
814 if (!DwarfDebugFlags.
empty())
815 EmitAbbrev(MCOS, dwarf::DW_AT_APPLE_flags, dwarf::DW_FORM_string);
816 EmitAbbrev(MCOS, dwarf::DW_AT_producer, dwarf::DW_FORM_string);
817 EmitAbbrev(MCOS, dwarf::DW_AT_language, dwarf::DW_FORM_data2);
824 EmitAbbrev(MCOS, dwarf::DW_AT_name, dwarf::DW_FORM_string);
825 EmitAbbrev(MCOS, dwarf::DW_AT_decl_file, dwarf::DW_FORM_data4);
826 EmitAbbrev(MCOS, dwarf::DW_AT_decl_line, dwarf::DW_FORM_data4);
827 EmitAbbrev(MCOS, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr);
828 EmitAbbrev(MCOS, dwarf::DW_AT_prototyped, dwarf::DW_FORM_flag);
846 const MCSymbol *InfoSectionSymbol) {
855 int Length = 4 + 2 + 4 + 1 + 1;
861 int Pad = 2 * AddrSize - (Length & (2 * AddrSize - 1));
862 if (Pad == 2 * AddrSize)
868 Length += 2 * AddrSize * Sections.size();
870 Length += 2 * AddrSize;
879 if (InfoSectionSymbol)
889 for(
int i = 0; i < Pad; i++)
895 const MCSymbol *StartSymbol = Sec->getBeginSymbol();
896 MCSymbol *EndSymbol = Sec->getEndSymbol(context);
897 assert(StartSymbol &&
"StartSymbol must not be NULL");
898 assert(EndSymbol &&
"EndSymbol must not be NULL");
903 *StartSymbol, *EndSymbol, 0);
917 const MCSymbol *AbbrevSectionSymbol,
919 const MCSymbol *RangesSectionSymbol) {
950 if (AbbrevSectionSymbol ==
nullptr)
965 if (LineSectionSymbol)
971 if (RangesSectionSymbol) {
984 const auto TextSection = Sections.begin();
985 assert(TextSection != Sections.end() &&
"No text section found");
987 MCSymbol *StartSymbol = (*TextSection)->getBeginSymbol();
988 MCSymbol *EndSymbol = (*TextSection)->getEndSymbol(context);
989 assert(StartSymbol &&
"StartSymbol must not be NULL");
990 assert(EndSymbol &&
"EndSymbol must not be NULL");
1006 if (MCDwarfDirs.
size() > 0) {
1023 if (!DwarfDebugFlags.
empty()){
1030 if (!DwarfDebugProducer.
empty())
1043 const std::vector<MCGenDwarfLabelEntry> &Entries =
1045 for (
const auto &Entry : Entries) {
1094 const MCSymbol *StartSymbol = Sec->getBeginSymbol();
1095 MCSymbol *EndSymbol = Sec->getEndSymbol(context);
1096 assert(StartSymbol &&
"StartSymbol must not be NULL");
1097 assert(EndSymbol &&
"EndSymbol must not be NULL");
1103 MCOS->
EmitValue(SectionStartAddr, AddrSize);
1107 *StartSymbol, *EndSymbol, 0);
1126 bool CreateDwarfSectionSymbols =
1128 MCSymbol *LineSectionSymbol =
nullptr;
1129 if (CreateDwarfSectionSymbols)
1131 MCSymbol *AbbrevSectionSymbol =
nullptr;
1132 MCSymbol *InfoSectionSymbol =
nullptr;
1133 MCSymbol *RangesSectionSymbol =
nullptr;
1145 const bool UseRangesSection =
1148 CreateDwarfSectionSymbols |= UseRangesSection;
1151 if (CreateDwarfSectionSymbols) {
1156 if (CreateDwarfSectionSymbols) {
1160 if (UseRangesSection) {
1162 if (CreateDwarfSectionSymbols) {
1168 assert((RangesSectionSymbol !=
nullptr) || !UseRangesSection);
1175 if (UseRangesSection)
1183 RangesSectionSymbol);
1240 unsigned symbolEncoding) {
1242 unsigned format = symbolEncoding & 0x0f;
1261 unsigned symbolEncoding,
bool isEH) {
1275 unsigned symbolEncoding) {
1287 class FrameEmitterImpl {
1289 int InitialCFAOffset = 0;
1295 : IsEH(IsEH), Streamer(Streamer) {}
1302 bool LastInSection,
const MCSymbol &SectionStart);
1316 auto *
MRI = Streamer.getContext().getRegisterInfo();
1323 Reg1 =
MRI->getDwarfRegNumFromDwarfEHRegNum(Reg1);
1324 Reg2 =
MRI->getDwarfRegNumFromDwarfEHRegNum(Reg2);
1326 Streamer.EmitIntValue(dwarf::DW_CFA_register, 1);
1327 Streamer.EmitULEB128IntValue(Reg1);
1328 Streamer.EmitULEB128IntValue(Reg2);
1332 Streamer.EmitIntValue(dwarf::DW_CFA_GNU_window_save, 1);
1336 Streamer.EmitIntValue(dwarf::DW_CFA_AARCH64_negate_ra_state, 1);
1341 Streamer.EmitIntValue(dwarf::DW_CFA_undefined, 1);
1342 Streamer.EmitULEB128IntValue(Reg);
1347 const bool IsRelative =
1350 Streamer.EmitIntValue(dwarf::DW_CFA_def_cfa_offset, 1);
1357 Streamer.EmitULEB128IntValue(CFAOffset);
1364 Reg =
MRI->getDwarfRegNumFromDwarfEHRegNum(Reg);
1365 Streamer.EmitIntValue(dwarf::DW_CFA_def_cfa, 1);
1366 Streamer.EmitULEB128IntValue(Reg);
1368 Streamer.EmitULEB128IntValue(CFAOffset);
1375 Reg =
MRI->getDwarfRegNumFromDwarfEHRegNum(Reg);
1376 Streamer.EmitIntValue(dwarf::DW_CFA_def_cfa_register, 1);
1377 Streamer.EmitULEB128IntValue(Reg);
1383 const bool IsRelative =
1388 Reg =
MRI->getDwarfRegNumFromDwarfEHRegNum(Reg);
1392 Offset -= CFAOffset;
1393 Offset = Offset / dataAlignmentFactor;
1396 Streamer.EmitIntValue(dwarf::DW_CFA_offset_extended_sf, 1);
1397 Streamer.EmitULEB128IntValue(Reg);
1398 Streamer.EmitSLEB128IntValue(Offset);
1399 }
else if (Reg < 64) {
1400 Streamer.EmitIntValue(dwarf::DW_CFA_offset + Reg, 1);
1401 Streamer.EmitULEB128IntValue(Offset);
1403 Streamer.EmitIntValue(dwarf::DW_CFA_offset_extended, 1);
1404 Streamer.EmitULEB128IntValue(Reg);
1405 Streamer.EmitULEB128IntValue(Offset);
1410 Streamer.EmitIntValue(dwarf::DW_CFA_remember_state, 1);
1413 Streamer.EmitIntValue(dwarf::DW_CFA_restore_state, 1);
1417 Streamer.EmitIntValue(dwarf::DW_CFA_same_value, 1);
1418 Streamer.EmitULEB128IntValue(Reg);
1424 Reg =
MRI->getDwarfRegNumFromDwarfEHRegNum(Reg);
1426 Streamer.EmitIntValue(dwarf::DW_CFA_restore | Reg, 1);
1428 Streamer.EmitIntValue(dwarf::DW_CFA_restore_extended, 1);
1429 Streamer.EmitULEB128IntValue(Reg);
1434 Streamer.EmitIntValue(dwarf::DW_CFA_GNU_args_size, 1);
1435 Streamer.EmitULEB128IntValue(Instr.
getOffset());
1451 if (Label && !Label->
isDefined())
continue;
1454 if (BaseLabel && Label) {
1456 if (ThisSym != BaseLabel) {
1457 Streamer.EmitDwarfAdvanceFrameAddr(BaseLabel, ThisSym);
1458 BaseLabel = ThisSym;
1462 EmitCFIInstruction(Instr);
1494 if (!Encoding)
return;
1498 if (!DwarfEHFrameOnly && Frame.
Lsda)
1499 Encoding |= 0x40000000;
1504 Streamer.EmitSymbolValue(Frame.
Begin, Size);
1513 Streamer.EmitIntValue(Encoding, Size);
1518 Streamer.EmitSymbolValue(Frame.
Personality, Size);
1520 Streamer.EmitIntValue(0, Size);
1524 if (!DwarfEHFrameOnly && Frame.
Lsda)
1525 Streamer.EmitSymbolValue(Frame.
Lsda, Size);
1527 Streamer.EmitIntValue(0, Size);
1533 switch (DwarfVersion) {
1546 MCContext &context = Streamer.getContext();
1551 Streamer.EmitLabel(sectionStart);
1561 unsigned CIE_ID = IsEH ? 0 : -1;
1562 Streamer.EmitIntValue(CIE_ID, 4);
1566 Streamer.EmitIntValue(CIEVersion, 1);
1570 Augmentation +=
"z";
1572 Augmentation +=
"P";
1574 Augmentation +=
"L";
1575 Augmentation +=
"R";
1577 Augmentation +=
"S";
1579 Augmentation +=
"B";
1580 Streamer.EmitBytes(Augmentation);
1582 Streamer.EmitIntValue(0, 1);
1584 if (CIEVersion >= 4) {
1589 Streamer.EmitIntValue(0, 1);
1599 unsigned RAReg = Frame.
RAReg;
1600 if (RAReg == static_cast<unsigned>(INT_MAX))
1603 if (CIEVersion == 1) {
1605 "DWARF 2 encodes return_address_register in one byte");
1606 Streamer.EmitIntValue(RAReg, 1);
1608 Streamer.EmitULEB128IntValue(RAReg);
1612 unsigned augmentationLength = 0;
1616 augmentationLength += 1;
1618 augmentationLength +=
1622 augmentationLength += 1;
1624 augmentationLength += 1;
1626 Streamer.EmitULEB128IntValue(augmentationLength);
1647 const std::vector<MCCFIInstruction> &Instructions =
1649 EmitCFIInstructions(Instructions,
nullptr);
1652 InitialCFAOffset = CFAOffset;
1655 Streamer.EmitValueToAlignment(IsEH ? 4 : MAI->getCodePointerSize());
1657 Streamer.EmitLabel(sectionEnd);
1658 return *sectionStart;
1661 void FrameEmitterImpl::EmitFDE(
const MCSymbol &cieStart,
1665 MCContext &context = Streamer.getContext();
1670 CFAOffset = InitialCFAOffset;
1676 Streamer.EmitLabel(fdeStart);
1689 Streamer.EmitSymbolValue(&cieStart, 4);
1693 unsigned PCEncoding =
1705 unsigned augmentationLength = 0;
1710 Streamer.EmitULEB128IntValue(augmentationLength);
1725 Streamer.EmitValueToAlignment(Align);
1727 Streamer.EmitLabel(fdeEnd);
1733 static const CIEKey getEmptyKey() {
1734 return CIEKey(
nullptr, 0, -1,
false,
false, static_cast<unsigned>(INT_MAX),
1738 static const CIEKey getTombstoneKey() {
1739 return CIEKey(
nullptr, -1, 0,
false,
false, static_cast<unsigned>(INT_MAX),
1743 CIEKey(
const MCSymbol *Personality,
unsigned PersonalityEncoding,
1744 unsigned LSDAEncoding,
bool IsSignalFrame,
bool IsSimple,
1745 unsigned RAReg,
bool IsBKeyFrame)
1746 : Personality(Personality), PersonalityEncoding(PersonalityEncoding),
1747 LsdaEncoding(LSDAEncoding), IsSignalFrame(IsSignalFrame),
1748 IsSimple(IsSimple), RAReg(RAReg), IsBKeyFrame(IsBKeyFrame) {}
1758 unsigned PersonalityEncoding;
1759 unsigned LsdaEncoding;
1776 Key.Personality, Key.PersonalityEncoding, Key.LsdaEncoding,
1777 Key.IsSignalFrame, Key.IsSimple, Key.RAReg, Key.IsBKeyFrame));
1780 static bool isEqual(
const CIEKey &LHS,
const CIEKey &RHS) {
1781 return LHS.Personality == RHS.Personality &&
1782 LHS.PersonalityEncoding == RHS.PersonalityEncoding &&
1783 LHS.LsdaEncoding == RHS.LsdaEncoding &&
1784 LHS.IsSignalFrame == RHS.IsSignalFrame &&
1785 LHS.IsSimple == RHS.IsSimple && LHS.RAReg == RHS.RAReg &&
1786 LHS.IsBKeyFrame == RHS.IsBKeyFrame;
1799 FrameEmitterImpl Emitter(IsEH, Streamer);
1805 bool SectionEmitted =
false;
1808 if (!SectionEmitted) {
1811 SectionEmitted =
true;
1813 NeedsEHFrameSection |=
1816 Emitter.EmitCompactUnwind(Frame);
1820 if (!NeedsEHFrameSection)
return;
1832 const MCSymbol *DummyDebugKey =
nullptr;
1834 for (
auto I = FrameArray.
begin(),
E = FrameArray.
end();
I !=
E;) {
1844 const MCSymbol *&CIEStart = IsEH ? CIEStarts[
Key] : DummyDebugKey;
1846 CIEStart = &Emitter.EmitCIE(Frame);
1848 Emitter.EmitFDE(*CIEStart, Frame,
I ==
E, *SectionStart);
1853 uint64_t AddrDelta) {
1869 if (AddrDelta == 0) {
1870 }
else if (
isUIntN(6, AddrDelta)) {
1871 uint8_t Opcode = dwarf::DW_CFA_advance_loc | AddrDelta;
1874 OS << uint8_t(dwarf::DW_CFA_advance_loc1);
1875 OS << uint8_t(AddrDelta);
1877 OS << uint8_t(dwarf::DW_CFA_advance_loc2);
1878 support::endian::write<uint16_t>(OS, AddrDelta,
E);
1881 OS << uint8_t(dwarf::DW_CFA_advance_loc4);
1882 support::endian::write<uint32_t>(OS, AddrDelta,
E);
static const MCExpr * forceExpAbs(MCStreamer &OS, const MCExpr *Expr)
const MCAsmInfo * getAsmInfo() const
void addMCGenDwarfLabelEntry(const MCGenDwarfLabelEntry &E)
constexpr bool isUInt< 32 >(uint64_t x)
Instances of this class represent a uniqued identifier for a section in the current translation unit...
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
static int getDataAlignmentFactor(MCStreamer &streamer)
unsigned FindBufferContainingLoc(SMLoc Loc) const
Return the ID of the buffer containing the specified location.
void EmitBytes(StringRef Data) override
Emit the bytes in Data into the output.
static CIEKey getTombstoneKey()
#define DWARF2_FLAG_PROLOGUE_END
static void Make(MCObjectStreamer *MCOS, MCSection *Section)
static const MCSymbolRefExpr * create(const MCSymbol *Symbol, MCContext &Ctx)
Optional< StringRef > Source
The source code of the file.
This class represents lattice values for constants.
void EmitSymbolValue(const MCSymbol *Sym, unsigned Size, bool IsSectionRelative=false)
Special case of EmitValue that avoids the client having to pass in a MCExpr for MCSymbols.
MCSection * getDwarfLineSection() const
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
static bool FixedEncode(MCContext &Context, MCDwarfLineTableParams Params, int64_t LineDelta, uint64_t AddrDelta, raw_ostream &OS, uint32_t *Offset, uint32_t *Size)
Utility function to encode a Dwarf pair of LineDelta and AddrDeltas using fixed length operands...
const SmallVectorImpl< MCDwarfFile > & getMCDwarfFiles(unsigned CUID=0)
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE size_t size() const
size - Get the string size.
virtual void EmitBytes(StringRef Data)
Emit the bytes in Data into the output.
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
bool needsDwarfSectionOffsetDirective() const
static void EmitAdvanceLoc(MCObjectStreamer &Streamer, uint64_t AddrDelta)
MCSection * getDwarfLineStrSection() const
A raw_ostream that writes to an SmallVector or SmallString.
MCSection * getDwarfARangesSection() const
MCDwarfLineStr(MCContext &Ctx)
Construct an instance that can emit .debug_line_str (for use in a normal v5 line table).
uint16_t getDwarfVersion() const
static void Emit(MCStreamer *MCOS, MCDwarfLineTableParams Params, int64_t LineDelta, uint64_t AddrDelta)
Utility function to emit the encoding to a streamer.
virtual MCSymbol * getDwarfLineTableSymbol(unsigned CUID)
bool getSupportsCompactUnwindWithoutEHFrame() const
static void EmitGenDwarfInfo(MCStreamer *MCOS, const MCSymbol *AbbrevSectionSymbol, const MCSymbol *LineSectionSymbol, const MCSymbol *RangesSectionSymbol)
StringRef getDwarfDebugFlags()
std::vector< MCDwarfLineEntry > MCDwarfLineEntryCollection
static void Encode(MCContext &Context, MCDwarfLineTableParams Params, int64_t LineDelta, uint64_t AddrDelta, raw_ostream &OS)
Utility function to encode a Dwarf pair of LineDelta and AddrDeltas.
void EmitDwarfAdvanceLineAddr(int64_t LineDelta, const MCSymbol *LastLabel, const MCSymbol *Label, unsigned PointerSize)
std::vector< MCCFIInstruction > Instructions
const std::vector< MCGenDwarfLabelEntry > & getMCGenDwarfLabelEntries() const
MCContext & getContext() const
#define DWARF2_FLAG_IS_STMT
amdgpu Simplify well known AMD library false Value Value const Twine & Name
StringRef getDwarfDebugProducer()
virtual const MCExpr * getExprForPersonalitySymbol(const MCSymbol *Sym, unsigned Encoding, MCStreamer &Streamer) const
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
ArrayRef< T > makeArrayRef(const T &OneElt)
Construct an ArrayRef from a single element.
ABS - Determine the unsigned absolute value of a signed integer value of the same bitwidth...
void finalizeDwarfSections(MCStreamer &MCOS)
Remove empty sections from SectionsForRanges, to avoid generating useless debug info for them...
Base class for the full range of assembler expressions which are needed for parsing.
uint8_t DWARF2LineRange
Range of line offsets in a special line info. opcode.
int getDwarfRegNum(unsigned RegNum, bool isEH) const
Map a target register to an equivalent dwarf register number.
Tagged union holding either a T or a Error.
unsigned getCompactUnwindDwarfEHFrameOnly() const
static void emitFDESymbol(MCObjectStreamer &streamer, const MCSymbol &symbol, unsigned symbolEncoding, bool isEH)
MCDwarfLineTable & getMCDwarfLineTable(unsigned CUID)
MCSection * getDwarfFrameSection() const
const SmallVectorImpl< std::string > & getMCDwarfDirs(unsigned CUID=0)
bool hasAggressiveSymbolFolding() const
bool getOmitDwarfIfHaveCompactUnwind() const
virtual void EmitAssignment(MCSymbol *Symbol, const MCExpr *Value)
Emit an assignment of Value to Symbol.
StringRef str() const
Explicit conversion to StringRef.
Context object for machine code objects.
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE bool startswith(StringRef Prefix) const
Check if this string starts with the given Prefix.
static void EmitGenDwarfAbbrev(MCStreamer *MCOS)
void write(raw_ostream &OS) const
Utility for building string tables with deduplicated suffixes.
unsigned getDwarfCompileUnitID()
size_t add(CachedHashStringRef S)
Add a string to the builder.
const std::map< unsigned, MCDwarfLineTable > & getMCDwarfLineTables() const
Streaming object file generation interface.
bool doesDwarfUseRelocationsAcrossSections() const
Instances of this class represent the information from a dwarf .loc directive.
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE bool empty() const
empty - Check if the string is empty.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory)...
MCSection * getCompactUnwindSection() const
SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...
virtual void EmitBinaryData(StringRef Data)
Functionally identical to EmitBytes.
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE StringRef substr(size_t Start, size_t N=npos) const
Return a reference to the substring from [Start, Start + N).
unsigned getGenDwarfFileNumber()
virtual void EmitIntValue(uint64_t Value, unsigned Size)
Special case of EmitValue that avoids the client having to pass in a MCExpr for constant integers...
MCSymbol * getLabel() const
void EmitValue(const MCExpr *Value, unsigned Size, SMLoc Loc=SMLoc())
MCSection * getDwarfAbbrevSection() const
static const MCBinaryExpr * create(Opcode Op, const MCExpr *LHS, const MCExpr *RHS, MCContext &Ctx, SMLoc Loc=SMLoc())
MCRegisterInfo base class - We assume that the target defines a static array of MCRegisterDesc object...
This class is intended to be used as a base class for asm properties and features specific to the tar...
static uint64_t SpecialAddr(MCDwarfLineTableParams Params, uint64_t op)
Given a special op, return the address skip amount (in units of DWARF2_LINE_MIN_INSN_LENGTH).
static unsigned getSizeForEncoding(MCStreamer &streamer, unsigned symbolEncoding)
Streaming machine code generation interface.
static unsigned getCIEVersion(bool IsEH, unsigned DwarfVersion)
static void EmitAbbrev(MCStreamer *MCOS, uint64_t Name, uint64_t Form)
MCSymbol * createTempSymbol(bool CanBeUnnamed=true)
Create and return a new assembler temporary symbol with a unique but unspecified name.
uint8_t DWARF2LineOpcodeBase
First special line opcode - leave room for the standard opcodes.
* if(!EatIfPresent(lltok::kw_thread_local)) return false
ParseOptionalThreadLocal := /*empty.
constexpr bool isUInt< 8 >(uint64_t x)
unsigned const MachineRegisterInfo * MRI
void EmitLabel(MCSymbol *Symbol, SMLoc Loc=SMLoc()) override
Emit a label for Symbol into the current section.
unsigned getRegister2() const
void finalizeInOrder()
Finalize the string table without reording it.
#define DWARF2_FLAG_EPILOGUE_BEGIN
size_t size() const
size - Get the array size.
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
virtual void SwitchSection(MCSection *Section, const MCExpr *Subsection=nullptr)
Set the current section where code is being emitted to Section.
static void emitAbsValue(MCStreamer &OS, const MCExpr *Value, unsigned Size)
unsigned getFDEEncoding() const
static void EmitDwarfLineTable(MCObjectStreamer *MCOS, MCSection *Section, const MCLineSection::MCDwarfLineEntryCollection &LineEntries)
static void EmitGenDwarfAranges(MCStreamer *MCOS, const MCSymbol *InfoSectionSymbol)
bool isTemporary() const
isTemporary - Check if this is an assembler temporary symbol.
OpType getOperation() const
const MCObjectFileInfo * getObjectFileInfo() const
#define DWARF2_FLAG_BASIC_BLOCK
bool doDwarfFDESymbolsUseAbsDiff() const
const MCDwarfLoc & getCurrentDwarfLoc()
StringRef parent_path(StringRef path, Style style=Style::native)
Get parent path.
unsigned PersonalityEncoding
This owns the files read by a parser, handles include stacks, and handles diagnostic wrangling...
static void emitOneV5FileEntry(MCStreamer *MCOS, const MCDwarfFile &DwarfFile, bool EmitMD5, bool HasSource, Optional< MCDwarfLineStr > &LineStr)
StringRef getValues() const
StringRef toStringRef(bool B)
Construct a string ref from a boolean.
int8_t DWARF2LineBase
Minimum line offset in a special line info.
StringRef get_separator(Style style=Style::native)
Return the preferred separator for this platform.
void generateCompactUnwindEncodings(MCAsmBackend *MAB)
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
unsigned getULEB128Size(uint64_t Value)
Utility function to get the size of the ULEB128-encoded value.
void EmitValueToAlignment(unsigned ByteAlignment, int64_t Value=0, unsigned ValueSize=1, unsigned MaxBytesToEmit=0) override
Emit some number of copies of Value until the byte alignment ByteAlignment is reached.
raw_ostream & write(unsigned char C)
StringRef getCompilationDir() const
Get the compilation directory for DW_AT_comp_dir The compilation directory should be set with setComp...
unsigned getRegister() const
const SetVector< MCSection * > & getGenDwarfSectionSyms()
const std::vector< MCCFIInstruction > & getInitialFrameState() const
void Emit(MCStreamer &MCOS, MCDwarfLineTableParams Params, MCSection *Section) const
auto size(R &&Range, typename std::enable_if< std::is_same< typename std::iterator_traits< decltype(Range.begin())>::iterator_category, std::random_access_iterator_tag >::value, void >::type *=nullptr) -> decltype(std::distance(Range.begin(), Range.end()))
Get the size of a range.
static unsigned getHashValue(const CIEKey &Key)
void EmitCU(MCObjectStreamer *MCOS, MCDwarfLineTableParams Params, Optional< MCDwarfLineStr > &LineStr) const
unsigned encodeULEB128(uint64_t Value, raw_ostream &OS, unsigned PadTo=0)
Utility function to encode a ULEB128 value to an output stream.
Expected< unsigned > tryGetFile(StringRef &Directory, StringRef &FileName, MD5::MD5Result *Checksum, Optional< StringRef > Source, unsigned FileNumber=0)
unsigned encodeSLEB128(int64_t Value, raw_ostream &OS, unsigned PadTo=0)
Utility function to encode a SLEB128 value to an output stream.
unsigned getMinInstAlignment() const
constexpr size_t array_lengthof(T(&)[N])
Find the length of an array.
static bool isEqual(const CIEKey &LHS, const CIEKey &RHS)
MCSymbol * getBeginSymbol()
StringRef str()
Return a StringRef for the vector contents.
static void EncodeAdvanceLoc(MCContext &Context, uint64_t AddrDelta, raw_ostream &OS)
MCSection * getDwarfInfoSection() const
uint32_t CompactUnwindEncoding
static void EmitGenDwarfRanges(MCStreamer *MCOS)
This file contains constants used for implementing Dwarf debug support.
bool isDefined() const
isDefined - Check if this symbol is defined (i.e., it has an address).
MCSection * getCurrentSectionOnly() const
static CIEKey getEmptyKey()
hash_code hash_combine(const Ts &...args)
Combine values into a single hash_code.
static void Emit(MCStreamer *MCOS)
iterator insert(iterator I, T &&Elt)
#define DWARF2_LINE_DEFAULT_IS_STMT
unsigned FindLineNumber(SMLoc Loc, unsigned BufferID=0) const
Find the line number for the specified location in the specified file.
bool isStackGrowthDirectionUp() const
True if target stack grow up.
static uint64_t ScaleAddrDelta(MCContext &Context, uint64_t AddrDelta)
Instances of this class represent the line information for the dwarf line table entries.
static void Emit(MCObjectStreamer *MCOS, MCDwarfLineTableParams Params)
static const MCExpr * MakeStartMinusEndExpr(const MCStreamer &MCOS, const MCSymbol &Start, const MCSymbol &End, int IntVal)
pointer data()
Return a pointer to the vector's buffer, even if empty().
static void EmitPersonality(MCStreamer &streamer, const MCSymbol &symbol, unsigned symbolEncoding)
StringRef filename(StringRef path, Style style=Style::native)
Get filename.
static void Make(MCSymbol *Symbol, MCStreamer *MCOS, SourceMgr &SrcMgr, SMLoc &Loc)
const MCSymbol * Personality
static const MCExpr * makeStartPlusIntExpr(MCContext &Ctx, const MCSymbol &Start, int IntVal)
unsigned getCalleeSaveStackSlotSize() const
Get the callee-saved register stack slot size in bytes.
bool isLittleEndian() const
True if the target is little endian.
Manage the .debug_line_str section contents, if we use it.
constexpr bool isUInt< 16 >(uint64_t x)
void emitFill(uint64_t NumBytes, uint8_t FillValue)
Emit NumBytes bytes worth of the value specified by FillValue.
MD5::MD5Result * Checksum
The MD5 checksum, if there is one.
unsigned getRARegister() const
This method should return the register where the return address can be found.
MCSymbol * endSection(MCSection *Section)
StringRef getName() const
getName - Get the symbol name.
unsigned getCodePointerSize() const
Get the code pointer size in bytes.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
void emitRef(MCStreamer *MCOS, StringRef Path)
Emit a reference to the string.
std::array< uint8_t, 16 > Bytes
const MCRegisterInfo * getRegisterInfo() const
LLVM Value Representation.
Generic interface to target specific assembler backends.
ArrayRef< MCDwarfFrameInfo > getDwarfFrameInfos() const
virtual void EmitLabel(MCSymbol *Symbol, SMLoc Loc=SMLoc())
Emit a label for Symbol into the current section.
uint64_t tell() const
tell - Return the current offset with the file.
static void emitEncodingByte(MCObjectStreamer &Streamer, unsigned Encoding)
This class implements an extremely fast bulk output stream that can only output to a stream...
void emitSection(MCStreamer *MCOS)
Emit the .debug_line_str section if appropriate.
static void Emit(MCObjectStreamer &streamer, MCAsmBackend *MAB, bool isEH)
StringRef - Represent a constant reference to a string, i.e.
Instances of this class represent the name of the dwarf .file directive and its associated dwarf file...
MCSection * getDwarfRangesSection() const
void EmitULEB128IntValue(uint64_t Value)
Special case of EmitULEB128Value that avoids the client having to pass in a MCExpr for constant integ...
Represents a location in source code.
bool isUIntN(unsigned N, uint64_t x)
Checks if an unsigned integer fits into the given (dynamic) bit width.
static const MCConstantExpr * create(int64_t Value, MCContext &Ctx)
virtual const MCExpr * getExprForFDESymbol(const MCSymbol *Sym, unsigned Encoding, MCStreamer &Streamer) const
std::error_code inconvertibleErrorCode()
The value returned by this function can be returned from convertToErrorCode for Error values where no...