[llvm] [SPARC] Use hardware byteswapper when we have V9 (PR #191720)
Sergei Barannikov via llvm-commits
llvm-commits at lists.llvm.org
Tue Apr 14 05:45:45 PDT 2026
================
@@ -3218,13 +3255,109 @@ SDValue SparcTargetLowering::PerformBITCASTCombine(SDNode *N,
return SDValue();
}
+SDValue SparcTargetLowering::PerformBSWAPCombine(SDNode *N,
+ DAGCombinerInfo &DCI) const {
+ SDLoc DL(N);
+ SelectionDAG &DAG = DCI.DAG;
+ SDValue Op0 = N->getOperand(0);
+ EVT Op0VT = N->getValueType(0);
+ bool IsLittleEndian = DAG.getDataLayout().isLittleEndian();
+
+ // Turn BSWAP (LOAD) -> ld*a #ASI_P(_L) on V9.
+ if (Subtarget->isV9() && ISD::isNormalLoad(Op0.getNode()) &&
+ Op0.getNode()->hasOneUse() &&
+ (Op0VT == MVT::i16 || Op0VT == MVT::i32 ||
+ (Subtarget->is64Bit() && Op0VT == MVT::i64))) {
+ SDValue Load = Op0;
+ LoadSDNode *LD = cast<LoadSDNode>(Load);
+
+ // Create the byte-swapping load.
+ SDValue Ops[] = {
+ LD->getChain(), // Chain
+ LD->getBasePtr(), // Ptr
+ DAG.getValueType(Op0VT) // VT
+ };
+
+ SDValue BSLoad = DAG.getMemIntrinsicNode(
+ IsLittleEndian ? SPISD::LOAD_BIG : SPISD::LOAD_LITTLE, DL,
+ DAG.getVTList(Op0VT == MVT::i64 ? MVT::i64 : MVT::i32, MVT::Other), Ops,
+ LD->getMemoryVT(), LD->getMemOperand());
+
+ // If this is an i16 load, insert the truncate.
+ SDValue ResVal = BSLoad;
+ if (Op0VT == MVT::i16)
+ ResVal = DAG.getNode(ISD::TRUNCATE, DL, MVT::i16, BSLoad);
+
+ // First, combine the bswap away. This makes the value produced by the
+ // load dead.
+ DCI.CombineTo(N, ResVal);
+
+ // Next, combine the load away, we give it a bogus result value but a real
+ // chain result. The result value is dead because the bswap is dead.
+ DCI.CombineTo(Load.getNode(), ResVal, BSLoad.getValue(1));
+
+ // Return N so it doesn't get rechecked!
+ return SDValue(N, 0);
----------------
s-barannikov wrote:
Can this just be
```suggestion
return DCI.CombineTo(N, ResVal);
```
https://github.com/llvm/llvm-project/pull/191720
More information about the llvm-commits
mailing list