Commit ada6bad9 by David Pagan Committed by Joseph Myers

PR c/46921 Lost side effect when struct initializer expression uses comma operator

This patch fixes improper handling of comma operator expression in a
struct field initializer as described in:

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=46921

Currently, function output_init_element () does not evaluate the left
hand expression in a comma operator that's used for a struct
initializer field if the right hand side is zero-sized. However, the
left hand expression must be evaluated if it's found to have side
effects (for example, a function call).

Patch was successfully bootstrapped and tested on x86_64-linux.

gcc/c:
2018-03-13  David Pagan  <dave.pagan@oracle.com>

	PR c/46921
	* c-typeck.c (output_init_element): Ensure field initializer
	expression is always evaluated if there are side effects.

gcc/testsuite:
2018-03-13  David Pagan  <dave.pagan@oracle.com>

	PR c/46921
	* gcc.dg/pr46921.c: New test.

From-SVN: r258497
parent b34f5c5e
2018-03-13 David Pagan <dave.pagan@oracle.com>
PR c/46921
* c-typeck.c (output_init_element): Ensure field initializer
expression is always evaluated if there are side effects.
2018-03-06 Jakub Jelinek <jakub@redhat.com> 2018-03-06 Jakub Jelinek <jakub@redhat.com>
PR c/84721 PR c/84721
......
...@@ -9208,12 +9208,14 @@ output_init_element (location_t loc, tree value, tree origtype, ...@@ -9208,12 +9208,14 @@ output_init_element (location_t loc, tree value, tree origtype,
"enum conversion in initialization is invalid in C++"); "enum conversion in initialization is invalid in C++");
} }
/* If this field is empty (and not at the end of structure), /* If this field is empty and does not have side effects (and is not at
don't do anything other than checking the initializer. */ the end of structure), don't do anything other than checking the
initializer. */
if (field if (field
&& (TREE_TYPE (field) == error_mark_node && (TREE_TYPE (field) == error_mark_node
|| (COMPLETE_TYPE_P (TREE_TYPE (field)) || (COMPLETE_TYPE_P (TREE_TYPE (field))
&& integer_zerop (TYPE_SIZE (TREE_TYPE (field))) && integer_zerop (TYPE_SIZE (TREE_TYPE (field)))
&& !TREE_SIDE_EFFECTS (new_value)
&& (TREE_CODE (constructor_type) == ARRAY_TYPE && (TREE_CODE (constructor_type) == ARRAY_TYPE
|| DECL_CHAIN (field))))) || DECL_CHAIN (field)))))
return; return;
......
2018-03-13 David Pagan <dave.pagan@oracle.com>
PR c/46921
* gcc.dg/pr46921.c: New test.
2018-03-13 Martin Sebor <msebor@redhat.com> 2018-03-13 Martin Sebor <msebor@redhat.com>
PR tree-optimization/84725 PR tree-optimization/84725
......
/* PR c/46921 lost side effect when struct initializer expr uses comma
operator */
/* { dg-do run } */
/* { dg-options "" } */
extern int printf(const char *, ...);
extern void abort (void);
typedef struct __uws_0 { } uw_unit;
uw_unit uw_unit_v = {};
struct __uws_1
{
struct __uws_0 __uwf_1;
struct __uws_1* __uwf_2;
};
static int left_hand_eval = 0;
static void
foo (const char *s)
{
++left_hand_eval;
printf("%s", s);
}
int
main ()
{
struct __uws_1 tmp = {(foo("Inner\n"), uw_unit_v)};
printf("Outer\n");
/* left hand expression in comma operator initializer must always be
evaluated if there are side effects. */
if (!left_hand_eval)
abort ();
return 0;
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment