首页 > 其他分享 >学习笔记-hook和主动调用

学习笔记-hook和主动调用

时间:2022-11-11 09:22:37浏览次数:48  
标签:调用 console addr lib args 笔记 hook myfirstjniJNI log

用户代码 native hook

  1. 静态注册函数参数,返回值打印和替换
  2. 调用栈
  3. 主动调动
  4. 符号hook == 偏移hook
  5. 枚举并保存结果

0x01 修改返回值以及参数和主动调用

  1. 修改返回值
    修改的原则本质上还是根据开发的套路去走,利用jni开发api去做,这里也是有文档可以进行查询的,https://github.com/frida/frida-java-bridge/blob/master/lib/env.js, 这里就可以直接搜索,ctrl+f直接搜就完事了,当然前提得先获取env,还是上次课的app,主要是修改返回值,上次那个函数的返回值是jstring,那么我们也需要去构造一个jstring对象出来,然后进行一波返回
    js代码:

function hook_nativelib()
{
var native_lib_addr=Module.findBaseAddress("libnative-lib.so");
console.log("native_lib_addr ->",native_lib_addr);
var myfirstjniJNI=Module.findExportByName("libnative-lib.so","Java_com_example_demoso1_MainActivity_myfirstjniJNI");
console.log("myfirstjiniJNI addr ->",myfirstjniJNI);
Interceptor.attach(myfirstjniJNI,{
onEnter:function(args){
console.log("Interceptor.attach myfirstjniJNI args:",args[0],args[1],args[2]);
console.log("jstring is",Java.vm.getEnv().getStringUtfChars(args[2],null).readCString());
},onLeave:function(retval){
//console.log("Interceptor.attach myfirstjniJNI retval",reval);
var newRetval=Java.vm.getEnv().newStringUtf("YenKoc fucking crazy");
retval.replace(newRetval);
}
})
}
function main1()
{
hook_nativelib();
}
setImmediate(main1);

  1. 修改参数值 没啥好说了,和上面差不多,用jni开发的角度去想

function hook_nativelib()
{
var native_lib_addr=Module.findBaseAddress("libnative-lib.so");
console.log("native_lib_addr ->",native_lib_addr);
var myfirstjniJNI=Module.findExportByName("libnative-lib.so","Java_com_example_demoso1_MainActivity_myfirstjniJNI");
console.log("myfirstjiniJNI addr ->",myfirstjniJNI);
Interceptor.attach(myfirstjniJNI,{
onEnter:function(args){
console.log("Interceptor.attach myfirstjniJNI args:",args[0],args[1],args[2]);
console.log("jstring is",Java.vm.getEnv().getStringUtfChars(args[2],null).readCString());
var newArgs2=Java.vm.getEnv().newStringUtf("I'm new Args");
args[2]=newArgs2;
},onLeave:function(retval){
//console.log("Interceptor.attach myfirstjniJNI retval",reval);
var newRetval=Java.vm.getEnv().newStringUtf("YenKoc fucking crazy");
retval.replace(newRetval);


}
})
}
function main1()
{
hook_nativelib();
}
setImmediate(main1);

不知道为什么一hook参数就crash了,lj app(吐槽
3. 主动调用 - 核心思想就是先在so中找到对应的地址,这是关键,没有地址一切都是扯淡,这里暂时还没用到偏移,都是通过objection的找到so的导出函数被符号修饰后的符号名,直接通过frida api得到的结果。至于手法就直接记住就好了

function hookandinvoke_add()
{
var native_lib_addr=Module.findBaseAddress("libnative-lib.so");
console.log("native_lib_addr ->",native_lib_addr);
var r0add_addr=Module.findExportByName("libnative-lib.so","_Z5r0addii");
console.log("r0add addr ->",r0add_addr);
Interceptor.attach(r0add_addr,{
onEnter:function(args){
console.log("x->",args[0],"y->",args[1]);

},onLeave:function(retval)
{
console.log("retval is ->",retval);

}
})
var r0add=new NativeFunction(r0add_addr,"int",["int","int"]);
var r0add_result=r0add(50,2);
console.log("invoke result is",r0add_result);

}
function main1()
{
//hook_nativelib();
hookandinvoke_add();
}
setImmediate(main1);

  • hook native函数
    这里的参数发现都是jstring等等的,这些其实都是指针,我们如果需要主动调用的话,也需要像jni开发一样构造出jstring指针,就像上文做的一样,不过这里有点骚的就是在hook native函数时,将本来传入的参数,再传入主动调用的函数,这样就不需要这么麻烦了

unction hook_nativelib()
{
var native_lib_addr=Module.findBaseAddress("libnative-lib.so");
console.log("native_lib_addr ->",native_lib_addr);
var myfirstjniJNI=Module.findExportByName("libnative-lib.so","Java_com_example_demoso1_MainActivity_myfirstjniJNI");
console.log("myfirstjiniJNI addr ->",myfirstjniJNI);
var myfirstjniJNI_invoke=new NativeFunction(myfirstjniJNI,"pointer",["pointer","pointer","pointer"]);
Interceptor.attach(myfirstjniJNI,{
onEnter:function(args){
console.log("Interceptor.attach myfirstjniJNI args:",args[0],args[1],args[2]);
console.log("jstring is",Java.vm.getEnv().getStringUtfChars(args[2],null).readCString());
//var newArgs2=Java.vm.getEnv().newStringUtf("I'm new Args");
//args[2]=newArgs2;
console.log("myfirstjniJNI_invoke result:",myfirstjniJNI_invoke(args[0],args[1],args[2]));
},onLeave:function(retval){
//console.log("Interceptor.attach myfirstjniJNI retval",reval);
var newRetval=Java.vm.getEnv().newStringUtf("YenKoc fucking crazy");
retval.replace(newRetval);


}
})
}
function hookandinvoke_add()
{
var native_lib_addr=Module.findBaseAddress("libnative-lib.so");
console.log("native_lib_addr ->",native_lib_addr);
var r0add_addr=Module.findExportByName("libnative-lib.so","_Z5r0addii");
console.log("r0add addr ->",r0add_addr);
Interceptor.attach(r0add_addr,{
onEnter:function(args){
console.log("x->",args[0],"y->",args[1]);

},onLeave:function(retval)
{
console.log("retval is ->",retval);

}
})
var r0add=new NativeFunction(r0add_addr,"int",["int","int"]);
var r0add_result=r0add(50,2);
console.log("invoke result is",r0add_result);

}
function main1()
{
hook_nativelib();
//hookandinvoke_add();
}
setImmediate(main1);

0x02 调用栈

console.log("CCCryptoCreate called from:\n"+Thread.backtrace(this.context,Backtracer.ACCURATE).map(DebugSymbol.fromAddress).join("\n")+'\n');

这行代码加入到hook的代码中去,就可以打印出调用栈 # 0x03 replace 这玩意其实就相当于java层中的hook,上面那个主动调用的话,其实就是this.xx的形式

function hook_replace()
{
var native_lib_addr=Module.findBaseAddress("libnative-lib.so");
console.log("native_lib_addr ->",native_lib_addr);
var myfirstjniJNI=Module.findExportByName("libnative-lib.so","Java_com_example_demoso1_MainActivity_myfirstjniJNI");
console.log("myfirstjiniJNI addr ->",myfirstjniJNI);
var myfirstjniJNI_invoke=new NativeFunction(myfirstjniJNI,"pointer",["pointer","pointer","pointer"]);
Interceptor.replace(myfirstjniJNI,new NativeCallback(function(args0,args1,args2){
console.log("Interceptor.attach myfirstjniJNI args:",args0,args1,args2);

return Java.vm.getEnv().newStringUtf("new Retval from frida");

},"pointer",["pointer","pointer","pointer"]));


}

肉丝说不常用,但是我感觉改返回值啥的,还可以把 # 0x04 枚举出所有模块的所有导出符号(静态注册的才行)

function EnumerateAllExports()
{
var modules=Process.enumerateModules();
//print all modules
//console.log("Process.enumerateModules->",JSON.stringify(modules));
for(var i=0;i<modules.length;i++)
{
var module=modules[i];
var module_name=modules[i].name;
var exports=module.enumerateExports();
console.log("module.enumerateeExports",JSON.stringify(exports))
}
}

 

 

 

点击关注,共同学习!
[安全狗的自我修养](https://mp.weixin.qq.com/s/E6Kp0fd7_I3VY5dOGtlD4w)


[github haidragon](https://github.com/haidragon)


https://github.com/haidragon

标签:调用,console,addr,lib,args,笔记,hook,myfirstjniJNI,log
From: https://www.cnblogs.com/haidragon/p/16879531.html

相关文章

  • 学习笔记-JNI框架层的Hook利用
    系统框架nativehookJNI函数符号hookJNI函数参数、返回值打印和替换动态注册JNI_OnloadhookRegisterNativesjnitrace引入一个例子,hookGetStringUTFChars这个jn......
  • 学习笔记-libc框架层的Hook利用
    系统框架层nativehooklibc函数符号hooklibc函数参数、返回值打印和替换主动调用libc读写文件hooklinkerdlopenfrida-trace引入例子,先hookpthread这个libc函......
  • Vue3学习笔记(五)——路由,Router
    一、前端路由的概念与原理1.1.什么是路由路由(英文:router)就是对应关系。1.2.SPA与前端路由SPA指的是一个web网站只有唯一的一个HTML页面,所有组件的展示与切换都......
  • 方滨兴院士讲座笔记
    安全和技术是伴生,没有技术,就没有安全问题人工智能在安全领域的四种表现形态深度伪造:利用人工智能仿生,通过像人脸识别那样的检测,或者AI换脸智能防御:人工智能预测攻击后......
  • Head First Java 读书笔记
    第11章:异常处理如果你把有风险的程序代码包含在try/catch块中,那么编译器会放心很多。try/catch块会告诉编译器你确实知道所调用的方法会有风险,并且也已经准备好要处理......
  • 通过调用函数判断一个数是否为质数
    /*//1.书写判断某个数是否为质数的方法,将这个方法封装在一个函数里    functionodd(a){      count=0      for(vari=1;i<......
  • 学习笔记 之 简单了解有关 CSS 那点事儿
    LZ-Says:调整心态,多读书,丰富内心,提升个人文化底蕴。前言前几天,初步了解了下HTML相关的知识点,在学习回顾时,还好,大部分都在,只是新增了一些其他内容,例如自适应等等。上手......
  • C语言学习笔记---sizeof关键字和strlen函数
    sizeof和strlen在C语言中常用来计算字符大小和长度,在应用中却有着本质的区别。 sizeof是C语言中的关键字,其作用是返回一个对象或类型所占的内存字节数。使用方式为:int......
  • MIT6.S081笔记:Lab Xv6 And Unix Utilities
    关于MIT6.S081这门课的前身是MIT著名的课程6.828,MIT的几位教授为了这门课曾专门开发了一个基于x86的教学用操作系统JOS,被众多名校作为自己的操统课程实验。但随......
  • 【学习笔记】AC自动机
    AC自动机其实我将近三个月前就准备写这个并且随笔都建好了,但是一直咕咕到现在才写。其实记忆力好的同学应该意识到这篇其实8月份已经发过了,这次只是更新了一下发布日期而......