]> git.ipfire.org Git - thirdparty/gcc.git/commit
[frange] Clean up floating point relational folding.
authorAldy Hernandez <aldyh@redhat.com>
Tue, 19 Sep 2023 01:41:08 +0000 (21:41 -0400)
committerAldy Hernandez <aldyh@redhat.com>
Tue, 19 Sep 2023 19:18:21 +0000 (15:18 -0400)
commit7a4e57ffc9a97f172487dab81123ad62bebd4997
treea63ac93ec66354a0db1bd6f7a64459dc1ba29fc7
parent4f52e61e0665e760b95975b4d49437873967be2e
[frange] Clean up floating point relational folding.

The following patch removes all the special casing from the floating
point relational folding code.  Now all the code relating to folding
of relationals is in frelop_early_resolve() and in
operator_not_equal::fold_range() which requires a small tweak.

I have written new relational tests, and moved them to
gcc.dg/tree-ssa/vrp-float-relations-* for easy reference.  In the
tests it's easy to see the type of things we need to handle:

(a)
if (x != y)
  if (x == y)
    link_error ();

(b)
if (a != b)
  if (a != b) // Foldable as true.

(c)
/* We can thread BB2->BB4->BB5 even though we have no knowledge
   of the NANness of either x_1 or a_5.  */
__BB(4):
  x_1 = __PHI (__BB2: a_5(D), __BB3: b_4(D));
  if (x_1 __UNEQ a_5(D))

(d)
/* Even though x_1 and a_4 are equivalent on the BB2->BB4 path,
   we cannot fold the conditional because of possible NANs:  */
__BB(4):
  # x_1 = __PHI (__BB2: a_4(D), __BB3: 8.0e+0(3));
  if (x_1 == a_4(D))

(e)
if (cond)
  x = a;
else
  x = 8.0;

/* We can fold this as false on the path coming out of cond==1,
   regardless of NANs on either "x" or "a".  */
if (x < a)
  stuff ();

[etc, etc]

We can implement everything without either special casing,
get_identity_relation(), or adding new unordered relationals.

The basic idea is that if we accurately reflect NANs in op[12]_range,
this information gets propagated to the relevant edges, and there's no
need for unordered relations (VREL_UN*), because the information is in
the range itself.  This information is then used in
frelop_early_resolve() to fold certain combinations.

I don't mean this patch as a hard-no against implementing the
unordered relations Jakub preferred, but seeing that it's looking
cleaner and trivially simple without the added burden of more enums,
I'd like to flesh it out completely and then discuss if we still think
new codes are needed.

More testcases or corner cases are highly welcome.

In follow-up patches I will finish up unordered relation folding, and
come up with suitable tests.

gcc/ChangeLog:

* range-op-float.cc (frelop_early_resolve): Clean-up and remove
special casing.
(operator_not_equal::fold_range): Handle VREL_EQ.
(operator_lt::fold_range): Remove special casing for VREL_EQ.
(operator_gt::fold_range): Same.
(foperator_unordered_equal::fold_range): Same.

gcc/testsuite/ChangeLog:

* gcc.dg/tree-ssa/vrp-float-12.c: Moved to...
* gcc.dg/tree-ssa/vrp-float-relations-1.c: ...here.
* gcc.dg/tree-ssa/vrp-float-relations-2.c: New test.
* gcc.dg/tree-ssa/vrp-float-relations-3.c: New test.
* gcc.dg/tree-ssa/vrp-float-relations-4.c: New test.
gcc/range-op-float.cc
gcc/testsuite/gcc.dg/tree-ssa/vrp-float-relations-1.c [moved from gcc/testsuite/gcc.dg/tree-ssa/vrp-float-12.c with 100% similarity]
gcc/testsuite/gcc.dg/tree-ssa/vrp-float-relations-2.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/tree-ssa/vrp-float-relations-3.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/tree-ssa/vrp-float-relations-4.c [new file with mode: 0644]