summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/CodeGen/AsmPrinter/DIEHash.cpp26
-rw-r--r--lib/CodeGen/AsmPrinter/DIEHash.h8
-rw-r--r--lib/CodeGen/AsmPrinter/DwarfDebug.cpp2
-rw-r--r--test/DebugInfo/X86/fission-cu.ll6
-rw-r--r--unittests/CodeGen/DIEHashTest.cpp55
5 files changed, 93 insertions, 4 deletions
diff --git a/lib/CodeGen/AsmPrinter/DIEHash.cpp b/lib/CodeGen/AsmPrinter/DIEHash.cpp
index 1275d69a26..dbeb5890b0 100644
--- a/lib/CodeGen/AsmPrinter/DIEHash.cpp
+++ b/lib/CodeGen/AsmPrinter/DIEHash.cpp
@@ -17,6 +17,7 @@
#include "DIE.h"
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/StringRef.h"
+#include "llvm/CodeGen/AsmPrinter.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/Dwarf.h"
#include "llvm/Support/Endian.h"
@@ -269,6 +270,15 @@ void DIEHash::hashDIEEntry(dwarf::Attribute Attribute, dwarf::Tag Tag,
computeHash(Entry);
}
+// Hash all of the values in a block like set of values. This assumes that
+// all of the data is going to be added as integers.
+void DIEHash::hashBlockData(const SmallVectorImpl<DIEValue *> &Values) {
+ for (SmallVectorImpl<DIEValue *>::const_iterator I = Values.begin(),
+ E = Values.end();
+ I != E; ++I)
+ Hash.update((uint64_t)cast<DIEInteger>(*I)->getValue());
+}
+
// Hash an individual attribute \param Attr based on the type of attribute and
// the form.
void DIEHash::hashAttribute(AttrEntry Attr, dwarf::Tag Tag) {
@@ -321,6 +331,22 @@ void DIEHash::hashAttribute(AttrEntry Attr, dwarf::Tag Tag) {
addULEB128(dwarf::DW_FORM_flag);
addULEB128((int64_t)cast<DIEInteger>(Value)->getValue());
break;
+ case dwarf::DW_FORM_exprloc:
+ case dwarf::DW_FORM_block1:
+ case dwarf::DW_FORM_block2:
+ case dwarf::DW_FORM_block4:
+ case dwarf::DW_FORM_block:
+ addULEB128('A');
+ addULEB128(Attribute);
+ addULEB128(dwarf::DW_FORM_block);
+ if (isa<DIEBlock>(Value)) {
+ addULEB128(cast<DIEBlock>(Value)->ComputeSize(AP));
+ hashBlockData(cast<DIEBlock>(Value)->getValues());
+ } else {
+ addULEB128(cast<DIELoc>(Value)->ComputeSize(AP));
+ hashBlockData(cast<DIELoc>(Value)->getValues());
+ }
+ break;
default:
llvm_unreachable("Add support for additional forms");
}
diff --git a/lib/CodeGen/AsmPrinter/DIEHash.h b/lib/CodeGen/AsmPrinter/DIEHash.h
index bac3c55784..40d6f44f31 100644
--- a/lib/CodeGen/AsmPrinter/DIEHash.h
+++ b/lib/CodeGen/AsmPrinter/DIEHash.h
@@ -17,6 +17,7 @@
namespace llvm {
+class AsmPrinter;
class CompileUnit;
/// \brief An object containing the capability of hashing and adding hash
@@ -84,6 +85,8 @@ class DIEHash {
};
public:
+ DIEHash(AsmPrinter *A = NULL) : AP(A) {}
+
/// \brief Computes the ODR signature.
uint64_t computeDIEODRSignature(const DIE &Die);
@@ -122,6 +125,10 @@ private:
/// \brief Hashes the attributes in \param Attrs in order.
void hashAttributes(const DIEAttrs &Attrs, dwarf::Tag Tag);
+ /// \brief Hashes the data in a block like DIEValue, e.g. DW_FORM_block or
+ /// DW_FORM_exprloc.
+ void hashBlockData(const SmallVectorImpl<DIEValue *> &Values);
+
/// \brief Hashes an individual attribute.
void hashAttribute(AttrEntry Attr, dwarf::Tag Tag);
@@ -143,6 +150,7 @@ private:
private:
MD5 Hash;
+ AsmPrinter *AP;
DenseMap<const DIE *, unsigned> Numbering;
};
}
diff --git a/lib/CodeGen/AsmPrinter/DwarfDebug.cpp b/lib/CodeGen/AsmPrinter/DwarfDebug.cpp
index 70db96e43a..9428fea7e1 100644
--- a/lib/CodeGen/AsmPrinter/DwarfDebug.cpp
+++ b/lib/CodeGen/AsmPrinter/DwarfDebug.cpp
@@ -1007,7 +1007,7 @@ void DwarfDebug::finalizeModuleInfo() {
// This should be a unique identifier when we want to build .dwp files.
uint64_t ID = 0;
if (GenerateCUHash) {
- DIEHash CUHash;
+ DIEHash CUHash(Asm);
ID = CUHash.computeCUSignature(*TheU->getUnitDie());
}
TheU->addUInt(TheU->getUnitDie(), dwarf::DW_AT_GNU_dwo_id,
diff --git a/test/DebugInfo/X86/fission-cu.ll b/test/DebugInfo/X86/fission-cu.ll
index 1482ec27cf..43d36266c8 100644
--- a/test/DebugInfo/X86/fission-cu.ll
+++ b/test/DebugInfo/X86/fission-cu.ll
@@ -1,4 +1,4 @@
-; RUN: llc -split-dwarf=Enable -O0 %s -mtriple=x86_64-unknown-linux-gnu -filetype=obj -o %t
+; RUN: llc -split-dwarf=Enable -generate-cu-hash -O0 %s -mtriple=x86_64-unknown-linux-gnu -filetype=obj -o %t
; RUN: llvm-dwarfdump -debug-dump=all %t | FileCheck %s
; RUN: llvm-readobj --relocations %t | FileCheck --check-prefix=OBJ %s
@@ -61,7 +61,7 @@
; CHECK: DW_AT_GNU_dwo_name [DW_FORM_strp] ( .debug_str[0x00000000] = "baz.dwo")
; CHECK: DW_AT_GNU_addr_base [DW_FORM_sec_offset] (0x00000000)
; CHECK: DW_AT_comp_dir [DW_FORM_strp] ( .debug_str[0x00000008] = "/usr/local/google/home/echristo/tmp")
-; CHECK: DW_AT_GNU_dwo_id [DW_FORM_data8] (0x0000000000000000)
+; CHECK: DW_AT_GNU_dwo_id [DW_FORM_data8] (0x1f1f859683d49324)
; CHECK: DW_AT_low_pc [DW_FORM_addr] (0x0000000000000000)
; Check that the rest of the compile units have information.
@@ -73,7 +73,7 @@
; CHECK-NOT: DW_AT_low_pc
; CHECK-NOT: DW_AT_stmt_list
; CHECK-NOT: DW_AT_comp_dir
-; CHECK: DW_AT_GNU_dwo_id [DW_FORM_data8] (0x0000000000000000)
+; CHECK: DW_AT_GNU_dwo_id [DW_FORM_data8] (0x1f1f859683d49324)
; CHECK: DW_TAG_variable
; CHECK: DW_AT_name [DW_FORM_GNU_str_index] ( indexed (00000002) string = "a")
; CHECK: DW_AT_type [DW_FORM_ref4] (cu + 0x{{[0-9a-f]*}} => {[[TYPE:0x[0-9a-f]*]]})
diff --git a/unittests/CodeGen/DIEHashTest.cpp b/unittests/CodeGen/DIEHashTest.cpp
index e613181996..c874cef924 100644
--- a/unittests/CodeGen/DIEHashTest.cpp
+++ b/unittests/CodeGen/DIEHashTest.cpp
@@ -594,4 +594,59 @@ TEST(DIEHashTest, MemberSdata) {
uint64_t MD5Res = DIEHash().computeTypeSignature(A);
ASSERT_EQ(0x9a216000dd3788a7ULL, MD5Res);
}
+
+// Derived from:
+// struct A {
+// const static float PI = 3.14;
+// };
+// A a;
+TEST(DIEHashTest, MemberBlock) {
+ DIE A(dwarf::DW_TAG_structure_type);
+ DIEInteger One(1);
+ DIEString AStr(&One, "A");
+ A.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &AStr);
+ A.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One);
+ A.addValue(dwarf::DW_AT_decl_file, dwarf::DW_FORM_data1, &One);
+ A.addValue(dwarf::DW_AT_decl_line, dwarf::DW_FORM_data1, &One);
+
+ DIEInteger Four(4);
+ DIEString FStr(&One, "float");
+ DIE *FloatTyDIE = new DIE(dwarf::DW_TAG_base_type);
+ FloatTyDIE->addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &Four);
+ FloatTyDIE->addValue(dwarf::DW_AT_encoding, dwarf::DW_FORM_data1, &Four);
+ FloatTyDIE->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FStr);
+
+ DIEEntry FloatTy(FloatTyDIE);
+ DIE *PITyDIE = new DIE(dwarf::DW_TAG_const_type);
+ PITyDIE->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &FloatTy);
+
+ DIEEntry PITy(PITyDIE);
+ DIE *PI = new DIE(dwarf::DW_TAG_member);
+ DIEString PIStr(&One, "PI");
+ DIEInteger Two(2);
+ PI->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &PIStr);
+ PI->addValue(dwarf::DW_AT_decl_file, dwarf::DW_FORM_data1, &One);
+ PI->addValue(dwarf::DW_AT_decl_line, dwarf::DW_FORM_data1, &Two);
+ PI->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &PITy);
+ PI->addValue(dwarf::DW_AT_external, dwarf::DW_FORM_flag_present, &One);
+ PI->addValue(dwarf::DW_AT_declaration, dwarf::DW_FORM_flag_present, &One);
+
+ DIEBlock *PIBlock = new DIEBlock();
+ DIEInteger Blk1(0xc3);
+ DIEInteger Blk2(0xf5);
+ DIEInteger Blk3(0x48);
+ DIEInteger Blk4(0x40);
+
+ PIBlock->addValue((dwarf::Attribute)0, dwarf::DW_FORM_data1, &Blk1);
+ PIBlock->addValue((dwarf::Attribute)0, dwarf::DW_FORM_data1, &Blk2);
+ PIBlock->addValue((dwarf::Attribute)0, dwarf::DW_FORM_data1, &Blk3);
+ PIBlock->addValue((dwarf::Attribute)0, dwarf::DW_FORM_data1, &Blk4);
+
+ PI->addValue(dwarf::DW_AT_const_value, dwarf::DW_FORM_block1, PIBlock);
+
+ A.addChild(PI);
+
+ uint64_t MD5Res = DIEHash().computeTypeSignature(A);
+ ASSERT_EQ(0x493af53ad3d3f651ULL, MD5Res);
+}
}