diff options
Diffstat (limited to 'llvm/lib')
| -rw-r--r-- | llvm/lib/Target/X86/X86ISelDAGToDAG.cpp | 22 |
1 files changed, 15 insertions, 7 deletions
diff --git a/llvm/lib/Target/X86/X86ISelDAGToDAG.cpp b/llvm/lib/Target/X86/X86ISelDAGToDAG.cpp index 3c6dfb45a56..1bc7af73a48 100644 --- a/llvm/lib/Target/X86/X86ISelDAGToDAG.cpp +++ b/llvm/lib/Target/X86/X86ISelDAGToDAG.cpp @@ -73,6 +73,7 @@ namespace { int JT; unsigned Align; // CP alignment. unsigned char SymbolFlags; // X86II::MO_* + bool NegateIndex = false; X86ISelAddressMode() : BaseType(RegBase), Base_FrameIndex(0), Scale(1), IndexReg(), Disp(0), @@ -115,6 +116,8 @@ namespace { dbgs() << " Base.FrameIndex " << Base_FrameIndex << '\n'; dbgs() << " Scale " << Scale << '\n' << "IndexReg "; + if (NegateIndex) + dbgs() << "negate "; if (IndexReg.getNode()) IndexReg.getNode()->dump(DAG); else @@ -271,6 +274,14 @@ namespace { Scale = getI8Imm(AM.Scale, DL); + // Negate the index if needed. + if (AM.NegateIndex) { + unsigned NegOpc = VT == MVT::i64 ? X86::NEG64r : X86::NEG32r; + SDValue Neg = SDValue(CurDAG->getMachineNode(NegOpc, DL, VT, MVT::i32, + AM.IndexReg), 0); + AM.IndexReg = Neg; + } + if (AM.IndexReg.getNode()) Index = AM.IndexReg; else @@ -1863,14 +1874,11 @@ bool X86DAGToDAGISel::matchAddressRecursively(SDValue N, X86ISelAddressMode &AM, } // Ok, the transformation is legal and appears profitable. Go for it. - SDValue Zero = CurDAG->getConstant(0, dl, N.getValueType()); - SDValue Neg = CurDAG->getNode(ISD::SUB, dl, N.getValueType(), Zero, RHS); - AM.IndexReg = Neg; + // Negation will be emitted later to avoid creating dangling nodes if this + // was an unprofitable LEA. + AM.IndexReg = RHS; + AM.NegateIndex = true; AM.Scale = 1; - - // Insert the new nodes into the topological ordering. - insertDAGNode(*CurDAG, N, Zero); - insertDAGNode(*CurDAG, N, Neg); return false; } |

