From 0a500dd3acd012e36ffdd1518640d1c701fa890c Mon Sep 17 00:00:00 2001 From: Richard Guenther Date: Mon, 24 Oct 2011 12:31:01 +0000 Subject: [PATCH] re PR tree-optimization/50838 (ice in refs_may_alias_p_1 with -O3) 2011-10-24 Richard Guenther PR tree-optimization/50838 * tree-data-ref.c (dr_analyze_indices): Properly canonicalize a MEM_REF base if we change it. * gcc.dg/torture/pr50838.c: New testcase. From-SVN: r180381 --- gcc/ChangeLog | 6 +++++ gcc/testsuite/ChangeLog | 5 ++++ gcc/testsuite/gcc.dg/torture/pr50838.c | 27 ++++++++++++++++++++++ gcc/tree-data-ref.c | 42 ++++++++++++++++++++-------------- 4 files changed, 63 insertions(+), 17 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/torture/pr50838.c diff --git a/gcc/ChangeLog b/gcc/ChangeLog index d91e39f..69450bb 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,9 @@ +2011-10-24 Richard Guenther + + PR tree-optimization/50838 + * tree-data-ref.c (dr_analyze_indices): Properly canonicalize + a MEM_REF base if we change it. + 2011-10-24 Bernd Schmidt PR bootstrap/50836 diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index af10398..bd252aa 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2011-10-24 Richard Guenther + + PR tree-optimization/50838 + * gcc.dg/torture/pr50838.c: New testcase. + 2011-10-24 Ira Rosen PR tree-optimization/50730 diff --git a/gcc/testsuite/gcc.dg/torture/pr50838.c b/gcc/testsuite/gcc.dg/torture/pr50838.c new file mode 100644 index 0000000..a3911c9 --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr50838.c @@ -0,0 +1,27 @@ +/* { dg-do compile } */ + +typedef void * gcv_object_t; +typedef gcv_object_t object; +typedef const void * Pseudofun; +extern struct pseudocode_tab_ { + Pseudofun pseudo_eql; + Pseudofun pseudo_iconv_wcslen; + Pseudofun pseudo_iconv_wcstombs; + Pseudofun pseudo_iconv_range; +} +pseudocode_tab; +extern struct symbol_tab_ { + object pointer[1024]; +} pseudofun_tab; +int +init_memory (void) +{ + object* ptr2 = &pseudofun_tab.pointer[0]; + const Pseudofun* ptr1 = (const Pseudofun*)&pseudocode_tab; + unsigned int count = (sizeof(pseudocode_tab)/sizeof(Pseudofun)); + while (count--) + { + *ptr2++ = (gcv_object_t)(((unsigned char *)((*ptr1)))); + ptr1++; + } +} diff --git a/gcc/tree-data-ref.c b/gcc/tree-data-ref.c index 053ffea..4e0de05 100644 --- a/gcc/tree-data-ref.c +++ b/gcc/tree-data-ref.c @@ -855,7 +855,7 @@ static void dr_analyze_indices (struct data_reference *dr, loop_p nest, loop_p loop) { VEC (tree, heap) *access_fns = NULL; - tree ref, aref, op; + tree ref, *aref, op; tree base, off, access_fn; basic_block before_loop; @@ -886,50 +886,58 @@ dr_analyze_indices (struct data_reference *dr, loop_p nest, loop_p loop) } /* Analyze access functions of dimensions we know to be independent. */ - aref = ref; - while (handled_component_p (aref)) + aref = &ref; + while (handled_component_p (*aref)) { - if (TREE_CODE (aref) == ARRAY_REF) + if (TREE_CODE (*aref) == ARRAY_REF) { - op = TREE_OPERAND (aref, 1); + op = TREE_OPERAND (*aref, 1); access_fn = analyze_scalar_evolution (loop, op); access_fn = instantiate_scev (before_loop, loop, access_fn); VEC_safe_push (tree, heap, access_fns, access_fn); /* For ARRAY_REFs the base is the reference with the index replaced by zero if we can not strip it as the outermost component. */ - if (aref == ref) - ref = TREE_OPERAND (ref, 0); + if (*aref == ref) + { + *aref = TREE_OPERAND (*aref, 0); + continue; + } else - TREE_OPERAND (aref, 1) = build_int_cst (TREE_TYPE (op), 0); + TREE_OPERAND (*aref, 1) = build_int_cst (TREE_TYPE (op), 0); } - aref = TREE_OPERAND (aref, 0); + aref = &TREE_OPERAND (*aref, 0); } /* If the address operand of a MEM_REF base has an evolution in the analyzed nest, add it as an additional independent access-function. */ - if (TREE_CODE (aref) == MEM_REF) + if (TREE_CODE (*aref) == MEM_REF) { - op = TREE_OPERAND (aref, 0); + op = TREE_OPERAND (*aref, 0); access_fn = analyze_scalar_evolution (loop, op); access_fn = instantiate_scev (before_loop, loop, access_fn); if (TREE_CODE (access_fn) == POLYNOMIAL_CHREC) { + tree orig_type; base = initial_condition (access_fn); + orig_type = TREE_TYPE (base); + STRIP_USELESS_TYPE_CONVERSION (base); split_constant_offset (base, &base, &off); /* Fold the MEM_REF offset into the evolutions initial value to make more bases comparable. */ - if (!integer_zerop (TREE_OPERAND (aref, 1))) + if (!integer_zerop (TREE_OPERAND (*aref, 1))) { off = size_binop (PLUS_EXPR, off, fold_convert (ssizetype, - TREE_OPERAND (aref, 1))); - TREE_OPERAND (aref, 1) - = build_int_cst (TREE_TYPE (TREE_OPERAND (aref, 1)), 0); + TREE_OPERAND (*aref, 1))); + TREE_OPERAND (*aref, 1) + = build_int_cst (TREE_TYPE (TREE_OPERAND (*aref, 1)), 0); } access_fn = chrec_replace_initial_condition - (access_fn, fold_convert (TREE_TYPE (base), off)); - TREE_OPERAND (aref, 0) = base; + (access_fn, fold_convert (orig_type, off)); + *aref = fold_build2_loc (EXPR_LOCATION (*aref), + MEM_REF, TREE_TYPE (*aref), + base, TREE_OPERAND (*aref, 1)); VEC_safe_push (tree, heap, access_fns, access_fn); } } -- 2.7.4