IDA分析
main方法分析
根据伪代码,得知flag长度36位,逐位判断字符串是否相等(红色断点行)
动态调试
断点判断语句
查看v7地址,v8是从v20来的,即输入文本
凯撒分析
void *Src[5];
void *Block[5];
sub_732560(Src, "ioCj~KCss|bQ6zbhCu$5r57$Iljkwlqj$$$€", 36u);
if ( v21 == 36 )
{
sub_732490(Src);
sub_731FE0();
LOBYTE(v23) = 2;
v7 = Block;
v8 = v20;
if ( v19 >= 16 )
v7 = (void **)Block[0];
if ( v4 >= 16 )
v8 = v5;
if ( Block[4] == (void *)36 )
{
v9 = 32;
do
{
if ( *v8 != *v7 )
break;
++v8;
++v7;
v10 = v9 < 4;
v9 -= 4;
}
while ( !v10 );
}
...
_DWORD *__thiscall sub_732490(_DWORD *this, _DWORD *Src)
{
_OWORD *v2; // ebx
unsigned int v4; // ecx
_DWORD *result; // eax
int v6; // edi
size_t v7; // eax
void *v8; // eax
_DWORD *v9; // ecx
unsigned int v10; // [esp+Ch] [ebp-4h]
v2 = Src;
this[4] = 0;
this[5] = 0;
v4 = Src[4];
v10 = v4;
if ( Src[5] >= 16u )
v2 = (_OWORD *)*Src;
if ( v4 >= 16 )
{
v6 = v4 | 15;
if ( (v4 | 15) > 2147483647 )
v6 = 2147483647;
if ( (unsigned int)(v6 + 1) < 4096 )
{
if ( v6 == -1 )
v9 = 0;
else
v9 = operator new(v6 + 1);
}
else
{
v7 = v6 + 36;
if ( v6 + 36 <= (unsigned int)(v6 + 1) )
v7 = -1;
v8 = operator new(v7);
if ( !v8 )
_invalid_parameter_noinfo_noreturn();
v9 = (_DWORD *)(((unsigned int)v8 + 35) & 0xFFFFFFE0);
*(v9 - 1) = v8;
}
*this = v9;
memmove(v9, v2, v10 + 1);
this[4] = v10;
result = this;
this[5] = v6;
}
else
{
result = this;
*(_OWORD *)this = *v2;
this[4] = v4;
this[5] = 15;
}
return result;
}
由于tip的提示过于明了,直接根据万年答案flag{}
编写测试脚本
a = "ioCj~KCss|bQ6zbhCu$5r57$Iljkwlqj$$$€"
# flag f=>102 i->105
for i in a:
print(chr(ord(i)-(105-102)),end="")