aboutsummaryrefslogtreecommitdiffstats
path: root/gcc-4.9/gcc/gimplify.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc-4.9/gcc/gimplify.c')
-rw-r--r--gcc-4.9/gcc/gimplify.c205
1 files changed, 156 insertions, 49 deletions
diff --git a/gcc-4.9/gcc/gimplify.c b/gcc-4.9/gcc/gimplify.c
index 9f4bad853..a550544a0 100644
--- a/gcc-4.9/gcc/gimplify.c
+++ b/gcc-4.9/gcc/gimplify.c
@@ -138,6 +138,7 @@ struct gimplify_omp_ctx
enum omp_clause_default_kind default_kind;
enum omp_region_type region_type;
bool combined_loop;
+ bool distribute;
};
static struct gimplify_ctx *gimplify_ctxp;
@@ -1940,15 +1941,6 @@ gimplify_compound_lval (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
if (TREE_OPERAND (t, 3) == NULL_TREE)
{
tree elmt_type = TREE_TYPE (TREE_TYPE (TREE_OPERAND (t, 0)));
- /* FIXME google - In some edge cases, ELMT_TYPE may
- not have been laid out. This causes an ICE later
- (PR 55245). We call layout_type if ELMT_TYPE is not
- yet complete, but this is not where this bug should
- be fixed. The FE should have laid out all the types
- before gimplification. When a proper fix for PR
- 55245 is available, remove this. */
- if (!COMPLETE_TYPE_P (elmt_type))
- layout_type (elmt_type);
tree elmt_size = unshare_expr (array_ref_element_size (t));
tree factor = size_int (TYPE_ALIGN_UNIT (elmt_type));
@@ -2178,7 +2170,7 @@ maybe_with_size_expr (tree *expr_p)
Store any side-effects in PRE_P. CALL_LOCATION is the location of
the CALL_EXPR. */
-static enum gimplify_status
+enum gimplify_status
gimplify_arg (tree *arg_p, gimple_seq *pre_p, location_t call_location)
{
bool (*test) (tree);
@@ -4855,19 +4847,29 @@ gimplify_addr_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
mark_addressable (TREE_OPERAND (expr, 0));
- /* The FEs may end up building ADDR_EXPRs early on a decl with
- an incomplete type. Re-build ADDR_EXPRs in canonical form
- here. */
- if (!types_compatible_p (TREE_TYPE (op0), TREE_TYPE (TREE_TYPE (expr))))
- *expr_p = build_fold_addr_expr (op0);
+ /* Fix to PR/41163 (r151122) broke LIPO. Calls to builtin functions
+ were 'canonicized' in profile-use pass, but not in profile-gen. */
+ if (!flag_dyn_ipa)
+ {
+ /* The FEs may end up building ADDR_EXPRs early on a decl with
+ an incomplete type. Re-build ADDR_EXPRs in canonical form
+ here. */
+ if (!types_compatible_p (TREE_TYPE (op0), TREE_TYPE (TREE_TYPE (expr))))
+ *expr_p = build_fold_addr_expr (op0);
+ }
/* Make sure TREE_CONSTANT and TREE_SIDE_EFFECTS are set properly. */
recompute_tree_invariant_for_addr_expr (*expr_p);
- /* If we re-built the ADDR_EXPR add a conversion to the original type
- if required. */
- if (!useless_type_conversion_p (TREE_TYPE (expr), TREE_TYPE (*expr_p)))
- *expr_p = fold_convert (TREE_TYPE (expr), *expr_p);
+ /* Fix to PR/41163 (r151122) broke LIPO. Calls to builtin functions
+ were 'canonicized' in profile-use pass, but not in profile-gen. */
+ if (!flag_dyn_ipa)
+ {
+ /* If we re-built the ADDR_EXPR add a conversion to the original type
+ if required. */
+ if (!useless_type_conversion_p (TREE_TYPE (expr), TREE_TYPE (*expr_p)))
+ *expr_p = fold_convert (TREE_TYPE (expr), *expr_p);
+ }
break;
}
@@ -5651,6 +5653,7 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
if (ctx->region_type == ORT_TARGET)
{
+ ret = lang_hooks.decls.omp_disregard_value_expr (decl, true);
if (n == NULL)
{
if (!lang_hooks.types.omp_mappable_type (TREE_TYPE (decl)))
@@ -5663,8 +5666,12 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
omp_add_variable (ctx, decl, GOVD_MAP | flags);
}
else
- n->value |= flags;
- ret = lang_hooks.decls.omp_disregard_value_expr (decl, true);
+ {
+ /* If nothing changed, there's nothing left to do. */
+ if ((n->value & flags) == flags)
+ return ret;
+ n->value |= flags;
+ }
goto do_outer;
}
@@ -5950,14 +5957,21 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
goto do_add;
case OMP_CLAUSE_MAP:
- if (OMP_CLAUSE_SIZE (c)
- && gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
- NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
+ decl = OMP_CLAUSE_DECL (c);
+ if (error_operand_p (decl))
+ {
+ remove = true;
+ break;
+ }
+ if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
+ OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
+ : TYPE_SIZE_UNIT (TREE_TYPE (decl));
+ if (gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
+ NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
{
remove = true;
break;
}
- decl = OMP_CLAUSE_DECL (c);
if (!DECL_P (decl))
{
if (gimplify_expr (&OMP_CLAUSE_DECL (c), pre_p,
@@ -5995,15 +6009,17 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
case OMP_CLAUSE_TO:
case OMP_CLAUSE_FROM:
- if (OMP_CLAUSE_SIZE (c)
- && gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
- NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
+ decl = OMP_CLAUSE_DECL (c);
+ if (error_operand_p (decl))
{
remove = true;
break;
}
- decl = OMP_CLAUSE_DECL (c);
- if (error_operand_p (decl))
+ if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
+ OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
+ : TYPE_SIZE_UNIT (TREE_TYPE (decl));
+ if (gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
+ NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
{
remove = true;
break;
@@ -6075,6 +6091,27 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
gimplify_omp_ctxp = outer_ctx;
}
+ else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
+ && OMP_CLAUSE_LINEAR_STMT (c))
+ {
+ gimplify_omp_ctxp = ctx;
+ push_gimplify_context ();
+ if (TREE_CODE (OMP_CLAUSE_LINEAR_STMT (c)) != BIND_EXPR)
+ {
+ tree bind = build3 (BIND_EXPR, void_type_node, NULL,
+ NULL, NULL);
+ TREE_SIDE_EFFECTS (bind) = 1;
+ BIND_EXPR_BODY (bind) = OMP_CLAUSE_LINEAR_STMT (c);
+ OMP_CLAUSE_LINEAR_STMT (c) = bind;
+ }
+ gimplify_and_add (OMP_CLAUSE_LINEAR_STMT (c),
+ &OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c));
+ pop_gimplify_context
+ (gimple_seq_first_stmt (OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c)));
+ OMP_CLAUSE_LINEAR_STMT (c) = NULL_TREE;
+
+ gimplify_omp_ctxp = outer_ctx;
+ }
if (notice_outer)
goto do_notice;
break;
@@ -6157,6 +6194,12 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
remove = true;
break;
}
+ if (gimplify_expr (&OMP_CLAUSE_ALIGNED_ALIGNMENT (c), pre_p, NULL,
+ is_gimple_val, fb_rvalue) == GS_ERROR)
+ {
+ remove = true;
+ break;
+ }
if (!is_global_var (decl)
&& TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
omp_add_variable (ctx, decl, GOVD_ALIGNED);
@@ -6179,13 +6222,21 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
gimplify_omp_ctxp = ctx;
}
+struct gimplify_adjust_omp_clauses_data
+{
+ tree *list_p;
+ gimple_seq *pre_p;
+};
+
/* For all variables that were not actually used within the context,
remove PRIVATE, SHARED, and FIRSTPRIVATE clauses. */
static int
gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
{
- tree *list_p = (tree *) data;
+ tree *list_p = ((struct gimplify_adjust_omp_clauses_data *) data)->list_p;
+ gimple_seq *pre_p
+ = ((struct gimplify_adjust_omp_clauses_data *) data)->pre_p;
tree decl = (tree) n->key;
unsigned flags = n->value;
enum omp_clause_code code;
@@ -6278,6 +6329,8 @@ gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (clause);
OMP_CLAUSE_CHAIN (clause) = nc;
}
+ else
+ OMP_CLAUSE_SIZE (clause) = DECL_SIZE_UNIT (decl);
}
if (code == OMP_CLAUSE_FIRSTPRIVATE && (flags & GOVD_LASTPRIVATE) != 0)
{
@@ -6286,15 +6339,21 @@ gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (nc) = 1;
OMP_CLAUSE_CHAIN (nc) = *list_p;
OMP_CLAUSE_CHAIN (clause) = nc;
- lang_hooks.decls.omp_finish_clause (nc);
+ struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
+ gimplify_omp_ctxp = ctx->outer_context;
+ lang_hooks.decls.omp_finish_clause (nc, pre_p);
+ gimplify_omp_ctxp = ctx;
}
*list_p = clause;
- lang_hooks.decls.omp_finish_clause (clause);
+ struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
+ gimplify_omp_ctxp = ctx->outer_context;
+ lang_hooks.decls.omp_finish_clause (clause, pre_p);
+ gimplify_omp_ctxp = ctx;
return 0;
}
static void
-gimplify_adjust_omp_clauses (tree *list_p)
+gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
{
struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
tree c, decl;
@@ -6338,7 +6397,11 @@ gimplify_adjust_omp_clauses (tree *list_p)
if (n == NULL
|| (n->value & GOVD_DATA_SHARE_CLASS) == 0)
{
- int flags = GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE;
+ int flags = GOVD_FIRSTPRIVATE;
+ /* #pragma omp distribute does not allow
+ lastprivate clause. */
+ if (!ctx->outer_context->distribute)
+ flags |= GOVD_LASTPRIVATE;
if (n == NULL)
omp_add_variable (ctx->outer_context, decl,
flags | GOVD_SEEN);
@@ -6436,6 +6499,8 @@ gimplify_adjust_omp_clauses (tree *list_p)
OMP_CLAUSE_CHAIN (c) = nc;
c = nc;
}
+ else if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
+ OMP_CLAUSE_SIZE (c) = DECL_SIZE_UNIT (decl);
break;
case OMP_CLAUSE_TO:
@@ -6460,6 +6525,8 @@ gimplify_adjust_omp_clauses (tree *list_p)
OMP_CLAUSE_SIZE (c), true);
}
}
+ else if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
+ OMP_CLAUSE_SIZE (c) = DECL_SIZE_UNIT (decl);
break;
case OMP_CLAUSE_REDUCTION:
@@ -6495,7 +6562,10 @@ gimplify_adjust_omp_clauses (tree *list_p)
}
/* Add in any implicit data sharing. */
- splay_tree_foreach (ctx->variables, gimplify_adjust_omp_clauses_1, list_p);
+ struct gimplify_adjust_omp_clauses_data data;
+ data.list_p = list_p;
+ data.pre_p = pre_p;
+ splay_tree_foreach (ctx->variables, gimplify_adjust_omp_clauses_1, &data);
gimplify_omp_ctxp = ctx->outer_context;
delete_omp_context (ctx);
@@ -6526,7 +6596,7 @@ gimplify_omp_parallel (tree *expr_p, gimple_seq *pre_p)
else
pop_gimplify_context (NULL);
- gimplify_adjust_omp_clauses (&OMP_PARALLEL_CLAUSES (expr));
+ gimplify_adjust_omp_clauses (pre_p, &OMP_PARALLEL_CLAUSES (expr));
g = gimple_build_omp_parallel (body,
OMP_PARALLEL_CLAUSES (expr),
@@ -6562,7 +6632,7 @@ gimplify_omp_task (tree *expr_p, gimple_seq *pre_p)
else
pop_gimplify_context (NULL);
- gimplify_adjust_omp_clauses (&OMP_TASK_CLAUSES (expr));
+ gimplify_adjust_omp_clauses (pre_p, &OMP_TASK_CLAUSES (expr));
g = gimple_build_omp_task (body,
OMP_TASK_CLAUSES (expr),
@@ -6619,6 +6689,8 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
|| TREE_CODE (for_stmt) == CILK_SIMD);
gimplify_scan_omp_clauses (&OMP_FOR_CLAUSES (for_stmt), pre_p,
simd ? ORT_SIMD : ORT_WORKSHARE);
+ if (TREE_CODE (for_stmt) == OMP_DISTRIBUTE)
+ gimplify_omp_ctxp->distribute = true;
/* Handle OMP_FOR_INIT. */
for_pre_body = NULL;
@@ -6702,6 +6774,31 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
bool lastprivate
= (!has_decl_expr
|| !bitmap_bit_p (has_decl_expr, DECL_UID (decl)));
+ if (lastprivate
+ && gimplify_omp_ctxp->outer_context
+ && gimplify_omp_ctxp->outer_context->region_type
+ == ORT_WORKSHARE
+ && gimplify_omp_ctxp->outer_context->combined_loop
+ && !gimplify_omp_ctxp->outer_context->distribute)
+ {
+ struct gimplify_omp_ctx *outer
+ = gimplify_omp_ctxp->outer_context;
+ n = splay_tree_lookup (outer->variables,
+ (splay_tree_key) decl);
+ if (n != NULL
+ && (n->value & GOVD_DATA_SHARE_CLASS) == GOVD_LOCAL)
+ lastprivate = false;
+ else if (omp_check_private (outer, decl, false))
+ error ("lastprivate variable %qE is private in outer "
+ "context", DECL_NAME (decl));
+ else
+ {
+ omp_add_variable (outer, decl,
+ GOVD_LASTPRIVATE | GOVD_SEEN);
+ if (outer->outer_context)
+ omp_notice_variable (outer->outer_context, decl, true);
+ }
+ }
c = build_omp_clause (input_location,
lastprivate ? OMP_CLAUSE_LASTPRIVATE
: OMP_CLAUSE_PRIVATE);
@@ -6721,10 +6818,13 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
/* If DECL is not a gimple register, create a temporary variable to act
as an iteration counter. This is valid, since DECL cannot be
- modified in the body of the loop. */
+ modified in the body of the loop. Similarly for any iteration vars
+ in simd with collapse > 1 where the iterator vars must be
+ lastprivate. */
if (orig_for_stmt != for_stmt)
var = decl;
- else if (!is_gimple_reg (decl))
+ else if (!is_gimple_reg (decl)
+ || (simd && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) > 1))
{
var = create_tmp_var (TREE_TYPE (decl), get_name (decl));
TREE_OPERAND (t, 0) = var;
@@ -6777,8 +6877,8 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
case POSTINCREMENT_EXPR:
{
tree decl = TREE_OPERAND (t, 0);
- // c_omp_for_incr_canonicalize_ptr() should have been
- // called to massage things appropriately.
+ /* c_omp_for_incr_canonicalize_ptr() should have been
+ called to massage things appropriately. */
gcc_assert (!POINTER_TYPE_P (TREE_TYPE (decl)));
if (orig_for_stmt != for_stmt)
@@ -6794,6 +6894,9 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
case PREDECREMENT_EXPR:
case POSTDECREMENT_EXPR:
+ /* c_omp_for_incr_canonicalize_ptr() should have been
+ called to massage things appropriately. */
+ gcc_assert (!POINTER_TYPE_P (TREE_TYPE (decl)));
if (orig_for_stmt != for_stmt)
break;
t = build_int_cst (TREE_TYPE (decl), -1);
@@ -6834,12 +6937,16 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
ret = MIN (ret, tret);
if (c)
{
- OMP_CLAUSE_LINEAR_STEP (c) = TREE_OPERAND (t, 1);
+ tree step = TREE_OPERAND (t, 1);
+ tree stept = TREE_TYPE (decl);
+ if (POINTER_TYPE_P (stept))
+ stept = sizetype;
+ step = fold_convert (stept, step);
if (TREE_CODE (t) == MINUS_EXPR)
+ step = fold_build1 (NEGATE_EXPR, stept, step);
+ OMP_CLAUSE_LINEAR_STEP (c) = step;
+ if (step != TREE_OPERAND (t, 1))
{
- t = TREE_OPERAND (t, 1);
- OMP_CLAUSE_LINEAR_STEP (c)
- = fold_build1 (NEGATE_EXPR, TREE_TYPE (t), t);
tret = gimplify_expr (&OMP_CLAUSE_LINEAR_STEP (c),
&for_pre_body, NULL,
is_gimple_val, fb_rvalue);
@@ -6906,7 +7013,7 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
TREE_OPERAND (TREE_OPERAND (t, 1), 0) = var;
}
- gimplify_adjust_omp_clauses (&OMP_FOR_CLAUSES (orig_for_stmt));
+ gimplify_adjust_omp_clauses (pre_p, &OMP_FOR_CLAUSES (orig_for_stmt));
int kind;
switch (TREE_CODE (orig_for_stmt))
@@ -7006,7 +7113,7 @@ gimplify_omp_workshare (tree *expr_p, gimple_seq *pre_p)
}
else
gimplify_and_add (OMP_BODY (expr), &body);
- gimplify_adjust_omp_clauses (&OMP_CLAUSES (expr));
+ gimplify_adjust_omp_clauses (pre_p, &OMP_CLAUSES (expr));
switch (TREE_CODE (expr))
{
@@ -7045,7 +7152,7 @@ gimplify_omp_target_update (tree *expr_p, gimple_seq *pre_p)
gimplify_scan_omp_clauses (&OMP_TARGET_UPDATE_CLAUSES (expr), pre_p,
ORT_WORKSHARE);
- gimplify_adjust_omp_clauses (&OMP_TARGET_UPDATE_CLAUSES (expr));
+ gimplify_adjust_omp_clauses (pre_p, &OMP_TARGET_UPDATE_CLAUSES (expr));
stmt = gimple_build_omp_target (NULL, GF_OMP_TARGET_KIND_UPDATE,
OMP_TARGET_UPDATE_CLAUSES (expr));