This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: [C++ PATCH] Fix constexpr OBJ_TYPE_REF handling on array elts (PR c++/87398)
- From: Jason Merrill <jason at redhat dot com>
- To: Jakub Jelinek <jakub at redhat dot com>
- Cc: Marek Polacek <polacek at redhat dot com>, gcc-patches List <gcc-patches at gcc dot gnu dot org>
- Date: Tue, 25 Sep 2018 11:40:29 -0400
- Subject: Re: [C++ PATCH] Fix constexpr OBJ_TYPE_REF handling on array elts (PR c++/87398)
- References: <20180925071754.GX8250@tucnak> <CADzB+2nc+62ioqFcPNJY7SKxsfQBMuXC=Xi-45V_P6zoWDBHbQ@mail.gmail.com> <20180925145723.GE8250@tucnak> <CADzB+2mmHCzhTkoAS02dgyh8GsemJxckNwCx8LN-a-54UF_k5Q@mail.gmail.com> <20180925151458.GF8250@tucnak>
Yes, thanks.
On Tue, Sep 25, 2018 at 11:14 AM, Jakub Jelinek <jakub@redhat.com> wrote:
> On Tue, Sep 25, 2018 at 11:07:19AM -0400, Jason Merrill wrote:
>> > You're right. So like this (only look through COMPONENT_REFs where the
>> > FIELD_DECL is DECL_FIELD_IS_BASE)?
>> > Only checked
>> > make check-c++-all RUNTESTFLAGS="dg.exp='constexpr-virt* pr87398*'"
>> > so far, but it also fixes the PR87425 testcase and doesn't regress anything.
>>
>> Looks good.
>
> Thanks, will bootstrap/regtest it now. I also took your testcase and turned it into
> something that ICEd without this patch too, is that testcase also ok
> (constexpr-virtual11.C)?
>
> 2018-09-25 Jakub Jelinek <jakub@redhat.com>
>
> PR c++/87398
> * constexpr.c (cxx_eval_constant_expression) <case OBJ_TYPE_REF>: Only
> look through COMPONENT_REFs with DECL_FIELD_IS_BASE FIELD_DECLs.
>
> * g++.dg/other/pr87398.C: New test.
> * g++.dg/cpp2a/constexpr-virtual10.C: New test.
> * g++.dg/cpp2a/constexpr-virtual11.C: New test.
>
> --- gcc/cp/constexpr.c.jj 2018-09-25 15:14:36.335386401 +0200
> +++ gcc/cp/constexpr.c 2018-09-25 16:50:38.085334475 +0200
> @@ -4812,7 +4812,8 @@ cxx_eval_constant_expression (const cons
> return t;
> }
> obj = TREE_OPERAND (obj, 0);
> - while (handled_component_p (obj))
> + while (TREE_CODE (obj) == COMPONENT_REF
> + && DECL_FIELD_IS_BASE (TREE_OPERAND (obj, 1)))
> obj = TREE_OPERAND (obj, 0);
> tree objtype = TREE_TYPE (obj);
> /* Find the function decl in the virtual functions list. TOKEN is
> --- gcc/testsuite/g++.dg/other/pr87398.C.jj 2018-09-25 16:49:40.458304980 +0200
> +++ gcc/testsuite/g++.dg/other/pr87398.C 2018-09-25 16:49:40.458304980 +0200
> @@ -0,0 +1,12 @@
> +// PR c++/87398
> +// { dg-do compile }
> +
> +struct A { virtual int foo (); };
> +
> +int
> +bar (int x)
> +{
> + A e[5][2];
> + int f = e[4][x].foo ();
> + return f;
> +}
> --- gcc/testsuite/g++.dg/cpp2a/constexpr-virtual10.C.jj 2018-09-25 16:49:40.458304980 +0200
> +++ gcc/testsuite/g++.dg/cpp2a/constexpr-virtual10.C 2018-09-25 16:49:40.458304980 +0200
> @@ -0,0 +1,18 @@
> +// P1064R0
> +// { dg-do compile }
> +// { dg-options "-std=c++2a" }
> +
> +struct X
> +{
> + constexpr virtual int f() const { return 1; };
> +};
> +
> +struct Y : public X
> +{
> + constexpr virtual int f() const { return 2; };
> +};
> +
> +constexpr X a[2][1][3];
> +constexpr Y b[3][12];
> +static_assert (a[1][0][1].f() == 1);
> +static_assert (b[2][11].f() == 2);
> --- gcc/testsuite/g++.dg/cpp2a/constexpr-virtual11.C.jj 2018-09-01 11:09:41.506153390 +0200
> +++ gcc/testsuite/g++.dg/cpp2a/constexpr-virtual11.C 2018-09-25 17:11:30.563244029 +0200
> @@ -0,0 +1,26 @@
> +// P1064R0
> +// { dg-do compile }
> +// { dg-options "-std=c++2a" }
> +
> +struct A
> +{
> + constexpr virtual int f () const { return 1; }
> +};
> +
> +struct B : public A
> +{
> + constexpr virtual int f () const { return 2; }
> +};
> +
> +struct C
> +{
> + A a;
> + B b;
> +};
> +
> +constexpr C c;
> +constexpr const A &d = c.a;
> +constexpr const A &e = c.b;
> +constexpr const B &f = c.b;
> +static_assert (c.a.f () == 1 && c.b.f () == 2);
> +static_assert (d.f () == 1 && e.f () == 2 && f.f () == 2);
>
>
> Jakub