aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorMartin Sebor <msebor@redhat.com>2016-05-24 20:29:36 +0000
committerMartin Sebor <msebor@gcc.gnu.org>2016-05-24 14:29:36 -0600
commitf65e97fd3dc83bdbe6a1415f9527e68c35b841b3 (patch)
tree3d9ac91feb80adf20ab2902d32b9bdfb0ca76ed2 /gcc
parent8e0dc0549a9d11fbf580db3ac45b49b5479dff13 (diff)
downloadgcc-f65e97fd3dc83bdbe6a1415f9527e68c35b841b3.zip
gcc-f65e97fd3dc83bdbe6a1415f9527e68c35b841b3.tar.gz
gcc-f65e97fd3dc83bdbe6a1415f9527e68c35b841b3.tar.bz2
PR c++/71147 - [6 Regression] Flexible array member wrongly rejected in template
gcc/ChangeLog: 2016-05-24 Martin Sebor <msebor@redhat.com> PR c++/71147 * gcc/tree.h (complete_or_array_type_p): New inline function. gcc/testsuite/ChangeLog: 2016-05-24 Martin Sebor <msebor@redhat.com> PR c++/71147 * g++.dg/ext/flexary16.C: New test. gcc/cp/ChangeLog: 2016-05-24 Martin Sebor <msebor@redhat.com> PR c++/71147 * decl.c (layout_var_decl, grokdeclarator): Use complete_or_array_type_p. * pt.c (instantiate_class_template_1): Try to complete the element type of a flexible array member. (can_complete_type_without_circularity): Handle arrays of unknown bound. * typeck.c (complete_type): Also complete the type of the elements of arrays with an unspecified bound. From-SVN: r236664
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog5
-rw-r--r--gcc/cp/ChangeLog10
-rw-r--r--gcc/cp/decl.c8
-rw-r--r--gcc/cp/pt.c17
-rw-r--r--gcc/cp/typeck.c2
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/g++.dg/ext/flexary16.C37
-rw-r--r--gcc/tree.h11
8 files changed, 77 insertions, 18 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 8c61f1d..b07aa80 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,8 @@
+2016-05-24 Martin Sebor <msebor@redhat.com>
+
+ PR c++/71147
+ * gcc/tree.h (complete_or_array_type_p): New inline function.
+
2016-05-24 Jakub Jelinek <jakub@redhat.com>
* config/i386/i386.h (TARGET_AVOID_4BYTE_PREFIXES): Define.
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index 4e06a71..5e7eb3d 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,13 @@
+2016-05-24 Martin Sebor <msebor@redhat.com>
+
+ PR c++/71147
+ * decl.c (layout_var_decl, grokdeclarator): Use complete_or_array_type_p.
+ * pt.c (instantiate_class_template_1): Try to complete the element
+ type of a flexible array member.
+ (can_complete_type_without_circularity): Handle arrays of unknown bound.
+ * typeck.c (complete_type): Also complete the type of the elements of
+ arrays with an unspecified bound.
+
2016-05-24 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/69872
diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c
index 7a69711..ef5fd66 100644
--- a/gcc/cp/decl.c
+++ b/gcc/cp/decl.c
@@ -5305,10 +5305,7 @@ layout_var_decl (tree decl)
complete_type (type);
if (!DECL_SIZE (decl)
&& TREE_TYPE (decl) != error_mark_node
- && (COMPLETE_TYPE_P (type)
- || (TREE_CODE (type) == ARRAY_TYPE
- && !TYPE_DOMAIN (type)
- && COMPLETE_TYPE_P (TREE_TYPE (type)))))
+ && complete_or_array_type_p (type))
layout_decl (decl, 0);
if (!DECL_EXTERNAL (decl) && DECL_SIZE (decl) == NULL_TREE)
@@ -11165,8 +11162,7 @@ grokdeclarator (const cp_declarator *declarator,
}
else if (!staticp && !dependent_type_p (type)
&& !COMPLETE_TYPE_P (complete_type (type))
- && (TREE_CODE (type) != ARRAY_TYPE
- || !COMPLETE_TYPE_P (TREE_TYPE (type))
+ && (!complete_or_array_type_p (type)
|| initialized == 0))
{
if (TREE_CODE (type) != ARRAY_TYPE
diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
index 3e07fb0..df3d634 100644
--- a/gcc/cp/pt.c
+++ b/gcc/cp/pt.c
@@ -9555,7 +9555,7 @@ can_complete_type_without_circularity (tree type)
return 0;
else if (COMPLETE_TYPE_P (type))
return 1;
- else if (TREE_CODE (type) == ARRAY_TYPE && TYPE_DOMAIN (type))
+ else if (TREE_CODE (type) == ARRAY_TYPE)
return can_complete_type_without_circularity (TREE_TYPE (type));
else if (CLASS_TYPE_P (type)
&& TYPE_BEING_DEFINED (TYPE_MAIN_VARIANT (type)))
@@ -10120,17 +10120,12 @@ instantiate_class_template_1 (tree type)
if (can_complete_type_without_circularity (rtype))
complete_type (rtype);
- if (TREE_CODE (r) == FIELD_DECL
- && TREE_CODE (rtype) == ARRAY_TYPE
- && COMPLETE_TYPE_P (TREE_TYPE (rtype))
- && !COMPLETE_TYPE_P (rtype))
- {
- /* Flexible array mmembers of elements
- of complete type have an incomplete type
- and that's okay. */
- }
- else if (!COMPLETE_TYPE_P (rtype))
+ if (!complete_or_array_type_p (rtype))
{
+ /* If R's type couldn't be completed and
+ it isn't a flexible array member (whose
+ type is incomplete by definition) give
+ an error. */
cxx_incomplete_type_error (r, rtype);
TREE_TYPE (r) = error_mark_node;
}
diff --git a/gcc/cp/typeck.c b/gcc/cp/typeck.c
index 8b3fec6..f68c2a3 100644
--- a/gcc/cp/typeck.c
+++ b/gcc/cp/typeck.c
@@ -112,7 +112,7 @@ complete_type (tree type)
if (type == error_mark_node || COMPLETE_TYPE_P (type))
;
- else if (TREE_CODE (type) == ARRAY_TYPE && TYPE_DOMAIN (type))
+ else if (TREE_CODE (type) == ARRAY_TYPE)
{
tree t = complete_type (TREE_TYPE (type));
unsigned int needs_constructing, has_nontrivial_dtor;
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index d88618e..6c03e26 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2016-05-24 Martin Sebor <msebor@redhat.com>
+
+ PR c++/71147
+ * g++.dg/ext/flexary16.C: New test.
+
2016-05-24 Ilya Verbin <ilya.verbin@intel.com>
* gcc.target/i386/avx-ceil-sfix-2-vec.c: Define __NO_MATH_INLINES before
diff --git a/gcc/testsuite/g++.dg/ext/flexary16.C b/gcc/testsuite/g++.dg/ext/flexary16.C
new file mode 100644
index 0000000..a3e040d
--- /dev/null
+++ b/gcc/testsuite/g++.dg/ext/flexary16.C
@@ -0,0 +1,37 @@
+// PR c++/71147 - [6 Regression] Flexible array member wrongly rejected
+// in template
+// { dg-do compile }
+
+template <typename>
+struct container
+{
+ struct elem {
+ unsigned u;
+ };
+
+ struct incomplete {
+ int x;
+ elem array[];
+ };
+};
+
+unsigned f (container<void>::incomplete* i)
+{
+ return i->array [0].u;
+}
+
+
+template <typename T>
+struct D: container<T>
+{
+ struct S {
+ int x;
+ typename container<T>::elem array[];
+ };
+};
+
+
+unsigned g (D<void>::S *s)
+{
+ return s->array [0].u;
+}
diff --git a/gcc/tree.h b/gcc/tree.h
index 2510d16..90413fc 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -4753,6 +4753,17 @@ ptrofftype_p (tree type)
&& TYPE_UNSIGNED (type) == TYPE_UNSIGNED (sizetype));
}
+/* Return true if the argument is a complete type or an array
+ of unknown bound (whose type is incomplete but) whose elements
+ have complete type. */
+static inline bool
+complete_or_array_type_p (const_tree type)
+{
+ return COMPLETE_TYPE_P (type)
+ || (TREE_CODE (type) == ARRAY_TYPE
+ && COMPLETE_TYPE_P (TREE_TYPE (type)));
+}
+
extern tree strip_float_extensions (tree);
extern int really_constant_p (const_tree);
extern bool decl_address_invariant_p (const_tree);