Skip to content

Commit 0fa2249

Browse files
committed
[ObjC] Use NamedTypeReference to refer to id / SEL / BOOL
Rather than introducing duplicate definitions of these types, use a NamedTypeReference that will be resolved to the type from the libobjc type library when it is loaded. This prevents these types from showing up as id_1 / SEL_1 in some places rather than as their expected names.
1 parent 6706cc8 commit 0fa2249

File tree

2 files changed

+28
-21
lines changed

2 files changed

+28
-21
lines changed

objectivec/objc.cpp

Lines changed: 22 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,13 @@ namespace {
106106
return component;
107107
}
108108

109+
Ref<Type> NamedType(const std::string& name)
110+
{
111+
NamedTypeReferenceBuilder builder;
112+
builder.SetName(QualifiedName(name));
113+
return Type::NamedType(builder.Finalize());
114+
}
115+
109116
} // namespace
110117

111118
Ref<Metadata> ObjCProcessor::SerializeMethod(uint64_t loc, const Method& method)
@@ -320,12 +327,12 @@ std::vector<QualifiedNameOrType> ObjCProcessor::ParseEncodedType(const std::stri
320327
nameOrType.type = Type::PointerType(m_data->GetAddressSize(), Type::IntegerType(1, true));
321328
break;
322329
case '@':
323-
qualifiedName = "id";
330+
nameOrType.type = m_types.id;
324331
// There can be a type after this, like @"NSString", that overrides this
325332
// The handler for " will catch it and drop this "id" entry.
326333
break;
327334
case ':':
328-
qualifiedName = "SEL";
335+
nameOrType.type = m_types.sel;
329336
break;
330337
case '#':
331338
qualifiedName = "objc_class_t";
@@ -1214,11 +1221,11 @@ bool ObjCProcessor::ApplyMethodType(Class& cls, Method& method, bool isInstanceM
12141221

12151222
params.push_back({"self",
12161223
cls.associatedName.IsEmpty() ?
1217-
Type::NamedType(m_data, {"id"}) :
1224+
m_types.id :
12181225
Type::PointerType(m_data->GetAddressSize(), Type::NamedType(m_data, cls.associatedName)),
12191226
true, BinaryNinja::Variable()});
12201227

1221-
params.push_back({"sel", Type::NamedType(m_data, {"SEL"}), true, BinaryNinja::Variable()});
1228+
params.push_back({"sel", m_types.sel, true, BinaryNinja::Variable()});
12221229

12231230
for (size_t i = 3; i < typeTokens.size(); i++)
12241231
{
@@ -1370,6 +1377,10 @@ ObjCProcessor::ObjCProcessor(BinaryView* data, const char* loggerName, bool skip
13701377
m_skipClassBaseProtocols(skipClassBaseProtocols), m_data(data)
13711378
{
13721379
m_logger = m_data->CreateLogger(loggerName);
1380+
1381+
m_types.id = NamedType("id");
1382+
m_types.sel = NamedType("SEL");
1383+
m_types.BOOL = NamedType("BOOL");
13731384
}
13741385

13751386
uint64_t ObjCProcessor::GetObjCRelativeMethodBaseAddress(ObjCReader* reader)
@@ -1387,11 +1398,6 @@ void ObjCProcessor::ProcessObjCData()
13871398
auto guard = ScopedSymbolQueue::Make();
13881399

13891400
auto addrSize = m_data->GetAddressSize();
1390-
1391-
m_typeNames.id = defineTypedef(m_data, {"id"}, Type::PointerType(addrSize, Type::VoidType()));
1392-
m_typeNames.sel = defineTypedef(m_data, {"SEL"}, Type::PointerType(addrSize, Type::IntegerType(1, false)));
1393-
1394-
m_typeNames.BOOL = defineTypedef(m_data, {"BOOL"}, Type::IntegerType(1, false));
13951401
m_typeNames.nsInteger = defineTypedef(m_data, {"NSInteger"}, Type::IntegerType(addrSize, true));
13961402
m_typeNames.nsuInteger = defineTypedef(m_data, {"NSUInteger"}, Type::IntegerType(addrSize, false));
13971403
m_typeNames.cgFloat = defineTypedef(m_data, {"CGFloat"}, Type::FloatType(addrSize));
@@ -1719,11 +1725,10 @@ void ObjCProcessor::ProcessNSConstantArrays()
17191725
auto guard = ScopedSymbolQueue::Make();
17201726
uint64_t ptrSize = m_data->GetAddressSize();
17211727

1722-
auto idType = Type::NamedType(m_data, m_typeNames.id);
17231728
StructureBuilder nsConstantArrayBuilder;
17241729
nsConstantArrayBuilder.AddMember(Type::PointerType(ptrSize, Type::VoidType()), "isa");
17251730
nsConstantArrayBuilder.AddMember(Type::IntegerType(ptrSize, false), "count");
1726-
nsConstantArrayBuilder.AddMember(Type::PointerType(ptrSize, idType), "objects");
1731+
nsConstantArrayBuilder.AddMember(Type::PointerType(ptrSize, m_types.id), "objects");
17271732
auto type = finalizeStructureBuilder(m_data, nsConstantArrayBuilder, "__NSConstantArray");
17281733
m_typeNames.nsConstantArray = type.first;
17291734

@@ -1740,7 +1745,7 @@ void ObjCProcessor::ProcessNSConstantArrays()
17401745
uint64_t count = reader->ReadPointer();
17411746
auto dataLoc = ReadPointerAccountingForRelocations(reader.get());
17421747
DefineObjCSymbol(
1743-
DataSymbol, Type::ArrayType(idType, count), fmt::format("nsarray_{:x}_data", i), dataLoc, true);
1748+
DataSymbol, Type::ArrayType(m_types.id, count), fmt::format("nsarray_{:x}_data", i), dataLoc, true);
17441749
DefineObjCSymbol(DataSymbol, Type::NamedType(m_data, m_typeNames.nsConstantArray),
17451750
fmt::format("nsarray_{:x}", i), i, true);
17461751
}
@@ -1757,13 +1762,12 @@ void ObjCProcessor::ProcessNSConstantDictionaries()
17571762
auto guard = ScopedSymbolQueue::Make();
17581763
uint64_t ptrSize = m_data->GetAddressSize();
17591764

1760-
auto idType = Type::NamedType(m_data, m_typeNames.id);
17611765
StructureBuilder nsConstantDictionaryBuilder;
17621766
nsConstantDictionaryBuilder.AddMember(Type::PointerType(ptrSize, Type::VoidType()), "isa");
17631767
nsConstantDictionaryBuilder.AddMember(Type::IntegerType(ptrSize, false), "options");
17641768
nsConstantDictionaryBuilder.AddMember(Type::IntegerType(ptrSize, false), "count");
1765-
nsConstantDictionaryBuilder.AddMember(Type::PointerType(ptrSize, idType), "keys");
1766-
nsConstantDictionaryBuilder.AddMember(Type::PointerType(ptrSize, idType), "objects");
1769+
nsConstantDictionaryBuilder.AddMember(Type::PointerType(ptrSize, m_types.id), "keys");
1770+
nsConstantDictionaryBuilder.AddMember(Type::PointerType(ptrSize, m_types.id), "objects");
17671771
auto type = finalizeStructureBuilder(m_data, nsConstantDictionaryBuilder, "__NSConstantDictionary");
17681772
m_typeNames.nsConstantDictionary = type.first;
17691773

@@ -1782,9 +1786,9 @@ void ObjCProcessor::ProcessNSConstantDictionaries()
17821786
auto keysLoc = ReadPointerAccountingForRelocations(reader.get());
17831787
auto objectsLoc = ReadPointerAccountingForRelocations(reader.get());
17841788
DefineObjCSymbol(
1785-
DataSymbol, Type::ArrayType(idType, count), fmt::format("nsdict_{:x}_keys", i), keysLoc, true);
1786-
DefineObjCSymbol(
1787-
DataSymbol, Type::ArrayType(idType, count), fmt::format("nsdict_{:x}_objects", i), objectsLoc, true);
1789+
DataSymbol, Type::ArrayType(m_types.id, count), fmt::format("nsdict_{:x}_keys", i), keysLoc, true);
1790+
DefineObjCSymbol(DataSymbol, Type::ArrayType(m_types.id, count), fmt::format("nsdict_{:x}_objects", i),
1791+
objectsLoc, true);
17881792
DefineObjCSymbol(DataSymbol, Type::NamedType(m_data, m_typeNames.nsConstantDictionary),
17891793
fmt::format("nsdict_{:x}", i), i, true);
17901794
}

objectivec/objc.h

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -252,9 +252,12 @@ namespace BinaryNinja {
252252

253253
class ObjCProcessor {
254254
struct Types {
255-
QualifiedName id;
256-
QualifiedName sel;
257-
QualifiedName BOOL;
255+
Ref<Type> id;
256+
Ref<Type> sel;
257+
Ref<Type> BOOL;
258+
} m_types;
259+
260+
struct TypeNames {
258261
QualifiedName nsInteger;
259262
QualifiedName nsuInteger;
260263
QualifiedName cgFloat;

0 commit comments

Comments
 (0)