还是老套路,ida打开,F5主函数。
__main();
printf("start\n");
printf("PS:strlen(flag)==16\nplease input the right flag:\n");
v3 = input;
do
{
scanf("%c", v3);
++v3;
}
while ( v3 != (int *)&unk_411080 );
printf("algorithm...\n");
v11 = CN;
v4 = CA;
v5 = 0;
do
{
v6 = input[v5];
if ( (unsigned int)(v6 - 48) <= 9 )
input[v5] = (v6 + v11++ - '0') % 10 + '0';
v7 = input[v5];
if ( (unsigned int)(v7 - 97) <= 0x19 )
input[v5] = (v4++ + v7 - 97) % 24 + 'a';
v8 = input[v5];
if ( v8 - 65 <= (unsigned int)'\x19' )
input[v5] = (v4++ + v8 - 65) % 24 + 'A';
++v5;
}
while ( v5 != 16 );
CN = v11;
CA = v4;
if ( input[0] == flag[0] )
{
v9 = 1;
while ( input[v9] == flag[v9] )
{
if ( ++v9 == 16 )
{
printf("ANS:right");
return 0;
}
}
}
printf("ANS:wrong\n");
return 0;
}
容易知道答案是16个字符,主要的算法在do-while语句。这个可以理解为把答案的每一个字符取出来,然后多加了个CN或者CA然后再做其他运算,得到一个字符串 eqwx{5a_2o5d_EP} 。 那么如何逆向回去呢?我们只需要把加上的CN或者CA减去就变成了原来的值之后再做其他一样的运算就得到答案了。需要注意的是:++a和a++的区别。
脚本如下:
a = "eqwx{5a_2o5d_EP}"
CN = 4
CA = 2
for j in a:
j = ord(j)
if 48 <= j <= 57:
q = CN
CN += 1
j = (j-q-48) % 10 + 48
print(chr(j),end="")
elif 97 <= j <= 122:
w = CA
CA += 1
j = (j-w-97) % 24 + 97
print(chr(j),end="")
elif 65 <= j <= 90:
e = CA
CA += 1
j = (j-e-65) % 24 + 65
print(chr(j),end="")
else:
print(chr(j),end="")
得到结果为:cnss{1s_7h9t_TF}
网友评论