应用安全
这段时间 iOS12 越狱工具发布了,屁颠屁颠的去研究了一键砸壳,昨天忽然想起来之前公司的产品被人破解,拿到了关键信息进而薅羊毛的事。那时的解决方案是检测异常请求和独立出一个加密framework
。现在想想,这些措施都太简单或者不够高效,还需要更进一步研究应用的安全问题。
1.被破解的危害
- 被人逆向分析通信协议、API、核心算法等;
- 篡改IPA、植入广告和木马;
- 重打包并发布盗版应用;
- 破解内购;
2.防范
在这方面我是真没有经验,于是抱着学习的态度去查看了相关的论坛和资料,学学别人的经验,这里做一个简单的记录~
2.1.检测是否越狱(念茜)
这是最常见的被动防御方法,比如当应用启动时,先检测设备是否已经越狱,如果已越狱则禁止应用启动;在用户发起内购支付时,如果发现设备已越狱,则直接拒绝内购请求并给出相应的提示。根据我的测试,部落冲突
游戏就是通过闪退直接禁止越狱设备启动自己,而腾讯旗下的产品基本上都会在越狱设备发起支付时给出提示,别踩音乐块儿
也是如此。
以下摘自念茜的博客:
- 检测越狱文件或目录
越狱后的设备中会有相关的文件:
1 |
|
检测方法:
1 |
|
- 检测 Cydia 的 URL scheme
越狱后的设备一般都会安装 Cydia,这里可以通过检测其 URL Scheme 来反推设备是否越狱。这个方法在 iOS9 之后会因为权限问题而出现问题,所以你需要配置好LSApplicationQueriesSchemes
白名单。
1 |
|
- 读取应用列表,看有无权限:
在未越狱的情况下,用户是没有权限查看设备上的某些目录的,也就无法知晓有哪些已安装的应用,除非你像某些三方市场一样用苹果的私有API,但这会导致上架被拒。所以,我们可以利用这一特性来检测设备是否越狱:
1 |
|
- 用 stat 系列函数检测 Cydia 等工具:
1 |
|
- 检测 DYLD_INSERT_LIBRARIES 环境变量
DYLD_INSERT_LIBRARIES
是一个环境变量,dyld
动态链接器在加载二进制文件时会检测这个变量,如果有配置过则会加载其指向的动态库,从而实现动态注入并将程序的内存dump出来,这正是越狱设备中调试时常用的方法。所以我们可以检测此环境变量来确定设备是否越狱:
1 |
|
未越狱设备返回结果是null,已越狱设备返回自己的配置。
2.2.代码 & 逻辑混淆
- 关键字:类名、属性、方法名等;
- 常量:URL、字符串;
- 将原逻辑拆分成各种怪癖语法;
代码混淆和逻辑混淆,其本质上只是在应用编译时将指定的字符串或逻辑进行混淆替换,从而增加应用破解后阅读源码的难度。具体的混淆方法,我之前的文章中也已经介绍过,这里不再赘述~
2.3.__RESTRICT反动态库注入
restrict,C语言中的一种类型限定符(Type Qualifiers),用于告诉编译器,对象已经被指针所引用,不能通过除该指针外所有其他直接或间接的方式修改该对象的内容。
restrict是c99标准引入的,它只可以用于限定和约束指针,并表明指针是访问一个数据对象的唯一且初始的方式。即它告诉编译器,所有修改该指针所指向内存中内容的操作都必须通过该指针来修改,而不能通过其它途径(其它变量或指针)来修改;这样做的好处是,能帮助编译器进行更好的优化代码,生成更有效率的汇编代码。如 int *restrict ptr, ptr 指向的内存单元只能被 ptr 访问到,任何同样指向这个内存单元的其他指针都是未定义的,直白点就是无效指针。
示例:
1 |
|
这里说明restar是访问由malloc()分配的内存的唯一且初始的方式。par就不是了。
通过在 Xcode 里的 Other Linker Flags 设置参数,可以防止应用的二进制文件被注入 dylib(仅限于iOS 10 以下系统)。dylib 无法注入,也就意味着没办法用cycript
动态调试进程
- Other Linker Flags 参数:
1 |
|
参考博文:
2.4.反ptrace调试
ptrace
是系统函数,此函数提供一个进程去监听和控制另一个进程,并且可以检测被控制进程的内存和寄存器里面的数据。ptrace
可以用来实现断点调试和系统调用跟踪。
参考博文:https://www.jianshu.com/p/ebdfb0a25c85
2.5.第三方加固
缺点:
- 安装包变大;
- 运行速度变慢;
第三方加固提供商:
- 网易易盾
- 百度加固
- 腾讯乐固
- 通付盾
根据应用对安全等级的要求衡量成本~~
相关参考:
#©念茜
#©反注入