CobaltStrike逆向学习系列(4):Beacon 上线协议分析
字数 1425 2025-08-29 08:31:35
CobaltStrike Beacon上线协议分析教学文档
1. 概述
本文档详细分析CobaltStrike Beacon的上线协议流程,涵盖从Beacon DLL发送上线请求到TeamServer处理的全过程,包括关键函数调用、数据加密、C2Profile解析等核心技术点。
2. Beacon发送流程
2.1 通信函数调用链
Beacon上线时通过以下Windows API函数序列建立HTTP连接:
- InternetOpenA - 初始化WinINet,传入agent标识
- InternetConnectA - 指定C2服务器的IP和端口
- HttpOpenRequestA - 设置请求类型和URI
- HttpSendRequestA - 发送HTTP请求(此时COOKIE已加密)
2.2 加密前准备
在进入功能性while循环前,Beacon已完成:
- 信息收集
- 数据加密
- C2Profile解析
2.3 C2Profile解析机制
C2Profile的解析采用索引(index)方式获取值:
- 从C2Profile中取出index为7的值(对应publickey)
- GetPtrValue函数逻辑(汇编级分析更清晰):
- 根据index跳转到对应偏移
- 前8字节判断数据类型
- 后8字节存储实际值/地址
其他类型值的获取采用相同机制。
3. TeamServer处理流程
3.1 请求接收
TeamServer使用NanoHTTPD库处理HTTP请求:
- 自定义WebServer类继承NanoHTTPD
- 包含专门的处理函数
3.2 请求处理流程
- 请求首先进入
MalleableHook.serve() - 实际调用
BeaconHTTP.serve()进行解析 - 关键处理步骤:
- 检查数据长度是否为128位
- 使用私钥进行解密
- 验证标志位0x48879
- 检查数据长度是否小于117字节
- 返回剩余字符
3.3 Beacon元数据处理
- 保留前16字节作为关键数据
- 16-20字节用于字符集判断
- 获取Listener名称
- 初始化
BeaconEntry:- 从中间数据连续取值
- 填充Beacon所需的各种信息
3.4 加密密钥注册
调用this.getSymmetricCrypto().registerKey方法:
- 传入参数为前16字节数据
- 检查BeaconId是否存在(首次上线不存在)
- 对16字节数据进行SHA-256哈希:
- 前16字节作为AES密钥
- 后16字节作为HMAC-SHA256密钥
- 将密钥与BeaconId建立映射关系
- 最后通过
sendResponse返回响应
4. 关键技术点总结
-
C2Profile解析:
- 基于索引的取值机制
- 8字节类型标识+8字节值/地址的结构
-
加密流程:
- 上线前完成数据加密
- 使用C2Profile中的公钥
- TeamServer使用私钥解密
-
元数据结构:
- 前16字节为关键数据
- 特定位置包含字符集信息
- 中间数据包含Beacon配置信息
-
密钥派生:
- 基于SHA-256的密钥派生
- 分割哈希值作为不同用途的密钥
-
标志验证:
- 固定标志位0x48879验证
- 长度检查机制(<117字节)
5. 流程图要点
(注:原文未提供具体流程图,根据描述可构建以下流程)
Beacon DLL:
1. 收集信息 → 加密数据 → 构建HTTP请求
└─ C2Profile解析 → 获取公钥
TeamServer:
1. 接收请求 → 验证长度 → 解密数据
2. 验证标志 → 解析元数据 → 注册密钥
3. 创建BeaconEntry → 发送响应
此文档全面覆盖了CobaltStrike Beacon上线协议的关键技术细节,可作为深入分析CobaltStrike行为的参考指南。