Both vectorizable_load and vectorizable_store compute an alias type commoning differences between SLP lanes. The following makes sure to use that for gather/scatter rather than the random one from the representative created during scalar stmt gather/scatter analysis.
Bootstrapped and tested on x86_64-unknown-linux-gnu, local aarch64 qemu testing on the way. * tree-vect-stmts.cc (vectorizable_store): Build proper alias + align pointer value for gather/scatter and SLP and use it. (vectorizable_load): Likewise. --- gcc/tree-vect-stmts.cc | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/gcc/tree-vect-stmts.cc b/gcc/tree-vect-stmts.cc index 1ccd38b91af..5c17888060f 100644 --- a/gcc/tree-vect-stmts.cc +++ b/gcc/tree-vect-stmts.cc @@ -8585,7 +8585,6 @@ vectorizable_store (vec_info *vinfo, gcc_assert (useless_type_conversion_p (vectype, TREE_TYPE (vec_oprnd))); } - unsigned HOST_WIDE_INT align; tree final_mask = NULL_TREE; tree final_len = NULL_TREE; tree bias = NULL_TREE; @@ -8600,6 +8599,8 @@ vectorizable_store (vec_info *vinfo, final_mask, vec_mask, gsi); } + unsigned align = get_object_alignment (DR_REF (first_dr_info->dr)); + tree alias_align_ptr = build_int_cst (ref_type, align); if (GATHER_SCATTER_IFN_P (gs_info)) { if (costing_p) @@ -8641,7 +8642,7 @@ vectorizable_store (vec_info *vinfo, if (VECTOR_TYPE_P (TREE_TYPE (vec_offset))) call = gimple_build_call_internal ( IFN_MASK_LEN_SCATTER_STORE, 8, dataref_ptr, - gs_info.alias_ptr, + alias_align_ptr, vec_offset, scale, vec_oprnd, final_mask, final_len, bias); else @@ -8658,12 +8659,12 @@ vectorizable_store (vec_info *vinfo, else if (final_mask) call = gimple_build_call_internal (IFN_MASK_SCATTER_STORE, 6, dataref_ptr, - gs_info.alias_ptr, + alias_align_ptr, vec_offset, scale, vec_oprnd, final_mask); else call = gimple_build_call_internal (IFN_SCATTER_STORE, 5, dataref_ptr, - gs_info.alias_ptr, + alias_align_ptr, vec_offset, scale, vec_oprnd); gimple_call_set_nothrow (call, true); @@ -8819,7 +8820,6 @@ vectorizable_store (vec_info *vinfo, = (j % factor) * const_nunits; tree idx_type = TREE_TYPE (TREE_TYPE (vec_offset)); tree scale = size_int (gs_info.scale); - align = get_object_alignment (DR_REF (first_dr_info->dr)); tree ltype = build_aligned_type (TREE_TYPE (vectype), align); for (unsigned k = 0; k < const_nunits; ++k) { @@ -10448,7 +10448,8 @@ vectorizable_load (vec_info *vinfo, } /* 2. Create the vector-load in the loop. */ - unsigned HOST_WIDE_INT align; + unsigned align = get_object_alignment (DR_REF (first_dr_info->dr)); + tree alias_align_ptr = build_int_cst (ref_type, align); if (GATHER_SCATTER_IFN_P (gs_info)) { if (costing_p) @@ -10496,7 +10497,7 @@ vectorizable_load (vec_info *vinfo, if (VECTOR_TYPE_P (TREE_TYPE (vec_offset))) call = gimple_build_call_internal (IFN_MASK_LEN_GATHER_LOAD, 9, dataref_ptr, - gs_info.alias_ptr, + alias_align_ptr, vec_offset, scale, zero, final_mask, vec_els, final_len, bias); @@ -10512,13 +10513,13 @@ vectorizable_load (vec_info *vinfo, else if (final_mask) call = gimple_build_call_internal (IFN_MASK_GATHER_LOAD, 7, dataref_ptr, - gs_info.alias_ptr, + alias_align_ptr, vec_offset, scale, zero, final_mask, vec_els); else call = gimple_build_call_internal (IFN_GATHER_LOAD, 5, dataref_ptr, - gs_info.alias_ptr, + alias_align_ptr, vec_offset, scale, zero); gimple_call_set_nothrow (call, true); new_stmt = call; @@ -10676,7 +10677,6 @@ vectorizable_load (vec_info *vinfo, unsigned elt_offset = (i % factor) * const_nunits; tree idx_type = TREE_TYPE (TREE_TYPE (vec_offset)); tree scale = size_int (gs_info.scale); - align = get_object_alignment (DR_REF (first_dr_info->dr)); tree ltype = build_aligned_type (TREE_TYPE (vectype), align); for (unsigned k = 0; k < const_nunits; ++k) { -- 2.43.0