[llvm] [AArch64] Fix #94909: Optimize vector fmul(sitofp(x), 0.5) -> scvtf(x, 2) (PR #141480)
JP Hafer via llvm-commits
llvm-commits at lists.llvm.org
Wed Jul 2 06:48:32 PDT 2025
================
@@ -3952,6 +3960,125 @@ static bool checkCVTFixedPointOperandWithFBits(SelectionDAG *CurDAG, SDValue N,
return true;
}
+static bool checkCVTFixedPointOperandWithFBitsForVectors(SelectionDAG *CurDAG,
+ SDValue N,
+ SDValue &FixedPos,
+ unsigned FloatWidth,
+ bool IsReciprocal) {
+
+ if (N->getNumOperands() < 1)
+ return false;
+
+ SDValue ImmediateNode = N.getOperand(0);
+ if (N.getOpcode() == ISD::BITCAST || N.getOpcode() == AArch64ISD::NVCAST) {
+ // This could have been a bitcast to a scalar
+ if (!ImmediateNode.getValueType().isVector())
+ return false;
+ }
+
+ if (ImmediateNode.getOpcode() == AArch64ISD::DUP ||
+ ImmediateNode.getOpcode() == AArch64ISD::MOVIshift ||
+ ImmediateNode.getOpcode() == AArch64ISD::FMOV ||
+ ImmediateNode.getOpcode() == ISD::SPLAT_VECTOR ||
+ ImmediateNode.getOpcode() == ISD::BUILD_VECTOR) {
+ auto *C = dyn_cast<ConstantSDNode>(ImmediateNode.getOperand(0));
+ if (!C)
+ return false;
+ }
+
+ if (ImmediateNode.getOpcode() == ISD::BUILD_VECTOR) {
+ // For BUILD_VECTOR, we must explicitly check if it's a constant splat.
+ BuildVectorSDNode *BVN = cast<BuildVectorSDNode>(ImmediateNode.getNode());
+ APInt SplatValue;
+ APInt SplatUndef;
+ unsigned SplatBitSize;
+ bool HasAnyUndefs;
+ if (!BVN->isConstantSplat(SplatValue, SplatUndef, SplatBitSize,
+ HasAnyUndefs)) {
+ return false;
+ }
+ }
+
+ APInt Imm;
+ bool IsIntConstant = false;
+ if (ImmediateNode.getOpcode() == AArch64ISD::MOVIshift) {
+ EVT NodeVT = N.getValueType();
+ Imm = APInt(NodeVT.getScalarSizeInBits(),
+ ImmediateNode.getConstantOperandVal(0)
+ << ImmediateNode.getConstantOperandVal(1));
+ IsIntConstant = true;
+ } else if (ImmediateNode.getOpcode() == ISD::Constant) {
----------------
jph-13 wrote:
Fair point. I fixed my shielding code and removed the FMUL from above.
```
if (!(ImmediateNode.getOpcode() == AArch64ISD::DUP ||
ImmediateNode.getOpcode() == AArch64ISD::MOVIshift ||
ImmediateNode.getOpcode() == ISD::BUILD_VECTOR ||
ImmediateNode.getOpcode() == ISD::Constant ||
ImmediateNode.getOpcode() == ISD::SPLAT_VECTOR)) {
return false;
}
if (ImmediateNode.getOpcode() != ISD::Constant) {
auto *C = dyn_cast<ConstantSDNode>(ImmediateNode.getOperand(0));
if (!C)
return false;
}
```
The ISD::Constant logic is needed for ```test_v4f32_div_const_4```
https://github.com/llvm/llvm-project/pull/141480
More information about the llvm-commits
mailing list