aboutsummaryrefslogtreecommitdiff
path: root/gcc/final.c
diff options
context:
space:
mode:
authorTom de Vries <vries@gcc.gnu.org>2014-07-09 21:03:44 +0000
committerTom de Vries <vries@gcc.gnu.org>2014-07-09 21:03:44 +0000
commit26e288bab56e529b3249c580ad31da4f0e77d76f (patch)
tree8f870b283ee2ce1cc19e7bdf8ea4acb72ccad8dc /gcc/final.c
parentf5168e47a83d6afcab6afa176da2ba466c383dbb (diff)
downloadgcc-26e288bab56e529b3249c580ad31da4f0e77d76f.zip
gcc-26e288bab56e529b3249c580ad31da4f0e77d76f.tar.gz
gcc-26e288bab56e529b3249c580ad31da4f0e77d76f.tar.bz2
Enable fuse-caller-save on self-recursive functions
2014-07-09 Tom de Vries <tom@codesourcery.com> * final.c (get_call_fndecl): Declare. (self_recursive_call_p): New function. (collect_fn_hard_reg_usage): Handle self-recursive function calls. * gcc.target/i386/fuse-caller-save-rec.c: New test. From-SVN: r212409
Diffstat (limited to 'gcc/final.c')
-rw-r--r--gcc/final.c14
1 files changed, 13 insertions, 1 deletions
diff --git a/gcc/final.c b/gcc/final.c
index cf2a278..304ae2a 100644
--- a/gcc/final.c
+++ b/gcc/final.c
@@ -225,6 +225,7 @@ static int final_addr_vec_align (rtx);
#endif
static int align_fuzz (rtx, rtx, int, unsigned);
static void collect_fn_hard_reg_usage (void);
+static tree get_call_fndecl (rtx);
/* Initialize data in final at the beginning of a compilation. */
@@ -4746,6 +4747,16 @@ make_pass_clean_state (gcc::context *ctxt)
return new pass_clean_state (ctxt);
}
+/* Return true if INSN is a call to the the current function. */
+
+static bool
+self_recursive_call_p (rtx insn)
+{
+ tree fndecl = get_call_fndecl (insn);
+ return (fndecl == current_function_decl
+ && decl_binds_to_current_def_p (fndecl));
+}
+
/* Collect hard register usage for the current function. */
static void
@@ -4771,7 +4782,8 @@ collect_fn_hard_reg_usage (void)
if (!NONDEBUG_INSN_P (insn))
continue;
- if (CALL_P (insn))
+ if (CALL_P (insn)
+ && !self_recursive_call_p (insn))
{
if (!get_call_reg_set_usage (insn, &insn_used_regs,
call_used_reg_set))