拓冰建站拓冰建站
首页 / 资讯中心 / 正文

SMB共享取pcap流量包:攻击溯源与恶意载荷提取修复实战

如果你在靶场考核或者应急演练里遇到过这种开局一台被控主机开着 SMB 共享里面躺着一个 pcap 流量包任务描述只有一句话——“还原攻击者做了什么”。别急着用 Wireshark 从头翻包这不是一道简单的“打开文件看流量”的题。真正要走的链路其实是通过 SMB 共享把流量包取回来确认 pcap 的完整性和捕获位置再从噪声极大的协议洪流里定位攻击会话最后把攻击者藏在流量里的传输载荷完整地抠出来——甚至修复成可以直接做样本分析的二进制文件。这套路径我在实际项目里反复用过也在好几套靶场题里见过同款套路这篇文章就把完整过程拆开讲从挂载共享、校验 pcap到 Wireshark 会话筛选、攻击时间线还原再到分片、编码、截断三类载荷修复场景每一步都会给出能直接复现的命令和过滤器适合正在刷靶场、准备应急响应考核或者刚转向安全分析方向、想系统掌握流量取证的同学。1. 从靶场 SMB 共享取包挂载、校验与概况摸底1.1 连接 SMB 共享这一步的常见卡点靶场里通常会给一台“已经被攻陷”的 Windows 主机攻击者为了传文件开了 SMB 共享pcap 就在共享目录下。我在 Linux 分析机上一般先探测共享列表不会直接蒙路径smbclient -L //192.168.31.100 -U hacker如果靶场只给了 guest 或者空口令可以显式加-U guest%或者-U hacker%密码。看到共享名之后再进入目录下载文件smbclient //192.168.31.100/shared -U hacker -W WORKGROUP smb: \ dir smb: \ get capture_2024.pcap smb: \ exit我这里拿到的 pcap 是一个 180MB 左右的抓包文件文件名带着抓取日期明显是攻击者自己抓的或者靶场设计者模拟的“受害主机视角流量”。除了 smbclient也可以直接把共享挂载到本地适合后面还要从共享里继续翻其他文件的情况sudo mkdir -p /mnt/evidence sudo mount -t cifs //192.168.31.100/shared /mnt/evidence -o usernamehacker,password123456,vers2.0实际测试中两个问题最常见一是mount error(112): Host is down优先检查是否禁用了 SMB1以及防火墙 445 端口是否可达二是在靶场里密码带特殊字符时 shell 容易转义出错建议把密码写进credentials/root/.smbcred文件。如果平时用 impacket 更多也可以直接用impacket-smbclient它能指定本地端口在某些 NAT 环境下比挂载更省事impacket-smbclient hacker:123456192.168.31.100取包这一步看起来简单但它决定了后续分析质量。我之前见过有人直接在 Windows 分析机上用\\ip\share打开共享再把 pcap 拖到桌面结果文件因为 SMB 缓存问题只有 0 字节。所以只要条件允许我都会用命令行工具下载然后立刻做哈希校验。1.2 拿到 pcap 后先别急着打开Wireshark 直接双击打开大文件确实流畅但分析前先做三个基础校验能省掉后面大量返工。首先是文件类型和哈希file capture_2024.pcap sha256sum capture_2024.pcap拿到哈希有两个作用一是确认下载过程没有截断二是后面如果从流量里提取出样本可以和原始哈希对比判断提取是否完整。其次是看包的数量和时间跨度用 capinfos 一眼就能看完capinfos capture_2024.pcap我这次跑出来的几个关键字段列在下面字段值分析意义File size180 MB属于中大型流量需要明确阶段再深挖Capture duration06:32:11跨度较长攻击可能分多个阶段Number of packets1,284,556百万级包手动翻页不现实Data byte rate65 kbps流量不大低频 C2 特征明显EncapsulationEthernet可以解析二层 MAC 和 VLAN 标签看到这个时间跨度我基本就有底了拿到的不是某个瞬间的抓包而是主机被控后一段完整的“带外通信记录”。这样的 pcap 里大概率同时存在横向扫描、凭据尝试、载荷投递、C2 心跳几类行为分析重点就应该放在“时间阶段划分”上而不是漫无目的地看协议列表。提示有些靶场拿到的 pcap 文件名很随意比如1.pcap、trace.pcap不要被误导先看 capinfos 输出的封装类型和丢包信息。如果封装类型是 Linux cooked capture说明这个包是在 Linux 主机上抓的和题面里“受害机是 Windows”矛盾时就要警惕流量是镜像过来的。1.3 用协议统计给流量先做一次“CT 扫描”打开 Wireshark 后我做的第一件事不是看包列表而是看Statistics - Protocol Hierarchy。这个面板能按协议树展示流量占比几秒钟就能确定哪些协议值得跟如果看到 HTTP 占比超过 20%说明攻击者很可能直接用了明文 HTTP 做载荷传输提取样本会非常顺利如果 TLS 占比很高但 HTTP 几乎为零那后门通信十有八九是加密的后面要考虑从进程内存里找 keylog或者在受害机上抓执行时的环境变量如果 SMB 占比很高则要重点关注文件共享行为里是否存在通过admin$、IPC$进行的横向移动。我这次的结果里TCP 占绝对大头HTTP 只占很小比例但 SMB2 有 400 多个包一下子把矛盾点引到了文件共享上。再打开Statistics - Endpoints看 IPv4 标签页很快就能排出一个可疑的外部 IP45.143.xx.xx和内部 192.168.31.100 之间建立了大量长连接而这些连接里最活跃的端口不是 80而是 8443。到这里就已经可以从“流量概况”阶段切入到“会话筛选”阶段了。2. 用 Wireshark 把攻击链从流量里挑出来2.1 先看会话矩阵定位“谁在跟谁说话”流量分析最容易犯的错就是一上来就盯着数据包列表看看到哪个包可疑就点哪个结果被各种 ARP、广播和 TCP 重传干扰。正确做法是先建立会话矩阵Statistics - Conversations把 TCP 和 UDP 标签页都看一遍。这个矩阵里最有价值的信息是三个维度会话总时长、上下行字节比、包数量。比如内部主机和外网 IP 之间有 4000 多个包但单方向流量很小这就是典型的 C2 心跳而如果内网两台主机之间有大量 SMB 写请求那大概率是横向移动中的文件投递。我当时在 TCP Conversations 里按“Packets”排序发现 192.168.31.100 和外网 45.143.xx.xx 的 8443 端口会话包数排第三但持续时间最长单个包平均只有 65 字节符合低频心跳特征。再用过滤器把它固定下来ip.addr 192.168.31.100 tcp.port 8443此时包列表就干净多了能看到每过 30 秒左右客户端就会发一个长度极其接近的 TCP 数据包服务端很快回一个 40 字节左右的 ACK。这种规律性单包交互正是后门通信的典型画像。2.2 把攻击链拆成四个阶段有了 IP 和端口的“主线”再从时间维度把流量拆成阶段。我的习惯是把Statistics - IO Graph打开纵轴用数据包数量横轴按 5 分钟粒度统计能明显看到几个“脉冲式”的峰值第一阶段是扫描探测集中在最开始的 15 分钟SYN 包大量出现第二阶段是漏洞利用和载荷投放表现为短暂但集中几个大包第三阶段是 C2 心跳整个时间段内低频稳定存在第四阶段可能还有一次横向移动表现为 SMB 会话突然活跃。这里要特别熟悉几个过滤器它们比手动翻包快得多分析目标显示过滤器定位扫描源tcp.flags.syn 1 tcp.flags.ack 0定位 HTTP 明文请求http.request定位 DNS 查询行为dns.flags.response 0定位 TLS 握手阶段tls.handshake.type 1定位 SMB 写文件行为smb2.cmd 9只看包含数据载荷的包tcp.len 0我注意到扫描阶段源 IP 集中在 192.168.31.50而后面建立 8443 连接的又是 192.168.31.100说明攻击者从某一台跳板机打进了受害主机然后又从受害主机回连外部 C2。这个时间顺序放在最终报告里本身就是一条完整入侵链。2.3 加密流量不是死路TLS 会话的合法解密思路当 pcap 里大量流量是 TLS 加密时很多人会直接放弃。但靶场和真实应急里只要条件合适加密流量是可以解开的。Wireshark 支持预主密钥日志文件也就是浏览器或其他 TLS 客户端把每个会话的随机数和主密钥记录下来。实际操作中如果靶场给了一个keylog.log文件很多时候放在受害主机的临时目录或 SMB 共享里只需要在Edit - Preferences - Protocols - TLS中把(Pre)-Master-Secret log filename指向它Wireshark 会自动解密后续的所有 TLS 流量。我这里没有直接拿到 keylog但观察到 TLS 握手里的 Server Name Indication 字段反复出现一个域名的子域update.microsoft-helper[.]com。这个域名一看就不是微软官方先用过滤器把所有 SNI 提出来tls.handshake.extensions_server_name然后看 DNS 解析历史发现这个域名解析结果多次变化典型的恶意域名随机解析行为。即使看不到加密内容仅凭 SNI、证书、握手时间间隔也能把“加密通道”标记为恶意行为的证据。在最终报告里我把 SNI、证书签发者、TLS 版本三项作为“加密通信指纹”单独列出证明攻击者通过 TLS 通道隐蔽回连。3. 溯源攻击者的证据链时间线、IP 与行为指纹3.1 用时间线把独立事件串成攻击故事流量包里每个包单独看都没有意义但把时间戳串起来就能成为攻击者作案全过程的一条时间线。Wireshark 的 IO Graph 再加过滤器可以分段还原第一阶段我筛出了 192.168.31.50 对目标网段发起 SYN 扫描扫描目标是 192.168.31.0/24 全段常见端口。用下面的命令统计源 IP 和目的端口确认扫描行为来自哪台机器tshark -r capture_2024.pcap -Y tcp.flags.syn 1 tcp.flags.ack 0 -T fields -e ip.src -e ip.dst -e tcp.dstport | sort | uniq -c | sort -rn | head -20第二阶段是漏洞利用。流量里出现大量指向 192.168.31.100 的 HTTP 请求路径集中在/index.php和/upload/并且有几次请求体积明显偏大。在 Wireshark 里直接定位http.request ip.dst 192.168.31.100可以看到请求体中包含 base64 编码字符串长度在 2KB 以上。这个特征配合当时的环境基本可以判断是 Web 层面的漏洞利用加文件上传。第三阶段是权限维持。攻击者成功上传后受害主机开始向外网 45.143.xx.xx 的 8443 端口发起连接并且之后每小时都有固定间隔的小包产生。这里重点看 TCP 会话的持续时间和包间隔tcp.port 8443 tcp.len 03.2 攻击者的微特征UA、频率与命令特征流量取证里最容易被忽略的是攻击者 HTTP 请求头和心跳包里的“微特征”。比如这个靶场里攻击者请求恶意文件时使用的 User-Agent 是Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36看起来和正常浏览器无差别但它的 Accept-Language 头永远排在最后而且从未加载过页面里的图片资源。这个差异说明了自动化工具调用而不是真实浏览器行为。另一个微特征是心跳包的数据载荷长度。正常情况下TCP 会分段传输数据但 C2 心跳通常由客户端单次 write 发出长度固定。我提取了 8443 端口所有 TSL/应用数据段长度发现大多数落在 45~55 字节区间少数达到 1200 字节左右——后者很可能就是攻击者下发指令的“命令包”或者回传的“结果包”。从这里能反推攻击者的指令频率和被控端的响应节奏。再用 tshark 输出每个 TCP 流的元信息tshark -r capture_2024.pcap -q -z conv,tcp会话矩阵里能看出 45.143.xx.xx 与 192.168.31.100 的连接持续了 6 小时 17 分钟期间上下行包数比接近 1:1说明交互式 shell 或轮询型后门。如果只发生一次文件下载上下行比例往往差距悬殊不会这样均匀。3.3 溯源报告怎么组织证据对这次分析的结论我在输出报告时没有把所有流量头尾不拉地贴出来而是按“攻击源头 → 攻击路径 → 后门会话 → 载荷落盘”四条线组织证据攻击源头192.168.31.50内网跳板机发起扫描和 Web 利用对应 pcap 前 3000 个包攻击路径通过 HTTP 上传脚本到/upload/随后执行并回连后门会话45.143.xx.xx:8443 的长连接心跳间隔约 30 秒SNI 为恶意域名载荷落盘受害主机通过 SMB 共享拉取了后续文件或者攻击者上传了文件这部分流量在 SMB2 写请求中体现。每一条证据都要对应 pcap 中具体时间戳和数据包编号这样复盘的人和评审专家都能快速定位原始数据。流量分析报告的最终价值不是“我找到了一个可疑 IP”而是“我证明了从哪台机器、在什么时间、用什么方法、完成了哪些操作”。4. 从混杂流量中抠出恶意传输载荷并修复4.1 追踪 TCP 流提取原始字节最直接的提取方式是 Wireshark 的Follow TCP Stream。在包含 HTTP 上传或下载的包上右键选择Follow - TCP Stream然后在弹窗里把 Show data 设置为 Raw另存为即可。但要提醒一句大部分情况下直接保存出来的文件并不是那个干净的可执行文件而是“HTTP 响应头 文件数据”的混合体甚至还会带上 chunked 分块的长度标记。所以我通常用 tshark 直接把 HTTP 响应里的http.file_data字段单独导出。这个字段是 Wireshark 解复用 TCP 流之后重组出的 HTTP body理论上拿到的就是载荷主体tshark -r capture_2024.pcap -Y http.response -T fields -e http.file_data | xxd -r -p payload.bin这里的关键是xxd -r -p因为http.file_data默认以十六进制字符串输出需要转回二进制。如果文件是 Web 上传请求里的二进制内容过滤器就换成http.request字段同样用http.file_data。做完这步再用file payload.bin看文件类型。我这次提取出的文件头是MZ也就是说“直接得到了一个 Windows 可执行文件”但这只是最理想的情况更多时候还需要修复。4.2 SMB 对象导出与文件段重组如果 pcap 里载荷是通过 SMB 共享传输的那就不能用 HTTP 那套办法了。Wireshark 在File - Export Objects菜单下其实有 SMB/SMB2 两个选项它们可以把共享会话中传输的完整文件直接导出省去手动按偏移量重组数据的步骤。实际操作中我遇到过导出的文件可以打开但文件内容中间有大段00填充说明抓包过程中有报文丢失或者 SMB 写请求和读请求没有配对完整。这时候可以手工按smb2.cmd 8读或smb2.cmd 9写过滤把关注的 TCP 流二进制数据用 tshark 导出tshark -r capture_2024.pcap -Y tcp.stream eq 7 -w stream7.pcap然后还在 Wireshark 里看这个流的 Follow TCP Stream按 Raw 保存。保存下来的文件往往带着 SMB2 头部字段需要用 010 Editor 或者 HxD 手动切掉各个 SMB 头保留 payload 区段。更省事的方法是直接在 Export Objects 里保存Wireshark 重组这些头部的正确率比较高。提示SMB 会话中同名文件如果被覆盖写Export Objects 里可能只导出最后一个版本。取证时务必先看smb2.cmd 9写请求的次数、写入偏移和文件大小判断是否存在多次写入覆盖否则你修好的样本可能不是攻击者最初投递的那一版。4.3 载荷修复的三类常见情况修载荷没有统一标准核心思路是“找回原始文件在传输中被破坏和编码掉的字节”。我用一个表把最常见的情况和修复手段列清楚损坏/编码场景特征修复方案文件前带 HTTP 响应头文件头不是 MZ/ELF而是HTTP/1.1 200 OK用 010 Editor 或 xxd 查找真实文件头偏移再从该偏移截取数据chunked 分块传输文件内容里穿插十六进制长度行和\r\n用 tshark 的http.file_data字段直接取重组 body或写脚本去除分块标记Base64 编码文件内容全是字母数字和/file识别为 ASCII textbase64 -d payload.b64 payload.bin如果带 URL 编码先替换%2B为SMB 写入偏移错乱导出的文件中间有超大段00文件大小与真实不符按FileOffset重排多个 Write Request 的 payload我那次提取的是一个“带 HTTP 响应头 chunked 分块”的复合情况。Follow TCP Stream存下来的 stream.bin 前 900 字节是 HTTP 头后面每隔一段就出现\r\n\r\n和数字长度行。先用 hexdump 定位到第一个真实文件头偏移再把数据截出来接着用一段 Python 按 CRLF 分隔解析 chunk 长度把有效数据拼接后写入新的 bin 文件。import re data open(stream.bin, rb).read() # 假设已完成文件头偏移裁剪得到 chunks_raw chunks_raw data[offset:] body b pos 0 while pos len(chunks_raw): # 读取 chunk-size 行直到遇到 line_end chunks_raw.index(b\r\n, pos) chunk_size int(chunks_raw[pos:line_end], 16) pos line_end 2 if chunk_size 0: break body chunks_raw[pos:pos chunk_size] pos chunk_size 2 with open(payload_fixed.bin, wb) as f: f.write(body)注意在 HTTP/1.1 的 chunked 编码里每块数据之后还会跟一个\r\n所以 pos 的偏移要跳过。用这个脚本修完后file payload_fixed.bin终于输出PE32 executable (GUI) Intel 80386整个提取修复流程才算是闭环。4.4 修复后的载荷识别与验证载荷修好不代表结束还要验证它是不是完整的原文件。验证分三层第一层是哈希比对。下载原始 pcap 时我们已经有了sha256sum但那个哈希是针对 pcap 文件的不是针对载荷的。所以修复后的样本要单独算一次哈希看是否和流量中另一段文件比对值一致有些恶意软件会在 C2 协议里下发文件的 MD5/SHA1。如果 pcap 里没有现成哈希就去 VirusTotal 或者本地病毒库查确认这个样本是已知家族还是未知样本。第二层是字符串和导入表分析。对修复出的 PE 文件跑一次strings重点过滤 IP、域名、URL、注册表、互斥体名strings payload_fixed.bin | grep -E (45\.143|http|\.com|Mutex|Run) | head -50如果修复正确C2 地址和 pcap 里看到的 45.143.xx.xx、恶意域名会对上说明“pcap 里的回连流量”和“被投放的载荷”形成了完整的证据闭环。第三层是动态验证。在隔离虚拟机里运行样本观察是否回连相同地址。这个步骤在靶场里可能超纲但对真实应急响应来说最关键因为只有验证了样本行为才能确认 pcap 中观察到的 TLS 长连接确实是由该样本产生的。跑沙箱时记得先给虚拟机打快照避免样本破坏分析环境。5. 实战排错与工具链收尾技巧5.1 Wireshark 常见“显示异常”背后的真实原因很多初学者在分析 pcap 时会遇到一个疑问“为什么我只能看到 520 字节的数据明明应用层文件很大”这个问题我在热词里也看到了说明不是个例。根本原因通常有两种第一种是抓包时的 snaplen抓包长度被设置得太小。比如抓包工具默认每个包捕获 65535 字节但如果为了节省空间设置了-s 520那么每个超过 520 字节的包都会被截断。这种 pcap 里的包Wireshark 只能看到前 520 字节后面的载荷永远无法恢复。判断方法是在包列表里看Frame的 “Frame length on wire” 和 “Captured length” 是否一致如果 wire 长度远大于 captured length就是抓包阶段截断了。第二种是 TCP 分段问题。一个 8KB 的 HTTP 响应被拆成 6 个 TCP 段每个段大约 1460 字节在包列表里看起来“数据只有 1460 字节”是正常的。必须开启 TCP 重组才能看到完整应用层数据。如果发现Follow TCP Stream显示的数据不完整检查Edit - Preferences - Protocols - TCP里的Allow subdissector to reassemble TCP streams和Reassemble out-of-order segments两个选项是否勾选。默认是勾选的但有些精简配置文件会把它关掉。5.2 tshark 命令行与批处理提升效率到分析后期尤其是 pcap 很大、需要反复试过滤器时我会从 Wireshark 切到 tshark因为命令行能快速输出统计结果还能把数据导入 Python 做进一步处理。下面几个命令是我每次流量取证都要用的# 查看协议统计快速判断重点 tshark -r capture_2024.pcap -q -z io,stat,60 # 统计端口会话数找出热点端口 tshark -r capture_2024.pcap -q -z conv,tcp # 导出所有 HTTP 请求 URI tshark -r capture_2024.pcap -Y http.request -T fields -e http.host -e http.request.uri | sort -u # 筛选出不符合常规的 DNS 查询名 tshark -r capture_2024.pcap -Y dns.flags.response 0 -T fields -e dns.qry.name | sort | uniq -c | sort -rn | head -50 # 导出特定 TCP 流的原始数据 tshark -r capture_2024.pcap -q -z follow,tcp,raw,7follow,tcp,raw,7里的7是 TCP stream 编号根据 Wireshark 窗口左下角或者tcp.stream eq 7过滤器确定。这个命令在网络取证里相当于一键导出流内容省去了 Wireshark 图形界面里反复右键另存为的时间。另一个比较实用的批处理思路是把 pcap 按 IP 对拆分成多个小文件避免单个 pcap 太大导致 Wireshark 卡顿。比如针对某个 C2 地址tshark -r capture_2024.pcap -Y ip.addr 45.143.xx.xx -w c2_only.pcap拆分之后再打开响应速度会快很多。5.3 安全收尾和后续扩展方向靶场和真实应急里的流量取证最后一步往往是“清场”。pcap 里可能有大量受害主机真实 IP、账号口令、内网地址写报告前要脱敏尤其是对外分享时不能直接粘贴原始包。恶意样本更不能放在共享目录里随便传播分析完最好在隔离虚拟机里压缩加密存档或者直接上传到沙箱平台做检测不要在宿主机留副本。我自己习惯的做法是单独建一个带密码的压缩包文件名里标注时间和样本哈希方便日后回溯。如果你想把这次流量取证的能力再往上推一层后续可以朝两个方向扩展一是自动化把 tshark 的输出接进 Python 的pyshark或dpkt批量提取 IOCs 并生成威胁情报格式二是从单包分析走向“全流量留存系统”在一个长期运行的网络出口上做持续性的 pcap 留存再配合定期任务扫描 C2 心跳特征这样即使攻击者行为只在某个时段出现也能被流量平台捞出来。我在实际做这类题时最大的体会是Wireshark 过滤器语法只是工具真正的分析能力是“把流量里的时间、IP、协议特征、文件内容组合成一条可验证的故事线”。从 SMB 共享里取出 pcap 只是起点之后每一步都在追问攻击者为什么用了这个协议、为什么在这个时间点发这个包、这个载荷修复后长什么样。顺着这三个问题一步步走无论靶场题怎么变最后都能落到一个能被证据支撑的结论上。
分享:

看完干货,该让你的企业上线了

免费需求沟通 · 48 小时内出具建站方案 · 河南本地可上门