1 //===- CoverageMappingReader.h - Code coverage mapping reader ---*- 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 // This file contains support for reading coverage mapping data for 11 // instrumentation based coverage. 12 // 13 //===----------------------------------------------------------------------===// 14 15 #ifndef LLVM_PROFILEDATA_COVERAGE_COVERAGEMAPPINGREADER_H 16 #define LLVM_PROFILEDATA_COVERAGE_COVERAGEMAPPINGREADER_H 17 18 #include "llvm/ADT/ArrayRef.h" 19 #include "llvm/ADT/StringRef.h" 20 #include "llvm/ProfileData/Coverage/CoverageMapping.h" 21 #include "llvm/ProfileData/InstrProf.h" 22 #include "llvm/Support/Error.h" 23 #include "llvm/Support/MemoryBuffer.h" 24 #include <cstddef> 25 #include <cstdint> 26 #include <iterator> 27 #include <memory> 28 #include <vector> 29 30 namespace llvm { 31 namespace coverage { 32 33 class CoverageMappingReader; 34 35 /// \brief Coverage mapping information for a single function. 36 struct CoverageMappingRecord { 37 StringRef FunctionName; 38 uint64_t FunctionHash; 39 ArrayRef<StringRef> Filenames; 40 ArrayRef<CounterExpression> Expressions; 41 ArrayRef<CounterMappingRegion> MappingRegions; 42 }; 43 44 /// \brief A file format agnostic iterator over coverage mapping data. 45 class CoverageMappingIterator 46 : public std::iterator<std::input_iterator_tag, CoverageMappingRecord> { 47 CoverageMappingReader *Reader = nullptr; 48 CoverageMappingRecord Record; 49 50 void increment(); 51 52 public: 53 CoverageMappingIterator() = default; 54 55 CoverageMappingIterator(CoverageMappingReader *Reader) : Reader(Reader) { 56 increment(); 57 } 58 59 CoverageMappingIterator &operator++() { 60 increment(); 61 return *this; 62 } 63 bool operator==(const CoverageMappingIterator &RHS) { 64 return Reader == RHS.Reader; 65 } 66 bool operator!=(const CoverageMappingIterator &RHS) { 67 return Reader != RHS.Reader; 68 } 69 CoverageMappingRecord &operator*() { return Record; } 70 CoverageMappingRecord *operator->() { return &Record; } 71 }; 72 73 class CoverageMappingReader { 74 public: 75 virtual ~CoverageMappingReader() = default; 76 77 virtual Error readNextRecord(CoverageMappingRecord &Record) = 0; 78 CoverageMappingIterator begin() { return CoverageMappingIterator(this); } 79 CoverageMappingIterator end() { return CoverageMappingIterator(); } 80 }; 81 82 /// \brief Base class for the raw coverage mapping and filenames data readers. 83 class RawCoverageReader { 84 protected: 85 StringRef Data; 86 87 RawCoverageReader(StringRef Data) : Data(Data) {} 88 89 Error readULEB128(uint64_t &Result); 90 Error readIntMax(uint64_t &Result, uint64_t MaxPlus1); 91 Error readSize(uint64_t &Result); 92 Error readString(StringRef &Result); 93 }; 94 95 /// \brief Reader for the raw coverage filenames. 96 class RawCoverageFilenamesReader : public RawCoverageReader { 97 std::vector<StringRef> &Filenames; 98 99 public: 100 RawCoverageFilenamesReader(StringRef Data, std::vector<StringRef> &Filenames) 101 : RawCoverageReader(Data), Filenames(Filenames) {} 102 RawCoverageFilenamesReader(const RawCoverageFilenamesReader &) = delete; 103 RawCoverageFilenamesReader & 104 operator=(const RawCoverageFilenamesReader &) = delete; 105 106 Error read(); 107 }; 108 109 /// \brief Checks if the given coverage mapping data is exported for 110 /// an unused function. 111 class RawCoverageMappingDummyChecker : public RawCoverageReader { 112 public: 113 RawCoverageMappingDummyChecker(StringRef MappingData) 114 : RawCoverageReader(MappingData) {} 115 116 Expected<bool> isDummy(); 117 }; 118 119 /// \brief Reader for the raw coverage mapping data. 120 class RawCoverageMappingReader : public RawCoverageReader { 121 ArrayRef<StringRef> TranslationUnitFilenames; 122 std::vector<StringRef> &Filenames; 123 std::vector<CounterExpression> &Expressions; 124 std::vector<CounterMappingRegion> &MappingRegions; 125 126 public: 127 RawCoverageMappingReader(StringRef MappingData, 128 ArrayRef<StringRef> TranslationUnitFilenames, 129 std::vector<StringRef> &Filenames, 130 std::vector<CounterExpression> &Expressions, 131 std::vector<CounterMappingRegion> &MappingRegions) 132 : RawCoverageReader(MappingData), 133 TranslationUnitFilenames(TranslationUnitFilenames), 134 Filenames(Filenames), Expressions(Expressions), 135 MappingRegions(MappingRegions) {} 136 RawCoverageMappingReader(const RawCoverageMappingReader &) = delete; 137 RawCoverageMappingReader & 138 operator=(const RawCoverageMappingReader &) = delete; 139 140 Error read(); 141 142 private: 143 Error decodeCounter(unsigned Value, Counter &C); 144 Error readCounter(Counter &C); 145 Error 146 readMappingRegionsSubArray(std::vector<CounterMappingRegion> &MappingRegions, 147 unsigned InferredFileID, size_t NumFileIDs); 148 }; 149 150 /// \brief Reader for the coverage mapping data that is emitted by the 151 /// frontend and stored in an object file. 152 class BinaryCoverageReader : public CoverageMappingReader { 153 public: 154 struct ProfileMappingRecord { 155 CovMapVersion Version; 156 StringRef FunctionName; 157 uint64_t FunctionHash; 158 StringRef CoverageMapping; 159 size_t FilenamesBegin; 160 size_t FilenamesSize; 161 162 ProfileMappingRecord(CovMapVersion Version, StringRef FunctionName, 163 uint64_t FunctionHash, StringRef CoverageMapping, 164 size_t FilenamesBegin, size_t FilenamesSize) 165 : Version(Version), FunctionName(FunctionName), 166 FunctionHash(FunctionHash), CoverageMapping(CoverageMapping), 167 FilenamesBegin(FilenamesBegin), FilenamesSize(FilenamesSize) {} 168 }; 169 170 private: 171 std::vector<StringRef> Filenames; 172 std::vector<ProfileMappingRecord> MappingRecords; 173 InstrProfSymtab ProfileNames; 174 size_t CurrentRecord = 0; 175 std::vector<StringRef> FunctionsFilenames; 176 std::vector<CounterExpression> Expressions; 177 std::vector<CounterMappingRegion> MappingRegions; 178 179 BinaryCoverageReader() = default; 180 181 public: 182 BinaryCoverageReader(const BinaryCoverageReader &) = delete; 183 BinaryCoverageReader &operator=(const BinaryCoverageReader &) = delete; 184 185 static Expected<std::unique_ptr<BinaryCoverageReader>> 186 create(std::unique_ptr<MemoryBuffer> &ObjectBuffer, 187 StringRef Arch); 188 189 Error readNextRecord(CoverageMappingRecord &Record) override; 190 }; 191 192 } // end namespace coverage 193 } // end namespace llvm 194 195 #endif // LLVM_PROFILEDATA_COVERAGE_COVERAGEMAPPINGREADER_H 196