diff options
author | Richard Osborne <richard@xmos.com> | 2010-03-10 18:12:27 +0000 |
---|---|---|
committer | Richard Osborne <richard@xmos.com> | 2010-03-10 18:12:27 +0000 |
commit | 54a2c326702baedcce8011af78eadeb0bf03e875 (patch) | |
tree | 8c30ced22fe72e29b69e49dca79f2c774beb3cd0 /llvm/lib/Target/XCore/XCoreISelLowering.cpp | |
parent | 7e3283c055acaeab6c6bd441b7b72408d57f5143 (diff) | |
download | bcm5719-llvm-54a2c326702baedcce8011af78eadeb0bf03e875.tar.gz bcm5719-llvm-54a2c326702baedcce8011af78eadeb0bf03e875.zip |
Handle MVT::i64 type in DAG combine for ISD::ADD. Fold 64 bit
expression add(add(mul(x,y),a),b) -> lmul(x,y,a,b) if all
operands are zero extended.
llvm-svn: 98168
Diffstat (limited to 'llvm/lib/Target/XCore/XCoreISelLowering.cpp')
-rw-r--r-- | llvm/lib/Target/XCore/XCoreISelLowering.cpp | 31 |
1 files changed, 29 insertions, 2 deletions
diff --git a/llvm/lib/Target/XCore/XCoreISelLowering.cpp b/llvm/lib/Target/XCore/XCoreISelLowering.cpp index 82492193d20..3b3bb6d7dae 100644 --- a/llvm/lib/Target/XCore/XCoreISelLowering.cpp +++ b/llvm/lib/Target/XCore/XCoreISelLowering.cpp @@ -1342,11 +1342,13 @@ SDValue XCoreTargetLowering::PerformDAGCombine(SDNode *N, } break; case ISD::ADD: { - // Fold expressions such as add(add(mul(x,y),a),b) -> lmul(x, y, a, b). + // Fold 32 bit expressions such as add(add(mul(x,y),a),b) -> + // lmul(x, y, a, b). The high result of lmul will be ignored. // This is only profitable if the intermediate results are unused // elsewhere. SDValue Mul0, Mul1, Addend0, Addend1; - if (isADDADDMUL(SDValue(N, 0), Mul0, Mul1, Addend0, Addend1, true)) { + if (N->getValueType(0) == MVT::i32 && + isADDADDMUL(SDValue(N, 0), Mul0, Mul1, Addend0, Addend1, true)) { SDValue Zero = DAG.getConstant(0, MVT::i32); SDValue Ignored = DAG.getNode(XCoreISD::LMUL, dl, DAG.getVTList(MVT::i32, MVT::i32), Mul0, @@ -1354,6 +1356,31 @@ SDValue XCoreTargetLowering::PerformDAGCombine(SDNode *N, SDValue Result(Ignored.getNode(), 1); return Result; } + APInt HighMask = APInt::getHighBitsSet(64, 32); + // Fold 64 bit expression such as add(add(mul(x,y),a),b) -> + // lmul(x, y, a, b) if all operands are zero-extended. We do this + // before type legalization as it is messy to match the operands after + // that. + if (N->getValueType(0) == MVT::i64 && + isADDADDMUL(SDValue(N, 0), Mul0, Mul1, Addend0, Addend1, false) && + DAG.MaskedValueIsZero(Mul0, HighMask) && + DAG.MaskedValueIsZero(Mul1, HighMask) && + DAG.MaskedValueIsZero(Addend0, HighMask) && + DAG.MaskedValueIsZero(Addend1, HighMask)) { + SDValue Mul0L = DAG.getNode(ISD::EXTRACT_ELEMENT, dl, MVT::i32, + Mul0, DAG.getConstant(0, MVT::i32)); + SDValue Mul1L = DAG.getNode(ISD::EXTRACT_ELEMENT, dl, MVT::i32, + Mul1, DAG.getConstant(0, MVT::i32)); + SDValue Addend0L = DAG.getNode(ISD::EXTRACT_ELEMENT, dl, MVT::i32, + Addend0, DAG.getConstant(0, MVT::i32)); + SDValue Addend1L = DAG.getNode(ISD::EXTRACT_ELEMENT, dl, MVT::i32, + Addend1, DAG.getConstant(0, MVT::i32)); + SDValue Hi = DAG.getNode(XCoreISD::LMUL, dl, + DAG.getVTList(MVT::i32, MVT::i32), Mul0L, Mul1L, + Addend0L, Addend1L); + SDValue Lo(Hi.getNode(), 1); + return DAG.getNode(ISD::BUILD_PAIR, dl, MVT::i64, Lo, Hi); + } } break; case ISD::STORE: { |