This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Fix powerpc zapping static chain
- From: Alan Modra <amodra at bigpond dot net dot au>
- To: gcc-patches at gcc dot gnu dot org
- Date: Mon, 24 Mar 2003 21:54:53 +1030
- Subject: Fix powerpc zapping static chain
The following testcase compiled with powerpc-linux-gcc -fpic shows r11,
the static chain pointer, being zapped inside function bar.
extern int x;
int foo (void)
{
int y;
int bar (void) { return x + y; }
return bar ();
}
This patch fixes the problem, and marks the instructions used to save
and restore LR as possibly dead. See PR 8659 for why they might be
dead with new-ra.
* config/rs6000/rs6000.c (rs6000_emit_prologue): Use r12 for
save_LR_around_toc_setup, and mark insns as maybe_dead. Simplify
cr_save_rtx test.
Bootstrapped, regtested powerpc-linux. OK mainline? 3.3 too?
Index: gcc/config/rs6000/rs6000.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/rs6000/rs6000.c,v
retrieving revision 1.445
diff -u -p -r1.445 rs6000.c
--- gcc/config/rs6000/rs6000.c 19 Mar 2003 03:23:44 -0000 1.445
+++ gcc/config/rs6000/rs6000.c 24 Mar 2003 10:31:28 -0000
@@ -10451,7 +10451,7 @@ rs6000_emit_prologue ()
rtx sp_reg_rtx = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
rtx frame_ptr_rtx = gen_rtx_REG (Pmode, 12);
rtx frame_reg_rtx = sp_reg_rtx;
- rtx cr_save_rtx = NULL;
+ rtx cr_save_rtx = NULL_RTX;
rtx insn;
int saving_FPRs_inline;
int using_store_multiple;
@@ -10738,7 +10738,7 @@ rs6000_emit_prologue ()
/* If r12 was used to hold the original sp, copy cr into r0 now
that it's free. */
- if (REGNO (frame_reg_rtx) == 12)
+ if (cr_save_rtx == NULL_RTX)
{
cr_save_rtx = gen_rtx_REG (SImode, 0);
emit_insn (gen_movesi_from_cr (cr_save_rtx));
@@ -10774,7 +10774,7 @@ rs6000_emit_prologue ()
&& regs_ever_live[RS6000_PIC_OFFSET_TABLE_REGNUM]))
{
/* If emit_load_toc_table will use the link register, we need to save
- it. We use R11 for this purpose because emit_load_toc_table
+ it. We use R12 for this purpose because emit_load_toc_table
can use register 0. This allows us to use a plain 'blr' to return
from the procedure more often. */
int save_LR_around_toc_setup = (TARGET_ELF
@@ -10783,14 +10783,14 @@ rs6000_emit_prologue ()
&& ! info->lr_save_p
&& EXIT_BLOCK_PTR->pred != NULL);
if (save_LR_around_toc_setup)
- emit_move_insn (gen_rtx_REG (Pmode, 11),
- gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM));
-
- rs6000_emit_load_toc_table (TRUE);
-
- if (save_LR_around_toc_setup)
- emit_move_insn (gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM),
- gen_rtx_REG (Pmode, 11));
+ {
+ rtx lr = gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM);
+ rs6000_maybe_dead (emit_move_insn (frame_ptr_rtx, lr));
+ rs6000_emit_load_toc_table (TRUE);
+ rs6000_maybe_dead (emit_move_insn (lr, frame_ptr_rtx));
+ }
+ else
+ rs6000_emit_load_toc_table (TRUE);
}
#if TARGET_MACHO
--
Alan Modra
IBM OzLabs - Linux Technology Centre