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][4.4] Fix PR42995


This fixes a regression on the 4.4 branch where we fail to inline
trivial wrappers because of a subtle error in estimate_num_insns.
The patch requires backport of other trivial fixes to not regress
in the testsuite and Wunreachable-2.c removal which is broken
(it warns on blocks we remove when now completely unrolling the loop).

Bootstrapped and tested on x86_64-unknown-linux-gnu, applied to
the branch.

Richard.

2010-02-08  Richard Guenther  <rguenther@suse.de>

	PR middle-end/42995
	* tree-inline.c (estimate_move_cost): Assert we are not called
	with a void type.
	(estimate_num_insns): Do not count the terminating void_type_node
	of a function argument type list.

	Backport from mainline:
	2010-01-06  Richard Guenther  <rguenther@suse.de>

	* ipa-inline.c (cgraph_decide_inlining_incrementally): Do
	not inline regular functions into always-inline functions.

	2010-01-05  Martin Jambor  <mjambor@suse.cz>

	PR tree-optimization/42462
	* ipa-inline.c (compute_inline_parameters): Pass node->decl instead of
	current_function_decl to helper functions and macros.

	* gcc.dg/tree-ssa/inline-4.c: New testcase.
	* gcc.dg/Wunreachable-2.c: Remove.

Index: gcc/tree-inline.c
===================================================================
*** gcc/tree-inline.c	(revision 156597)
--- gcc/tree-inline.c	(working copy)
*************** estimate_move_cost (tree type)
*** 2729,2734 ****
--- 2729,2736 ----
  {
    HOST_WIDE_INT size;
  
+   gcc_assert (!VOID_TYPE_P (type));
+ 
    size = int_size_in_bytes (type);
  
    if (size < 0 || size > MOVE_MAX_PIECES * MOVE_RATIO (!optimize_size))
*************** estimate_num_insns (gimple stmt, eni_wei
*** 2980,2986 ****
  	  {
  	    tree t;
  	    for (t = TYPE_ARG_TYPES (funtype); t; t = TREE_CHAIN (t))
! 	      cost += estimate_move_cost (TREE_VALUE (t));
  	  }
  	else
  	  {
--- 2982,2989 ----
  	  {
  	    tree t;
  	    for (t = TYPE_ARG_TYPES (funtype); t; t = TREE_CHAIN (t))
! 	      if (!VOID_TYPE_P (TREE_VALUE (t)))
! 		cost += estimate_move_cost (TREE_VALUE (t));
  	  }
  	else
  	  {
Index: gcc/testsuite/gcc.dg/tree-ssa/inline-4.c
===================================================================
*** gcc/testsuite/gcc.dg/tree-ssa/inline-4.c	(revision 0)
--- gcc/testsuite/gcc.dg/tree-ssa/inline-4.c	(revision 0)
***************
*** 0 ****
--- 1,26 ----
+ /* { dg-do compile } */
+ /* { dg-options "-O2 -fdump-tree-einline2" } */
+ 
+ extern int rand(void);
+ 
+ int get_data_for (int id)
+ {
+   return rand();
+ }
+ 
+ int my_id;
+ 
+ int main()
+ {
+   int res = get_data_for (my_id);
+   switch (res)
+     {
+       case 0:
+ 	  return 666;
+       default:
+ 	  return -1;
+     }
+ }
+ 
+ /* { dg-final { scan-tree-dump "Inlining get_data_for into main" "einline2" } } */
+ /* { dg-final { cleanup-tree-dump "einline2" } } */
Index: gcc/ipa-inline.c
===================================================================
*** gcc/ipa-inline.c	(revision 156597)
--- gcc/ipa-inline.c	(working copy)
*************** cgraph_decide_inlining_incrementally (st
*** 1418,1424 ****
      }
  
    /* Now do the automatic inlining.  */
!   if (mode != INLINE_ALL && mode != INLINE_ALWAYS_INLINE)
      for (e = node->callees; e; e = e->next_callee)
        {
  	if (!e->callee->local.inlinable
--- 1418,1427 ----
      }
  
    /* Now do the automatic inlining.  */
!   if (mode != INLINE_ALL && mode != INLINE_ALWAYS_INLINE
!       /* Never inline regular functions into always-inline functions
! 	 during incremental inlining.  */
!       && !node->local.disregard_inline_limits)
      for (e = node->callees; e; e = e->next_callee)
        {
  	if (!e->callee->local.inlinable
*************** compute_inline_parameters (struct cgraph
*** 1606,1622 ****
    node->global.stack_frame_offset = 0;
  
    /* Can this function be inlined at all?  */
!   node->local.inlinable = tree_inlinable_function_p (current_function_decl);
  
    /* Estimate the number of instructions for this function.
       ??? At -O0 we don't use this information except for the dumps, and
  	 even then only for always_inline functions.  But disabling this
  	 causes ICEs in the inline heuristics...  */
    inline_summary (node)->self_insns
!       = estimate_num_insns_fn (current_function_decl, &eni_inlining_weights);
    if (node->local.inlinable && !node->local.disregard_inline_limits)
      node->local.disregard_inline_limits
!       = DECL_DISREGARD_INLINE_LIMITS (current_function_decl);
  
    /* Inlining characteristics are maintained by the cgraph_mark_inline.  */
    node->global.insns = inline_summary (node)->self_insns;
--- 1609,1625 ----
    node->global.stack_frame_offset = 0;
  
    /* Can this function be inlined at all?  */
!   node->local.inlinable = tree_inlinable_function_p (node->decl);
  
    /* Estimate the number of instructions for this function.
       ??? At -O0 we don't use this information except for the dumps, and
  	 even then only for always_inline functions.  But disabling this
  	 causes ICEs in the inline heuristics...  */
    inline_summary (node)->self_insns
!       = estimate_num_insns_fn (node->decl, &eni_inlining_weights);
    if (node->local.inlinable && !node->local.disregard_inline_limits)
      node->local.disregard_inline_limits
!       = DECL_DISREGARD_INLINE_LIMITS (node->decl);
  
    /* Inlining characteristics are maintained by the cgraph_mark_inline.  */
    node->global.insns = inline_summary (node)->self_insns;


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