我用我们老师C++课上留的一道小学奥赛水平的弱智题的程序代码为例,先用MinGW编译,结果用IDA反编译出了几千个函数,全都是sub_加编号的名称,每一个都很短,变量名都是v1、v2等等的,一点也看不懂,我甚至连主函数在哪里都找不到。
然后又用VS2010编译,再反编译,令我大开眼界,函数名、变量名全能被正确地反编译出来,主程序反编译得也非常漂亮(那道题我就写了一个主函数)。
给大家展示下,
源程序的主函数:
int main(void){
now = tail = 0;
stk[0] = "http://www.acm.org/";
while ((cin >> in)&&(in[0] != 'Q')){
if (in[0] == 'V') {
now += 1;
cin >> stk[now];
cout << stk[now] << endl;
tail = now;
};
if (in[0] == 'B') {
if (now == 0){
cout << "Ignored" << endl;
}else{
-- now;
cout << stk[now] << endl;
};
};
if (in[0] == 'F') {
if (now == tail){
cout << "Ignored" << endl;
}else{
++ now;
cout << stk[now] << endl;
};
};
};
return 0;
};
用VS2010编译,然后反编译出的主函数:
int __cdecl main()
{
int v0; // eax@1
int *v1; // eax@2
int *v2; // eax@5
char v3; // zf@7
int v4; // eax@7
int v5; // eax@8
int *v6; // ecx@9
int v7; // eax@13
int *v8; // ecx@16
int v9; // eax@20
int v10; // eax@23
void *v12; // [sp-4h] [bp-Ch]@20
tail = 0;
now = 0;
std__basic_string_char_std__char_traits_char__std__allocator_char_____assign();
v0 = std__operator___char_std__char_traits_char__std__allocator_char____0(std__cin);
if ( (*(_DWORD *)(*(_DWORD *)(*(_DWORD *)v0 + 4) + v0 + 12) & 6) == 0 ? v0 + *(_DWORD *)(*(_DWORD *)v0 + 4) : 0 )
{
do
{
v1 = (int *)in;
if ( (unsigned int)dword_405098 < 0x10 )
v1 = ∈
if ( *(_BYTE *)v1 == 81 )
break;
v2 = (int *)in;
if ( (unsigned int)dword_405098 < 0x10 )
v2 = ∈
v3 = *(_BYTE *)v2 == 86;
v4 = now;
if ( v3 )
{
++now;
std__operator___char_std__char_traits_char__std__allocator_char____0(std__cin);
v5 = std__operator___char_std__char_traits_char__std__allocator_char_(std__cout, &stk + 7 * now);
std__basic_ostream_char_std__char_traits_char____operator__(v5, std__endl);
v4 = now;
tail = now;
}
v6 = (int *)in;
if ( (unsigned int)dword_405098 < 0x10 )
v6 = ∈
if ( *(_BYTE *)v6 == 66 )
{
if ( v4 )
{
now = v4 - 1;
v7 = std__operator___char_std__char_traits_char__std__allocator_char_(std__cout, &stk + 7 * now);
}
else
{
v7 = std__operator___std__char_traits_char_(std__cout);
}
std__basic_ostream_char_std__char_traits_char____operator__(v7, std__endl);
v4 = now;
}
v8 = (int *)in;
if ( (unsigned int)dword_405098 < 0x10 )
v8 = ∈
if ( *(_BYTE *)v8 == 70 )
{
if ( v4 == tail )
{
v12 = std__endl;
v9 = std__operator___std__char_traits_char_(std__cout);
}
else
{
v12 = std__endl;
now = v4 + 1;
v9 = std__operator___char_std__char_traits_char__std__allocator_char_(std__cout, &stk + 7 * now);
}
std__basic_ostream_char_std__char_traits_char____operator__(v9, v12);
}
v10 = std__operator___char_std__char_traits_char__std__allocator_char____0(std__cin);
}
while ( (*(_DWORD *)(*(_DWORD *)(*(_DWORD *)v10 + 4) + v10 + 12) & 6) == 0 ? v10 + *(_DWORD *)(*(_DWORD *)v10 + 4) : 0 );
}
return 0;
}
可以看出多出了很多临时变量,那些多数是寄存器变量,此外把C++的代码全部反编译成了C的代码。。
另外,刚刚找到了MinGW编译出的主函数,反编译完的不太一样,可以和VS的对比一下:
int __cdecl sub_4015D0()
{
int v0; // eax@2
int v2; // eax@4
char v3; // dl@6
int v4; // eax@17
int v5; // ebx@17
int v6; // esi@17
int v7; // eax@17
char v8; // al@19
int v9; // eax@20
int v10; // eax@22
int v11; // ebx@22
char v12; // al@24
int v13; // eax@25
int v14; // eax@26
int v15; // ebx@26
int v16; // esi@26
int v17; // eax@26
char v18; // al@28
int v19; // eax@29
int v20; // eax@30
int v21; // ebx@30
int v22; // esi@30
int v23; // eax@30
char v24; // al@32
int v25; // eax@33
int v26; // eax@38
int v27; // ebx@38
char v28; // al@40
int v29; // eax@41
sub_413960();
dword_4741B8 = 0;
dword_4741BC = 0;
sub_449910(dword_474020, "http://www.acm.org/", 19);
while ( 1 )
{
v0 = sub_40566C(&dword_4741E0, &dword_4741B4);
if ( *(_BYTE *)(v0 + *(_DWORD *)(*(_DWORD *)v0 - 12) + 20) & 5 )
return 0;
v2 = dword_4741B4;
if ( *(_DWORD *)(dword_4741B4 - 4) >= 0 )
{
sub_448C58(&dword_4741B4);
v2 = dword_4741B4;
}
v3 = *(_BYTE *)v2;
if ( *(_BYTE *)v2 == 81 )
return 0;
if ( *(_DWORD *)(v2 - 4) >= 0 )
{
sub_448C58(&dword_4741B4);
v2 = dword_4741B4;
v3 = *(_BYTE *)dword_4741B4;
}
if ( v3 == 86 )
{
++dword_4741BC;
sub_40566C(&dword_4741E0, 4 * dword_4741BC + 4669472);
v23 = sub_466D2C(&dword_474280, dword_474020[dword_4741BC], *(_DWORD *)(dword_474020[dword_4741BC] - 12));
v21 = v23;
v20 = *(_DWORD *)(*(_DWORD *)v23 - 12);
v22 = *(_DWORD *)(v21 + v20 + 124);
if ( !v22 )
goto LABEL_43;
if ( *(_BYTE *)(v22 + 28) )
{
v24 = *(_BYTE *)(v22 + 39);
}
else
{
sub_40623C(*(_DWORD *)(v21 + v20 + 124));
v24 = (*(int (__cdecl **)(int, signed int))(*(_DWORD *)v22 + 24))(v22, 10);
}
v25 = sub_4464E0(v21, v24);
sub_4466CC(v25);
dword_4741B8 = dword_4741BC;
v2 = dword_4741B4;
}
if ( *(_DWORD *)(v2 - 4) >= 0 )
{
sub_448C58(&dword_4741B4);
v2 = dword_4741B4;
}
if ( *(_BYTE *)v2 == 66 )
{
if ( dword_4741BC )
{
--dword_4741BC;
v17 = sub_466D2C(&dword_474280, dword_474020[dword_4741BC], *(_DWORD *)(dword_474020[dword_4741BC] - 12));
v15 = v17;
v14 = *(_DWORD *)(*(_DWORD *)v17 - 12);
v16 = *(_DWORD *)(v15 + v14 + 124);
if ( !v16 )
goto LABEL_43;
if ( *(_BYTE *)(v16 + 28) )
{
v18 = *(_BYTE *)(v16 + 39);
}
else
{
sub_40623C(*(_DWORD *)(v15 + v14 + 124));
v18 = (*(int (__cdecl **)(int, signed int))(*(_DWORD *)v16 + 24))(v16, 10);
}
v19 = sub_4464E0(v15, v18);
sub_4466CC(v19);
v2 = dword_4741B4;
}
else
{
sub_466D2C(&dword_474280, "Ignored", 7);
v10 = *(_DWORD *)(dword_474280 - 12);
v11 = *(int *)((char *)&dword_4742FC + v10);
if ( !v11 )
goto LABEL_43;
if ( *(_BYTE *)(v11 + 28) )
{
v12 = *(_BYTE *)(v11 + 39);
}
else
{
sub_40623C(*(int *)((char *)&dword_4742FC + v10));
v12 = (*(int (__cdecl **)(int, signed int))(*(_DWORD *)v11 + 24))(v11, 10);
}
v13 = sub_4464E0(&dword_474280, v12);
sub_4466CC(v13);
v2 = dword_4741B4;
}
}
if ( *(_DWORD *)(v2 - 4) >= 0 )
{
sub_448C58(&dword_4741B4);
v2 = dword_4741B4;
}
if ( *(_BYTE *)v2 == 70 )
{
if ( dword_4741BC == dword_4741B8 )
{
sub_466D2C(&dword_474280, "Ignored", 7);
v26 = *(_DWORD *)(dword_474280 - 12);
v27 = *(int *)((char *)&dword_4742FC + v26);
if ( !v27 )
LABEL_43:
sub_406800();
if ( *(_BYTE *)(v27 + 28) )
{
v28 = *(_BYTE *)(v27 + 39);
}
else
{
sub_40623C(*(int *)((char *)&dword_4742FC + v26));
v28 = (*(int (__cdecl **)(int, signed int))(*(_DWORD *)v27 + 24))(v27, 10);
}
v29 = sub_4464E0(&dword_474280, v28);
sub_4466CC(v29);
}
else
{
++dword_4741BC;
v7 = sub_466D2C(&dword_474280, dword_474020[dword_4741BC], *(_DWORD *)(dword_474020[dword_4741BC] - 12));
v5 = v7;
v4 = *(_DWORD *)(*(_DWORD *)v7 - 12);
v6 = *(_DWORD *)(v5 + v4 + 124);
if ( !v6 )
goto LABEL_43;
if ( *(_BYTE *)(v6 + 28) )
{
v8 = *(_BYTE *)(v6 + 39);
}
else
{
sub_40623C(*(_DWORD *)(v5 + v4 + 124));
v8 = (*(int (__cdecl **)(int, signed int))(*(_DWORD *)v6 + 24))(v6, 10);
}
v9 = sub_4464E0(v5, v8);
sub_4466CC(v9);
}
}
}
}