aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp
diff options
context:
space:
mode:
authorHeejin Ahn <aheejin@gmail.com>2022-09-21 14:48:34 -0700
committerHeejin Ahn <aheejin@gmail.com>2023-01-10 09:54:59 -0800
commite9ea7a0e20c27dc080dc16dc4b7c5c104801fe69 (patch)
treee7c0d3b404ca116eccae575a45c92b0818b7bf55 /llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp
parentbc21af6a43db45bf0d0192afab0a079ecf400aa2 (diff)
downloadllvm-e9ea7a0e20c27dc080dc16dc4b7c5c104801fe69.zip
llvm-e9ea7a0e20c27dc080dc16dc4b7c5c104801fe69.tar.gz
llvm-e9ea7a0e20c27dc080dc16dc4b7c5c104801fe69.tar.bz2
[WebAssembly] Use LiveDebugValues analysis
This enables `LiveDebugValues` analysis for Wasm. `DBG_VALUE`s expire at the end of a BB, and this is the analysis extends their lifetime when possible, greatly increasing the coverage of variable debug info. Specifically, this removes the current constraint that this analysis is only used with physical registers, which was first introduced in D18421, because Wasm uses only virtual registers. I don't think there's anything inherent in this analysis that only applies to physical registers; it was just because all targets using this analysis ran this at the end of their compiliation pipeline, at which point all their vregs had been allocated, and Wasm's debug info infrastructure was not really set up yet, so it was not using it. This adds supports to Wasm-specific target-index operands, defined in https://github.com/llvm/llvm-project/blob/2166d9529a60d1cdedb733d2e4134c971f0969ec/llvm/lib/Target/WebAssembly/WebAssembly.h#L87-L100. Among these, `TI_LOCAL`, `TI_LOCAL_INDIRECT`, and `TI_OPERAND_STACK` are used by Wasm `DBG_VALUE` instructions. This does not yet handle mutable target indices, i.e., this does not terminate a `DBG_VALUE` for a local index when we encounter a new `local.set` or `local.tee`. It will be implemented as a follow-up. Reviewed By: dschuff, jmorse Differential Revision: https://reviews.llvm.org/D138943
Diffstat (limited to 'llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp')
-rw-r--r--llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp71
1 files changed, 59 insertions, 12 deletions
diff --git a/llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp b/llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp
index 9686f82..062b5f5 100644
--- a/llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp
+++ b/llvm/lib/CodeGen/LiveDebugValues/VarLocBasedImpl.cpp
@@ -299,6 +299,16 @@ private:
}
};
+ // Target indices used for wasm-specific locations.
+ struct WasmLoc {
+ int Index; // One of TargetIndex values defined in WebAssembly.h
+ int64_t Offset;
+ bool operator==(const WasmLoc &Other) const {
+ return Index == Other.Index && Offset == Other.Offset;
+ }
+ bool operator!=(const WasmLoc &Other) const { return !(*this == Other); }
+ };
+
/// Identity of the variable at this location.
const DebugVariable Var;
@@ -313,7 +323,8 @@ private:
InvalidKind = 0,
RegisterKind,
SpillLocKind,
- ImmediateKind
+ ImmediateKind,
+ WasmLocKind
};
enum class EntryValueLocKind {
@@ -332,6 +343,7 @@ private:
int64_t Immediate;
const ConstantFP *FPImm;
const ConstantInt *CImm;
+ WasmLoc WasmLocation;
MachineLocValue() : Hash(0) {}
};
@@ -348,6 +360,8 @@ private:
switch (Kind) {
case MachineLocKind::SpillLocKind:
return Value.SpillLocation == Other.Value.SpillLocation;
+ case MachineLocKind::WasmLocKind:
+ return Value.WasmLocation == Other.Value.WasmLocation;
case MachineLocKind::RegisterKind:
case MachineLocKind::ImmediateKind:
return Value.Hash == Other.Value.Hash;
@@ -366,6 +380,11 @@ private:
Other.Kind, Other.Value.SpillLocation.SpillBase,
Other.Value.SpillLocation.SpillOffset.getFixed(),
Other.Value.SpillLocation.SpillOffset.getScalable());
+ case MachineLocKind::WasmLocKind:
+ return std::make_tuple(Kind, Value.WasmLocation.Index,
+ Value.WasmLocation.Offset) <
+ std::make_tuple(Other.Kind, Other.Value.WasmLocation.Index,
+ Other.Value.WasmLocation.Offset);
case MachineLocKind::RegisterKind:
case MachineLocKind::ImmediateKind:
return std::tie(Kind, Value.Hash) <
@@ -429,6 +448,9 @@ private:
} else if (Op.isCImm()) {
Kind = MachineLocKind::ImmediateKind;
Loc.CImm = Op.getCImm();
+ } else if (Op.isTargetIndex()) {
+ Kind = MachineLocKind::WasmLocKind;
+ Loc.WasmLocation = {Op.getIndex(), Op.getOffset()};
} else
llvm_unreachable("Invalid Op kind for MachineLoc.");
return {Kind, Loc};
@@ -562,6 +584,10 @@ private:
MOs.push_back(Orig);
break;
}
+ case MachineLocKind::WasmLocKind: {
+ MOs.push_back(Orig);
+ break;
+ }
case MachineLocKind::InvalidKind:
llvm_unreachable("Tried to produce DBG_VALUE for invalid VarLoc");
}
@@ -654,8 +680,9 @@ private:
}
#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
- // TRI can be null.
- void dump(const TargetRegisterInfo *TRI, raw_ostream &Out = dbgs()) const {
+ // TRI and TII can be null.
+ void dump(const TargetRegisterInfo *TRI, const TargetInstrInfo *TII,
+ raw_ostream &Out = dbgs()) const {
Out << "VarLoc(";
for (const MachineLoc &MLoc : Locs) {
if (Locs.begin() != &MLoc)
@@ -674,6 +701,22 @@ private:
case MachineLocKind::ImmediateKind:
Out << MLoc.Value.Immediate;
break;
+ case MachineLocKind::WasmLocKind: {
+ if (TII) {
+ auto Indices = TII->getSerializableTargetIndices();
+ auto Found =
+ find_if(Indices, [&](const std::pair<int, const char *> &I) {
+ return I.first == MLoc.Value.WasmLocation.Index;
+ });
+ assert(Found != Indices.end());
+ Out << Found->second;
+ if (MLoc.Value.WasmLocation.Offset > 0)
+ Out << " + " << MLoc.Value.WasmLocation.Offset;
+ } else {
+ Out << "WasmLoc";
+ }
+ break;
+ }
case MachineLocKind::InvalidKind:
llvm_unreachable("Invalid VarLoc in dump method");
}
@@ -1201,7 +1244,7 @@ void VarLocBasedLDV::printVarLocInMBB(const MachineFunction &MF,
for (const VarLoc &VL : VarLocs) {
Out << " Var: " << VL.Var.getVariable()->getName();
Out << " MI: ";
- VL.dump(TRI, Out);
+ VL.dump(TRI, TII, Out);
}
}
Out << "\n";
@@ -1339,7 +1382,7 @@ void VarLocBasedLDV::transferDebugValue(const MachineInstr &MI,
if (all_of(MI.debug_operands(), [](const MachineOperand &MO) {
return (MO.isReg() && MO.getReg()) || MO.isImm() || MO.isFPImm() ||
- MO.isCImm();
+ MO.isCImm() || MO.isTargetIndex();
})) {
// Use normal VarLoc constructor for registers and immediates.
VarLoc VL(MI);
@@ -1452,7 +1495,7 @@ void VarLocBasedLDV::insertTransferDebugPair(
ProcessVarLoc(VL);
LLVM_DEBUG({
dbgs() << "Creating VarLoc for register copy:";
- VL.dump(TRI);
+ VL.dump(TRI, TII);
});
return;
}
@@ -1465,7 +1508,7 @@ void VarLocBasedLDV::insertTransferDebugPair(
ProcessVarLoc(VL);
LLVM_DEBUG({
dbgs() << "Creating VarLoc for spill:";
- VL.dump(TRI);
+ VL.dump(TRI, TII);
});
return;
}
@@ -1478,7 +1521,7 @@ void VarLocBasedLDV::insertTransferDebugPair(
ProcessVarLoc(VL);
LLVM_DEBUG({
dbgs() << "Creating VarLoc for restore:";
- VL.dump(TRI);
+ VL.dump(TRI, TII);
});
return;
}
@@ -1816,7 +1859,7 @@ bool VarLocBasedLDV::transferTerminator(MachineBasicBlock *CurMBB,
for (VarLoc &VL : VarLocs) {
// Copy OpenRanges to OutLocs, if not already present.
dbgs() << "Add to OutLocs in MBB #" << CurMBB->getNumber() << ": ";
- VL.dump(TRI);
+ VL.dump(TRI, TII);
}
});
VarLocSet &VLS = getVarLocsInMBB(CurMBB, OutLocs);
@@ -2056,10 +2099,14 @@ bool VarLocBasedLDV::isEntryValueCandidate(
/// Collect all register defines (including aliases) for the given instruction.
static void collectRegDefs(const MachineInstr &MI, DefinedRegsSet &Regs,
const TargetRegisterInfo *TRI) {
- for (const MachineOperand &MO : MI.operands())
- if (MO.isReg() && MO.isDef() && MO.getReg())
+ for (const MachineOperand &MO : MI.operands()) {
+ if (MO.isReg() && MO.isDef() && MO.getReg() &&
+ Register::isPhysicalRegister(MO.getReg())) {
+ Regs.insert(MO.getReg());
for (MCRegAliasIterator AI(MO.getReg(), TRI, true); AI.isValid(); ++AI)
Regs.insert(*AI);
+ }
+ }
}
/// This routine records the entry values of function parameters. The values
@@ -2100,7 +2147,7 @@ bool VarLocBasedLDV::ExtendRanges(MachineFunction &MF,
TargetPassConfig *TPC, unsigned InputBBLimit,
unsigned InputDbgValLimit) {
(void)DomTree;
- LLVM_DEBUG(dbgs() << "\nDebug Range Extension\n");
+ LLVM_DEBUG(dbgs() << "\nDebug Range Extension: " << MF.getName() << "\n");
if (!MF.getFunction().getSubprogram())
// VarLocBaseLDV will already have removed all DBG_VALUEs.