[llvm] [AMDGPU] Only fold mul24+add into V_MAD_U64_U32 when operands fit in 24 bits (PR #198729)
Jay Foad via llvm-commits
llvm-commits at lists.llvm.org
Wed May 20 06:58:42 PDT 2026
================
@@ -1070,16 +1070,50 @@ multiclass IMAD32_Pats <VOP3_Pseudo inst> {
>;
}
+// AMDGPUmul_u24 only consumes the low 24 bits of its operands, and
+// simplifyMul24 may strip outer AND masks. V_MAD_U64_U32 does a full 32x32
+// multiply, so this fold is only valid when both operands are known to fit
+// in 24 unsigned bits at SDAG level.
+def AMDGPUmul_u24_24bit_ops : PatFrag<
+ (ops node:$src0, node:$src1),
+ (AMDGPUmul_u24 node:$src0, node:$src1),
+ [{
+ // AMDGPUmul_u24 is a PatFrags over an intrinsic and an SDNode; skip the
+ // intrinsic ID operand when needed.
+ unsigned BaseIdx = N->getOpcode() == ISD::INTRINSIC_WO_CHAIN ? 1 : 0;
+ return AMDGPUTargetLowering::numBitsUnsigned(N->getOperand(BaseIdx),
+ *CurDAG) <= 24 &&
+ AMDGPUTargetLowering::numBitsUnsigned(N->getOperand(BaseIdx + 1),
+ *CurDAG) <= 24;
+ }]>;
+
// Handle cases where amdgpu-codegenprepare-mul24 made a mul24 instead of a normal mul.
// We need to separate this because otherwise OtherPredicates would be overriden.
+// Preferred form: operands provably fit in 24 unsigned bits, no masking needed.
class IMAD32_Mul24_Pats_Impl<VOP3_Pseudo inst, SDPatternOperator AddOp> : GCNPat <
- (i64 (AddOp (i64 (AMDGPUmul_u24 i32:$src0, i32:$src1)), i64:$src2)),
+ (i64 (AddOp (i64 (AMDGPUmul_u24_24bit_ops i32:$src0, i32:$src1)), i64:$src2)),
(inst $src0, $src1, $src2, 0 /* clamp */)
+ > {
+ let AddedComplexity = 1;
+}
+
+// Fallback: AMDGPUmul_u24 only uses the low 24 bits of its operands, but
+// V_MAD_U64_U32 does a full 32x32 multiply. Mask the high bits explicitly so
+// the fold remains valid even when SDAG cannot prove the operands already fit
+// in 24 bits. DAGCombine folds the AND away when the high bits are known zero,
+// recovering the single-instruction form.
----------------
jayfoad wrote:
I don't understand this part. No DAG combine will remove the V_AND_B32 instructions that you generate here, will it? E.g. if only one of the operands is known to fit in 24 bits already.
In general, it is not a good idea to write selection patterns that generate more than one instruction, for this reason.
https://github.com/llvm/llvm-project/pull/198729
More information about the llvm-commits
mailing list