+2020-02-09 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/93633
+ * constexpr.c (cxx_eval_constant_expression): If obj is heap var with
+ ARRAY_TYPE, use the element type. Punt if objtype after that is not
+ a class type.
+
2020-02-08 Jason Merrill <jason@redhat.com>
PR c++/90691
&& DECL_FIELD_IS_BASE (TREE_OPERAND (obj, 1)))
obj = TREE_OPERAND (obj, 0);
tree objtype = TREE_TYPE (obj);
+ if (VAR_P (obj)
+ && DECL_NAME (obj) == heap_identifier
+ && TREE_CODE (objtype) == ARRAY_TYPE)
+ objtype = TREE_TYPE (objtype);
+ if (!CLASS_TYPE_P (objtype))
+ {
+ if (!ctx->quiet)
+ error_at (loc, "expression %qE is not a constant expression", t);
+ *non_constant_p = true;
+ return t;
+ }
/* Find the function decl in the virtual functions list. TOKEN is
the DECL_VINDEX that says which function we're looking for. */
tree virtuals = BINFO_VIRTUALS (TYPE_BINFO (objtype));
+2020-02-09 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/93633
+ * g++.dg/cpp2a/constexpr-new11.C: New test.
+ * g++.dg/cpp2a/constexpr-new12.C: New test.
+ * g++.dg/cpp2a/constexpr-new13.C: New test.
+
2020-02-08 Andrew Pinski <apinski@marvel.com>
PR target/91927
--- /dev/null
+// PR c++/93633
+// { dg-do compile { target c++2a } }
+
+struct A {
+ constexpr A () : a (0) {}
+ constexpr virtual int foo () { return 1 + a * 4; }
+ int a;
+};
+
+struct B : A {
+ constexpr B () : b (0) {}
+ constexpr virtual int foo () { return 0 + b * 4; }
+ int b;
+};
+
+constexpr int
+foo ()
+{
+ A *a = new B ();
+ a->a = 4;
+ int r = a->foo ();
+ delete a;
+ return r;
+}
+
+int
+main ()
+{
+ constexpr auto a = foo ();
+ static_assert (a == 0);
+}
--- /dev/null
+// PR c++/93633
+// { dg-do compile { target c++2a } }
+
+struct A {
+ constexpr A () : a (0) {}
+ constexpr virtual int foo () { return 1 + a * 4; }
+ int a;
+};
+
+struct B : A {
+ constexpr B () : b (0) {}
+ constexpr virtual int foo () { return 0 + b * 4; }
+ int b;
+};
+
+constexpr int
+foo ()
+{
+ A *a = new B ();
+ a->a = 4;
+ delete a;
+ int r = a->foo ();
+ return r;
+}
+
+constexpr auto a = foo (); // { dg-error "is not a constant expression" }
--- /dev/null
+// PR c++/93633
+// { dg-do compile { target c++2a } }
+
+struct A {
+ constexpr A () : a (0) {}
+ virtual int foo () { return 1 + a * 4; }
+ int a;
+};
+
+struct B : A {
+ constexpr B () : b (0) {}
+ virtual int foo () { return 0 + b * 4; } // { dg-message "declared here" }
+ int b;
+};
+
+constexpr int
+foo ()
+{
+ A *a = new B ();
+ a->a = 4;
+ int r = a->foo (); // { dg-error "call to non-.constexpr. function" }
+ delete a;
+ return r;
+}
+
+constexpr auto a = foo ();