2016 LCTF EASY EASY 200

2016年LCTF的第二道Mobile题,分值200,有言在先,本百分之九十九靠着自己多年酱油选手的灵感

Jadx载入样本,先判断了输入字符串的长度,然后对字符串进行处理,最后调用函数进行校验

调用Format类的函数进行处理,这里写了这么多个,肯定在后面会用到,不然出题人吃饱撑着写这么多

check()函数里显示检测了模拟器,所以直接运行在真机上,然后调用native函数进行校验

IDA载入so,先看checkEmulator()函数,这个函数并没有做其它操作,只是根据传入的值返回

同时,我们看到还有一个checkPasswd()函数

我们进行简单的分析,可以看出来中间用到了某种加密操作

在对整个校验函数有了简单的认识后,进行深入分析

在翻了几下之后,发现这几个函数并没有太大关系,我们需要关注的是

找到v22 - 12的定义就是vInput_,v20在后面会有操作,所以应该是输出

跟进去

这明显的Base64算法,那么分析到这里就可以回去了

最后的对比

这里调用sub_7B10,可以跟进去

调用memcpy()函数进行对比,那么现在关键的就是secret

使用交叉引用,找到一处对secret的调用

从第二个字符串来看,这是Base64算法无误了

那么分析到这,我们可以逆推一下,首先将dHR0dGlldmFodG5vZGllc3VhY2VibGxlaHNhdG5hd2k.用Base64还原,然后倒序

鉴于没有参赛我也不知道flag到底是什么

网上流传的flag:iwantashellbecauseidonthaveitttt

可是我记得前面是有调用一个Format类的一个函数做substring()操作,应该是补上固定长度的任意字符串

不过还有一点点其它的东西可以跟大家聊一聊

我们注意到

而我们Java层传进来的字符串应该是33位,再来翻so文件,蓦然发现有一个JNI_OnLoad()函数

粗略一看,这里面的东西还是很多的,先是做初始化,猜测这里是要获取dex文件

通过/proc/self/maps找dex文件

寻找dex的Magic Number

接下来看到了比较关键的代码,这通常用于Dex文件自篡改,一大堆乱七八糟的东西没看懂是啥

这时候开始瞎猜,一定有篡改,而且截取的长度由33变成32,获取的是Lcom/example/ring/wantashell/Format;

再回头看该类的四个函数,主办方还是很仁慈的,并没有换三个长度都是32的函数

大胆的猜测这里是将form()自篡改成f0rm()

那么现在flag是iwantashellbecauseidonthaveitttt就没什么问题了

至于反调试,可以直接patch so的调用反调试函数指令,也可以动态调试的时候下断点,patch一下内存

如果有同学感觉好的,在看secret赋值那里,就应该猜到这是Base64算法,感觉再好一点的,直接就解出了flag

Last updated