@@ -16729,6 +16729,28 @@ SDValue DAGCombiner::visitFADDForFMACombine(SDNode *N) {
16729
16729
}
16730
16730
}
16731
16731
16732
+ // fold (fadd (freeze (fmul x, y)), z) -> (fma x, y, z).
16733
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
16734
+ N0.getOpcode() == ISD::FREEZE) {
16735
+ SDValue FrozenMul = N0.getOperand(0);
16736
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
16737
+ SDValue X = FrozenMul.getOperand(0);
16738
+ SDValue Y = FrozenMul.getOperand(1);
16739
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, X, Y, N1);
16740
+ }
16741
+ }
16742
+
16743
+ // fold (fadd x, (freeze (fmul y, z))) -> (fma y, z, x)
16744
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
16745
+ N1.getOpcode() == ISD::FREEZE) {
16746
+ SDValue FrozenMul = N1.getOperand(0);
16747
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
16748
+ SDValue X = FrozenMul.getOperand(0);
16749
+ SDValue Y = FrozenMul.getOperand(1);
16750
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, X, Y, N0);
16751
+ }
16752
+ }
16753
+
16732
16754
// More folding opportunities when target permits.
16733
16755
if (Aggressive) {
16734
16756
// fold (fadd (fma x, y, (fpext (fmul u, v))), z)
@@ -17006,6 +17028,30 @@ SDValue DAGCombiner::visitFSUBForFMACombine(SDNode *N) {
17006
17028
}
17007
17029
}
17008
17030
17031
+ // fold (fsub (freeze (fmul x, y)), z) -> (fma x, y, (fneg z))
17032
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
17033
+ N0.getOpcode() == ISD::FREEZE) {
17034
+ SDValue FrozenMul = N0.getOperand(0);
17035
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
17036
+ SDValue X = FrozenMul.getOperand(0);
17037
+ SDValue Y = FrozenMul.getOperand(1);
17038
+ SDValue NegZ = matcher.getNode(ISD::FNEG, SL, VT, N1);
17039
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, X, Y, NegZ);
17040
+ }
17041
+ }
17042
+
17043
+ // fold (fsub z, (freeze(fmul x, y))) -> (fma (fneg x), y, z)
17044
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
17045
+ N1.getOpcode() == ISD::FREEZE) {
17046
+ SDValue FrozenMul = N1.getOperand(0);
17047
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
17048
+ SDValue X = FrozenMul.getOperand(0);
17049
+ SDValue Y = FrozenMul.getOperand(1);
17050
+ SDValue NegX = matcher.getNode(ISD::FNEG, SL, VT, X);
17051
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, NegX, Y, N0);
17052
+ }
17053
+ }
17054
+
17009
17055
auto isReassociable = [&Options](SDNode *N) {
17010
17056
return Options.UnsafeFPMath || N->getFlags().hasAllowReassociation();
17011
17057
};
0 commit comments