Commit 6d098c57 by Richard Biener Committed by Richard Biener

tree-vectorizer.h (_loop_vec_info): Add scalar_cost_vec and single_scalar_iteration_cost members.

2015-06-22  Richard Biener  <rguenther@suse.de>

	* tree-vectorizer.h (_loop_vec_info): Add scalar_cost_vec
	and single_scalar_iteration_cost members.
	(LOOP_VINFO_SCALAR_ITERATION_COST): New.
	(LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST): Likewise.
	(vect_get_single_scalar_iteration_cost): Remove.
	* tree-vect-data-refs.c (vect_peeling_hash_get_lowest_cost):
	Use LOOP_VINFO_SCALAR_ITERATION_COST.
	* tree-vect-loop.c (destroy_loop_vec_info): Free
	scalar_cost_vec.
	(vect_get_single_scalar_iteration_cost): Compute result into
	LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST and
	LOOP_VINFO_SCALAR_ITERATION_COST.  Make static.
	(vect_analyze_loop_2): Call vect_get_single_scalar_iteration_cost.
	(vect_estimate_min_profitable_iters): Use them.

From-SVN: r224723
parent 606e3099
2015-06-22 Richard Biener <rguenther@suse.de>
* tree-vectorizer.h (_loop_vec_info): Add scalar_cost_vec
and single_scalar_iteration_cost members.
(LOOP_VINFO_SCALAR_ITERATION_COST): New.
(LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST): Likewise.
(vect_get_single_scalar_iteration_cost): Remove.
* tree-vect-data-refs.c (vect_peeling_hash_get_lowest_cost):
Use LOOP_VINFO_SCALAR_ITERATION_COST.
* tree-vect-loop.c (destroy_loop_vec_info): Free
scalar_cost_vec.
(vect_get_single_scalar_iteration_cost): Compute result into
LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST and
LOOP_VINFO_SCALAR_ITERATION_COST. Make static.
(vect_analyze_loop_2): Call vect_get_single_scalar_iteration_cost.
(vect_estimate_min_profitable_iters): Use them.
2015-06-22 Christian Bruel <christian.bruel@st.com>
PR target/52144
......
......@@ -1165,11 +1165,10 @@ vect_peeling_hash_get_lowest_cost (_vect_peel_info **slot,
SET_DR_MISALIGNMENT (dr, save_misalignment);
}
auto_vec<stmt_info_for_cost> scalar_cost_vec;
vect_get_single_scalar_iteration_cost (loop_vinfo, &scalar_cost_vec);
outside_cost += vect_get_known_peeling_cost
(loop_vinfo, elem->npeel, &dummy,
&scalar_cost_vec, &prologue_cost_vec, &epilogue_cost_vec);
&LOOP_VINFO_SCALAR_ITERATION_COST (loop_vinfo),
&prologue_cost_vec, &epilogue_cost_vec);
/* Prologue and epilogue costs are added to the target model later.
These costs depend only on the scalar iteration cost, the
......
......@@ -1095,12 +1095,82 @@ destroy_loop_vec_info (loop_vec_info loop_vinfo, bool clean_stmts)
LOOP_VINFO_PEELING_HTAB (loop_vinfo) = NULL;
destroy_cost_data (LOOP_VINFO_TARGET_COST_DATA (loop_vinfo));
loop_vinfo->scalar_cost_vec.release ();
free (loop_vinfo);
loop->aux = NULL;
}
/* Calculate the cost of one scalar iteration of the loop. */
static void
vect_get_single_scalar_iteration_cost (loop_vec_info loop_vinfo)
{
struct loop *loop = LOOP_VINFO_LOOP (loop_vinfo);
basic_block *bbs = LOOP_VINFO_BBS (loop_vinfo);
int nbbs = loop->num_nodes, factor, scalar_single_iter_cost = 0;
int innerloop_iters, i;
/* Count statements in scalar loop. Using this as scalar cost for a single
iteration for now.
TODO: Add outer loop support.
TODO: Consider assigning different costs to different scalar
statements. */
/* FORNOW. */
innerloop_iters = 1;
if (loop->inner)
innerloop_iters = 50; /* FIXME */
for (i = 0; i < nbbs; i++)
{
gimple_stmt_iterator si;
basic_block bb = bbs[i];
if (bb->loop_father == loop->inner)
factor = innerloop_iters;
else
factor = 1;
for (si = gsi_start_bb (bb); !gsi_end_p (si); gsi_next (&si))
{
gimple stmt = gsi_stmt (si);
stmt_vec_info stmt_info = vinfo_for_stmt (stmt);
if (!is_gimple_assign (stmt) && !is_gimple_call (stmt))
continue;
/* Skip stmts that are not vectorized inside the loop. */
if (stmt_info
&& !STMT_VINFO_RELEVANT_P (stmt_info)
&& (!STMT_VINFO_LIVE_P (stmt_info)
|| !VECTORIZABLE_CYCLE_DEF (STMT_VINFO_DEF_TYPE (stmt_info)))
&& !STMT_VINFO_IN_PATTERN_P (stmt_info))
continue;
vect_cost_for_stmt kind;
if (STMT_VINFO_DATA_REF (vinfo_for_stmt (stmt)))
{
if (DR_IS_READ (STMT_VINFO_DATA_REF (vinfo_for_stmt (stmt))))
kind = scalar_load;
else
kind = scalar_store;
}
else
kind = scalar_stmt;
scalar_single_iter_cost
+= record_stmt_cost (&LOOP_VINFO_SCALAR_ITERATION_COST (loop_vinfo),
factor, kind, NULL, 0, vect_prologue);
}
}
LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST (loop_vinfo)
= scalar_single_iter_cost;
}
/* Function vect_analyze_loop_1.
Apply a set of analyses on LOOP, and create a loop_vec_info struct
......@@ -1834,6 +1904,9 @@ vect_analyze_loop_2 (loop_vec_info loop_vinfo)
return false;
}
/* Compute the scalar iteration cost. */
vect_get_single_scalar_iteration_cost (loop_vinfo);
/* This pass will decide on using loop versioning and/or loop peeling in
order to enhance the alignment of data references in the loop. */
......@@ -2706,74 +2779,6 @@ vect_force_simple_reduction (loop_vec_info loop_info, gimple phi,
double_reduc, true);
}
/* Calculate the cost of one scalar iteration of the loop. */
int
vect_get_single_scalar_iteration_cost (loop_vec_info loop_vinfo,
stmt_vector_for_cost *scalar_cost_vec)
{
struct loop *loop = LOOP_VINFO_LOOP (loop_vinfo);
basic_block *bbs = LOOP_VINFO_BBS (loop_vinfo);
int nbbs = loop->num_nodes, factor, scalar_single_iter_cost = 0;
int innerloop_iters, i;
/* Count statements in scalar loop. Using this as scalar cost for a single
iteration for now.
TODO: Add outer loop support.
TODO: Consider assigning different costs to different scalar
statements. */
/* FORNOW. */
innerloop_iters = 1;
if (loop->inner)
innerloop_iters = 50; /* FIXME */
for (i = 0; i < nbbs; i++)
{
gimple_stmt_iterator si;
basic_block bb = bbs[i];
if (bb->loop_father == loop->inner)
factor = innerloop_iters;
else
factor = 1;
for (si = gsi_start_bb (bb); !gsi_end_p (si); gsi_next (&si))
{
gimple stmt = gsi_stmt (si);
stmt_vec_info stmt_info = vinfo_for_stmt (stmt);
if (!is_gimple_assign (stmt) && !is_gimple_call (stmt))
continue;
/* Skip stmts that are not vectorized inside the loop. */
if (stmt_info
&& !STMT_VINFO_RELEVANT_P (stmt_info)
&& (!STMT_VINFO_LIVE_P (stmt_info)
|| !VECTORIZABLE_CYCLE_DEF (STMT_VINFO_DEF_TYPE (stmt_info)))
&& !STMT_VINFO_IN_PATTERN_P (stmt_info))
continue;
vect_cost_for_stmt kind;
if (STMT_VINFO_DATA_REF (vinfo_for_stmt (stmt)))
{
if (DR_IS_READ (STMT_VINFO_DATA_REF (vinfo_for_stmt (stmt))))
kind = scalar_load;
else
kind = scalar_store;
}
else
kind = scalar_stmt;
scalar_single_iter_cost
+= record_stmt_cost (scalar_cost_vec, factor, kind,
NULL, 0, vect_prologue);
}
}
return scalar_single_iter_cost;
}
/* Calculate cost of peeling the loop PEEL_ITERS_PROLOGUE times. */
int
vect_get_known_peeling_cost (loop_vec_info loop_vinfo, int peel_iters_prologue,
......@@ -2901,9 +2906,8 @@ vect_estimate_min_profitable_iters (loop_vec_info loop_vinfo,
TODO: Consider assigning different costs to different scalar
statements. */
auto_vec<stmt_info_for_cost> scalar_cost_vec;
scalar_single_iter_cost
= vect_get_single_scalar_iteration_cost (loop_vinfo, &scalar_cost_vec);
= LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST (loop_vinfo);
/* Add additional cost for the peeled instructions in prologue and epilogue
loop.
......@@ -2941,7 +2945,7 @@ vect_estimate_min_profitable_iters (loop_vec_info loop_vinfo,
NULL, 0, vect_epilogue);
stmt_info_for_cost *si;
int j;
FOR_EACH_VEC_ELT (scalar_cost_vec, j, si)
FOR_EACH_VEC_ELT (LOOP_VINFO_SCALAR_ITERATION_COST (loop_vinfo), j, si)
{
struct _stmt_vec_info *stmt_info
= si->stmt ? vinfo_for_stmt (si->stmt) : NULL;
......@@ -2968,7 +2972,8 @@ vect_estimate_min_profitable_iters (loop_vec_info loop_vinfo,
(void) vect_get_known_peeling_cost (loop_vinfo, peel_iters_prologue,
&peel_iters_epilogue,
&scalar_cost_vec,
&LOOP_VINFO_SCALAR_ITERATION_COST
(loop_vinfo),
&prologue_cost_vec,
&epilogue_cost_vec);
......
......@@ -328,6 +328,12 @@ typedef struct _loop_vec_info {
/* Hash table used to choose the best peeling option. */
hash_table<peel_info_hasher> *peeling_htab;
/* Cost vector for a single scalar iteration. */
vec<stmt_info_for_cost> scalar_cost_vec;
/* Cost of a single scalar iteration. */
int single_scalar_iteration_cost;
/* Cost data used by the target cost model. */
void *target_cost_data;
......@@ -406,6 +412,8 @@ typedef struct _loop_vec_info {
#define LOOP_VINFO_PEELING_FOR_NITER(L) (L)->peeling_for_niter
#define LOOP_VINFO_NO_DATA_DEPENDENCIES(L) (L)->no_data_dependencies
#define LOOP_VINFO_SCALAR_LOOP(L) (L)->scalar_loop
#define LOOP_VINFO_SCALAR_ITERATION_COST(L) (L)->scalar_cost_vec
#define LOOP_VINFO_SINGLE_SCALAR_ITERATION_COST(L) (L)->single_scalar_iteration_cost
#define LOOP_REQUIRES_VERSIONING_FOR_ALIGNMENT(L) \
((L)->may_misalign_stmts.length () > 0)
......@@ -1101,8 +1109,6 @@ extern int vect_get_known_peeling_cost (loop_vec_info, int, int *,
stmt_vector_for_cost *,
stmt_vector_for_cost *,
stmt_vector_for_cost *);
extern int vect_get_single_scalar_iteration_cost (loop_vec_info,
stmt_vector_for_cost *);
/* In tree-vect-slp.c. */
extern void vect_free_slp_instance (slp_instance);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment