了解mach-o文件结构

转载自 http://www.blogfshare.com/ioss-mach-o.html

我们知道Windows下的文件都是PE文件,同样在OS X和iOS中可执行文件是Mach-o格式的。

所以我们如果要进行逆向分析,首先要熟悉Mach-o文件结构。
Mach-o 包含三个基本区域:

  • 头部(header structure)
  • 加载命令(load command)
  • 段(segment)。可以拥有多个`段(segment),每个段可以拥有零个或多个区域(section)。每一个段(segment)都拥有一段虚拟地址映射到进程的地址空间。
  • 链接信息。一个完整的用户级Mach-o文件的末端是链接信息。其中包含了动态加载器用来链接可执行文件或者依赖库所需使用的符号表,字符串表等等。


你也可以在这里找到Mach-o的官方资料。

一、我们先使用otool工具来查看Mach-o的头部,看看都包含哪些信息。

头部的的结构如下(32位):

struct mach_header {
     uint32_t    magic ;
    cpu_type_t  cputype ;
    cpu_subtype_t   cpusubtype ;
     uint32_t    filetype ;
     uint32_t    ncmds ;
     uint32_t    sizeofcmds ;
     uint32_t    flags ;
}
  • magic,是mach-o文件的魔数,0xfeedface代表的是32位,0xfeedfacf代表64位

  • cputypecupsubtype代表的是cpu的类型和其子类型,例子中分别是c和9,定义如下:

#define CPU_TYPE_ARM((cpu_type_t) 12)

#define CPU_SUBTYPE_ARM_V7((cpu_subtype_t) 9

即为:armv7

  • filetype,2,代表可执行的文件
#defineMH_EXECUTE 0×2
  • ncmds 指的是加载命令(load commands)的数量,例子中一共23个,编号0-22

  • sizeofcmds 表示23个load commands的总字节大小, load commands区域是紧接着header区域的。

  • flags,例子中是0×00200085,可以按文档分析之。

当然不用工具,直接使用UE看也是一样的。按照定义的结构来就行了。

二、头部之后就是加载命令。加载命令的数目以及总的大小在header中已经给出。

  • cmdload command的类型,本文中值=1就是LC_SEGMENT,,LC_SEGMENT的含义是(将文件中的段映射到进程地址空间)

  • cmdsize 代表load command的大小(0×58个字节)。

  • segname 16字节的段名字,当前是__PAGEZERO。

  • vmaddr 段的虚拟内存起始地址

  • vmsize 段的虚拟内存大小

  • fileoff 段在文件中的偏移量

  • filesize 段在文件中的大小

  • maxprot 段页面所需要的最高内存保护(4=r,2=w,1=x)

  • initprot 段页面初始的内存保护

  • nsects 段中包含section的数量

  • flags 其他杂项标志位

三、接下来就是 section了:

结构如下:

struct section  { 
     char sectname [ 16 ] ; 
     char segname [ 16 ] ; 
     uint32_t addr ; 
     uint32_t size ; 
     uint32_t offset ; 
     uint32_t align ; 
     uint32_t reloff ; 
     uint32_t nreloc ; 
     uint32_t flags ; 
     uint32_t reserved1 ; 
     uint32_t reserved2 ;
} ;
  • sectname 第一个是__text ,就是主程序代码

  • segname 该section所属的 segment名,第一个是__TEXT

  • addr 该section在内存的启始位置,0xa588。

  • size 该section的大小,0x84a

  • offset 该section的文件偏移,28116 0x6dd4

  • align 字节大小对齐 ,4

  • reloff 重定位入口的文件偏移,0

  • nreloc 需要重定位的入口数量,0

  • flags 包含section的type和attributes
    S_REGULAR—This section has no particular type. The standard tools create a __TEXT,__text section of this type.

结构中的最后2项保留用。

段的命名规则是两个下划线紧跟着大写字母(如__TEXT),而section的命名则是两个下划线紧跟着小写字母(__text)。

下面列出段中可能包含的section:

__TEXT段:
__text, __cstring, __picsymbol_stub, __symbol_stub, __const, __litera14, __litera18;

__DATA段
__data, __la_symbol_ptr, __nl_symbol_ptr, __dyld, __const, __mod_init_func, __mod_term_func, __bss, __commom;

__IMPORT段
__jump_table, __pointers;

其中__TEXT段中的__text是实际上的代码部分;__DATA段的__data是实际的初始数据。

绝大多数mach-o包括以下三个段(支持用户自定义Segment,但是很少使用):

  • __TEXT 代码段,只读,包括函数,和只读的字符串__TEXT,__text的都是代码段
  • __DATA 数据段,读写,包括可读写的全局变量等,__DATA,__data都是数据段
  • __LINKEDIT __LINKEDIT包含了方法和变量的元数据(位置,偏移量),以及代码签名等信息。

可以通过otool –s查看某segment的某个section

可以通过otool –t直接查看代码段(__TEXT)的反汇编代码:

最常见的加载命令如下:


  • LC_SEGMENT_64: 将该段(64位)映射到进程地址空间中

  • LC_DYLD_INFO_ONLY:加载动态链接库信息(重定向地址、弱引用绑定、懒加载绑定、开放函数等的偏移值等信息)

  • LC_SYMTAB:载入符号表地址

  • LC_DYSYMTAB:载入动态符号表地址

  • LC_LOAD_DYLINKER:加载动态加载库,可以看出示例使用的是/usr/lib/dyld

  • LC_UUID:确定文件的唯一标识,crash解析中也会有这个,去检测dysm文件和crash文件是否匹配

  • LC_VERSION_MIN_MACOSX/LC_VERSION_MIN_IPHONEOS:确定二进制文件要求的最低操作系统版本

  • LC_SOURCE_VERSION:构建该二进制文件使用的源代码版本

  • LC_MAIN:设置程序主线程的入口地址和栈大小

  • LC_ENCRYPTION_INFO_64:获取加密信息

  • LC_LOAD_DYLIB:加载额外的动态库

  • LC_FUNCTION_STARTS:定义一个函数起始地址表,使调试器和其他程序易于看到一个地址是否在函数内

  • LC_DATA_IN_CODE:定义在代码段内的非指令的表

  • LC_CODE_SIGNATURE:获取应用签名信息

作者:小可长江
链接:https://juejin.cn/post/6844903780853481479
来源:稀土掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

其它的大家参考官方文档就行了。
相关文章

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,362评论 5 477
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,330评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,247评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,560评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,580评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,569评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,929评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,587评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,840评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,596评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,678评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,366评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,945评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,929评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,165评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 43,271评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,403评论 2 342

推荐阅读更多精彩内容

  • 上一篇说到源码经过预处理、编译、汇编之后生成目标文件,这一章介绍一下iOS、Mac OS中目标文件的格式Mach-...
    Tenloy阅读 2,003评论 2 9
  • 1. Mach-O 文件结构 Mach-O(Mach Object) 文件格式是 OS X 与 iOS 系统上的可...
    蓝天白云_Sam阅读 452评论 0 3
  • 本文源码从苹果开源官网获得 什么是Mach-O Mach-O 为 Mach Object文件格式的缩写,是用于 i...
    Rimson阅读 497评论 0 0
  • 本文所读的源码,可以从这里找到,这是 Mach-O 系列的第一篇 我们的程序想要跑起来,肯定它的可执行文件格式要被...
    Joy___阅读 24,146评论 9 97
  • Mach-o文件结构 Mach-o包含三个基本区域: 头部(header structure)加载命令(load ...
    介和阅读 429评论 0 0