BloodyStealer源码分析
恶意软件分析报告 - BloodyStealer
1. 概述
这份分析报告基于对一个名为BloodyStealer的恶意软件样本的逆向工程分析。该恶意软件主要设计用于从受感染系统中窃取各种敏感信息,包括浏览器凭据、游戏平台账户信息、即时通讯工具数据以及其他敏感文件。代码经过大量混淆处理,但通过分析,我们可以确定其主要功能和工作原理。
2. 代码结构分析
2.1 主程序结构
恶意软件的主要功能在Program.cs
文件的Main
方法中实现,该方法负责协调整个恶意软件的运行流程:
防重复执行机制:
- 生成一个基于系统特征的唯一标识符
- 检查特定目录是否存在标记文件,如存在则退出
- 执行完毕后在随机选择的目录创建标记文件
反分析技术:
- 反虚拟机检测(
Anti.VT.Core.Execute()
) - 反逆向工程技术(
Anti.Reverse.Core.Execute()
) - 检测独联体(CIS)国家,如果用户位于这些国家则退出
- 反虚拟机检测(
多线程数据收集:
- 浏览器数据收集线程(
Application.Grabber.Browsers.Core.Execute()
) - 应用程序数据收集线程(
Application.Grabber.Applications.Core.Execute()
) - 文件数据收集线程(
Files.Execute()
)
- 浏览器数据收集线程(
数据处理与发送:
- 处理收集的数据,去除重复项
- 收集系统信息和屏幕截图
- 创建ZIP归档文件
- 将数据发送到远程服务器
2.2 混淆特征
代码显示出明显的混淆特征,这表明它已经过反混淆处理:
无意义的命名:
- 类名使用格式如
c0000b4
、delegate0c9
等无语义命名 - 方法名使用格式如
f000094
、m000001
等序列名称
- 类名使用格式如
字符串加密:
- 使用
c0000c0.m00000f("ýn*\rÈ\u001a")
等形式的加密字符串 - 所有明文字符串都被替换为加密形式
- 使用
控制流混淆:
- 使用如
delegate0da.f0000d7(-3)
的数值来控制执行流程 - 复杂的
switch
语句和goto
标签结构 - 无限循环和条件跳转的非结构化组合
- 使用如
委托调用:
- 使用委托字段而非直接方法调用,如
delegate0c9.f000094
- 方法与实现分离,增加跟踪难度
- 使用委托字段而非直接方法调用,如
3. 功能分析
3.1 数据收集目标
恶意软件针对以下数据类型进行收集:
浏览器数据:
- 保存的密码 (
Chromium_Edited.Passwords
) - Cookies (
Chromium_Edited.Cookies
和Firefox_Edited.Cookies
) - 自动填充表单数据 (
Chromium_Edited.Forms
) - 保存的信用卡信息 (
Chromium_Edited.Cards
)
- 保存的密码 (
应用程序账户数据:
- Telegram聊天工具
- 游戏平台: EpicGames、GOG、Origin、Steam、VimeWorld
- 文件共享: uTorrent
系统信息:
- 用户名
- IP地址和地理位置信息
- 屏幕截图
- 特定类型的用户文件
3.2 传输机制
收集的数据通过以下方式传输:
- 将所有收集的信息打包成ZIP文件
- 使用基于国家和IP地址的命名格式
- 通过
Sender.Execute
方法发送至远程服务器 - 使用TLS协议进行安全传输
3.3 规避技术
该恶意软件采用多种技术来规避检测:
- 反虚拟机检测:检测是否在虚拟环境中运行
- 反调试/反分析:检测调试器和分析工具
- 独联体国家规避:避开特定地区,可能是开发者所在地区
- 一次性执行:使用标记文件防止重复感染
- 代码混淆:使代码难以分析和理解
4. 技术细节
4.1 主要类和方法
Program类:
Main
:主入口点,协调整个恶意软件行为NormalizeResults
:处理收集的数据,去除重复和无效项- 内部类
c000007
:包含三个数据收集线程方法
核心执行方法:
Application.Grabber.Browsers.Core.Execute()
:收集浏览器数据Application.Grabber.Applications.Core.Execute()
:收集应用程序数据Files.Execute()
:收集文件数据
辅助功能:
System.Screenshot()
:捕获屏幕截图System.Geo()
:获取地理位置信息System.UserName()
:获取用户名System.Other()
:获取其他系统信息
4.2 混淆技术分析
代码混淆在该样本中广泛存在,主要表现为:
对象引用混淆:
delegate0c9.f000094(array2[i]); // 可能是Thread.Start()方法
控制流混淆:
int num = delegate0da.f0000d7(-3); // 状态机控制
字符串加密:
c0000c0.m00000f("ýn*\rÈ\u001a") // 加密的字符串常量
根据分析,该混淆可能使用了ConfuserEx或其变种工具,这从命名模式delegate0xx
和控制流混淆特征可以推断。
4.3 防护措施
该恶意软件采取多种措施防止被分析或在特定环境中执行:
地理位置检测:
if (Settings.AntiCis && Settings.CisCountries.Where(new Func<string, bool>(c.m000004)).Count<string>() > 0) { delegate0d3.f0000c4(null); // 如果在CIS国家,则退出 }
防重复执行:
// 在特定目录创建标记文件 delegate0d9.f0000d5(delegate0d1.f0000bd(new string[] { text2, c0000c0.m00000f("Í"), text6, c0000c0.m00000f("Í"), text }));
5. 恶意行为评估
基于代码分析,该恶意软件主要具有以下恶意特征:
- 信息窃取:从多个来源广泛收集用户敏感信息
- 隐蔽通信:使用加密通信发送窃取的数据
- 反分析技术:采用多种技术规避检测和分析
- 持久性:通过标记文件确保执行但不重复感染
- 有针对性:避开特定地理区域,表明有特定目标
这些特征表明该恶意软件是一个专业设计的信息窃取工具,可能是用于有针对性的攻击或商业间谍活动。
6. 混淆技术分析
6.1 代码标记
代码中存在大量类似以下的标记:
// Token: 0x040003E2 RID: 994
internal static delegate0c9 f000094;
这些不是原始代码中的注释,而是反编译工具(如ILSpy或dnSpy)生成的元数据标记。它们提供了关于反编译过程的额外信息:
Token: 0x040003E2
:.NET元数据中的唯一标识符RID: 994
:在元数据表中的行号
这些标记证实了代码是通过反编译获得的,而非原始源代码。
6.2 推断的混淆器
基于代码特征,特别是命名模式和控制流混淆方式,该样本很可能使用了以下混淆工具之一:
- ConfuserEx:最可能的候选,其特征与样本高度匹配
- Eazfuscator.NET:也可能被使用
- SmartAssembly:较低可能性
- 自定义混淆工具:不能排除
7. 总结与建议
BloodyStealer是一个复杂的信息窃取恶意软件,设计用于收集和窃取用户敏感数据。它采用先进的混淆技术和反分析措施,表明其开发者具有相当的技术能力。
防护建议
- 保持安全软件更新:确保防病毒和防恶意软件解决方案是最新的
- 网络监控:监控异常网络流量和连接
- 用户教育:提高对社会工程学攻击的警惕性
- 多因素认证:对敏感账户启用多因素认证
- 定期备份:保持数据备份,以防受到攻击
研究建议
- 深入分析文件组成:检查其他组件文件的功能
- 监控网络通信:分析数据传输目的地和协议
- 动态分析:在受控环境中执行样本以观察实际行为
- IOC提取:提取可用于检测的指标
8. 附录:代码关键部分
主要执行流程
private static void Main()
{
// 创建程序上下文对象
Program.c000007 c = new Program.c000007();
// 防重复运行检查...
// 反虚拟机/沙盒检测
if (Settings.AntiVT)
{
Application.Anti.VT.Core.Execute();
}
// 反逆向工程检测
if (Settings.AntiReverse)
{
Application.Anti.Reverse.Core.Execute();
}
// 多线程数据收集
Thread[] array = new Thread[]
{
new Thread(new ThreadStart(c.m000001)), // 浏览器数据收集线程
new Thread(new ThreadStart(c.m000002)), // 应用程序数据收集线程
new Thread(new ThreadStart(c.m000003)) // 文件数据收集线程
};
// 启动和等待线程...
// 处理数据并发送...
// 创建标记文件防止再次运行
}
数据收集线程
// 浏览器数据收集
internal void m000001()
{
this.results.AddRange(Application.Grabber.Browsers.Core.Execute());
}
// 应用程序数据收集
internal void m000002()
{
this.results.AddRange(Application.Grabber.Applications.Core.Execute());
}
// 文件数据收集
internal void m000003()
{
this.results.AddRange(Files.Execute());
}
反CIS国家检测
// 如果启用了反CIS国家功能,且当前地理位置在CIS国家列表中,则退出程序
if (Settings.AntiCis && Settings.CisCountries.Where(new Func<string, bool>(c.m000004)).Count<string>() > 0)
{
delegate0d3.f0000c4(null);
}