在前面的些文章里,我提到了怎么交叉编译Unicorn-engine,以及在windows上使用Unicorn python bindings进行分析程序。这一次我介绍下如何使用Unicorn-engine和Idaemu来解决一个ollvm混淆的android逆向,也就是Geekpwn SecretCode 150。

    拿到题目,java的代码很简单,用户输入一个数字,程序调用native方法Java_net_bluelotus_tomorrow_easyandroid_MainActivity_stringFromJNI来进行验证。使用IDA打开so,发现代码经过了o-llvm混淆,控制流非常复杂。

利用Unicorn和Idaemu辅助解决Geekpwn SecretCode

    这个时候如果直接逆的话,难度很大,所以我在这里借助了idaemu来对某些函数模拟执行,然后通过函数的输入和输出来猜测函数的功能。首先要知道的是,一个double类型的数据是要两个寄存器存储的,使用的是IEEE 754标准将数字存放到寄存器当中。直接对Java_net_bluelotus_tomorrow_easyandroid_MainActivity_stringFromJNI进行f5,可以看到里面除了复杂的控制流外,调用了几个别的函数,比如aeabi_dadd,fixdfsi,浏览函数列表的时候还发现了f0, f1, f2, f3函数,只从这几个函数名上就知道这是用户写的函数,并且在Java_net_bluelotus_tomorrow_easyandroid_MainActivity_stringFromJNI也发现调用了f1和f2,f2又调用了四次f0。

    根据名字我大概觉得aeabi_dadd是浮点数的加法,我先google了aeabi_dadd 和fixdfsi,知道了fixdfsi是将浮点数转换为整数。我使用了idaemu模拟了几次aeabi_dadd,证实了自己的看法。用到的部分脚本如下:

a = Emu(UC_ARCH_ARM, UC_MODE_THUMB)
#0xBFF0000000000000
#add -1
def aeabi_dadd(f):
    for i in f:
        p = struct.pack('>d',i)
        arg0 = int(binascii.hexlify(p[4:]),16)
        arg1 = int(binascii.hexlify(p[:4]),16)
        arg = []
        arg.append(arg0)
        arg.append(arg1)
        arg.append(0)
        arg.append(0xBFF00000)
        r0 = a.eFunc(0x4188, None, arg)
        r1 = a.curUC.reg_read(UC_ARM_REG_R1)
        value = (r1<<32)|r0
        print 'handling: '+ str(i))
        result = hex(value)[2:-1].rjust(16,'0')
        print(result)
        result = binascii.unhexlify(result)
        print('final result: ' + str(struct.unpack('>d',result)[0]))
aeabi_dadd([1,2,4,100])
View Code

相关文章:

  • 2021-06-01
  • 2021-05-23
  • 2021-11-16
  • 2021-11-02
  • 2022-02-01
  • 2022-01-03
  • 2021-08-03
  • 2021-07-13
猜你喜欢
  • 2022-03-06
  • 2022-02-28
  • 2021-08-04
  • 2021-10-09
  • 2021-06-26
  • 2021-12-10
  • 2021-08-17
相关资源
相似解决方案