On Tue, 4 Aug 2020, Jakub Jelinek wrote: > Hi! > > In debug stmts, we are less strict about what is and what is not accepted > there, so this patch just punts on optimization of a debug stmt rather than > ICEing. > > Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?
OK. Richard. > 2020-08-04 Jakub Jelinek <ja...@redhat.com> > > PR debug/96354 > * gimple-fold.c (maybe_canonicalize_mem_ref_addr): Add IS_DEBUG > argument. Return false instead of gcc_unreachable if it is true and > get_addr_base_and_unit_offset returns NULL. > (fold_stmt_1) <case GIMPLE_DEBUG>: Adjust caller. > > * g++.dg/opt/pr96354.C: New test. > > --- gcc/gimple-fold.c.jj 2020-07-28 15:39:09.908757602 +0200 > +++ gcc/gimple-fold.c 2020-08-03 13:23:57.579436442 +0200 > @@ -4875,7 +4875,7 @@ replace_stmt_with_simplification (gimple > /* Canonicalize MEM_REFs invariant address operand after propagation. */ > > static bool > -maybe_canonicalize_mem_ref_addr (tree *t) > +maybe_canonicalize_mem_ref_addr (tree *t, bool is_debug = false) > { > bool res = false; > tree *orig_t = t; > @@ -4939,7 +4939,11 @@ maybe_canonicalize_mem_ref_addr (tree *t > base = get_addr_base_and_unit_offset (TREE_OPERAND (addr, 0), > &coffset); > if (!base) > - gcc_unreachable (); > + { > + if (is_debug) > + return false; > + gcc_unreachable (); > + } > > TREE_OPERAND (*t, 0) = build_fold_addr_expr (base); > TREE_OPERAND (*t, 1) = int_const_binop (PLUS_EXPR, > @@ -5119,7 +5123,7 @@ fold_stmt_1 (gimple_stmt_iterator *gsi, > if (*val > && (REFERENCE_CLASS_P (*val) > || TREE_CODE (*val) == ADDR_EXPR) > - && maybe_canonicalize_mem_ref_addr (val)) > + && maybe_canonicalize_mem_ref_addr (val, true)) > changed = true; > } > break; > --- gcc/testsuite/g++.dg/opt/pr96354.C.jj 2020-07-29 11:25:15.701164242 > +0200 > +++ gcc/testsuite/g++.dg/opt/pr96354.C 2020-07-29 11:26:16.490291018 > +0200 > @@ -0,0 +1,24 @@ > +// PR debug/96354 > +// { dg-do compile } > +// { dg-options "-O2 -g -fopenmp-simd" } > + > +template <int N> struct A { typedef double T[N]; }; > +template <int N> struct B { typename A<N>::T b; double *baz () { return b; } > }; > +template <int N> struct C { B<N> d; C (); }; > +template <int N> C<N>::C () { double c = *d.baz (); } > +template <int N> void operator- (C<N>, const C<N> &); > +template <int> struct D {}; > +template <int N, int M> C<N> foo (D<N>, C<M>) { C<N> t; return t; } > +int e; > +struct E { D<3> d; void bar (); }; > + > +void > +E::bar () > +{ > +#pragma omp simd > + for (int i = 0; i < e; i++) > + { > + C<3> f, g; > + g - foo (d, f); > + } > +} > > Jakub > > -- Richard Biener <rguent...@suse.de> SUSE Software Solutions Germany GmbH, Maxfeldstrasse 5, 90409 Nuernberg, Germany; GF: Felix Imendörffer; HRB 36809 (AG Nuernberg)