Hi! As mentioned in the PR, the recent change to handle constant_decl_p stuff sometimes results in attempts to store the scalarized pieces again into constant_decl_p fields, which of course can't work, those usually live in read-only memory. This happens usually when the aggregate has some paddings within it, and for constant pool constant of course only the scalarized values that were read from the constant earlier are attempted to be stored there.
Fixed by not storing anything in those cases (note, WRITE is true if it is write from the AGG, and !WRITE for writes into the AGG). Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk? 2016-04-12 Jakub Jelinek <ja...@redhat.com> PR tree-optimization/70602 * tree-sra.c (generate_subtree_copies): Don't write anything into constant pool decls. * gcc.c-torture/execute/pr70602.c: New test. --- gcc/tree-sra.c.jj 2016-04-09 13:21:06.000000000 +0200 +++ gcc/tree-sra.c 2016-04-11 23:29:40.257694402 +0200 @@ -2743,6 +2743,9 @@ generate_subtree_copies (struct access * gimple_stmt_iterator *gsi, bool write, bool insert_after, location_t loc) { + /* Never write anything into constant pool decls. See PR70602. */ + if (!write && constant_decl_p (agg)) + return; do { if (chunk_size && access->offset >= start_offset + chunk_size) --- gcc/testsuite/gcc.c-torture/execute/pr70602.c.jj 2016-04-11 23:27:39.408312395 +0200 +++ gcc/testsuite/gcc.c-torture/execute/pr70602.c 2016-04-11 23:27:23.000000000 +0200 @@ -0,0 +1,23 @@ +/* PR tree-optimization/70602 */ + +struct __attribute__((packed)) S +{ + int s : 1; + int t : 20; +}; + +int a, b, c; + +int +main () +{ + for (; a < 1; a++) + { + struct S e[] = { {0, 9}, {0, 9}, {0, 9}, {0, 0}, {0, 9}, {0, 9}, {0, 9}, + {0, 0}, {0, 9}, {0, 9}, {0, 9}, {0, 0}, {0, 9}, {0, 9}, + {0, 9}, {0, 0}, {0, 9}, {0, 9}, {0, 9}, {0, 0}, {0, 9} }; + b = b || e[0].s; + c = e[0].t; + } + return 0; +} Jakub