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]

Fix profile updating in tailcall


Hi,
tailcall reduces number of invocations of function but forgets to update
profile.  Interestingly this causes code estimating number of iterations
to always return 1 iteration that results in newly formed loop beeing
peeled instead of unrolled and cause us to lose relative to ICC on very
important ackerman function benchmark ;).  Fixed thus.  I've also took
oppurtunity to fix cleanup of dump files as pointed out by Janis ages
ago.

Bootstrapped/regtested i686-pc-gnu-linux, comitted.

Honza

2005-07-27  Jan Hubicka  <jh@suse.cz>
	* tree-tailcall.c (decrease_profile): New function.
	(eliminate_tail_call): Use it.

	* inliner-1.c: Add cleanup of dumps.
	* val-prof-*.c: Likewise.
	* update-tailcall.c: New.
Index: tree-tailcall.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-tailcall.c,v
retrieving revision 2.45
diff -c -3 -p -r2.45 tree-tailcall.c
*** tree-tailcall.c	13 Jul 2005 22:35:28 -0000	2.45
--- tree-tailcall.c	27 Jul 2005 07:27:14 -0000
*************** adjust_return_value (basic_block bb, tre
*** 668,673 ****
--- 668,696 ----
    update_stmt (ret_stmt);
  }
  
+ /* Subtract COUNT and FREQUENCY from the basic block and it's
+    outgoing edge.  */
+ static void
+ decrease_profile (basic_block bb, gcov_type count, int frequency)
+ {
+   edge e;
+   bb->count -= count;
+   if (bb->count < 0)
+     bb->count = 0;
+   bb->frequency -= frequency;
+   if (bb->frequency < 0)
+     bb->frequency = 0;
+   if (!single_succ_p (bb))
+     {
+       gcc_assert (!EDGE_COUNT (bb->succs));
+       return;
+     }
+   e = single_succ_edge (bb);
+   e->count -= count;
+   if (e->count < 0)
+     e->count = 0;
+ }
+ 
  /* Eliminates tail call described by T.  TMP_VARS is a list of
     temporary variables used to copy the function arguments.  */
  
*************** eliminate_tail_call (struct tailcall *t)
*** 717,722 ****
--- 740,752 ----
        release_defs (t);
      }
  
+   /* Number of executions of function has reduced by the tailcall.  */
+   e = single_succ_edge (t->call_block);
+   decrease_profile (EXIT_BLOCK_PTR, e->count, EDGE_FREQUENCY (e));
+   decrease_profile (ENTRY_BLOCK_PTR, e->count, EDGE_FREQUENCY (e));
+   if (e->dest != EXIT_BLOCK_PTR)
+     decrease_profile (e->dest, e->count, EDGE_FREQUENCY (e));
+ 
    /* Replace the call by a jump to the start of function.  */
    e = redirect_edge_and_branch (single_succ_edge (t->call_block), first);
    gcc_assert (e);
Index: testsuite/gcc.dg/tree-prof/inliner-1.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/gcc.dg/tree-prof/inliner-1.c,v
retrieving revision 1.1
diff -c -3 -p -r1.1 inliner-1.c
*** testsuite/gcc.dg/tree-prof/inliner-1.c	25 May 2005 12:34:01 -0000	1.1
--- testsuite/gcc.dg/tree-prof/inliner-1.c	27 Jul 2005 07:27:19 -0000
*************** main ()
*** 35,37 ****
--- 35,38 ----
     declaration or other apperances of the string in dump.  */
  /* { dg-final-use { scan-tree-dump "cold_function ..;" "optimized"} } */
  /* { dg-final-use { scan-tree-dump-not "hot_function ..;" "optimized"} } */
+ /* { dg-final-use { cleanup-tree-dump "optimized" } } */
Index: testsuite/gcc.dg/tree-prof/update-tailcall.c
===================================================================
RCS file: testsuite/gcc.dg/tree-prof/update-tailcall.c
diff -N testsuite/gcc.dg/tree-prof/update-tailcall.c
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- testsuite/gcc.dg/tree-prof/update-tailcall.c	27 Jul 2005 07:27:19 -0000
***************
*** 0 ****
--- 1,18 ----
+ /* { dg-options "-O2 -fdump-tree-tailcall" } */
+ __attribute__ ((noinline))
+ int factorial(int x)
+ {
+    if (x == 1)
+      return 1;
+    else
+      return x*factorial(--x);
+ }
+ int gbl;
+ int
+ main()
+ {
+    gbl = factorial(100);
+    return 0;
+ }
+ /* { dg-final-use { scan-tree-dump-not "Invalid sum" "tailc"} } */
+ /* { dg-final-use { cleanup-tree-dump "tailc" } } */
Index: testsuite/gcc.dg/tree-prof/val-prof-1.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/gcc.dg/tree-prof/val-prof-1.c,v
retrieving revision 1.1
diff -c -3 -p -r1.1 val-prof-1.c
*** testsuite/gcc.dg/tree-prof/val-prof-1.c	28 May 2005 18:03:56 -0000	1.1
--- testsuite/gcc.dg/tree-prof/val-prof-1.c	27 Jul 2005 07:27:19 -0000
*************** main ()
*** 18,20 ****
--- 18,22 ----
  /* { dg-final-use { scan-tree-dump "Div.mod by constant n=257 transformation on insn" "tree_profile"} } */
  /* { dg-final-use { scan-tree-dump "if \\(n != 257\\)" "optimized"} } */
  /* { dg-final-use { scan-tree-dump-not "Invalid sum" "optimized"} } */
+ /* { dg-final-use { cleanup-tree-dump "optimized" } } */
+ /* { dg-final-use { cleanup-tree-dump "tree_profile" } } */
Index: testsuite/gcc.dg/tree-prof/val-prof-2.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/gcc.dg/tree-prof/val-prof-2.c,v
retrieving revision 1.1
diff -c -3 -p -r1.1 val-prof-2.c
*** testsuite/gcc.dg/tree-prof/val-prof-2.c	28 May 2005 18:03:56 -0000	1.1
--- testsuite/gcc.dg/tree-prof/val-prof-2.c	27 Jul 2005 07:27:19 -0000
*************** main ()
*** 28,30 ****
--- 28,32 ----
     didn't get optimized out.  */
  /* { dg-final-use { scan-tree-dump "n \\+ \\-1" "optimized"} } */
  /* { dg-final-use { scan-tree-dump-not "Invalid sum" "optimized"} } */
+ /* { dg-final-use { cleanup-tree-dump "optimized" } } */
+ /* { dg-final-use { cleanup-tree-dump "tree_profile" } } */
Index: testsuite/gcc.dg/tree-prof/val-prof-3.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/gcc.dg/tree-prof/val-prof-3.c,v
retrieving revision 1.1
diff -c -3 -p -r1.1 val-prof-3.c
*** testsuite/gcc.dg/tree-prof/val-prof-3.c	28 May 2005 18:03:56 -0000	1.1
--- testsuite/gcc.dg/tree-prof/val-prof-3.c	27 Jul 2005 07:27:19 -0000
*************** main ()
*** 28,30 ****
--- 28,32 ----
     didn't get optimized out.  */
  /* { dg-final-use { scan-tree-dump "if \\(n \\>" "optimized"} } */
  /* { dg-final-use { scan-tree-dump-not "Invalid sum" "optimized"} } */
+ /* { dg-final-use { cleanup-tree-dump "optimized" } } */
+ /* { dg-final-use { cleanup-tree-dump "tree_profile" } } */
Index: testsuite/gcc.dg/tree-prof/val-prof-4.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/gcc.dg/tree-prof/val-prof-4.c,v
retrieving revision 1.1
diff -c -3 -p -r1.1 val-prof-4.c
*** testsuite/gcc.dg/tree-prof/val-prof-4.c	28 May 2005 18:03:56 -0000	1.1
--- testsuite/gcc.dg/tree-prof/val-prof-4.c	27 Jul 2005 07:27:19 -0000
*************** main ()
*** 28,30 ****
--- 28,32 ----
     didn't get optimized out.  */
  /* { dg-final-use { scan-tree-dump "if \\(n \\>" "optimized"} } */
  /* { dg-final-use { scan-tree-dump-not "Invalid sum" "optimized"} } */
+ /* { dg-final-use { cleanup-tree-dump "optimized" } } */
+ /* { dg-final-use { cleanup-tree-dump "tree_profile" } } */


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