mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-05-20 20:38:48 +00:00
DIEHash: Summary hashing of nested types
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@193427 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
ed400c7108
commit
a954618c6e
@ -141,6 +141,34 @@ enum Tag LLVM_ENUM_INT_TYPE(uint16_t) {
|
|||||||
DW_TAG_hi_user = 0xffff
|
DW_TAG_hi_user = 0xffff
|
||||||
};
|
};
|
||||||
|
|
||||||
|
inline bool isType(Tag T) {
|
||||||
|
switch (T) {
|
||||||
|
case DW_TAG_array_type:
|
||||||
|
case DW_TAG_class_type:
|
||||||
|
case DW_TAG_interface_type:
|
||||||
|
case DW_TAG_enumeration_type:
|
||||||
|
case DW_TAG_pointer_type:
|
||||||
|
case DW_TAG_reference_type:
|
||||||
|
case DW_TAG_rvalue_reference_type:
|
||||||
|
case DW_TAG_string_type:
|
||||||
|
case DW_TAG_structure_type:
|
||||||
|
case DW_TAG_subroutine_type:
|
||||||
|
case DW_TAG_union_type:
|
||||||
|
case DW_TAG_ptr_to_member_type:
|
||||||
|
case DW_TAG_set_type:
|
||||||
|
case DW_TAG_subrange_type:
|
||||||
|
case DW_TAG_base_type:
|
||||||
|
case DW_TAG_const_type:
|
||||||
|
case DW_TAG_file_type:
|
||||||
|
case DW_TAG_packed_type:
|
||||||
|
case DW_TAG_volatile_type:
|
||||||
|
case DW_TAG_typedef:
|
||||||
|
return true;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
enum Attribute LLVM_ENUM_INT_TYPE(uint16_t) {
|
enum Attribute LLVM_ENUM_INT_TYPE(uint16_t) {
|
||||||
// Attributes
|
// Attributes
|
||||||
DW_AT_sibling = 0x01,
|
DW_AT_sibling = 0x01,
|
||||||
|
@ -384,6 +384,18 @@ void DIEHash::addAttributes(const DIE &Die) {
|
|||||||
hashAttributes(Attrs, Die.getTag());
|
hashAttributes(Attrs, Die.getTag());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void DIEHash::hashNestedType(const DIE &Die, StringRef Name) {
|
||||||
|
// 7.27 Step 7
|
||||||
|
// ... append the letter 'S',
|
||||||
|
addULEB128('S');
|
||||||
|
|
||||||
|
// the tag of C,
|
||||||
|
addULEB128(Die.getTag());
|
||||||
|
|
||||||
|
// and the name.
|
||||||
|
addString(Name);
|
||||||
|
}
|
||||||
|
|
||||||
// Compute the hash of a DIE. This is based on the type signature computation
|
// Compute the hash of a DIE. This is based on the type signature computation
|
||||||
// given in section 7.27 of the DWARF4 standard. It is the md5 hash of a
|
// given in section 7.27 of the DWARF4 standard. It is the md5 hash of a
|
||||||
// flattened description of the DIE.
|
// flattened description of the DIE.
|
||||||
@ -398,8 +410,19 @@ void DIEHash::computeHash(const DIE &Die) {
|
|||||||
// Then hash each of the children of the DIE.
|
// Then hash each of the children of the DIE.
|
||||||
for (std::vector<DIE *>::const_iterator I = Die.getChildren().begin(),
|
for (std::vector<DIE *>::const_iterator I = Die.getChildren().begin(),
|
||||||
E = Die.getChildren().end();
|
E = Die.getChildren().end();
|
||||||
I != E; ++I)
|
I != E; ++I) {
|
||||||
|
// 7.27 Step 7
|
||||||
|
// If C is a nested type entry or a member function entry, ...
|
||||||
|
if (isType((*I)->getTag())) {
|
||||||
|
StringRef Name = getDIEStringAttr(**I, dwarf::DW_AT_name);
|
||||||
|
// ... and has a DW_AT_name attribute
|
||||||
|
if (!Name.empty()) {
|
||||||
|
hashNestedType(**I, Name);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
computeHash(**I);
|
computeHash(**I);
|
||||||
|
}
|
||||||
|
|
||||||
// Following the last (or if there are no children), append a zero byte.
|
// Following the last (or if there are no children), append a zero byte.
|
||||||
Hash.update(makeArrayRef((uint8_t)'\0'));
|
Hash.update(makeArrayRef((uint8_t)'\0'));
|
||||||
|
@ -137,6 +137,8 @@ private:
|
|||||||
/// \brief Hashes a reference to a previously referenced type DIE.
|
/// \brief Hashes a reference to a previously referenced type DIE.
|
||||||
void hashRepeatedTypeReference(dwarf::Attribute Attribute, unsigned DieNumber);
|
void hashRepeatedTypeReference(dwarf::Attribute Attribute, unsigned DieNumber);
|
||||||
|
|
||||||
|
void hashNestedType(const DIE &Die, StringRef Name);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
MD5 Hash;
|
MD5 Hash;
|
||||||
DenseMap<const DIE *, unsigned> Numbering;
|
DenseMap<const DIE *, unsigned> Numbering;
|
||||||
|
@ -477,4 +477,23 @@ TEST(DIEHashTest, RefUnnamedType) {
|
|||||||
|
|
||||||
ASSERT_EQ(0x954e026f01c02529ULL, MD5Res);
|
ASSERT_EQ(0x954e026f01c02529ULL, MD5Res);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// struct { struct bar { }; };
|
||||||
|
TEST(DIEHashTest, NestedType) {
|
||||||
|
DIE Unnamed(dwarf::DW_TAG_structure_type);
|
||||||
|
DIEInteger One(1);
|
||||||
|
Unnamed.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One);
|
||||||
|
|
||||||
|
DIE *Foo = new DIE(dwarf::DW_TAG_structure_type);
|
||||||
|
DIEString FooStr(&One, "foo");
|
||||||
|
Foo->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr);
|
||||||
|
Foo->addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One);
|
||||||
|
|
||||||
|
Unnamed.addChild(Foo);
|
||||||
|
|
||||||
|
uint64_t MD5Res = DIEHash().computeTypeSignature(Unnamed);
|
||||||
|
|
||||||
|
// The exact same hash GCC produces for this DIE.
|
||||||
|
ASSERT_EQ(0xde8a3b7b43807f4aULL, MD5Res);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user