二进制炸弹实验binarybomb 拆弹_木杉Vincent的博客-程序员宝宝_binarybomb实验

技术标签: 系统级编程  课程随笔  二进制炸弹  逆向工程  

写在前面

这个实验是系统级编程的课程实验,非常有意思,给定一个可执行文件bomb.exe,这个程序打开之后需要用户输入一些东西,只有输入指定的字符串或者数字才能到达下一个步骤,一共有7个步骤,如果输入错误,屏幕会显示boom!!并退出程序,意味着你引爆了这个炸弹。你需要反汇编这个可执行文件来找到拆弹的线索。老师给我们提供了两种方法:使用GDB+objdump来反汇编;使用IDA 来反汇编

做本实验采用的工具是IDA Pro6.6

实验的材料在这里:
(百度云)二进制炸弹实验所需资源下载(GDB+objdump) 提取码qss1
(百度云)IDAPro6.6 提取码:jzwu
(2020年更:之前是放在了CSDN资源零积分供大家下载的,无奈每次积分都会变成非零值,大家私信我的话我又不一定有时间回,于是我把它们放在了百度云盘,欢迎大家学习交流取用。如果你发现这个链接失效了或者什么问题,欢迎大家私信我(P.S.由于年代久远,我已经不记得实验细节,有关实验内容我可能帮不到大家,抱歉啦))

Phase 1:

打开IDA,反汇编bomb.exe。可以看到如图

这里写图片描述
这里写图片描述
看到汇编代码,这里有一句string 内容是”Public speaking is very easy.”,然后将它放在ESP+4的位置,再将输入数据放在ESP的位置,调用_strings_not_equal方法,所以我们可以确定要输入的字符串是Public speaking is very easy. Phase 1解决。
这里写图片描述

Phase 2

打开IDA,选择phase2 的函数,按F4,可以看到反汇编得到的C语言代码,这代码是根据汇编函数反汇编得到的,跟原来的代码有很大差别,不过还是可以从中窥探出一些踪迹。
这里写图片描述
其中,核心代码是这段,也就是红色框框起来的代码:
这里写图片描述
很明显v5是一个计数器变量,用来遍历6个数,从蓝色框的结构我们可以猜测这是一个数组,int型的,因此if语句换个说法就是(i+1)*a[i-1]!=a[i],所以拆除炸弹所需要的6个数字应该满足(i+1)*a[i-1]!=a[i] ,也就是
2a[0]=a[1]
3a[1]=a[2]
4a[2]=a[3]
5a[3]=a[4]
6a[4]=a[5]
如果第一个数是1,那么这6个数是:1 2 6 24 120 720
Phase 2 解决。
这里写图片描述

Phase 3

打开IDA,选中phase 3的函数,按f4,我们可以得到phase 3的代码
这里写图片描述
可以看到这是一堆switch case代码
看到这句语句
这里写图片描述
可以得知我们应该输入两个整数,一个字符
选中右边的代码块可以对应到左边的汇编指令,我发现第一个整数对应的内存是[ebp-0x18]
字符对应的内存是[ebp-0x11],第二个整数对应的是[ebp-0x10].
这里写图片描述
对第一个整数进行判断
这里写图片描述
每个相应的case中都会给v9赋值,我们看汇编指令可以发现v9其实是[ebp-0x9],看到代码后边可以发现,是要将[ebp-0x11]也就是字符的值赋给eax54这个变量,然后再取低4位与[ebp-0x11]比较。
这里写图片描述
这里写图片描述
发现除了 2 3 7 之外其他的数都是十六进制的,并且7没有break,会出现问题,在这里我选2,那v9的值就是98,通过查ASCII码表可以知道98是小写字母b,那第一第二个参数就出来了,然后第三个参数,v29,如果不等于0xfb就会引爆炸弹,那0xfb是十进制的755,所以我们第三个参数就是755。所以我们应该输入2 b 755 。Phase 3解决。
这里写图片描述

Phase 4

打开IDA,选择phase 4,按f4反汇编成C语言代码,可以看到如图
这里写图片描述
通过查看程序可以知道,phase 4的主体代码很简单,就是让用户输入一个整数,调用一个func4(),如果返回值不是55就引爆炸弹。
所以我们看一下func4()。
这里写图片描述
这里写图片描述
所以我们一层层推,可知只有当参数是9的时候递归的结果是55,所以我们应该输入9,phase 4 解决。
这里写图片描述

Phase 5

打开IDA 选择phase 5 按住f4反汇编成c语言 可以看到如下图
这里写图片描述
通过程序我们可以看到,我们需要输入6个数
这里写图片描述
这里写图片描述
看到这句关键代码,eax6是一个Int型,而且下面的句子也出现了eax6,这时候光看这份不完整的代码就不够了,看一下汇编代码
这里写图片描述
可以看到,代码的意思是将数组_array_2464的第[eax]个字节存放到eax里面,再拼接起来,我们可以看到这个数组是一个字符串数组,在看到后面还有一个数组,将拼接的结果和aGiants数组压栈之后调用了_strings_not_equal函数,所以我们可以断定拆这个炸弹的方法就是从_array_2464这个数组中提取“giants”,那位置是15 0 5 11 13 1 。化成十六进制就是0xf 0x0 0x5 0xb 0xd 0x1.
这里写图片描述
但是要注意到它的偏移量不是直接通过输入数字获得的。它是通过每个输入的数取低4位,再与0xf进行与运算,结果是什么呢,当然就是输入的数的最后一个字节。
这里写图片描述
我知道内存中存放数值是变成16进制的,00 00 00 00,它取的是第一个00的后一个0的位置,所以我们输入了之后,我们希望内存是这个样子:
0f 00 00 00
00 00 00 00
05 00 00 00
0b 00 00 00
0d 00 00 00
01 00 00 00
当然0的位置随便是什么都可以,所以我选3f 30 35 3b 3d 31,查找ASCII码表可以知道它们分别是?05;=1 ,Phase 5 解决
这里写图片描述

Phase 6

打开IDA 选择phase 6 按住f4反汇编成c语言 可以看到如下图
这里写图片描述
根据炸弹会爆炸的情况分成3段:
这里写图片描述
第一段的意思是每个数字不能大于6,第二段的意思是这6个组成一个数组的话a[i]不能等于a[i+1],第三段的意思暂时不需要管,后面会说
这里写图片描述
我们看到struct s1应该是一个链表,f8指向下一个节点,s0应该是一个节点
从汇编代码和c代码中看不出什么,所以在phase 6的开头设一个断点,调试一下看看。
我们输入1 2 3 4 5 6,很显然这个输入是满足前面两个条件的,所以我们直接看最后一个条件,这里我们看到我输入的6个数,生成了6个节点
这里写图片描述
看到内存相应的位置
红色框的是我的链表,蓝色框的是每一个节点,我们可以清楚的看到节点的结构,第一行是一个数值,跟第二行有关,第二行是每个输入的数字,第三行是下一个节点的地址
这里写图片描述
继续执行到cmp语句,查看当前比较的两个参数,eax和edx
这里写图片描述
刚好是第一第二个节点的内存中第一行的值
如果要满足条件的话,前一个值要大于等于后一个值,由内存中的值可以得到,每个数字对应生成的该值为
6->01b0
5->00d4
4->03e5
3->012d
2->02d5
1->00fd
所以正确的排序应该是4 2 6 3 1 5
这里说一下为什么要用1到6来试,因为之前有说过这六个数不能大于6,而且如果他们小于0的话,在汇编代码中有一个eax-1的操作,0x00000000-1会变成0xFFFFFFFE,这也是不对的。
Phase 6解决
这里写图片描述

至此,炸弹拆除。

Secret phase:

但是我们可以发现在代码的字符串集中有这么一句话:
这里写图片描述

所以这个炸弹有一个secret phase
怎么进入这个secret phase呢
我在phase 6 的方法的最后设置了一个断点,发现当拆除phase 6之后会进入一个_phase_defused的函数
这里写图片描述

可以发现进入secret phase的条件有两个:一个是输入的字符串数目达到6,也就是拆除所有phase之后,另一个是从一个内存中读入一个整数和一个字符串,这个字符串要跟austinpower一样。
我们设置断点,进行调试,发现当它调用_sscanf函数的时候,它的参数是一个存放在地址00408190的内容
这里写图片描述

我点进去看这个地址,发现这个地址存放的是phase4的输入值,那里本来只有一个9
这里写图片描述
但是要进入secret phase呢就要再输入一个austinpower的字符串。

那我在拆炸弹的时候,在拆phase4的时候多输入一个austinpower,然后就成功进入了secret phase
我们看到secret phase的代码
这里写图片描述
这里有一个func7的函数,我们再来看一下func7
这里写图片描述
它定义了一个结构体,初步看应该是一个树的结构,再结合下面代码它访问的两个不同成员,可以确定是一棵二叉树。
那二叉树的值在哪呢?
这里写图片描述
我们可以看这个ebp-r,r的值是8,所以看到相应的位置
这里写图片描述
里面的值也是一个地址,双击到这个地址去看
这里写图片描述

这正好就是二叉树的内容。我根据内容把这棵树画出来是这样子:
这里写图片描述
好了,再来看一下func7的代码
这里写图片描述
调用func7会传递两个参数:二叉树的根节点和一个整数
如果这个数小于当前节点,就往一个子节点遍历,并且eax3=eax42+1 如果大于当前节点,就往另一个子节点遍历,并且eax3=eax52 如果相等则返回0。
而secret phase的拆弹条件是这个函数的返回值要等于7,所以我们逆推一下,只有满足7=3+3+1,3=1+1+1,1=0+0+1的时候才能说得通,所以我们可以确定这个二叉树的遍历顺序是一直往这个数小于当前节点的方向遍历,也就是往右边子节点遍历,要使二叉树往右边遍历,那这个整数就只能是1001.
到此,二进制炸弹完美解决。
这里写图片描述

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/neverever01/article/details/78403412

智能推荐

centos7上配置jdk_wudinaniya的博客-程序员宝宝

小技巧:linux用vim编辑后如何保存退出?按住shift,再按两下 'z' 键。保存退出。linux安装jdk后还需要打开 etc/profile文件 配置环境变量写入成功之后,输入命令使配置生效: source /etc/profile java -version 查看jdk版本安装jdkjava -versionlin...

2021用brew安装cocoapods,两步完成_赤手空拳的博客-程序员宝宝_brew 安装cocoapods

2021用brew安装cocoapods,两步完成1.安装brew:(Homebrew国内如何自动安装(国内地址)/bin/zsh -c "$(curl -fsSL https://gitee.com/cunkai/HomebrewCN/raw/master/Homebrew.sh)"2.安装cocoapods点我–>回答中有答案brew install cocoapods...

Cesium中级教程1 - 空间数据可视化_qq_2252224326的博客-程序员宝宝

本教程将教读者如何使用Cesium的实体(Entity)API绘制空间数据,如点、标记、标签、线、模型、形状和物体。不需要Cesium的先验知识,但是如果读者完全没有这方面的经验,那么读者可能希望从“新手入门中文教程(原创)”开始学习。什么是实体(Entity)API?Cesium具有丰富的用于空间数据的API,可以分为两类:面向图形开发人员的低级API(通常称为原始(Primitive)API)和用于数据驱动的可视化的高级API(称为实体(Entity)API)。原始API的主要目标是暴露手头

python:读取文本文件的行数据,文件.splitlines()_萱子子子的博客-程序员宝宝

一般跟踪训练的ground_truth的数据保存在文本文文件中,故每一行的数据为一张图片的标签数据,这个时候读取每一张图片的标签,具体实现如下:test_txt = '/home/zcm/tensorf/siamfc-tf-master/data/Biker/groundtruth.txt'def load_label_set(label_dir): label_folder =

机器人的洪流:刷库、撞库那些事儿_aya648206的博客-程序员宝宝

原文链接机器人的洪流:刷库、撞库那些事儿目明@阿里安全一、 那些信息泄露的事面对社会上层出不穷的诈骗新闻,我们可以发现骗子们诈骗成功的一个关键是:骗子们知道你叫什么、住在哪里、买了什么东西、花了多少钱。这些信息骗子们是从哪里得来的呢?最近某票务网站就出现了这么一例case,因为骗子们知道其在该网站上的订单信息、电话和住址,因此...

.Net Core开发学习(四) ——Blazor(MVVM)应用_自云的博客-程序员宝宝_.net core mvvm

.Net Core开发学习(四) ——Blazor(MVVM)应用MVVM(Model-View-ViewModel)MVVM,双向数据绑定。既 模型数据 与 页面显示的数据 双向绑定,改变视图数据 也会 改变模型数据。使用Blazor框架可以减少很多Js脚本代码甚至可以无Js脚本实现快速开发。当然,想要做到这点,必须浏览器与服务器保持实时连接,所以Blazor的底层是基于WebSocket的。现在比较出名的mvvm架构的框架有vue.js,angular.js等。创建Blazor应用创

随便推点

百信银行社招面试_littlebirdman的博客-程序员宝宝_百信银行面试题目

上周六去百信银行参加了社招面试,受到了一些打击,面试我的应该是架构师级别的大牛,对分布式架构/微服务很感兴趣,而我对这方面了解不多,所以面试效果不怎么理想。另外还问了一些spring框架、java多线程的一些问题,但是自己感觉每个问题都没答到点子上,可以很明显的看出面试官早就对我失去了兴趣。还是自己技不如人啊。...

jQuery 完整 ajax示例_xianhenyuan的博客-程序员宝宝

$(function(){ //请求参数 var list = {}; // $.ajax({ //请求方式 type : "POST", //请求的媒体类型 contentType: "application/json;chars...

Git学习 - 4【远程仓库】-廖老师博客学习_二十克的博客-程序员宝宝

  一个服务器管理一个远程仓库,所有人从这个远程仓库拿东西,我们称之为中央仓库或者远程仓库,现实中我们可以利用gitHub来充当远程仓库的角色。  从而建立本地Git仓库和远程仓库的联系。如何利用GitHub进行远程仓库的操作?前提是你已经有一个GitHub的账号了,并且你的机器是可以联网的!  由于公司屏蔽gitHub,以下代码在家里自己电脑上操作演示!演示环境为Windows系统,关...

程序员C语言快速上手——工程篇(十三)_编程之路从0到1的博客-程序员宝宝_c语言工程目录结构

文章目录C语言的编译脚本shell脚本(bat脚本)Makefile 脚本C语言的编译脚本为什么需要编译脚本?当C语言工程很大,源码非常多时,如果还去使用GCC命令编译程序,几乎是不现实的。这时候,可以通过编写shell脚本去执行编译命令,当然这并不是一种好的方式。在Linux上我们可以写shell脚本,在Windows上则可以编写bat脚本假设有以下几个源文件和头文件,需要编译一个mai...

CSP 201909-2 小明种苹果(续)100分 62ms 408.0KB_WM~hbu的博客-程序员宝宝

试题编号: 201909-2试题名称: 小明种苹果(续)时间限制: 1.0s内存限制: 512.0MB问题描述: ```c```c#include <stdio.h>int main(){ int N,T=0,D=0,E=0; short e[1000]={0}; int i,j,m,a,num; scanf("%d",&...

推荐文章

热门文章

相关标签