Commit b034930f by Ian Lance Taylor Committed by Ian Lance Taylor

arm.c (output_return_instruction): Only restore IP into SP if frame_pointer_needed.

	* config/arm/arm.c (output_return_instruction): Only restore IP
	into SP if frame_pointer_needed.

	* gcc.dg/arm-mmx-1.c: New test.

From-SVN: r76710
parent be446dfc
2004-01-27 Ian Lance Taylor <ian@wasabisystems.com>
* config/arm/arm.c (output_return_instruction): Only restore IP
into SP if frame_pointer_needed.
2004-01-27 Eric Botcazou <ebotcazou@libertysurf.fr>
* config/sparc/sparc.c (function_arg_pass_by_reference): Return 1
......
......@@ -8260,15 +8260,25 @@ output_return_instruction (rtx operand, int really_return, int reverse)
return_reg = reg_names[LR_REGNUM];
if ((live_regs_mask & (1 << IP_REGNUM)) == (1 << IP_REGNUM))
/* There are two possible reasons for the IP register being saved.
Either a stack frame was created, in which case IP contains the
old stack pointer, or an ISR routine corrupted it. If this in an
ISR routine then just restore IP, otherwise restore IP into SP. */
if (! IS_INTERRUPT (func_type))
{
live_regs_mask &= ~ (1 << IP_REGNUM);
live_regs_mask |= (1 << SP_REGNUM);
}
{
/* There are three possible reasons for the IP register
being saved. 1) a stack frame was created, in which case
IP contains the old stack pointer, or 2) an ISR routine
corrupted it, or 3) it was saved to align the stack on
iWMMXt. In case 1, restore IP into SP, otherwise just
restore IP. */
if (frame_pointer_needed)
{
live_regs_mask &= ~ (1 << IP_REGNUM);
live_regs_mask |= (1 << SP_REGNUM);
}
else
{
if (! IS_INTERRUPT (func_type)
&& ! TARGET_REALLY_IWMMXT)
abort ();
}
}
/* On some ARM architectures it is faster to use LDR rather than
LDM to load a single register. On other architectures, the
......
2004-01-27 Ian Lance Taylor <ian@wasabisystems.com>
* gcc.dg/arm-mmx-1.c: New test.
2004-01-27 Eric Botcazou <ebotcazou@libertysurf.fr>
* gcc.dg/20040127-1.c: New test.
......
/* Verify that if IP is saved to ensure stack alignment, we don't load
it into sp. */
/* { dg-do compile { target arm*-*-* strongarm*-*-* xscale*-*-*} } */
/* { dg-options "-O -mno-apcs-frame -mcpu=iwmmxt" } */
/* { dg-final { scan-assembler "ldmfd\[ ]sp!.*ip,\[ ]*pc" } } */
/* This function uses all the call-saved registers, namely r4, r5, r6,
r7, r8, r9, sl, fp. Since we also save pc, that leaves an odd
number of registers, and the compiler will push ip to align the
stack. Make sure that we restore ip into ip, not into sp as is
done when using a frame pointer. The -mno-apcs-frame option
permits the frame pointer to be used as an ordinary register. */
int
foo(int *a, int *b, int *c, int *d, int *tot)
{
int i, j, k, l, m, n, o;
*tot = 0;
for (i = *a; i < *b; i += *c)
for (j = *a; j < *b; j += *d)
for (k = *a; k < *c; k += *d)
for (l = *b; k < *c; k += *d)
for (m = *d; k < *c; k += *b)
*tot += i + j + k + l + m;
return *tot;
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment