This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[patch] Fix tree-optimization/20139.


Hi,

Attached is a patch to fix tree-optimization/20139.

Consider the attached testcase.

TER changes

  p_2 = ABS_EXPR <x_1>;
  if (p_2 < 0.0) goto <L0>; else goto <L1>;

into

  if (ABS_EXPR <x> < 0.0) goto <L0>; else goto <L1>;

which would get folded by fold in find_taken_edge, which I recently
removed, causing a missed optimization at tree level.

The patch essentially restores fold for the last run of
cleanup_tree_cfg by running fold_cond_expr_cond immediately before
cleanup_tree_cfg.

IMHO, the right thing to do is to propagate the range of ABS_EXPR's
result, and fold the "if" statement accordingly.  I hope this patch
will be reverted in 4.1 once we start doing a good VRP.

Some people are for removing gcc.c-torture/execute/20020720-1.c as the
testcase in this patch will be stronger in that it checks that "if" is
gone at tree level.  Others don't see a reason for removing the old
testcase.  Personally, I can go with either option.

Tested on i686-pc-linux-gnu.  OK to apply?

Kazu Hirata

2005-02-22  Kazu Hirata  <kazu@cs.umass.edu>

	PR tree-optimization/20139
	* tree-cfg.c (fold_cond_expr_cond): Export.
	* tree-flow.h: Add a prototype for fold_cond_expr_cond.
	* tree-optimize.c (execute_cleanup_cfg_post_optimizing): Call
	fold_cond_expr_cond.

2005-02-22  Kazu Hirata  <kazu@cs.umass.edu>

	PR tree-optimization/20139
	* gcc.dg/tree-ssa/pr20139.c: New.

Index: tree-cfg.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-cfg.c,v
retrieving revision 2.151
diff -u -d -p -r2.151 tree-cfg.c
--- tree-cfg.c	21 Feb 2005 18:38:05 -0000	2.151
+++ tree-cfg.c	22 Feb 2005 16:57:21 -0000
@@ -442,7 +442,7 @@ create_bb (void *h, void *e, basic_block
 
 /* Fold COND_EXPR_COND of each COND_EXPR.  */
 
-static void
+void
 fold_cond_expr_cond (void)
 {
   basic_block bb;
Index: tree-flow.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-flow.h,v
retrieving revision 2.81
diff -u -d -p -r2.81 tree-flow.h
--- tree-flow.h	10 Feb 2005 00:32:44 -0000	2.81
+++ tree-flow.h	22 Feb 2005 16:57:21 -0000
@@ -477,6 +477,7 @@ extern void debug_loop_ir (void);
 extern void print_loop_ir (FILE *);
 extern void cleanup_dead_labels (void);
 extern void group_case_labels (void);
+extern void fold_cond_expr_cond (void);
 extern bool cleanup_tree_cfg (void);
 extern tree first_stmt (basic_block);
 extern tree last_stmt (basic_block);
Index: tree-optimize.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-optimize.c,v
retrieving revision 2.73
diff -u -d -p -r2.73 tree-optimize.c
--- tree-optimize.c	17 Feb 2005 16:19:41 -0000	2.73
+++ tree-optimize.c	22 Feb 2005 16:57:21 -0000
@@ -111,6 +111,11 @@ static struct tree_opt_pass pass_all_opt
 static void 
 execute_cleanup_cfg_post_optimizing (void)
 {
+  /* TODO: For 4.1, remove this call to fold_cond_expr_cond and fix
+     any missed optimization that may arise.  With good range
+     propagation and bit tracking, we should be able to eliminate this
+     call.  */
+  fold_cond_expr_cond ();
   cleanup_tree_cfg ();
   cleanup_dead_labels ();
   group_case_labels ();
--- /dev/null	2005-02-20 05:55:40.284481520 -0500
+++ testsuite/gcc.dg/tree-ssa/pr20139.c	2005-02-22 20:49:35.643197360 -0500
@@ -0,0 +1,39 @@
+/* Copyright (C) 2002, 2005  Free Software Foundation.
+
+   Ensure that fabs(x) < 0.0 optimization is working.
+
+   Written by Roger Sayle, 20th July 2002.
+   Adapted to the tree optimizers by Kazu Hirata.
+
+   This testcase is essentially the same as
+   gcc.c-torture/execute/20020720-1.c.  The only difference is that
+   this testcase ensures that the "if" statement is optimized away at
+   tree level, whereas 20020720-1.c tests that the "if" statement is
+   optimized away at some point during the compilation.  */
+
+/* { dg-do compile } */
+/* { dg-options "-O1 -fdump-tree-final_cleanup" } */
+
+extern void abort (void);
+extern double fabs (double);
+extern void link_error (void);
+
+void
+foo (double x)
+{
+  double p, q;
+
+  p = fabs (x);
+  q = 0.0;
+  if (p < q)
+    link_error ();
+}
+
+int
+main()
+{
+  foo (1.0);
+  return 0;
+}
+
+/* { dg-final { scan-tree-dump-times "if" 0 "final_cleanup"} } */


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]