安卓逆向学习笔记(5) - 在JNI_Onload 函数处下断点避开针对IDA Pro的反调试

本文介绍如何使用IDA Pro在JNI_Onload及init_array处下断点,以避开针对IDA Pro的反调试措施。通过实例展示了从配置调试信息到触发断点的具体步骤。

转:http://blog.youkuaiyun.com/pengyan0812/article/details/43991983


在上篇文章中,我们介绍了如何利用IDA Pro来动态调试so文件。在移动安全领域有攻就有防,为了防止apk中的so文件被动态调试,开发者往往会使用一些反调试手段来干扰黑客的动态调试。

其中最常见的就是在so文件中检测TracerPid值,详情请见这篇博客:爱加密脱壳

本文以2015阿里巴巴移动安全大赛中的第二道题为例,IDA Pro版本为6.5 。

这里只介绍如何通过在JNI_Onload下断点避开反调试,而具体的解题步骤请看鬼哥的教程:MSC阿里比赛第二题详解

(0)先将libcrackme.so拖入到IDA Pro中进行静态分析,在JNI_Onload函数上下断点,如图1所示:


图1 静态分析libcrackme.so文件 在JNI_Onload函数处下断点


(1) 执行android_server,如图2所示:


图2  执行android_server


另外再开一个命令提示符,输入以下命令,执行端口转发,如图3所示:


图3  执行端口转发


(2) 在debug模式下启动apk,即使用am命令启动apk并进行调试。如图4所示:

图4 使用am命令启动apk


(3)IDA进行附加进程
回到之前静态分析libcrackme.so的IDA界面单击Debugger -> Process options 配置调试信息,这里只需配置hostname为localhost,其余的保持默认设置即可。如图5所示:

图5 配置process options


Debugger options:

                                             



单击Debugger -> Attach to process进行附加进程的操作,如图6所示:


图6 附加进程


(4)打开DDMS,查看jdb对应的调试端口。如图7所示:


图7 打开DDMS查看jdb的调试端口


(5)打开命令提示符,输入以下命令,进行jdb调试。如图8所示:


图8 使用jdb进行调试


(6)回到之前静态分析libcrackme.so的IDA界面 执行F9命令。在接下来弹出的对话框中,一律点击“cancel”按钮,待弹出图9所示的对话框后,选择same按钮。


图9 ida提示程序所调试的so文件是否与当前静态分析的so文件一样

(7)然后继续运行程序就会触发之前在JNI_Onload处所下的断点,如图10所示:


图10 JNI_Onload函数断点触发成功






 

ida动态调试so,在init_array和JNI_ONLOAD处下断点


转:http://blog.youkuaiyun.com/jltxgcy/article/details/50598430

   本文涉及到的apk,请在github下载https://github.com/jltxgcy/AliCrack/AliCrackme_2.apk

   0x00

    如何在JNI_ONLOAD下断点,参考安卓逆向学习笔记(5) - 在JNI_Onload 函数处下断点避开针对IDA Pro的反调试。最好使用模拟器调试,确保 Attach to process后,对应进程在DDMS中出现小红蜘蛛。

    下面将如何在init_array下断点,首先要找到so的init_array端,把so拖入ida,然后按Crtl+s,会出现该so的所有段。如下:

     

    进入.init_array,如下:

    

   其中sub_2378就是init_array的代码。

   

   我们在这里下断点,具体调试的步骤和在JNI_ONLOAD下断点调试是一样的,参考安卓逆向学习笔记(5) - 在JNI_Onload 函数处下断点避开针对IDA Pro的反调试。网上有很多其他方法在init_array下断点,例如Android安全–linker加载so流程,在.init下断点。我还是觉得上面的方法比较方便。

   调试时使用jdb -connect com.sun.jdi.SocketAttach:port=8700,hostname=localhost,有时会报如下错误:


    此时,我们先观察DDMS。


    使用jdb -connect com.sun.jdi.SocketAttach:port=8622,hostname=localhost即可。



### 如何在 IDAJNI_OnLoad 函数 #### 定位 JNI_OnLoad 函数 为了定位 `JNI_OnLoad` 函数,可以利用已知的偏移量来计算其实际地址。对于给定的例子,如果 `libcrackme.so` 文件中的 `JNI_OnLoad` 函数相对于起始位置有固定的偏移,则可以通过简单的加法运算找到该函数的具体地址[^3]。 例如,假设 SO 文件加载基址为 AA238000H 并且 `JNI_OnLoad` 的 RVA (Relative Virtual Address) 是 00001B9CH, 那么真实的内存地址将是: ```assembly AA238000H + 00001B9CH = AA239B9CH ``` 一旦获得了这个确切的位置,在 IDA Pro 中就可以通过按 G 键并输入上述地址来进行导航;接着使用 F2 设置断点以便于后续调试操作。 #### 动态调试准备 为了让动态调试更加顺利,建议先让应用于等待状态直到连接上外部调试工具再继续运行。这通常涉及到修改 Android 应用启动参数使其支持远程调试模式[^4]。具体做法是在命令行中执行如下指令: ```bash adb shell am start -D -n com.example.app/.MainActivity ``` 这里的 `-D` 参数指示系统暂停应用程序直至有一个合适的调试器被挂载上去为止。 #### 调试过程中注意事项 值得注意的是,尽管 `JNI_OnLoad` 常用于初始化 Java Native Interface 扩展功能,但它并非总是最先被执行的部分。实际上,在某些情况下,操作系统可能会优先调用 ELF 文件内的 `.init` 或者 `.init_array` 段里的其他代码片段[^2]。这意味着仅依赖于 `JNI_OnLoad` 来部署保护机制可能不够安全可靠,开发者应当考虑更全面的安全策略。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值