aboutsummaryrefslogtreecommitdiff
path: root/gcc/gimplify.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/gimplify.c')
-rw-r--r--gcc/gimplify.c109
1 files changed, 107 insertions, 2 deletions
diff --git a/gcc/gimplify.c b/gcc/gimplify.c
index 0f3e917..3b4fdc7 100644
--- a/gcc/gimplify.c
+++ b/gcc/gimplify.c
@@ -118,6 +118,9 @@ enum gimplify_omp_var_data
GOVD_CONDTEMP = 0x1000000,
+ /* Flag for GOVD_REDUCTION: inscan seen in {in,ex}clusive clause. */
+ GOVD_REDUCTION_INSCAN = 0x2000000,
+
GOVD_DATA_SHARE_CLASS = (GOVD_SHARED | GOVD_PRIVATE | GOVD_FIRSTPRIVATE
| GOVD_LASTPRIVATE | GOVD_REDUCTION | GOVD_LINEAR
| GOVD_LOCAL)
@@ -5492,6 +5495,7 @@ is_gimple_stmt (tree t)
case OMP_SIMD:
case OMP_DISTRIBUTE:
case OACC_LOOP:
+ case OMP_SCAN:
case OMP_SECTIONS:
case OMP_SECTION:
case OMP_SINGLE:
@@ -8119,13 +8123,13 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
case OMP_DISTRIBUTE:
error_at (OMP_CLAUSE_LOCATION (c),
"conditional %<lastprivate%> clause on "
- "%<distribute%> construct");
+ "%qs construct", "distribute");
OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) = 0;
break;
case OMP_TASKLOOP:
error_at (OMP_CLAUSE_LOCATION (c),
"conditional %<lastprivate%> clause on "
- "%<taskloop%> construct");
+ "%qs construct", "taskloop");
OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) = 0;
break;
default:
@@ -8242,6 +8246,36 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
OMP_CLAUSE_REDUCTION_TASK (c) = 0;
}
}
+ if (OMP_CLAUSE_REDUCTION_INSCAN (c))
+ switch (code)
+ {
+ case OMP_SECTIONS:
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%<inscan%> %<reduction%> clause on "
+ "%qs construct", "sections");
+ OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
+ break;
+ case OMP_PARALLEL:
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%<inscan%> %<reduction%> clause on "
+ "%qs construct", "parallel");
+ OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
+ break;
+ case OMP_TEAMS:
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%<inscan%> %<reduction%> clause on "
+ "%qs construct", "teams");
+ OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
+ break;
+ case OMP_TASKLOOP:
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%<inscan%> %<reduction%> clause on "
+ "%qs construct", "taskloop");
+ OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
+ break;
+ default:
+ break;
+ }
/* FALLTHRU */
case OMP_CLAUSE_IN_REDUCTION:
case OMP_CLAUSE_TASK_REDUCTION:
@@ -9290,6 +9324,36 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
ctx->default_kind = OMP_CLAUSE_DEFAULT_KIND (c);
break;
+ case OMP_CLAUSE_INCLUSIVE:
+ case OMP_CLAUSE_EXCLUSIVE:
+ decl = OMP_CLAUSE_DECL (c);
+ {
+ splay_tree_node n = splay_tree_lookup (outer_ctx->variables,
+ (splay_tree_key) decl);
+ if (n == NULL || (n->value & GOVD_REDUCTION) == 0)
+ {
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%qD specified in %qs clause but not in %<inscan%> "
+ "%<reduction%> clause on the containing construct",
+ decl, omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
+ remove = true;
+ }
+ else
+ {
+ n->value |= GOVD_REDUCTION_INSCAN;
+ if (outer_ctx->region_type == ORT_SIMD
+ && outer_ctx->outer_context
+ && outer_ctx->outer_context->region_type == ORT_WORKSHARE)
+ {
+ n = splay_tree_lookup (outer_ctx->outer_context->variables,
+ (splay_tree_key) decl);
+ if (n && (n->value & GOVD_REDUCTION) != 0)
+ n->value |= GOVD_REDUCTION_INSCAN;
+ }
+ }
+ }
+ break;
+
default:
gcc_unreachable ();
}
@@ -9683,7 +9747,9 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, gimple_seq body, tree *list_p,
enum tree_code code)
{
struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
+ tree *orig_list_p = list_p;
tree c, decl;
+ bool has_inscan_reductions = false;
if (body)
{
@@ -10024,6 +10090,21 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, gimple_seq body, tree *list_p,
break;
case OMP_CLAUSE_REDUCTION:
+ if (OMP_CLAUSE_REDUCTION_INSCAN (c))
+ {
+ decl = OMP_CLAUSE_DECL (c);
+ n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
+ if ((n->value & GOVD_REDUCTION_INSCAN) == 0)
+ {
+ remove = true;
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%qD specified in %<inscan%> %<reduction%> clause "
+ "but not in %<scan%> directive clause", decl);
+ break;
+ }
+ has_inscan_reductions = true;
+ }
+ /* FALLTHRU */
case OMP_CLAUSE_IN_REDUCTION:
case OMP_CLAUSE_TASK_REDUCTION:
decl = OMP_CLAUSE_DECL (c);
@@ -10105,6 +10186,8 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, gimple_seq body, tree *list_p,
case OMP_CLAUSE_TILE:
case OMP_CLAUSE_IF_PRESENT:
case OMP_CLAUSE_FINALIZE:
+ case OMP_CLAUSE_INCLUSIVE:
+ case OMP_CLAUSE_EXCLUSIVE:
break;
default:
@@ -10123,6 +10206,18 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, gimple_seq body, tree *list_p,
data.pre_p = pre_p;
splay_tree_foreach (ctx->variables, gimplify_adjust_omp_clauses_1, &data);
+ if (has_inscan_reductions)
+ for (c = *orig_list_p; c; c = OMP_CLAUSE_CHAIN (c))
+ if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
+ && !OMP_CLAUSE_LINEAR_NO_COPYIN (c))
+ {
+ error_at (OMP_CLAUSE_LOCATION (c),
+ "%<inscan%> %<reduction%> clause used together with "
+ "%<linear%> clause for a variable other than loop "
+ "iterator");
+ break;
+ }
+
gimplify_omp_ctxp = ctx->outer_context;
delete_omp_context (ctx);
}
@@ -13124,6 +13219,7 @@ gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
case OMP_MASTER:
case OMP_ORDERED:
case OMP_CRITICAL:
+ case OMP_SCAN:
{
gimple_seq body = NULL;
gimple *g;
@@ -13150,6 +13246,14 @@ gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
OMP_CRITICAL_NAME (*expr_p),
OMP_CRITICAL_CLAUSES (*expr_p));
break;
+ case OMP_SCAN:
+ gimplify_scan_omp_clauses (&OMP_SCAN_CLAUSES (*expr_p),
+ pre_p, ORT_WORKSHARE, OMP_SCAN);
+ gimplify_adjust_omp_clauses (pre_p, body,
+ &OMP_SCAN_CLAUSES (*expr_p),
+ OMP_SCAN);
+ g = gimple_build_omp_scan (body, OMP_SCAN_CLAUSES (*expr_p));
+ break;
default:
gcc_unreachable ();
}
@@ -13514,6 +13618,7 @@ gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
&& code != OMP_TASKGROUP
&& code != OMP_ORDERED
&& code != OMP_PARALLEL
+ && code != OMP_SCAN
&& code != OMP_SECTIONS
&& code != OMP_SECTION
&& code != OMP_SINGLE);