https://gcc.gnu.org/g:1d2257dc850d088f6d9267b4624ba08533ab2475
commit r15-8649-g1d2257dc850d088f6d9267b4624ba08533ab2475 Author: Richard Earnshaw <rearn...@arm.com> Date: Fri Mar 21 15:20:03 2025 +0000 arm: testsuite: make unaligned-memcpy-*.c executable tests [PR91614] These tests have been looking for a very specific instruction sequence which has the tendency to be fairly unstable as a result. But what is more interesting is that the the tests must not contain instructions that can't be used for unaligned data, and whether or not the copy is executed correctly. So make these tests executable and scan the assembler only to confirm the absence of instructions that must not be used when the data is not aligned. These tests also used to be restricted to targets that support unaligned accesses (because you get very different code otherwise). But now we've made the tests executable and to check for the absence of problem instructions, just falling back to memcpy *is* an acceptable implementation. So remove the requirement for unaligned accesses. gcc/testsuite: PR target/91614 * gcc.target/arm/unaligned-memcpy-1.c: Make the test executable. Only scan for the absence of instructions that cannot access misaligned data. Remove constraint of having unaligned accesses. * gcc.target/arm/unaligned-memcpy-2.c: Likewise. * gcc.target/arm/unaligned-memcpy-3.c: Likewise. * gcc.target/arm/unaligned-memcpy-4.c: Likewise. Diff: --- gcc/testsuite/gcc.target/arm/unaligned-memcpy-1.c | 34 +++++++++++++++-------- gcc/testsuite/gcc.target/arm/unaligned-memcpy-2.c | 33 ++++++++++++---------- gcc/testsuite/gcc.target/arm/unaligned-memcpy-3.c | 33 ++++++++++++---------- gcc/testsuite/gcc.target/arm/unaligned-memcpy-4.c | 32 +++++++++++---------- 4 files changed, 77 insertions(+), 55 deletions(-) diff --git a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-1.c b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-1.c index c4f564042252..0d883e3c1739 100644 --- a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-1.c +++ b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-1.c @@ -1,19 +1,31 @@ -/* { dg-do compile } */ -/* { dg-require-effective-target arm_unaligned } */ -/* { dg-options "-O2" } */ +/* { dg-do run } */ +/* { dg-options "-O2 -save-temps" } */ #include <string.h> -void unknown_alignment (char *dest, char *src) +char src[17] __attribute__ ((aligned(8))) = "abcdefghijklmnopq"; +char result[17] __attribute__ ((aligned(8))) = {0}; + +void __attribute__ ((noinline,noclone)) +unknown_alignment (char *dest, char *src) { memcpy (dest, src, 15); } -/* We should see three unaligned word loads and store pairs, one unaligned - ldrh/strh pair, and an ldrb/strb pair. Sanity check that. */ +int main () +{ + int i; + unknown_alignment (result+1, src+2); + for (i = 0; i < 15; i++) + if (result[i+1] != src[i+2]) + __builtin_abort (); + if (result[16] != 0) + __builtin_abort (); + return 0; +} + +/* Check that we don't use any instructions that assume an aligned source. */ +/* { dg-final { scan-assembler-not {(ldm(ia)?\tr[0-9]|ldrd\t.*\[r[0-9]|vldr)} } } */ -/* { dg-final { scan-assembler-times "@ unaligned" 8 } } */ -/* { dg-final { scan-assembler-times "ldrh" 1 } } */ -/* { dg-final { scan-assembler-times "strh" 1 } } */ -/* { dg-final { scan-assembler-times "ldrb" 1 } } */ -/* { dg-final { scan-assembler-times "strb" 1 } } */ +/* Check that we don't use any instructions that assume an aligned dest. */ +/* { dg-final { scan-assembler-not {(stm(ia)?\tr[0-9]|strd\t.*\[r[0-9]|vstr)} } } */ diff --git a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-2.c b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-2.c index 1ad730d6407f..0da0bcd1c247 100644 --- a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-2.c +++ b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-2.c @@ -1,24 +1,27 @@ -/* { dg-do compile } */ -/* { dg-require-effective-target arm_unaligned } */ -/* { dg-options "-O2" } */ +/* { dg-do run } */ +/* { dg-options "-O2 -save-temps" } */ #include <string.h> -char dest[16] = { 0 }; +char dest[16] __attribute__((aligned(8))) = { 0 } ; +char input[17] __attribute__ ((aligned(8))) = "abcdefghijklmnop"; -void aligned_dest (char *src) +void __attribute__ ((noinline,noclone)) aligned_dest (char *src) { memcpy (dest, src, 15); } -/* Expect a multi-word store for the main part of the copy, but subword - loads/stores for the remainder. */ +int main () +{ + int i; + aligned_dest (input+1); + for (i = 0; i < 15; i++) + if (dest[i] != input[i+1]) + __builtin_abort (); + if (dest[15] != 0) + __builtin_abort (); + return 0; +} -/* { dg-final { scan-assembler-times "ldmia" 0 } } */ -/* { dg-final { scan-assembler-times "ldrd" 0 } } */ -/* { dg-final { scan-assembler-times "stmia" 1 { target { ! { arm_prefer_ldrd_strd } } } } } */ -/* { dg-final { scan-assembler-times "strd" 1 { target { arm_prefer_ldrd_strd } } } } */ -/* { dg-final { scan-assembler-times "ldrh" 1 } } */ -/* { dg-final { scan-assembler-times "strh" 1 } } */ -/* { dg-final { scan-assembler-times "ldrb" 1 } } */ -/* { dg-final { scan-assembler-times "strb" 1 } } */ +/* Check that we don't use any instructions that assume an aligned source. */ +/* { dg-final { scan-assembler-not {(ldm(ia)?\tr[0-9]|ldrd\t.*\[r[0-9]|vldr)} } } */ diff --git a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-3.c b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-3.c index d0b09bd48fef..2cfe8b9b39eb 100644 --- a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-3.c +++ b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-3.c @@ -1,24 +1,27 @@ -/* { dg-do compile } */ -/* { dg-require-effective-target arm_unaligned } */ -/* { dg-options "-O2" } */ +/* { dg-do run } */ +/* { dg-options "-O2 -save-temps" } */ #include <string.h> -char src[16] = {0}; +char src[17] __attribute__ ((aligned(8))) = "abcdefghijklmnop"; +char result[17] __attribute__ ((aligned(8))) = {0}; -void aligned_src (char *dest) +void __attribute__ ((noinline,noclone)) aligned_src (char *dest) { memcpy (dest, src, 15); } -/* Expect a multi-word load for the main part of the copy, but subword - loads/stores for the remainder. */ +int main () +{ + int i; + aligned_src (result+1); + for (i = 0; i < 15; i++) + if (result[i+1] != src[i]) + __builtin_abort (); + if (result[16] != 0) + __builtin_abort (); + return 0; +} -/* { dg-final { scan-assembler-times "ldmia" 1 { target { ! { arm_prefer_ldrd_strd } } } } } */ -/* { dg-final { scan-assembler-times "ldrd" 1 { target { arm_prefer_ldrd_strd } } } } */ -/* { dg-final { scan-assembler-times "strd" 0 } } */ -/* { dg-final { scan-assembler-times "stm" 0 } } */ -/* { dg-final { scan-assembler-times "ldrh" 1 { target { ! { arm_prefer_ldrd_strd } } } } } */ -/* { dg-final { scan-assembler-times "strh" 1 } } */ -/* { dg-final { scan-assembler-times "ldrb" 1 { target { ! { arm_prefer_ldrd_strd } } } } } */ -/* { dg-final { scan-assembler-times "strb" 1 } } */ +/* Check that we don't use any instructions that assume an aligned dest. */ +/* { dg-final { scan-assembler-not {(stm(ia)?\tr[0-9]|strd\t.*\[r[0-9]|vstr)} } } */ diff --git a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-4.c b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-4.c index d2365131d880..3f074e30d864 100644 --- a/gcc/testsuite/gcc.target/arm/unaligned-memcpy-4.c +++ b/gcc/testsuite/gcc.target/arm/unaligned-memcpy-4.c @@ -1,22 +1,26 @@ -/* { dg-do compile } */ -/* { dg-require-effective-target arm_unaligned } */ -/* { dg-options "-O2" } */ +/* { dg-do run } */ +/* { dg-options "-O2 -save-temps" } */ #include <string.h> -char src[16] = { 0 }; -char dest[16] = { 0 }; +char src[16] __attribute__ ((aligned(8))) = "abcdefghijklmnop"; +char dest[16] __attribute__ ((aligned(8))) = { 0 }; -void aligned_both (void) +void __attribute__ ((noinline,noclone)) +aligned_both (void) { - memcpy (dest, src, 15); + memcpy (dest, src, 16); } -/* We know both src and dest to be aligned: expect multiword loads/stores. */ +int main () +{ + int i; + aligned_both (); + for (i = 0; i < 16; i++) + if (dest[i] != src[i]) + __builtin_abort (); + return 0; +} -/* { dg-final { scan-assembler-times "ldm" 1 { target { ! { arm_prefer_ldrd_strd } } } } } */ -/* { dg-final { scan-assembler-times "stmia" 1 { target { ! { arm_prefer_ldrd_strd } } } } } */ -/* { dg-final { scan-assembler "ldrd" { target { arm_prefer_ldrd_strd } } } } */ -/* { dg-final { scan-assembler-times "ldm" 0 { target { arm_prefer_ldrd_strd } } } } */ -/* { dg-final { scan-assembler "strd" { target { arm_prefer_ldrd_strd } } } } */ -/* { dg-final { scan-assembler-times "stm" 0 { target { arm_prefer_ldrd_strd } } } } */ +/* There should be no 'unaligned' comments. */ +/* { dg-final { scan-assembler-not "unaligned" } } */