On Sat, Sep 29, 2018 at 11:02 AM Uros Bizjak <[email protected]> wrote:
>
> On Sat, Sep 29, 2018 at 6:36 PM H.J. Lu <[email protected]> wrote:
> >
> > When passing and returning BLKmode values in 2 integer registers, use
> > 1 TImode register instead of 2 DImode registers. Otherwise, V1TImode
> > may be used to move and store such BLKmode values, which prevent RTL
> > optimizations.
> >
> > Tested on x86-64. OK for trunk?
> >
> > Thanks.
> >
> > H.J.
> > ---
> > gcc/
> >
> > PR target/87370
> > * config/i386/i386.c (construct_container): Use TImode for
> > BLKmode values in 2 integer registers.
> >
> > gcc/testsuite/
> >
> > PR target/87370
> > * gcc.target/i386/pr87370.c: New test.
>
> OK.
I'd like to backport it to release branches. Is that OK?
Thanks.
H.J.
> Thanks,
> Uros.
>
> > ---
> > gcc/config/i386/i386.c | 17 +++++++++--
> > gcc/testsuite/gcc.target/i386/pr87370.c | 39 +++++++++++++++++++++++++
> > 2 files changed, 54 insertions(+), 2 deletions(-)
> > create mode 100644 gcc/testsuite/gcc.target/i386/pr87370.c
> >
> > diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c
> > index 176cce521b7..54752513076 100644
> > --- a/gcc/config/i386/i386.c
> > +++ b/gcc/config/i386/i386.c
> > @@ -7914,9 +7914,22 @@ construct_container (machine_mode mode, machine_mode
> > orig_mode,
> > if (n == 2
> > && regclass[0] == X86_64_INTEGER_CLASS
> > && regclass[1] == X86_64_INTEGER_CLASS
> > - && (mode == CDImode || mode == TImode)
> > + && (mode == CDImode || mode == TImode || mode == BLKmode)
> > && intreg[0] + 1 == intreg[1])
> > - return gen_rtx_REG (mode, intreg[0]);
> > + {
> > + if (mode == BLKmode)
> > + {
> > + /* Use TImode for BLKmode values in 2 integer registers. */
> > + exp[0] = gen_rtx_EXPR_LIST (VOIDmode,
> > + gen_rtx_REG (TImode, intreg[0]),
> > + GEN_INT (0));
> > + ret = gen_rtx_PARALLEL (mode, rtvec_alloc (1));
> > + XVECEXP (ret, 0, 0) = exp[0];
> > + return ret;
> > + }
> > + else
> > + return gen_rtx_REG (mode, intreg[0]);
> > + }
> >
> > /* Otherwise figure out the entries of the PARALLEL. */
> > for (i = 0; i < n; i++)
> > diff --git a/gcc/testsuite/gcc.target/i386/pr87370.c
> > b/gcc/testsuite/gcc.target/i386/pr87370.c
> > new file mode 100644
> > index 00000000000..c7b6295a33b
> > --- /dev/null
> > +++ b/gcc/testsuite/gcc.target/i386/pr87370.c
> > @@ -0,0 +1,39 @@
> > +/* { dg-do compile { target { ! ia32 } } } */
> > +/* { dg-options "-O2" } */
> > +
> > +struct A
> > +{
> > + int b[4];
> > +};
> > +struct B
> > +{
> > + char a[12];
> > + int b;
> > +};
> > +struct C
> > +{
> > + char a[16];
> > +};
> > +
> > +struct A
> > +f1 (void)
> > +{
> > + struct A x = {};
> > + return x;
> > +}
> > +
> > +struct B
> > +f2 (void)
> > +{
> > + struct B x = {};
> > + return x;
> > +}
> > +
> > +struct C
> > +f3 (void)
> > +{
> > + struct C x = {};
> > + return x;
> > +}
> > +
> > +/* { dg-final { scan-assembler-not "xmm" } } */
> > --
> > 2.17.1
> >