firmAE模拟仿真DIR815栈溢出漏洞复现
字数 1915 2025-08-29 08:30:05

MIPS架构栈溢出漏洞复现与分析:DIR815路由器漏洞利用

1. 环境准备

1.1 工具准备

  • FirmAE: 用于固件仿真,下载地址:https://github.com/pr0v3rbs/FirmAE
  • Binwalk: 版本需v2.2.3以上,建议手动编译
  • 操作系统: 推荐Ubuntu 20.04,高版本可能遇到兼容性问题

1.2 环境搭建

  1. 安装FirmAE依赖项
  2. 编译安装Binwalk
  3. 准备DIR815固件文件

2. 固件分析

2.1 固件解包

binwalk -Me DIR815_FW.bin

常见问题:

2.2 漏洞文件定位

  • /htdocs/web/hedwig.cgi/htdocs/cgibin的软链接
  • 需要逆向分析cgibin二进制文件

3. 漏洞分析

3.1 漏洞定位

  1. 使用IDA Pro分析cgibin文件
  2. 定位hedwigcgi_main函数
  3. 分析cgibin_parse_request函数

3.2 漏洞成因

  1. 通过post方式请求
  2. sess_get_uid函数获取cookie值
  3. 对cookie进行分割处理:
    • 等号前的内容存入ptr
    • 等号后的内容存入v4
  4. 判断ptr内容是否为"uid"
  5. 通过sprintf函数将v4内容拼接到缓冲区

关键点:

  • 缓冲区s的栈空间为1024字节
  • cookie长度无限制,导致栈溢出
  • 存在两个sprintf函数调用,均可造成溢出

4. MIPS架构特性

4.1 重要特性

  1. 流水线效应:

    • 分支延迟效应:分支跳转语句后的指令会在跳转前执行
    • 分支延迟槽:跳转指令后的指令位置
  2. 缓存刷新机制:

    • 指令cache和数据cache分离
    • 攻击payload通常存储在数据缓存中
    • 需要触发flush将数据写回主内存(常用sleep(1)

4.2 寄存器与栈布局

  • $s0 ~ $s7, $fp, $sp在栈中存放的地址依次递增
  • 函数调用规则:
    • 前四个参数通过$a0$a1$a2$a3传递
    • 额外参数通过栈传递

4.3 常用汇编指令

  1. sw: 将寄存器内容存储到内存

    sw $ra, 0x24($sp)
    
  2. move: 寄存器间赋值

    move $rd, $rs
    
  3. jalr: 跳转并链接寄存器

    jalr $t9
    
  4. addui: 带符号立即数加法

    addiu $s5, $sp, 0x10
    

5. 漏洞利用

5.1 利用策略

  1. 纯ROP链:

    • 调用system函数getshell
  2. Shellcode执行:

    • 构造ROP链跳转至栈/bss段的shellcode

5.2 固件仿真

  1. 使用FirmAE仿真固件
  2. 选择选项2连接shell
  3. 选择选项4启动gdbserver
  4. 浏览器访问192.168.0.1

5.3 动态调试

  1. 输入ps查看系统进程
  2. 找到http服务进程号(示例中为2364)
  3. 启动调试并输入目标进程号

5.4 溢出测试

  1. 使用pwntools的cyclic功能生成测试字符串
  2. 发送POC并调试确定偏移量
  3. 测试结果:返回地址偏移为1009字节

5.5 ROP链构造

目标:

  • 执行system("telnetd -l /bin/sh -p 55557")

关键点:

  1. 查找gadget控制寄存器

  2. 确定寄存器在栈中的偏移:

    • $s0偏移为973
  3. system函数偏移:0x53200

挑战:

  • sprintf遇到\x00会截断
  • 利用MIPS流水线效应绕过限制

解决方案:

  1. 寻找特殊gadget:

    jalr $s0
    addiu $s0, $s0, 1
    
  2. 构造ROP:

    • $s0设置为system-10x531ff
    • $s5传入0x000159cc的gadget
    • 溢出后首先返回到s5地址
    • s0++变为system地址
    • 执行第二个gadget,将"telnetd"传入s5
    • 跳转到$s0执行system
    • s5赋值到$a0作为第一个参数

6. 最终利用

6.1 完整利用流程

  1. 构造包含ROP链的恶意请求
  2. 发送到目标路由器的hedwig.cgi
  3. 触发栈溢出执行system("telnetd")
  4. 连接开启的telnet服务获取shell

6.2 验证结果

  • 成功连接telnet服务
  • 获取路由器root权限shell

7. 总结

本案例展示了MIPS架构下栈溢出漏洞的完整利用过程,重点包括:

  1. 固件分析与漏洞定位
  2. MIPS架构特性对漏洞利用的影响
  3. 绕过限制的ROP链构造技巧
  4. 利用流水线效应的创新方法

这种技术不仅适用于DIR815路由器,也可应用于其他MIPS架构设备的漏洞分析和利用。

MIPS架构栈溢出漏洞复现与分析:DIR815路由器漏洞利用 1. 环境准备 1.1 工具准备 FirmAE : 用于固件仿真,下载地址: https://github.com/pr0v3rbs/FirmAE Binwalk : 版本需v2.2.3以上,建议手动编译 操作系统 : 推荐Ubuntu 20.04,高版本可能遇到兼容性问题 1.2 环境搭建 安装FirmAE依赖项 编译安装Binwalk 准备DIR815固件文件 2. 固件分析 2.1 固件解包 常见问题 : 解包过程中出现软链接指向 /dev/null 的warning 解决方法参考: https://zikh26.github.io/posts/d1f081a9.html 2.2 漏洞文件定位 /htdocs/web/hedwig.cgi 是 /htdocs/cgibin 的软链接 需要逆向分析 cgibin 二进制文件 3. 漏洞分析 3.1 漏洞定位 使用IDA Pro分析 cgibin 文件 定位 hedwigcgi_main 函数 分析 cgibin_parse_request 函数 3.2 漏洞成因 通过 post 方式请求 sess_get_uid 函数获取cookie值 对cookie进行分割处理: 等号前的内容存入 ptr 等号后的内容存入 v4 判断 ptr 内容是否为"uid" 通过 sprintf 函数将 v4 内容拼接到缓冲区 关键点 : 缓冲区 s 的栈空间为1024字节 cookie长度无限制,导致栈溢出 存在两个 sprintf 函数调用,均可造成溢出 4. MIPS架构特性 4.1 重要特性 流水线效应 : 分支延迟效应:分支跳转语句后的指令会在跳转前执行 分支延迟槽:跳转指令后的指令位置 缓存刷新机制 : 指令cache和数据cache分离 攻击payload通常存储在数据缓存中 需要触发flush将数据写回主内存(常用 sleep(1) ) 4.2 寄存器与栈布局 $s0 ~ $s7 , $fp , $sp 在栈中存放的地址依次递增 函数调用规则: 前四个参数通过 $a0 、 $a1 、 $a2 和 $a3 传递 额外参数通过栈传递 4.3 常用汇编指令 sw : 将寄存器内容存储到内存 move : 寄存器间赋值 jalr : 跳转并链接寄存器 addui : 带符号立即数加法 5. 漏洞利用 5.1 利用策略 纯ROP链 : 调用 system 函数getshell Shellcode执行 : 构造ROP链跳转至栈/bss段的shellcode 5.2 固件仿真 使用FirmAE仿真固件 选择选项2连接shell 选择选项4启动gdbserver 浏览器访问 192.168.0.1 5.3 动态调试 输入 ps 查看系统进程 找到http服务进程号(示例中为2364) 启动调试并输入目标进程号 5.4 溢出测试 使用pwntools的 cyclic 功能生成测试字符串 发送POC并调试确定偏移量 测试结果:返回地址偏移为1009字节 5.5 ROP链构造 目标 : 执行 system("telnetd -l /bin/sh -p 55557") 关键点 : 查找gadget控制寄存器 确定寄存器在栈中的偏移: $s0 偏移为973 system 函数偏移: 0x53200 挑战 : sprintf 遇到 \x00 会截断 利用MIPS流水线效应绕过限制 解决方案 : 寻找特殊gadget: 构造ROP: 将 $s0 设置为 system-1 ( 0x531ff ) $s5 传入 0x000159cc 的gadget 溢出后首先返回到 s5 地址 s0++ 变为 system 地址 执行第二个gadget,将"telnetd"传入 s5 跳转到 $s0 执行 system s5 赋值到 $a0 作为第一个参数 6. 最终利用 6.1 完整利用流程 构造包含ROP链的恶意请求 发送到目标路由器的 hedwig.cgi 触发栈溢出执行 system("telnetd") 连接开启的telnet服务获取shell 6.2 验证结果 成功连接telnet服务 获取路由器root权限shell 7. 总结 本案例展示了MIPS架构下栈溢出漏洞的完整利用过程,重点包括: 固件分析与漏洞定位 MIPS架构特性对漏洞利用的影响 绕过限制的ROP链构造技巧 利用流水线效应的创新方法 这种技术不仅适用于DIR815路由器,也可应用于其他MIPS架构设备的漏洞分析和利用。