1.前言之前介绍了很多破解相关的文章。在这个过程中,我们难免会遇到一些反调试的策略,当时我只是简单介绍一下如何解决反调试。其实我去年介绍过一篇关于Android安全逆向保护之战的文章:Android安全逆向保护分析;那么本文将详细总结。现阶段流行几种反调试方案。2、反调试方案分析第一种:先占坑,自己添加代码很简单,在so中添加这行代码即可:ptrace(PTRACE_TRACEME,0,0,0);其中,PTRACE_TRACEME表示:本进程被父进程跟踪的其他进程阻塞。父进程应该想要跟踪子进程。一般一个进程只能附加一次。我们在破解调试的时候,会附上需要调试的进程。如果我们先占坑,父进程自己附着,那么后面追加调试就会失败。.添加这段代码,运行后看看效果:我们都知道,在进行crack动态调试时,附加进程的状态文件中的TracerPid字段就是被调试进程的pid。这里我们运行程序,查看进程对应的状态文件,发现TracerPid值是进程的父进程的pid值。那么后面如果有进程想附加调试,就会失败。这种方法启动有一定的调试效果,但也不是绝对安全的。后面会讲解决这个反调试方案。第二种:签名验证签名验证其实在准备中不被认为是一种反调试方案,但它也是一种安全保护策略。我会在这里提到它。签名验证现在一般都有很多用处,目的就是为了防止重复。二次打包一般有两种解决方案:***:直接做本地保护,发现签名不一致直接退出应用。第二种:在请求参数中携带签名信息参与加密,服务端进行签名校验,校验失败则返回错误数据。这两种方式都不是最安全的保护方式,因为只要有签名验证逻辑,就可以在本地进行过滤。在之前的几篇文章中,我都介绍过如何过滤这种签名验证方式。不知道的同学可以看看:破解Android中某个应用的签名验证;而对于服务器签名验证和签名校验等的文章,后面会单独介绍。第三种方法:Debugstatuscheck这种方法纯粹是基于Android中的api。有两种方法:***:检查应用是否属于debug模式,直接调用Android中的flag属性:ApplicationInfo.FLAG_DEBUGGABLE来判断是否属于debug模式:这个其实是为了防止破解者反编译应用为了调试应用程序。在AndroidManifest.xml中添加:android:debuggable属性值并设置为true。然后就可以调试了。添加该属性后,我们可以使用dumpsyspackage[packagename]命令查看调试状态:这样我们就可以查看应用程序ApplicationInfo的flag字段是否可调试。不过这个方法并不完美,后面会介绍如何解决这个反调试问题。第二:检查应用程序是否处于调试状态。这个也是通过系统的一个api来判断的:android.os.Debug.isDebuggerConnected();这是判断当前应用程序是否被调试。我们添加这段代码后,按照上篇文章:取下360加固保护壳,有一个jdb连接操作的步骤:jdb-connectcom.sun.jdi.SocketAttach:hostname=127.0.0.1,port=8700,当连接成功后,这个方法会返回true,这时我们就可以通过这个api来判断当前应用是否处于调试状态,进行反调试操作。但是这个方法并不完美,后面会介绍如何解决这个反调试问题。第四种:循环检查端口我们之前在破解反向的时候,需要用到一个强大的工具,那就是IDA。在使用IDA的时候,我们知道需要在设备中启动android_server进行通信,那么这个启动会默认占用端口。23946:我们可以查看设备的tcp端口使用情况cat/proc/net/tcp:5D8A转换成十进制为23946,uid为0,因为我们以root运行android_server,所以uid必须为0。所以我们可以使用端口检查方法来执行反调试策略。当然,这种方法并不完美。后面会详细介绍如何解决这样的反调试方法。第五种方法:循环检查TracerPid值在第一种方法中,我们简单介绍过,如果应用程序被调试,它的TracerPid值就是调试进程的pid值,而在使用IDA进行调试时,需要在启动时device端的android_server进行通信,那么调试的进程会被attach,这个是android_server进程的pid值:查看android_server的pid值:所以我们可以在我们应用的native层加一个循环来查看自己如果status中TracerPid字段的值为非0或者非自己进程的pid(如果采用第一种方案,这里还需要一个filter);那么它被认为是被额外调试的。当然,这里还有一个解决方案,就是查看进程列表中是否存在android_server进程,但是这个方法并不完美,后面会详细介绍这个反调试方案是怎么解决的。3、反调试方案总结下面简单的几句总结一下这些方案:***,自己附上进程,先占坑,ptrace(PTRACE_TRACEME,0,0,0)!二、不可或缺的签名验证选择,本地验证和服务器验证是双管齐下的!三、利用系统api判断应用调试状态和调试属性,最基本的保障!四、轮训查看android_server调试端口信息和进程信息,有效保护IDAWay!第五,轮训是检查自身状态下TracerPid字段值,防止其他进程额外调试的有效方式!以上简单介绍了几种流行的应用反调试策略方案,可以是所有你也可以使用几种用法,但是记住一点:如果你想更安全,记得把反调试方案放在native层.时机最早,一般在JNI_OnUnload函数中。函数可以自己手动注册,也可以自己把函数名弄混。具体可以参考这篇文章:Android安全逆向保护浅析。为了更有效的保护,现在一些加固平台在多进程间开启保护监控,多进程参与反调试方案。这种方法会增加破解的难度,但也不是绝对安全的。文章中提到了每一种破解方法,没有一种是安全的,也有解决的方法,这部分内容将在下一篇文章中详细介绍。反调试方案攻略代码下载:https://github.com/fourbrother/android_anti_debug四.小结本文主要介绍了Android应用中的几种反调试和反破解方案,并对每种方案进行了详细的原理分析。代码也给出了下载地址,大家可以自己运行看看效果,但是这些反调试方案都不是绝对安全的,后面会详细介绍如何解决这些反调试功能,不过为了方便起见就应用安全而言,这几种解决方案都不是绝对安全的。没必要,聊胜于无!
