diff options
author | Thomas Lively <tlively@google.com> | 2019-10-29 22:31:22 -0700 |
---|---|---|
committer | Thomas Lively <tlively@google.com> | 2019-10-31 14:22:30 -0700 |
commit | 11850a6305c5778b180243eb06aefe86762dd4ce (patch) | |
tree | 88248bd32ea04c4c54abd01433fadddf6e6cc1fd /llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp | |
parent | d816d9bdc585bbf77a7a1c47a7199fd9e0c34402 (diff) | |
download | bcm5719-llvm-11850a6305c5778b180243eb06aefe86762dd4ce.tar.gz bcm5719-llvm-11850a6305c5778b180243eb06aefe86762dd4ce.zip |
[WebAssembly] Expand setcc of v2i64
Summary:
The SIMD spec does not include i64x2 comparisons, so they need to be
expanded. Using setOperationAction to expand them also causes f64x2
comparisons to be expanded, so setCondCodeAction needs to be used
instead. But since there are no legal condition codes, the legalizer
does not know how to expand the comparisons. We therefore manually
unroll the operation, taking care to fill each lane with -1 or 0
rather than 1 or 0 for consistency with the other vector comparisons.
Reviewers: aheejin
Subscribers: dschuff, sbc100, jgravelle-google, hiraditya, sunfish, llvm-commits
Tags: #llvm
Differential Revision: https://reviews.llvm.org/D69604
Diffstat (limited to 'llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp')
-rw-r--r-- | llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp | 30 |
1 files changed, 30 insertions, 0 deletions
diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp b/llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp index f06afdbcea9..2f698711a74 100644 --- a/llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp +++ b/llvm/lib/Target/WebAssembly/WebAssemblyISelLowering.cpp @@ -189,6 +189,11 @@ WebAssemblyTargetLowering::WebAssemblyTargetLowering( setOperationAction(Op, MVT::v2f64, Expand); } + // Expand operations not supported for i64x2 vectors + if (Subtarget->hasUnimplementedSIMD128()) + for (unsigned CC = 0; CC < ISD::SETCC_INVALID; ++CC) + setCondCodeAction(static_cast<ISD::CondCode>(CC), MVT::v2i64, Custom); + // Expand additional SIMD ops that V8 hasn't implemented yet if (!Subtarget->hasUnimplementedSIMD128()) { setOperationAction(ISD::FSQRT, MVT::v4f32, Expand); @@ -1011,6 +1016,8 @@ SDValue WebAssemblyTargetLowering::LowerOperation(SDValue Op, return LowerBUILD_VECTOR(Op, DAG); case ISD::VECTOR_SHUFFLE: return LowerVECTOR_SHUFFLE(Op, DAG); + case ISD::SETCC: + return LowerSETCC(Op, DAG); case ISD::SHL: case ISD::SRA: case ISD::SRL: @@ -1472,6 +1479,29 @@ WebAssemblyTargetLowering::LowerVECTOR_SHUFFLE(SDValue Op, return DAG.getNode(WebAssemblyISD::SHUFFLE, DL, Op.getValueType(), Ops); } +SDValue WebAssemblyTargetLowering::LowerSETCC(SDValue Op, + SelectionDAG &DAG) const { + SDLoc DL(Op); + // The legalizer does not know how to expand the comparison modes of i64x2 + // vectors because no comparison modes are supported. We could solve this by + // expanding all i64x2 SETCC nodes, but that seems to expand f64x2 SETCC nodes + // (which return i64x2 results) as well. So instead we manually unroll i64x2 + // comparisons here. + assert(Subtarget->hasUnimplementedSIMD128()); + assert(Op->getOperand(0)->getSimpleValueType(0) == MVT::v2i64); + SmallVector<SDValue, 2> LHS, RHS; + DAG.ExtractVectorElements(Op->getOperand(0), LHS); + DAG.ExtractVectorElements(Op->getOperand(1), RHS); + const SDValue &CC = Op->getOperand(2); + auto MakeLane = [&](unsigned I) { + return DAG.getNode(ISD::SELECT_CC, DL, MVT::i64, LHS[I], RHS[I], + DAG.getConstant(uint64_t(-1), DL, MVT::i64), + DAG.getConstant(uint64_t(0), DL, MVT::i64), CC); + }; + return DAG.getBuildVector(Op->getValueType(0), DL, + {MakeLane(0), MakeLane(1)}); +} + SDValue WebAssemblyTargetLowering::LowerAccessVectorElement(SDValue Op, SelectionDAG &DAG) const { |