首先要确保你所使用的gdb和gdbserver是配对的,最好(或必须)是sdk内相同platform(api level)下的gdb和gdbserver。否则你使用的gdb可能与运行测试机上的gdbserver,因为协议不兼容,而不能正常调试。

gdb 连接后提示,"Argument to arithmetic operation not a number or boolean."

gdbserver 连接后提示,“Unable to get location for thread creation breakpoint: requested event is not supported."

这种情况下,gdb是没法正常使用的,你将会在后续的调试中,不同情况地收到”Remote 'g' packet reply is too long:"

因为这个问题可能会耗费掉了你不少的时间和注意力。这时候最好就是去将你使用的gdb配对的gdbserver从sdk放到测试机去使用。

在测试机中默认有一个远程调试服务程序/system/bin/gdbserver,如果有上面的情况出现,至少使用绝对路径下的你所安排的gdbserver。

参数传递方式:

在x86下,要清楚特殊的传参行为。android的x86 gcc对静态函数的传参规则是,前面两个参数分别应用%eax和%edx,第三个参数开始应用参数栈。而this指针不是我们熟知的vc下应用ecx,gun gcc应用%ebx,而ndk是应用%eax。

下面回到百度加固平台的libbaiduprotect.so逆向。

libbaiduprotect_x86.so是对目标app的dex进行了加固,并且它自身也是加壳了的。下面是以加壳方式存储文件和脱壳后运行在内存映像的dump对比。

壳程序一般都安排在elf格式文件的.init_array section,由linker加载时最先执行。linker有这样的执行流程:

dl_open -> do_open -> soinfo::CallConstructors

只要通过中断linker的soinfo::CallConstructors方法,就可以将加载动态库之初使用程序中断。

中断后,我们通过%eax查看this指针的对象内容,soinfo::CallConstructors是成员方法,指针的对象类型是soinfo,这个结构体包含了加载后section信息。

这个结构的第一个结构成员是不同gcc平台下的linker都一样的,so文件名,查看结果与我调试加载的库名一致,libbaiduproctect_x86.so。后面的结构组织,不同版本的linker各不相同。在这里我懒得去配对正确的版本代码,也就不去搞清它的结构。但是可以通过运行时映射信息,以及readelf查看到的section信息,清楚看到.init_array和.fini_array的section信息加载到soinfo结构了。.init_array section一共0x14字节加载在0xadfa5464。

本例中so映射在0xadf16000,.text段偏移0x2bc0,也就说在0xadf8bc0。而JNI_OnLoad函数偏移量是0x3060,位于0xadf19060。

不用翻查代码,通过查看.init_array段0x14字节的内容,可以大至清楚这个段约等同一个函数指针数组,以空指针结尾。第一个函数指针位于.text的末端,后面三个函数指针位于.text段的开端。linker将按顺序去执行这四个函数。也就是说脱壳程序的其中一个入口就在这四个函数中。

现在我们的程序中断在soinfo::CallConstructors的入口,还没有执行so文件中任何的程序,我们如果反汇编JNI_OnLoad地址的话,就只能得到无法解释的加壳内容。

而so文件.init_array段的函数指针指向的函数则是怎么也就能是加壳的,或者至少保证前面的一个函数可以被执行脱壳出后面的函数。一般地,程序在对代码段进行脱壳,都必须要修改该段的内存访问属性,从只读变为可写才能将脱壳后的代码更新上去,也就说我们只要中断mprotect同样也会将脱壳程序中断到。

libbaiduprotect_x86.so并没有对所有.text段的代码进行脱壳,只是脱壳了一部分,并且在这阶段创建了6个线程,其中包含了反调试的监控线程。由于现在程序的运行被一步步掌控,所以可以将这些线程冻结然后进行后面的调试。

在这里我将被部分脱壳后的so映像dump出来,尝试用ida来静态分析,结果发现ida对x86指令支持并不好,一些原本在gdb能够反汇编的代码,不ida却识别不了。

逆向libbaiduprotect(二)的更多相关文章

  1. 逆向libbaiduprotect(四)

    百度加固libbaiduprotect.so自身对只读字符串进行了加密保护,防止成为破解和逆向的切入口.一般地认为,只要找出这个解密算法就可以对.rodata段的只读字符串进行破解,从而窥探程序的意图 ...

  2. OD 实验(二十一) - 对反调试程序的逆向分析(二)

    程序: 运行程序 点击“Verify” 关闭该程序,启动 OD 再运行程序 逆向: 用 OD 载入程序 按 F8 往下走 执行完这个 call 指令就弹出了对话框 这个 call 指令调用了 Dial ...

  3. 逆向libbaiduprotect(三)- 移植python操作dalvik虚拟机c++函数,配合gdb控制程序运行流程

    python编译移植到测试机,并且移植ctypes模块.利用ctypes代替c程序,利用dalvik内部c++函数,在运行过程中手动命令操控dalvik虚拟机,并结合gdb进行调试.绕过zygote和 ...

  4. Python逆向(二)—— pyc文件结构分析

    一.前言 上一节我们知道了pyc文件是python在编译过程中出现的主要中间过程文件.pyc文件是二进制的,可以由python虚拟机直接执行的程序.分析pyc文件的文件结构对于实现python编译与反 ...

  5. 从零开始Android逆向教程(二)——什么是Xposed

    前言在阅读本文之前,假设你的手机已经root,并且已经成功安装好了 XposedInstaller. Xposed是什么?       Xposed 是一个 Android 平台上的动态劫持框架,通过 ...

  6. x32下PsSetLoadImageNotifyRoutine的逆向

    一丶简介 纯属兴趣爱好.特来逆向玩玩. PsSetLoadImageNotifyRoutine 是内核中用来监控模块加载.操作系统给我们提供的回调. 我们只需要填写对应的回调函数原型即可进行加监控. ...

  7. x32下逆向 PsSetCreateProcessNotifyRoutine 进程钩子

    目录 一丶前言 二丶逆向过程 1.windbg挂载 win7 32位.定位到函数反汇编位置 2.逆向 PspSetCreateProcessNotifyRoutine 3.逆向 ExReference ...

  8. Python逆向(一)—— 前言及Python运行原理

    一.前言 最近在学习Python逆向相关,涉及到python字节码的阅读,编译及反汇编一些问题.经过长时间的学习有了一些眉目,为了方便大家交流,特地将学习过程整理,形成了这篇专题.专题对python逆 ...

  9. Mysql高可用

    一.二进制日志 二进制日志,记录所有对库的修改,如update.修改表结构等等 需要开启二进制日志的原因: 1.主从复制都是通过二进制日志进行.主库写二进制日志,传输到从库,从库replay二进制日志 ...

随机推荐

  1. asp.net core mvc中自定义ActionResult

    在GitHub上有个项目,本来是作为自己研究学习.net core的Demo,没想到很多同学在看,还给了很多星,所以觉得应该升成3.0,整理一下,写成博分享给学习.net core的同学们. 项目名称 ...

  2. 开源造轮子:一个简洁,高效,轻量级,酷炫的不要不要的canvas粒子运动插件库

    一:开篇 哈哈哈,感谢标题党的莅临~ 虽然标题有点夸张的感觉,但实际上,插件库确实是简洁,高效,轻量级,酷炫酷炫的咯.废话不多说,先来看个标配例子吧: (codepen在线演示编辑:http://co ...

  3. Vue系列---源码调试(二)

    我们要对Vue源码进行分析,首先我们需要能够对vue源码进行调式(这里的源码调式是ES6版本的,不是打包后的代码),因此首先我们要去官方github上克隆一份vue项目下来,如下具体操作: 1. cl ...

  4. git jenkins 基本部署之git远程仓库

    1.git远程仓库如何使用? 实战一.如何将本地仓库与远程Gitee进行关联?        1.注册gitee        2.创建一个远程仓库?        3.配置使用远程仓库       ...

  5. Git 项目提交新仓库

    提示:进入项目文件操作 步骤: 1.git init   ----------初始化git仓库 2.git remote add origin 你的项目地址  ------------------如: ...

  6. javascript函数前面加~波浪线的作用

    如下,在函数前加上波浪号,其作用是把函数声明转换为表达式,这样就可以直接运行. ~function sayHello(){ console.log('hello'); }() 测试: 在console ...

  7. K8s 还是 k3s?This is a question

    本文来自:Rancher Labs 自k3s问世以来,社区里有许多小伙伴都问过这样的问题"除了中间的数字之外,k3s和K8s的区别在哪里?","在两者之间应该如何选择?& ...

  8. 阿里云和微软共同开源的 OAM 对 Kubernetes 开发人员意味着什么?

    上周,微软和阿里巴巴共同推出了开放应用模型(OAM),用于定义部署在任何地方的应用模型的一种规范.Rudr是Microsoft基于Kubernetes环境的OAM标准实现. 我用了一个周末来了解OAM ...

  9. 【阿里云IoT+YF3300】8.物联网设备用户脚本开发

    除了我们必须熟悉的网页脚本,比如JavaScript.其实在工业自动化中,组态软件是必备脚本的,只是有的脚本语言风格类似C或类似Basic而已.比如昆仑通泰的组态屏中的组态软件.通过安装组态软件可以简 ...

  10. MIT线性代数:19.行列式和代数余子式