根据题目提示也可以知道涉及到花指令和TEA
32位无壳
shift+f12字符串定位
有花,双击红字到达错误位置直接NOP
向上翻到main_0函数开头按P解析函数,之后F5
输入两个数,32行TEA加密,v13是四个key
看一下32行,确实是TEA,有一点改动,v4最后变成负数,写脚本时注意数据类型
密文是v14,v15对应的1115126522 2014982346
密钥是v13的12 34 56 78
delta是1640531527
下面给出两个语言的脚本
#eft
from ctypes import *
def decrypt(v,k):
v0=c_uint32(v[0])
v1=c_uint32(v[1])
delta=0x61C88647
sum1=c_uint32(-delta*32)
for i in range(32):
v1.value-=((v0.value<<4)+k[2])^(v0.value+sum1.value)^((v0.value>>5)+k[3])
v0.value-=((v1.value<<4)+k[0])^(v1.value+sum1.value)^((v1.value>>5)+k[1])
sum1.value+=delta
return v0.value,v1.value
if __name__=='__main__':
a=[0x42777AFA,0x781A30CA]
k=[12,34,56,78]
res=decrypt(a,k)
print("解密后数据:",res)
#解密后数据: (1472353, 3847872)
#include <stdio.h>
#include <stdlib.h>
#include <Windows.h>
void Decrypt(unsigned int* EntryData,int* Key)
{
//分别加密数组中的前四个字节与后4个字节,4个字节为一组每次加密两组
unsigned int x = EntryData[0];
unsigned int y = EntryData[1];
int sum = -(0x61C88647*32); //注意这里,sum = 32轮之后的黄金分割值. 因为我们要反序解密.
//总共加密32轮 那么反序也解密32轮
for (int i = 0; i < 32; ++i)
{
// 先将y解开 然后参与运算在解x
y -= ((x << 4) + Key[2]) ^ (x + sum) ^ ((x >> 5) + Key[3]);
x -= ((y << 4) + Key[0]) ^ (y + sum) ^ ((y >> 5) + Key[1]);
sum += 0x61C88647;
}
//最后加密的结果重新写入到数组中
EntryData[0] = x;
EntryData[1] = y;
}
int main()
{
unsigned int enc[3] = { 0x42777AFA,0x781A30CA,0x0 };
int key[4] = { 12,34,56,78 };
//Encrypt每次只是加密4字节数组中的两组(也就是每次加密8个字节) 如果你数据多.可以来个for循环来循环加密,但是Entrypt内部还有32次循环,所以速度上还是会有点影响.
Decrypt(enc, key);
printf("解密后的数值 = %d %d", enc[0],enc[1]);
system("pause");
}
//解密后的数值 = 1472353 3847872
flag格式中间要加个空格ISCTF{1472353 3847872}