From 91635d0806bad0493405beac1cd528ed07cbaf87 Mon Sep 17 00:00:00 2001 From: Anatoly Sokolov Date: Sun, 8 Jun 2008 20:08:08 +0400 Subject: [PATCH] re PR target/36424 (avr-gcc use don't saved registers in ISR with -O3 ('-frename-registers' ) optimization) PR target/36424 * config/avr/avr.h (HARD_REGNO_RENAME_OK): Define. * config/avr/avr.c (avr_hard_regno_rename_ok): New function. * config/avr/avr-protos.h (avr_hard_regno_rename_ok): New prototype. From-SVN: r136562 --- gcc/ChangeLog | 7 +++++++ gcc/config/avr/avr-protos.h | 1 + gcc/config/avr/avr.c | 17 +++++++++++++++++ gcc/config/avr/avr.h | 3 +++ 4 files changed, 28 insertions(+) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index a64dc10d0f6..216f818920b 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,10 @@ +2008-07-08 Anatoly Sokolov + + PR target/36424 + * config/avr/avr.h (HARD_REGNO_RENAME_OK): Define. + * config/avr/avr.c (avr_hard_regno_rename_ok): New function. + * config/avr/avr-protos.h (avr_hard_regno_rename_ok): New prototype. + 2008-06-07 Danny Smith * config/i386/cygming.h (MAYBE_UWIN_CPP_BUILTINS): Remove. diff --git a/gcc/config/avr/avr-protos.h b/gcc/config/avr/avr-protos.h index 3fa3ea8e69c..73e70c6f8cb 100644 --- a/gcc/config/avr/avr-protos.h +++ b/gcc/config/avr/avr-protos.h @@ -37,6 +37,7 @@ extern int initial_elimination_offset (int from, int to); extern int avr_simple_epilogue (void); extern void gas_output_limited_string (FILE *file, const char *str); extern void gas_output_ascii (FILE *file, const char *str, size_t length); +extern int avr_hard_regno_rename_ok (unsigned int, unsigned int); #ifdef TREE_CODE extern void asm_output_external (FILE *file, tree decl, char *name); diff --git a/gcc/config/avr/avr.c b/gcc/config/avr/avr.c index 405f42f7632..e4820e623f0 100644 --- a/gcc/config/avr/avr.c +++ b/gcc/config/avr/avr.c @@ -5916,6 +5916,23 @@ avr_peep2_scratch_safe (rtx scratch) return 1; } +/* Return nonzero if register OLD_REG can be renamed to register NEW_REG. */ + +int +avr_hard_regno_rename_ok (unsigned int old_reg ATTRIBUTE_UNUSED, + unsigned int new_reg) +{ + /* Interrupt functions can only use registers that have already been + saved by the prologue, even if they would normally be + call-clobbered. */ + + if ((cfun->machine->is_interrupt || cfun->machine->is_signal) + && !df_regs_ever_live_p (new_reg)) + return 0; + + return 1; +} + /* Output a branch that tests a single bit of a register (QI, HI or SImode) or memory location in the I/O space (QImode only). diff --git a/gcc/config/avr/avr.h b/gcc/config/avr/avr.h index 6ae1c63d01e..90e62a30b16 100644 --- a/gcc/config/avr/avr.h +++ b/gcc/config/avr/avr.h @@ -1026,6 +1026,9 @@ mmcu=*:-mmcu=%*}" #define OBJECT_FORMAT_ELF +#define HARD_REGNO_RENAME_OK(OLD_REG, NEW_REG) \ + avr_hard_regno_rename_ok (OLD_REG, NEW_REG) + /* A C structure for machine-specific, per-function data. This is added to the cfun structure. */ struct machine_function GTY(()) -- 2.30.2