91 萝莉 [原创]2023腾讯游戏安全大赛-安卓赛谈决赛wp-Android安全-看雪-安全社区|安全招聘|kanxue.com
本文档是进行完有关分析之后的回往来忆, 是以可能有的场所的花教唆是被去除了再截图的, 函数名和数据结构被重定名了. 这决赛的沾污太恶心了91 萝莉,我无法作念到将代码规复, 是以完好意思手撕汇编作念的.
这一部分和预赛是一样的, il2cpp那块并莫得过多的加密, 已经和预赛一样从内存中将libil2cpp.so dump下来之后使用il2cppdumper得到对应的cs文献, 定位到MouseController__CollectCoin按序中, 找到偏移0x4652AC这里, 使用gg修改器将CMP W0, #0x3E8这条教唆修改为CMP W0, #0之后随便吃一个金币得到flag.
有了预赛的教导, 是以此次亦然将frida_server的二进制文献patch掉re.frida.server字符串, 而且使用./fs -l 0.0.0.0:2394号召切换监听端口, 为了保证万无一失, 将责任目次从tmp文献夹移到别的场所取, 这样一来就能够告捷过掉这一大类的检测.
然则亦然一样的, 除了文献检测和端口检测, libsec2023.so中还有针对代码段的crc检测, 使用findcrypt插件从so文献的特征中也能够发现. 不测的这里还看到了aes特征, 背面的算法也有可能使用到了aes算法, 仅仅说可能.
亦然同预赛一样, 关于crc检测一定是不隔断的读取代码段数据, 是以只需要对其代码段下一个硬件读写断点就能够定位到检测的要道点. 我依旧是使用rwProcMem形态中的内核硬件断点门径进行操作, 在libsec2023.so的内存区域中纵脱聘用一个地址, 如下图所示告捷定位到读取的要道点.
此时libsec2023.so的内存基址是0x7cecf00000. 不错定位到读取内存段的代码在libsec2023.so + 0x7d934处, 这里因为沾污方式的改造, 是以f5也不行和预赛一样将其规复出来, 因此只可稽查汇编代码.
这里因为被沾污了, 而且这里仅仅作念了读取内存的操作, 是以找不到稳妥的patch点, 此时稽查lr寄存器, 不错得到调用读取函数的复返的上一层地址是libsec2023.so + 0x7B300.
这里能够看到0x7B2FC的blr x8就是调用点, 读取完代码段的校验和之后复返值会存储在x0寄存器中, 因此不错按照此为脚迹往底下拉, 看到0x7B320处有一个cmp w0, w8. 之后一个b跳转到0x7AF00处
在0x7AF04这里会依据前边的cmp语句的着力对w8进行赋值, 而w8的值就会影响到之后的分支, 是以这就能够找到patch的要道点了, 用硬件断点器具下奉行断点稽查寄存器的数据不错发现平时历程中w0和w8的值应当是格外的, 是以要朝上crc检测则应该将cmp w0, w8语句改成mov w0, w8, 同期将csel w8, w9, w8, eq改成mov w8, w9. 试验中发现背面那句不改也不错, eq默许成立.
是以在frida的剧本中启动化中加入以下语句即可绝对过掉检测.
至此反调试就分析罢了, frida能够平时使用了.
比拟于预赛, 决赛的沾污进度愈加严重了, ida的伪代码功能绝对报废, 门径中函数的跳转和门径内分支语句一齐变成了寄存器辗转跳转, 关于函数跳转尚可使用unidbg这种模拟奉行的方式规复, 然则要求分支具有动态性, 是以很难规复且归. 是以我聘用了frida-trace日记静态分析 + frida hook动态的方式进行分析.
雷同先约略看了一下历程, 同预赛一样, 刚脱手会从libil2cpp.so中接收输入数字, 然后传入后续的算法奉行, 然青年景无意的token.
通过frida hook不错得知这里的跳转会跳转到libsec2023.so + 0x70E74.
上图的sub_94368就是加密算法的主体部分, v5跳转则会跳回libil2cpp.so + 0x465994, 参数v3是复返的int64值.
复返的值如果知足低32位等于token, 高32为0, 则开启mod. 不同于预赛, 这里终末并莫得其他校验, 是以算法的一齐终了都在libsec2023.so中.
来源假定输入的数字是666666, 对应的十六进制抒发是0xa2c2a. 先干涉sub_94368函数, 从这里脱手的统统代码都被严重沾污了, 截图为我部分设立之后的伪代码. 其中要知足strcmp着力一致之后才会干涉破裂对数算法之后的后续逻辑
在这个函数中主如果启动化了两个大数数组, 之后干涉sub_9e93c中进行某种运算, 其中第一个参数是输入的数字和0xffff00ffffff进行按位与运算的着力. 关于输入数字数字666666, 其筹算的着力是1db29b949927d377f0270e1161964bb0b9fc004f7125b6956d057e09a7c2fadf77df04bbcae93aa0000字符串, 之后将s2的字符串与前边启动化的某个数组使用strcmp函数进行比较, 经过hook得回发现该数组是一个恒定不变的字符串25f6b048b4f32e3ce9175bb64930f65101a706ae74988a4ec87b4d5ec7feb9223ab782bcf1ec9d7fee750. 刚脱手看到这个字符串思到了哈希, 然则具体是什么还需要干涉sub_9e93c函数稽查.
sub_9e93c函数来源会进行一系列启动化, 然后干涉sub_9F0A8函数和sub_9f704中, 使用frida hook也能够发现输入的数字是在终末奉行完sub_9f704出现了字符串. 理所应领先干涉sub_9f704望望这个字符串是怎样产生的, 稽查frida-trace的log能够发现其在某处脱手会每8个一组产生0, 一直产出了168个0之后才生成思看到的字符串.
而上头的阿谁br跳转则是干涉了sub_9FC3C这个函数
进去稽查发现这个函数终了的功能是将某个数字按照十六进制生成字符串, 不及8位补皆, 是往常边的00000000就是这样产生的, 经过hook发现最毕生成的一长串数字亦然在这里一组一组生成最终拼接而成. 经过详备的比对, 最终细目sub_9f704函数仅仅一个雷同于袒露层的函数, 筹算出的数字是在sub_9F0A8中生成出来的.
sub_9F0A8函数存在有限制流沾污, 使用OBPO插件去除沾污后能够得到这样伪代码, 其中凝视和函数称号是我经过无数hook与对应trace log比对后得到其对应功能后定名的.
这个函数最终终了的功能是关于输入数字x, 输出着力y = pow(x, 17) mod key, 其中key的值是已知的, 也就是前边启动化的某个数组之一, 经过hook后得到key为0x028a831a5bf4b902e95318e50c2075259f91094d08d84409e1b76eadfa0865d1278acc90fa7c6cf6acb375. 这个算法是破裂对数问题, y为已知的25f6b048b4f32e3ce9175bb64930f65101a706ae74988a4ec87b4d5ec7feb9223ab782bcf1ec9d7fee750, 其逆算法也就是求得输入数字x. 其中x的范围已知是和0xffff00ffffff按位与之后的着力, 那么最绵薄的逆算法就是爆破摆设.
在知足前边的strcmp要求之后, 门径奉行流会干涉到sub_99EF4中.
在上图中能够看到设立后伪代码, 主如果会启动化一些参数. 使用frida-trace对其进行trace能够看到一些奇怪的字符串
其中能看到PK, vm_main, builtin, PK是压缩包的magic标志, 有可能这里的br是奉行了解压缩操作, 回溯稽查这个PK的来源能够发现是sub_B59DC函数得回该地址的.
其中libsec2023.so + 0x10A698处就是压缩包的数据.
使用010editor将其手动索要出来, 灵通后不错发现里面存在两个文献a64.dat和a64.sig. 此处尚且知其具体含义, 不竭阅读背面的汇编代码, 稽查是怎样使用该数据的. 不出所料在0x96190近邻看到了这样一段汇编记载
其中x0是压缩包的二进制数据地址, x1为该压缩包二进制数据的长度, x2是a64.dat字符串, x3是某个数据. 使用ida干涉该函数sub_523DC不错发现并莫得被沾污. 那么约略率不是什么迫切的函数, 字据参数臆测应该是从安设包中索要a64.dat这个文献. 使用frida hook稽查参数和内存变化情况.
从上头的图中不错看到, 0x7cd3ee05d8这个地址的内存数据在经过sub_523DC之后被修改了, 其中前8个字节像一个指针, 后两个字节像是文献大小.
将该内存区域打印后和文献作念对比发现如实是该文献, 0x2a3亦然a64.dat的文献大小. 得知sub_523DC索要了a64.dat文献之后, 不竭往背面看汇编代码, 望望是怎样使用该文献的.
不错看到97da8中调用了sub_5A65C函数
这个函数是我分析完对结构体定名后的着力, 其主如果启动化了某个结构体, 将文献地址填入前8字节. 臆测是某种数据流的终了, 用于读取文献的信息. 在启动化完之后, 之后的分析应该是围绕这个结构体进行的.
不错看到这里调用了sub_5A7A8函数, 使用到了该结构体, 进ida稽查
其主要的功能是按照大端读取四个字节的int数字并复返.
从汇编平分析不错看出在977a8之后出现了字符串, 因此对其里面进行分析, 发现会调用sub_5AAD8函数, 而这个函数如实是读取某一块内存而且对字符串进行解密. 然后使用frida hook发现这里会产出这三个字符串: vm_main.img, __ff_11, __ff_12.
在上头这段汇编中0xb400007bef75a300是之前界说的结构体指针, x2参数很显着是某个比文献小的长度. 干涉sub_5AA78望望.
发现该函数的主邀功能是对文献的某一段本体复制到另一块内存区域当中, 对应到上头的调用, 那含义很显着就是从a64.dat文献的0x1b肇始, 长度为0x284的部分. 不竭跟进望望其是怎样使用这个区域的.
不错发现前边内存复制之后, 会随即使用到这块区域, 这是一个很显着的加解密操作, 其终了的操作是取第一个字节0x4和0x23异或得到着力0x27, 然后从正本的字节被替换为MEM[0x10A536 + 0x27]的值. 那么这个0x10A536偏移的区域很有可能是映射码表之类的东西. 不竭稽查背面的汇编不错发现尽然在背面的x8会渐渐递加, 并重叠这段操作, 也就是轮回对每个字节进行这样的操作. 那么不错望望这个码表解密之后是什么样的. 这里使用hook会变成门径卡死, 那么使用以下的python剧本静态解密一下望望是什么东西.
不错看到这块区域被解密出来了, 其中也能够看到vm_main字符串, 是以应该是莫得相当的.
时期和元气心灵原因背面的莫得分析完, 前边findcrypt插件发现了aes的特征, 是以也有可能背面用到了aes算法, 看字符串带vm字样也不甩掉使用了vm时间. 看汇编是确凿累
到此为止告捷得回了flag, 过掉了统统反调试使得frida能够平时责任, 之后静态分析加动态调试规复了破裂对数算法, 而且还给出了其逆算法.看汇编已经太累了, 说的确的这样高强度的沾污和前边的vm混打, 此次比赛难度真不小.
[防范]传递专科常识、拓宽行业东谈主脉——看雪讲师团队等你加入!91 萝莉