From 0064f49e76154354fa41c13403cac1da9069093a Mon Sep 17 00:00:00 2001 From: Wilco Dijkstra Date: Wed, 7 Dec 2016 14:55:31 +0000 Subject: [PATCH] GCC caches the whether a function is a leaf in crtl->is_leaf. GCC caches the whether a function is a leaf in crtl->is_leaf. Using this in the backend is best as leaf_function_p may not work correctly (eg. while emitting prolog or epilog code). There are many reads of crtl->is_leaf before it is initialized. Many targets do in targetm.frame_pointer_required (eg. arm, aarch64, i386, mips, sparc), which is called before register allocation by ira_setup_eliminable_regset and sched_init. Additionally, SHRINK_WRAPPING_ENABLED calls targetm.have_simple_return, which evaluates the condition of the simple_return instruction. On ARM this results in a call to use_simple_return_p which requires crtl->is_leaf to be set correctly. To fix this, initialize crtl->is_leaf in ira_setup_eliminable_regset and early on in ira. A bootstrap did not find any uninitialized reads of crtl->is_leaf on Thumb-2. A follow-up patch will remove incorrect uses of leaf_function_p from the ARM backend. gcc/ * gcc/ira.c (ira_setup_eliminable_regset): Initialize crtl->is_leaf. (ira): Move initialization of crtl->is_leaf earlier. From-SVN: r243347 --- gcc/ChangeLog | 5 +++++ gcc/ira.c | 16 +++++++++++----- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index c1b8784ce9d..5556c78eb06 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,8 @@ +2016-12-07 Wilco Dijkstra + + * gcc/ira.c (ira_setup_eliminable_regset): Initialize crtl->is_leaf. + (ira): Move initialization of crtl->is_leaf earlier. + 2016-12-07 Wilco Dijkstra * config/aarch64/aarch64.md (movti_aarch64): Change Ump to m. diff --git a/gcc/ira.c b/gcc/ira.c index ab322889c6c..4a95e3d22be 100644 --- a/gcc/ira.c +++ b/gcc/ira.c @@ -2266,6 +2266,10 @@ ira_setup_eliminable_regset (void) int i; static const struct {const int from, to; } eliminables[] = ELIMINABLE_REGS; + /* Setup is_leaf as frame_pointer_required may use it. This function + is called by sched_init before ira if scheduling is enabled. */ + crtl->is_leaf = leaf_function_p (); + /* FIXME: If EXIT_IGNORE_STACK is set, we will not save and restore sp for alloca. So we can't eliminate the frame pointer in that case. At some point, we should improve this by emitting the @@ -5079,6 +5083,13 @@ ira (FILE *f) clear_bb_flags (); + /* Determine if the current function is a leaf before running IRA + since this can impact optimizations done by the prologue and + epilogue thus changing register elimination offsets. + Other target callbacks may use crtl->is_leaf too, including + SHRINK_WRAPPING_ENABLED, so initialize as early as possible. */ + crtl->is_leaf = leaf_function_p (); + /* Perform target specific PIC register initialization. */ targetm.init_pic_reg (); @@ -5164,11 +5175,6 @@ ira (FILE *f) if (warn_clobbered) generate_setjmp_warnings (); - /* Determine if the current function is a leaf before running IRA - since this can impact optimizations done by the prologue and - epilogue thus changing register elimination offsets. */ - crtl->is_leaf = leaf_function_p (); - if (resize_reg_info () && flag_ira_loop_pressure) ira_set_pseudo_classes (true, ira_dump_file); -- 2.30.2