On Sun, 12 Nov 2017, Jakub Jelinek wrote: > Hi! > > The conditions split groups if some operand is loaded in first stmt > and the second load is incompatible with it, or if it is loaded and > second stmt has constant in there instead of load. > But as this testcase shows, I didn't handle properly the case when > some operand is a constant first and in second stmt changes into a load. > We need to split group between those too. > > Bootstrapped/regtested on {x86_64,i686,powerpc64{,le}}-linux, ok for trunk?
Ok. Thanks, Richard. > 2017-11-12 Jakub Jelinek <ja...@redhat.com> > > PR tree-optimization/82954 > * gimple-ssa-store-merging.c > (imm_store_chain_info::coalesce_immediate_stores): If > !infof->ops[N].base_addr, split group if info->ops[N].base_addr. > > * gcc.c-torture/execute/pr82954.c: New test. > > --- gcc/gimple-ssa-store-merging.c.jj 2017-11-10 15:42:39.000000000 +0100 > +++ gcc/gimple-ssa-store-merging.c 2017-11-12 15:18:16.614785829 +0100 > @@ -1198,10 +1198,12 @@ imm_store_chain_info::coalesce_immediate > std::swap (info->ops[0], info->ops[1]); > info->ops_swapped_p = true; > } > - if ((!infof->ops[0].base_addr > - || compatible_load_p (merged_store, info, base_addr, 0)) > - && (!infof->ops[1].base_addr > - || compatible_load_p (merged_store, info, base_addr, 1))) > + if ((infof->ops[0].base_addr > + ? compatible_load_p (merged_store, info, base_addr, 0) > + : !info->ops[0].base_addr) > + && (infof->ops[1].base_addr > + ? compatible_load_p (merged_store, info, base_addr, 1) > + : !info->ops[1].base_addr)) > { > merged_store->merge_into (info); > continue; > --- gcc/testsuite/gcc.c-torture/execute/pr82954.c.jj 2017-11-12 > 15:27:44.478188823 +0100 > +++ gcc/testsuite/gcc.c-torture/execute/pr82954.c 2017-11-12 > 15:27:27.000000000 +0100 > @@ -0,0 +1,22 @@ > +/* PR tree-optimization/82954 */ > + > +__attribute__((noipa)) void > +foo (int *__restrict p, int *__restrict q) > +{ > + p[0] = p[0] ^ 1; > + p[1] = p[1] ^ 2; > + p[2] = p[2] ^ q[2]; > + p[3] = p[3] ^ q[3]; > +} > + > +int > +main () > +{ > + int p[4] = { 16, 32, 64, 128 }; > + int q[4] = { 8, 4, 2, 1 }; > + asm volatile ("" : : "g" (p), "g" (q) : "memory"); > + foo (p, q); > + if (p[0] != 17 || p[1] != 34 || p[2] != 66 || p[3] != 129) > + __builtin_abort (); > + return 0; > +} > > Jakub > > -- Richard Biener <rguent...@suse.de> SUSE LINUX GmbH, GF: Felix Imendoerffer, Jane Smithard, Graham Norton, HRB 21284 (AG Nuernberg)