固件简介

前言

该文章用于总结部分网络的固件知识,不具有原创性,只是转载和总结。

固件下载

虽然通过官网下载固件的方法比较便捷,但是有些厂商并不会提供固件的下载链接,这就需要我们通过其他途径来获取固件。使用从硬件设备提取固件的方法会比较通用(前提是需要有实体机设备),因为固件一般都会存储在 PCB 的某个位置里。将设备拆开之后,找到相应的 flash rom 或者 Nor flash,使用专门的工具(烧写器、编程器)进行固件的提取。

先认识一下flash文件系统和固件类型

flash文件系统

与普通计算机系统不同的是,嵌入式系统往往需要使用低成本的存储器,诸如EEPROM(带电可擦可编程只读存储器)或Nor/Nand Flash等。Nand flash存储器经常可以与NOR Flash存储器互换使用。大多数情况下闪存只是用来存储少量的代码,这时NOR闪存更适合一些,而NAND则是高数据存储密度的理想解决方案。

这里列举一些最常见的Flash文件系统,具体如下:

Squashfs

SquashFS 是一套基于Linux内核使用的压缩只读文件系统,文件最大支持2^64字节。他是基于GPL协议的开源软件。初始的版本使用gzip压缩,2.6.34版本Linux内核增加了支持LZMA和LZO压缩,并且在2.6.3内核版本上增加支持XZ压缩OpenWrt以及DD-Wrt的固件使用的就是这种文件系统,多见于4~16MB的Nor型Flash中。

JFFS/JFFS2

全名是Journalling Flash File System,是RedHat公司开发的闪存文件系统,最早是为NOR Flash设计的,自2.6版本以后开始支持NAND Flash,极适合用于嵌入式系统,多见于32MB以下的Nor型Flash固件中。它支持三种压缩算法:zlib、rubin以及rtime

YAFFS/YAFFS2

全称为Yet Another Flash File System,是由Aleph One公司发展出来的NAND flash嵌入式文件系统。与JFFS不同的
是,YAFFS最初是专门针对Nand型Flash所设计的,对于大容量的Flash读写更有优势,而JFFS在小容量的FLASH中更具优势,两者各有侧重。这种文件系统多见于128MB以上的Nand型Flash固件中。

固件提取

一般是通过串口UART或者编程器去提取固件,由于没有对应的设备和工具,这里不再复现,简单贴一下大哥的博客

UART提取:https://www.cnblogs.com/pwnfeifei/p/16926238.html

编程器提取: https://www.cnblogs.com/pwnfeifei/p/16928361.html

固件类型

固件就是程序+文件系统的组合,由文件系统将多个程序组合成一个更大、更复杂的二进制文件。当然这里的大小指的是一个相对的概念。很多时候,固件的大小往往只有几MB,而在Windows或Linux上的可执行文件动辄就是几百MB,当然两者是不能比的,相比而言,固件是麻雀虽小,五脏俱全。

裸机程序

它是组成最简单的固件,也是最容易分析的固件,IDA可以正确识别并分析这种类型的固件。这类的设备可以看作是 “单片机设备”,设备固件中是比较简单的控制、循环逻辑,利用中断、例程来处理外部世界的各种事件,如常见的智能门锁内部固件

固件解包

binwak 是一款优秀的固件分析、固件解包工具。可以用来解析绝大多数没有加密的固件,进行解包从而获取到固件的文件系统。

针对不同的flash文件系统也有不同的工具来解包,比如

  • Firmware Mod Kit广泛应用于Squashfs类型的固件编辑,支持多款路由器,OpenWrtDD-Wrt的所有固件,以及TP-Link、ASUS、D-Link的大部分路由型号的固件。

  • mtd-utils 由于jffs/jffs2和yaffs/yaffs2是基于MTD的文件系统,因此可以使用Linux下的mtd-utils中的内核工具来获得对这两种文件系统的支持

binwalk

binwalk通过识别文件头 智能扫描目标文件所有可识别的文件类型

“-e” 按照预定义的配置文件中的提取方法提取文件

“-M” 用于根据magic签名扫描结果进行递归提取

“-d” 用于限制递归提取深度,默认为8

“-A “ 使用普通可执行操作码签名扫描目标文件

提取文件

1
binwalk -Me DIR818LW_FW205b03.bin

[image-20231222184020145](https://springbird3.oss-cn-chengdu.aliyuncs.com/lianxiang/20221022230518.png)

提取出的文件如下

[image-20231222184057325](https://springbird3.oss-cn-chengdu.aliyuncs.com/lianxiang/20221022230518.png)

可以加上-t -vv参数查看详细的提取过程。通过输出信息,可以得知该固件系统没有加密压缩,好了之后就可以看到squashfs-root这个文件夹了。得到的squashfs-root就是固件系统

[image-20231226111403391](https://springbird3.oss-cn-chengdu.aliyuncs.com/lianxiang/20221022230518.png)

firmware-mod-kit

firmware-mod-kit 工具包可用于提取固件中的文件系统,然后对其进行修改,并重新打包成固件。我们可以使用它对固件做定制化的修改,但是也有可能被恶意地用于在固件中添加后门等,所以在下载固件时应到官方网站下载,并检查固件是否被修改过。

该工具包支持以下固件:

DD-WRT v23 tested - versions v23 SP1 and later are compatible (soon older versions too).
DD-WRT v24 tested
OpenWrt White Russian tested
OpenWrt Kamikaze untested (should work) - not really necessary, based on OpenWrt has its Image Builder.
FreeWrt untested - should work ok
HyperWrt untested
Ewrt untested
Sveasoft Alchemy untested
Sveasoft Talisman untested
Linksys / other vendor not supported by scripts yet - haven’t added cramfs handling
ASUS WL-330G untested - should work ok
ASUS WL-520G untested - should work ok
ASUS WL-530G supported
ASUS WL-550G untested - should work ok
Trendnet TEW-632BRP tested
DLink DIR-615 untested
many others* untested

安装

可在 google code 下载 Firmware Mod Kit v0.99 安装包,然后解压安装,安装前需要先安装相应的依赖库。

1
2
3
sudo apt-get install git build-essential zlib1g-dev liblzma-dev python-magic
cd firmware-mod-kit/src
./configure && make

使用

firmware-mod-kit 中包含以下几个工具脚本:

extract-firmware.sh:解包固件
build-firmware.sh:重新打包固件
check_for_upgrade.sh:检查更新
unsquashfs_all.sh:解包提取出来的 squashfs 文件

  • 解包固件

使用以下命令解包固件,firmware.bin 为需解包的固件,working_directory 为解包结果存储位置。

1
$ ./extract_firmware.sh firmware.bin working_directory/
  • 重新打包固件

修改完解包后的文件系统后,使用 build_firmware.sh 重新打包固件,新生成的固件将存在 output_directory 目录下。

1
$ ./build_firmware.sh output_directory/ working_directory/

固件对比

1
2
git clone https://github.com/bmaia/binwall
python binwally.py dir1 dir2

固件模拟

因为例如 MIPS、ARM 指令集是无法直接在 X86 的指令集机器上直接运行的,所以就需要使用一个模拟环境,可以用 qemu或者Firmadyne来模拟

qemu

qemu有系统模式和用户模式。对于只想模拟单个程序的话使用用户模拟即可;对于整个设备(摄像头、路由器等)的环境来说,使用系统模式比较方便

用户模式

以DIR-822为例子

[image-20231226113200742](https://springbird3.oss-cn-chengdu.aliyuncs.com/lianxiang/20221022230518.png)

查看squashfs-root/bin/busybox为mips32 静态链接程序,busybox就是类似于linux下的/bin/sh[image-20231226113233857](https://springbird3.oss-cn-chengdu.aliyuncs.com/lianxiang/20221022230518.png)

所以用qemu-mips-static来模拟,启动单个文件

1
2
cp /usr/bin/qemu-mips-static .
sudo chroot . ./qemu-mips-static ./bin/busybox ls -ail ./

[image-20231226113414105](https://springbird3.oss-cn-chengdu.aliyuncs.com/lianxiang/20221022230518.png)

可以看到运行成功了