sibcall vs function cse
Richard Henderson
rth@redhat.com
Tue Jul 17 20:31:00 GMT 2001
Sibcalls are supposed to be direct only, since we don't really
have a good way to control which register will be clobbered in
the process. But if !NO_FUNCTION_CSE, we force the address into
a register. Oops.
The fix being to stop prepare_call_address from being helpful here.
Originally tested on a part under nda; sanity checked on alpha
to see that the patch compiles in the fsf tree.
r~
* calls.c (prepare_call_address): New parameter SIBCALLP. If true,
don't force the function address into a register.
(expand_call, emit_library_call_value_1): Update callers.
* builtins.c (expand_builtin_apply): Likewise.
* expr.h (prepare_call_address): Update decl.
Index: builtins.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/builtins.c,v
retrieving revision 1.105
diff -c -p -d -r1.105 builtins.c
*** builtins.c 2001/07/11 20:35:51 1.105
--- builtins.c 2001/07/18 03:15:17
*************** expand_builtin_apply (function, argument
*** 1138,1144 ****
}
/* All arguments and registers used for the call are set up by now! */
! function = prepare_call_address (function, NULL_TREE, &call_fusage, 0);
/* Ensure address is valid. SYMBOL_REF is already valid, so no need,
and we don't want to load it into a register as an optimization,
--- 1138,1144 ----
}
/* All arguments and registers used for the call are set up by now! */
! function = prepare_call_address (function, NULL_TREE, &call_fusage, 0, 0);
/* Ensure address is valid. SYMBOL_REF is already valid, so no need,
and we don't want to load it into a register as an optimization,
Index: calls.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/calls.c,v
retrieving revision 1.187
diff -c -p -d -r1.187 calls.c
*** calls.c 2001/07/11 20:35:51 1.187
--- calls.c 2001/07/18 03:15:17
*************** calls_function_1 (exp, which)
*** 355,365 ****
CALL_INSN_FUNCTION_USAGE information. */
rtx
! prepare_call_address (funexp, fndecl, call_fusage, reg_parm_seen)
rtx funexp;
tree fndecl;
rtx *call_fusage;
int reg_parm_seen;
{
rtx static_chain_value = 0;
--- 355,366 ----
CALL_INSN_FUNCTION_USAGE information. */
rtx
! prepare_call_address (funexp, fndecl, call_fusage, reg_parm_seen, sibcallp)
rtx funexp;
tree fndecl;
rtx *call_fusage;
int reg_parm_seen;
+ int sibcallp;
{
rtx static_chain_value = 0;
*************** prepare_call_address (funexp, fndecl, ca
*** 377,383 ****
funexp = ((SMALL_REGISTER_CLASSES && reg_parm_seen)
? force_not_mem (memory_address (FUNCTION_MODE, funexp))
: memory_address (FUNCTION_MODE, funexp));
! else
{
#ifndef NO_FUNCTION_CSE
if (optimize && ! flag_no_function_cse)
--- 378,384 ----
funexp = ((SMALL_REGISTER_CLASSES && reg_parm_seen)
? force_not_mem (memory_address (FUNCTION_MODE, funexp))
: memory_address (FUNCTION_MODE, funexp));
! else if (! sibcallp)
{
#ifndef NO_FUNCTION_CSE
if (optimize && ! flag_no_function_cse)
*************** expand_call (exp, target, ignore)
*** 3038,3044 ****
}
funexp = prepare_call_address (funexp, fndecl, &call_fusage,
! reg_parm_seen);
load_register_parameters (args, num_actuals, &call_fusage, flags);
--- 3039,3045 ----
}
funexp = prepare_call_address (funexp, fndecl, &call_fusage,
! reg_parm_seen, pass == 0);
load_register_parameters (args, num_actuals, &call_fusage, flags);
*************** emit_library_call_value_1 (retval, orgfu
*** 4005,4011 ****
else
argnum = 0;
! fun = prepare_call_address (fun, NULL_TREE, &call_fusage, 0);
/* Now load any reg parms into their regs. */
--- 4006,4012 ----
else
argnum = 0;
! fun = prepare_call_address (fun, NULL_TREE, &call_fusage, 0, 0);
/* Now load any reg parms into their regs. */
Index: expr.h
===================================================================
RCS file: /cvs/gcc/egcs/gcc/expr.h,v
retrieving revision 1.85
diff -c -p -d -r1.85 expr.h
*** expr.h 2001/07/10 06:18:32 1.85
--- expr.h 2001/07/18 03:15:17
*************** extern rtx trampoline_address PARAMS ((t
*** 1112,1118 ****
in its original home. This becomes invalid if any more code is emitted. */
extern rtx hard_function_value PARAMS ((tree, tree, int));
! extern rtx prepare_call_address PARAMS ((rtx, tree, rtx *, int));
extern rtx expand_call PARAMS ((tree, rtx, int));
--- 1112,1118 ----
in its original home. This becomes invalid if any more code is emitted. */
extern rtx hard_function_value PARAMS ((tree, tree, int));
! extern rtx prepare_call_address PARAMS ((rtx, tree, rtx *, int, int));
extern rtx expand_call PARAMS ((tree, rtx, int));
More information about the Gcc-patches
mailing list