re PR tree-optimization/68379 (BB vectorization: definition in block 13 follows the use for SSA_NAME)

2015-12-01  Richard Biener  <rguenther@suse.de>

	PR tree-optimization/68379
	* tree-vect-stmts.c (vectorizable_load): For BB vectorization
	always base loads on the first used DR of a group.
	* tree-vect-data-refs.c (vect_slp_analyze_and_verify_node_alignment):
	Compute alignment of the first scalar element unconditionally.

	* gcc.dg/torture/pr68379.c: New testcase.
	* gfortran.dg/pr68379-1.f90: Likewise.
	* gfortran.dg/pr68379-2.f: Likewise.

From-SVN: r231111
This commit is contained in:
Richard Biener 2015-12-01 14:24:54 +00:00 committed by Richard Biener
parent 2d3f4bf73c
commit 4f0a0218d6
7 changed files with 116 additions and 2 deletions

View File

@ -1,3 +1,11 @@
2015-12-01 Richard Biener <rguenther@suse.de>
PR tree-optimization/68379
* tree-vect-stmts.c (vectorizable_load): For BB vectorization
always base loads on the first used DR of a group.
* tree-vect-data-refs.c (vect_slp_analyze_and_verify_node_alignment):
Compute alignment of the first scalar element unconditionally.
2015-12-01 Richard Biener <rguenther@suse.de> 2015-12-01 Richard Biener <rguenther@suse.de>
PR middle-end/68590 PR middle-end/68590

View File

@ -1,3 +1,10 @@
2015-12-01 Richard Biener <rguenther@suse.de>
PR tree-optimization/68379
* gcc.dg/torture/pr68379.c: New testcase.
* gfortran.dg/pr68379-1.f90: Likewise.
* gfortran.dg/pr68379-2.f: Likewise.
2015-12-01 Christophe Lyon <christophe.lyon@linaro.org> 2015-12-01 Christophe Lyon <christophe.lyon@linaro.org>
* gcc.dg/pr46032.c: Add dg-require-effective-target fopenmp. * gcc.dg/pr46032.c: Add dg-require-effective-target fopenmp.

View File

@ -0,0 +1,12 @@
/* { dg-do compile } */
int a, b[3], c[3][5];
void
fn1 ()
{
int e;
for (a = 2; a >= 0; a--)
for (e = 0; e < 4; e++)
c[a][e] = b[a];
}

View File

@ -0,0 +1,35 @@
! { dg-do compile }
! { dg-options "-O3" }
MODULE qs_efield_berry
TYPE cp_error_type
END TYPE
INTEGER, PARAMETER :: dp=8
TYPE qs_energy_type
REAL(KIND=dp), POINTER :: efield
END TYPE
TYPE qs_environment_type
END TYPE
INTERFACE
SUBROUTINE foo(qs_env,energy,error)
IMPORT
TYPE(qs_environment_type), POINTER :: qs_env
TYPE(cp_error_type) :: error
TYPE(qs_energy_type), POINTER :: energy
END SUBROUTINE
END INTERFACE
CONTAINS
SUBROUTINE qs_efield_mo_derivatives()
TYPE(qs_environment_type), POINTER :: qs_env
TYPE(cp_error_type) :: error
COMPLEX(dp) :: zi(3), zphase(3)
REAL(dp) :: ci(3)
TYPE(qs_energy_type), POINTER :: energy
CALL foo(qs_env, energy, error)
zi = zi * zphase
ci = AIMAG(LOG(zi))
DO idir=1,3
ener_field=ener_field+ci(idir)*fieldfac(idir)
END DO
energy%efield=ener_field
END SUBROUTINE qs_efield_mo_derivatives
END MODULE qs_efield_berry

View File

@ -0,0 +1,24 @@
! { dg-do compile }
! { dg-additional-options "-Ofast" }
! { dg-additional-options "-mavx" { target x86_64-*-* i?86-*-* } }
SUBROUTINE PASSB4 (IDO,L1,CC,CH,WA1,WA2,WA3)
IMPLICIT REAL(4) (A-H, O-Z)
DIMENSION CC(IDO,4,L1), CH(IDO,L1,4), WA1(*), WA2(*), WA3(*)
102 DO 104 K=1,L1
DO 103 I=2,IDO,2
TI1 = CC(I,1,K)-CC(I,3,K)
TI2 = CC(I,1,K)+CC(I,3,K)
TI3 = CC(I,2,K)+CC(I,4,K)
TR2 = CC(I-1,1,K)+CC(I-1,3,K)
TI4 = CC(I-1,2,K)-CC(I-1,4,K)
TR3 = CC(I-1,2,K)+CC(I-1,4,K)
CH(I-1,K,1) = TR2+TR3
CH(I,K,1) = TI2+TI3
CI4 = TI1-TI4
CH(I-1,K,4) = CI4
CH(I,K,4) = CI4
103 CONTINUE
104 CONTINUE
RETURN
END

View File

@ -2102,11 +2102,16 @@ vect_slp_analyze_and_verify_node_alignment (slp_tree node)
the node is permuted in which case we start from the first the node is permuted in which case we start from the first
element in the group. */ element in the group. */
gimple *first_stmt = SLP_TREE_SCALAR_STMTS (node)[0]; gimple *first_stmt = SLP_TREE_SCALAR_STMTS (node)[0];
data_reference_p first_dr = STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt));
if (SLP_TREE_LOAD_PERMUTATION (node).exists ()) if (SLP_TREE_LOAD_PERMUTATION (node).exists ())
first_stmt = GROUP_FIRST_ELEMENT (vinfo_for_stmt (first_stmt)); first_stmt = GROUP_FIRST_ELEMENT (vinfo_for_stmt (first_stmt));
data_reference_p dr = STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt)); data_reference_p dr = STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt));
if (! vect_compute_data_ref_alignment (dr) if (! vect_compute_data_ref_alignment (dr)
/* For creating the data-ref pointer we need alignment of the
first element anyway. */
|| (dr != first_dr
&& ! vect_compute_data_ref_alignment (first_dr))
|| ! verify_data_ref_alignment (dr)) || ! verify_data_ref_alignment (dr))
{ {
if (dump_enabled_p ()) if (dump_enabled_p ())

View File

@ -6148,6 +6148,7 @@ vectorizable_load (gimple *stmt, gimple_stmt_iterator *gsi, gimple **vec_stmt,
bool grouped_load = false; bool grouped_load = false;
bool load_lanes_p = false; bool load_lanes_p = false;
gimple *first_stmt; gimple *first_stmt;
gimple *first_stmt_for_drptr = NULL;
bool inv_p; bool inv_p;
bool negative = false; bool negative = false;
bool compute_in_loop = false; bool compute_in_loop = false;
@ -6751,10 +6752,14 @@ vectorizable_load (gimple *stmt, gimple_stmt_iterator *gsi, gimple **vec_stmt,
if (grouped_load) if (grouped_load)
{ {
first_stmt = GROUP_FIRST_ELEMENT (stmt_info); first_stmt = GROUP_FIRST_ELEMENT (stmt_info);
/* For BB vectorization we directly vectorize a subchain /* For SLP vectorization we directly vectorize a subchain
without permutation. */ without permutation. */
if (slp && ! SLP_TREE_LOAD_PERMUTATION (slp_node).exists ()) if (slp && ! SLP_TREE_LOAD_PERMUTATION (slp_node).exists ())
first_stmt = SLP_TREE_SCALAR_STMTS (slp_node)[0]; first_stmt = SLP_TREE_SCALAR_STMTS (slp_node)[0];
/* For BB vectorization always use the first stmt to base
the data ref pointer on. */
if (bb_vinfo)
first_stmt_for_drptr = SLP_TREE_SCALAR_STMTS (slp_node)[0];
/* Check if the chain of loads is already vectorized. */ /* Check if the chain of loads is already vectorized. */
if (STMT_VINFO_VEC_STMT (vinfo_for_stmt (first_stmt)) if (STMT_VINFO_VEC_STMT (vinfo_for_stmt (first_stmt))
@ -6966,6 +6971,24 @@ vectorizable_load (gimple *stmt, gimple_stmt_iterator *gsi, gimple **vec_stmt,
(DR_REF (first_dr)), 0); (DR_REF (first_dr)), 0);
inv_p = false; inv_p = false;
} }
else if (first_stmt_for_drptr
&& first_stmt != first_stmt_for_drptr)
{
dataref_ptr
= vect_create_data_ref_ptr (first_stmt_for_drptr, aggr_type,
at_loop, offset, &dummy, gsi,
&ptr_incr, simd_lane_access_p,
&inv_p, byte_offset);
/* Adjust the pointer by the difference to first_stmt. */
data_reference_p ptrdr
= STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt_for_drptr));
tree diff = fold_convert (sizetype,
size_binop (MINUS_EXPR,
DR_INIT (first_dr),
DR_INIT (ptrdr)));
dataref_ptr = bump_vector_ptr (dataref_ptr, ptr_incr, gsi,
stmt, diff);
}
else else
dataref_ptr dataref_ptr
= vect_create_data_ref_ptr (first_stmt, aggr_type, at_loop, = vect_create_data_ref_ptr (first_stmt, aggr_type, at_loop,