vm
比较经典的虚拟机的题目是南邮的cg-ctf的题目,
然后先写了前面的cg-ctf的两个题目,其实当时做的时候还没太大虚拟机的感觉,后面接触到hgame的题目,然后再看的时候就感觉到有些那个意思,但是两个题目是基础题目也就不是太难为人,看成数据处理的考点也做的出来,
后面那个hagem的题目中间有一个栈的结构,也是比较有感觉的虚拟机题目了
另外hgame已经结束:https://hgame.vidar.club/#/user/login?return=Challenge-List
cg-ctf: https://cgctf.nuptsast.com/challenges#Re
题目文件:
链接: https://pan.baidu.com/s/1iizvnWWcDncj8uGVNmsmNA 密码: 1vle
cg-ctf WxyVM1
WxyVM
我们的flag,先是经过一个函数的加密,然后判定了下长度为24,之后和一个数组比较,而且这是一个已知的数组。
我们看到了大量的数据处理过程,通过寻址找到一个大数组的其中的位数,然后其中的连续三位拿出,一个指示运算方式,一个指示操作的flag的哪一位,一个作为运算数,
我们首先看看指示运算方式的数,直接使用ida-python脚本直接调用那个大数组即可
addr = 0x6010c0
arr = []
for i in range(0,15000,3):
arr.append(Byte(addr + i))
print(arr)
print(1 in arr)
print(2 in arr)
print(3 in arr)
print(4 in arr)
print(5 in arr)
我们知道了只会存在前三种运算,即加减异或,这都是很好逆的算法。
我们查看第二个值,指向flag的位数的,可以知道会出现很多重复的,我们只能逆着写这个算法,然后逆向得到flag,这时候就需要注意,我们的i,从0开始,到<15000,每次增3,不会取到15000,i取到的最大为14997,我们的脚本也应该是14997开始,每次增量-3,但是注意python的前包后不包,我们想最后取到0,就要写为结束在-1,
我们还需要注意的是数据溢出的处理,最开始可能数据大一些,但是到后期数据会变得很小,然后我们在计算完成以后再使用x & 0xff
来空值数据溢出。
得到:
arr = [4294967236, 52, 34, 4294967217, 4294967251, 17, 4294967191, 7, 4294967259, 55, 4294967236, 6, 29, 4294967292, 91, 4294967277, 4294967192, 4294967263, 4294967188, 4294967256, 4294967219, 4294967172, 4294967244, 8]
addr = 0x6010c0
for i