设为主页 | 加入收藏 | 繁體中文

恶意软件反检测技术介绍

  本文中,我们将向读者先容歹意软件用以拦阻对其进行逆向工程的各种反调试技能,以资助读者很好的明白这些技能,从而能够更有用地对歹意软件进行静态检测和分析。
  一、反调试技能
  反调试技能是一种常见的反检测技能,因为歹意软件总是企图监督自己的代码以检测能否自己正在被调试。为做到这一点,歹意软件可以查抄自己代码能否被设置了断点,或者间接经过系统挪用来检测调试器。
  1.断点
  为了检测其代码能否被设置断点,歹意软件可以查找指令操作码0xcc(调试器会利用该指令在断点处取得歹意软件的控制权),它会引起一个SIGTRAP。要是歹意软件代码自己建立了一个独自的处置惩罚程序的话,歹意软件也可以设置伪断点。用这种方法歹意软件可以在被设置断点的情况下一连执行其指令。
  歹意软件也可以设法笼罩断点,比方有的病毒采用了反向解密循环来笼罩病毒中的断点。相反,另有的病毒则利用汉密码自我改正自身的代码。汉密码使得程序可以检测并修改错误,但是在这里却使病毒能够检测并扫除在它的代码中的断点。
  2.盘算校验和
  歹意软件也可以盘算自身的校验和,要是校验和产生变革,那么病毒会假定它正在被调试,而且其代码外部已被安排断点。VAMPiRE是一款抗反调试工具,可用来躲避断点的检测。VaMPiRE经过在内存中维护一张断点表来到达目的,该表记载已被设置的所有断点。该程序由一个页故障处置惩罚程序(PFH),一个通用掩护故障处置惩罚程序(GPFH),一个单步处置惩罚程序和一个框架API组成。当一个断点被触发的时间,控制官僚么传给PFH(处置惩罚设置在代码、数据或者内存映射I/O中的断点),要么传给GPFH(处置惩罚遗留的I/O断点)。单步处置惩罚程序用于存放断点,使断点可以屡次利用。
  3.检测调试器
  在Linux系统上检测调试器有一个简单的方法,只需挪用Ptrace即可,因为对付一个特定的进程而言无法一连地挪用Ptrace两次以上。在Windows中,要是程序现在处于被调试状态的话,系统挪用isDebuggerPresent将前往1,不然前往0。这个系统挪用简单查抄一个标记位,当调试器正在运行时该标记位被置1。间接经过进程环境块的第二个字节就可以完成这项查抄,以下代码为大家展示的便是这种技能:
  mov eax, fs:[30h]
  move eax, byte [eax+2]
  test eax, eax
  jne @DdebuggerDetected
  在上面的代码中,eax被设置为PEB(进程环境块),然后拜访PEB的第二个字节,并将该字节的内容移入eax。经过检察eax能否为零,即可完成这项检测。要是为零,则不存在调试器;不然,阐明存在一个调试器。
  要是某个进程为提早运行的调试器所创建的,那么系统就会给ntdll.dll中的堆操作例程设置某些标记,这些标记分别是FLG_HEAP_ENABLE_TAIL_CHECK、FLG_HEAP_ENABLE_FREE_CHECK和FLG_HEAP_VALIDATE_PARAMETERS。我们可以经过下列代码来查抄这些标记:
  mov eax, fs:[30h]
  mov eax, [eax+68h]
  and eax, 0x70
  test eax, eax
  jne @DebuggerDetected
  在上面的代码中,我们还是拜访PEB,然后经过将PEB的地址加上偏移量68h到达堆操作例程所利用的这些标记的肇始位置,经过查抄这些标记就能知道能否存在调试器。
  查抄堆头部内诸如ForceFlags之类的标记也能检测能否有调试器在运行,如下所示:
  mov eax, fs:[30h]
  mov eax, [eax+18h] ;process heap
  mov eax, [eax+10h] ;heap flags
  test eax, eax
  jne @DebuggerDetected
  上面的代码向我们展示了如何经过PEB的偏移量来拜访进程的堆及堆标记,经过查抄这些内容,我们就能知道Force标记能否曾经被以后运行的调试器提早设置为1了。
  另一种检测调试器的方法是,利用NtQueryInformationProcess这个系统挪用。我们可以将ProcessInformationClass设为7来挪用该函数,这样会援用ProcessDebugPort,要是该进程正在被调试的话,该函数将前往-1。示例代码如下所示。
  push 0push 4push offset isdebuggedpush 7 ;ProcessDebugPortpush -1call NtQueryInformationProcesstest eax, eaxjne @ExitErrorcmp isdebugged, 0jne @DebuggerDetected
  在本例中,起首把NtQueryInformationProcess的参数压入货仓。这些参数先容如下:第一个是句柄(在本例中是0),第二个是进程信息的长度(在本例中为4字节),接上去是进程信息类别(在本例中是7,表现ProcessDebugPort),下一个是一个变量,用于前往能否存在调试器的信息。要是该值为非零值,那么阐明该进程正运行在一个调试器下;不然,阐明一切正常。最后一个参数是前往长度。利用这些参数挪用NtQueryInformationProcess后的前往值位于isdebugged中。随后测试该前往值能否为0即可。
  另外,另有其他一些检测调试器的方法,如查抄设置装备摆设列表能否含有调试器的名称,查抄能否存在用于调试器的注册表键,以及经过扫描内存以查抄此中能否含有调试器的代码等。
  另一种非常类似于EPO的方法是,关照PE加载器经过PE头部中的线程部分存储器(TLS)表项来援用程序的入口点。这会招致起首执行TLS中的代码,而不是先去读取程序的入口点。因此,TLS在程序启动就可以完成反调试所需检测。从TLS启动时,使得病毒得以能够在调试器启动之前就开始运行,因为一些调试器是在程序的主入口点处切入的。
  4.探测单步执行
  歹意软件还能够经过查抄单步执行来检测调试器。要想检测单步执行的话,我们可以把一个值放进货仓指针,然后看看这个值能否还在那边。要是该值在那边,这意味着,代码正在被单步执行。当调试器单步执行一个进程时,当其取得控制时需要把某些指令压入栈,并在执行下一个指令之前将其出栈。所以,要是该值仍然在那边,就意味着别的正在运行的进程曾经在利用货仓。下面的示例代码展示了歹意软件是如何经过货仓状态来检测单步执行的:
  Mov bp,sp;选择货仓指针
  Push ax ;将ax压入货仓
  Pop ax ;从货仓中选择该
  Cmp word ptr [bp -2],ax ;跟货仓中的值进行比较
  Jne debug ;要是不同,阐明发明了调试器。
  如上面的解释所述,一个值被压入货仓然后又被弹出。要是存在调试器,那么货仓指针–2位置上的值就会跟刚才弹出货仓的值有所不同,这时就可以接纳得当的行动。
  5.在运行时中检测速度衰减
  经过视察程序在运行时能否加速,歹意代码也可以检测出调试器。要是程序在运行时速度明显放缓,那就很可能意味着代码正在单步执行。因此要是两次挪用的时间戳相差甚远,那么歹意软件就需要接纳相应的行动了。Linux跟踪工具包LTTng/LTTV经过视察加速问题来跟踪病毒。当LTTng/LTTV追踪程序时,它不需要在程序运行时添加断点或者从事任何分析。别的,它还是用了一种无锁的重入机制,这意味着它不会锁定任何Linux内核代码,纵然这些内核代码是被跟踪的程序需要利用的部分也是云云,所以它不会招致被跟踪的程序的加速和等候。
  6.指令预取
  要是歹意代码篡改了指令序列中的下一条指令而且该新指令被执行了的话,那么阐明一个调试器正在运行。这是指令预取所致:要是该新指令被预取,就意味着进程的执行历程中有其他程序的切入。不然,被预取和执行的应该是原来的指令。
  7.自修改代码
  歹意软件也可以让其他代码自行修改(自行修改其他代码),这样的一个例子是HDSpoof。这个歹意软件起首启动了一些异常处置惩罚例程,然后在运行历程中将其消弭。这样一来,要是产生任何故障的话,运行中的进程会抛出一个异常,这时病毒将终止运行。别的,它在运行期间偶然还会经过扫除或者添加异常处置惩罚例程来篡改异常处置惩罚例程。在下面是HDSpoof扫除全部异常处置惩罚例程(默认异常处置惩罚例程除外)的代码。
  exception handlers before:
  0x77f79bb8 ntdll.dll:executehandler2@20 + 0x003a0x0041adc9 hdspoof.exe+0x0001adc90x77e94809 __except_handler3
  exception handlers after:
  0x77e94809 __except_handler3
  0x41b770: 8b44240c mov eax,dword ptr [esp+0xc]0x41b774: 33c9 xor ecx,ecx 0x41b776: 334804 xor ecx,dword ptr [eax+0x4]0x41b779: 334808 xor ecx,dword ptr [eax+0x8]0x41b77c: 33480c xor ecx,dword ptr [eax+0xc]0x41b77f: 334810 xor ecx,dword ptr [eax+0x10]0x41b782: 8b642408 mov esp,dword ptr [esp+0x8]0x41b786: 648f0500000000 pop dword ptr fs:[0x0]
  下面是HDSpoof创建一个新的异常处置惩罚程序的代码。
  0x41f52b: add dword ptr [esp],0x9ca
  0x41f532: push dword ptr [dword ptr fs:[0x0]
  0x41f539: mov dword ptr fs:[0x0],esp
  8.笼罩调试程序信息
  一些歹意软件利用各种技能来笼罩调试信息,这会招致调试器或者病毒自己的功效变态。经过钩住停止INT 1和INT 3(INT 3是调试器利用的操作码0xCC),歹意软件还可能致使调试器丢失其上下文。这对正常运行中的病毒来说毫无阻碍。另一种选择是钩住各种停止,并挪用另外的停止来间接运行病毒代码。
  下面是Tequila 病毒用来钩住INT 1的代码:
  new_interrupt_one:
  push bp
  mov bp,sp
  cs cmp b[0a],1 ;masm mod. needed
  je 0506 ;masm mod. needed
  cmp w[bp+4],09b4
  ja 050b ;masm mod. needed
  push ax
  push es


    文章作者: 福州军威计算机技术有限公司
    军威网络是福州最专业的电脑维修公司,专业承接福州电脑维修、上门维修、IT外包、企业电脑包年维护、局域网网络布线、网吧承包等相关维修服务。
    版权声明:原创作品,允许转载,转载时请务必以超链接形式标明文章原始出处 、作者信息和声明。否则将追究法律责任。

TAG:
评论加载中...
内容:
评论者: 验证码: