你的位置:首页 > ASP.net教程

[ASP.net教程]C++反汇编学习笔记(五)各种算数运算的工作形式(3)


1、  自增、自减

  很简单,没什么可解释的,注意一下前缀和后缀运算的区别

C++源码

Debug版

Release版

#include <iostream>

using namespace std;

int main()

{

         int a, b;

         cin >> a >> b;

         //自增

         a = ++b + 10;

         cout << a;

         a = (b++ )- 10;

         cout << a;

         //自减

         a = --b - 10;

         cout << a;

         a = (b--) - 10;

         cout << a;

 

         system("pause");

         return 0;

}

#include <iostream>

using namespace std;

int main()

{

..............略

         int a, b;

         cin >> a >> b;

...........略

         //自增

         a = ++b + 10;

008C5EB6  mov         eax,dword ptr [b] 

008C5EB9  add         eax,1 

008C5EBC  mov         dword ptr [b],eax 

008C5EBF  mov         ecx,dword ptr [b] 

008C5EC2  add         ecx,0Ah 

008C5EC5  mov         dword ptr [a],ecx 

         cout << a;

008C5EC8  mov         esi,esp 

008C5ECA  mov         eax,dword ptr [a] 

008C5ECD  push        eax 

008C5ECE  mov         ecx,dword ptr ds:[8D10A8h] 

008C5ED4  call        dword ptr ds:[8D1094h] 

008C5EDA  cmp         esi,esp 

008C5EDC  call        __RTC_CheckEsp (08C1339h) 

         a = (b++ )- 10;

008C5EE1  mov         eax,dword ptr [b] 

008C5EE4  sub         eax,0Ah 

008C5EE7  mov         dword ptr [a],eax 

008C5EEA  mov         ecx,dword ptr [b] 

008C5EED  add         ecx,1 

008C5EF0  mov         dword ptr [b],ecx 

         cout << a;

008C5EF3  mov         esi,esp 

008C5EF5  mov         eax,dword ptr [a] 

008C5EF8  push        eax 

008C5EF9  mov         ecx,dword ptr ds:[8D10A8h] 

008C5EFF  call        dword ptr ds:[8D1094h] 

008C5F05  cmp         esi,esp 

008C5F07  call        __RTC_CheckEsp (08C1339h) 

         //自减

         a = --b - 10;

008C5F0C  mov         eax,dword ptr [b] 

008C5F0F  sub         eax,1 

008C5F12  mov         dword ptr [b],eax 

008C5F15  mov         ecx,dword ptr [b] 

008C5F18  sub         ecx,0Ah 

008C5F1B  mov         dword ptr [a],ecx 

         cout << a;

008C5F1E  mov         esi,esp 

008C5F20  mov         eax,dword ptr [a] 

008C5F23  push        eax 

008C5F24  mov         ecx,dword ptr ds:[8D10A8h] 

008C5F2A  call        dword ptr ds:[8D1094h] 

008C5F30  cmp         esi,esp 

008C5F32  call        __RTC_CheckEsp (08C1339h) 

         a = (b--) - 10;

008C5F37  mov         eax,dword ptr [b] 

         a = (b--) - 10;

008C5F3A  sub         eax,0Ah 

008C5F3D  mov         dword ptr [a],eax 

008C5F40  mov         ecx,dword ptr [b] 

008C5F43  sub         ecx,1 

008C5F46  mov         dword ptr [b],ecx 

         cout << a;

008C5F49  mov         esi,esp 

008C5F4B  mov         eax,dword ptr [a] 

008C5F4E  push        eax 

008C5F4F  mov         ecx,dword ptr ds:[8D10A8h] 

008C5F55  call        dword ptr ds:[8D1094h] 

008C5F5B  cmp         esi,esp 

008C5F5D  call        __RTC_CheckEsp (08C1339h) 

 

         system("pause");

008C5F62  mov         esi,esp 

008C5F64  push        8CDC70h 

008C5F69  call        dword ptr ds:[8D11DCh] 

008C5F6F  add         esp,4 

008C5F72  cmp         esi,esp 

008C5F74  call        __RTC_CheckEsp (08C1339h) 

         return 0;

008C5F79  xor         eax,eax 

}

..............略

#include <iostream>

using namespace std;

int main()

{

012E12A0  push        ebp 

012E12A1  mov         ebp,esp 

012E12A3  sub         esp,0Ch 

012E12A6  mov         eax,dword ptr ds:[012E4000h] 

012E12AB  xor         eax,ebp 

012E12AD  mov         dword ptr [ebp-4],eax 

         int a, b;

         cin >> a >> b;

012E12B0  mov         ecx,dword ptr ds:[12E3038h] 

         int a, b;

         cin >> a >> b;

012E12B6  lea         eax,[b] 

012E12B9  push        eax 

012E12BA  lea         eax,[a] 

012E12BD  push        eax 

012E12BE  call        dword ptr ds:[12E3028h] 

012E12C4  mov         ecx,eax 

012E12C6  call        dword ptr ds:[12E3028h] 

         //自增

         a = ++b + 10;

012E12CC  mov         eax,dword ptr [b] 

         cout << a;

012E12CF  mov         ecx,dword ptr ds:[12E303Ch] 

//从内存中取得b的值放入寄存器eax,然后加1,再放回内存,

//并将b加1后(eax)的结果与10相加,最后将最终结果压栈,作为cout<<的参数,保存到变量a中。

012E12D5  inc         eax 

012E12D6  mov         dword ptr [b],eax 

012E12D9  add         eax,0Ah 

012E12DC  push        eax 

012E12DD  mov         dword ptr [a],eax 

012E12E0  call        dword ptr ds:[12E3024h] 

         a = (b++ )- 10;

012E12E6  mov         eax,dword ptr [b] 

012E12E9  lea         ecx,[eax-0Ah]  //b+10

012E12EC  inc         eax  //b+1

012E12ED  mov         dword ptr [a],ecx  //将b+10的结果保存到a变量中

         cout << a;

012E12F0  push        ecx  //将b+10的结果压栈作为cout<<的参数

012E12F1  mov         ecx,dword ptr ds:[12E303Ch] 

012E12F7  mov         dword ptr [b],eax  //将b+1的结果放回变量b中。

012E12FA  call        dword ptr ds:[12E3024h] 

         //自减

         a = --b - 10;

//减法与加法同理

012E1300  mov         eax,dword ptr [b] 

         cout << a;

012E1303  mov         ecx,dword ptr ds:[12E303Ch] 

012E1309  dec         eax 

012E130A  mov         dword ptr [b],eax 

012E130D  add         eax,0FFFFFFF6h 

012E1310  push        eax 

         cout << a;

012E1311  mov         dword ptr [a],eax 

012E1314  call        dword ptr ds:[12E3024h] 

         a = (b--) - 10;

012E131A  mov         eax,dword ptr [b] 

012E131D  lea         ecx,[eax-0Ah] 

012E1320  dec         eax 

012E1321  mov         dword ptr [a],ecx 

         cout << a;

012E1324  push        ecx 

012E1325  mov         ecx,dword ptr ds:[12E303Ch] 

012E132B  mov         dword ptr [b],eax 

012E132E  call        dword ptr ds:[12E3024h] 

 

         system("pause");

012E1334  push        12E319Ch 

012E1339  call        dword ptr ds:[12E30C4h] 

         return 0;

}

............略

 

 

2、  关系运算和条件跳转

  关系运算的作用是比较关系运算符左右两边的操作数的值,得出一个判断结果,真或假;然后根据关系运算的结果,选择对应的条件跳转指令。

  通常情况下,条件跳转指令都与CMP和TEST匹配出现。但条件跳转指令检查的是标记位,在算术运算等有修改标记位的代码处,也可以根据需要使用条件跳转指令来修改程序流程。

 

 

3、  位运算

  二进制数据的运算称为位运算,位运算操作符有:

    <<:左移,最高位左移到CF中,最低位补零。

    >>:右移,最高位不变,最低位右移到CF中

    |:位或,两数的相同位,只要有一个为1,则结果为1

    &:位于,两数的相同位,只要有一个为0,则结果为0

    ^:异或,两数的相同位,相同是为0,不同时为1

    ~:取反,想操作数的每一位,1变0,0变1

  Debug和relase版没有太大区别,很简单。

C++源码

Debug

Release版

#include <iostream>

using namespace std;

int main()

{

         int a, b;

         cin >> a >> b;

         //左移

         a=a << 2;

         cout << a;

         //右移

         a=a >> 2;

         cout << a;

         //位与

         a = a & b;

         cout << a;

         //位或

         a = a | b;

         cout << a;

         //异或

         a = a^b;

         cout << a;

         //取反

         a = ~a;

         cout << a;

 

         system("pause");

         return 0;

}

#include <iostream>

using namespace std;

int main()

{

............略

         int a, b;

         cin >> a >> b;

..............略

         //左移

         a=a << 2;

01345EB6  mov         eax,dword ptr [a] 

01345EB9  shl         eax,2 

01345EBC  mov         dword ptr [a],eax 

         cout << a;

01345EBF  mov         esi,esp 

01345EC1  mov         eax,dword ptr [a] 

01345EC4  push        eax 

01345EC5  mov         ecx,dword ptr ds:[13510A8h] 

01345ECB  call        dword ptr ds:[1351094h] 

01345ED1  cmp         esi,esp 

01345ED3  call        __RTC_CheckEsp (01341339h) 

         //右移

         a=a >> 2;

01345ED8  mov         eax,dword ptr [a] 

01345EDB  sar         eax,2 

01345EDE  mov         dword ptr [a],eax 

         cout << a;

01345EE1  mov         esi,esp 

01345EE3  mov         eax,dword ptr [a] 

01345EE6  push        eax 

01345EE7  mov         ecx,dword ptr ds:[13510A8h] 

01345EED  call        dword ptr ds:[1351094h] 

01345EF3  cmp         esi,esp 

01345EF5  call        __RTC_CheckEsp (01341339h) 

         //位与

         a = a & b;

01345EFA  mov         eax,dword ptr [a] 

01345EFD  and         eax,dword ptr [b] 

01345F00  mov         dword ptr [a],eax 

         cout << a;

01345F03  mov         esi,esp 

01345F05  mov         eax,dword ptr [a] 

01345F08  push        eax 

01345F09  mov         ecx,dword ptr ds:[13510A8h] 

01345F0F  call        dword ptr ds:[1351094h] 

01345F15  cmp         esi,esp 

01345F17  call        __RTC_CheckEsp (01341339h) 

         //位或

         a = a | b;

01345F1C  mov         eax,dword ptr [a] 

01345F1F  or          eax,dword ptr [b] 

01345F22  mov         dword ptr [a],eax 

         cout << a;

01345F25  mov         esi,esp 

01345F27  mov         eax,dword ptr [a] 

01345F2A  push        eax 

01345F2B  mov         ecx,dword ptr ds:[13510A8h] 

01345F31  call        dword ptr ds:[1351094h] 

01345F37  cmp         esi,esp 

         cout << a;

01345F39  call        __RTC_CheckEsp (01341339h) 

         //异或

         a = a^b;

01345F3E  mov         eax,dword ptr [a] 

01345F41  xor         eax,dword ptr [b] 

01345F44  mov         dword ptr [a],eax 

         cout << a;

01345F47  mov         esi,esp 

01345F49  mov         eax,dword ptr [a] 

01345F4C  push        eax 

01345F4D  mov         ecx,dword ptr ds:[13510A8h] 

01345F53  call        dword ptr ds:[1351094h] 

01345F59  cmp         esi,esp 

01345F5B  call        __RTC_CheckEsp (01341339h) 

         //取反

         a = ~a;

01345F60  mov         eax,dword ptr [a] 

01345F63  not         eax 

01345F65  mov         dword ptr [a],eax 

         cout << a;

01345F68  mov         esi,esp 

01345F6A  mov         eax,dword ptr [a] 

01345F6D  push        eax 

01345F6E  mov         ecx,dword ptr ds:[13510A8h] 

01345F74  call        dword ptr ds:[1351094h] 

01345F7A  cmp         esi,esp 

01345F7C  call        __RTC_CheckEsp (01341339h) 

 

         system("pause");

.............略

         return 0;

01345F98  xor         eax,eax 

}

..............略

#include <iostream>

using namespace std;

int main()

{

011712A0  push        ebp 

011712A1  mov         ebp,esp 

011712A3  sub         esp,0Ch 

011712A6  mov         eax,dword ptr ds:[01174000h] 

011712AB  xor         eax,ebp 

011712AD  mov         dword ptr [ebp-4],eax 

         int a, b;

         cin >> a >> b;

011712B0  mov         ecx,dword ptr ds:[1173038h] 

         int a, b;

         cin >> a >> b;

011712B6  lea         eax,[b] 

011712B9  push        eax 

011712BA  lea         eax,[a] 

011712BD  push        eax 

011712BE  call        dword ptr ds:[1173028h] 

011712C4  mov         ecx,eax 

011712C6  call        dword ptr ds:[1173028h] 

         //左移

         a=a << 2;

011712CC  mov         eax,dword ptr [a] 

         cout << a;

011712CF  mov         ecx,dword ptr ds:[117303Ch] 

011712D5  shl         eax,2 

011712D8  push        eax 

011712D9  mov         dword ptr [a],eax 

011712DC  call        dword ptr ds:[1173024h] 

         //右移

         a=a >> 2;

011712E2  mov         eax,dword ptr [a] 

         cout << a;

011712E5  mov         ecx,dword ptr ds:[117303Ch] 

011712EB  sar         eax,2 

011712EE  push        eax 

011712EF  mov         dword ptr [a],eax 

011712F2  call        dword ptr ds:[1173024h] 

         //位与

         a = a & b;

011712F8  mov         eax,dword ptr [a] 

011712FB  and         eax,dword ptr [b] 

         cout << a;

011712FE  mov         ecx,dword ptr ds:[117303Ch] 

01171304  push        eax 

01171305  mov         dword ptr [a],eax 

01171308  call        dword ptr ds:[1173024h] 

         //位或

         a = a | b;

0117130E  mov         eax,dword ptr [a] 

01171311  or          eax,dword ptr [b] 

         cout << a;

01171314  mov         ecx,dword ptr ds:[117303Ch] 

0117131A  push        eax 

         cout << a;

0117131B  mov         dword ptr [a],eax 

0117131E  call        dword ptr ds:[1173024h] 

         //异或

         a = a^b;

01171324  mov         eax,dword ptr [a] 

01171327  xor         eax,dword ptr [b] 

         cout << a;

0117132A  mov         ecx,dword ptr ds:[117303Ch] 

01171330  push        eax 

01171331  mov         dword ptr [a],eax 

01171334  call        dword ptr ds:[1173024h] 

         //取反

         a = ~a;

0117133A  mov         eax,dword ptr [a] 

         cout << a;

0117133D  mov         ecx,dword ptr ds:[117303Ch] 

01171343  not         eax 

01171345  push        eax 

01171346  mov         dword ptr [a],eax 

01171349  call        dword ptr ds:[1173024h] 

 

         system("pause");

0117134F  push        117319Ch 

01171354  call        dword ptr ds:[11730C4h] 

         return 0;

}

0117135A  mov         ecx,dword ptr [ebp-4] 

0117135D  add         esp,4 

01171360  xor         ecx,ebp 

01171362  xor         eax,eax 

01171364  call        __security_check_cookie (011717ADh) 

01171369  mov         esp,ebp 

0117136B  pop         ebp 

0117136C  ret