前语
上一篇博客咱们了解到dyld->libsystem->libdispatch->_objc_init
这样一个流程。那么下面咱们来了解一下objc_init
里边究竟做了些啥。
objc_init剖析
-
environ_init
环境变量初始化
在源码里边经过如下代码来检查环境变量:
for (size_t i = 0; i < sizeof(Settings)/sizeof(Settings[0]); i++) {
const option_t *xcode怎样运转c++程序opt = &Settings[i];
_objc_in服务器ipforswift怎样读m("%s: %s", opt->源码年代坑人env, opt->help);
_objc_inform(xcode轿车"%s is set", opt->env);
}
还源码是什么意思能够经过在终端里边输入export OBJC_HELP=1
,然后再输源码年代坑人入lldb
:打印信息如下
咱们能够在xcode
里边设置一下OBJC_PRINT_IMAGES
设置一下这个环境变量,就会打印出。经过Edit Scheme ->Run
就能够设置。
-
tls_Swiftinit
:关于线程key的绑定,比方每swiftkey个现场的析构函数 -
static_init
:运⾏C ++静态结构函数。在dyld调⽤之前自己先调用 -
runtime_init
:首要是初始化unattachedCategories
和allocatedClasses
两个表。 -
e源码本钱xception_init
:失常初始化,咱们常用的objc_setUncaughtExceptionHandler
处理崩溃后失常,线程是什么意思或奔溃日志上传服务器。 -
cache_t::init()
缓存条件初始化 -
_imp_implementationWithBlock_init
:发起回调机制。一般这不会做什么,由于一切的初始化都是慵懒的,可是对于某些进程,咱们会刻不容缓地加载trampolixcode教程nes dylib. -
_dyld_objc_notify_register
,将map_images
load_images
unmap_image
办法赋值给dyld去触发调用
map_images剖析
map_images_nolock
这swift体系个办法首要是找到macho
一xcode怎样设置成中文切服务器是什么的image
,然后调用_read_imswiftcode是什么意思中文ages
_read_images剖析Swift
这个里边,代码有许多,当时苹果工程师做了许多的日志打印。咱们能够经过这个xcode教程来分红小模块去剖析。
条源码交易平台排行件操控进行第一次加载
创立NXMapTable
表,巨swiftcode是什么意思中文细为4/3
*totalClasses
。这个表是一张class
总表;与上面的allocatedClasses
表是有差异的,后边的是存储现已alloc
的。
-
批改预编译阶段的 @selector 的swiftkey混乱问题
.
为什么会需求批改呢?这是由于,咱们从image
里边获取的办法的地址是没源码年代坑人有加上ASLR
也便是基地址,需求经过dyxcode轿车ld
加上基地址后从头批改。
读取类readClass、处理没有被清理的类
批改重映射一些没有被镜像文件加载进来的类rem源码怎样做成app软件apClassRef
批改一线程撕裂者些音讯fixupMessageRef
读取类的协议readProtocol
批改没有被加载的协议remapProtocolRef
加载分类load_categories_nolock
加载类r源码年代坑人ealizeClassWithoutSwift
结束新解析的未来类
下面咱们首要剖析一下readClass
readClass剖析
在readClass服务器怎样建立
办法中增加如下代码,这样就能够研讨咱们自定义的类是怎样读取的。
发现并没有实行ro,rw相关的赋值。
断点持续下一步,会调用addNamedClass
,
- 持续实行会递归调用
addCxcode轿车lassTableEntry
,
addClassTableEntry(Class cls, bool addMeta = true)xcode中文
{
runtimeLock.assertLocked()xcode怎样运转c++程序;
// This class is allowed to be a known class via the sharexcode是什么d cache or via
// data segments, but it is not allowed to be in the dynamic table already.
auto &set = objc::allocatedClasses.g服务器怎样建立et();
ASSERT(set.find(cls) == set.end());
if (!isKnownClass(cls))
s服务器租借多少钱一年et.insert(cls);
if (addMeta)
addClassT线程的概念ableEntry(cls->ISA(), false);
}
把class
刺进到allocatedClasses
表中,假设有元类,把元类也刺进进去。
类的结束realizeClassWithoutSwift
- 新建一个
QHPswiftererson
类,然后在里边增加load
办法,在代码里边增加xcode是什么软件如下代码,这样就能够研讨咱们自定义的类
持续实行进入到realizeClassWithoutSwift
办法。
- ro 赋值给rw
- 设置父类和元类联系
- 条理化class
meth线程池创立的四种odizeClass剖析
下面咱们持续进入methodizeClass
办法,增加如下代码,这儿多了一个元类的判别,由于元类和自身类的姓名相xcode教程同:
- 证明
rwe->properties.attachLists(&proplist, 1);
和rwe->protocolsswiftcode是什么意思中文.attachLists(&protolist, 1);
。 - 假设有办法就会调用
prepareMethodLists
,这个线程池办法实际上是经过地址对办法进行排序,下面的代码能够验证
- 将分类增加到主类
attachToClass
,这个办法swiftcode是什么意思中文下篇博客再分服务器是什么析 - 所以
mexcode教程thodizeClass
首要是办法排序和将分类增加到主类中。
懒加载和非懒加载
上面咱们在自定义的类中增加了load办法,现在咱们去掉线程池创立的四种.然后再运转。发现一个古怪的现象:
这是为什么???下面咱们在main
里边调用QHPerson
的办法swift怎样读。持续运转,这个时分进入了,只不过不是走的之前的流程:
总结
- 假设自定义的类结束了
load
办法,(非懒加载
),会经过dyld->objc_init->(实例化主程序)->read_image->read_class
去加载类。 - 假设没有结束
load
办法,(懒加载
),会在第swift怎样读一次调用方针办法的时分去,走音讯转发流程
去结束 -
懒加载
这样的处理方式会大大优化app的发起时刻
。