On 13-12-13 06:43, Jeff Law wrote:
Was this meant perhaps?
...
       || (reg_parm_stack_space != REG_PARM_STACK_SPACE
(current_function_decl))
I think you're probably right.

sibcall/tailcall basically re-use the current function's stack

Jeff,

Right, say we have function a tail-calling function b. If the sibcall optimization is done, function a deallocates it's stack frame before calling function b.

so if there's a
difference between REG_PARM_STACK_SPACE (fndecl) and REG_PARM_STACK_SPACE
(current_function_decl), then we can't perform a sibcall/tailcall optimization.

So the pattern that we want to check a property of fndecl and
current_function_decl and if they don't match, then don't do a sibcall is
repeated in a few places.


I wonder if OUTGOING_REG_PARM_STACK_SPACE makes a difference here.

If OUTGOING_REG_PARM_STACK_SPACE == 0, it is the responsibility of the callee to allocate the area reserved for arguments passed in registers. AFAIU, both functions a and b would do that in their own stack frame, and there's no need to test for reg_parm_stack_space != REG_PARM_STACK_SPACE (current_function_decl).

If OUTGOING_REG_PARM_STACK_SPACE != 0, it is the responsibility of the caller to allocate the area reserved for arguments passed in registers. Which means that function a and b share the space allocated by the caller of function a. AFAIU, what is required is reg_parm_stack_space <= REG_PARM_STACK_SPACE (current_function_decl).

So this might be a more precise fix:
...
diff --git a/gcc/calls.c b/gcc/calls.c
index 3963bc2..47dc844 100644
--- a/gcc/calls.c
+++ b/gcc/calls.c
@@ -2593,7 +2593,8 @@ expand_call (tree exp, rtx target, int ignore)
        /* If outgoing reg parm stack space changes, we can not do sibcall.  */
        || (OUTGOING_REG_PARM_STACK_SPACE (funtype)
          != OUTGOING_REG_PARM_STACK_SPACE (TREE_TYPE (current_function_decl)))
-      || (reg_parm_stack_space != REG_PARM_STACK_SPACE (fndecl))
+      || (OUTGOING_REG_PARM_STACK_SPACE (funtype)
+         && reg_parm_stack_space > REG_PARM_STACK_SPACE 
(current_function_decl))
  #endif
        /* Check whether the target is able to optimize the call
         into a sibcall.  */
...

But probably not a stage3 fix.

Assuming you bootstrap & test successfully, consider a patch which fixes this
pre-approved.


Bootstrapped and reg-tested attached patch on x86_64. Committed to trunk.

Thanks,
- Tom

jeff

2013-12-14  Tom de Vries  <t...@codesourcery.com>

	* calls.c (expand_call): Fix REG_PARM_STACK_SPACE comparison.

diff --git a/gcc/calls.c b/gcc/calls.c
index 2226e78..501474b 100644
--- a/gcc/calls.c
+++ b/gcc/calls.c
@@ -2595,7 +2595,7 @@ expand_call (tree exp, rtx target, int ignore)
       /* If outgoing reg parm stack space changes, we can not do sibcall.  */
       || (OUTGOING_REG_PARM_STACK_SPACE (funtype)
 	  != OUTGOING_REG_PARM_STACK_SPACE (TREE_TYPE (current_function_decl)))
-      || (reg_parm_stack_space != REG_PARM_STACK_SPACE (fndecl))
+      || (reg_parm_stack_space != REG_PARM_STACK_SPACE (current_function_decl))
 #endif
       /* Check whether the target is able to optimize the call
 	 into a sibcall.  */

Reply via email to