上一次 学习了如何制作金手指文件。不过那个例子是改的游戏数据而非代码,这次学习如何修改游戏代码。
查找游戏数据
还是以塞尔达传说:旷野之息
为例。游戏信息:
1 | TID:01007EF00011E000 |
这次修改精力值,因为精力值不显示具体的数字,所以需要用模糊搜索。Breeze 中的模糊搜索功能是 Memory Dump。
模糊搜索过程就不细讲了,无非就是让林克跑动一下让精力值不停变化、查找,如此循环。。。
最后确认精力数据地址:
1 | 当前精力:heap + A74F9EDC |
数据类型为float
,占 4 字节。测试发现每一圈精力值对应值是 1000。那么在这个游戏中精力最大为三圈,也就是 3000。
虽然我们可以锁定这个值达到无限精力的目的,但是直接改数据会造成精力圈闪烁,游戏体验不好。
我期望的是跑步时不会出现精力圈,也就是修改游戏逻辑,让跑步所消耗的精力为零。
查找数据写入位置
利用 Breeze 的断点功能,对精力值位置 heap + A74F9EDC
处设置写入断点
回到游戏,跑动一下减少精力值,再切回修改器。发现一处写入位置 main + 0x00F70024
虽然 Breeze 中也可以看到汇编代码,但是远不如 IDA 显示的多,操作起来也不方便。
所以我们需要到 IDA 中来查看相关代码。
提取游戏 NSO 文件
NSO 文件类似于 Windows 系统上的 EXE/DLL 文件,其中包含着游戏逻辑代码。我们需要提取出来然后在 IDA 中查看它。
准备工具:
- 游戏文件管理工具 NSGame Manager。用于提取游戏NSO文件。
- IDA 插件 SwitchIDAProLoader。用于静态分析NSO文件。
在 NSGame Manager 中加载游戏文件(nsp、xci),找到版本最新且 ROM 为 UPD 的包(对于没有补丁的游戏那就只有一个 ROM 为 APP 的包),选择右侧“工具”页面,然后选择容量最大的 NCA,点击“提取并解包NCA”即可,如图:
会提取出一个没有扩展名的名为main
的文件,它就是 NSO 文件。用 SwitchIDAProLoader 插件加载它
分析程序
前面分析发现写入精力的地方是 main + 0x00F70024
。我们在 IDA 中来到偏移 0x00F70024
的地方。可以看到汇编代码和 Breeze 捕捉到的地方是一样的,说明找对地方了。
此时用 IDA 强大的 F5 还原成伪代码
把这条语句 NOP
掉就可以达到锁定精力值的目的了。但有个不算是问题的问题,精力值虽然不会减少,但也不会增加,而我希望可以恢复精力,而不减少精力。
接着就是在 IDA 中静态分析这个函数,同时在 Breeze 中修改指令。来回几轮测试后找到关键语句:
精力是从这个地址取的,是一个固定的地址
1 | qword_7102CA1140 + 0xA4 |
所以,精力的金手指格式就是
1 | [main + 2CA1140] + 0xA4 |
写入精力值这一行代码在偏移 0x00F6FF50
处,看看汇编代码
将汇编改为 fmov s8, s0
可以避免进行减法操作
现在可以制作金手指了。注意,金手指中的机器码要用大端方式。可以在 ARM to HEX Converter 这样的网站中计算转换后的机器码。
勾选右上角,以大端方式转换。
最终金手指文件如下:
1 | [精力不减 开] |