使用objc4V818.2源码编译,没有什么比苹果底层源码更有说服力去证明底层原理真假
前言
为什么会想要调试源码?
苹果开源了部分源码, 但相似内容太多, 基本找不到代码见的对应关系, 如果能像自己工程一样进行跳转那多好哇~~
苹果源码开源地址: https://opensource.apple.com/
本文将以macOS 11.2/objc4-818.2的源码进行配置
源码配置
首先选中运行target: objc > My Mac
然后⌘+b进行编译
翻一下爆红的点看看都有哪些错误, 然后找到下面对应的解决方案~
编译报错 'sys/reason.h' file not found

解决方案: 谷歌中输入reason.h site:opensource.apple.com定向检索

点进去搜索结果里面, 进行"文件另存为"下载
下载后, 在objc源码根目录中创建一个文件夹"ZKLib",
然后因为reason.h文件是在sys目录下的, 所以我们在"ZKLib"目录下创建"sys"文件夹, 并把reason.h放到该目录里面(如下图)

接下来我们在源码工程 target > objc > Build Settings中搜索"Header Search Paths", 给Debug和Release都加上$(SRCROOT)/ZKLib即可
(不需要把ZKLib拉进源码Xcode工程里哦! )\

然后继续⌘+b编译
其它文件缺失
我们会发现相同的报错还有\
'mach-o/dyld_priv.h' file not found
'os/lock_private.h' file not found
'os/base_private.h' file not found
'pthread/tsd_private.h' file not found
'System/machine/cpu_capabilities.h' file not found
'os/tsd.h' file not found
'pthread/spinlock_private.h' file not found
'System/pthread_machdep.h' file not found
'CrashReporterClient.h' file not found
'objc-shared-cache.h' file not found
'_simple.h' file not found
'Block_private.h' file not found
这些报错的解决方案都跟上面的一样处理
objc源码文件代码修改
CrashReporterClient明明放进去了还是"file not found"
打开CrashReporterClient.h文件,

在#ifdef前面加上以下代码:
#define LIBC_NO_LIBCRASHREPORTERCLIENT
注释掉一些妨碍编译的代码
总的来说一共有这么多:
具体都有:
objc-cache.mm
87行:
#if TARGET_OS_OSX
//#include <Cambria/Traps.h>
//#include <Cambria/Cambria.h>
#endif
1120行:
//#if TARGET_OS_OSX
// if (oah_is_current_process_translated()) {
// kern_return_t ret = objc_thread_get_rip(threads[count], (uint64_t*)&pc);
// if (ret != KERN_SUCCESS) {
// pc = PC_SENTINEL;
// }
// } else {
// pc = _get_pc_for_thread (threads[count]);
// }
//#else
pc = _get_pc_for_thread (threads[count]);
//#endif
NSObject.mm
42行:
//#include <os/feature_private.h>
extern "C" {
//#include <os/reason_private.h>
//#include <os/variant_private.h>
}
1185行:
// if (DebugPoolAllocation || sdkIsAtLeast(10_12, 10_0, 10_0, 3_0, 2_0)) {
// // OBJC_DEBUG_POOL_ALLOCATION or new SDK. Bad pop is fatal.
// _objc_fatal
// ("Invalid or prematurely-freed autorelease pool %p.", token);
// }
objc-runtime.mm
36行:
//#include <os/feature_private.h> // os_feature_enabled_simple()
379行:
// if (!dyld_program_sdk_at_least(dyld_fall_2020_os_versions))
// DisableAutoreleaseCoalescingLRU = true;
444行:
// if (!os_feature_enabled_simple(objc4, preoptimizedCaches, true)) {
// DisablePreoptCaches = true;
// }
objc-class.mm
896行:
// LINKER_SET_FOREACH(_dupi, const objc_duplicate_class **, "__objc_dupclass") {
// const objc_duplicate_class *dupi = *_dupi;
//
// if (strcmp(dupi->name, name) == 0) {
// return;
// }
// }
objc-os.mm
31行:
//#include "objc-bp-assist.h"
\
567行:
// if (!dyld_program_sdk_at_least(dyld_platform_version_macOS_10_13)) {
// DisableInitializeForkSafety = true;
// if (PrintInitializing) {
// _objc_inform("INITIALIZE: disabling +initialize fork "
// "safety enforcement because the app is "
// "too old.)");
// }
// }
objc-runtime-new.mm
3547行:
// if (!dyld_program_sdk_at_least(dyld_platform_version_macOS_10_11)) {
// DisableNonpointerIsa = true;
// if (PrintRawIsa) {
// _objc_inform("RAW ISA: disabling non-pointer isa because "
// "the app is too old.");
// }
// }
8328行:
if (!DisableTaggedPointerObfuscation /**&& dyld_program_sdk_at_least(dyld_fall_2018_os_versions)*/) {
编译报错 Can't open order file: libobjc.order
具体来说是这么一个报错:

解决方案:
在源码工程 target > objc > Build Settings中搜索"Order File", 把Debug和Release的内容都改成$(SRCROOT)/libobjc.order即可

编译报错 Library not found for -lCrashReporterClient
在源码工程 target > objc > Build Settings中搜索"Other Linker Flags", 把Debug和Release中的-lCrashReporterClient都删掉

编译报错 SDK "macosx.internal" cannot be located.
具体来说是这么一个报错:

解决方案:
在源码工程 target > objc > Build Phases中找到Run Script(markgc)里面, 把脚本中的macosx.internal改成macosx即可

编译报错 library not found for -loah
具体来说是这么一个报错:

解决方案:
在源码工程 target > objc > Build Settings中搜索"Other Linker Flags", 把Debug和Release里的-loah删掉

编译报错 '_static_assert' declared as an array with a negative size
具体来说是这么一个报错:

解决方案:
把报错的这两行注释掉~~
编译成功!
诶嘿嘿~
是不是突然间看到"Build Successed"就很兴奋了, 反正我是兴奋了
编译调试
新建一个target
选择macOS里面的Command Line Tool (我们这里不需要界面)

将target命名为ZKBuild (如下图)

绑定依赖关系
在源码工程 target > ZKBuild > Build Phases中
在Dependencies 添加objc

打断点进行调试
切换运行target: ZKBuild > My Mac
在main.m代码中打断点, 并按⌘+r运行

此时按
(step into)进入这一行代码里面

来到objc源码里面, 则表示已经能成功调试objc源码
使用objc4V818.2源码编译,没有什么比苹果底层源码更有说服力去证明底层原理真假的更多相关文章
- SSH/SSL 源码编译安装简易操作说明
环境:CentOS 6.7 安全加固需求,由于某盟扫描系统主机有SSL系列漏洞,客户要求必须修复: 解决方案:将SSH/SSL升级到最新版本,删除SSL旧版本(实测不删除旧版本某盟扫描无法通过). 当 ...
- centos7源码编译安装Subversion 1.9.5
svn是Subversion的简称,是一个开放源代码的版本控制系统.svn有两种运行方式:1.独立服务器(svn://xxx.xxx/xxx) 2.借助apache(http://svn.xxx.xx ...
- 【运维技术】Nginx安装教程(yum安装,源码编译)
安装方式 yum直接更新源安装 源码直接编译之后安装 使用yum进行直接安装 Installing a Prebuilt CentOS/RHEL Package from an OS Reposito ...
- 日常工作之Zabbix源码编译,兼容mysql5.6
原文链接:http://www.leleblog.top/daily/more?id=6 Zabbix源码编译 环境: centOS7.mysql5.6.21(已存在). 任务简述: 服务器搭建zab ...
- GDAL源码编译
转自阿Fai, GDAL源码编译 在这里,我使用源码编译出C#可以使用的dll静态文件. 一.简单的编译 1.简单的认识 首先进入GDAL的源代码目录,可以看到有几个sln为后缀的文件名,比如make ...
- 十四.自定义yum仓库、源码编译安装
pc7:192.168.4.7 1.自定义yum仓库1.1 源码仓库下:/root/tools/other]# createrepo .]# ls ntfs-3g-2014.2.15-6.el6.x8 ...
- CentOS7 源码编译安装Nginx
源码编译安装nginx 1.下载nginx源码包(这里以nginx-1.18.0为例) wget http://nginx.org/download/nginx-1.18.0.tar.gz 2 ...
- Spring 6 源码编译和高效阅读源码技巧分享
一. 前言 Spring Boot 3 RELEASE版本于 2022年11月24日 正式发布,相信已经有不少同学开始准备新版本的学习了,不过目前还不建议在实际项目中做升级,毕竟还有很多框架和中间件没 ...
- Hadoop2.x 体系结构和源码编译
体系结构 Hadoop1的核心组成包括HDFS和MapReduce.HDFS和MapReduce的共同点就是他们都是分布式的. HDFS是包括主节点NameNode,只有一个,还有很多从节点DataN ...
- Android源码分析(六)-----蓝牙Bluetooth源码目录分析
一 :Bluetooth 的设置应用 packages\apps\Settings\src\com\android\settings\bluetooth* 蓝牙设置应用及设置参数,蓝牙状态,蓝牙设备等 ...
随机推荐
- [转帖]宁可信鬼,也不信 iowait 这张嘴!
https://zhuanlan.zhihu.com/p/407333624 原创:小姐姐味道(微信公众号ID:xjjdog),欢迎分享,转载请保留出处. 我们经常遇到iowait这个名词,在top命 ...
- scss常用语法
在线编译 https://wow.techbrood.com/fiddle/11143 群组选择器的嵌套[编译前] .container { h1, h2, h3 {margin-bottom: .8 ...
- 什么是ChatGPT,什么是大模型prompt
什么是ChatGpt ChatGPT是一个由美国的OpenAI公司开发的聊天机器人,它使用了大型语言模型,现在有GPT-3.GPT-3.5.GPT-4.0多个版本,目前还在快速发展,通过监督学习和强化 ...
- minIO系列文章04---windows下安装及在.netcore使用
一.minio下载与启动 下载后会有一个minio.exe文件,放到指定的目录 在该目录下运行:minio.exe server D:\minio\file 出现如下的提示代码启动动成功: 浏览器中 ...
- 每日一库:Memcache
Memcache 是一个高性能.分布式的内存缓存系统,常用于缓存数据库查询结果.API调用结果.页面内容等,以提升应用程序的性能和响应速度.下面详细介绍一些 Memcache 的特点和使用方式: 内存 ...
- 使用telnet来调试游戏
telnet是什么 Telnet协议是TCP/IP协议族中的一员,是Internet远程登陆服务的标准协议和主要方式.它为用户提供了在本地计算机上完成远程主机工作的能力 但是,telnet因为采用明文 ...
- 手撕Vue-构建Vue实例
前言 要想使用Vue必须先创建Vue的实例, 创建Vue的实例通过new来创建, 所以说明Vue是一个类, 所以我们要想使用自己的Vue, 就必须定义一个名称叫做Vue的类. 只要创建好了Vue的实例 ...
- 深度学习应用篇-推荐系统[11]:推荐系统的组成、场景转化指标(pv点击率,uv点击率,曝光点击率)、用户数据指标等评价指标详解
深度学习应用篇-推荐系统[11]:推荐系统的组成.场景转化指标(pv点击率,uv点击率,曝光点击率).用户数据指标等评价指标详解 1. 推荐系统介绍 在网络技术不断发展和电子商务规模不断扩大的背景下, ...
- 【译】命名变得简单:AI 支持的重命名建议
您是否曾经为命名一个变量.方法或类而挣扎过?找到表达性和简洁性之间的完美平衡了吗?您并不孤单.我们通过 GitHub Copilot Chat 扩展(需要订阅)在最新的 Visual Studio 预 ...
- 技嘉水雕II 360水冷散热器评测:稳压340W i9-14900K
一.前言:极简卡扣连锁风扇设计 再多风扇也只需2根线 如今这个年代,DIY主机几乎都会配大量的RGB风扇,然而"光污染"虽然带来了视觉感官享受,在理线方面却非常繁琐. 就拿360水 ...