diff options
author | Ahmed Bougacha <ahmed.bougacha@gmail.com> | 2017-03-07 20:53:06 +0000 |
---|---|---|
committer | Ahmed Bougacha <ahmed.bougacha@gmail.com> | 2017-03-07 20:53:06 +0000 |
commit | 5c7924fca51e0580bba5d9103b43558889a149bb (patch) | |
tree | ac3c65be657ec17fc673ef94a64061cb4e02a425 /llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp | |
parent | 38455ea8a61f18d2c6824b22faad49d9a8d5cd28 (diff) | |
download | bcm5719-llvm-5c7924fca51e0580bba5d9103b43558889a149bb.tar.gz bcm5719-llvm-5c7924fca51e0580bba5d9103b43558889a149bb.zip |
[GlobalISel] Avoid invalidating ValToVReg when translating no-op bitcast.
When we translate a no-op (same type) bitcast, we try to be clever and
only emit a COPY if we already assigned a vreg to the defined value.
However, when we didn't, we tried to assign to a reference into the
ValToVReg DenseMap, even though the RHS of the assignment
(getOrCreateVReg) could potentially grow that DenseMap, invalidating the
reference.
Avoid that by getting the source vreg first.
I audited the rest of the translator; this is the only tricky case.
The test is quite unwieldy, as the problem is caused by the DenseMap
growing, which happens after the 47th mapped value.
llvm-svn: 297208
Diffstat (limited to 'llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp')
-rw-r--r-- | llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp | 9 |
1 files changed, 7 insertions, 2 deletions
diff --git a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp index 70333057a76..1a70947a4aa 100644 --- a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp +++ b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp @@ -396,12 +396,17 @@ bool IRTranslator::translateSelect(const User &U, bool IRTranslator::translateBitCast(const User &U, MachineIRBuilder &MIRBuilder) { + // If we're bitcasting to the source type, we can reuse the source vreg. if (LLT{*U.getOperand(0)->getType(), *DL} == LLT{*U.getType(), *DL}) { + // Get the source vreg now, to avoid invalidating ValToVReg. + unsigned SrcReg = getOrCreateVReg(*U.getOperand(0)); unsigned &Reg = ValToVReg[&U]; + // If we already assigned a vreg for this bitcast, we can't change that. + // Emit a copy to satisfy the users we already emitted. if (Reg) - MIRBuilder.buildCopy(Reg, getOrCreateVReg(*U.getOperand(0))); + MIRBuilder.buildCopy(Reg, SrcReg); else - Reg = getOrCreateVReg(*U.getOperand(0)); + Reg = SrcReg; return true; } return translateCast(TargetOpcode::G_BITCAST, U, MIRBuilder); |