今天换个方向,来题Re题//DOGE
下载下来后拖入exeinfoPE中你会发现文件加了壳
用upx脱壳后 ida64打开即可
打开后shift+F12
双击,Crtl+x
然后F5直接看伪代码
int __cdecl main(int argc, const char **argv, const char **envp)
{
unsigned int v3; // eax
int v4; // edx
int v6; // [rsp+20h] [rbp-60h]
int v7; // [rsp+24h] [rbp-5Ch]
int v8; // [rsp+28h] [rbp-58h]
int v9; // [rsp+2Ch] [rbp-54h]
int v10; // [rsp+30h] [rbp-50h]
int v11; // [rsp+34h] [rbp-4Ch]
int v12; // [rsp+38h] [rbp-48h]
int v13; // [rsp+3Ch] [rbp-44h]
int v14; // [rsp+40h] [rbp-40h]
int v15; // [rsp+44h] [rbp-3Ch]
int v16; // [rsp+48h] [rbp-38h]
int v17; // [rsp+4Ch] [rbp-34h]
int v18; // [rsp+50h] [rbp-30h]
int v19; // [rsp+54h] [rbp-2Ch]
int v20; // [rsp+58h] [rbp-28h]
int v21; // [rsp+5Ch] [rbp-24h]
int v22; // [rsp+60h] [rbp-20h]
int v23; // [rsp+64h] [rbp-1Ch]
int v24; // [rsp+68h] [rbp-18h]
int v25; // [rsp+6Ch] [rbp-14h]
int v26; // [rsp+70h] [rbp-10h]
int v27; // [rsp+74h] [rbp-Ch]
char Buffer[112]; // [rsp+80h] [rbp+0h]
int v29[103]; // [rsp+F0h] [rbp+70h]
int j; // [rsp+28Ch] [rbp+20Ch]
int v31; // [rsp+290h] [rbp+210h]
int v32; // [rsp+294h] [rbp+214h]
int i; // [rsp+298h] [rbp+218h]
int v34; // [rsp+29Ch] [rbp+21Ch]
_main();
v34 = 1;
puts("please input your flag:");
gets(Buffer);
for ( i = 0; i <= 21; ++i )
v29[i] = Buffer[i];
if ( strlen(Buffer) == 22 )
{
v32 = 1;
v31 = 1;
for ( j = 0; j <= 21; ++j )
{
if ( j & 1 )
{
v31 += v32;
v3 = (unsigned int)((v31 + j + v29[j]) >> 31) >> 26;
v4 = ((_BYTE)v3 + (_BYTE)v31 + (_BYTE)j + LOBYTE(v29[j])) & 63;
}
else
{
v32 += v31;
v3 = (unsigned int)((v32 + j + v29[j]) >> 31) >> 26;
v4 = ((_BYTE)v3 + (_BYTE)v32 + (_BYTE)j + LOBYTE(v29[j])) & 63;
}
v29[j] = v4 - v3 + 64;
}
v6 = 'd';
v7 = 'y';
v8 = 'n';
v9 = 'v';
v10 = 'F';
v11 = 'U';
v12 = '{';
v13 = 'm';
v14 = '@';
v15 = '^';
v16 = 'm';
v17 = 'c';
v18 = 't';
v19 = 'Q';
v20 = 'm';
v21 = 'V';
v22 = 'S';
v23 = '~';
v24 = 'w';
v25 = 'e';
v26 = 'n';
v27 = 'r';
for ( j = 0; j <= 21; ++j )
{
if ( *(&v6 + j) != v29[j] )
v34 = 0;
}
if ( !v34 )
printf("wrong!");
if ( v34 == 1 )
printf("right flag!");
}
else
{
printf("wrong lenth!");
}
return 0;
}
v6-v27十分引人注目
你从v27后面开始分析可以发现,它只是将传入的值中的每个数和v6-v27进行对比以判断flag
那么由此可以判断出关键代码
for ( i = 0; i <= 21; ++i )
v29[i] = Buffer[i];
if ( strlen(Buffer) == 22 )//传入的字符长度必须等于22
{
v32 = 1;
v31 = 1;
for ( j = 0; j <= 21; ++j )
{
if ( j & 1 )//这里在判断是否为奇数
{
v31 += v32;
v3 = (unsigned int)((v31 + j + v29[j]) >> 31) >> 26;
v4 = ((_BYTE)v3 + (_BYTE)v31 + (_BYTE)j + LOBYTE(v29[j])) & 63;
}
else
{
v32 += v31;
v3 = (unsigned int)((v32 + j + v29[j]) >> 31) >> 26;
v4 = ((_BYTE)v3 + (_BYTE)v32 + (_BYTE)j + LOBYTE(v29[j])) & 63;
}
v29[j] = v4 - v3 + 64;
}
既然我们知道了运算方式,以及运算后的结果(v6-v27),那么我们可以由此进行逆向操作
str = "dynvFU{m@^mctQmVS~wenr"
flag = ""
v31 = 1
v32 = 1
for i in range(len(str)):
if (i & 1) != 0:
v31 += v32
v3 = ord(str[i]) - v31 - i
else:
v32 += v31
v3 = ord(str[i]) - v32 - i
v3 = v3 % 64 + 64 #这里的%64对应的是源码中的&63操作
flag += chr(v3)
print(flag)
由此得到flag
bugku{So_Ez_Fibon@cci}
我承认确实有点水...........主要是最近有点忙...........
求赞求关注,感谢!!!!!!!