From: Zachary Turner Date: Fri, 9 Jun 2017 20:46:52 +0000 (+0000) Subject: [pdb] Support CoffSymbolRVA debug subsection. X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=bb67f7f534acb397bdcd5c775f63c58c7440afdb;p=llvm [pdb] Support CoffSymbolRVA debug subsection. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@305108 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/include/llvm/DebugInfo/CodeView/DebugSubsectionVisitor.h b/include/llvm/DebugInfo/CodeView/DebugSubsectionVisitor.h index 419ce34922e..d4a3d9195a3 100644 --- a/include/llvm/DebugInfo/CodeView/DebugSubsectionVisitor.h +++ b/include/llvm/DebugInfo/CodeView/DebugSubsectionVisitor.h @@ -27,6 +27,7 @@ class DebugCrossModuleImportsSubsectionRef; class DebugFrameDataSubsectionRef; class DebugLinesSubsectionRef; class DebugStringTableSubsectionRef; +class DebugSymbolRVASubsectionRef; class DebugSymbolsSubsectionRef; class DebugUnknownSubsectionRef; @@ -108,6 +109,8 @@ public: virtual Error visitFrameData(DebugFrameDataSubsectionRef &FD, const DebugSubsectionState &State) = 0; + virtual Error visitCOFFSymbolRVAs(DebugSymbolRVASubsectionRef &RVAs, + const DebugSubsectionState &State) = 0; }; Error visitDebugSubsection(const DebugSubsectionRecord &R, diff --git a/include/llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h b/include/llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h new file mode 100644 index 00000000000..ad58a293cb0 --- /dev/null +++ b/include/llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h @@ -0,0 +1,59 @@ +//===- DebugSymbolRVASubsection.h -------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_DEBUGINFO_CODEVIEW_DEBUGSYMBOLRVASUBSECTION_H +#define LLVM_DEBUGINFO_CODEVIEW_DEBUGSYMBOLRVASUBSECTION_H + +#include "llvm/DebugInfo/CodeView/DebugSubsection.h" +#include "llvm/Support/BinaryStreamArray.h" +#include "llvm/Support/BinaryStreamReader.h" +#include "llvm/Support/Error.h" + +namespace llvm { +namespace codeview { + +class DebugSymbolRVASubsectionRef final : public DebugSubsectionRef { +public: + typedef FixedStreamArray ArrayType; + + DebugSymbolRVASubsectionRef(); + + static bool classof(const DebugSubsectionRef *S) { + return S->kind() == DebugSubsectionKind::CoffSymbolRVA; + } + + ArrayType::Iterator begin() const { return RVAs.begin(); } + ArrayType::Iterator end() const { return RVAs.end(); } + + Error initialize(BinaryStreamReader &Reader); + +private: + ArrayType RVAs; +}; + +class DebugSymbolRVASubsection final : public DebugSubsection { +public: + DebugSymbolRVASubsection(); + + static bool classof(const DebugSubsection *S) { + return S->kind() == DebugSubsectionKind::CoffSymbolRVA; + } + + Error commit(BinaryStreamWriter &Writer) const override; + uint32_t calculateSerializedSize() const override; + + void addRVA(uint32_t RVA) { RVAs.push_back(support::ulittle32_t(RVA)); } + +private: + std::vector RVAs; +}; +} // namespace codeview +} // namespace llvm + +#endif diff --git a/lib/DebugInfo/CodeView/CMakeLists.txt b/lib/DebugInfo/CodeView/CMakeLists.txt index c543a6e9ae1..2f9e8981b69 100644 --- a/lib/DebugInfo/CodeView/CMakeLists.txt +++ b/lib/DebugInfo/CodeView/CMakeLists.txt @@ -13,6 +13,7 @@ add_llvm_library(LLVMDebugInfoCodeView DebugSubsection.cpp DebugSubsectionRecord.cpp DebugSubsectionVisitor.cpp + DebugSymbolRVASubsection.cpp DebugSymbolsSubsection.cpp EnumTables.cpp Formatters.cpp diff --git a/lib/DebugInfo/CodeView/DebugSubsectionVisitor.cpp b/lib/DebugInfo/CodeView/DebugSubsectionVisitor.cpp index be56ea19198..8550107741c 100644 --- a/lib/DebugInfo/CodeView/DebugSubsectionVisitor.cpp +++ b/lib/DebugInfo/CodeView/DebugSubsectionVisitor.cpp @@ -17,6 +17,7 @@ #include "llvm/DebugInfo/CodeView/DebugLinesSubsection.h" #include "llvm/DebugInfo/CodeView/DebugStringTableSubsection.h" #include "llvm/DebugInfo/CodeView/DebugSubsectionRecord.h" +#include "llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h" #include "llvm/DebugInfo/CodeView/DebugSymbolsSubsection.h" #include "llvm/DebugInfo/CodeView/DebugUnknownSubsection.h" #include "llvm/Support/BinaryStreamReader.h" @@ -111,6 +112,12 @@ Error llvm::codeview::visitDebugSubsection(const DebugSubsectionRecord &R, return EC; return V.visitFrameData(Section, State); } + case DebugSubsectionKind::CoffSymbolRVA: { + DebugSymbolRVASubsectionRef Section; + if (auto EC = Section.initialize(Reader)) + return EC; + return V.visitCOFFSymbolRVAs(Section, State); + } default: { DebugUnknownSubsectionRef Fragment(R.kind(), R.getRecordData()); return V.visitUnknown(Fragment); diff --git a/lib/DebugInfo/CodeView/DebugSymbolRVASubsection.cpp b/lib/DebugInfo/CodeView/DebugSymbolRVASubsection.cpp new file mode 100644 index 00000000000..5f91b68f3ad --- /dev/null +++ b/lib/DebugInfo/CodeView/DebugSymbolRVASubsection.cpp @@ -0,0 +1,31 @@ +//===- DebugSymbolRVASubsection.cpp ------------------------------*- C++-*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h" + +using namespace llvm; +using namespace llvm::codeview; + +DebugSymbolRVASubsectionRef::DebugSymbolRVASubsectionRef() + : DebugSubsectionRef(DebugSubsectionKind::CoffSymbolRVA) {} + +Error DebugSymbolRVASubsectionRef::initialize(BinaryStreamReader &Reader) { + return Reader.readArray(RVAs, Reader.bytesRemaining() / sizeof(uint32_t)); +} + +DebugSymbolRVASubsection::DebugSymbolRVASubsection() + : DebugSubsection(DebugSubsectionKind::CoffSymbolRVA) {} + +Error DebugSymbolRVASubsection::commit(BinaryStreamWriter &Writer) const { + return Writer.writeArray(makeArrayRef(RVAs)); +} + +uint32_t DebugSymbolRVASubsection::calculateSerializedSize() const { + return RVAs.size() * sizeof(uint32_t); +} diff --git a/lib/ObjectYAML/CodeViewYAMLDebugSections.cpp b/lib/ObjectYAML/CodeViewYAMLDebugSections.cpp index 3bcedd02d47..08a4bb715fa 100644 --- a/lib/ObjectYAML/CodeViewYAMLDebugSections.cpp +++ b/lib/ObjectYAML/CodeViewYAMLDebugSections.cpp @@ -25,6 +25,7 @@ #include "llvm/DebugInfo/CodeView/DebugLinesSubsection.h" #include "llvm/DebugInfo/CodeView/DebugStringTableSubsection.h" #include "llvm/DebugInfo/CodeView/DebugSubsectionVisitor.h" +#include "llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h" #include "llvm/DebugInfo/CodeView/DebugSymbolsSubsection.h" #include "llvm/DebugInfo/CodeView/EnumTables.h" #include "llvm/DebugInfo/CodeView/SymbolRecord.h" @@ -208,6 +209,21 @@ struct YAMLFrameDataSubsection : public YAMLSubsectionBase { std::vector Frames; }; + +struct YAMLCoffSymbolRVASubsection : public YAMLSubsectionBase { + YAMLCoffSymbolRVASubsection() + : YAMLSubsectionBase(DebugSubsectionKind::CoffSymbolRVA) {} + + void map(IO &IO) override; + std::unique_ptr + toCodeViewSubsection(BumpPtrAllocator &Allocator, + DebugStringTableSubsection *Strings, + DebugChecksumsSubsection *Checksums) const override; + static Expected> + fromCodeViewSubsection(const DebugSymbolRVASubsectionRef &RVAs); + + std::vector RVAs; +}; } void ScalarBitSetTraits::bitset(IO &io, LineFlags &Flags) { @@ -337,6 +353,11 @@ void YAMLFrameDataSubsection::map(IO &IO) { IO.mapRequired("Frames", Frames); } +void YAMLCoffSymbolRVASubsection::map(IO &IO) { + IO.mapTag("!COFFSymbolRVAs", true); + IO.mapRequired("RVAs", RVAs); +} + void MappingTraits::mapping( IO &IO, YAMLDebugSubsection &Subsection) { if (!IO.outputting()) { @@ -359,6 +380,8 @@ void MappingTraits::mapping( Subsection.Subsection = std::make_shared(); } else if (IO.mapTag("!FrameData")) { Subsection.Subsection = std::make_shared(); + } else if (IO.mapTag("!COFFSymbolRVAs")) { + Subsection.Subsection = std::make_shared(); } else { llvm_unreachable("Unexpected subsection tag!"); } @@ -502,6 +525,16 @@ std::unique_ptr YAMLFrameDataSubsection::toCodeViewSubsection( return std::move(Result); } +std::unique_ptr +YAMLCoffSymbolRVASubsection::toCodeViewSubsection( + BumpPtrAllocator &Allocator, DebugStringTableSubsection *Strings, + DebugChecksumsSubsection *Checksums) const { + auto Result = llvm::make_unique(); + for (const auto &RVA : RVAs) + Result->addRVA(RVA); + return std::move(Result); +} + static Expected convertOneChecksum(const DebugStringTableSubsectionRef &Strings, const FileChecksumEntry &CS) { @@ -698,6 +731,16 @@ YAMLFrameDataSubsection::fromCodeViewSubsection( return Result; } +Expected> +YAMLCoffSymbolRVASubsection::fromCodeViewSubsection( + const DebugSymbolRVASubsectionRef &Section) { + auto Result = std::make_shared(); + for (const auto &RVA : Section) { + Result->RVAs.push_back(RVA); + } + return Result; +} + Expected>> llvm::CodeViewYAML::toCodeViewSubsectionList( BumpPtrAllocator &Allocator, ArrayRef Subsections, @@ -782,6 +825,8 @@ struct SubsectionConversionVisitor : public DebugSubsectionVisitor { const DebugSubsectionState &State) override; Error visitFrameData(DebugFrameDataSubsectionRef &Symbols, const DebugSubsectionState &State) override; + Error visitCOFFSymbolRVAs(DebugSymbolRVASubsectionRef &Symbols, + const DebugSubsectionState &State) override; YAMLDebugSubsection Subsection; }; @@ -871,6 +916,15 @@ Error SubsectionConversionVisitor::visitFrameData( Subsection.Subsection = *Result; return Error::success(); } + +Error SubsectionConversionVisitor::visitCOFFSymbolRVAs( + DebugSymbolRVASubsectionRef &RVAs, const DebugSubsectionState &State) { + auto Result = YAMLCoffSymbolRVASubsection::fromCodeViewSubsection(RVAs); + if (!Result) + return Result.takeError(); + Subsection.Subsection = *Result; + return Error::success(); +} } Expected YAMLDebugSubsection::fromCodeViewSubection( diff --git a/tools/llvm-pdbutil/LLVMOutputStyle.cpp b/tools/llvm-pdbutil/LLVMOutputStyle.cpp index 8096ceda942..824f88f8efd 100644 --- a/tools/llvm-pdbutil/LLVMOutputStyle.cpp +++ b/tools/llvm-pdbutil/LLVMOutputStyle.cpp @@ -22,6 +22,7 @@ #include "llvm/DebugInfo/CodeView/DebugLinesSubsection.h" #include "llvm/DebugInfo/CodeView/DebugStringTableSubsection.h" #include "llvm/DebugInfo/CodeView/DebugSubsectionVisitor.h" +#include "llvm/DebugInfo/CodeView/DebugSymbolRVASubsection.h" #include "llvm/DebugInfo/CodeView/DebugSymbolsSubsection.h" #include "llvm/DebugInfo/CodeView/DebugUnknownSubsection.h" #include "llvm/DebugInfo/CodeView/EnumTables.h" @@ -286,6 +287,16 @@ public: return Error::success(); } + Error visitCOFFSymbolRVAs(DebugSymbolRVASubsectionRef &RVAs, + const DebugSubsectionState &State) override { + if (!opts::checkModuleSubsection(opts::ModuleSubsection::CoffSymbolRVAs)) + return Error::success(); + + ListScope D(P, "COFF Symbol RVAs"); + P.printHexList("RVAs", RVAs); + return Error::success(); + } + private: Error dumpTypeRecord(StringRef Label, TypeIndex Index) { CompactTypeDumpVisitor CTDV(IPI, Index, &P); diff --git a/tools/llvm-pdbutil/llvm-pdbutil.cpp b/tools/llvm-pdbutil/llvm-pdbutil.cpp index fa2a5bdd9d3..f6b6a156a76 100644 --- a/tools/llvm-pdbutil/llvm-pdbutil.cpp +++ b/tools/llvm-pdbutil/llvm-pdbutil.cpp @@ -442,6 +442,8 @@ cl::list DumpModuleSubsections( clEnumValN(ModuleSubsection::Symbols, "symbols", "Symbols (DEBUG_S_SYMBOLS subsection) (not typically " "present in PDB file)"), + clEnumValN(ModuleSubsection::CoffSymbolRVAs, "rvas", + "COFF Symbol RVAs (DEBUG_S_COFF_SYMBOL_RVA subsection)"), clEnumValN(ModuleSubsection::Unknown, "unknown", "Any subsection not covered by another option"), clEnumValN(ModuleSubsection::All, "all", "All known subsections")), diff --git a/tools/llvm-pdbutil/llvm-pdbutil.h b/tools/llvm-pdbutil/llvm-pdbutil.h index 4f3665237c7..f1699d0bb55 100644 --- a/tools/llvm-pdbutil/llvm-pdbutil.h +++ b/tools/llvm-pdbutil/llvm-pdbutil.h @@ -37,6 +37,7 @@ enum class ModuleSubsection { StringTable, Symbols, FrameData, + CoffSymbolRVAs, All };