On Wed, 2022-04-27 at 14:57 +0800, Lulu Cheng wrote: > I think the modification should be below. > > > > > > > if (!TYPE_P (TREE_TYPE (f))) > > > > return -1;
I think (!TYPE_P (TREE_TYPE (f)) will never be true (the code handling calling convention of other ports does not has this check). But "first thing first" so I'll move the change below this for now. gcc/ * config/loongarch/loongarch.cc (loongarch_flatten_aggregate_field): Ignore empty fields for RECORD_TYPE. gcc/testsuite/ * gcc.target/loongarch/zero-size-field-pass.c: New test. * gcc.target/loongarch/zero-size-field-ret.c: New test. --- gcc/config/loongarch/loongarch.cc | 3 ++ .../loongarch/zero-size-field-pass.c | 30 +++++++++++++++++++ .../loongarch/zero-size-field-ret.c | 28 +++++++++++++++++ 3 files changed, 61 insertions(+) create mode 100644 gcc/testsuite/gcc.target/loongarch/zero-size-field-pass.c create mode 100644 gcc/testsuite/gcc.target/loongarch/zero-size-field-ret.c diff --git a/gcc/config/loongarch/loongarch.cc b/gcc/config/loongarch/loongarch.cc index f22150a60cc..80046b64006 100644 --- a/gcc/config/loongarch/loongarch.cc +++ b/gcc/config/loongarch/loongarch.cc @@ -329,6 +329,9 @@ loongarch_flatten_aggregate_field (const_tree type, if (!TYPE_P (TREE_TYPE (f))) return -1; + if (DECL_SIZE (f) && integer_zerop (DECL_SIZE (f))) + continue; + HOST_WIDE_INT pos = offset + int_byte_position (f); n = loongarch_flatten_aggregate_field (TREE_TYPE (f), fields, n, pos); diff --git a/gcc/testsuite/gcc.target/loongarch/zero-size-field-pass.c b/gcc/testsuite/gcc.target/loongarch/zero-size-field-pass.c new file mode 100644 index 00000000000..999dc913a71 --- /dev/null +++ b/gcc/testsuite/gcc.target/loongarch/zero-size-field-pass.c @@ -0,0 +1,30 @@ +/* Test that LoongArch backend ignores zero-sized fields of aggregates in + argument passing. */ + +/* { dg-do compile } */ +/* { dg-options "-O2 -mdouble-float -mabi=lp64d" } */ +/* { dg-final { scan-assembler "\\\$f1" } } */ + +struct test +{ + int empty1[0]; + double empty2[0]; + int : 0; + float x; + long empty3[0]; + long : 0; + float y; + unsigned : 0; + char empty4[0]; +}; + +extern void callee (struct test); + +void +caller (void) +{ + struct test test; + test.x = 114; + test.y = 514; + callee (test); +} diff --git a/gcc/testsuite/gcc.target/loongarch/zero-size-field-ret.c b/gcc/testsuite/gcc.target/loongarch/zero-size-field-ret.c new file mode 100644 index 00000000000..40137d97555 --- /dev/null +++ b/gcc/testsuite/gcc.target/loongarch/zero-size-field-ret.c @@ -0,0 +1,28 @@ +/* Test that LoongArch backend ignores zero-sized fields of aggregates in + returning. */ + +/* { dg-do compile } */ +/* { dg-options "-O2 -mdouble-float -mabi=lp64d" } */ +/* { dg-final { scan-assembler-not "\\\$r4" } } */ + +struct test +{ + int empty1[0]; + double empty2[0]; + int : 0; + float x; + long empty3[0]; + long : 0; + float y; + unsigned : 0; + char empty4[0]; +}; + +extern struct test callee (void); + +float +caller (void) +{ + struct test test = callee (); + return test.x + test.y; +} -- 2.36.0