@@ -92,6 +92,20 @@ along with GCC; see the file COPYING3. If not see
#include "tree-pass.h" /* FIXME: only for PROP_gimple_any */
#include "builtins.h"
+struct tree_compare_decl_uid : default_hashmap_traits {
+ static inline hashval_t hash(tree t)
+ {
+ return iterative_hash_expr(t, 0);
+ }
+
+ static inline bool equal_keys(const tree &xa, const tree &xb)
+ {
+ return DECL_UID (xa) == DECL_UID (xb);
+ }
+};
+
+typedef hash_map<tree, unsigned, tree_compare_decl_uid> gimplify_tree_t;
+
enum gimplify_omp_var_data
{
GOVD_SEEN = 1,
@@ -166,7 +180,7 @@ struct gimplify_ctx
struct gimplify_omp_ctx
{
struct gimplify_omp_ctx *outer_context;
- splay_tree variables;
+ gimplify_tree_t *variables;
hash_set<tree> *privatized_types;
location_t location;
enum omp_clause_default_kind default_kind;
@@ -364,17 +378,6 @@ gimple_pop_condition (gimple_seq *pre_p)
}
}
-/* A stable comparison routine for use with splay trees and DECLs. */
-
-static int
-splay_tree_compare_decl_uid (splay_tree_key xa, splay_tree_key xb)
-{
- tree a = (tree) xa;
- tree b = (tree) xb;
-
- return DECL_UID (a) - DECL_UID (b);
-}
-
/* Create a new omp construct that deals with variable remapping. */
static struct gimplify_omp_ctx *
@@ -384,7 +387,7 @@ new_omp_context (enum omp_region_type region_type)
c = XCNEW (struct gimplify_omp_ctx);
c->outer_context = gimplify_omp_ctxp;
- c->variables = splay_tree_new (splay_tree_compare_decl_uid, 0, 0);
+ c->variables = new gimplify_tree_t;
c->privatized_types = new hash_set<tree>;
c->location = input_location;
c->region_type = region_type;
@@ -401,7 +404,7 @@ new_omp_context (enum omp_region_type region_type)
static void
delete_omp_context (struct gimplify_omp_ctx *c)
{
- splay_tree_delete (c->variables);
+ delete c->variables;
delete c->privatized_types;
XDELETE (c);
}
@@ -1093,8 +1096,7 @@ gimplify_bind_expr (tree *expr_p, gimple_seq *pre_p)
/* Mark variable as local. */
if (ctx && !DECL_EXTERNAL (t)
&& (! DECL_SEEN_IN_BIND_EXPR_P (t)
- || splay_tree_lookup (ctx->variables,
- (splay_tree_key) t) == NULL))
+ || ctx->variables->get(t) == NULL))
{
if (ctx->region_type == ORT_SIMD
&& TREE_ADDRESSABLE (t)
@@ -5550,20 +5552,20 @@ gimplify_stmt (tree *stmt_p, gimple_seq *seq_p)
void
omp_firstprivatize_variable (struct gimplify_omp_ctx *ctx, tree decl)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
if (decl == NULL || !DECL_P (decl))
return;
do
{
- n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
+ n = ctx->variables->get(decl);
if (n != NULL)
{
- if (n->value & GOVD_SHARED)
- n->value = GOVD_FIRSTPRIVATE | (n->value & GOVD_SEEN);
- else if (n->value & GOVD_MAP)
- n->value |= GOVD_MAP_TO_ONLY;
+ if (*n & GOVD_SHARED)
+ *n = GOVD_FIRSTPRIVATE | (*n & GOVD_SEEN);
+ else if (*n & GOVD_MAP)
+ *n |= GOVD_MAP_TO_ONLY;
else
return;
}
@@ -5640,7 +5642,7 @@ omp_firstprivatize_type_sizes (struct gimplify_omp_ctx *ctx, tree type)
static void
omp_add_variable (struct gimplify_omp_ctx *ctx, tree decl, unsigned int flags)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
unsigned int nflags;
tree t;
@@ -5653,19 +5655,19 @@ omp_add_variable (struct gimplify_omp_ctx *ctx, tree decl, unsigned int flags)
|| TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl)))
flags |= GOVD_SEEN;
- n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
- if (n != NULL && n->value != GOVD_ALIGNED)
+ n = ctx->variables->get(decl);
+ if (n != NULL && *n != GOVD_ALIGNED)
{
/* We shouldn't be re-adding the decl with the same data
sharing class. */
- gcc_assert ((n->value & GOVD_DATA_SHARE_CLASS & flags) == 0);
+ gcc_assert ((*n & GOVD_DATA_SHARE_CLASS & flags) == 0);
/* The only combination of data sharing classes we should see is
FIRSTPRIVATE and LASTPRIVATE. */
- nflags = n->value | flags;
+ nflags = *n | flags;
gcc_assert ((nflags & GOVD_DATA_SHARE_CLASS)
== (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE)
|| (flags & GOVD_DATA_SHARE_CLASS) == 0);
- n->value = nflags;
+ *n = nflags;
return;
}
@@ -5734,9 +5736,9 @@ omp_add_variable (struct gimplify_omp_ctx *ctx, tree decl, unsigned int flags)
}
if (n != NULL)
- n->value |= flags;
+ *n |= flags;
else
- splay_tree_insert (ctx->variables, (splay_tree_key)decl, flags);
+ ctx->variables->put(decl, flags);
}
/* Notice a threadprivate variable DECL used in OMP context CTX.
@@ -5748,36 +5750,36 @@ static bool
omp_notice_threadprivate_variable (struct gimplify_omp_ctx *ctx, tree decl,
tree decl2)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
struct gimplify_omp_ctx *octx;
for (octx = ctx; octx; octx = octx->outer_context)
if (octx->region_type == ORT_TARGET)
{
- n = splay_tree_lookup (octx->variables, (splay_tree_key)decl);
+ n = octx->variables->get(decl);
if (n == NULL)
{
error ("threadprivate variable %qE used in target region",
DECL_NAME (decl));
error_at (octx->location, "enclosing target region");
- splay_tree_insert (octx->variables, (splay_tree_key)decl, 0);
+ octx->variables->put(decl, 0);
}
if (decl2)
- splay_tree_insert (octx->variables, (splay_tree_key)decl2, 0);
+ octx->variables->put(decl2, 0);
}
if (ctx->region_type != ORT_UNTIED_TASK)
return false;
- n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
+ n = ctx->variables->get(decl);
if (n == NULL)
{
error ("threadprivate variable %qE used in untied task",
DECL_NAME (decl));
error_at (ctx->location, "enclosing task");
- splay_tree_insert (ctx->variables, (splay_tree_key)decl, 0);
+ ctx->variables->put(decl, 0);
}
if (decl2)
- splay_tree_insert (ctx->variables, (splay_tree_key)decl2, 0);
+ ctx->variables->put(decl2, 0);
return false;
}
@@ -5790,7 +5792,7 @@ omp_notice_threadprivate_variable (struct gimplify_omp_ctx *ctx, tree decl,
static bool
omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
unsigned flags = in_code ? GOVD_SEEN : 0;
bool ret = false, shared;
@@ -5812,7 +5814,7 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
}
}
- n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
+ n = ctx->variables->get(decl);
if (ctx->region_type == ORT_TARGET)
{
ret = lang_hooks.decls.omp_disregard_value_expr (decl, true);
@@ -5830,9 +5832,9 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
else
{
/* If nothing changed, there's nothing left to do. */
- if ((n->value & flags) == flags)
+ if ((*n & flags) == flags)
return ret;
- n->value |= flags;
+ *n |= flags;
}
goto do_outer;
}
@@ -5895,12 +5897,12 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
omp_notice_variable (ctx->outer_context, decl, in_code);
for (octx = ctx->outer_context; octx; octx = octx->outer_context)
{
- splay_tree_node n2;
+ gimplify_tree_t::data_type *n2;
if ((octx->region_type & (ORT_TARGET_DATA | ORT_TARGET)) != 0)
continue;
- n2 = splay_tree_lookup (octx->variables, (splay_tree_key) decl);
- if (n2 && (n2->value & GOVD_DATA_SHARE_CLASS) != GOVD_SHARED)
+ n2 = octx->variables->get(decl);
+ if (n2 && (*n2 & GOVD_DATA_SHARE_CLASS) != GOVD_SHARED)
{
flags |= GOVD_FIRSTPRIVATE;
break;
@@ -5935,28 +5937,29 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
goto do_outer;
}
- if ((n->value & (GOVD_SEEN | GOVD_LOCAL)) == 0
+ if ((*n & (GOVD_SEEN | GOVD_LOCAL)) == 0
&& (flags & (GOVD_SEEN | GOVD_LOCAL)) == GOVD_SEEN
&& DECL_SIZE (decl)
&& TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
{
- splay_tree_node n2;
+ gimplify_tree_t::data_type *n2;
tree t = DECL_VALUE_EXPR (decl);
gcc_assert (TREE_CODE (t) == INDIRECT_REF);
t = TREE_OPERAND (t, 0);
gcc_assert (DECL_P (t));
- n2 = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
- n2->value |= GOVD_SEEN;
+ n2 = ctx->variables->get(t);
+ gcc_assert(n2);
+ *n2 |= GOVD_SEEN;
}
- shared = ((flags | n->value) & GOVD_SHARED) != 0;
+ shared = ((flags | *n) & GOVD_SHARED) != 0;
ret = lang_hooks.decls.omp_disregard_value_expr (decl, shared);
/* If nothing changed, there's nothing left to do. */
- if ((n->value & flags) == flags)
+ if ((*n & flags) == flags)
return ret;
- flags |= n->value;
- n->value = flags;
+ flags |= *n;
+ *n = flags;
do_outer:
/* If the variable is private in the current context, then we don't
@@ -5975,12 +5978,12 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
static bool
omp_is_private (struct gimplify_omp_ctx *ctx, tree decl, int simd)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
- n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
+ n = ctx->variables->get(decl);
if (n != NULL)
{
- if (n->value & GOVD_SHARED)
+ if (*n & GOVD_SHARED)
{
if (ctx == gimplify_omp_ctxp)
{
@@ -5990,30 +5993,30 @@ omp_is_private (struct gimplify_omp_ctx *ctx, tree decl, int simd)
else
error ("iteration variable %qE should be private",
DECL_NAME (decl));
- n->value = GOVD_PRIVATE;
+ *n = GOVD_PRIVATE;
return true;
}
else
return false;
}
- else if ((n->value & GOVD_EXPLICIT) != 0
+ else if ((*n & GOVD_EXPLICIT) != 0
&& (ctx == gimplify_omp_ctxp
|| (ctx->region_type == ORT_COMBINED_PARALLEL
&& gimplify_omp_ctxp->outer_context == ctx)))
{
- if ((n->value & GOVD_FIRSTPRIVATE) != 0)
+ if ((*n & GOVD_FIRSTPRIVATE) != 0)
error ("iteration variable %qE should not be firstprivate",
DECL_NAME (decl));
- else if ((n->value & GOVD_REDUCTION) != 0)
+ else if ((*n & GOVD_REDUCTION) != 0)
error ("iteration variable %qE should not be reduction",
DECL_NAME (decl));
- else if (simd == 1 && (n->value & GOVD_LASTPRIVATE) != 0)
+ else if (simd == 1 && (*n & GOVD_LASTPRIVATE) != 0)
error ("iteration variable %qE should not be lastprivate",
DECL_NAME (decl));
- else if (simd && (n->value & GOVD_PRIVATE) != 0)
+ else if (simd && (*n & GOVD_PRIVATE) != 0)
error ("iteration variable %qE should not be private",
DECL_NAME (decl));
- else if (simd == 2 && (n->value & GOVD_LINEAR) != 0)
+ else if (simd == 2 && (*n & GOVD_LINEAR) != 0)
error ("iteration variable %qE is predetermined linear",
DECL_NAME (decl));
}
@@ -6037,7 +6040,7 @@ omp_is_private (struct gimplify_omp_ctx *ctx, tree decl, int simd)
static bool
omp_check_private (struct gimplify_omp_ctx *ctx, tree decl, bool copyprivate)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
do
{
@@ -6053,9 +6056,9 @@ omp_check_private (struct gimplify_omp_ctx *ctx, tree decl, bool copyprivate)
if ((ctx->region_type & (ORT_TARGET | ORT_TARGET_DATA)) != 0)
continue;
- n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
+ n = ctx->variables->get(decl);
if (n != NULL)
- return (n->value & GOVD_SHARED) == 0;
+ return (*n & GOVD_SHARED) == 0;
}
while (ctx->region_type == ORT_WORKSHARE
|| ctx->region_type == ORT_SIMD);
@@ -6418,13 +6421,14 @@ struct gimplify_adjust_omp_clauses_data
remove PRIVATE, SHARED, and FIRSTPRIVATE clauses. */
static int
-gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
+gimplify_adjust_omp_clauses_1 (std::pair<tree, unsigned> n,
+ gimplify_adjust_omp_clauses_data *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;
+ tree decl = n.first;
+ unsigned flags = n.second;
enum omp_clause_code code;
tree clause;
bool private_debug;
@@ -6455,9 +6459,8 @@ gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp->outer_context;
while (ctx != NULL)
{
- splay_tree_node on
- = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
- if (on && (on->value & (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE
+ gimplify_tree_t::data_type *on = ctx->variables->get(decl);
+ if (on && (*on & (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE
| GOVD_PRIVATE | GOVD_REDUCTION
| GOVD_LINEAR | GOVD_MAP)) != 0)
break;
@@ -6547,7 +6550,8 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
while ((c = *list_p) != NULL)
{
- splay_tree_node n;
+ gimplify_tree_t::data_type *n;
+
bool remove = false;
switch (OMP_CLAUSE_CODE (c))
@@ -6557,16 +6561,17 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
case OMP_CLAUSE_FIRSTPRIVATE:
case OMP_CLAUSE_LINEAR:
decl = OMP_CLAUSE_DECL (c);
- n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
- remove = !(n->value & GOVD_SEEN);
+ n = ctx->variables->get(decl);
+ gcc_assert(n);
+ remove = !(*n & GOVD_SEEN);
if (! remove)
{
bool shared = OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED;
- if ((n->value & GOVD_DEBUG_PRIVATE)
+ if ((*n & GOVD_DEBUG_PRIVATE)
|| lang_hooks.decls.omp_private_debug_clause (decl, shared))
{
- gcc_assert ((n->value & GOVD_DEBUG_PRIVATE) == 0
- || ((n->value & GOVD_DATA_SHARE_CLASS)
+ gcc_assert ((*n & GOVD_DEBUG_PRIVATE) == 0
+ || ((*n & GOVD_DATA_SHARE_CLASS)
== GOVD_PRIVATE));
OMP_CLAUSE_SET_CODE (c, OMP_CLAUSE_PRIVATE);
OMP_CLAUSE_PRIVATE_DEBUG (c) = 1;
@@ -6579,21 +6584,23 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
if (ctx->outer_context->combined_loop
&& !OMP_CLAUSE_LINEAR_NO_COPYIN (c))
{
- n = splay_tree_lookup (ctx->outer_context->variables,
- (splay_tree_key) decl);
- if (n == NULL
- || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
+ gimplify_tree_t::data_type *n2;
+ gimplify_omp_ctx *octx = ctx->outer_context;
+ n2 = octx->variables->get(decl);
+ n = n2;
+ if (n2 == NULL
+ || (*n2 & GOVD_DATA_SHARE_CLASS) == 0)
{
int flags = GOVD_FIRSTPRIVATE;
/* #pragma omp distribute does not allow
lastprivate clause. */
if (!ctx->outer_context->distribute)
flags |= GOVD_LASTPRIVATE;
- if (n == NULL)
+ if (n2 == NULL)
omp_add_variable (ctx->outer_context, decl,
flags | GOVD_SEEN);
else
- n->value |= flags | GOVD_SEEN;
+ *n2 |= flags | GOVD_SEEN;
}
}
else if (!is_global_var (decl))
@@ -6606,38 +6613,37 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
/* Make sure OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE is set to
accurately reflect the presence of a FIRSTPRIVATE clause. */
decl = OMP_CLAUSE_DECL (c);
- n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
+ n = ctx->variables->get(decl);
+ gcc_assert(n);
OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c)
- = (n->value & GOVD_FIRSTPRIVATE) != 0;
+ = (*n & GOVD_FIRSTPRIVATE) != 0;
break;
case OMP_CLAUSE_ALIGNED:
decl = OMP_CLAUSE_DECL (c);
if (!is_global_var (decl))
{
- n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
- remove = n == NULL || !(n->value & GOVD_SEEN);
+ n = ctx->variables->get(decl);
+ remove = n == NULL || !(*n & GOVD_SEEN);
if (!remove && TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
{
struct gimplify_omp_ctx *octx;
if (n != NULL
- && (n->value & (GOVD_DATA_SHARE_CLASS
- & ~GOVD_FIRSTPRIVATE)))
+ && (*n & (GOVD_DATA_SHARE_CLASS & ~GOVD_FIRSTPRIVATE)))
remove = true;
else
for (octx = ctx->outer_context; octx;
octx = octx->outer_context)
{
- n = splay_tree_lookup (octx->variables,
- (splay_tree_key) decl);
+ n = octx->variables->get(decl);
if (n == NULL)
continue;
- if (n->value & GOVD_LOCAL)
+ if (*n & GOVD_LOCAL)
break;
/* We have to avoid assigning a shared variable
to itself when trying to add
__builtin_assume_aligned. */
- if (n->value & GOVD_SHARED)
+ if (*n & GOVD_SHARED)
{
remove = true;
break;
@@ -6647,8 +6653,8 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
}
else if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
{
- n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
- if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
+ n = ctx->variables->get(decl);
+ if (n != NULL && (*n & GOVD_DATA_SHARE_CLASS) != 0)
remove = true;
}
break;
@@ -6657,8 +6663,9 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *list_p)
decl = OMP_CLAUSE_DECL (c);
if (!DECL_P (decl))
break;
- n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
- if (ctx->region_type == ORT_TARGET && !(n->value & GOVD_SEEN))
+ n = ctx->variables->get(decl);
+ gcc_assert(n);
+ if (ctx->region_type == ORT_TARGET && !(*n & GOVD_SEEN))
remove = true;
else if (DECL_SIZE (decl)
&& TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST
@@ -6772,7 +6779,10 @@ gimplify_adjust_omp_clauses (gimple_seq *pre_p, tree *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);
+ for (typename gimplify_tree_t::iterator it = ctx->variables->begin(),
+ ie = ctx->variables->end(); it != ie; ++it) {
+ gimplify_adjust_omp_clauses_1(*it, &data);
+ }
gimplify_omp_ctxp = ctx->outer_context;
delete_omp_context (ctx);
@@ -6986,12 +6996,11 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
/* Do this only on innermost construct for combined ones. */;
else if (simd)
{
- splay_tree_node n = splay_tree_lookup (gimplify_omp_ctxp->variables,
- (splay_tree_key)decl);
+ gimplify_tree_t::data_type *n = gimplify_omp_ctxp->variables->get(decl);
omp_is_private (gimplify_omp_ctxp, decl,
1 + (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
!= 1));
- if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
+ if (n != NULL && (*n & GOVD_DATA_SHARE_CLASS) != 0)
omp_notice_variable (gimplify_omp_ctxp, decl, true);
else if (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1)
{
@@ -7020,10 +7029,9 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
{
struct gimplify_omp_ctx *outer
= gimplify_omp_ctxp->outer_context;
- n = splay_tree_lookup (outer->variables,
- (splay_tree_key) decl);
+ n = outer->variables->get(decl);
if (n != NULL
- && (n->value & GOVD_DATA_SHARE_CLASS) == GOVD_LOCAL)
+ && (*n & GOVD_DATA_SHARE_CLASS) == GOVD_LOCAL)
lastprivate = false;
else if (omp_check_private (outer, decl, false))
error ("lastprivate variable %qE is private in outer "
@@ -187,6 +187,10 @@ class GTY((user)) hash_map
};
public:
+
+ typedef Key key_type;
+ typedef Value data_type;
+
explicit hash_map (size_t n = 13, bool ggc = false) : m_table (n, ggc) {}
/* Create a hash_map in ggc memory. */