linux下恶意软件的七种反分析技术

  • 7 类主流的 Linux 恶意软件反分析/检测躲避技术
    • 反调试(Anti-Debug): 软件调试是恶意软件分析的常⽤⼿段之⼀,但恶意软件可以通过识别调试器特征,实现⾃⾝恶意⾏为的隐藏,或导致调试失败,从⽽规避分析与检测
    • 反内存转储(Anti-Memory-Dump):内存转储是恶意软件取证分析的重要⼿段,但恶意软件可通过更改代码数据结构实现⾃⾝恶意⾏为的隐藏或导致内存转储失败,从⽽规避分析检测
    • 反模拟执⾏(Anti-Emulation):⼆进制程序模拟执⾏是恶意软件深度分析的常⽤技术之⼀,但恶意软件可以针对常⽤模拟器(如 QEMU)的某些指纹特征,实现⾃⾝恶意⾏为的隐藏,或导致模拟执⾏失败,从⽽规避分析检测
    • 反代码插桩(Anti-Instrumentation):⼆进制程序代码插桩(DBI)技术通常采⽤ JIT 编译器,实现运⾏时代码插桩,是重要的恶意软件分析与检测⼿段,但恶意软件也可以通过比较插桩前后差异(如特定寄存器)探测到执⾏环境异常,实现⾃⾝恶意⾏为隐藏或导致插桩执⾏失败,从⽽规避分析检测
    • 代码注入(Code Injection):恶意软件可将⾃⾝注入合法进程实现攻击⾏为隐藏,从⽽规避分析检测,实现⽆文件攻击和攻击持久化等⽬标
    • 迟滞代码(Stalling Code):恶意软件通过迟滞恶意⾏为导致动态分析检测沙箱超时,从⽽规避检测
    • 运⾏环境测量(Runtime Measurement):通过测量特定⾏为(如指令、API 调⽤等)执⾏时间,探测当前执⾏环境中是否存在检测探针(例如:采⽤ API hook,VM/Emulator 的检测⽅法)

反代码插桩(Anti-Instrumentation)

**代码插桩(Code Instrumentation)**是一种在程序代码中插入额外指令或代码片段的技术。这通常是为了收集执行时的信息、监控程序行为、调试代码或进行性能分析。
⼆进制程序代码插桩(DBI)技术通常采⽤ JIT 编译器,实现运⾏
时代码插桩,是重要的恶意软件分析与检测⼿段,但恶意软件也可以通过比较插桩前后差异(如特定寄
存器)探测到执⾏环境异常,实现⾃⾝恶意⾏为隐藏或导致插桩执⾏失败,从⽽规避分析检测

代码加密和压缩

使用加密和压缩技术对恶意代码进行加密和压缩,使代码难以解析和识别,从而阻止了动态检测

插桩检测(Instrumentation detection)

恶意软件检查程序的代码部分是否已被修改。如果修改,则更改程序的执行并异常退出

抵制调试(Resist debugging)

“Resist debugging”(抵抗调试)是一种在软件中采取措施以防止被调试的技术。当程序被调试时,调试器(debugger)可以访问程序的内部状态、内存内容和执行路径,这为逆向工程和分析提供了便利。因此,一些软件开发者或软件保护方案可能会采取措施,以抵抗调试,增加对逆向工程的难度。
这些技术的目标是增加逆向工程的难度,以保护软件免受未经授权的分析和修改。然而,反调试技术并不是绝对的,有经验的逆向工程师通常能够找到方法来绕过这些保护机制

真实的恶意软件示例Mirai:

  • 简介:
    Mirai 是一种恶意软件,最初在2016年首次被发现。它专门针对物联网(IoT)设备,例如网络摄像头、路由器和智能家居设备。Mirai 的主要目标是通过感染这些设备来创建一个庞大的僵尸网络,该网络可以被用于发起分布式拒绝服务攻击(DDoS 攻击)。
    它发布后被攻击者开源,可以在Github上直接访问源代码
  • 示例
    这是几个C语言中用于信号处理的函数,用来定义程序接收到特定信号时的行为
    sigemptyset(&sigs);
    sigaddset($set, SIGINT);
    sigprocmask(SIG_BLOCK, &sigs, NULL);
    signal(SIGCHLD, SIG_IGN);
    signal(SIGTRAP, &anti_gdb_entry);
    
    1. sigemptyset(&sigs);:
      作用: 该函数用于初始化一个信号集,将指定的信号集 sigs 清空,即将其中的所有信号都设置为未阻塞。
      参数: &sigs 是指向信号集的指针。
    2. sigaddset($set, SIGINT);:
      作用: 该函数用于向信号集中添加一个特定的信号,此处是将 SIGINT(中断信号)添加到 $set 信号集中。
      参数: $set 是一个信号集。
    3. sigprocmask(SIG_BLOCK, &sigs, NULL);:
      作用: 此函数用于修改当前进程的信号屏蔽集。在这里,它将 sigs 中的信号添加到当前进程的信号屏蔽集中,即将这些信号设置为被阻塞,使得它们在阻塞状态下不会被处理。
      参数: SIG_BLOCK 表示将信号集添加到当前信号屏蔽集,&sigs 是要添加的信号集,最后一个参数为 NULL 表示不保存原来的信号屏蔽集。
      4. signal(SIGCHLD, SIG_IGN);:
      作用: 该函数用于指定对信号 SIGCHLD(子进程状态改变信号)的处理方式。在这里,通过设置为 SIG_IGN,表示忽略 SIGCHLD 信号,即子进程终止时不会创建僵尸进程。
      参数: SIGCHLD 是要设置处理方式的信号,SIG_IGN 表示忽略。
    4. signal(SIGTRAP, &anti_gdb_entry);:
      作用: 该函数用于指定对信号 SIGTRAP(调试中断信号)的处理方式,这里将其设置为调用 anti_gdb_entry 函数。
      参数: SIGTRAP 是要设置处理方式的信号,&anti_gdb_entry 是处理该信号时调用的函数。

使用sigemptyset()和sigaddset()分别清除和添加信号集,并将SIGINT信号添加到信号集。使用sigprocmask()函数来阻止信号集,以防止程序运行时其他进程或信号处理程序将其发送到此进程。使用signal()函数设置信号处理程序,设置要忽略的SIGCHLD信号,并设置要由反gdb-entry()函数处理的SIGTRAP信号。CPU将在硬件断点处触发中断信号(SIGTRAP),并暂停程序的执行。

Mirai使用了一系列技术,通过信号攻击来防止被调试器检测和分析

  1. 修改中断信号处理功能
    Mirai 修改了中断信号(如SIGTRAP)的处理方式,将其指向一个自定义的函数 anti_gdb_entry()。这样,当调试器(如 GDB)尝试对被感染的程序进行调试时,会调用这个自定义的函数。
  2. 检查调试符号表和调试信息表
    在 anti_gdb_entry() 方法中,Mirai 进行检查以确认是否存在调试符号表和调试信息表。这是为了识别是否有调试工具正在尝试分析程序。
  3. 使用特殊指令检查调试器状态
    Mirai 使用特殊指令检查调试器的运行状态。这可能涉及检查调试器标志或执行特殊的指令以确定是否在调试模式下运行。
  4. 修改CPU寄存器中的指令指针
    如果检测到调试器正在运行,Mirai 将修改 CPU 寄存器中的指令指针,使其指向下一条指令的地址。这样,当程序在调试器中停止时,Mirai 能够通过跳过断点等措施继续执行,防止被调试器检测到。
  5. 输出大量无用信息
    当 GDB 连接到被感染的程序并停止其运行时,Mirai 会通过输出大量的空格字符和 ANSI 转义序列到控制台,使 GDB 输出窗口充满大量无用的信息。这增加了分析者在调试过程中的困难,使输出窗口难以阅读。

DBI工具检测

Dynamic Binary Instrumentation (DBI) 工具用于在运行时分析和修改二进制程序的行为。这类工具常用于调试、性能分析、安全研究等领域。然而,一些恶意软件或反分析技术可能会尝试检测 DBI 工具的存在,以防止被分析。

反调试

许多恶意代码使用反调试技术来识别它们是否正在被调试或禁用调试器。恶意代码编写者意识到,分析人员经常使用调试器来观察恶意代码的操作,因此他们使用反调试技术来尽可能延长恶意代码的分析时间。为了防止调试器进行分析,当恶意代码意识到它正在被调试时,它可能会更改正常执行路径或修改自己的程序以崩溃,从而增加调试时间和复杂性。

插入"int3"

"int3"是一种用于在x86架构上触发调试中断的汇编指令。它实际上是一条中断指令,它引发的是中断号为3的中断。在Intel x86体系结构中,中断号3通常用于调试目的。
int3 指令的作用是在程序执行过程中插入一个软中断,这可以被调试器(如GDB)捕获。一旦中断被触发,操作系统或调试器会停止程序的执行,并将控制权传递给调试器,以便进行相应的调试操作。
当调试器想要在某一点停止,即设置断点或断点时,它将使用“int3”(0xcc)。在旧版本的gdb中,我们可以通过识别这个字符来判断它是否处于调试状态,但在新版本中它无法工作。但是我们可以尝试在代码中插入“int3”字符来破坏程序。
在一些恶意软件分析和逆向工程的情境中,int3 指令有时被用来干扰调试工具的运行,例如通过检测调试器的存在或动态修改代码来绕过调试。
在这个例子中,我们捕获SigTrap信号,这样程序在正常操作过程中就不会崩溃,并启动一个“int3”,它以类似于断点的方式在调试器中触发SigTrap

// Insert ’int3 ’
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>// 信号处理器,对 SIGTRAP 信号的处理函数
void handler(int signo) {}// 在函数中插入 int3 指令的函数
void PassByInt3() {// 设置对 SIGTRAP 信号的处理函数为 handlersignal(SIGTRAP, handler);// 在汇编中插入 nop 和 int3 指令asm("nop\n\t" "int3\n\t");// 这条语句将在 int3 执行成功后被打印printf("Code executes successfully\n");
}int main(int argc, char *argv[]) {// 调用函数插入 int3 指令PassByInt3();return 0;
}

使用ptrace()

ptrace()系统调用用于进程跟踪。它为父进程提供了观察和控制其子进程执行的能力,并允许父进程检查和替换子进程内核映像(包括寄存器)的值。许多调试工具都是基于此功能进行调试的。但是,每个进程只能调用一个ptrace()。只要我们试图在代码中跟踪自己,就会出现错误

进程识别

交互进程有一个标识符,称为会话的“Leader”进程,即SID。我们可以通过父进程(PPID)和引导进程(SID)之间的差异来判断执行应用程序时是否存在中间程序,也就是我们的调试工具。通过关注getsid()、getppid()、getpgid()和getpgrp()的值,我们可以检测调试器当前是否正在运行。

参数和环境变量

从bash-shell解释文档中,我们可以看到环境变量“-”的值将包含已运行的每个应用程序的全名。在正常环境中,此变量的值应等于/path/argv[0]。但是,在调试器中,这个变量的值经常被修改,因此我们可以通过比较这两个值来知道它当前是否处于调试环境中

运行时检测Runtime detection

当程序处于调试状态时,由于调试期间的断点、内存检查和其他操作,运行时间通常比正常时间长得多。因此,如果程序运行时间过长,可能是由于正在调试。具体来说,当程序启动时,通过警报设置计时器,当计时器到达时,程序终止。但是,对于一些调试器(如gdb),我们可以设置gdb处理信号的方式。如果我们选择忽略SIGALRM而不是将其传递给程序,则不会执行alarmHandler。我们需要考虑其他实时检测运行时的方法。

进程插入

使用Ptrace

Ptrace是Unix系列系统的系统调用之一。它的主要功能是跟踪过程。对于目标进程,执行流量控制,读取和写入用户寄存器值,以及读取和修改内存。这个特性非常适合编写实现和远程代码注入。大多数病毒都会使用它来实现自用空间注入、rip位置直接注入以及文本和数据段之间的间隙注入。

使用LD PRELOAD

LD PRELOAD是Linux/Unix系统的一个环境变量。它会影响程序的运行时链接器。它允许在程序运行之前定义要首先加载的动态链接库。该函数主要用于在不同的动态链接库中选择性地加载相同的函数。通过这个环境变量,我们可以在主程序与其动态链接库之间加载其他动态链接库,甚至可以覆盖正常的函数库

使用Proc文件系统

Proc是一个虚拟文件系统,安装在Linux系统中的/Proc目录上。Proc具有多种功能,包括允许用户访问内核信息或使用它进行故障排除。其中一个非常有用的功能是能够以文本流的形式访问进程信息,这在Linux中变得更加独特。在Proc中,有两个伪文件,即Proc/pid/maps和Proc/pid/mem。

proc/pid/mem提供了进程使用的完整内存空间的稀疏架构,并结合从maps文件获得的偏移量,mem文件可以用于读取和写入进程的内存空间。如果偏移量不正确,或者从起始位置按顺序读取文件,则会返回读写错误,因为这相当于读取无法访问的未分配内存。

通过这两个文件,可以定位目标进程中的函数。使用这些函数地址可以替换当前堆栈上的正常返回地址,并完成进程注入。

失速代码

特点

  1. 指令序列在分析环境中的运行速度比在真实(本地)主机上慢得多
  2. 他整个执行必须花费不可忽略的时间

在这里,不可忽略的必须与分配给程序自动分析的总时间联系起来

运行时间测量

恶意软件的运行时度量是指在程序运行时收集信息的行为。这些信息可能包括系统配置、进程信息、文件系统结构、网络连接等。这些信息可以帮助恶意软件适应不同的环境,或者帮助它们在感染计算机后进行更多攻击。通过编译语言插入,我们可以获得CPU品牌、供应商、版本和Hypervisor模式状态等信息。

反仿真 anti-emulation

许多恶意代码使用反仿真技术来阻止研究人员在沙盒中检查程序。反仿真技术包括硬件检查、环境检查和时间分析三种方法

硬件检测

从字面上看,硬件检查就是检查模拟器不支持的硬件命令和行为。这是因为虚拟机/模拟器对某些指令的实现与物理机不同。首先,官方arm手册对某些指令的返回值有所保留,未定义的返回值由处理器制造商自行返回。第二种是,qemu等模拟器在执行特殊指令时可能与arm手册不一致,包括arm自己的fvp试剂盒,该试剂盒也与手册不一致。因此,通过检查指令的特性,它不仅有助于识别它是否在模拟器中运行,而且有助于确定它在哪个模拟器中运行。

环境检测

环境检查是恶意软件检测系统环境中是否存在模拟器相关内容的地方。通常模拟器中的环境变量会与物理机器不同,例如硬盘、NIC信息和制造商。

时序分析

时序分析是检测程序是否在模拟器中执行的常用方法。在物理机器上,一些与加密、解密、媒体编码和解码相关的指令由硬件加速。然而,在模拟器中,指令不是由硬件加速的,而是由CPU计算的,这导致了执行时间的指数差。通过这种方式,恶意软件可以很容易地检测它是否在模拟器中执行。

反内存转储 Anti-Memory-Dump

“反内存转储”(Anti-Memory Dumping)是指一类技术和手段,旨在防止或干扰对程序内存的转储操作。在计算机安全领域,内存转储是指将程序的内存内容写入文件,通常是为了进行分析、调试或逆向工程。反内存转储技术旨在对抗这种操作,使得攻击者难以获取敏感信息或分析程序的内部结构

反内存转储是用于防止恶意代码分析的常用方法。通常,恶意软件实际上无法阻止我们转储物理内存,但恶意软件可以对代码进行模糊处理并加密,只有在代码执行时才能解密。恶意软件通常会虚拟化指令并使用虚拟指令解释器。重新配置寄存器和指令,以重新模拟CPU的本机指令,并形成一个虚拟指令集,该虚拟指令集依赖解释器将它们解释为本机指令以供执行,解释器只处理当前获取的指令。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/182857.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

二叉树OJ题之二

今天我们一起来看一道判断一棵树是否为对称二叉树的题&#xff0c;力扣101题&#xff0c; https://leetcode.cn/problems/symmetric-tree/ 我们首先先来分析这道题&#xff0c;要判断这道题是否对称&#xff0c;我们首先需要判断的是这颗树根节点的左右子树是否对称&#xff0…

VSCODE+QEMU+WSL调试RISCV代码(SBI、kernel)

前言 最近在对RISC-V架构比较感兴趣&#xff0c;正好手头有《RISC-V体系结构编程与实践》的书籍&#xff0c;就打算跟随笨叔将这块的知识学习起来&#xff0c;最开始当然是需要搭建一个基础的实验平台&#xff0c;本来笨叔是贴心的提供了VMare的环境&#xff0c;奈何天生叛逆的…

消息中间件——RabbitMQ(七)高级特性 2

前言 上一篇消息中间件——RabbitMQ&#xff08;七&#xff09;高级特性 1中我们介绍了消息如何保障100%的投递成功&#xff1f;,幂等性概念详解,在海量订单产生的业务高峰期&#xff0c;如何避免消息的重复消费的问题&#xff1f;,Confirm确认消息、Return返回消息。这篇我们…

作为用户,推荐算法真的是最优解么?

前言 众所周知&#xff0c;随着互联网技术的发展&#xff0c;推荐算法也越来越普及。无论是购物网站、社交媒体平台还是在线影视平台&#xff0c;推荐算法已成为用户获取相关信息的主要途径。据悉&#xff0c;近期GitHub决定结合算法推荐&#xff0c;将“Following”和“For Yo…

uniapp打包ios有时间 uniapp打包次数

我们经常用的解决方案有,分包,将图片上传到服务器上,减少插件引入。但是还有一个方案好多刚入门uniapp的人都给忽略了,就是在源码视图中配置,开启分包优化。 1.分包 目前微信小程序可以分8个包,每个包的最大存储是2M,也就是说你文件总体的大小不能超过16M,每个包的大…

刷题学习记录

[SWPUCTF 2021 新生赛]sql 进入环境 查看源码&#xff0c;发现是get传参且参数为wllm fuzz测试&#xff0c;发现空格&#xff0c;&#xff0c;and被过滤了 同样的也可以用python脚本进行fuzz测试 import requests fuzz{length ,,handler,like,select,sleep,database,delete,h…

【MySQL】常用内置函数:数值函数 / 字符串函数 / 日期函数 / 其他函数

文章目录 数值函数round()&#xff1a;四舍五入ceiling()&#xff1a;上限函数floor()&#xff1a;地板函数abs()&#xff1a;计算绝对值rand()&#xff1a;生成0-1的随机浮点数 字符串函数length()&#xff1a;获取字符串中的字符数upper() / lower()&#xff1a;将字符串转化…

算法---定长子串中元音的最大数目

题目 给你字符串 s 和整数 k 。 请返回字符串 s 中长度为 k 的单个子字符串中可能包含的最大元音字母数。 英文中的 元音字母 为&#xff08;a, e, i, o, u&#xff09;。 示例 1&#xff1a; 输入&#xff1a;s “abciiidef”, k 3 输出&#xff1a;3 解释&#xff1a;…

ThinkPHP的方法接收json数据问题

第一次接触到前后端分离开发&#xff0c;需要在后端接收前端ajax提交的json数据&#xff0c;开发基于ThinkPHP3.2.3框架。于是一开始习惯性的直接用I()方法接收到前端发送的json数据&#xff0c;然后用json_decode()解析发现结果为空&#xff01;但是打印出还未解析的值却打印得…

【代码随想录算法训练营-第一天】【数组】704. 二分查找、27. 移除元素

LeetCode-704.二分查找 【错误】第一遍提交的代码 主要错误点&#xff1a; 没弄清楚区间的定义导致&#xff1a;r 在定义处的赋值和 if 判断之后 r 的复制没有想清楚&#xff1b;没有搞清楚判断循环结束的条件&#xff1b;没有搞明白区间的定义&#xff0c;r 和 l 如何赋值&a…

使用Ray轻松进行Python分布式计算

大家好&#xff0c;在实际研究中&#xff0c;即使是具有多个CPU核心的单处理器计算机&#xff0c;也会给人一种能够同时运行多个任务的错觉。当我们拥有多个处理器时&#xff0c;就可以真正以并行的方式执行计算&#xff0c;本文将简要介绍Python分布式计算。 1.并行计算与分布…

MySQL事务日志

文章目录 1. redo日志 1. redo日志 口述&#xff1a;redo log 日志其实保证了ACID中的持久性&#xff0c;就是说当事务commit后&#xff0c;那么相应的修改呀更新这些操作其实都会记录到redo log中&#xff0c;其实这里的操作还是区别于redis中的aof中&#xff0c;它不是具体的…

文件中找TopK问题

目录 1.解题思路2.创建一个文件并在文件中写入数据3.为什么要建立小堆而不建立大堆&#xff1f;4.如何在现有的数据中建立适合的大堆&#xff1f;5.代码实现 1.解题思路 TopK问题即是在众多数据中找出前K大的值&#xff0c;则可以根据堆的性质来实现&#xff0c;但在使用堆之前…

Guacamole简介及centos7下搭建教程

简介 Guacamole是一款开源的远程桌面框架&#xff0c;它允许用户通过Web浏览器远程访问计算机资源。 官网地址&#xff1a;Apache Guacamole™ 官方文档&#xff1a;Installing Guacamole natively — Apache Guacamole Manual v1.5.3 架构 组件描述客户端浏览器用户通过支…

数据结构 / day02作业

1. 有若干个学校人员的信息,包括学生和教师。 其中学生的数据包括&#xff1a;姓名、性别、职业s/S、分数。 教师的数据包括:姓名、性别、职业t/T、职务。 1&#xff0c;定义指针指向堆区内存 2.循环输入 3.计算老师的个数 4.计算学生的平均值 5.循环输出 6释放堆区空间 #inc…

Jquery中的bind(),live(),delegate(),on()绑定事件方式

bind() 简要描述 bind()向匹配元素添加一个或多个事件处理器。 使用方式 $(selector).bind(event,data,function) event&#xff1a;必需项&#xff1b;添加到元素的一个或多个事件&#xff0c;例如 click,dblclick等&#xff1b; 单事件处理&#xff1a;例如 $(selector).bi…

不同类型的开源许可证

不同类型的开源许可证 什么是开源许可证 最简单的解释是&#xff0c;开源许可证是计算机软件和其他产品的许可证&#xff0c;允许在定义的条款和条件下使用、修改或共享源代码、蓝图或设计。开源并不意味着该软件可以根据需要使用、复制、修改和分发。根据开源许可证的类型&a…

gcp, loki, honeybadger 查看日志 语句

gcp, loki, honeybadger 查看日志 语句 GCP resource.type“cloudsql_database” AND logName:“projects/ebay-mag/logs/cloudsql.googleapis.com%2Fpostgres.log” AND ( textPayload:“[2823409]”) log_name“projects/ebay-mag/logs/cloudsql.googleapis.com%2Fpostgres…

代码随想录算法训练营第四十九天 | 121. 买卖股票的最佳时机,122.买卖股票的最佳时机II

目录 121. 买卖股票的最佳时机 122.买卖股票的最佳时机II 121. 买卖股票的最佳时机 题目链接&#xff1a;121. 买卖股票的最佳时机 比较好想到的是贪心算法&#xff0c;贪心选择价格更低的日子买入&#xff0c;价格更高的日子卖出。 class Solution { public:int maxProfit(vec…

ROS命令行工具

1、roscore 在使用ROS之前&#xff0c;首先要启动roscore进程。当我们在终端中运行这个命令时&#xff0c;系统就会启动ROS Master、参数服务器和日志节点。在这之后&#xff0c;就可以运行任何其他的ROS程序&#xff0f;节点了。所以可以在一个终端窗口运行roscore指令&#…