声明:文中所涉及的技术、思路和工具仅供以安全为目的的学习交流使用,任何人不得将其用于非法用途给予盈利等目的,否则后果自行承担!
下载地址:https://github.com/DERE-ad2001/Frida-Labs/tree/main/Frida 0xB
预备知识
x86指令集的frida使用模板
var writer = new X86Writer(<address_of_the_instruction>);
try {
// Insert instructions
// Flush the changes to memory
writer.flush();
} finally {
// Dispose of the X86Writer to free up resources
writer.dispose();
}
实例化 X86Writervar writer = new X86Writer(<address_of_the_instruction>);
创建一个X86Writer实例,指定要修改的指令的地址。这将设置写入器对指定的内存位置进行操作。
插入指令try { /* Insert instructions here */ }
在try块内,我们可以插入或修改x86 指令。X86Writer实例插入x86 指令的不同方法。
刷新更改writer.flush();
插入指令后,我们调用 flush方法来将更改应用到内存中,以确保指令被写入存储单元中。
清除finally { /* Dispose of the X86Writer to free up resources */ writer.dispose(); }
finally
块用于确保正确清理X86Writer资源。调用dispose
释放X86Writer实例的资源。
x86writer
https://frida.re/docs/javascript-api/#x86writer
arm64writer
https://frida.re/docs/javascript-api/#arm64writer
解题
这个实验的主要目标是利用rida引入临时补丁指令。
安装后,打开
点击按钮没有反应,查看jadx的反编译
找到getFlag函数,是native,在so中
根据System.loadLibrary找到so的名称 frida0xb.so
static {
System.loadLibrary("frida0xb");
}
IDA分析
搜索函数 getFlag
F5是空的
查看控制流
loc_1532C 直接跳到函数最后,没有执行中间的部分
控制流中出现了永假条件跳转
分析之后,可以得出,解下的目标是 patch B.NE loc_1532C
/*
* hook 加载so的函数,
* */
function hook_dlopen() {
var android_dlopen_ext = Module.findExportByName(null, "android_dlopen_ext");
Interceptor.attach(android_dlopen_ext, {
onEnter: function (args) {
var so_name = args[0].readCString();
if (so_name.indexOf("libfrida0xb.so") >= 0) this.call_hook = true;
}, onLeave: function (retval) {
if (this.call_hook) hook();
}
});
}
function hook(){
var adr = Module.findBaseAddress("libfrida0xb.so").add(0x15248); // Addres of the b.ne instruction
Memory.protect(adr, 0x1000, "rwx");
var writer = new Arm64Writer(adr); // ARM64 writer object
var target = Module.findBaseAddress("libfrida0xb.so").add(0x1524c); // Address of the next instruction b LAB_00115250
// console.log(hexdump(adr))
try {
// writer.putNop();
writer.putBImm(target); // Inserts the <b target> instruction in the place of b.ne instruction
writer.flush();
console.log(`Branch instruction inserted at ${adr}`);
} finally {
writer.dispose();
}
// console.log(hexdump(adr))
}
function main(){
Java.perform(function (){
hook_dlopen();
})
}
setTimeout(main);
writer.putBImm(target); // 在指定位置写入地址为target的指令
B loc_15250 覆盖了 B.NE loc_1532C
通过打印内存的hexdump可以看到
还有一种是通过writer.putNop();写入nop,让程序继续往下执行从而跳转
/*
* hook 加载so的函数,
* */
function hook_dlopen() {
var android_dlopen_ext = Module.findExportByName(null, "android_dlopen_ext");
Interceptor.attach(android_dlopen_ext, {
onEnter: function (args) {
var so_name = args[0].readCString();
if (so_name.indexOf("libfrida0xb.so") >= 0) this.call_hook = true;
}, onLeave: function (retval) {
if (this.call_hook) hook();
}
});
}
function hook(){
var adr = Module.findBaseAddress("libfrida0xb.so").add(0x15248); // Addres of the b.ne instruction
Memory.protect(adr, 0x1000, "rwx");
var writer = new Arm64Writer(adr); // ARM64 writer object
var target = Module.findBaseAddress("libfrida0xb.so").add(0x1524c); // Address of the next instruction b LAB_00115250
// console.log(hexdump(adr))
try {
writer.putNop();
// writer.putBImm(target); // Inserts the <b target> instruction in the place of b.ne instruction
writer.flush();
console.log(`Branch instruction inserted at ${adr}`);
} finally {
writer.dispose();
}
// console.log(hexdump(adr))
}
function main(){
Java.perform(function (){
hook_dlopen();
})
}
setTimeout(main);
1f 20 03 d5 就是 nop
检查 log日志,可以看到打印了flag
参考链接
https://bbs.kanxue.com/thread-280812.htm#msg_header_h2_4
https://github.com/DERE-ad2001/Frida-Labs/blob/main/Frida 0xB/Solution/Solution.md
往期推荐
价值$5,825赏金的tomcat信息泄露(CVE-2024-21733)
代码审计 | API批量分配导致的普通用户垂直越权到admin
原文始发于微信公众号(进击的HACK):frida patch so中指令
- 左青龙
- 微信扫一扫
- 右白虎
- 微信扫一扫
评论