diff options
author | Tom Stellard <[email protected]> | 2012-06-01 14:49:03 -0400 |
---|---|---|
committer | Tom Stellard <[email protected]> | 2012-06-01 16:52:26 -0400 |
commit | 0ebf2318b3d5e60adfc43e477b19acdc3cd4cc07 (patch) | |
tree | 0fc1f6ded65fc97e095420b7d3750f32098c0eb5 /src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp | |
parent | c108831d4451f624167d2c433282c6ac63541a79 (diff) |
radeon/llvm: Fix VTX_READ patterns
The VTX_READ instructions were using the ADDRParam ComplexPattern which
allows a load instruction's offset to be a register, but VTX_READ
instructions can only handle an immediate offset.
Also, the load_param pattern fragment had an erroneous return true;
statement that was causing it to match the wrong load instructions.
Diffstat (limited to 'src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp')
-rw-r--r-- | src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp | 29 |
1 files changed, 29 insertions, 0 deletions
diff --git a/src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp b/src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp index b14a360c3cc..d7b08b0aa77 100644 --- a/src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp +++ b/src/gallium/drivers/radeon/AMDILISelDAGToDAG.cpp @@ -69,6 +69,7 @@ private: bool SelectADDR8BitOffset(SDValue Addr, SDValue& Base, SDValue& Offset); bool SelectADDRReg(SDValue Addr, SDValue& Base, SDValue& Offset); + bool SelectADDRVTX_READ(SDValue Addr, SDValue &Base, SDValue &Offset); // Include the pieces autogenerated from the target description. #include "AMDGPUGenDAGISel.inc" @@ -556,6 +557,34 @@ bool AMDILDAGToDAGISel::SelectADDR8BitOffset(SDValue Addr, SDValue& Base, return true; } +bool AMDILDAGToDAGISel::SelectADDRVTX_READ(SDValue Addr, SDValue &Base, + SDValue &Offset) +{ + ConstantSDNode * IMMOffset; + + if (Addr.getOpcode() == ISD::ADD + && (IMMOffset = dyn_cast<ConstantSDNode>(Addr.getOperand(1))) + && isInt<16>(IMMOffset->getZExtValue())) { + + Base = Addr.getOperand(0); + Offset = CurDAG->getTargetConstant(IMMOffset->getZExtValue(), MVT::i32); + return true; + // If the pointer address is constant, we can move it to the offset field. + } else if ((IMMOffset = dyn_cast<ConstantSDNode>(Addr)) + && isInt<16>(IMMOffset->getZExtValue())) { + Base = CurDAG->getCopyFromReg(CurDAG->getEntryNode(), + CurDAG->getEntryNode().getDebugLoc(), + AMDIL::ZERO, MVT::i32); + Offset = CurDAG->getTargetConstant(IMMOffset->getZExtValue(), MVT::i32); + return true; + } + + // Default case, no offset + Base = Addr; + Offset = CurDAG->getTargetConstant(0, MVT::i32); + return true; +} + bool AMDILDAGToDAGISel::SelectADDRReg(SDValue Addr, SDValue& Base, SDValue& Offset) { if (Addr.getOpcode() == ISD::TargetExternalSymbol || |