2. 固件字符串提取与初步分析
任务目标
对一份嵌入式固件二进制文件执行字符串提取,通过分析可读字符串快速判断固件的架构类型、使用的文件系统、协议栈、版本信息及潜在调试接口,为后续逆向定位关键函数建立初步情报。
环境与依赖
- Linux 环境(或 WSL)
binutils(提供strings)file命令(用于交叉验证架构判断)
固件样本准备
本案例使用一个模拟 IoT 设备固件 fw_sample.bin,由以下命令生成(便于复现):
# 生成 1MB 固件,包含文件系统标记、版本串、调试口与架构特征
dd if=/dev/zero of=fw_sample.bin bs=1024 count=1024
printf 'OpenWrt firmware, Linux kernel 4.14, squashfs filesystem' | dd of=fw_sample.bin bs=1 seek=2048 conv=notrunc
printf 'U-Boot 2018.03, ARMv7, serial console ttyS0, debug enabled' | dd of=fw_sample.bin bs=1 seek=40960 conv=notrunc
printf 'rootfs squashfs, LZMA compression, busybox v1.28' | dd of=fw_sample.bin bs=1 seek=204800 conv=notrunc
printf 'telnetd port 23, dropbear SSH, admin/admin default creds' | dd of=fw_sample.bin bs=1 seek=524288 conv=notrunc
关键完整代码
以下脚本执行字符串提取、过滤与分类分析:
#!/bin/bash
# extract_strings.sh - 固件字符串提取与初步分析
FW="fw_sample.bin"
OUT_DIR="strings_out"
mkdir -p "$OUT_DIR"
# 1. 提取所有可打印字符串(长度≥6),保留偏移地址
strings -a -t x -n 6 "$FW" > "$OUT_DIR/all_strings.txt"
# 2. 按关键特征分类
echo "=== 架构/引导特征 ==="
grep -iE 'ARM|MIPS|x86|U-Boot|Linux kernel|kernel [0-9]' "$OUT_DIR/all_strings.txt" || true
echo "=== 文件系统特征 ==="
grep -iE 'squashfs|jffs2|ubifs|ext4|LZMA|gzip' "$OUT_DIR/all_strings.txt" || true
echo "=== 网络服务/调试接口 ==="
grep -iE 'telnet|ssh|dropbear|httpd|serial|console|debug|ttyS' "$OUT_DIR/all_strings.txt" || true
echo "=== 凭据/敏感信息 ==="
grep -iE 'password|passwd|admin|root|login|default' "$OUT_DIR/all_strings.txt" || true
echo "=== 版本/产品信息 ==="
grep -iE 'v[0-9]+\.[0-9]+|version|build|OpenWrt|busybox' "$OUT_DIR/all_strings.txt" || true
# 3. 输出统计
echo ""
echo "=== 提取统计 ==="
wc -l "$OUT_DIR/all_strings.txt"
运行方式
chmod +x extract_strings.sh
./extract_strings.sh
验证方法与判定标准
执行后检查输出:
all_strings.txt应包含带十六进制偏移的字符串列表,且行数大于 0- “架构/引导特征”分类中应出现
ARMv7、U-Boot 2018.03、Linux kernel 4.14 - “文件系统特征”中应出现
squashfs、LZMA - “网络服务/调试接口”中应出现
serial console ttyS0、debug enabled、telnetd - “凭据/敏感信息”中应出现
admin/admin
以上特征全部出现即判定通过。可进一步用 file fw_sample.bin 交叉验证——由于字符串分散写入,file 可能仍报 data,此时以字符串分类结果为准,这正说明字符串预分析在 file 失效时的价值。
常见问题
- 字符串乱码:固件可能使用 UTF-16 编码,用
strings -e l补充提取。 - 偏移地址用途:记录偏移便于后续用
dd或binwalk定位具体数据块,是文件系统分割的起点。 - 误报过滤:二进制随机数据可能产生假字符串,结合上下文(如相邻字符串是否成组出现)可辅助判断。