Commit 84baa4b9 by Trevor Saunders Committed by Trevor Saunders

allow storing values directly in hash tables

gcc/

	* hash-table.h: Add a template arg to choose between storing values
	and storing pointers to values, and then provide partial
	specializations for both.
	* tree-browser.c (tree_upper_hasher): Provide the type the hash table
	should store, not the type values should point to.
	* tree-into-ssa.c (var_info_hasher): Likewise.
	* tree-ssa-dom.c (expr_elt_hasher): Likewise.
	* tree-complex.c: Adjust.
	* tree-hasher.h (int_tree_hasher): store int_tree_map in the hash
	table instead of int_tree_map *.
	* tree-parloops.c: Adjust.
	* tree-ssa-reassoc.c (ocount_hasher): Don't lie to hash_map about what
	type is being stored.
	* tree-vectorizer.c: Adjust.

From-SVN: r211937
parent c203e8a7
2014-06-24 Trevor Saunders <tsaunders@mozilla.com>
* hash-table.h: Add a template arg to choose between storing values
and storing pointers to values, and then provide partial
specializations for both.
* tree-browser.c (tree_upper_hasher): Provide the type the hash table
should store, not the type values should point to.
* tree-into-ssa.c (var_info_hasher): Likewise.
* tree-ssa-dom.c (expr_elt_hasher): Likewise.
* tree-complex.c: Adjust.
* tree-hasher.h (int_tree_hasher): store int_tree_map in the hash
table instead of int_tree_map *.
* tree-parloops.c: Adjust.
* tree-ssa-reassoc.c (ocount_hasher): Don't lie to hash_map about what
type is being stored.
* tree-vectorizer.c: Adjust.
2014-06-24 Trevor Saunders <tsaunders@mozilla.com>
* hash-table.h: Remove a layer of indirection from hash_table so that
it contains the hash table's data instead of a pointer to the data.
* alloc-pool.c, asan.c, attribs.c, bitmap.c, cfg.c,
......
......@@ -102,22 +102,13 @@ static tree TB_history_prev (void);
void browse_tree (tree);
/* Hashtable helpers. */
struct tree_upper_hasher : typed_noop_remove <tree_node>
struct tree_upper_hasher : pointer_hash<tree_node>
{
typedef tree_node value_type;
typedef tree_node compare_type;
static inline hashval_t hash (const value_type *);
static inline bool equal (const value_type *, const compare_type *);
static inline bool equal (const value_type &, const compare_type &);
};
inline hashval_t
tree_upper_hasher::hash (const value_type *v)
{
return pointer_hash <value_type>::hash (v);
}
inline bool
tree_upper_hasher::equal (const value_type *parent, const compare_type *node)
tree_upper_hasher::equal (const value_type &parent, const compare_type &node)
{
if (parent == NULL || node == NULL)
return 0;
......
......@@ -83,10 +83,9 @@ static vec<tree> complex_ssa_name_components;
static tree
cvc_lookup (unsigned int uid)
{
struct int_tree_map *h, in;
struct int_tree_map in;
in.uid = uid;
h = complex_variable_components->find_with_hash (&in, uid);
return h ? h->to : NULL;
return complex_variable_components->find_with_hash (in, uid).to;
}
/* Insert the pair UID, TO into the complex_variable_components hashtable. */
......@@ -94,14 +93,13 @@ cvc_lookup (unsigned int uid)
static void
cvc_insert (unsigned int uid, tree to)
{
struct int_tree_map *h;
int_tree_map **loc;
int_tree_map h;
int_tree_map *loc;
h = XNEW (struct int_tree_map);
h->uid = uid;
h->to = to;
h.uid = uid;
loc = complex_variable_components->find_slot_with_hash (h, uid, INSERT);
*loc = h;
loc->uid = uid;
loc->to = to;
}
/* Return true if T is not a zero constant. In the case of real values,
......
......@@ -30,28 +30,37 @@ struct int_tree_map {
/* Hashtable helpers. */
struct int_tree_hasher : typed_free_remove <int_tree_map>
struct int_tree_hasher
{
typedef int_tree_map value_type;
typedef int_tree_map compare_type;
static inline hashval_t hash (const value_type *);
static inline bool equal (const value_type *, const compare_type *);
typedef int store_values_directly;
static inline hashval_t hash (const value_type &);
static inline bool equal (const value_type &, const compare_type &);
static bool is_deleted (const value_type &v)
{
return v.to == reinterpret_cast<tree> (1);
}
static void mark_deleted (value_type &v) { v.to = reinterpret_cast<tree> (0x1); }
static bool is_empty (const value_type &v) { return v.to == NULL; }
static void mark_empty (value_type &v) { v.to = NULL; }
static void remove (value_type &) {}
};
/* Hash a UID in a int_tree_map. */
inline hashval_t
int_tree_hasher::hash (const value_type *item)
int_tree_hasher::hash (const value_type &item)
{
return item->uid;
return item.uid;
}
/* Return true if the uid in both int tree maps are equal. */
inline bool
int_tree_hasher::equal (const value_type *a, const compare_type *b)
int_tree_hasher::equal (const value_type &a, const compare_type &b)
{
return (a->uid == b->uid);
return (a.uid == b.uid);
}
typedef hash_table <int_tree_hasher> int_tree_htab_type;
......
......@@ -203,20 +203,21 @@ typedef struct var_info_d *var_info_p;
struct var_info_hasher : typed_free_remove <var_info_d>
{
typedef var_info_d value_type;
typedef var_info_d compare_type;
static inline hashval_t hash (const value_type *);
static inline bool equal (const value_type *, const compare_type *);
typedef var_info_d *value_type;
typedef var_info_d *compare_type;
typedef int store_values_directly;
static inline hashval_t hash (const value_type &);
static inline bool equal (const value_type &, const compare_type &);
};
inline hashval_t
var_info_hasher::hash (const value_type *p)
var_info_hasher::hash (const value_type &p)
{
return DECL_UID (p->var);
}
inline bool
var_info_hasher::equal (const value_type *p1, const compare_type *p2)
var_info_hasher::equal (const value_type &p1, const compare_type &p2)
{
return p1->var == p2->var;
}
......
......@@ -489,8 +489,6 @@ take_address_of (tree obj, tree type, edge entry,
int_tree_htab_type *decl_address, gimple_stmt_iterator *gsi)
{
int uid;
int_tree_map **dslot;
struct int_tree_map ielt, *nielt;
tree *var_p, name, addr;
gimple stmt;
gimple_seq stmts;
......@@ -511,9 +509,10 @@ take_address_of (tree obj, tree type, edge entry,
in the address and share it for all accesses and addresses based
on it. */
uid = DECL_UID (TREE_OPERAND (TREE_OPERAND (*var_p, 0), 0));
ielt.uid = uid;
dslot = decl_address->find_slot_with_hash (&ielt, uid, INSERT);
if (!*dslot)
int_tree_map elt;
elt.uid = uid;
int_tree_map *slot = decl_address->find_slot (elt, INSERT);
if (!slot->to)
{
if (gsi == NULL)
return NULL;
......@@ -527,13 +526,11 @@ take_address_of (tree obj, tree type, edge entry,
stmt = gimple_build_assign (name, addr);
gsi_insert_on_edge_immediate (entry, stmt);
nielt = XNEW (struct int_tree_map);
nielt->uid = uid;
nielt->to = name;
*dslot = nielt;
slot->uid = uid;
slot->to = name;
}
else
name = (*dslot)->to;
name = slot->to;
/* Express the address in terms of the canonical SSA name. */
TREE_OPERAND (*var_p, 0) = name;
......@@ -822,10 +819,10 @@ separate_decls_in_region_name (tree name, name_to_copy_table_type *name_copies,
{
tree copy, var, var_copy;
unsigned idx, uid, nuid;
struct int_tree_map ielt, *nielt;
struct int_tree_map ielt;
struct name_to_copy_elt elt, *nelt;
name_to_copy_elt **slot;
int_tree_map **dslot;
int_tree_map *dslot;
if (TREE_CODE (name) != SSA_NAME)
return name;
......@@ -858,29 +855,25 @@ separate_decls_in_region_name (tree name, name_to_copy_table_type *name_copies,
uid = DECL_UID (var);
ielt.uid = uid;
dslot = decl_copies->find_slot_with_hash (&ielt, uid, INSERT);
if (!*dslot)
dslot = decl_copies->find_slot_with_hash (ielt, uid, INSERT);
if (!dslot->to)
{
var_copy = create_tmp_var (TREE_TYPE (var), get_name (var));
DECL_GIMPLE_REG_P (var_copy) = DECL_GIMPLE_REG_P (var);
nielt = XNEW (struct int_tree_map);
nielt->uid = uid;
nielt->to = var_copy;
*dslot = nielt;
dslot->uid = uid;
dslot->to = var_copy;
/* Ensure that when we meet this decl next time, we won't duplicate
it again. */
nuid = DECL_UID (var_copy);
ielt.uid = nuid;
dslot = decl_copies->find_slot_with_hash (&ielt, nuid, INSERT);
gcc_assert (!*dslot);
nielt = XNEW (struct int_tree_map);
nielt->uid = nuid;
nielt->to = var_copy;
*dslot = nielt;
dslot = decl_copies->find_slot_with_hash (ielt, nuid, INSERT);
gcc_assert (!dslot->to);
dslot->uid = nuid;
dslot->to = var_copy;
}
else
var_copy = ((struct int_tree_map *) *dslot)->to;
var_copy = dslot->to;
replace_ssa_name_symbol (copy, var_copy);
return copy;
......@@ -944,7 +937,7 @@ separate_decls_in_region_debug (gimple stmt,
struct int_tree_map ielt;
struct name_to_copy_elt elt;
name_to_copy_elt **slot;
int_tree_map **dslot;
int_tree_map *dslot;
if (gimple_debug_bind_p (stmt))
var = gimple_debug_bind_get_var (stmt);
......@@ -956,13 +949,13 @@ separate_decls_in_region_debug (gimple stmt,
return true;
gcc_assert (DECL_P (var) && SSA_VAR_P (var));
ielt.uid = DECL_UID (var);
dslot = decl_copies->find_slot_with_hash (&ielt, ielt.uid, NO_INSERT);
dslot = decl_copies->find_slot_with_hash (ielt, ielt.uid, NO_INSERT);
if (!dslot)
return true;
if (gimple_debug_bind_p (stmt))
gimple_debug_bind_set_var (stmt, ((struct int_tree_map *) *dslot)->to);
gimple_debug_bind_set_var (stmt, dslot->to);
else if (gimple_debug_source_bind_p (stmt))
gimple_debug_source_bind_set_var (stmt, ((struct int_tree_map *) *dslot)->to);
gimple_debug_source_bind_set_var (stmt, dslot->to);
FOR_EACH_PHI_OR_STMT_USE (use, stmt, oi, SSA_OP_USE)
{
......
......@@ -158,21 +158,22 @@ static void free_expr_hash_elt (void *);
struct expr_elt_hasher
{
typedef expr_hash_elt value_type;
typedef expr_hash_elt compare_type;
static inline hashval_t hash (const value_type *);
static inline bool equal (const value_type *, const compare_type *);
static inline void remove (value_type *);
typedef expr_hash_elt *value_type;
typedef expr_hash_elt *compare_type;
typedef int store_values_directly;
static inline hashval_t hash (const value_type &);
static inline bool equal (const value_type &, const compare_type &);
static inline void remove (value_type &);
};
inline hashval_t
expr_elt_hasher::hash (const value_type *p)
expr_elt_hasher::hash (const value_type &p)
{
return p->hash;
}
inline bool
expr_elt_hasher::equal (const value_type *p1, const compare_type *p2)
expr_elt_hasher::equal (const value_type &p1, const compare_type &p2)
{
gimple stmt1 = p1->stmt;
const struct hashable_expr *expr1 = &p1->expr;
......@@ -211,7 +212,7 @@ expr_elt_hasher::equal (const value_type *p1, const compare_type *p2)
/* Delete an expr_hash_elt and reclaim its storage. */
inline void
expr_elt_hasher::remove (value_type *element)
expr_elt_hasher::remove (value_type &element)
{
free_expr_hash_elt (element);
}
......
......@@ -1023,32 +1023,36 @@ static vec<oecount> cvec;
/* Oecount hashtable helpers. */
struct oecount_hasher : typed_noop_remove <void>
struct oecount_hasher
{
/* Note that this hash table stores integers, not pointers.
So, observe the casting in the member functions. */
typedef void value_type;
typedef void compare_type;
static inline hashval_t hash (const value_type *);
static inline bool equal (const value_type *, const compare_type *);
typedef int value_type;
typedef int compare_type;
typedef int store_values_directly;
static inline hashval_t hash (const value_type &);
static inline bool equal (const value_type &, const compare_type &);
static bool is_deleted (int &v) { return v == 1; }
static void mark_deleted (int &e) { e = 1; }
static bool is_empty (int &v) { return v == 0; }
static void mark_empty (int &e) { e = 0; }
static void remove (int &) {}
};
/* Hash function for oecount. */
inline hashval_t
oecount_hasher::hash (const value_type *p)
oecount_hasher::hash (const value_type &p)
{
const oecount *c = &cvec[(size_t)p - 42];
const oecount *c = &cvec[p - 42];
return htab_hash_pointer (c->op) ^ (hashval_t)c->oecode;
}
/* Comparison function for oecount. */
inline bool
oecount_hasher::equal (const value_type *p1, const compare_type *p2)
oecount_hasher::equal (const value_type &p1, const compare_type &p2)
{
const oecount *c1 = &cvec[(size_t)p1 - 42];
const oecount *c2 = &cvec[(size_t)p2 - 42];
const oecount *c1 = &cvec[p1 - 42];
const oecount *c2 = &cvec[p2 - 42];
return (c1->oecode == c2->oecode
&& c1->op == c2->op);
}
......@@ -1473,23 +1477,23 @@ undistribute_ops_list (enum tree_code opcode,
FOR_EACH_VEC_ELT (subops[i], j, oe1)
{
oecount c;
void **slot;
size_t idx;
int *slot;
int idx;
c.oecode = oecode;
c.cnt = 1;
c.id = next_oecount_id++;
c.op = oe1->op;
cvec.safe_push (c);
idx = cvec.length () + 41;
slot = ctable.find_slot ((void *)idx, INSERT);
slot = ctable.find_slot (idx, INSERT);
if (!*slot)
{
*slot = (void *)idx;
*slot = idx;
}
else
{
cvec.pop ();
cvec[(size_t)*slot - 42].cnt++;
cvec[*slot - 42].cnt++;
}
}
}
......
......@@ -550,14 +550,14 @@ vectorize_loops (void)
for (hash_table<simd_array_to_simduid>::iterator iter
= simd_array_to_simduid_htab->begin ();
iter != simd_array_to_simduid_htab->end (); ++iter)
if ((*iter).simduid != -1U)
if ((*iter)->simduid != -1U)
{
tree decl = (*iter).decl;
tree decl = (*iter)->decl;
int vf = 1;
if (simduid_to_vf_htab)
{
simduid_to_vf *p = NULL, data;
data.simduid = (*iter).simduid;
data.simduid = (*iter)->simduid;
p = simduid_to_vf_htab->find (&data);
if (p)
vf = p->vf;
......
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