compiler: Correctly handle identical unnamed structs with methods.
From-SVN: r202723
This commit is contained in:
parent
e3816ac91f
commit
f4b525e714
|
@ -4229,6 +4229,11 @@ Struct_field::is_embedded_builtin(Gogo* gogo) const
|
|||
|
||||
Struct_type::Identical_structs Struct_type::identical_structs;
|
||||
|
||||
// A hash table used to merge method sets for identical unnamed
|
||||
// structs.
|
||||
|
||||
Struct_type::Struct_method_tables Struct_type::struct_method_tables;
|
||||
|
||||
// Traversal.
|
||||
|
||||
int
|
||||
|
@ -4693,9 +4698,24 @@ Struct_type::interface_method_table(Gogo* gogo,
|
|||
const Interface_type* interface,
|
||||
bool is_pointer)
|
||||
{
|
||||
std::pair<Struct_type*, Struct_type::Struct_method_table_pair*>
|
||||
val(this, NULL);
|
||||
std::pair<Struct_type::Struct_method_tables::iterator, bool> ins =
|
||||
Struct_type::struct_method_tables.insert(val);
|
||||
|
||||
Struct_method_table_pair* smtp;
|
||||
if (!ins.second)
|
||||
smtp = ins.first->second;
|
||||
else
|
||||
{
|
||||
smtp = new Struct_method_table_pair();
|
||||
smtp->first = NULL;
|
||||
smtp->second = NULL;
|
||||
ins.first->second = smtp;
|
||||
}
|
||||
|
||||
return Type::interface_method_table(gogo, this, interface, is_pointer,
|
||||
&this->interface_method_tables_,
|
||||
&this->pointer_interface_method_tables_);
|
||||
&smtp->first, &smtp->second);
|
||||
}
|
||||
|
||||
// Convert struct fields to the backend representation. This is not
|
||||
|
|
|
@ -2041,8 +2041,7 @@ class Struct_type : public Type
|
|||
public:
|
||||
Struct_type(Struct_field_list* fields, Location location)
|
||||
: Type(TYPE_STRUCT),
|
||||
fields_(fields), location_(location), all_methods_(NULL),
|
||||
interface_method_tables_(NULL), pointer_interface_method_tables_(NULL)
|
||||
fields_(fields), location_(location), all_methods_(NULL)
|
||||
{ }
|
||||
|
||||
// Return the field NAME. This only looks at local fields, not at
|
||||
|
@ -2200,6 +2199,16 @@ class Struct_type : public Type
|
|||
|
||||
static Identical_structs identical_structs;
|
||||
|
||||
// Used to manage method tables for identical unnamed structs.
|
||||
typedef std::pair<Interface_method_tables*, Interface_method_tables*>
|
||||
Struct_method_table_pair;
|
||||
|
||||
typedef Unordered_map_hash(Struct_type*, Struct_method_table_pair*,
|
||||
Type_hash_identical, Type_identical)
|
||||
Struct_method_tables;
|
||||
|
||||
static Struct_method_tables struct_method_tables;
|
||||
|
||||
// Used to avoid infinite loops in field_reference_depth.
|
||||
struct Saw_named_type
|
||||
{
|
||||
|
@ -2218,13 +2227,6 @@ class Struct_type : public Type
|
|||
Location location_;
|
||||
// If this struct is unnamed, a list of methods.
|
||||
Methods* all_methods_;
|
||||
// A mapping from interfaces to the associated interface method
|
||||
// tables for this type. Only used if this struct is unnamed.
|
||||
Interface_method_tables* interface_method_tables_;
|
||||
// A mapping from interfaces to the associated interface method
|
||||
// tables for pointers to this type. Only used if this struct is
|
||||
// unnamed.
|
||||
Interface_method_tables* pointer_interface_method_tables_;
|
||||
};
|
||||
|
||||
// The type of an array.
|
||||
|
|
Loading…
Reference in New Issue