This is an archive of the discontinued LLVM Phabricator instance.

[InstCombine] Preserve FMF in foldLogicOfFCmps.
ClosedPublic

Authored by craig.topper on Mar 8 2022, 12:19 PM.

Details

Summary

This patch intersects the fast math flags from the two fcmps instead
of dropping them.

I poked at this a bunch with Alive2 for nnan and ninf flags and it seemed
to check out. With the other flags it told me "Couldn't prove the
correctness of the transformation". Not sure if I should just preserve
nnan and ninf?

Diff Detail

Event Timeline

craig.topper created this revision.Mar 8 2022, 12:19 PM
Herald added a project: Restricted Project. · View Herald TranscriptMar 8 2022, 12:19 PM
Herald added a subscriber: hiraditya. · View Herald Transcript
craig.topper requested review of this revision.Mar 8 2022, 12:19 PM
Herald added a project: Restricted Project. · View Herald TranscriptMar 8 2022, 12:19 PM

https://llvm.org/docs/LangRef.html#id306 says:

Any set of fast-math flags are legal on an fcmp instruction, but the only flags that have any effect on its semantics are those that allow assumptions to be made about the values of input arguments; namely nnan, ninf, and reassoc. See Fast-Math Flags for more information.

So please add tests with reassoc?

https://llvm.org/docs/LangRef.html#id306 says:

Any set of fast-math flags are legal on an fcmp instruction, but the only flags that have any effect on its semantics are those that allow assumptions to be made about the values of input arguments; namely nnan, ninf, and reassoc. See Fast-Math Flags for more information.

So please add tests with reassoc?

Alive2 can't seem to verify the reassoc preservation. Is it better to drop everything but nnan and ninf?

spatel added a comment.Mar 8 2022, 1:40 PM

https://llvm.org/docs/LangRef.html#id306 says:

Any set of fast-math flags are legal on an fcmp instruction, but the only flags that have any effect on its semantics are those that allow assumptions to be made about the values of input arguments; namely nnan, ninf, and reassoc. See Fast-Math Flags for more information.

So please add tests with reassoc?

"fast" implicitly covers that, so more tests with individual flags wouldn't add much IMO.

For this transform only -- because we are guaranteed to repeat the values in each fcmp -- I was expecting that we could 'or' the relevant flags. But there's a surprising corner case with true and false fcmp predicates according to Alive2:
https://alive2.llvm.org/ce/z/Nffn3L

The behavior -- blocking poison via predicate? -- does not seem to be documented in the LangRef.

Adding a TODO for unioning the flags. Intersecting at least an improvement for many cases where both instructions have the same flags.

nlopes added a comment.Mar 8 2022, 2:06 PM

For this transform only -- because we are guaranteed to repeat the values in each fcmp -- I was expecting that we could 'or' the relevant flags. But there's a surprising corner case with true and false fcmp predicates according to Alive2:
https://alive2.llvm.org/ce/z/Nffn3L

The behavior -- blocking poison via predicate? -- does not seem to be documented in the LangRef.

oops, that seems to be a bug in Alive2.
We convert fcmp true to true, but that is wrong as we lose the fast-math flags. Let me fix that.

nlopes added a comment.Mar 8 2022, 2:15 PM

For this transform only -- because we are guaranteed to repeat the values in each fcmp -- I was expecting that we could 'or' the relevant flags. But there's a surprising corner case with true and false fcmp predicates according to Alive2:
https://alive2.llvm.org/ce/z/Nffn3L

The behavior -- blocking poison via predicate? -- does not seem to be documented in the LangRef.

oops, that seems to be a bug in Alive2.
We convert fcmp true to true, but that is wrong as we lose the fast-math flags. Let me fix that.

Fixed (not poison anymore):

define i1 @src(double %a, double %b) {
%0:
  %cmp = fcmp ninf true double %a, %b
  %cmp1 = fcmp nnan oge double %a, %b
  %retval = and i1 %cmp, %cmp1
  ret i1 %retval
}
=>
define i1 @tgt(double %a, double %b) {
%0:
  %r = fcmp nnan ninf oeq double %a, %b
  ret i1 %r
}
Transformation doesn't verify!

ERROR: Value mismatch

Example:
double %a = #x0015250a74408022 (0.000000000000?)
double %b = #x88018b0635082009 (-0.000000000000?)

Source:
i1 %cmp = #x1 (1)
i1 %cmp1 = #x1 (1)
i1 %retval = #x1 (1)

Target:
i1 %r = #x0 (0)
Source value: #x1 (1)
Target value: #x0 (0)
spatel accepted this revision.Mar 8 2022, 3:13 PM

We convert fcmp true to true, but that is wrong as we lose the fast-math flags. Let me fix that.

Thanks for the fix! So we can remove the code comment about the fcmp predicates, and I think this patch is fine.
Note that we've (slowly) been moving away from relying on FMF on fcmp and trying to put FMF directly on all FP values instead. I'm not sure how many transforms are predicated on FMF on fcmp at this point, but it may go to zero some day.

This revision is now accepted and ready to land.Mar 8 2022, 3:13 PM

We convert fcmp true to true, but that is wrong as we lose the fast-math flags. Let me fix that.

Thanks for the fix! So we can remove the code comment about the fcmp predicates, and I think this patch is fine.
Note that we've (slowly) been moving away from relying on FMF on fcmp and trying to put FMF directly on all FP values instead. I'm not sure how many transforms are predicated on FMF on fcmp at this point, but it may go to zero some day.

So leave the union TODO, but drop the uncertainty about FCMP_TRUE/FALSE?

Remove mention of FCMP_TRUE/FALSE from FIXME.

lebedev.ri accepted this revision.Mar 9 2022, 2:52 AM
spatel added a comment.Mar 9 2022, 8:39 AM

We convert fcmp true to true, but that is wrong as we lose the fast-math flags. Let me fix that.

Thanks for the fix! So we can remove the code comment about the fcmp predicates, and I think this patch is fine.
Note that we've (slowly) been moving away from relying on FMF on fcmp and trying to put FMF directly on all FP values instead. I'm not sure how many transforms are predicated on FMF on fcmp at this point, but it may go to zero some day.

So leave the union TODO, but drop the uncertainty about FCMP_TRUE/FALSE?

Yes - LGTM.

This revision was landed with ongoing or failed builds.Mar 9 2022, 9:17 AM
This revision was automatically updated to reflect the committed changes.