1 //===- DebugStringTableSubsection.cpp - CodeView String Table ---*- 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 #include "llvm/DebugInfo/CodeView/DebugStringTableSubsection.h" 11 12 #include "llvm/Support/BinaryStream.h" 13 #include "llvm/Support/BinaryStreamReader.h" 14 #include "llvm/Support/BinaryStreamWriter.h" 15 16 using namespace llvm; 17 using namespace llvm::codeview; 18 19 DebugStringTableSubsectionRef::DebugStringTableSubsectionRef() 20 : DebugSubsectionRef(DebugSubsectionKind::StringTable) {} 21 22 Error DebugStringTableSubsectionRef::initialize(BinaryStreamRef Contents) { 23 Stream = Contents; 24 return Error::success(); 25 } 26 27 Expected<StringRef> 28 DebugStringTableSubsectionRef::getString(uint32_t Offset) const { 29 BinaryStreamReader Reader(Stream); 30 Reader.setOffset(Offset); 31 StringRef Result; 32 if (auto EC = Reader.readCString(Result)) 33 return std::move(EC); 34 return Result; 35 } 36 37 DebugStringTableSubsection::DebugStringTableSubsection() 38 : DebugSubsection(DebugSubsectionKind::StringTable) {} 39 40 uint32_t DebugStringTableSubsection::insert(StringRef S) { 41 auto P = Strings.insert({S, StringSize}); 42 43 // If a given string didn't exist in the string table, we want to increment 44 // the string table size. 45 if (P.second) 46 StringSize += S.size() + 1; // +1 for '\0' 47 return P.first->second; 48 } 49 50 uint32_t DebugStringTableSubsection::calculateSerializedSize() const { 51 return StringSize; 52 } 53 54 Error DebugStringTableSubsection::commit(BinaryStreamWriter &Writer) const { 55 assert(Writer.bytesRemaining() == StringSize); 56 uint32_t MaxOffset = 1; 57 58 for (auto &Pair : Strings) { 59 StringRef S = Pair.getKey(); 60 uint32_t Offset = Pair.getValue(); 61 Writer.setOffset(Offset); 62 if (auto EC = Writer.writeCString(S)) 63 return EC; 64 MaxOffset = std::max<uint32_t>(MaxOffset, Offset + S.size() + 1); 65 } 66 67 Writer.setOffset(MaxOffset); 68 assert(Writer.bytesRemaining() == 0); 69 return Error::success(); 70 } 71 72 uint32_t DebugStringTableSubsection::size() const { return Strings.size(); } 73 74 uint32_t DebugStringTableSubsection::getStringId(StringRef S) const { 75 auto P = Strings.find(S); 76 assert(P != Strings.end()); 77 return P->second; 78 } 79