testsuite: Expand coverage for unaligned memory stores

Expand coverage for unaligned memory stores, for the "insvmisalignM"
patterns, for 2-byte, 4-byte, and 8-byte scalars, across byte alignments
of 1, 2, 4 and byte misalignments within from 0 up to 7 (there's some
redundancy there for the sake of simplicity of the test case), making
sure all data is written and no data is changed outside the area meant
to be written.

The test case has turned invaluable in verifying changes to the Alpha
backend, but functionality covered is generic, so I have concluded this
test qualifies for generic verification and does not have to be limited
to the Alpha-specific subset of the testsuite.

	gcc/testsuite/
	* gcc.c-torture/execute/misalign.c: New file.
This commit is contained in:
Maciej W. Rozycki 2024-12-25 22:23:39 +00:00
parent 5a089689a2
commit 665e0f9c08

View file

@ -0,0 +1,84 @@
typedef unsigned int __attribute__ ((mode (QI))) intw1_t;
typedef unsigned int __attribute__ ((mode (HI))) intw2_t;
typedef unsigned int __attribute__ ((mode (SI))) intw4_t;
typedef unsigned int __attribute__ ((mode (DI))) intw8_t;
#define MISALIGN_DEFINE_ONE(align, width, offset) \
static void \
misalign_check_one_ ## align ## width ## offset (void) \
{ \
static union \
{ \
intw1_t v[32]; \
struct __attribute__ ((packed)) \
{ \
intw1_t o[8 + offset]; \
intw ## width ## _t x; \
} x; \
intw ## align ## _t a; \
} \
dst = {{ [0 ... 31] = 0xaa }}; \
static const union \
{ \
intw1_t v[8]; \
intw ## width ## _t x; \
} \
src = {{ 1, 2, 3, 4, 5, 6, 7, 8 }}; \
int i, j; \
\
dst.x.x = src.x; \
asm ("" : : : "memory"); \
for (i = 0; i < 8 + offset; i++) \
if (dst.v[i] != 0xaa) \
__builtin_abort (); \
for (j = 0; i < 8 + offset + width; i++, j++) \
if (dst.v[i] != src.v[j]) \
__builtin_abort (); \
for (; i < sizeof (dst.v); i++) \
if (dst.v[i] != 0xaa) \
__builtin_abort (); \
}
#define MISALIGN_DEFINE_ONE_ALIGN_WIDTH(align, width) \
MISALIGN_DEFINE_ONE (align, width, 1) \
MISALIGN_DEFINE_ONE (align, width, 2) \
MISALIGN_DEFINE_ONE (align, width, 3) \
MISALIGN_DEFINE_ONE (align, width, 4) \
MISALIGN_DEFINE_ONE (align, width, 5) \
MISALIGN_DEFINE_ONE (align, width, 6) \
MISALIGN_DEFINE_ONE (align, width, 7)
MISALIGN_DEFINE_ONE_ALIGN_WIDTH (1, 2)
MISALIGN_DEFINE_ONE_ALIGN_WIDTH (1, 4)
MISALIGN_DEFINE_ONE_ALIGN_WIDTH (1, 8)
MISALIGN_DEFINE_ONE_ALIGN_WIDTH (2, 4)
MISALIGN_DEFINE_ONE_ALIGN_WIDTH (2, 8)
MISALIGN_DEFINE_ONE_ALIGN_WIDTH (4, 8)
#define MISALIGN_CHECK_ONE(align, width, offset) \
misalign_check_one_ ## align ## width ## offset ();
#define MISALIGN_CHECK_ONE_ALIGN_WIDTH(align, width) \
do \
{ \
MISALIGN_CHECK_ONE (align, width, 1); \
MISALIGN_CHECK_ONE (align, width, 2); \
MISALIGN_CHECK_ONE (align, width, 3); \
MISALIGN_CHECK_ONE (align, width, 4); \
MISALIGN_CHECK_ONE (align, width, 5); \
MISALIGN_CHECK_ONE (align, width, 6); \
MISALIGN_CHECK_ONE (align, width, 7); \
} \
while (0);
int
main (void)
{
MISALIGN_CHECK_ONE_ALIGN_WIDTH (1, 2);
MISALIGN_CHECK_ONE_ALIGN_WIDTH (1, 4);
MISALIGN_CHECK_ONE_ALIGN_WIDTH (1, 8);
MISALIGN_CHECK_ONE_ALIGN_WIDTH (2, 4);
MISALIGN_CHECK_ONE_ALIGN_WIDTH (2, 8);
MISALIGN_CHECK_ONE_ALIGN_WIDTH (4, 8);
return 0;
}