53
53
#include " llvm/IR/DebugLoc.h"
54
54
#include " llvm/IR/Instruction.h"
55
55
#include " llvm/IR/SymbolTableListTraits.h"
56
+ #include " llvm/Support/Casting.h"
56
57
57
58
namespace llvm {
58
59
@@ -66,43 +67,105 @@ class DPMarker;
66
67
class DPValue ;
67
68
class raw_ostream ;
68
69
69
- // / Record of a variable value-assignment, aka a non instruction representation
70
- // / of the dbg.value intrinsic. Features various methods copied across from the
71
- // / Instruction class to aid ease-of-use. DPValue objects should always be
72
- // / linked into a DPMarker's StoredDPValues list. The marker connects a DPValue
73
- // / back to it's position in the BasicBlock.
70
+ // / Base class for non-instruction debug metadata records that have positions
71
+ // / within IR. Features various methods copied across from the Instruction
72
+ // / class to aid ease-of-use. DbgRecords should always be linked into a
73
+ // / DPMarker's StoredDPValues list. The marker connects a DbgRecord back to
74
+ // / it's position in the BasicBlock.
74
75
// /
75
- // / This class inherits from DebugValueUser to allow LLVM's metadata facilities
76
- // / to update our references to metadata beneath our feet.
77
- class DPValue : public ilist_node <DPValue>, private DebugValueUser {
78
- friend class DebugValueUser ;
79
-
80
- // NB: there is no explicit "Value" field in this class, it's effectively the
81
- // DebugValueUser superclass instead. The referred to Value can either be a
82
- // ValueAsMetadata or a DIArgList.
76
+ // / We need a discriminator for dyn/isa casts. In order to avoid paying for a
77
+ // / vtable for "virtual" functions too, subclasses must add a new discriminator
78
+ // / value (RecordKind) and cases to a few functions in the base class:
79
+ // / deleteRecord
80
+ // / clone
81
+ // / isIdenticalToWhenDefined
82
+ // / isEquivalentTo
83
+ // / both print methods
84
+ class DbgRecord : public ilist_node <DbgRecord> {
85
+ public:
86
+ // / Marker that this DbgRecord is linked into.
87
+ DPMarker *Marker = nullptr ;
88
+ // / Subclass discriminator.
89
+ enum Kind : uint8_t { ValueKind };
83
90
84
- DILocalVariable *Variable;
85
- DIExpression *Expression;
91
+ protected:
86
92
DebugLoc DbgLoc;
87
- DIExpression *AddressExpression;
93
+ Kind RecordKind; // /< Subclass discriminator.
88
94
89
95
public:
90
- void deleteInstr ();
96
+ DbgRecord (Kind RecordKind, DebugLoc DL)
97
+ : DbgLoc(DL), RecordKind(RecordKind) {}
98
+
99
+ // / Methods that dispatch to subclass implementations. These need to be
100
+ // / manually updated when a new subclass is added.
101
+ // /@{
102
+ void deleteRecord ();
103
+ DbgRecord *clone () const ;
104
+ void print (raw_ostream &O, bool IsForDebug = false ) const ;
105
+ void print (raw_ostream &O, ModuleSlotTracker &MST, bool IsForDebug) const ;
106
+ bool isIdenticalToWhenDefined (const DbgRecord &R) const ;
107
+ bool isEquivalentTo (const DbgRecord &R) const ;
108
+ // /@}
109
+
110
+ Kind getRecordKind () const { return RecordKind; }
111
+
112
+ void setMarker (DPMarker *M) { Marker = M; }
113
+
114
+ DPMarker *getMarker () { return Marker; }
115
+ const DPMarker *getMarker () const { return Marker; }
116
+
117
+ BasicBlock *getBlock ();
118
+ const BasicBlock *getBlock () const ;
119
+
120
+ Function *getFunction ();
121
+ const Function *getFunction () const ;
122
+
123
+ Module *getModule ();
124
+ const Module *getModule () const ;
125
+
126
+ LLVMContext &getContext ();
127
+ const LLVMContext &getContext () const ;
91
128
92
129
const Instruction *getInstruction () const ;
93
130
const BasicBlock *getParent () const ;
94
131
BasicBlock *getParent ();
95
- void dump () const ;
132
+
96
133
void removeFromParent ();
97
134
void eraseFromParent ();
98
135
99
- DPValue *getNextNode () { return &*std::next (getIterator ()); }
100
- DPValue *getPrevNode () { return &*std::prev (getIterator ()); }
136
+ DbgRecord *getNextNode () { return &*std::next (getIterator ()); }
137
+ DbgRecord *getPrevNode () { return &*std::prev (getIterator ()); }
138
+ void insertBefore (DbgRecord *InsertBefore);
139
+ void insertAfter (DbgRecord *InsertAfter);
140
+ void moveBefore (DbgRecord *MoveBefore);
141
+ void moveAfter (DbgRecord *MoveAfter);
142
+
143
+ DebugLoc getDebugLoc () const { return DbgLoc; }
144
+ void setDebugLoc (DebugLoc Loc) { DbgLoc = std::move (Loc); }
145
+
146
+ void dump () const ;
147
+
148
+ using self_iterator = simple_ilist<DbgRecord>::iterator;
149
+ using const_self_iterator = simple_ilist<DbgRecord>::const_iterator;
101
150
102
- using self_iterator = simple_ilist<DPValue>::iterator;
103
- using const_self_iterator = simple_ilist<DPValue>::const_iterator;
151
+ protected:
152
+ // / Similarly to Value, we avoid paying the cost of a vtable
153
+ // / by protecting the dtor and having deleteRecord dispatch
154
+ // / cleanup.
155
+ // / Use deleteRecord to delete a generic record.
156
+ ~DbgRecord () = default ;
157
+ };
158
+
159
+ // / Record of a variable value-assignment, aka a non instruction representation
160
+ // / of the dbg.value intrinsic.
161
+ // /
162
+ // / This class inherits from DebugValueUser to allow LLVM's metadata facilities
163
+ // / to update our references to metadata beneath our feet.
164
+ class DPValue : public DbgRecord , protected DebugValueUser {
165
+ friend class DebugValueUser ;
104
166
105
- enum class LocationType {
167
+ public:
168
+ enum class LocationType : uint8_t {
106
169
Declare,
107
170
Value,
108
171
Assign,
@@ -113,11 +176,18 @@ class DPValue : public ilist_node<DPValue>, private DebugValueUser {
113
176
// / Classification of the debug-info record that this DPValue represents.
114
177
// / Essentially, "is this a dbg.value or dbg.declare?". dbg.declares are not
115
178
// / currently supported, but it would be trivial to do so.
179
+ // / FIXME: We could use spare padding bits from DbgRecord for this.
116
180
LocationType Type;
117
181
118
- // / Marker that this DPValue is linked into.
119
- DPMarker *Marker = nullptr ;
182
+ // NB: there is no explicit "Value" field in this class, it's effectively the
183
+ // DebugValueUser superclass instead. The referred to Value can either be a
184
+ // ValueAsMetadata or a DIArgList.
185
+
186
+ DILocalVariable *Variable;
187
+ DIExpression *Expression;
188
+ DIExpression *AddressExpression;
120
189
190
+ public:
121
191
// / Create a new DPValue representing the intrinsic \p DVI, for example the
122
192
// / assignment represented by a dbg.value.
123
193
DPValue (const DbgVariableIntrinsic *DVI);
@@ -235,9 +305,6 @@ class DPValue : public ilist_node<DPValue>, private DebugValueUser {
235
305
bool isAddressOfVariable () const { return Type == LocationType::Declare; }
236
306
LocationType getType () const { return Type; }
237
307
238
- DebugLoc getDebugLoc () const { return DbgLoc; }
239
- void setDebugLoc (DebugLoc Loc) { DbgLoc = std::move (Loc); }
240
-
241
308
void setKillLocation ();
242
309
bool isKillLocation () const ;
243
310
@@ -270,12 +337,12 @@ class DPValue : public ilist_node<DPValue>, private DebugValueUser {
270
337
// / is described.
271
338
std::optional<uint64_t > getFragmentSizeInBits () const ;
272
339
273
- bool isEquivalentTo (const DPValue &Other) {
340
+ bool isEquivalentTo (const DPValue &Other) const {
274
341
return DbgLoc == Other.DbgLoc && isIdenticalToWhenDefined (Other);
275
342
}
276
343
// Matches the definition of the Instruction version, equivalent to above but
277
344
// without checking DbgLoc.
278
- bool isIdenticalToWhenDefined (const DPValue &Other) {
345
+ bool isIdenticalToWhenDefined (const DPValue &Other) const {
279
346
return std::tie (Type, DebugValues, Variable, Expression,
280
347
AddressExpression) ==
281
348
std::tie (Other.Type , Other.DebugValues , Other.Variable ,
@@ -314,43 +381,37 @@ class DPValue : public ilist_node<DPValue>, private DebugValueUser {
314
381
// / \returns A new dbg.value intrinsic representiung this DPValue.
315
382
DbgVariableIntrinsic *createDebugIntrinsic (Module *M,
316
383
Instruction *InsertBefore) const ;
317
- void setMarker (DPMarker *M) { Marker = M; }
318
-
319
- DPMarker *getMarker () { return Marker; }
320
- const DPMarker *getMarker () const { return Marker; }
321
-
322
- BasicBlock *getBlock ();
323
- const BasicBlock *getBlock () const ;
324
-
325
- Function *getFunction ();
326
- const Function *getFunction () const ;
327
384
328
- Module *getModule ();
329
- const Module *getModule () const ;
330
-
331
- LLVMContext &getContext ();
332
- const LLVMContext &getContext () const ;
333
-
334
- // / Insert this DPValue prior to \p InsertBefore. Must not be called if this
335
- // / is already contained in a DPMarker.
336
- void insertBefore (DPValue *InsertBefore);
337
- void insertAfter (DPValue *InsertAfter);
338
- void moveBefore (DPValue *MoveBefore);
339
- void moveAfter (DPValue *MoveAfter);
385
+ // / Handle changes to the location of the Value(s) that we refer to happening
386
+ // / "under our feet".
387
+ void handleChangedLocation (Metadata *NewLocation);
340
388
341
389
void print (raw_ostream &O, bool IsForDebug = false ) const ;
342
390
void print (raw_ostream &ROS, ModuleSlotTracker &MST, bool IsForDebug) const ;
391
+
392
+ // / Filter the DbgRecord range to DPValue types only and downcast.
393
+ static inline auto
394
+ filter (iterator_range<simple_ilist<DbgRecord>::iterator> R) {
395
+ return map_range (
396
+ make_filter_range (R, [](DbgRecord &E) { return isa<DPValue>(E); }),
397
+ [](DbgRecord &E) { return std::ref (cast<DPValue>(E)); });
398
+ }
399
+
400
+ // / Support type inquiry through isa, cast, and dyn_cast.
401
+ static bool classof (const DbgRecord *E) {
402
+ return E->getRecordKind () == ValueKind;
403
+ }
343
404
};
344
405
345
406
// / Per-instruction record of debug-info. If an Instruction is the position of
346
407
// / some debugging information, it points at a DPMarker storing that info. Each
347
408
// / marker points back at the instruction that owns it. Various utilities are
348
- // / provided for manipulating the DPValues contained within this marker.
409
+ // / provided for manipulating the DbgRecords contained within this marker.
349
410
// /
350
- // / This class has a rough surface area, because it's needed to preserve the one
351
- // / arefact that we can't yet eliminate from the intrinsic / dbg.value
352
- // / debug-info design: the order of DPValues/ records is significant, and
353
- // / duplicates can exist. Thus, if one has a run of debug-info records such as:
411
+ // / This class has a rough surface area, because it's needed to preserve the
412
+ // / one arefact that we can't yet eliminate from the intrinsic / dbg.value
413
+ // / debug-info design: the order of records is significant, and duplicates can
414
+ // / exist. Thus, if one has a run of debug-info records such as:
354
415
// / dbg.value(...
355
416
// / %foo = barinst
356
417
// / dbg.value(...
@@ -370,12 +431,11 @@ class DPMarker {
370
431
// / operations that move a marker from one instruction to another.
371
432
Instruction *MarkedInstr = nullptr ;
372
433
373
- // / List of DPValues, each recording a single variable assignment, the
374
- // / equivalent of a dbg.value intrinsic. There is a one-to-one relationship
375
- // / between each dbg.value in a block and each DPValue once the
376
- // / representation has been converted, and the ordering of DPValues is
377
- // / meaningful in the same was a dbg.values.
378
- simple_ilist<DPValue> StoredDPValues;
434
+ // / List of DbgRecords, the non-instruction equivalent of llvm.dbg.*
435
+ // / intrinsics. There is a one-to-one relationship between each debug
436
+ // / intrinsic in a block and each DbgRecord once the representation has been
437
+ // / converted, and the ordering is meaningful in the same way.
438
+ simple_ilist<DbgRecord> StoredDPValues;
379
439
bool empty () const { return StoredDPValues.empty (); }
380
440
381
441
const BasicBlock *getParent () const ;
@@ -395,40 +455,40 @@ class DPMarker {
395
455
void print (raw_ostream &ROS, ModuleSlotTracker &MST, bool IsForDebug) const ;
396
456
397
457
// / Produce a range over all the DPValues in this Marker.
398
- iterator_range<simple_ilist<DPValue >::iterator> getDbgValueRange ();
399
- iterator_range<simple_ilist<DPValue >::const_iterator>
458
+ iterator_range<simple_ilist<DbgRecord >::iterator> getDbgValueRange ();
459
+ iterator_range<simple_ilist<DbgRecord >::const_iterator>
400
460
getDbgValueRange () const ;
401
461
// / Transfer any DPValues from \p Src into this DPMarker. If \p InsertAtHead
402
462
// / is true, place them before existing DPValues, otherwise afterwards.
403
463
void absorbDebugValues (DPMarker &Src, bool InsertAtHead);
404
464
// / Transfer the DPValues in \p Range from \p Src into this DPMarker. If
405
465
// / \p InsertAtHead is true, place them before existing DPValues, otherwise
406
466
// afterwards.
407
- void absorbDebugValues (iterator_range<DPValue ::self_iterator> Range,
467
+ void absorbDebugValues (iterator_range<DbgRecord ::self_iterator> Range,
408
468
DPMarker &Src, bool InsertAtHead);
409
469
// / Insert a DPValue into this DPMarker, at the end of the list. If
410
470
// / \p InsertAtHead is true, at the start.
411
- void insertDPValue (DPValue *New, bool InsertAtHead);
471
+ void insertDPValue (DbgRecord *New, bool InsertAtHead);
412
472
// / Insert a DPValue prior to a DPValue contained within this marker.
413
- void insertDPValue (DPValue *New, DPValue *InsertBefore);
473
+ void insertDPValue (DbgRecord *New, DbgRecord *InsertBefore);
414
474
// / Insert a DPValue after a DPValue contained within this marker.
415
- void insertDPValueAfter (DPValue *New, DPValue *InsertAfter);
475
+ void insertDPValueAfter (DbgRecord *New, DbgRecord *InsertAfter);
416
476
// / Clone all DPMarkers from \p From into this marker. There are numerous
417
477
// / options to customise the source/destination, due to gnarliness, see class
418
478
// / comment.
419
479
// / \p FromHere If non-null, copy from FromHere to the end of From's DPValues
420
480
// / \p InsertAtHead Place the cloned DPValues at the start of StoredDPValues
421
481
// / \returns Range over all the newly cloned DPValues
422
- iterator_range<simple_ilist<DPValue >::iterator>
482
+ iterator_range<simple_ilist<DbgRecord >::iterator>
423
483
cloneDebugInfoFrom (DPMarker *From,
424
- std::optional<simple_ilist<DPValue >::iterator> FromHere,
484
+ std::optional<simple_ilist<DbgRecord >::iterator> FromHere,
425
485
bool InsertAtHead = false );
426
486
// / Erase all DPValues in this DPMarker.
427
- void dropDPValues ();
428
- // / Erase a single DPValue from this marker. In an ideal future, we would
487
+ void dropDbgValues ();
488
+ // / Erase a single DbgRecord from this marker. In an ideal future, we would
429
489
// / never erase an assignment in this way, but it's the equivalent to
430
- // / erasing a dbg.value from a block.
431
- void dropOneDPValue (DPValue *DPV );
490
+ // / erasing a debug intrinsic from a block.
491
+ void dropOneDbgValue (DbgRecord *DR );
432
492
433
493
// / We generally act like all llvm Instructions have a range of DPValues
434
494
// / attached to them, but in reality sometimes we don't allocate the DPMarker
@@ -438,8 +498,10 @@ class DPMarker {
438
498
// / DPValue in that range, but they should be using the Official (TM) API for
439
499
// / that.
440
500
static DPMarker EmptyDPMarker;
441
- static iterator_range<simple_ilist<DPValue>::iterator> getEmptyDPValueRange (){
442
- return make_range (EmptyDPMarker.StoredDPValues .end (), EmptyDPMarker.StoredDPValues .end ());
501
+ static iterator_range<simple_ilist<DbgRecord>::iterator>
502
+ getEmptyDPValueRange () {
503
+ return make_range (EmptyDPMarker.StoredDPValues .end (),
504
+ EmptyDPMarker.StoredDPValues .end ());
443
505
}
444
506
};
445
507
@@ -457,7 +519,7 @@ inline raw_ostream &operator<<(raw_ostream &OS, const DPValue &Value) {
457
519
// / to be inlined as it's frequently called, but also come after the declaration
458
520
// / of DPMarker. Thus: it's pre-declared by users like Instruction, then an
459
521
// / inlineable body defined here.
460
- inline iterator_range<simple_ilist<DPValue >::iterator>
522
+ inline iterator_range<simple_ilist<DbgRecord >::iterator>
461
523
getDbgValueRange (DPMarker *DbgMarker) {
462
524
if (!DbgMarker)
463
525
return DPMarker::getEmptyDPValueRange ();
0 commit comments