整个程序有两个表保存类:gdb_objc_realized_classes 和 allocatedClasses
gdb_objc_realized_classes:是全部从Maco里面加载的类
allocatedClasses:已经从Maco中加载到内存中的类
加载流程如下:
1 _objc_init
2 map_images
3 _read_images
3.1 readClass
以下代码基本是不走的!!
if (Class newCls = popFutureNamedClass(mangledName)) {
// This name was previously allocated as a future class.
// Copy objc_class to future class's struct.
// Preserve future's rw data block.
if (newCls->isAnySwift()) {
_objc_fatal("Can't complete future class request for '%s' "
"because the real class is too big.",
cls->nameForLogging());
}
class_rw_t *rw = newCls->data();
const class_ro_t *old_ro = rw->ro;
memcpy(newCls, cls, sizeof(objc_class));
rw->ro = (class_ro_t *)newCls->data();
newCls->setData(rw);
freeIfMutable((char *)old_ro->name);
free((void *)old_ro);
addRemappedClass(cls, newCls);
replacing = cls;
cls = newCls;
}
3.1.1 addNamedClass(cls, mangledName, replacing);
3.1.1.1 NXMapInsert(gdb_objc_realized_classes, name, cls);
gdb_objc_realized_classes
3.1.2 addClassTableEntry(cls);
allocatedClasses
3.1.2.1 allocatedClasses.insert
3.2 如果是非懒加载类 :realizeClassWithoutSwift
懒加载类会在方法调用的时候生成
IMP lookUpImpOrForward(Class cls, SEL sel, id inst,
bool initialize, bool cache, bool resolver)
{
if (!cls->isRealized()) {
cls = realizeClassMaybeSwiftAndLeaveLocked(cls, runtimeLock);
}
}
3.2.1 读取ro、创建rw、赋值ro\rw
ro = (const class_ro_t *)cls->data();
rw = (class_rw_t *)calloc(sizeof(class_rw_t), 1);
rw->ro = ro;
rw->flags = RW_REALIZED|RW_REALIZING;
cls->setData(rw);
3.2.2 实现metacls和supercls(递归)
supercls = realizeClassWithoutSwift(remapClass(cls->superclass), nil);
metacls = realizeClassWithoutSwift(remapClass(cls->ISA()), nil);
出口为NSObject.superClass = nil
3.2.3 赋值metacls和supercls
cls->superclass = supercls;
cls->initClassIsa(metacls);
3.2.4 反向赋值superClass,实现双向链表结构
if (supercls) {
addSubclass(supercls, cls);
} else {
addRootClass(cls);
}
3.2.5 methodizeClass
method_list_t *list = ro->baseMethods();
if (list) {
prepareMethodLists(cls, &list, 1, YES, isBundleClass(cls));
rw->methods.attachLists(&list, 1);
}
property_list_t *proplist = ro->baseProperties;
if (proplist) {
rw->properties.attachLists(&proplist, 1);
}
protocol_list_t *protolist = ro->baseProtocols;
if (protolist) {
rw->protocols.attachLists(&protolist, 1);
}