1 //===- StringsAndChecksums.h ------------------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #ifndef LLVM_DEBUGINFO_CODEVIEW_STRINGSANDCHECKSUMS_H 11 #define LLVM_DEBUGINFO_CODEVIEW_STRINGSANDCHECKSUMS_H 12 13 #include "llvm/DebugInfo/CodeView/CodeView.h" 14 #include "llvm/DebugInfo/CodeView/DebugChecksumsSubsection.h" 15 #include "llvm/DebugInfo/CodeView/DebugStringTableSubsection.h" 16 #include "llvm/DebugInfo/CodeView/DebugSubsectionRecord.h" 17 #include <memory> 18 19 namespace llvm { 20 namespace codeview { 21 22 class StringsAndChecksumsRef { 23 public: 24 // If no subsections are known about initially, we find as much as we can. 25 StringsAndChecksumsRef(); 26 27 // If only a string table subsection is given, we find a checksums subsection. 28 explicit StringsAndChecksumsRef(const DebugStringTableSubsectionRef &Strings); 29 30 // If both subsections are given, we don't need to find anything. 31 StringsAndChecksumsRef(const DebugStringTableSubsectionRef &Strings, 32 const DebugChecksumsSubsectionRef &Checksums); 33 34 void setStrings(const DebugStringTableSubsectionRef &Strings); 35 void setChecksums(const DebugChecksumsSubsectionRef &CS); 36 37 void reset(); 38 void resetStrings(); 39 void resetChecksums(); 40 initialize(T && FragmentRange)41 template <typename T> void initialize(T &&FragmentRange) { 42 for (const DebugSubsectionRecord &R : FragmentRange) { 43 if (Strings && Checksums) 44 return; 45 if (R.kind() == DebugSubsectionKind::FileChecksums) { 46 initializeChecksums(R); 47 continue; 48 } 49 if (R.kind() == DebugSubsectionKind::StringTable && !Strings) { 50 // While in practice we should never encounter a string table even 51 // though the string table is already initialized, in theory it's 52 // possible. PDBs are supposed to have one global string table and 53 // then this subsection should not appear. Whereas object files are 54 // supposed to have this subsection appear exactly once. However, 55 // for testing purposes it's nice to be able to test this subsection 56 // independently of one format or the other, so for some tests we 57 // manually construct a PDB that contains this subsection in addition 58 // to a global string table. 59 initializeStrings(R); 60 continue; 61 } 62 } 63 } 64 strings()65 const DebugStringTableSubsectionRef &strings() const { return *Strings; } checksums()66 const DebugChecksumsSubsectionRef &checksums() const { return *Checksums; } 67 hasStrings()68 bool hasStrings() const { return Strings != nullptr; } hasChecksums()69 bool hasChecksums() const { return Checksums != nullptr; } 70 71 private: 72 void initializeStrings(const DebugSubsectionRecord &SR); 73 void initializeChecksums(const DebugSubsectionRecord &FCR); 74 75 std::shared_ptr<DebugStringTableSubsectionRef> OwnedStrings; 76 std::shared_ptr<DebugChecksumsSubsectionRef> OwnedChecksums; 77 78 const DebugStringTableSubsectionRef *Strings = nullptr; 79 const DebugChecksumsSubsectionRef *Checksums = nullptr; 80 }; 81 82 class StringsAndChecksums { 83 public: 84 using StringsPtr = std::shared_ptr<DebugStringTableSubsection>; 85 using ChecksumsPtr = std::shared_ptr<DebugChecksumsSubsection>; 86 87 // If no subsections are known about initially, we find as much as we can. 88 StringsAndChecksums() = default; 89 setStrings(const StringsPtr & SP)90 void setStrings(const StringsPtr &SP) { Strings = SP; } setChecksums(const ChecksumsPtr & CP)91 void setChecksums(const ChecksumsPtr &CP) { Checksums = CP; } 92 strings()93 const StringsPtr &strings() const { return Strings; } checksums()94 const ChecksumsPtr &checksums() const { return Checksums; } 95 hasStrings()96 bool hasStrings() const { return Strings != nullptr; } hasChecksums()97 bool hasChecksums() const { return Checksums != nullptr; } 98 99 private: 100 StringsPtr Strings; 101 ChecksumsPtr Checksums; 102 }; 103 104 } // end namespace codeview 105 } // end namespace llvm 106 107 #endif // LLVM_DEBUGINFO_CODEVIEW_STRINGSANDCHECKSUMS_H 108