I haven't checked this patch in yet.  This implements a side effect that the divisor cannot be 0 after a divide executes. This allows us to fold the divide away:

a = b / c;
if (c == 0)
  dead();

This bootstraps on x86_64-pc-linux-gnu with no regressions, but I first wanted to check to see if there are some flags or conditions that should e checked in order NOT to do this optimization.  I am guessing there is probably something :-)    Anyway, this is how we straightforwardly add side effects now.

Does the patch conditions need tweaking to apply the side effect?

Andrew

commit 3bbcccf2ddd4d50cc5febf630bd8b55a45688352
Author: Andrew MacLeod <amacl...@redhat.com>
Date:   Mon Apr 4 16:13:57 2022 -0400

    Add divide by zero side effect.
    
    After a divide, we know the divisor is not zero.
    
            gcc/
            * gimple-range-side-effect.cc (stmt_side_effects::stmt_side_effects):
            Add support for all divides.
    
            gcc/testsuite/
            * gcc.dg/tree-ssa/evrp-zero.c: New.

diff --git a/gcc/gimple-range-side-effect.cc b/gcc/gimple-range-side-effect.cc
index 2c8c77dc569..548e4bea313 100644
--- a/gcc/gimple-range-side-effect.cc
+++ b/gcc/gimple-range-side-effect.cc
@@ -116,6 +116,23 @@ stmt_side_effects::stmt_side_effects (gimple *s)
     walk_stmt_load_store_ops (s, (void *)this, non_null_loadstore,
 			      non_null_loadstore);
 
+  if (is_a<gassign *> (s))
+    {
+      switch (gimple_assign_rhs_code (s))
+	{
+	case TRUNC_DIV_EXPR:
+	case CEIL_DIV_EXPR:
+	case FLOOR_DIV_EXPR:
+	case ROUND_DIV_EXPR:
+	case EXACT_DIV_EXPR:
+	  // Divide means operand 2 is not zero after this stmt.
+	  if (gimple_range_ssa_p (gimple_assign_rhs2 (s)))
+	    add_nonzero (gimple_assign_rhs2 (s));
+	  break;
+	default:
+	  break;
+	}
+    }
 }
 
 // -------------------------------------------------------------------------
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/evrp-zero.c b/gcc/testsuite/gcc.dg/tree-ssa/evrp-zero.c
new file mode 100644
index 00000000000..2b76e449c9b
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/tree-ssa/evrp-zero.c
@@ -0,0 +1,28 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fdump-tree-evrp " } */
+
+/* Side effects of divide are that the divisor cannot be 0. */
+
+void dead (int);
+
+void
+f1 (int a, int c) {
+  int b = a;
+  if (a / c > 10)
+    b = c;
+
+  if (c == 0)
+    dead (b);
+}
+
+
+void
+f2 (int a, int c) {
+  int nz = c == 0;
+  int b = a / c;
+  if (nz)
+    dead (0);
+}
+
+
+/* { dg-final { scan-tree-dump-not "dead" "evrp" } } */

Reply via email to