iOS15 类加载原理2

251 阅读2分钟

前面文章分析了 _objc_init与read_images的逻辑,最后定位到了类的初始化是在realizeClassWithoutSwift中的,这篇文章主要分析realizeClassWithoutSwift

1,realizeClassWithoutSwift

  • realizeClassWithoutSwift 源码
static Class realizeClassWithoutSwift(Class cls, Class previously)
{
    runtimeLock.assertLocked();

    class_rw_t *rw;
    Class supercls;
    Class metacls;

    if (!cls) return nil;
    if (cls->isRealized()) {
        validateAlreadyRealizedClass(cls);
        return cls;
    }
    ASSERT(cls == remapClass(cls));

    //生成rw数据
    auto ro = (const class_ro_t *)cls->data();
    auto isMeta = ro->flags & RO_META;
    if (ro->flags & RO_FUTURE) {
        rw = cls->data();
        ro = cls->data()->ro();
        ASSERT(!isMeta);
        cls->changeInfo(RW_REALIZED|RW_REALIZING, RW_FUTURE);
    } else {
    //开辟rw空间
        rw = objc::zalloc<class_rw_t>();
        //将ro数据存入rw中,这也是为什么从data()->ro()的原因。
        rw->set_ro(ro);
        //flag标识位设置 uint32_t 1<<31 1<<19  1<<0(元类为1非元类为0)
        rw->flags = RW_REALIZED|RW_REALIZING|isMeta;
        //设置rw数据,这个时候data()拿出来的就是rw数据了。
        cls->setData(rw);
    }

    //1,生成rw数据逻辑
    //cache的初始化
    cls->cache.initializeToEmptyOrPreoptimizedInDisguise();

#if FAST_CACHE_META
    //是否是元类
    if (isMeta) cls->cache.setBit(FAST_CACHE_META);
#endif

    cls->chooseClassArrayIndex();

    if (PrintConnecting) {
        _objc_inform("CLASS: realizing class '%s'%s %p %p #%u %s%s",
                     cls->nameForLogging(), isMeta ? " (meta)" : "", 
                     (void*)cls, ro, cls->classArrayIndex(),
                     cls->isSwiftStable() ? "(swift)" : "",
                     cls->isSwiftLegacy() ? "(pre-stable swift)" : "");
    }
    
    //父类和元类的实例化
    supercls = realizeClassWithoutSwift(remapClass(cls->getSuperclass()), nil);
    metacls = realizeClassWithoutSwift(remapClass(cls->ISA()), nil);

#if SUPPORT_NONPOINTER_ISA
    //元类isa是纯之中
    if (isMeta) {
        cls->setInstancesRequireRawIsa();
    } else {
        bool instancesRequireRawIsa = cls->instancesRequireRawIsa();
        bool rawIsaIsInherited = false;
        static bool hackedDispatch = false;
        //这就是环境变量中配置的 OBJC_DISABLE_NONPOINTER_ISA
        if (DisableNonpointerIsa) {
            instancesRequireRawIsa = true;
        }
        //OS_object类是纯指针
        else if (!hackedDispatch  &&  0 == strcmp(ro->getName(), "OS_object"))
        {
            hackedDispatch = true;
            instancesRequireRawIsa = true;
        }
        //父类是纯指针,并且父类还有父类。那么自己也要是纯指针。rawIsaIsInherited 表示继承的是纯指针
        else if (supercls  &&  supercls->getSuperclass()  &&
                 supercls->instancesRequireRawIsa())
        {
            instancesRequireRawIsa = true;
            rawIsaIsInherited = true;
        }
        //递归设置isa为纯指针,子类也设置为纯指针。(父类为纯指针,子类也为纯指针)。rawIsaIsInherited只是控制打印。
        if (instancesRequireRawIsa) {
            cls->setInstancesRequireRawIsaRecursively(rawIsaIsInherited);
        }
    }
// SUPPORT_NONPOINTER_ISA
#endif
    cls->setSuperclass(supercls);
    cls->initClassIsa(metacls);

    //调整ivar的offset,可能会重新创建`class_ro_t`来更新ivar
    if (supercls  &&  !isMeta) reconcileInstanceVariables(cls, supercls, ro);
    //设置成员变量占用空间大小
    cls->setInstanceSize(ro->instanceSize);
    
    //拷贝ro的flags到rw中  flags第2位 c++构造方法 RO_HAS_CXX_STRUCTORS,flags第8位 RO_HAS_CXX_DTOR_ONLY(c++析构方法)
    if (ro->flags & RO_HAS_CXX_STRUCTORS) {
        cls->setHasCxxDtor();
        if (! (ro->flags & RO_HAS_CXX_DTOR_ONLY)) {
            cls->setHasCxxCtor();
        }
    }
 
    //是否禁止关联对象 第20位标记是否允许关联对象。
    if ((ro->flags & RO_FORBIDS_ASSOCIATED_OBJECTS) ||
        (supercls && supercls->forbidsAssociatedObjects()))
    {
        rw->flags |= RW_FORBIDS_ASSOCIATED_OBJECTS;
    }
    
    if (supercls) {
        //关联子类
        addSubclass(supercls, cls);
    } else {
    //设置根类 nextSiblingClass 为 _firstRealizedClass 根类是第一个被实例化的类。
        addRootClass(cls);
    }
    
    methodizeClass(cls, previously);

    return cls;
}