diff options
-rw-r--r-- | gcc/cp/ChangeLog | 11 | ||||
-rw-r--r-- | gcc/cp/typeck2.c | 15 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/cpp0x/initlist11.C | 17 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/cpp0x/initlist12.C | 15 |
5 files changed, 61 insertions, 2 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index e6cb289..7ffa760 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,14 @@ +2009-01-02 Jason Merrill <jason@redhat.com> + + PR c++/38698 + * typeck2.c (process_init_constructor_union): Handle excess + initializers. + (process_init_constructor_record): Likewise. + + PR c++/38684 + * typeck2.c (digest_init_r): Don't use process_init_constructor + for non-aggregate classes. + 2008-12-31 Jakub Jelinek <jakub@redhat.com> PR c++/38647 diff --git a/gcc/cp/typeck2.c b/gcc/cp/typeck2.c index 207dd99..e313e4b 100644 --- a/gcc/cp/typeck2.c +++ b/gcc/cp/typeck2.c @@ -820,7 +820,8 @@ digest_init_r (tree type, tree init, bool nested) || TREE_CODE (type) == UNION_TYPE || TREE_CODE (type) == COMPLEX_TYPE); - if (BRACE_ENCLOSED_INITIALIZER_P (init)) + if (BRACE_ENCLOSED_INITIALIZER_P (init) + && !TYPE_NON_AGGREGATE_CLASS (type)) return process_init_constructor (type, init); else { @@ -1081,6 +1082,9 @@ process_init_constructor_record (tree type, tree init) CONSTRUCTOR_APPEND_ELT (v, field, next); } + if (idx < VEC_length (constructor_elt, CONSTRUCTOR_ELTS (init))) + error ("too many initializers for %qT", type); + CONSTRUCTOR_ELTS (init) = v; return flags; } @@ -1093,12 +1097,19 @@ static int process_init_constructor_union (tree type, tree init) { constructor_elt *ce; + int len; /* If the initializer was empty, use default zero initialization. */ if (VEC_empty (constructor_elt, CONSTRUCTOR_ELTS (init))) return 0; - gcc_assert (VEC_length (constructor_elt, CONSTRUCTOR_ELTS (init)) == 1); + len = VEC_length (constructor_elt, CONSTRUCTOR_ELTS (init)); + if (len > 1) + { + error ("too many initializers for %qT", type); + VEC_block_remove (constructor_elt, CONSTRUCTOR_ELTS (init), 1, len-1); + } + ce = VEC_index (constructor_elt, CONSTRUCTOR_ELTS (init), 0); /* If this element specifies a field, initialize via that field. */ diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 9b59cb4..199784f 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2009-01-02 Jason Merrill <jason@redhat.com> + + * g++.dg/cpp0x/initlist11.C: New test. + * g++.dg/cpp0x/initlist12.C: New test. + 2009-01-02 Richard Sandiford <rdsandiford@googlemail.com> * gcc.dg/fixed-point/composite-type.c: Update wording of messages. diff --git a/gcc/testsuite/g++.dg/cpp0x/initlist11.C b/gcc/testsuite/g++.dg/cpp0x/initlist11.C new file mode 100644 index 0000000..789afc0 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/initlist11.C @@ -0,0 +1,17 @@ +// PR c++/38684 + +#include <initializer_list> + +struct Y {}; + +struct X : Y { + X(std::initializer_list<int>) {} +}; + +struct A { + X v; +}; + +int main() { + A a{ {1,2,3} }; +} diff --git a/gcc/testsuite/g++.dg/cpp0x/initlist12.C b/gcc/testsuite/g++.dg/cpp0x/initlist12.C new file mode 100644 index 0000000..f3329d9 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/initlist12.C @@ -0,0 +1,15 @@ +// PR c++/38698 + +struct A +{ + int i; +}; + +A a({1,2}); + +union U +{ + int i,j; +}; + +U u({1,2}); |