Runtime 之 isa

2020-08-13  本文已影响0人  ychen3022
1、isa

isa是一个Class类型的指针。每个实例对象有个isa的指针指向对象的类,而类里也有个isa的指针,指向meteClass(元类)。
元类保存了类方法的列表。当类方法被调用时,先会从本身查找类方法的实现,如果没有,元类会向他父类查找该方法。

同时,元类(meteClass)也是类,它也是对象。元类也有isa指针,它的isa指针最终指向的是一个根元类(root meteClass)。根元类的isa指针指向本身,这样形成了一个封闭的内循环。 实例/类对象的isa指针结构图
2、isa结构

在arm64架构之前,isa就是一个普通的指针,存储着Class、Meta-Class对象的内存地址。
从arm64架构开始,对isa进行了优化,变成了一个共用体(union)结构,还使用位域来存储更多的信息。

# if __arm64__

    struct {
        uintptr_t nonpointer        : 1;   //0:代表普通的指针,存储着Class、Meta-Class对象的内存地址; 1:代表优化过,使用位域存储更多的信息
        uintptr_t has_assoc         : 1;   //是否有设置过关联对象,如果没有,释放时会更快
        uintptr_t has_cxx_dtor      : 1;   //是否有C++的析构函数(.cxx_destruct),如果没有,释放时会更快。(析构函数:用来释放内存的操作)
        uintptr_t shiftcls          : 33;  //存储着Class、Meta-Class对象的内存地址信息
        uintptr_t magic             : 6;   //用于在调试时分辨对象是否未完成初始化
        uintptr_t weakly_referenced : 1;   //是否有被弱引用指向过,如果没有,释放时会更快
        uintptr_t deallocating      : 1;   //对象是否正在释放
        uintptr_t has_sidetable_rc  : 1;   //引用计数器是否过大无法存储在isa中,如果为1,那么引用计数会存储在一个叫SideTable的类的属性中
        uintptr_t extra_rc          : 19;  //里面存储的值是引用计数器减1
#       define RC_ONE   (1ULL<<45)
#       define RC_HALF  (1ULL<<18)
    };

# elif __x86_64__
#   define ISA_MASK        0x00007ffffffffff8ULL
#   define ISA_MAGIC_MASK  0x001f800000000001ULL
#   define ISA_MAGIC_VALUE 0x001d800000000001ULL
    struct {
        uintptr_t nonpointer        : 1;
        uintptr_t has_assoc         : 1;
        uintptr_t has_cxx_dtor      : 1;
        uintptr_t shiftcls          : 44; // MACH_VM_MAX_ADDRESS 0x7fffffe00000
        uintptr_t magic             : 6;
        uintptr_t weakly_referenced : 1;
        uintptr_t deallocating      : 1;
        uintptr_t has_sidetable_rc  : 1;
        uintptr_t extra_rc          : 8;
#       define RC_ONE   (1ULL<<56)
#       define RC_HALF  (1ULL<<7)
    };
上一篇下一篇

猜你喜欢

热点阅读