Ping.

Normally we shouldn't ping a patch after only a few days, but we're
running out of time to catch GCC 12 milestone.  And once GCC 12 is
released the patch will become far more complicated for a psABI warning.

And please note that the ABI difference between GCC and G++ should be
considered a bug, and it has to be fixed anyway.  If you don't like the
idea of this patch, please develop another solution and apply it *before
GCC 12*.

On Wed, 2022-04-20 at 14:23 +0800, Xi Ruoyao via Gcc-patches wrote:
> Currently, LoongArch ELF psABI is not clear on the handling of zero-
> sized fields in aggregates arguments or return values [1].  The behavior
> of GCC trunk is puzzling considering the following cases:
> 
> struct test1
> {
>   double a[0];
>   float x;
> };
> 
> struct test2
> {
>   float a[0];
>   float x;
> };
> 
> GCC trunk passes test1::x via GPR, but test2::x via FPR.  I believe no
> rational Homo Sapiens can understand (or even expect) this.
> 
> And, to make things even worse, test1 behaves differently in C and C++.
> GCC trunk passes test1::x via GPR, but G++ trunk passes test1::x via
> FPR.
> 
> I've write a paragraph about current GCC behavior for the psABI [2], but
> I think it's cleaner to just ignore all zero-sized fields in the ABI. 
> This will require only a two-line change in GCC (this patch), and an
> one-line change in the ABI doc.
> 
> If there is not any better idea I'd like to see this reviewed and
> applied ASAP.  If we finally have to apply this patch after GCC 12
> release, we'll need to add a lot more boring code to emit a -Wpsabi
> inform [3].  That will be an unnecessary burden for both us, and the
> users using the compiler (as the compiler will spend CPU time only for
> checking if a warning should be informed).
> 
> [1]:https://github.com/loongson/LoongArch-Documentation/issues/48
> [2]:https://github.com/loongson/LoongArch-Documentation/pull/49
> [3]:https://gcc.gnu.org/PR102024
> 
> 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..57e4d9f82ce 100644
> --- a/gcc/config/loongarch/loongarch.cc
> +++ b/gcc/config/loongarch/loongarch.cc
> @@ -326,6 +326,9 @@ loongarch_flatten_aggregate_field (const_tree type,
>        for (tree f = TYPE_FIELDS (type); f; f = DECL_CHAIN (f))
>         if (TREE_CODE (f) == FIELD_DECL)
>           {
> +           if (DECL_SIZE (f) && integer_zerop (DECL_SIZE (f)))
> +             continue;
> +
>             if (!TYPE_P (TREE_TYPE (f)))
>               return -1;
>  
> 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;
> +}

-- 
Xi Ruoyao <xry...@mengyan1223.wang>
School of Aerospace Science and Technology, Xidian University

Reply via email to