Fix mis-hashing of base specifiers and function_decl during comparison

* include/abg-ir.h (function_decl::get_hash): Declare new virtual
	overload.
	* src/abg-hash.cc (class_decl::base_spec:#️⃣:operator()):
	Properly hash the base specifier so that it doesn't collide with
	hashing a class.
	* src/abg-ir.cc (decl_base::get_hash): Abort if we detect a
	missing overload for this;
	(function_decl::get_hash() const): Implement this missing
	overload, allowing using the virtual decl_base::get_hash for
	function_decl.

Signed-off-by: Dodji Seketeli <dodji@redhat.com>
This commit is contained in:
Dodji Seketeli 2014-04-08 15:56:18 +02:00
parent dce487d39c
commit 793be5e374
3 changed files with 26 additions and 1 deletions

View File

@ -1435,6 +1435,9 @@ public:
&& get_parameters().back()->get_variadic_marker());
}
virtual size_t
get_hash() const;
virtual bool
traverse(ir_node_visitor&);

View File

@ -430,8 +430,14 @@ class_decl::base_spec::hash::operator()(const base_spec& t) const
{
member_base::hash hash_member;
type_base::shared_ptr_hash hash_type_ptr;
std::hash<size_t> hash_size;
std::hash<bool> hash_bool;
std::hash<string> hash_string;
size_t v = hash_member(t);
size_t v = hash_string(typeid(t).name());
v = hashing::combine_hashes(v, hash_member(t));
v = hashing::combine_hashes(v, hash_size(t.get_offset_in_bits()));
v = hashing::combine_hashes(v, hash_bool(t.get_is_virtual()));
v = hashing::combine_hashes(v, hash_type_ptr(t.get_base_class()));
return v;
}

View File

@ -348,6 +348,10 @@ decl_base::get_hash() const
if (!hashing_started_)
set_hash(result);
}
else
// If we reach this point, it mean we are missing a virtual
// overload for decl_base::get_hash. Add it!
abort();
}
return result;
}
@ -3439,6 +3443,18 @@ function_decl::operator==(const decl_base& other) const
{return false;}
}
/// The virtual implementation of 'get_hash' for a function_decl.
///
/// This allows decl_base::get_hash to work for function_decls.
///
/// @return the hash value for function decl.
size_t
function_decl::get_hash() const
{
function_decl::hash hash_fn;
return hash_fn(*this);
}
/// This implements the ir_traversable_base::traverse pure virtual
/// function.
///