mirror of
https://gcc.gnu.org/git/gcc.git
synced 2026-02-22 03:46:53 -05:00
df-scan.c (df_get_call_refs): Mark global registers as both a DF_REF_REG_USE and a non-clobber DF_REF_REG_DEF.
gcc/: 2007-10-22 Seongbae Park <seongbae.park@gmail.com> David S. Miller <davem@davemloft.net> * df-scan.c (df_get_call_refs): Mark global registers as both a DF_REF_REG_USE and a non-clobber DF_REF_REG_DEF. gcc/testsuite/: 2007-10-22 David S. Miller <davem@davemloft.net> * gcc.dg/globalreg-1.c: New test. From-SVN: r129573
This commit is contained in:
@@ -1,3 +1,9 @@
|
||||
2007-10-22 Seongbae Park <seongbae.park@gmail.com>
|
||||
David S. Miller <davem@davemloft.net>
|
||||
|
||||
* df-scan.c (df_get_call_refs): Mark global registers as both a
|
||||
DF_REF_REG_USE and a non-clobber DF_REF_REG_DEF.
|
||||
|
||||
2007-10-22 Richard Sandiford <rsandifo@nildram.co.uk>
|
||||
|
||||
PR target/33169
|
||||
|
||||
@@ -1584,12 +1584,19 @@ df_insn_refs_record (struct dataflow *dflow, basic_block bb, rtx insn)
|
||||
so they are recorded as used. */
|
||||
for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
|
||||
if (global_regs[i])
|
||||
df_uses_record (dflow, ®no_reg_rtx[i],
|
||||
DF_REF_REG_USE, bb, insn,
|
||||
0);
|
||||
{
|
||||
df_uses_record (dflow, ®no_reg_rtx[i],
|
||||
DF_REF_REG_USE, bb, insn, 0);
|
||||
df_ref_record (dflow, regno_reg_rtx[i], ®no_reg_rtx[i],
|
||||
bb, insn, DF_REF_REG_DEF, 0, true);
|
||||
}
|
||||
|
||||
EXECUTE_IF_SET_IN_BITMAP (df_invalidated_by_call, 0, ui, bi)
|
||||
df_ref_record (dflow, regno_reg_rtx[ui], ®no_reg_rtx[ui], bb,
|
||||
insn, DF_REF_REG_DEF, DF_REF_MAY_CLOBBER, false);
|
||||
{
|
||||
if (!global_regs[ui])
|
||||
df_ref_record (dflow, regno_reg_rtx[ui], ®no_reg_rtx[ui], bb,
|
||||
insn, DF_REF_REG_DEF, DF_REF_MAY_CLOBBER, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,3 +1,7 @@
|
||||
2007-10-22 David S. Miller <davem@davemloft.net>
|
||||
|
||||
* gcc.dg/globalreg-1.c: New test.
|
||||
|
||||
2007-10-18 Uros Bizjak <ubizjak@gmail.com>
|
||||
|
||||
PR target/32961
|
||||
|
||||
54
gcc/testsuite/gcc.dg/globalreg-1.c
Normal file
54
gcc/testsuite/gcc.dg/globalreg-1.c
Normal file
@@ -0,0 +1,54 @@
|
||||
/* { dg-do run { target sparc*-*-* } } */
|
||||
/* { dg-options "-std=gnu99 -Os" } */
|
||||
|
||||
/* This is a massively distilled test case based upon
|
||||
mm/memory.c:unmap_vmas() in the Linux kernel when compiled
|
||||
on sparc64 for SMP which uses a global register as the
|
||||
base of the per-cpu variable area.
|
||||
|
||||
Because of a bug in global register handling in the dataflow
|
||||
code, the loop-invariant pass would move 'expression(regval)'
|
||||
outside of the loop. */
|
||||
|
||||
extern void exit(int);
|
||||
extern void abort(void);
|
||||
|
||||
register unsigned long regval __asm__("g6");
|
||||
|
||||
extern void cond_resched(void);
|
||||
|
||||
unsigned int var;
|
||||
|
||||
static unsigned long expression(unsigned long v)
|
||||
{
|
||||
unsigned long ret;
|
||||
|
||||
__asm__("" : "=r" (ret) : "0" (0));
|
||||
return ret + v;
|
||||
}
|
||||
|
||||
void func(unsigned long *pp)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < 56; i++) {
|
||||
cond_resched();
|
||||
*pp = expression(regval);
|
||||
}
|
||||
}
|
||||
|
||||
void __attribute__((noinline)) cond_resched(void)
|
||||
{
|
||||
regval++;
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
unsigned long val;
|
||||
|
||||
regval = 100;
|
||||
func(&val);
|
||||
if (val != 156)
|
||||
abort();
|
||||
exit(0);
|
||||
}
|
||||
Reference in New Issue
Block a user