[backport gcc-4.9/trunk r199203, fixes PR57340 regression from PR19599 patch ] gcc/ 2013-05-22 Ramana Radhakrishnan PR target/19599 PR target/57340 * config/arm/arm.c (any_sibcall_uses_r3): Rename to .. (any_sibcall_could_use_r3): this and handle indirect calls. (arm_get_frame_offsets): Rename use of any_sibcall_uses_r3. --- gcc-4.8.0/gcc/config/arm/arm.c.~1~ 2013-05-25 12:44:28.513538225 +0200 +++ gcc-4.8.0/gcc/config/arm/arm.c 2013-05-25 12:48:20.273426218 +0200 @@ -16834,11 +16834,27 @@ thumb_force_lr_save (void) || df_regs_ever_live_p (LR_REGNUM)); } +/* We do not know if r3 will be available because + we do have an indirect tailcall happening in this + particular case. */ +static bool +is_indirect_tailcall_p (rtx call) +{ + rtx pat = PATTERN (call); + + /* Indirect tail call. */ + pat = XVECEXP (pat, 0, 0); + if (GET_CODE (pat) == SET) + pat = SET_SRC (pat); + + pat = XEXP (XEXP (pat, 0), 0); + return REG_P (pat); +} /* Return true if r3 is used by any of the tail call insns in the current function. */ static bool -any_sibcall_uses_r3 (void) +any_sibcall_could_use_r3 (void) { edge_iterator ei; edge e; @@ -16852,7 +16868,8 @@ any_sibcall_uses_r3 (void) if (!CALL_P (call)) call = prev_nonnote_nondebug_insn (call); gcc_assert (CALL_P (call) && SIBLING_CALL_P (call)); - if (find_regno_fusage (call, USE, 3)) + if (find_regno_fusage (call, USE, 3) + || is_indirect_tailcall_p (call)) return true; } return false; @@ -17019,7 +17036,7 @@ arm_get_frame_offsets (void) /* If it is safe to use r3, then do so. This sometimes generates better code on Thumb-2 by avoiding the need to use 32-bit push/pop instructions. */ - if (! any_sibcall_uses_r3 () + if (! any_sibcall_could_use_r3 () && arm_size_return_regs () <= 12 && (offsets->saved_regs_mask & (1 << 3)) == 0) {