# Performing Steganography Detection

> 使用隐写分析（Steganalysis）工具检测和提取嵌入在图像、音频及其他媒体文件中的隐藏数据，揭露隐蔽通信渠道。

- Skill: `killvxk/performing-steganography-detection` (Agent Skill, multi-file: 4 files)
- Install (CLI): `npx skillmds@latest add killvxk/performing-steganography-detection`
- Raw SKILL.md: https://api.skillmd.com/api/skills/killvxk/performing-steganography-detection/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: Coding & Dev Tools
- License: Apache-2.0
- Author: killvxk (https://skillmd.com/u/killvxk)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/killvxk/performing-steganography-detection

---


# 执行隐写术检测

## 适用场景
- 当怀疑图像、音频或视频文件中存在隐蔽数据隐藏时
- 在涉及通过媒体文件进行可疑数据外泄的调查中
- 分析间谍活动或内部威胁（Insider Threat）调查中的文件
- 当标准文件分析在媒体文件属性中发现异常时
- 检测使用隐写技术的通信渠道

## 前置条件
- StegDetect、zsteg、stegsolve、binwalk 用于分析
- steghide、OpenStego 用于提取尝试
- ExifTool 用于元数据分析
- Python 及 Pillow、numpy 用于自定义分析
- 了解常见隐写技术（LSB、DCT、扩频）
- 用于比较和统计分析的样本文件

## 工作流程

### 步骤 1：初始文件评估和元数据分析

```bash
# 安装隐写检测工具
sudo apt-get install steghide stegsnow
pip install zsteg
pip install stegoveritas
gem install zsteg  # 基于 Ruby 的 PNG/BMP 工具

# 检查文件元数据是否存在异常
exiftool /cases/case-2024-001/media/suspect_image.jpg | tee /cases/case-2024-001/analysis/metadata.txt

# 检查异常文件大小（是否大于分辨率/格式预期）
identify -verbose /cases/case-2024-001/media/suspect_image.jpg | head -30

# 验证文件类型是否与扩展名匹配
file /cases/case-2024-001/media/suspect_image.jpg
# 确认 JPEG 签名与实际内容匹配

# 检查文件尾部后附加的数据
python3 << 'PYEOF'
import os

filepath = '/cases/case-2024-001/media/suspect_image.jpg'
filesize = os.path.getsize(filepath)

with open(filepath, 'rb') as f:
    data = f.read()

# JPEG 文件以 FF D9 结尾
jpeg_end = data.rfind(b'\xff\xd9')
if jpeg_end > 0:
    trailing_bytes = filesize - jpeg_end - 2
    if trailing_bytes > 0:
        print(f"警告：JPEG 结束标记后有 {trailing_bytes} 字节数据！")
        print(f"  文件大小：{filesize} 字节")
        print(f"  JPEG 数据：{jpeg_end + 2} 字节")
        print(f"  隐藏数据：{trailing_bytes} 字节")
        # 提取尾部数据
        with open('/cases/case-2024-001/analysis/trailing_data.bin', 'wb') as out:
            out.write(data[jpeg_end + 2:])
    else:
        print("JPEG 结束标记后未检测到尾部数据")

# 检查嵌入的 ZIP/RAR 压缩包
zip_offset = data.find(b'PK\x03\x04')
rar_offset = data.find(b'Rar!\x1a\x07')
if zip_offset > 0:
    print(f"在偏移量 {zip_offset} 处发现 ZIP 压缩包")
if rar_offset > 0:
    print(f"在偏移量 {rar_offset} 处发现 RAR 压缩包")
PYEOF
```

### 步骤 2：运行自动化隐写分析工具

```bash
# 使用 binwalk 检测嵌入文件和数据
binwalk /cases/case-2024-001/media/suspect_image.jpg | tee /cases/case-2024-001/analysis/binwalk_scan.txt

# 提取嵌入文件
binwalk --extract --directory /cases/case-2024-001/analysis/binwalk_extracted/ \
   /cases/case-2024-001/media/suspect_image.jpg

# 使用 zsteg 进行 PNG 和 BMP 分析（LSB 检测）
zsteg /cases/case-2024-001/media/suspect_image.png | tee /cases/case-2024-001/analysis/zsteg_results.txt

# zsteg 全面检查
zsteg -a /cases/case-2024-001/media/suspect_image.png

# 使用 stegoveritas 进行综合分析
stegoveritas /cases/case-2024-001/media/suspect_image.jpg \
   -out /cases/case-2024-001/analysis/stegoveritas/

# stegoveritas 执行：
# - 元数据提取
# - LSB 分析（多个位平面）
# - 颜色映射分析
# - 尾部数据检测
# - 嵌入文件提取
# - 图像变换分析

# 使用 steghide 对 JPEG/BMP/WAV/AU 进行提取尝试
# 使用空密码尝试
steghide extract -sf /cases/case-2024-001/media/suspect_image.jpg -p "" \
   -xf /cases/case-2024-001/analysis/steghide_extract.bin 2>&1

# 使用常见密码尝试
for pwd in password secret hidden stego test 123456 admin; do
    result=$(steghide extract -sf /cases/case-2024-001/media/suspect_image.jpg \
       -p "$pwd" -xf "/cases/case-2024-001/analysis/steghide_$pwd.bin" 2>&1)
    if echo "$result" | grep -q "extracted"; then
        echo "使用密码成功提取：$pwd"
    fi
done
```

### 步骤 3：执行 LSB（最低有效位）分析

```bash
# 使用 Python 进行自定义 LSB 分析
python3 << 'PYEOF'
from PIL import Image
import numpy as np

img = Image.open('/cases/case-2024-001/media/suspect_image.png')
pixels = np.array(img)

# 从每个颜色通道提取 LSB
for channel, name in enumerate(['红色', '绿色', '蓝色']):
    if channel >= pixels.shape[2]:
        break

    lsb_data = pixels[:, :, channel] & 1

    # 统计分布（自然图像应约为 50/50）
    zeros = np.sum(lsb_data == 0)
    ones = np.sum(lsb_data == 1)
    total = zeros + ones
    ratio = ones / total

    print(f"{name}通道 LSB：0={zeros}（{zeros/total*100:.1f}%），1={ones}（{ones/total*100:.1f}%）")
    if abs(ratio - 0.5) < 0.01:
        print(f"  中性——接近随机（可能是隐写或自然图像）")
    elif ratio > 0.55 or ratio < 0.45:
        print(f"  异常——与预期分布存在显著偏差")

# 将 LSB 数据提取为字节
lsb_bits = (pixels[:, :, 0] & 1).flatten()
lsb_bytes = np.packbits(lsb_bits)

# 检查提取数据是否有结构
with open('/cases/case-2024-001/analysis/lsb_extracted.bin', 'wb') as f:
    f.write(lsb_bytes.tobytes())

# 在提取数据中检查已知文件签名
import struct
header = bytes(lsb_bytes[:16])
print(f"\nLSB 提取头部（十六进制）：{header.hex()}")
if header[:4] == b'PK\x03\x04':
    print("  检测到：LSB 数据中存在 ZIP 压缩包！")
elif header[:3] == b'GIF':
    print("  检测到：LSB 数据中存在 GIF 图像！")
elif header[:4] == b'\x89PNG':
    print("  检测到：LSB 数据中存在 PNG 图像！")
elif header[:2] == b'\xff\xd8':
    print("  检测到：LSB 数据中存在 JPEG 图像！")

# 生成 LSB 可视化
lsb_img = Image.fromarray((lsb_data * 255).astype(np.uint8))
lsb_img.save('/cases/case-2024-001/analysis/lsb_visualization.png')
print("\nLSB 可视化已保存至 lsb_visualization.png")
PYEOF
```

### 步骤 4：分析音频和视频隐写

```bash
# 对音频文件进行频谱分析
python3 << 'PYEOF'
import wave
import numpy as np

# 分析 WAV 文件中的音频隐写
with wave.open('/cases/case-2024-001/media/suspect_audio.wav', 'r') as wav:
    frames = wav.readframes(wav.getnframes())
    samples = np.frombuffer(frames, dtype=np.int16)

    # 音频样本的 LSB 分析
    lsb = samples & 1
    zeros = np.sum(lsb == 0)
    ones = np.sum(lsb == 1)
    total = len(lsb)

    print(f"音频 LSB 分析：")
    print(f"  样本数：{total}")
    print(f"  LSB 0：{zeros}（{zeros/total*100:.1f}%）")
    print(f"  LSB 1：{ones}（{ones/total*100:.1f}%）")

    # 提取 LSB 数据
    lsb_bytes = np.packbits(lsb)
    with open('/cases/case-2024-001/analysis/audio_lsb.bin', 'wb') as f:
        f.write(lsb_bytes.tobytes())

    # 卡方检验（Chi-square Test）检验随机性
    from scipy import stats
    chi2, p_value = stats.chisquare([zeros, ones])
    print(f"  卡方：{chi2:.4f}，p 值：{p_value:.4f}")
    if p_value < 0.05:
        print(f"  异常：LSB 分布不随机（可能存在隐写）")
PYEOF

# 对音频文件使用 steghide
steghide info /cases/case-2024-001/media/suspect_audio.wav

# 使用 sonic-visualiser 或 audacity 分析频谱异常
# （检查频谱图是否有在频域中编码的隐藏图像）
```

### 步骤 5：生成隐写分析报告

```bash
# 汇编发现
python3 << 'PYEOF'
import os, json

report = {
    "case": "2024-001",
    "files_analyzed": [],
    "findings": []
}

analysis_dir = '/cases/case-2024-001/analysis/'
for f in os.listdir(analysis_dir):
    if f.endswith('.txt'):
        with open(os.path.join(analysis_dir, f)) as fh:
            content = fh.read()
            if 'DETECTED' in content or 'SUCCESS' in content or 'WARNING' in content:
                report["findings"].append({
                    "source": f,
                    "content": content[:500]
                })

with open('/cases/case-2024-001/analysis/steg_report.json', 'w') as f:
    json.dump(report, f, indent=2)

print("隐写分析报告已生成")
print(f"发现总数：{len(report['findings'])}")
PYEOF
```

## 核心概念

| 概念 | 定义 |
|------|------|
| LSB（最低有效位，Least Significant Bit） | 将数据嵌入像素或样本值的最低位 |
| DCT 隐写 | 在 JPEG 离散余弦变换（DCT）系数中隐藏数据 |
| 扩频（Spread Spectrum） | 将隐藏数据分布在整个载体信号中 |
| 隐写分析（Steganalysis） | 检测隐藏信息存在性的科学 |
| 卡方攻击（Chi-square Attack） | 检测非随机 LSB 分布的统计测试 |
| 载体媒介（Cover Medium） | 用于携带隐藏数据的原始文件（图像、音频、视频） |
| 隐写媒介（Stego Medium） | 嵌入隐藏数据后生成的文件 |
| 容量（Capacity） | 可以在不产生可见失真的情况下隐藏的最大数据量 |

## 工具与系统

| 工具 | 用途 |
|------|------|
| steghide | 在 JPEG、BMP、WAV、AU 文件中嵌入/提取数据 |
| zsteg | 检测 PNG 和 BMP 文件中的 LSB 隐写 |
| binwalk | 检测二进制文件中的嵌入文件和数据 |
| stegoveritas | 综合隐写分析工具，支持多种检测方法 |
| StegSolve | 用于图像位平面和滤镜分析的 Java GUI 工具 |
| OpenStego | 开源隐写和水印工具 |
| ExifTool | 媒体文件的元数据提取和分析 |
| stegseek | 快速 steghide 密码破解工具，用于 JPEG 隐写提取 |

## 常见场景

**场景 1：隐蔽通信调查**
检查嫌疑人通过即时通讯平台交换的图像，对所有 PNG/BMP 文件运行 stegoveritas 和 zsteg，对 JPEG 文件尝试使用已知密码进行 steghide 提取，分析 LSB 分布的统计异常，提取并解码任何隐藏消息。

**场景 2：通过图像上传进行数据外泄**
监控上传到云服务的图像是否存在异常文件大小，比较图像元数据与预期的相机/设备配置文件，运行 binwalk 检测嵌入的压缩包，分析 JPEG 量化表中的 steghide 签名，提取并检查任何隐藏载荷。

**场景 3：恶意软件命令与控制**
分析恶意软件下载的图像是否包含嵌入命令，检查文件结束标记后附加的数据，检查 DNS 查询响应中 TXT 记录里的 Base64 编码数据，分析 PNG IDAT 块中异常的压缩数据大小。

**场景 4：通过音频文件窃取知识产权**
分析音频文件 LSB 中是否嵌入文档，检查频谱图是否有在频域中隐藏的视觉模式，将音频文件大小与比特率和时长的预期大小进行比较，提取并分析任何隐藏数据载荷。

## 输出格式

```
隐写分析摘要：
  已分析文件：45 个（32 个图像，8 个音频，5 个视频）

  检测结果：
    suspect_image_03.png：
      zsteg：在 R 通道 LSB 中检测到文本
      内容："Meet at location B, Tuesday 1400"
      方法：红色通道 LSB 嵌入

    suspect_photo_17.jpg：
      steghide：使用密码"secret123"提取数据
      隐藏文件：confidential_report.pdf（234 KB）
      方法：DCT 系数修改

    profile_pic.png：
      binwalk：在偏移量 45678 处嵌入 ZIP 压缩包
      内容：3 个含财务数据的电子表格文件
      方法：在 PNG IEND 标记后附加数据

    recording_05.wav：
      LSB 分析：非随机分布（p < 0.001）
      提取：12 KB 二进制载荷（需进一步分析）
      方法：音频 LSB 嵌入

  干净文件：41 个（无隐写指标）
  可疑文件：4 个（已提取数据）

  报告：/cases/case-2024-001/analysis/steg_report.json
```

