Skip to content

Commit 4b3e81a

Browse files
committed
Implement LLDBParser::enumerateClassParents
1 parent bbee1c8 commit 4b3e81a

File tree

3 files changed

+65
-19
lines changed

3 files changed

+65
-19
lines changed

oi/type_graph/LLDBParser.cpp

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,44 @@
1919
#include <lldb/API/LLDB.h>
2020
#include <cassert>
2121

22+
namespace std {
23+
/* We use the address of the name string for hashing and equality.
24+
* This relies on string de-duplication, two objects with the same name
25+
* might have different addresses, but their de-duplicated name will
26+
* have the same address.
27+
*
28+
* TODO: Is this correct? How does -fsimple-template-names impact this?
29+
* Is there a better way to do this?
30+
*/
31+
size_t hash<lldb::SBType>::operator()(const lldb::SBType& key) const {
32+
auto *name = const_cast<lldb::SBType&>(key).GetName();
33+
auto Hasher = std::hash<const char*>();
34+
{ /* Debugging
35+
auto &keyAsSP = reinterpret_cast<const lldb::TypeImplSP&>(key);
36+
fprintf(stderr, "LLDBType::hash(key@0x%08zx = (0x%08zx, %s)) = 0x%08zx\n",
37+
(uintptr_t)keyAsSP.get(), (uintptr_t)name, name, Hasher(name));
38+
// Debugging */
39+
}
40+
return Hasher(name);
41+
}
42+
43+
bool equal_to<lldb::SBType>::operator()(const lldb::SBType& lhs, const lldb::SBType& rhs) const {
44+
auto* lhsName = const_cast<lldb::SBType&>(lhs).GetName();
45+
auto* rhsName = const_cast<lldb::SBType&>(rhs).GetName();
46+
auto EqualTo = std::equal_to<const char*>();
47+
{ /* Debugging
48+
auto &lhsAsSP = reinterpret_cast<const lldb::TypeImplSP&>(lhs);
49+
auto &rhsAsSP = reinterpret_cast<const lldb::TypeImplSP&>(rhs);
50+
fprintf(stderr, "LLDBType::equal_to(lhs@0x%08zx = (0x%08zx, %s), rhs@0x%08zx = (0x%08zx, %s)) = %d\n",
51+
(uintptr_t)lhsAsSP.get(), (uintptr_t)lhsName, lhsName,
52+
(uintptr_t)rhsAsSP.get(), (uintptr_t)rhsName, rhsName,
53+
EqualTo(lhsName, rhsName));
54+
// Debugging */
55+
}
56+
return EqualTo(lhsName, rhsName);
57+
}
58+
} // namespace std
59+
2260
namespace oi::detail::type_graph {
2361

2462
Type& LLDBParser::parse(lldb::SBType& root) {
@@ -119,12 +157,25 @@ Class& LLDBParser::enumerateClass(lldb::SBType& type) {
119157

120158
auto &c = makeType<Class>(type, kind, displayName, name, size, virtuality);
121159

160+
enumerateClassParents(type, c.parents);
122161
enumerateClassMembers(type, c.members);
123162
enumerateClassFunctions(type, c.functions);
124163

125164
return c;
126165
}
127166

167+
void LLDBParser::enumerateClassParents(lldb::SBType& type, std::vector<Parent>& parents) {
168+
assert(parents.empty());
169+
parents.reserve(type.GetNumberOfDirectBaseClasses());
170+
171+
for (uint32_t i = 0; i < type.GetNumberOfDirectBaseClasses(); i++) {
172+
auto base = type.GetDirectBaseClassAtIndex(i);
173+
auto baseType = base.GetType();
174+
175+
parents.emplace_back(enumerateType(baseType), base.GetOffsetInBits());
176+
}
177+
}
178+
128179
void LLDBParser::enumerateClassMembers(lldb::SBType& type, std::vector<Member>& members) {
129180
assert(members.empty());
130181
members.reserve(type.GetNumberOfFields());

oi/type_graph/LLDBParser.h

Lines changed: 6 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -21,23 +21,17 @@
2121
#include <lldb/API/SBType.h>
2222

2323
namespace std {
24+
/* lldb::SBType doesn't provide a hash and equality operators.
25+
* So we define our own specialization of them here.
26+
*/
2427
template <>
2528
struct hash<lldb::SBType> {
26-
size_t operator()(const lldb::SBType& key) const {
27-
auto &keyAsSP = reinterpret_cast<const lldb::TypeImplSP&>(key);
28-
auto SPHasher = std::hash<lldb::TypeImplSP>();
29-
return SPHasher(keyAsSP);
30-
}
29+
size_t operator()(const lldb::SBType& type) const;
3130
};
3231

3332
template <>
3433
struct equal_to<lldb::SBType> {
35-
bool operator()(const lldb::SBType& lhs, const lldb::SBType& rhs) const {
36-
auto &lhsAsSP = reinterpret_cast<const lldb::TypeImplSP&>(lhs);
37-
auto &rhsAsSP = reinterpret_cast<const lldb::TypeImplSP&>(rhs);
38-
auto SPEqualTo = std::equal_to<lldb::TypeImplSP>();
39-
return SPEqualTo(lhsAsSP, rhsAsSP);
40-
}
34+
bool operator()(const lldb::SBType& lhs, const lldb::SBType& rhs) const;
4135
};
4236
} // namespace std
4337

@@ -67,6 +61,7 @@ class LLDBParser {
6761
Primitive::Kind primitiveIntKind(lldb::SBType& type, bool is_signed);
6862
Primitive::Kind primitiveFloatKind(lldb::SBType& type);
6963

64+
void enumerateClassParents(lldb::SBType& type, std::vector<Parent>& parents);
7065
void enumerateClassMembers(lldb::SBType& type, std::vector<Member>& members);
7166
void enumerateClassFunctions(lldb::SBType &type, std::vector<Function>& functions);
7267

test/test_lldb_parser.cpp

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -169,9 +169,9 @@ TEST_F(LLDBParserTest, SimpleUnion) {
169169
TEST_F(LLDBParserTest, Inheritance) {
170170
test("oid_test_case_inheritance_access_public", R"(
171171
[4] Pointer
172-
[0] Class: Public (size: 8)
172+
[0] Class: ns_inheritance_access::Public (size: 8)
173173
Parent (offset: 0)
174-
[1] Class: Base (size: 4)
174+
[1] Class: ns_inheritance_access::Base (size: 4)
175175
Member: base_int (offset: 0)
176176
[3] Typedef: int32_t
177177
[2] Typedef: __int32_t
@@ -184,25 +184,25 @@ TEST_F(LLDBParserTest, Inheritance) {
184184
TEST_F(LLDBParserTest, InheritanceMultiple) {
185185
test("oid_test_case_inheritance_multiple_a", R"(
186186
[6] Pointer
187-
[0] Struct: Derived_2 (size: 24)
187+
[0] Struct: ns_inheritance_multiple::Derived_2 (size: 24)
188188
Parent (offset: 0)
189-
[1] Struct: Base_1 (size: 4)
189+
[1] Struct: ns_inheritance_multiple::Base_1 (size: 4)
190190
Member: a (offset: 0)
191191
Primitive: int32_t
192192
Parent (offset: 4)
193-
[2] Struct: Derived_1 (size: 12)
193+
[2] Struct: ns_inheritance_multiple::Derived_1 (size: 12)
194194
Parent (offset: 0)
195-
[3] Struct: Base_2 (size: 4)
195+
[3] Struct: ns_inheritance_multiple::Base_2 (size: 4)
196196
Member: b (offset: 0)
197197
Primitive: int32_t
198198
Parent (offset: 4)
199-
[4] Struct: Base_3 (size: 4)
199+
[4] Struct: ns_inheritance_multiple::Base_3 (size: 4)
200200
Member: c (offset: 0)
201201
Primitive: int32_t
202202
Member: d (offset: 8)
203203
Primitive: int32_t
204204
Parent (offset: 16)
205-
[5] Struct: Base_4 (size: 4)
205+
[5] Struct: ns_inheritance_multiple::Base_4 (size: 4)
206206
Member: e (offset: 0)
207207
Primitive: int32_t
208208
Member: f (offset: 20)

0 commit comments

Comments
 (0)