This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: [PATCH]: fix for PR middle-end/38250
> On Wed, Nov 26, 2008 at 4:43 PM, Tomas Bily <tbily@suse.cz> wrote:
> > Hi,
> >
> > The PR is caused by two problems:
> >
> > In tree-loop-distribution.c (generate_memset_zero):
> >
> > 1. It can be DR_STEP(dr) NULL. But it is passed into fold_build2 that
> > expect two non null expressions.
> >
> > 2. If program flow goes to end: due to goto then temporary variables created
> > during force_gimple_operand are added to referenced vars. But this variables
> > have not def bb. So later checks fails.
> >
> > This patch add check for DR_STEP and remove newly generated stmts if
> > generating of memset fails.
> >
> > Tested and bootsraped on x86_64-unknown-linux-gnu.
> >
> > OK for mainline ?
>
> Please re-organize the function instead to not add the stmts until needed.
> This looks trivially possible.
Ok. I'll re-organize it.
Greetings
Tomas
> Thanks,
> Richard.
>
> > Greetings
> > Tomas
> >
> > Changelog:
> >
> > PR middle-end/38250
> > * tree-loop-distribution.c (remove_stmts): New function.
> > (generate_memset_zero): Checks if DR_STEP(de) is NULL. Remove generated
> > stmts if checks fails.
> >
> > Index: tree-loop-distribution.c
> > ===================================================================
> > --- tree-loop-distribution.c (revision 142159)
> > +++ tree-loop-distribution.c (working copy)
> > @@ -216,6 +216,21 @@ generate_loops_for_partition (struct loo
> > return true;
> > }
> >
> > +/* Remove stmts in a list. */
> > +
> > +static void
> > +remove_stmts (gimple_seq stmt_list)
> > +{
> > + gimple_stmt_iterator i;
> > +
> > + for (i = gsi_start (stmt_list); ; gsi_next (&i))
> > + {
> > + gsi_remove (&i, true);
> > + if (gsi_end_p (i))
> > + break;
> > + }
> > +}
> > +
> > /* Generate a call to memset. Return true when the operation succeeded. */
> >
> > static bool
> > @@ -240,6 +255,12 @@ generate_memset_zero (gimple stmt, tree
> > DR_REF (dr) = op0;
> > dr_analyze_innermost (dr);
> >
> > + if (!DR_STEP (dr))
> > + {
> > + remove_stmts (stmt_list);
> > + goto end;
> > + }
> > +
> > /* Test for a positive stride, iterating over every element. */
> > if (integer_zerop (fold_build2 (MINUS_EXPR, integer_type_node, DR_STEP (dr),
> > TYPE_SIZE_UNIT (TREE_TYPE (op0)))))
> > @@ -263,7 +284,10 @@ generate_memset_zero (gimple stmt, tree
> > DR_BASE_ADDRESS (dr), addr_base);
> > }
> > else
> > - goto end;
> > + {
> > + remove_stmts (stmt_list);
> > + goto end;
> > + }
> >
> > mem = force_gimple_operand (addr_base, &stmts, true, NULL);
> > gimple_seq_add_seq (&stmt_list, stmts);
> > Index: testsuite/gcc.dg/tree-ssa/pr38250.c
> > ===================================================================
> > --- testsuite/gcc.dg/tree-ssa/pr38250.c (revision 0)
> > +++ testsuite/gcc.dg/tree-ssa/pr38250.c (revision 0)
> > @@ -0,0 +1,24 @@
> > +/* { dg-do compile } */
> > +/* { dg-options "-O2 -ftree-loop-distribution" } */
> > +
> > +typedef long unsigned int size_t;
> > +typedef struct {
> > + long dat[2];
> > +} gsl_complex_long_double;
> > +typedef struct {
> > + size_t size;
> > + size_t stride;
> > + long *data;
> > +} gsl_vector_complex_long_double;
> > +
> > +void gsl_vector_complex_long_double_set_zero (gsl_vector_complex_long_double * v)
> > +{
> > + long * const data = v->data;
> > + const size_t n = v->size;
> > + const size_t stride = v->stride;
> > + const gsl_complex_long_double zero = { { 0,0} } ;
> > + size_t i;
> > + for (i = 0; i < n; i++)
> > + *(gsl_complex_long_double *) (data + 2 * i * stride) = zero;
> > +}
> > +
> >