Skip to content

Commit

Permalink
[dsymutil] Generate Apple accelerator tables
Browse files Browse the repository at this point in the history
This patch adds support for generating accelerator tables in dsymutil.
This feature was already present in our internal repository but not yet
upstreamed because it requires changes to the Apple accelerator table
implementation.

Differential revision: https://reviews.llvm.org/D42501

llvm-svn: 323655
  • Loading branch information
JDevlieghere committed Jan 29, 2018
1 parent 855fc3b commit 5ead3a2
Show file tree
Hide file tree
Showing 8 changed files with 642 additions and 50 deletions.
62 changes: 62 additions & 0 deletions llvm/include/llvm/CodeGen/AccelTable.h
Original file line number Diff line number Diff line change
Expand Up @@ -406,6 +406,68 @@ class AppleAccelTableTypeData : public AppleAccelTableOffsetData {
#endif
};

/// Accelerator table data implementation for simple accelerator tables with
/// a DIE offset but no actual DIE pointer.
class AppleAccelTableStaticOffsetData : public AppleAccelTableData {
public:
AppleAccelTableStaticOffsetData(uint32_t Offset) : Offset(Offset) {}

void emit(AsmPrinter *Asm) const override;

static constexpr AppleAccelTableHeader::Atom Atoms[] = {
AppleAccelTableHeader::Atom(dwarf::DW_ATOM_die_offset,
dwarf::DW_FORM_data4)};

#ifndef NDEBUG
void print(raw_ostream &OS) const override {
OS << " Static Offset: " << Offset << "\n";
}

#endif
protected:
uint64_t order() const override { return Offset; }

uint32_t Offset;
};

/// Accelerator table data implementation for type accelerator tables with
/// a DIE offset but no actual DIE pointer.
class AppleAccelTableStaticTypeData : public AppleAccelTableStaticOffsetData {
public:
AppleAccelTableStaticTypeData(uint32_t Offset, uint16_t Tag,
bool ObjCClassIsImplementation,
uint32_t QualifiedNameHash)
: AppleAccelTableStaticOffsetData(Offset),
QualifiedNameHash(QualifiedNameHash), Tag(Tag),
ObjCClassIsImplementation(ObjCClassIsImplementation) {}

void emit(AsmPrinter *Asm) const override;

static constexpr AppleAccelTableHeader::Atom Atoms[] = {
AppleAccelTableHeader::Atom(dwarf::DW_ATOM_die_offset,
dwarf::DW_FORM_data4),
AppleAccelTableHeader::Atom(dwarf::DW_ATOM_die_tag, dwarf::DW_FORM_data2),
AppleAccelTableHeader::Atom(5, dwarf::DW_FORM_data1),
AppleAccelTableHeader::Atom(6, dwarf::DW_FORM_data4)};

#ifndef NDEBUG
void print(raw_ostream &OS) const override {
OS << " Static Offset: " << Offset << "\n";
OS << " QualifiedNameHash: " << format("%x\n", QualifiedNameHash) << "\n";
OS << " Tag: " << dwarf::TagString(Tag) << "\n";
OS << " ObjCClassIsImplementation: "
<< (ObjCClassIsImplementation ? "true" : "false");
OS << "\n";
}
#endif
protected:
uint64_t order() const override { return Offset; }

uint32_t QualifiedNameHash;
uint16_t Tag;
bool ObjCClassIsImplementation;
};

} // end namespace llvm

#endif // LLVM_LIB_CODEGEN_ASMPRINTER_DWARFACCELTABLE_H
14 changes: 14 additions & 0 deletions llvm/lib/CodeGen/AsmPrinter/AccelTable.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,8 @@ void AppleAccelTableHeader::setBucketAndHashCount(uint32_t HashCount) {

constexpr AppleAccelTableHeader::Atom AppleAccelTableTypeData::Atoms[];
constexpr AppleAccelTableHeader::Atom AppleAccelTableOffsetData::Atoms[];
constexpr AppleAccelTableHeader::Atom AppleAccelTableStaticOffsetData::Atoms[];
constexpr AppleAccelTableHeader::Atom AppleAccelTableStaticTypeData::Atoms[];

void AppleAccelTableBase::emitHeader(AsmPrinter *Asm) { Header.emit(Asm); }

Expand Down Expand Up @@ -219,3 +221,15 @@ void AppleAccelTableTypeData::emit(AsmPrinter *Asm) const {
Asm->EmitInt16(Die->getTag());
Asm->EmitInt8(0);
}

void AppleAccelTableStaticOffsetData::emit(AsmPrinter *Asm) const {
Asm->EmitInt32(Offset);
}

void AppleAccelTableStaticTypeData::emit(AsmPrinter *Asm) const {
Asm->EmitInt32(Offset);
Asm->EmitInt16(Tag);
Asm->EmitInt8(ObjCClassIsImplementation ? dwarf::DW_FLAG_type_implementation
: 0);
Asm->EmitInt32(QualifiedNameHash);
}
Binary file added llvm/test/tools/dsymutil/Inputs/objc.macho.x86_64
Binary file not shown.
Binary file not shown.
195 changes: 193 additions & 2 deletions llvm/test/tools/dsymutil/X86/basic-lto-linking-x86.test
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ CHECK: DW_AT_name ("arg")
CHECK: DW_AT_type (0x0000000000000063
CHECK: DW_AT_location (0x00000000
CHECK: [0x0000000000000000, 0x000000000000000e): DW_OP_reg5 RDI, DW_OP_piece 0x4)
CHECK: DW_TAG_inlined_subroutine
CHECK:[[INC1:0x[0-9a-f]*]]{{.*}}DW_TAG_inlined_subroutine
CHECK: DW_AT_abstract_origin (cu + 0x00a7 "inc")
CHECK: DW_AT_low_pc (0x0000000100000f63)
CHECK: DW_AT_high_pc (0x0000000100000f72)
Expand Down Expand Up @@ -120,7 +120,7 @@ CHECK: [0x0000000000000019, 0x000000000000001d): DW_OP_reg5 RDI, DW_OP_
CHECK: DW_TAG_lexical_block
CHECK: DW_AT_low_pc (0x0000000100000f94)
CHECK: DW_AT_high_pc (0x0000000100000fa7)
CHECK: DW_TAG_inlined_subroutine
CHECK:[[INC2:0x[0-9a-f]*]]{{.*}}DW_TAG_inlined_subroutine
CHECK: DW_AT_abstract_origin (cu + 0x009a "inc")
CHECK: DW_AT_ranges (0x00000000
CHECK: [0x0000000100000f94, 0x0000000100000f9a)
Expand Down Expand Up @@ -197,3 +197,194 @@ CHECK-NEXT: length = 0x0000001f version = 0x0002 unit_offset = 0x00000000 unit_s
CHECK-NEXT: Offset Name
CHECK-NEXT: 0x00000063 "int"
CHECK-NEXT: 0x00000079 "char"

CHECK: .apple_names contents:
CHECK-NEXT: Header {
CHECK-NEXT: Magic: 0x48415348
CHECK-NEXT: Version: 0x1
CHECK-NEXT: Hash function: 0x0
CHECK-NEXT: Bucket count: 7
CHECK-NEXT: Hashes count: 7
CHECK-NEXT: HeaderData length: 12
CHECK-NEXT: }
CHECK-NEXT: DIE offset base: 0
CHECK-NEXT: Number of atoms: 1
CHECK-NEXT: Atoms [
CHECK-NEXT: Atom 0 {
CHECK-NEXT: Type: DW_ATOM_die_offset
CHECK-NEXT: Form: DW_FORM_data4
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Bucket 0 [
CHECK-NEXT: Hash 0xb8860c2 [
CHECK-NEXT: Name@0x74 {
CHECK-NEXT: String: 0x0000007e "baz"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x000000c0
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Hash 0xb88801f [
CHECK-NEXT: Name@0x84 {
CHECK-NEXT: String: 0x0000008a "inc"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x00000110
CHECK-NEXT: ]
CHECK-NEXT: Data 1 [
CHECK-NEXT: Atom[0]: 0x000001c7
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
CHECK-NEXT: Bucket 1 [
CHECK-NEXT: EMPTY
CHECK-NEXT: ]
CHECK-NEXT: Bucket 2 [
CHECK-NEXT: Hash 0xfed12c6a [
CHECK-NEXT: Name@0x98 {
CHECK-NEXT: String: 0x00000072 "private_int"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x000000a7
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
CHECK-NEXT: Bucket 3 [
CHECK-NEXT: Hash 0xb88b5c8 [
CHECK-NEXT: Name@0xa8 {
CHECK-NEXT: String: 0x00000097 "val"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x00000160
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Hash 0x7c9a7f6a [
CHECK-NEXT: Name@0xb8 {
CHECK-NEXT: String: 0x00000051 "main"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x00000026
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
CHECK-NEXT: Bucket 4 [
CHECK-NEXT: EMPTY
CHECK-NEXT: ]
CHECK-NEXT: Bucket 5 [
CHECK-NEXT: Hash 0xb887389 [
CHECK-NEXT: Name@0xc8 {
CHECK-NEXT: String: 0x00000082 "foo"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x000000d9
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
CHECK-NEXT: Bucket 6 [
CHECK-NEXT: Hash 0xb8860ba [
CHECK-NEXT: Name@0xd8 {
CHECK-NEXT: String: 0x0000009b "bar"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x0000017f
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]

CHECK: apple_types contents:
CHECK-NEXT: Header {
CHECK-NEXT: Magic: 0x48415348
CHECK-NEXT: Version: 0x1
CHECK-NEXT: Hash function: 0x0
CHECK-NEXT: Bucket count: 2
CHECK-NEXT: Hashes count: 2
CHECK-NEXT: HeaderData length: 24
CHECK-NEXT: }
CHECK-NEXT: DIE offset base: 0
CHECK-NEXT: Number of atoms: 4
CHECK-NEXT: Atoms [
CHECK-NEXT: Atom 0 {
CHECK-NEXT: Type: DW_ATOM_die_offset
CHECK-NEXT: Form: DW_FORM_data4
CHECK-NEXT: }
CHECK-NEXT: Atom 1 {
CHECK-NEXT: Type: DW_ATOM_die_tag
CHECK-NEXT: Form: DW_FORM_data2
CHECK-NEXT: }
CHECK-NEXT: Atom 2 {
CHECK-NEXT: Type: DW_ATOM_type_flags
CHECK-NEXT: Form: DW_FORM_data1
CHECK-NEXT: }
CHECK-NEXT: Atom 3 {
CHECK-NEXT: Type: DW_ATOM_qual_name_hash
CHECK-NEXT: Form: DW_FORM_data4
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Bucket 0 [
CHECK-NEXT: Hash 0xb888030 [
CHECK-NEXT: Name@0x44 {
CHECK-NEXT: String: 0x00000060 "int"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x00000063
CHECK-NEXT: Atom[1]: 0x0024
CHECK-NEXT: Atom[2]: 0x00
CHECK-NEXT: Atom[3]: 0x0c3a28a4
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
CHECK-NEXT: Bucket 1 [
CHECK-NEXT: Hash 0x7c952063 [
CHECK-NEXT: Name@0x5b {
CHECK-NEXT: String: 0x00000064 "char"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x00000079
CHECK-NEXT: Atom[1]: 0x0024
CHECK-NEXT: Atom[2]: 0x00
CHECK-NEXT: Atom[3]: 0x937bd757
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]

CHECK: .apple_namespaces contents:
CHECK-NEXT: Header {
CHECK-NEXT: Magic: 0x48415348
CHECK-NEXT: Version: 0x1
CHECK-NEXT: Hash function: 0x0
CHECK-NEXT: Bucket count: 1
CHECK-NEXT: Hashes count: 0
CHECK-NEXT: HeaderData length: 12
CHECK-NEXT: }
CHECK-NEXT: DIE offset base: 0
CHECK-NEXT: Number of atoms: 1
CHECK-NEXT: Atoms [
CHECK-NEXT: Atom 0 {
CHECK-NEXT: Type: DW_ATOM_die_offset
CHECK-NEXT: Form: DW_FORM_data4
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Bucket 0 [
CHECK-NEXT: EMPTY
CHECK-NEXT: ]

CHECK: .apple_objc contents:
CHECK-NEXT: Header {
CHECK-NEXT: Magic: 0x48415348
CHECK-NEXT: Version: 0x1
CHECK-NEXT: Hash function: 0x0
CHECK-NEXT: Bucket count: 1
CHECK-NEXT: Hashes count: 0
CHECK-NEXT: HeaderData length: 12
CHECK-NEXT: }
CHECK-NEXT: DIE offset base: 0
CHECK-NEXT: Number of atoms: 1
CHECK-NEXT: Atoms [
CHECK-NEXT: Atom 0 {
CHECK-NEXT: Type: DW_ATOM_die_offset
CHECK-NEXT: Form: DW_FORM_data4
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Bucket 0 [
CHECK-NEXT: EMPTY
CHECK-NEXT: ]
52 changes: 52 additions & 0 deletions llvm/test/tools/dsymutil/X86/objc.test
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
RUN: llvm-dsymutil -f -oso-prepend-path=%p/.. %p/../Inputs/objc.macho.x86_64 -o - \
RUN: | llvm-dwarfdump -apple-types -apple-objc - | FileCheck %s

CHECK: .apple_types contents:
CHECK: String: 0x00000066 "A"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x0000012d
CHECK-NEXT: Atom[1]: 0x0013
CHECK-NEXT: Atom[2]: 0x02
CHECK-NEXT: Atom[3]: 0x0b87b15a
CHECK-NEXT: ]

CHECK: .apple_objc contents:
CHECK-NEXT: Header {
CHECK-NEXT: Magic: 0x48415348
CHECK-NEXT: Version: 0x1
CHECK-NEXT: Hash function: 0x0
CHECK-NEXT: Bucket count: 2
CHECK-NEXT: Hashes count: 2
CHECK-NEXT: HeaderData length: 12
CHECK-NEXT: }
CHECK-NEXT: DIE offset base: 0
CHECK-NEXT: Number of atoms: 1
CHECK-NEXT: Atoms [
CHECK-NEXT: Atom 0 {
CHECK-NEXT: Type: DW_ATOM_die_offset
CHECK-NEXT: Form: DW_FORM_data4
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: Bucket 0 [
CHECK-NEXT: Hash 0x2b5e6 [
CHECK-NEXT: Name@0x38 {
CHECK-NEXT: String: 0x00000066 "A"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x00000027
CHECK-NEXT: ]
CHECK-NEXT: Data 1 [
CHECK-NEXT: Atom[0]: 0x0000007a
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
CHECK-NEXT: Bucket 1 [
CHECK-NEXT: Hash 0x3fa0f4b5 [
CHECK-NEXT: Name@0x4c {
CHECK-NEXT: String: 0x0000009d "A(Category)"
CHECK-NEXT: Data 0 [
CHECK-NEXT: Atom[0]: 0x0000007a
CHECK-NEXT: ]
CHECK-NEXT: }
CHECK-NEXT: ]
CHECK-NEXT: ]
Loading

0 comments on commit 5ead3a2

Please sign in to comment.