@@ -16736,6 +16736,28 @@ SDValue DAGCombiner::visitFADDForFMACombine(SDNode *N) {
16736
16736
}
16737
16737
}
16738
16738
16739
+ // fold (fadd (freeze (fmul x, y)), z) -> (fma x, y, z).
16740
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
16741
+ N0.getOpcode() == ISD::FREEZE) {
16742
+ SDValue FrozenMul = N0.getOperand(0);
16743
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
16744
+ SDValue X = FrozenMul.getOperand(0);
16745
+ SDValue Y = FrozenMul.getOperand(1);
16746
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, X, Y, N1);
16747
+ }
16748
+ }
16749
+
16750
+ // fold (fadd x, (freeze (fmul y, z))) -> (fma y, z, x)
16751
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
16752
+ N1.getOpcode() == ISD::FREEZE) {
16753
+ SDValue FrozenMul = N1.getOperand(0);
16754
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
16755
+ SDValue X = FrozenMul.getOperand(0);
16756
+ SDValue Y = FrozenMul.getOperand(1);
16757
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, X, Y, N0);
16758
+ }
16759
+ }
16760
+
16739
16761
// More folding opportunities when target permits.
16740
16762
if (Aggressive) {
16741
16763
// fold (fadd (fma x, y, (fpext (fmul u, v))), z)
@@ -17013,6 +17035,30 @@ SDValue DAGCombiner::visitFSUBForFMACombine(SDNode *N) {
17013
17035
}
17014
17036
}
17015
17037
17038
+ // fold (fsub (freeze (fmul x, y)), z) -> (fma x, y, (fneg z))
17039
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
17040
+ N0.getOpcode() == ISD::FREEZE) {
17041
+ SDValue FrozenMul = N0.getOperand(0);
17042
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
17043
+ SDValue X = FrozenMul.getOperand(0);
17044
+ SDValue Y = FrozenMul.getOperand(1);
17045
+ SDValue NegZ = matcher.getNode(ISD::FNEG, SL, VT, N1);
17046
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, X, Y, NegZ);
17047
+ }
17048
+ }
17049
+
17050
+ // fold (fsub z, (freeze(fmul x, y))) -> (fma (fneg x), y, z)
17051
+ if ((Options.UnsafeFPMath || N->getFlags().hasAllowContract()) &&
17052
+ N1.getOpcode() == ISD::FREEZE) {
17053
+ SDValue FrozenMul = N1.getOperand(0);
17054
+ if (matcher.match(FrozenMul, ISD::FMUL) && isContractableFMUL(FrozenMul)) {
17055
+ SDValue X = FrozenMul.getOperand(0);
17056
+ SDValue Y = FrozenMul.getOperand(1);
17057
+ SDValue NegX = matcher.getNode(ISD::FNEG, SL, VT, X);
17058
+ return matcher.getNode(PreferredFusedOpcode, SL, VT, NegX, Y, N0);
17059
+ }
17060
+ }
17061
+
17016
17062
auto isReassociable = [&Options](SDNode *N) {
17017
17063
return Options.UnsafeFPMath || N->getFlags().hasAllowReassociation();
17018
17064
};
0 commit comments