void DwarfExpression::addReg(int DwarfReg, const char *Comment) {
assert(DwarfReg >= 0 && "invalid negative dwarf register number");
- assert((LocationKind == Unknown || LocationKind == Register) &&
+ assert((isUnknownLocation() || isRegisterLocation()) &&
"location description already locked down");
LocationKind = Register;
if (DwarfReg < 32) {
void DwarfExpression::addBReg(int DwarfReg, int Offset) {
assert(DwarfReg >= 0 && "invalid negative dwarf register number");
- assert(LocationKind != Register && "location description already locked down");
+ assert(!isRegisterLocation() && "location description already locked down");
if (DwarfReg < 32) {
emitOp(dwarf::DW_OP_breg0 + DwarfReg);
} else {
}
void DwarfExpression::addSignedConstant(int64_t Value) {
- assert(LocationKind == Implicit || LocationKind == Unknown);
+ assert(isImplicitLocation() || isUnknownLocation());
LocationKind = Implicit;
emitOp(dwarf::DW_OP_consts);
emitSigned(Value);
}
void DwarfExpression::addUnsignedConstant(uint64_t Value) {
- assert(LocationKind == Implicit || LocationKind == Unknown);
+ assert(isImplicitLocation() || isUnknownLocation());
LocationKind = Implicit;
emitConstu(Value);
}
void DwarfExpression::addUnsignedConstant(const APInt &Value) {
- assert(LocationKind == Implicit || LocationKind == Unknown);
+ assert(isImplicitLocation() || isUnknownLocation());
LocationKind = Implicit;
unsigned Size = Value.getBitWidth();
}
// Handle simple register locations.
- if (LocationKind != Memory && !HasComplexExpression) {
+ if (!isMemoryLocation() && !HasComplexExpression) {
for (auto &Reg : DwarfRegs) {
if (Reg.DwarfRegNo >= 0)
addReg(Reg.DwarfRegNo, Reg.Comment);
SizeInBits = std::min<unsigned>(SizeInBits, SubRegisterSizeInBits);
// Emit a DW_OP_stack_value for implicit location descriptions.
- if (LocationKind == Implicit)
+ if (isImplicitLocation())
addStackValue();
// Emit the DW_OP_piece.
return;
}
case dwarf::DW_OP_plus_uconst:
- assert(LocationKind != Register);
+ assert(!isRegisterLocation());
emitOp(dwarf::DW_OP_plus_uconst);
emitUnsigned(Op->getArg(0));
break;
emitOp(Op->getOp());
break;
case dwarf::DW_OP_deref:
- assert(LocationKind != Register);
- if (LocationKind != Memory && ::isMemoryLocation(ExprCursor))
+ assert(!isRegisterLocation());
+ if (!isMemoryLocation() && ::isMemoryLocation(ExprCursor))
// Turning this into a memory location description makes the deref
// implicit.
LocationKind = Memory;
emitOp(dwarf::DW_OP_deref);
break;
case dwarf::DW_OP_constu:
- assert(LocationKind != Register);
+ assert(!isRegisterLocation());
emitConstu(Op->getArg(0));
break;
case dwarf::DW_OP_LLVM_convert: {
LocationKind = Implicit;
break;
case dwarf::DW_OP_swap:
- assert(LocationKind != Register);
+ assert(!isRegisterLocation());
emitOp(dwarf::DW_OP_swap);
break;
case dwarf::DW_OP_xderef:
- assert(LocationKind != Register);
+ assert(!isRegisterLocation());
emitOp(dwarf::DW_OP_xderef);
break;
case dwarf::DW_OP_deref_size:
}
}
- if (LocationKind == Implicit)
+ if (isImplicitLocation())
// Turn this into an implicit location description.
addStackValue();
}
/// Current Fragment Offset in Bits.
uint64_t OffsetInBits = 0;
- unsigned DwarfVersion;
/// Sometimes we need to add a DW_OP_bit_piece to describe a subregister.
- unsigned SubRegisterSizeInBits = 0;
- unsigned SubRegisterOffsetInBits = 0;
+ unsigned SubRegisterSizeInBits : 16;
+ unsigned SubRegisterOffsetInBits : 16;
/// The kind of location description being produced.
- enum { Unknown = 0, Register, Memory, Implicit } LocationKind = Unknown;
+ enum { Unknown = 0, Register, Memory, Implicit };
+ unsigned LocationKind : 3;
+ unsigned LocationFlags : 2;
+ unsigned DwarfVersion : 4;
+
+public:
+ bool isUnknownLocation() const {
+ return LocationKind == Unknown;
+ }
+
+ bool isMemoryLocation() const {
+ return LocationKind == Memory;
+ }
+
+ bool isRegisterLocation() const {
+ return LocationKind == Register;
+ }
+
+ bool isImplicitLocation() const {
+ return LocationKind == Implicit;
+ }
+
+protected:
/// Push a DW_OP_piece / DW_OP_bit_piece for emitting later, if one is needed
/// to represent a subregister.
void setSubRegisterPiece(unsigned SizeInBits, unsigned OffsetInBits) {
+ assert(SizeInBits < 65536 && OffsetInBits < 65536);
SubRegisterSizeInBits = SizeInBits;
SubRegisterOffsetInBits = OffsetInBits;
}
public:
DwarfExpression(unsigned DwarfVersion, DwarfCompileUnit &CU)
- : CU(CU), DwarfVersion(DwarfVersion) {}
+ : CU(CU), SubRegisterSizeInBits(0), SubRegisterOffsetInBits(0),
+ LocationKind(Unknown), LocationFlags(Unknown),
+ DwarfVersion(DwarfVersion) {}
/// This needs to be called last to commit any pending changes.
void finalize();
/// Emit an unsigned constant.
void addUnsignedConstant(const APInt &Value);
- bool isMemoryLocation() const { return LocationKind == Memory; }
- bool isUnknownLocation() const { return LocationKind == Unknown; }
-
/// Lock this down to become a memory location description.
void setMemoryLocationKind() {
- assert(LocationKind == Unknown);
+ assert(isUnknownLocation());
LocationKind = Memory;
}