Coverage Report

Created: 2019-07-24 05:18

/Users/buildslave/jenkins/workspace/clang-stage2-coverage-R/llvm/lib/Target/BPF/BTFDebug.h
Line
Count
Source (jump to first uncovered line)
1
//===- BTFDebug.h -----------------------------------------------*- C++ -*-===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
///
9
/// \file
10
/// This file contains support for writing BTF debug info.
11
///
12
//===----------------------------------------------------------------------===//
13
14
#ifndef LLVM_LIB_TARGET_BPF_BTFDEBUG_H
15
#define LLVM_LIB_TARGET_BPF_BTFDEBUG_H
16
17
#include "llvm/ADT/StringMap.h"
18
#include "llvm/CodeGen/DebugHandlerBase.h"
19
#include <unordered_map>
20
#include "BTF.h"
21
22
namespace llvm {
23
24
class AsmPrinter;
25
class BTFDebug;
26
class DIType;
27
class MCStreamer;
28
class MCSymbol;
29
class MachineFunction;
30
31
/// The base class for BTF type generation.
32
class BTFTypeBase {
33
protected:
34
  uint8_t Kind;
35
  bool IsCompleted;
36
  uint32_t Id;
37
  struct BTF::CommonType BTFType;
38
39
public:
40
592
  BTFTypeBase() : IsCompleted(false) {}
41
592
  virtual ~BTFTypeBase() = default;
42
592
  void setId(uint32_t Id) { this->Id = Id; }
43
668
  uint32_t getId() { return Id; }
44
218
  uint32_t roundupToBytes(uint32_t NumBits) { return (NumBits + 7) >> 3; }
45
  /// Get the size of this BTF type entry.
46
592
  virtual uint32_t getSize() { return BTF::CommonTypeSize; }
47
  /// Complete BTF type generation after all related DebugInfo types
48
  /// have been visited so their BTF type id's are available
49
  /// for cross referece.
50
0
  virtual void completeType(BTFDebug &BDebug) {}
51
  /// Emit types for this BTF type entry.
52
  virtual void emitType(MCStreamer &OS);
53
};
54
55
/// Handle several derived types include pointer, const,
56
/// volatile, typedef and restrict.
57
class BTFTypeDerived : public BTFTypeBase {
58
  const DIDerivedType *DTy;
59
  bool NeedsFixup;
60
61
public:
62
  BTFTypeDerived(const DIDerivedType *Ty, unsigned Tag, bool NeedsFixup);
63
  void completeType(BTFDebug &BDebug);
64
  void emitType(MCStreamer &OS);
65
  void setPointeeType(uint32_t PointeeType);
66
};
67
68
/// Handle struct or union forward declaration.
69
class BTFTypeFwd : public BTFTypeBase {
70
  StringRef Name;
71
72
public:
73
  BTFTypeFwd(StringRef Name, bool IsUnion);
74
  void completeType(BTFDebug &BDebug);
75
  void emitType(MCStreamer &OS);
76
};
77
78
/// Handle int type.
79
class BTFTypeInt : public BTFTypeBase {
80
  StringRef Name;
81
  uint32_t IntVal; ///< Encoding, offset, bits
82
83
public:
84
  BTFTypeInt(uint32_t Encoding, uint32_t SizeInBits, uint32_t OffsetInBits,
85
             StringRef TypeName);
86
163
  uint32_t getSize() { return BTFTypeBase::getSize() + sizeof(uint32_t); }
87
  void completeType(BTFDebug &BDebug);
88
  void emitType(MCStreamer &OS);
89
};
90
91
/// Handle enumerate type.
92
class BTFTypeEnum : public BTFTypeBase {
93
  const DICompositeType *ETy;
94
  std::vector<struct BTF::BTFEnum> EnumValues;
95
96
public:
97
  BTFTypeEnum(const DICompositeType *ETy, uint32_t NumValues);
98
4
  uint32_t getSize() {
99
4
    return BTFTypeBase::getSize() + EnumValues.size() * BTF::BTFEnumSize;
100
4
  }
101
  void completeType(BTFDebug &BDebug);
102
  void emitType(MCStreamer &OS);
103
};
104
105
/// Handle array type.
106
class BTFTypeArray : public BTFTypeBase {
107
  uint32_t ElemSize;
108
  struct BTF::BTFArray ArrayInfo;
109
110
public:
111
  BTFTypeArray(uint32_t ElemTypeId, uint32_t ElemSize, uint32_t NumElems);
112
20
  uint32_t getSize() { return BTFTypeBase::getSize() + BTF::BTFArraySize; }
113
  void completeType(BTFDebug &BDebug);
114
  void emitType(MCStreamer &OS);
115
  void getLocInfo(uint32_t Loc, uint32_t &LocOffset, uint32_t &ElementTypeId);
116
};
117
118
/// Handle struct/union type.
119
class BTFTypeStruct : public BTFTypeBase {
120
  const DICompositeType *STy;
121
  bool HasBitField;
122
  std::vector<struct BTF::BTFMember> Members;
123
124
public:
125
  BTFTypeStruct(const DICompositeType *STy, bool IsStruct, bool HasBitField,
126
                uint32_t NumMembers);
127
51
  uint32_t getSize() {
128
51
    return BTFTypeBase::getSize() + Members.size() * BTF::BTFMemberSize;
129
51
  }
130
  void completeType(BTFDebug &BDebug);
131
  void emitType(MCStreamer &OS);
132
  std::string getName();
133
  void getMemberInfo(uint32_t Loc, uint32_t &Offset, uint32_t &MemberType);
134
  uint32_t getStructSize();
135
};
136
137
/// Handle function pointer.
138
class BTFTypeFuncProto : public BTFTypeBase {
139
  const DISubroutineType *STy;
140
  std::unordered_map<uint32_t, StringRef> FuncArgNames;
141
  std::vector<struct BTF::BTFParam> Parameters;
142
143
public:
144
  BTFTypeFuncProto(const DISubroutineType *STy, uint32_t NumParams,
145
                   const std::unordered_map<uint32_t, StringRef> &FuncArgNames);
146
72
  uint32_t getSize() {
147
72
    return BTFTypeBase::getSize() + Parameters.size() * BTF::BTFParamSize;
148
72
  }
149
  void completeType(BTFDebug &BDebug);
150
  void emitType(MCStreamer &OS);
151
};
152
153
/// Handle subprogram
154
class BTFTypeFunc : public BTFTypeBase {
155
  StringRef Name;
156
157
public:
158
  BTFTypeFunc(StringRef FuncName, uint32_t ProtoTypeId);
159
64
  uint32_t getSize() { return BTFTypeBase::getSize(); }
160
  void completeType(BTFDebug &BDebug);
161
  void emitType(MCStreamer &OS);
162
};
163
164
/// Handle variable instances
165
class BTFKindVar : public BTFTypeBase {
166
  StringRef Name;
167
  uint32_t Info;
168
169
public:
170
  BTFKindVar(StringRef VarName, uint32_t TypeId, uint32_t VarInfo);
171
52
  uint32_t getSize() { return BTFTypeBase::getSize() + 4; }
172
  void completeType(BTFDebug &BDebug);
173
  void emitType(MCStreamer &OS);
174
};
175
176
/// Handle data sections
177
class BTFKindDataSec : public BTFTypeBase {
178
  AsmPrinter *Asm;
179
  std::string Name;
180
  std::vector<std::tuple<uint32_t, const MCSymbol *, uint32_t>> Vars;
181
182
public:
183
  BTFKindDataSec(AsmPrinter *AsmPrt, std::string SecName);
184
32
  uint32_t getSize() {
185
32
    return BTFTypeBase::getSize() + BTF::BTFDataSecVarSize * Vars.size();
186
32
  }
187
52
  void addVar(uint32_t Id, const MCSymbol *Sym, uint32_t Size) {
188
52
    Vars.push_back(std::make_tuple(Id, Sym, Size));
189
52
  }
190
0
  std::string getName() { return Name; }
191
  void completeType(BTFDebug &BDebug);
192
  void emitType(MCStreamer &OS);
193
};
194
195
/// String table.
196
class BTFStringTable {
197
  /// String table size in bytes.
198
  uint32_t Size;
199
  /// A mapping from string table offset to the index
200
  /// of the Table. It is used to avoid putting
201
  /// duplicated strings in the table.
202
  std::unordered_map<uint32_t, uint32_t> OffsetToIdMap;
203
  /// A vector of strings to represent the string table.
204
  std::vector<std::string> Table;
205
206
public:
207
136
  BTFStringTable() : Size(0) {}
208
132
  uint32_t getSize() { return Size; }
209
132
  std::vector<std::string> &getTable() { return Table; }
210
  /// Add a string to the string table and returns its offset
211
  /// in the table.
212
  uint32_t addString(StringRef S);
213
};
214
215
/// Represent one func and its type id.
216
struct BTFFuncInfo {
217
  const MCSymbol *Label; ///< Func MCSymbol
218
  uint32_t TypeId;       ///< Type id referring to .BTF type section
219
};
220
221
/// Represent one line info.
222
struct BTFLineInfo {
223
  MCSymbol *Label;      ///< MCSymbol identifying insn for the lineinfo
224
  uint32_t FileNameOff; ///< file name offset in the .BTF string table
225
  uint32_t LineOff;     ///< line offset in the .BTF string table
226
  uint32_t LineNum;     ///< the line number
227
  uint32_t ColumnNum;   ///< the column number
228
};
229
230
/// Represent one offset relocation.
231
struct BTFOffsetReloc {
232
  const MCSymbol *Label;  ///< MCSymbol identifying insn for the reloc
233
  uint32_t TypeID;        ///< Type ID
234
  uint32_t OffsetNameOff; ///< The string to traverse types
235
};
236
237
/// Represent one extern relocation.
238
struct BTFExternReloc {
239
  const MCSymbol *Label;  ///< MCSymbol identifying insn for the reloc
240
  uint32_t ExternNameOff; ///< The extern variable name
241
};
242
243
/// Collect and emit BTF information.
244
class BTFDebug : public DebugHandlerBase {
245
  MCStreamer &OS;
246
  bool SkipInstruction;
247
  bool LineInfoGenerated;
248
  uint32_t SecNameOff;
249
  uint32_t ArrayIndexTypeId;
250
  bool MapDefNotCollected;
251
  BTFStringTable StringTable;
252
  std::vector<std::unique_ptr<BTFTypeBase>> TypeEntries;
253
  std::unordered_map<const DIType *, uint32_t> DIToIdMap;
254
  std::map<uint32_t, std::vector<BTFFuncInfo>> FuncInfoTable;
255
  std::map<uint32_t, std::vector<BTFLineInfo>> LineInfoTable;
256
  std::map<uint32_t, std::vector<BTFOffsetReloc>> OffsetRelocTable;
257
  std::map<uint32_t, std::vector<BTFExternReloc>> ExternRelocTable;
258
  StringMap<std::vector<std::string>> FileContent;
259
  std::map<std::string, std::unique_ptr<BTFKindDataSec>> DataSecEntries;
260
  std::vector<BTFTypeStruct *> StructTypes;
261
  std::vector<BTFTypeArray *> ArrayTypes;
262
  std::map<std::string, int64_t> AccessOffsets;
263
  std::map<StringRef, std::pair<bool, std::vector<BTFTypeDerived *>>>
264
      FixupDerivedTypes;
265
266
  /// Add types to TypeEntries.
267
  /// @{
268
  /// Add types to TypeEntries and DIToIdMap.
269
  uint32_t addType(std::unique_ptr<BTFTypeBase> TypeEntry, const DIType *Ty);
270
  /// Add types to TypeEntries only and return type id.
271
  uint32_t addType(std::unique_ptr<BTFTypeBase> TypeEntry);
272
  /// @}
273
274
  /// IR type visiting functions.
275
  /// @{
276
  void visitTypeEntry(const DIType *Ty);
277
  void visitTypeEntry(const DIType *Ty, uint32_t &TypeId, bool CheckPointer,
278
                      bool SeenPointer);
279
  void visitBasicType(const DIBasicType *BTy, uint32_t &TypeId);
280
  void visitSubroutineType(
281
      const DISubroutineType *STy, bool ForSubprog,
282
      const std::unordered_map<uint32_t, StringRef> &FuncArgNames,
283
      uint32_t &TypeId);
284
  void visitFwdDeclType(const DICompositeType *CTy, bool IsUnion,
285
                        uint32_t &TypeId);
286
  void visitCompositeType(const DICompositeType *CTy, uint32_t &TypeId);
287
  void visitStructType(const DICompositeType *STy, bool IsStruct,
288
                       uint32_t &TypeId);
289
  void visitArrayType(const DICompositeType *ATy, uint32_t &TypeId);
290
  void visitEnumType(const DICompositeType *ETy, uint32_t &TypeId);
291
  void visitDerivedType(const DIDerivedType *DTy, uint32_t &TypeId,
292
                        bool CheckPointer, bool SeenPointer);
293
  void visitMapDefType(const DIType *Ty, uint32_t &TypeId);
294
  /// @}
295
296
  /// Get the file content for the subprogram. Certain lines of the file
297
  /// later may be put into string table and referenced by line info.
298
  std::string populateFileContent(const DISubprogram *SP);
299
300
  /// Construct a line info.
301
  void constructLineInfo(const DISubprogram *SP, MCSymbol *Label, uint32_t Line,
302
                         uint32_t Column);
303
304
  /// Generate types and variables for globals.
305
  void processGlobals(bool ProcessingMapDef);
306
307
  /// Generate one offset relocation record.
308
  void generateOffsetReloc(const MachineInstr *MI, const MCSymbol *ORSym,
309
                           DIType *RootTy, StringRef AccessPattern);
310
311
  /// Set the to-be-traversed Struct/Array Type based on TypeId.
312
  void setTypeFromId(uint32_t TypeId, BTFTypeStruct **PrevStructType,
313
                     BTFTypeArray **PrevArrayType);
314
315
  /// Populating unprocessed struct type.
316
  unsigned populateStructType(const DIType *Ty);
317
318
  /// Process LD_imm64 instructions.
319
  void processLDimm64(const MachineInstr *MI);
320
321
  /// Emit common header of .BTF and .BTF.ext sections.
322
  void emitCommonHeader();
323
324
  /// Emit the .BTF section.
325
  void emitBTFSection();
326
327
  /// Emit the .BTF.ext section.
328
  void emitBTFExtSection();
329
330
protected:
331
  /// Gather pre-function debug information.
332
  void beginFunctionImpl(const MachineFunction *MF) override;
333
334
  /// Post process after all instructions in this function are processed.
335
  void endFunctionImpl(const MachineFunction *MF) override;
336
337
public:
338
  BTFDebug(AsmPrinter *AP);
339
340
  ///
341
  bool InstLower(const MachineInstr *MI, MCInst &OutMI);
342
343
  /// Get the special array index type id.
344
20
  uint32_t getArrayIndexTypeId() {
345
20
    assert(ArrayIndexTypeId);
346
20
    return ArrayIndexTypeId;
347
20
  }
348
349
  /// Add string to the string table.
350
1.07k
  size_t addString(StringRef S) { return StringTable.addString(S); }
351
352
  /// Get the type id for a particular DIType.
353
309
  uint32_t getTypeId(const DIType *Ty) {
354
309
    assert(Ty && "Invalid null Type");
355
309
    assert(DIToIdMap.find(Ty) != DIToIdMap.end() &&
356
309
           "DIType not added in the BDIToIdMap");
357
309
    return DIToIdMap[Ty];
358
309
  }
359
360
118
  void setSymbolSize(const MCSymbol *Symbol, uint64_t Size) override {}
361
362
  /// Process beginning of an instruction.
363
  void beginInstruction(const MachineInstr *MI) override;
364
365
  /// Complete all the types and emit the BTF sections.
366
  void endModule() override;
367
};
368
369
} // end namespace llvm
370
371
#endif