We reject the following testcase in C99 mode, because in C99 we always
wrap COMPOUND_LITERAL_EXPR in a SAVE_EXPR when initializing a range of
elements, even though the expression is required to be constant.  As a
consequence, we error out with "initializer element is not constant".
It's been like this since Roger's fold changes in 2003.  Since the default
is now gnu11, I think we should accept the code even in C99.  So this patch
makes the C FE treat the expression the same in both C90/C99 modes.  There
is no need to add any pedwarns at this spot.

Bootstrapped/regtested on x86_64-linux, ok for trunk?

2015-02-09  Marek Polacek  <pola...@redhat.com>

        PR c/64856
        * c-typeck.c (process_init_element): Don't always wrap
        COMPOUND_LITERAL_EXPR in a SAVE_EXPR in C99 mode when
        initializing a range of elements.

        * gcc.dg/pr64856.c: New test.

diff --git gcc/c/c-typeck.c gcc/c/c-typeck.c
index 65c6f7f..a3a9c77 100644
--- gcc/c/c-typeck.c
+++ gcc/c/c-typeck.c
@@ -8785,8 +8785,7 @@ process_init_element (location_t loc, struct c_expr 
value, bool implicit,
       /* If value is a compound literal and we'll be just using its
         content, don't put it into a SAVE_EXPR.  */
       if (TREE_CODE (value.value) != COMPOUND_LITERAL_EXPR
-         || !require_constant_value
-         || flag_isoc99)
+         || !require_constant_value)
        {
          tree semantic_type = NULL_TREE;
          if (TREE_CODE (value.value) == EXCESS_PRECISION_EXPR)
diff --git gcc/testsuite/gcc.dg/pr64856.c gcc/testsuite/gcc.dg/pr64856.c
index e69de29..c21d95a 100644
--- gcc/testsuite/gcc.dg/pr64856.c
+++ gcc/testsuite/gcc.dg/pr64856.c
@@ -0,0 +1,13 @@
+/* PR c/64856 */
+/* { dg-do compile } */
+/* { dg-options "" } */
+
+struct A {
+  unsigned long b;
+};
+
+struct B {
+  struct A c[5];
+};
+
+struct B d = { .c = { [0 ... 4] = (struct A){ .b = 2 } } };

        Marek

Reply via email to