From 1d636cc69fa14e7f7daa4eef6ecb6a6a1413cfda Mon Sep 17 00:00:00 2001 From: Richard Guenther Date: Thu, 14 Jul 2005 07:39:56 +0000 Subject: [PATCH] Makefile.in (explow.o, [...]): Depend on target.h. 2005-07-14 Richard Guenther * Makefile.in (explow.o, reg-stack.o): Depend on target.h. * calls.c (expand_call): Pass fntype to hard_function_value. (emit_library_call_value_1): Likewise. * explow.c: Include target.h. (hard_function_value): Take extra argument, the fntype. Use new target hook for function_value. * expr.h (hard_function_value): Change prototype. * function.c (aggregate_value_p): Pass 0 as fntype to hard_function_value. (assign_parms): Use new target hook for function_value. Pass 0 as fntype to hard_function_value. (expand_function_end): Likewise. * reg-stack.c: Include target.h. (stack_result): Use new target hook for function_value. * target-def.h: New target hook function_value. * target.h: Likewise. * targhooks.c (default_function_value): New function. * targhooks.h (default_function_value): Declare. From-SVN: r102013 --- gcc/ChangeLog | 21 +++++++++++++++++++++ gcc/Makefile.in | 5 +++-- gcc/calls.c | 7 ++++--- gcc/explow.c | 14 +++++--------- gcc/expr.h | 2 +- gcc/function.c | 22 ++++++---------------- gcc/reg-stack.c | 11 +++-------- gcc/target-def.h | 5 ++++- gcc/target.h | 5 +++++ gcc/targhooks.c | 22 ++++++++++++++++++++++ gcc/targhooks.h | 2 ++ 11 files changed, 76 insertions(+), 40 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 0bf41ce000b..126409f6247 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,24 @@ +2005-07-14 Richard Guenther + + * Makefile.in (explow.o, reg-stack.o): Depend on target.h. + * calls.c (expand_call): Pass fntype to hard_function_value. + (emit_library_call_value_1): Likewise. + * explow.c: Include target.h. + (hard_function_value): Take extra argument, the fntype. + Use new target hook for function_value. + * expr.h (hard_function_value): Change prototype. + * function.c (aggregate_value_p): Pass 0 as fntype to + hard_function_value. + (assign_parms): Use new target hook for function_value. + Pass 0 as fntype to hard_function_value. + (expand_function_end): Likewise. + * reg-stack.c: Include target.h. + (stack_result): Use new target hook for function_value. + * target-def.h: New target hook function_value. + * target.h: Likewise. + * targhooks.c (default_function_value): New function. + * targhooks.h (default_function_value): Declare. + 2005-07-13 Ian Lance Taylor * config/mips/mips.h (CLZ_DEFINED_VALUE_AT_ZERO): Define. diff --git a/gcc/Makefile.in b/gcc/Makefile.in index 1c70c7ab9b9..2bc10923899 100644 --- a/gcc/Makefile.in +++ b/gcc/Makefile.in @@ -2079,7 +2079,7 @@ expmed.o : expmed.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(TREE_ toplev.h $(TM_P_H) langhooks.h explow.o : explow.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(TREE_H) \ $(FLAGS_H) hard-reg-set.h insn-config.h $(EXPR_H) $(OPTABS_H) $(RECOG_H) \ - toplev.h function.h $(GGC_H) $(TM_P_H) langhooks.h gt-explow.h + toplev.h function.h $(GGC_H) $(TM_P_H) langhooks.h gt-explow.h target.h optabs.o : optabs.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \ $(TREE_H) $(FLAGS_H) insn-config.h $(EXPR_H) $(OPTABS_H) libfuncs.h \ $(RECOG_H) reload.h toplev.h $(GGC_H) real.h $(TM_P_H) except.h \ @@ -2391,7 +2391,8 @@ recog.o : recog.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \ reg-stack.o : reg-stack.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) \ $(RTL_H) $(TREE_H) $(RECOG_H) $(REGS_H) hard-reg-set.h $(FLAGS_H) \ insn-config.h toplev.h reload.h function.h $(TM_P_H) $(GGC_H) \ - gt-reg-stack.h $(BASIC_BLOCK_H) output.h $(VARRAY_H) timevar.h tree-pass.h + gt-reg-stack.h $(BASIC_BLOCK_H) output.h $(VARRAY_H) timevar.h tree-pass.h \ + target.h sreal.o: sreal.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) sreal.h predict.o: predict.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \ $(TREE_H) $(FLAGS_H) insn-config.h $(BASIC_BLOCK_H) $(REGS_H) \ diff --git a/gcc/calls.c b/gcc/calls.c index 1613e883746..89f747fe2eb 100644 --- a/gcc/calls.c +++ b/gcc/calls.c @@ -2517,9 +2517,10 @@ expand_call (tree exp, rtx target, int ignore) { if (pcc_struct_value) valreg = hard_function_value (build_pointer_type (TREE_TYPE (exp)), - fndecl, (pass == 0)); + fndecl, NULL, (pass == 0)); else - valreg = hard_function_value (TREE_TYPE (exp), fndecl, (pass == 0)); + valreg = hard_function_value (TREE_TYPE (exp), fndecl, fntype, + (pass == 0)); } /* Precompute all register parameters. It isn't safe to compute anything @@ -3266,7 +3267,7 @@ emit_library_call_value_1 (int retval, rtx orgfun, rtx value, { #ifdef PCC_STATIC_STRUCT_RETURN rtx pointer_reg - = hard_function_value (build_pointer_type (tfom), 0, 0); + = hard_function_value (build_pointer_type (tfom), 0, 0, 0); mem_value = gen_rtx_MEM (outmode, pointer_reg); pcc_struct_value = 1; if (value == 0) diff --git a/gcc/explow.c b/gcc/explow.c index 510525edca6..23b124fbbb5 100644 --- a/gcc/explow.c +++ b/gcc/explow.c @@ -37,6 +37,7 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA #include "ggc.h" #include "recog.h" #include "langhooks.h" +#include "target.h" static rtx break_out_memory_refs (rtx); static void emit_stack_probe (rtx); @@ -1405,24 +1406,19 @@ probe_stack_range (HOST_WIDE_INT first, rtx size) /* Return an rtx representing the register or memory location in which a scalar value of data type VALTYPE was returned by a function call to function FUNC. - FUNC is a FUNCTION_DECL node if the precise function is known, - otherwise 0. + FUNC is a FUNCTION_DECL, FNTYPE a FUNCTION_TYPE node if the precise + function is known, otherwise 0. OUTGOING is 1 if on a machine with register windows this function should return the register in which the function will put its result and 0 otherwise. */ rtx -hard_function_value (tree valtype, tree func ATTRIBUTE_UNUSED, +hard_function_value (tree valtype, tree func, tree fntype, int outgoing ATTRIBUTE_UNUSED) { rtx val; -#ifdef FUNCTION_OUTGOING_VALUE - if (outgoing) - val = FUNCTION_OUTGOING_VALUE (valtype, func); - else -#endif - val = FUNCTION_VALUE (valtype, func); + val = targetm.calls.function_value (valtype, func ? func : fntype, outgoing); if (REG_P (val) && GET_MODE (val) == BLKmode) diff --git a/gcc/expr.h b/gcc/expr.h index 31c43c087d2..224e2857f2b 100644 --- a/gcc/expr.h +++ b/gcc/expr.h @@ -550,7 +550,7 @@ extern HOST_WIDE_INT int_expr_size (tree); /* Return an rtx that refers to the value returned by a function in its original home. This becomes invalid if any more code is emitted. */ -extern rtx hard_function_value (tree, tree, int); +extern rtx hard_function_value (tree, tree, tree, int); extern rtx prepare_call_address (rtx, rtx, rtx *, int, int); diff --git a/gcc/function.c b/gcc/function.c index 3fcc8b86089..160c80dfaa0 100644 --- a/gcc/function.c +++ b/gcc/function.c @@ -1732,7 +1732,7 @@ aggregate_value_p (tree exp, tree fntype) return 1; /* Make sure we have suitable call-clobbered regs to return the value in; if not, we must return it in memory. */ - reg = hard_function_value (type, 0, 0); + reg = hard_function_value (type, 0, fntype, 0); /* If we have something other than a REG (e.g. a PARALLEL), then assume it is OK. */ @@ -3055,13 +3055,8 @@ assign_parms (tree fndecl) { rtx real_decl_rtl; -#ifdef FUNCTION_OUTGOING_VALUE - real_decl_rtl = FUNCTION_OUTGOING_VALUE (TREE_TYPE (decl_result), - fndecl); -#else - real_decl_rtl = FUNCTION_VALUE (TREE_TYPE (decl_result), - fndecl); -#endif + real_decl_rtl = targetm.calls.function_value (TREE_TYPE (decl_result), + fndecl, true); REG_FUNCTION_VALUE_P (real_decl_rtl) = 1; /* The delay slot scheduler assumes that current_function_return_rtx holds the hard register containing the return value, not a @@ -4149,7 +4144,7 @@ expand_function_start (tree subr) /* In order to figure out what mode to use for the pseudo, we figure out what the mode of the eventual return register will actually be, and use that. */ - rtx hard_reg = hard_function_value (return_type, subr, 1); + rtx hard_reg = hard_function_value (return_type, subr, 0, 1); /* Structures that are returned in registers are not aggregate_value_p, so we may see a PARALLEL or a REG. */ @@ -4499,13 +4494,8 @@ expand_function_end (void) else value_address = XEXP (value_address, 0); -#ifdef FUNCTION_OUTGOING_VALUE - outgoing = FUNCTION_OUTGOING_VALUE (build_pointer_type (type), - current_function_decl); -#else - outgoing = FUNCTION_VALUE (build_pointer_type (type), - current_function_decl); -#endif + outgoing = targetm.calls.function_value (build_pointer_type (type), + current_function_decl, true); /* Mark this as a function return value so integrate will delete the assignment and USE below when inlining this function. */ diff --git a/gcc/reg-stack.c b/gcc/reg-stack.c index d1d8b9894bd..9f44f518095 100644 --- a/gcc/reg-stack.c +++ b/gcc/reg-stack.c @@ -172,6 +172,7 @@ #include "ggc.h" #include "timevar.h" #include "tree-pass.h" +#include "target.h" /* We use this array to cache info about insns, because otherwise we spend too much time in stack_regs_mentioned_p. @@ -667,14 +668,8 @@ stack_result (tree decl) result = DECL_RTL_IF_SET (DECL_RESULT (decl)); if (result != 0) - { -#ifdef FUNCTION_OUTGOING_VALUE - result - = FUNCTION_OUTGOING_VALUE (TREE_TYPE (DECL_RESULT (decl)), decl); -#else - result = FUNCTION_VALUE (TREE_TYPE (DECL_RESULT (decl)), decl); -#endif - } + result = targetm.calls.function_value (TREE_TYPE (DECL_RESULT (decl)), + decl, true); return result != 0 && STACK_REG_P (result) ? result : 0; } diff --git a/gcc/target-def.h b/gcc/target-def.h index 6f8470e4aec..a9921c7409a 100644 --- a/gcc/target-def.h +++ b/gcc/target-def.h @@ -438,6 +438,8 @@ Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. #define TARGET_CALLEE_COPIES hook_bool_CUMULATIVE_ARGS_mode_tree_bool_false #define TARGET_ARG_PARTIAL_BYTES hook_int_CUMULATIVE_ARGS_mode_tree_bool_0 +#define TARGET_FUNCTION_VALUE default_function_value + #define TARGET_CALLS { \ TARGET_PROMOTE_FUNCTION_ARGS, \ TARGET_PROMOTE_FUNCTION_RETURN, \ @@ -454,7 +456,8 @@ Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. TARGET_MUST_PASS_IN_STACK, \ TARGET_CALLEE_COPIES, \ TARGET_ARG_PARTIAL_BYTES, \ - TARGET_INVALID_ARG_FOR_UNPROTOTYPED_FN \ + TARGET_INVALID_ARG_FOR_UNPROTOTYPED_FN, \ + TARGET_FUNCTION_VALUE \ } #ifndef TARGET_UNWIND_TABLES_DEFAULT diff --git a/gcc/target.h b/gcc/target.h index 1b3aaf0cfc0..564c333136c 100644 --- a/gcc/target.h +++ b/gcc/target.h @@ -603,6 +603,11 @@ struct gcc_target is not allowed for this 'val' argument; NULL otherwise. */ const char *(*invalid_arg_for_unprototyped_fn) (tree typelist, tree funcdecl, tree val); + + /* Return an rtx for the return value location of the function + specified by FN_DECL_OR_TYPE with a return type of RET_TYPE. */ + rtx (*function_value) (tree ret_type, tree fn_decl_or_type, + bool outgoing); } calls; /* Return the diagnostic message string if conversion from FROMTYPE diff --git a/gcc/targhooks.c b/gcc/targhooks.c index 4fc6e10a30b..c0c42019a04 100644 --- a/gcc/targhooks.c +++ b/gcc/targhooks.c @@ -417,4 +417,26 @@ hook_bool_rtx_commutative_p (rtx x, int outer_code ATTRIBUTE_UNUSED) return COMMUTATIVE_P (x); } +rtx +default_function_value (tree ret_type ATTRIBUTE_UNUSED, + tree fn_decl_or_type, + bool outgoing ATTRIBUTE_UNUSED) +{ + /* The old interface doesn't handle receiving the function type. */ + if (fn_decl_or_type + && !DECL_P (fn_decl_or_type)) + fn_decl_or_type = NULL; + +#ifdef FUNCTION_OUTGOING_VALUE + if (outgoing) + return FUNCTION_OUTGOING_VALUE (ret_type, fn_decl_or_type); +#endif + +#ifdef FUNCTION_VALUE + return FUNCTION_VALUE (ret_type, fn_decl_or_type); +#else + return NULL_RTX; +#endif +} + #include "gt-targhooks.h" diff --git a/gcc/targhooks.h b/gcc/targhooks.h index ad526482ff2..a39d27df337 100644 --- a/gcc/targhooks.h +++ b/gcc/targhooks.h @@ -67,3 +67,5 @@ extern int hook_int_CUMULATIVE_ARGS_mode_tree_bool_0 extern const char *hook_invalid_arg_for_unprototyped_fn (tree, tree, tree); extern bool hook_bool_rtx_commutative_p (rtx, int); +extern rtx default_function_value (tree, tree, bool); +