本文内容较长,所以将目录整理在最前面,用于方便各位读者查阅,目录如下
简介
通信分析
电路分析
3.1 主要芯片分析
3.2 电路接口分析
固件分析
4.1 固件提取
4.2 固件结构分析
4.3 固件重打包
主要程序分析
5.1 静态分析
5.2 日志分析
5.3 动态调试的准备
5.4 加密和认证流程分析
5.4.1 master key 生成流程
5.4.2 share key 生成流程
小结
下面开始正文:
海康威视作为国际大厂,旗下如摄像头等产品早就被无数人分析过了,通过google和github等可以找到很多分析记录和分析工具。萤石是海康威视的一个子品牌,相比于海康威视,萤石的绝大部分产品侧重于家用领域,本文将要分析的智能门锁和网关就是萤石的产品。
之前果加门锁的分析文章中,我们分析了门锁和相关的app,这篇文章我们打算对门锁配套的网关进行一些分析(真正原因是门锁让我们搞坏了,虽然海康又补发了一个,但型号没对上)。刚刚看了看萤石的网上商城,最新的联网门锁已经没有外置网关了,我们在2019年分析的智能门锁还是有外置网关的款式,图片如下:
图1-1 海康萤石智能门锁网关
门锁和网关在拿到手之后,就已经是配对状态,我们不需要进行额外的配对操作。海康萤石智能门锁有一个配套使用的app,该app对服务端有证书校验,所以直接抓包是行不通的,由于我们这里是网关分析,所以就不讨论app的工作了,在本专题的后续文章中,还会遇到类似的问题,到那时我们在解决app的事。
按照正常思路,肯定是先抓包看一下网关与服务器的通信内容。这里我们通过交换机端口监控的方法抓取海康萤石网关的通信内容(用电脑开启热点,然后网关连到电脑的热点上也可以实现抓包的目的),如下图:
图2-1 海康萤石网关通信内容
通过上图中的通信内容,我们大体上可以分析出一些内容:
A. 网关上电之后,与litedev.ys7.com进行通信。
B. 与litedev.ys7.com通信中,获取了另一个ip,即101.71.30.172。此后,终止了与litedev.ys7.com通信,并一直保持与101.71.30.172的tcp连接。
C. 通信内容看起来是加密的,通信内容中没有很多直接可见的明文。
既然抓包获取不了太多有用的信息,那么我们就要进一步研究网关固件是如何处理这些通信数据的。
这次并没有像之前的果加智能门锁那样顺利:萤石配套的app不能获取固件的下载地址,在海康和萤石的官网仔细翻找,同样没有查到固件的下载地址。那么接下来我们需要先对电路进行一些分析,以找到固件提取和调试的方法。
我们首先来看一看网关电路板上用哪些芯片,尤其注意主控MCU的型号,以及有没有外置的Flash芯片。电路板如下图所示:
图3-1 海康萤石门锁网关电路板
上图中,最明显的就是中间的MCU,仔细观察可以确认品牌和型号为MEDIATEK MT7688AN,联发科的芯片,先下载一份芯片手册看一看,下载地址是:http://labs.mediatek.com/zh-cn/chipset/MT7688。
通过阅读芯片手册,可以找到关于Flash的部分内容:
图3-2 MT7688AN芯片关于Flash的内容
上图可以看到该芯片并没有内置Flash,而是使用SPI通信的外置Flash,那么我们继续在电路板上寻找Flash芯片。
在图2-2中,MCU的上方是Winbond W9751G6KB芯片,该芯片是DDR2 SDRAM存储器,简单说就是断电丢数据的内存,固件程序不可能在里面。在MCU的下方有两个芯片,分别是PCM5100A和GD25Q127CSIG芯片, PCM5100A是个音频立体声DAC芯片,而GD25Q127CSIG芯片则是128M-bit的Flash芯片,我们要提取的固件文件应该就是在此Flash中。关于Flash中固件的提取方法,我们将在第4章中介绍。
IoT设备在开发和测试过程中,都会使用JTAG、UART等接口用于辅助调试工作。在设备的发行版中,MCU的这些引脚是否与电路板上的接口接通就不一定了,这需要我们测试一下。
在MT7688AN的芯片手册中,我们可以看到该芯片UART0接口和UART1接口。其中UART0接口在30和31引脚,如下图:
图3-3 MT7688AN芯片UART0引脚位置
上图中,我们仅展示了UART0的位置,UART1可以自行查询芯片手册。如果海康萤石的网关没有屏蔽对UART的输入和输出,那么通过这些UART也许可以实现一些操作。通过万用表测量,可以确定芯片的UART是否被引出到了软排线接口上,如下图所示的。
图3-4 海康萤石网关软排线接口
为了接通软排线接口,我们需要购买一段20pin的软排线和转接板,淘宝可以买到,楼下手机店可能也有,软排线的尺寸间距我们在图3-4已经测量出来了。此外,我们还需要一个USB转TTL模块才能将UART口连接到电脑上,该模块用于调整USB电路和TTL电路的电平逻辑,软排线+转接板+USB转TTL模块的连接如下图所示。
图3-5 连接MCU的UART接口
我们在实际操作中,发现软排线的触点位置经常虚接,暂无法确定海康萤石的软排线接口是否需要特殊的软排线才能连接,但这样也勉强能用,后续我们会有更好的替代方法。
按照图3-5方式连接好之后,在电脑的“设备管理器”选项卡中就会出现一个COM口,可以使用xShell、SecureCRT或者sscom等串口调试工具来读取这个COM口上的通信数据,当使用xShell和SecureCRT的时候需要将连接方式选择为串行接口。
到此为止,如果操作无误,网关上电后,应该可以在串口调试工具中看到了类似下图的输出内容。
图3-6 串口输出内容
上图中的输出内容显然是网关上电之后的输出日志,待系统启动完成之后,我们可以试着输入一些内容,这时就会出现登陆嵌入式Linux系统的提示字符,但是登陆用户和登陆密码我们暂不知道。现在是时候去分析固件了。
我们在3.1节提到固件应该存储在电路板的Flash芯片中,要读取Flash芯片,只需要将芯片连到编程器上即可。如果情况允许,烧录夹是最优选择,这样我们就不需要将芯片焊下来了。不巧的是,烧录夹有点粗,海康萤石的门锁网关设计的很紧凑,烧录夹夹不上去。所以我们只好用热风枪和镊子就可以把Flash吹下来了,如下图所示:
图4-1 热风枪吹取Flash芯片
如果没有热风枪,用电烙铁也是可以的,注意手别抖就好。然后将摘下来的芯片放在编程器上。支持读写GD25Q127CSIG芯片的编程器有很多种,我们这里选择一种较为实惠的MinPro100B,如下图:
图4-2 将Flash芯片放置于编程器上
将编程器连接到电脑上,使用编程器配套的软件,选择相应的Flash芯片型号后即可提取芯片内容,提取完成后可以将读出的内容保存成文件,并命名为OriginFirmware.bin。
提取出固件之后,我们可以尝试用binwalk对它进行分析,这里,我们直接用-Me参数提取固件内容,其中M参数表示递归提取:
图4-3 binwalk提取固件内容
根据binwalk的分析结果,我们可以判断固件应该包含一个嵌入式Linux操作系统,智能网关的主要功能逻辑应该由文件系统中的可执行程序完成。待binwalk运行完毕之后,会生成几个文件夹,分别是2个squashfs文件系统,2个LZMA压缩的数据,以及1个jffs2文件系统,如下图所示:
图4-4 海康萤石网关提取内容
上图中,前2个文件夹即2个LZMA压缩的数据,解压之后会发现是cpio文件系统,binwalk会自动帮我们递归全部提取。
逐个浏览这些文件系统中的内容,可以得到以下信息:
A. jffs2文件系统保存着门锁和网关的相关信息,如id等;
B. 两个cpio文件系统中,其中一个应该是恢复出厂设置时的备份文件系统,另一个是当前正在使用的文件系统;
C. 两个squashfs文件系统中,一个保存的全部都是mp3文件,另一个保存着网关的主程序,该程序即为我们将要分析的主程序。
D. 在固件的cpio文件系统中,可以找到/etc/shadow文件,文件内容如下:
图4-5 文件系统中/etc/shadow文件
借助于彩虹表,就可以找到root用户的登陆密码为abc123。使用该用户名,就可以通过串口顺利登陆海康萤石的智能网关,并使用串口shell提供的各种功能了。
我们现在已经拿到了固件内容,但是在对主程序进行分析之前,我们还需要处理一个串口总是虚接的问题,调着程序唱着歌,突然就被麻匪劫了(划掉),串口断开连接了,也是一件很恼火的事情。
在海康萤石的网关固件中翻一翻,可以发现在/sbin目录中有telnetd程序,如果我们可以通过telnet连接智能网关,或许会稳定很多,如下图所示:
图4-6 智能网关中/sbin/telnetd程序
该程序是指向busybox的软链接,如果把解压缩出的固件内容拿到windows环境后,可能会导致/sbin目录中是空的。我们可以使用串口shell登陆设备,然后运行telnetd程序,但这就意味着每次设备重启之后,我们都要使用shell启动telnetd程序,这样操作很麻烦。
继续翻找,我们在squashfs文件系统中找到initrun.sh脚本,这个脚本是在网关上电启动后进行初始化操作的。如果我们在该脚本中启动telnetd,然后将固件重新打包烧录回去,这样应该就不需要软排线连接设备了,为此我们给initrun.sh增加telnetd命令,如下图:
图4-7 在initrun.sh中启动telnetd程序
接下来,就要考虑如何将固件重新打包,然后刷回至Flash中了。固件解包时,只要binwalk跑一下就完事了,但是重打包就相对麻烦一些。我们刚刚修改了initrun.sh文件,该文件在squashfs文件系统中,所以就需要重新打包squashfs文件系统,但mksquashfs在打包时,有很多细节的参数和配置,这些参数和配置将直接影响到我们重打包的系统是否可以正常运行,而且有些设备只能识别特定版本的mksquashfs打包出来的固件。
为解决squashfs文件系统打包的问题,我们最好参考一下MT7688AN的官方SDK。假设海康萤石的开发者基于该SDK的进行开发的,那么我们也根据SDK中的固件打包方法进行操作,得到的固件应该就是可运行的。首先在官网上下载MT7688 SDK,链接如下:http://labs.mediatek.com/zh-cn/platform/linkit-smart-7688,
在下载到的SDK文件中,我们可以在include文件夹中找到image.mk文件,在该文件中可以找到打包squashfs文件系统时的命令和参数,如下图所示:
图4-8 打包squashfs文件系统的命令和参数
同时,在‘staging_dir\host\bin’目录中可以找到图4-8 中的mksquashfs4程序.
我们尝试用SDK中的mksquashfs4程序和图4-8中的参数打包一下开启了telnetd程序的squashfs文件系统,如下图所示:
图4-9 完成squashfs文件系统打包
上图中,-comp xz是选择xz压缩格式,通过binwalk可以直接查看到原固件中的压缩格式,所以我们也选择该压缩格式。
最后,将打包后的文件系统重新放回固件文件中。我们用了一个颇为简单粗暴的方法,即用UltraEdit直接16进制编辑。4.2节中binwalk分析结果显示从地址0x700000开始的位置是squashfs文件系统的位置,我们只需要将重新打包的squashfs文件覆盖到此处即可。需要注意的是固件文件从地址0x900000起始就是另一个squashfs文件系统了,所以,覆盖完成后需要调整两个文件系统之间的填充字节数量以保证另一个squashfs文件系统的起始偏移仍然是0x900000。至此,我们完成了重打包工作。
重打包完成之后,还需要将打包的固件烧录到Flash中去。烧录和提取是类似的操作,使用编程器就可以完成,操作过程我们就不再赘述了。
按照4.3的方式重打包并烧录固件后,我们应该已经可以通过telnet连接到萤石的网关上了。telnet连上后执行“ps”指令,通过简单的排除法,就可以确定我们要分析主程序是:“/dav/davinci”(达芬奇?达文西?)。接下来我们就对这个程序以及部分它调用的动态库进行分析。
我们首先静态看一下davinci文件,通过代码可以看到这个程序是有运行日志的,只是把不重要的日志屏蔽了(debug、verbose等),只输出了较为严重的日志内容(fatal、error等)。那么我们修改几条指令,使其跳过对日志严重程度的判断,如下图:
图5-1 patch日志输出代码
除了要patch日志输出代码之外,davinci在启动之后,初始化了一个线程操作看门狗,该线程会不断向/dev/watchdog进行写操作。如果一段时间内/dev/watchdog没有收到任何数据,那么整个设备就会重启。由于我们计划调试davinci程序,如果在调试过程中,触发断点导致看门狗线程挂起,那么整个系统就会重启。为此,我们先把该线程patch掉,然后再弄一个写入/dev/watchdog的小脚本,用以专门喂狗防止重启。相关位置的代码截图如下:
[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!
最后于 2020-8-27 13:10
被Lightal编辑
,原因: