题解:ctf两道最简单入门级的逆向思路

Justdoit

这个小程序的链接:https://pan.baidu.com/s/1Xyg5U5uj9rX8Un_b0fbYzw 提取码:acwt
仅用于学习交流!
这个是老师在课堂上给的一个练手题,是没有壳的,所以我并没有用peid去对他进行去壳(其实我傻乎乎的去壳了),打开之后是这个页面
在这里插入图片描述
那么我就把这个东西拉到了od里面,试了试水,运行,结果是这样的:
在这里插入图片描述
作为一个小白,我确实没有看懂这是个啥,然后我就顺便输了两个数,不出意外,error!
在这里插入图片描述
然后我就想看看这到底是是什么东西,所以我就在od里面,往上翻(因为我分析了一下,老师给的这个东西,应该不会太难,也不会有flag提示,那么只有一种可能,就是flag就在注释里面),果然,在我快要翻的绝望的时候,看见了一个注释:
在这里插入图片描述
看见了Hello Word,所以我就确定了,这就是题解,果然,输进去,是这个;
总结,这一题真的好水,虽然我啥都不会,但是就是感觉好水,老师的意思应该是让我们了解一下od是怎么用的,应该还可以用ida吧…不是太确定,但是这确实不难;

迷宫

做出来了一道1+1等于二的题目,我感觉到了些许膨胀(菜的一批),然后老师又给了一道入门级的迷宫题,emmm,题目链接如下:
链接:https://pan.baidu.com/s/1HItSC6T6YifCHlkl0pAIAw 提取码:6rtl
打开这个exe是这样的
在这里插入图片描述
仔细一想,这不是一个矩阵迷宫题嘛,了解过算法的人一眼就能看出来,甚至于还可以写出来一个更为牛逼的迷宫题(显然我还没达到这种牛逼的程度),心理有个大概的了解,那接下来就是先尝试输入几个字试试喽,首先输入了1,啊~我死了;重新,输入2,一点问题都没得,说明这个东西是有道道可寻的,不过这样一直试可不行(这道题是可以的,后来知道这是个55矩阵,就一条路,所以一个一个试着来是可以的),万一这个东西是个200200的矩阵,就不行了,所以果断ida,拉进去之后,长这个样子:
在这里插入图片描述
然后空格看一下流程图,f5看一下了伪代码(这些基本用法自行百度嗷):
流程图
在这里插入图片描述
在这里插入图片描述
诶!发现伪代码有点好理解啊,首先是定义的数据,一个字符型(后面的是地址),然后都是32位的int(中间有一个是short int 16位),而且地址是连着的(如果不懂地址的话可以百度先学一下地址的知识),接下来就是赋值了,但是那个qmemcpy又是个啥,所以我去百度了一下,将以第二个参数地址为首地址的后面25个(0x19u按一下h就可以变为十进制)字符赋值给以v3(char)为首地址的25个字节,那么去看一下_data_start_是什么,双击它,跳过来了这个页面,
在这里插入图片描述
emmm,这玩意好像是111…这一串,也恰好是25个,诶~会不会这个就是地图呢?矩阵形式大概是这个样子:
* 1 1 1 1
0 1 0 0 0
0 1 0 1 0
0 0 0 1 0
1 1 1 1 #
这是我猜的,因为算法里面会有这种图,让走迷宫,再难一点的我都见过,所以如果我没猜错(为什么一定要猜呢?做题嘛!直觉很重要),从
出发,然后到达#,而观察图得出结论,0代表可以走,而1代表不可以走,所以我按照这个试试,输入222441144222,发现直接没了,机敏的我想到,要么是成功了,要么是失败了(废话),成功的话就是一闪而过,没有停在这个窗口,而我又输入了这么多,我就感觉是成功了!(后来分析后果然是成功了),如果在比赛中或者其他时间做这题,到这里就可以了,得到了flag,那么还管什么为什么,但是作为小白的我不能这样,我要努力,所以我又分析一下为什么:

首先分析出,有一个25位字符串,而v3也是字符型,往后复制25位;
然后,屏幕中捕获的是v6,v6是一个16位的字类型,判断v6,如果输入为2,v4++,3的话v5–,4的话v5++,而1的话,是v4–;而下面的for就很好理解了,为了限制数据大小,v4取地址,加上i,然后取值,也就是v4,v5均要大于等0,小于等4,而至于那个v5是怎么来的,就是v4+i,i不是1嘛?i是int类型,(强行解释!等我去查一下),接下来就有意思了,v8取地址,后加上5v4+v5-41==49,什么意思?就是v8的地址,减去41,算一下,恰好是v3的首地址,然后5v4+v5,如果v4是x,而v5是y,那么就好办了,也就是5v4是走了几行(其实是直接往下走),比如一个字符串111101000
* 1 1 1 1
0 1 0 0 0
走到0,你是直接走到下就行,表示到字符中就是走了15,同理(v4,v5)就表示你当前的位置,那么就可以理解了,v4++就是x,向下就是x+1,所以这道题就出来了,后来我根据这个功能,反写了一个c++,就是这样的:

#include<iostream>
using namespace std;

int main()
{
    char c;   //捕获输入
    string s="*11110100001010000101111#";  //迷宫数列
    int x=0,y=0;    //1,2,3,4对应的x,y
    int z;   //s的下标

    cout<<"* 是起点,#是终点,0表示可以走,1表示有墙,不可以走!"<<endl;
        for(int i=0;i<s.size();i++)
        {
            cout<<s[i];
            if((i+1)%5==0)
                cout<<endl;
        }
while(1)
{
    cout<<"you can choose one action to execute"<<endl;
    cout<<"1 up"<<endl;
    cout<<"2 down"<<endl;
    cout<<"3 left"<<endl;
    cout<<"4 right\n:";

    cin>>c;
    if(c=='1')
        x--;
    if(c=='2')
        x++;
    if(c=='3')
        y--;
    if(c=='4')
        y++;

    if(x<0 || x>5 || y<0 || y>5)
        break;

    z=5*x+y;
    //cout<<z<<endl;
    if(s[z]=='1')
        break;
    if(s[z]=='#')
    {
        cout<<"OK,you find the flag!"<<endl;
        break;
    }
}
return 0;
}

呼~结束了!

发布了29 篇原创文章 · 获赞 13 · 访问量 2764

猜你喜欢

转载自blog.csdn.net/zmx2473162621/article/details/103155538