re PR target/16407 (Unaligned access to local variables)
PR target/16407 * config/mips/mips-protos.h (mips_declare_common_object): Declare. * config/mips/mips.c (mips_declare_common_object): New function, mostly split out from... (mips_output_aligned_decl_common): ...here. * config/mips/mips.h (ASM_OUTPUT_LOCAL): Remove in favor of... (ASM_OUTPUT_ALIGNED_LOCAL): ...this new definition. * config/mips/iris6.h (ASM_OUTPUT_ALIGNED_LOCAL): Undefine this rather than ASM_OUTPUT_LOCAL. Call mips_declare_common_object. From-SVN: r84219
This commit is contained in:
parent
477eff9602
commit
48b2e0a72e
7 changed files with 58 additions and 10 deletions
|
@ -1,3 +1,15 @@
|
|||
2004-07-07 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
PR target/16407
|
||||
* config/mips/mips-protos.h (mips_declare_common_object): Declare.
|
||||
* config/mips/mips.c (mips_declare_common_object): New function,
|
||||
mostly split out from...
|
||||
(mips_output_aligned_decl_common): ...here.
|
||||
* config/mips/mips.h (ASM_OUTPUT_LOCAL): Remove in favor of...
|
||||
(ASM_OUTPUT_ALIGNED_LOCAL): ...this new definition.
|
||||
* config/mips/iris6.h (ASM_OUTPUT_ALIGNED_LOCAL): Undefine this
|
||||
rather than ASM_OUTPUT_LOCAL. Call mips_declare_common_object.
|
||||
|
||||
2004-07-07 John David Anglin <dave.anglin@nrc-cnrc.gc.ca>
|
||||
|
||||
PR c/16392
|
||||
|
|
|
@ -357,7 +357,7 @@ do \
|
|||
while (0)
|
||||
|
||||
/* ??? SGI assembler gives warning whenever .lcomm is used. */
|
||||
#undef ASM_OUTPUT_LOCAL
|
||||
#undef ASM_OUTPUT_ALIGNED_LOCAL
|
||||
#define ASM_OUTPUT_ALIGNED_LOCAL(STREAM, NAME, SIZE, ALIGN) \
|
||||
do \
|
||||
{ \
|
||||
|
@ -369,7 +369,8 @@ do \
|
|||
ASM_OUTPUT_SKIP (STREAM, SIZE); \
|
||||
} \
|
||||
else \
|
||||
mips_declare_object (STREAM, NAME, "\n\t.lcomm\t", ",%u\n", (int)(SIZE)); \
|
||||
mips_declare_common_object (STREAM, NAME, "\n\t.lcomm\t", \
|
||||
SIZE, ALIGN, false); \
|
||||
} \
|
||||
while (0)
|
||||
|
||||
|
|
|
@ -166,6 +166,9 @@ extern void mips_output_aligned_bss (FILE *, tree, const char *,
|
|||
extern void mips_output_aligned_decl_common (FILE *, tree, const char *,
|
||||
unsigned HOST_WIDE_INT,
|
||||
unsigned int);
|
||||
extern void mips_declare_common_object (FILE *, const char *,
|
||||
const char *, unsigned HOST_WIDE_INT,
|
||||
unsigned int, bool);
|
||||
extern void mips_declare_object (FILE *, const char *, const char *,
|
||||
const char *, ...);
|
||||
extern void mips_declare_object_name (FILE *, const char *, tree);
|
||||
|
|
|
@ -5987,17 +5987,32 @@ mips_output_aligned_decl_common (FILE *stream, tree decl, const char *name,
|
|||
":\n\t.space\t" HOST_WIDE_INT_PRINT_UNSIGNED "\n",
|
||||
size);
|
||||
}
|
||||
else if (TARGET_SGI_O32_AS)
|
||||
else
|
||||
/* The SGI o32 assembler doesn't accept an alignment. */
|
||||
mips_declare_common_object (stream, name, "\n\t.comm\t",
|
||||
size, align, !TARGET_SGI_O32_AS);
|
||||
}
|
||||
|
||||
/* Declare a common object of SIZE bytes using asm directive INIT_STRING.
|
||||
NAME is the name of the object and ALIGN is the required alignment
|
||||
in bytes. TAKES_ALIGNMENT_P is true if the directive takes a third
|
||||
alignment argument. */
|
||||
|
||||
void
|
||||
mips_declare_common_object (FILE *stream, const char *name,
|
||||
const char *init_string,
|
||||
unsigned HOST_WIDE_INT size,
|
||||
unsigned int align, bool takes_alignment_p)
|
||||
{
|
||||
if (!takes_alignment_p)
|
||||
{
|
||||
/* The SGI o32 assembler doesn't accept an alignment, so round up
|
||||
the size instead. */
|
||||
size += (align / BITS_PER_UNIT) - 1;
|
||||
size -= size % (align / BITS_PER_UNIT);
|
||||
mips_declare_object (stream, name, "\n\t.comm\t",
|
||||
mips_declare_object (stream, name, init_string,
|
||||
"," HOST_WIDE_INT_PRINT_UNSIGNED "\n", size);
|
||||
}
|
||||
else
|
||||
mips_declare_object (stream, name, "\n\t.comm\t",
|
||||
mips_declare_object (stream, name, init_string,
|
||||
"," HOST_WIDE_INT_PRINT_UNSIGNED ",%u\n",
|
||||
size, align / BITS_PER_UNIT);
|
||||
}
|
||||
|
|
|
@ -3189,9 +3189,10 @@ while (0)
|
|||
/* This says how to define a local common symbol (ie, not visible to
|
||||
linker). */
|
||||
|
||||
#define ASM_OUTPUT_LOCAL(STREAM, NAME, SIZE, ROUNDED) \
|
||||
mips_declare_object (STREAM, NAME, "\n\t.lcomm\t", ",%u\n", (int)(SIZE))
|
||||
|
||||
#ifndef ASM_OUTPUT_ALIGNED_LOCAL
|
||||
#define ASM_OUTPUT_ALIGNED_LOCAL(STREAM, NAME, SIZE, ALIGN) \
|
||||
mips_declare_common_object (STREAM, NAME, "\n\t.lcomm\t", SIZE, ALIGN, false)
|
||||
#endif
|
||||
|
||||
/* This says how to output an external. It would be possible not to
|
||||
output anything and let undefined symbol become external. However
|
||||
|
|
|
@ -1,3 +1,7 @@
|
|||
2004-07-07 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
* gcc.c-torture/execute/20040707-1.c: New test.
|
||||
|
||||
2004-07-06 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
* gcc.c-torture/execute/20040706-1.c: New test.
|
||||
|
|
12
gcc/testsuite/gcc.c-torture/execute/20040707-1.c
Normal file
12
gcc/testsuite/gcc.c-torture/execute/20040707-1.c
Normal file
|
@ -0,0 +1,12 @@
|
|||
struct s { char c1, c2; };
|
||||
void foo (struct s s)
|
||||
{
|
||||
static struct s s1;
|
||||
s1 = s;
|
||||
}
|
||||
int main ()
|
||||
{
|
||||
static struct s s2;
|
||||
foo (s2);
|
||||
exit (0);
|
||||
}
|
Loading…
Add table
Reference in a new issue