青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

聚星亭

吾笨笨且懶散兮 急須改之而奮進(jìn)
posts - 74, comments - 166, trackbacks - 0, articles - 0
  C++博客 :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理

    在函數(shù)調(diào)用的時(shí)候,無論是參數(shù)為對象還是返回一個(gè)對象,都將產(chǎn)生一個(gè)臨時(shí)對象。這個(gè)筆記就是為了學(xué)習(xí)這個(gè)臨時(shí)對象的產(chǎn)生過程而寫。

本代碼的詳細(xì)例子見實(shí)例代碼Ex.01

 

Ok,先讓我們定義一個(gè)類:

class CExample 

{

public:

       int m_nFirstNum;

       int m_nSecNum;

 

       int GetSum();

       bool SetNum(int nFirst, int nSec);

       CExample(){}                            // 空構(gòu)造,不實(shí)現(xiàn)任何功能

       virtual ~CExample(){}                 // 空析構(gòu)

 

};

 

// 定義的函數(shù)實(shí)現(xiàn)部分

int CExample::GetSum()

{

       return m_nFirstNum+m_nSecNum;

}

 

 

先讓我們看一下對象的創(chuàng)建過程

CExample objExp1;

//    00401393   lea         ecx,[ebp-18h]                  //  第一個(gè)對象

//    00401396   call        @ILT+20(CExample::CExample)

//    0040139B   mov         dword ptr [ebp-4],0              用來統(tǒng)計(jì)當(dāng)前對象個(gè)數(shù)

 

CExample objExp2;

//    004013A2   lea         ecx,[ebp-24h]                  //  第二個(gè)對象

//    004013A5   call        @ILT+20(CExample::CExample)

//    004013AA   mov         byte ptr [ebp-4],1

 

CExample objExp3;

//    004013AE   lea         ecx,[ebp-30h]                  //  第三個(gè)對象

//    004013B1   call        @ILT+20(CExample::CExample)

//    004013B6   mov         byte ptr [ebp-4],2

 

上面創(chuàng)建了三個(gè)對象,它們的過程都非常相似,將一個(gè)局部變量地址給了ECX寄存器,然后調(diào)用構(gòu)造函數(shù)。

先讓我們看看,構(gòu)造函數(shù)都干啥了:

12:   CExample::CExample()

13:   {

00401540   push        ebp

00401541   mov         ebp,esp

00401543   sub         esp,44h

00401546   push        ebx

00401547   push        esi

00401548   push        edi

00401549   push        ecx                                            // 保存寄存器環(huán)境

0040154A   lea         edi,[ebp-44h]

0040154D   mov         ecx,11h

00401552   mov         eax,0CCCCCCCCh

00401557   rep stos    dword ptr [edi]

00401559   pop         ecx                                                       // 填充完CC以后,恢復(fù)ECX內(nèi)容

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

0040155D   mov         eax,dword ptr [ebp-4]                           // 取到this指針

00401560   mov         dword ptr [eax],offset CExample::`vftable'   // this指針指向虛表

15:   }

00401566   mov         eax,dword ptr [ebp-4]

00401569   pop         edi

0040156A   pop         esi

0040156B   pop         ebx

0040156C   mov         esp,ebp

0040156E   pop         ebp

0040156F   ret

我們知道,我們再C代碼中,實(shí)現(xiàn)的是空構(gòu)造,沒有添加任何功能,可是反匯編的時(shí)候,發(fā)現(xiàn),函數(shù)應(yīng)該有個(gè)參數(shù)(是this指針),定位虛表的時(shí)候,是又構(gòu)造完成讓this指向虛表的工作的。

 

1、  傳遞一個(gè)對象的過程:

bool SetExpFun(CExample objExp)

{

       g_objExp.SetNum(objExp.m_nFirstNum, objExp.m_nSecNum);

       return true;

}

       這是我們樣例程序中,一個(gè)對象作為參數(shù)的情況。我們編寫如下的調(diào)用代碼:

       SetExpFun(objExp1);

 

       反匯編代碼如下:

       004013C8   sub         esp,0Ch                                    //     申請臨時(shí)對象空間

       004013CB   mov        ecx,esp                                     //     ECX指向臨時(shí)申請的對象

       004013CD   mov        dword ptr [ebp-34h],esp            //   賦值一份this

       004013D0   lea         eax,[ebp-18h]                             //   獲取第一個(gè)對象的this指針

       004013D3   push        eax                                              //   傳遞參數(shù)

       004013D4   call        @ILT+45(CExample::CExample)   //   使用了拷貝構(gòu)造所以有上面的參數(shù)

       004013D9   mov        dword ptr [ebp-48h],eax             //   產(chǎn)生一個(gè)臨時(shí)對象并保存它的this指針

       004013DC   call        @ILT+15(SetExpFun) (00401014)  //  調(diào)用函數(shù)

       004013E1   add         esp,0Ch

 

       上面代碼中,有兩處函數(shù)調(diào)用,一個(gè)是我們已經(jīng)非常熟悉的調(diào)用構(gòu)造函數(shù),另一個(gè)事調(diào)用我們需要的setExpFun函數(shù),當(dāng)然,通過上面的注釋,我們很容易就能知道,在這里創(chuàng)建了一個(gè)臨時(shí)的對象,而且貌似調(diào)用構(gòu)造函數(shù)的時(shí)候還傳遞了一個(gè)參數(shù)(參數(shù)是我們定義的第一個(gè)對象: objExp1)。

 

       是的,很明顯這里是個(gè)拷貝構(gòu)造,讓我們先來看下它的調(diào)用過程。

拷貝構(gòu)造

       {

              004011F0   push         ebp

              004011F1   mov         ebp,esp

              004011F3   sub          esp,44h

              004011F6   push         ebx

              004011F7   push         esi

              004011F8   push         edi

              004011F9   push         ecx                              ; 保存臨時(shí)對象的this指針

              004011FA   lea          edi,[ebp-44h]

              004011FD   mov         ecx,11h

              00401202   mov         eax,0CCCCCCCCh

              00401207   rep stos       dword ptr [edi]

              00401209   pop          ecx                              ; 找到調(diào)用時(shí)傳遞的臨時(shí)對象的this指針

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

              0040120D   mov         eax,dword ptr [ebp-4]

              00401210   mov               ecx,dword ptr [ebp+8]   ; 參數(shù)對象的this指針,ECX中是虛表

              00401213   mov         edx,dword ptr [ecx+4]   ; 取出參數(shù)對象的第一個(gè)成員

              00401216   mov         dword ptr [eax+4],edx    ; 并賦值給臨時(shí)對象的第一個(gè)成員

              00401219   mov         eax,dword ptr [ebp-4]

              0040121C   mov         ecx,dword ptr [ebp+8]

              0040121F   mov         edx,dword ptr [ecx+8]   ; 取到參數(shù)對象的第二個(gè)成員

              00401222   mov         dword ptr [eax+8],edx    ; 并賦值給臨時(shí)對象的第二個(gè)成員

              00401225   mov         eax,dword ptr [ebp-4]    ; 設(shè)置臨時(shí)對象的虛表

              00401228   mov         dword ptr [eax],offset CExample::`vftable'

              0040122E   mov         eax,dword ptr [ebp-4]    ; 返回一個(gè)臨時(shí)對象

              00401231   pop          edi

              00401232   pop          esi

              00401233   pop          ebx

              00401234   mov         esp,ebp

              00401236   pop          ebp

              00401237   ret           4

       }

 

從上面的代碼不難看出,我們這個(gè)拷貝構(gòu)造直接在參數(shù)中改寫的數(shù)據(jù),等出來這個(gè)函數(shù),我們main函數(shù)中:

004013C8   sub         esp,0Ch

申請的臨時(shí)對象空間中就是一個(gè)完整的對象了。

 

       好現(xiàn)在我們繼續(xù)跟蹤調(diào)用傳參的代碼:

       16:   bool SetExpFun(CExample objExp)

       17:   {

                     004012C0   push        ebp

                     004012C1   mov        ebp,esp

                     004012C3   push        0FFh

                     004012C5   push        offset __ehhandler$?SetExpFun@@YA_NVCExample@@@Z

                     004012CA   mov        eax,fs:[00000000]

                     004012D0   push        eax

                     004012D1   mov        dword ptr fs:[0],esp

                     004012D8   sub         esp,44h

                     004012DB   push        ebx

                     004012DC   push        esi

                     004012DD   push        edi

                     004012DE   lea          edi,[ebp-50h]

                     004012E1   mov         ecx,11h

                     004012E6   mov         eax,0CCCCCCCCh

                     004012EB   rep stos      dword ptr [edi]

                     004012ED   mov        dword ptr [ebp-4],0                      ; 計(jì)數(shù)對象數(shù)量

                     18:       g_objExp.SetNum(objExp.m_nFirstNum, objExp.m_nSecNum);

                     004012F4   mov         eax,dword ptr [ebp+0Ch]                    ; 直接引用臨時(shí)對象的成員

                     004012F7   push         eax

                     004012F8   mov         ecx,dword ptr [ebp+10h]

                     004012FB   push         ecx

                     004012FC   mov         ecx,offset g_objExp                     ; 傳遞this指針

                     00401301   call          @ILT+0(CExample::SetNum)

                     19:       return true;

                     00401306   mov         byte ptr [ebp-10h],1

                     0040130A   mov         dword ptr [ebp-4],0FFFFFFFFh   ; 清空臨時(shí)對象計(jì)數(shù)

                     00401311   lea          ecx,[ebp+8]                                  ; 取到臨時(shí)對象的this指針

                     00401314   call         @ILT+40(CExample::~CExample)

                     00401319   mov         al,byte ptr [ebp-10h]

       20:   }

       0040131C   mov         ecx,dword ptr [ebp-0Ch]

       0040131F   mov         dword ptr fs:[0],ecx

       00401326   pop         edi

       00401327   pop         esi

       00401328   pop         ebx

       00401329   add         esp,50h

       0040132C   cmp         ebp,esp

       0040132E   call        __chkesp (00401610)

       00401333   mov         esp,ebp

       00401335   pop         ebp

       00401336   ret

 

 

2、  返回一個(gè)對象的過程:

CExample GetExpFun()

{

       return g_objExp;

}

 

編寫如下的調(diào)用代碼:

       // 下面是返回對象的情況

       objExp2 = GetExpFun();

 

       調(diào)試下這個(gè)程序:

59:       objExp2 = GetExpFun();

       004013E4   lea         ecx,[ebp-40h]           ; 返回的臨時(shí)對象空間是進(jìn)入main函數(shù)的時(shí)候,提前分配好的。

       004013E7   push        ecx                                ;             先將對象壓棧

       004013E8   call        @ILT+25(GetExpFun)      ;             調(diào)用函數(shù)

              11:   CExample GetExpFun()

              12:   {

              00401190   push        ebp

              00401191   mov         ebp,esp

              00401193   sub         esp,44h

              00401196   push        ebx

              00401197   push        esi

              00401198   push        edi

              00401199   lea         edi,[ebp-44h]

              0040119C   mov         ecx,11h

              004011A1   mov         eax,0CCCCCCCCh

              004011A6   rep stos    dword ptr [edi]

              004011A8   mov         dword ptr [ebp-4],0

              13:       return g_objExp;

              004011AF   push        offset g_objExp (0042af80)

              004011B4   mov         ecx,dword ptr [ebp+8]                 ; 引用傳進(jìn)來的參數(shù)對象指針

              004011B7   call        @ILT+45(CExample::CExample)       ; 調(diào)用構(gòu)造創(chuàng)建對象

              004011BC   mov         eax,dword ptr [ebp-4]

              004011BF   or          al,1

              004011C1   mov         dword ptr [ebp-4],eax                  ; 更新對象個(gè)數(shù)

              004011C4   mov         eax,dword ptr [ebp+8]                 ; 返回……

              14:   }

              004011C7   pop         edi

              004011C8   pop         esi

              004011C9   pop         ebx

              004011CA   add         esp,44h

              004011CD   cmp         ebp,esp

              004011CF   call        __chkesp

              004011D4   mov         esp,ebp

              004011D6   pop         ebp

              004011D7   ret

 

       004013ED   add         esp,4                                   

       004013F0   mov         dword ptr [ebp-4Ch],eax                     ; 保存臨時(shí)對象的指針

       004013F3   mov         edx,dword ptr [ebp-4Ch]

       004013F6   mov         dword ptr [ebp-50h],edx

       004013F9   mov         byte ptr [ebp-4],3

       004013FD   mov         eax,dword ptr [ebp-50h]              ; 這里重載的 = 運(yùn)算符,因此將副本壓棧做復(fù)制操作

       00401400   push        eax

       00401401   lea         ecx,[ebp-24h]                                ; 得到第二個(gè)對象的this指針

       00401404   call        @ILT+10(CExample::operator=)

       00401409   mov         byte ptr [ebp-4],2

       0040140D   lea         ecx,[ebp-40h]                                ; 使用完成,釋放臨時(shí)對象

       00401410   call        @ILT+40(CExample::~CExample)

 

       printf("%d\r\n", objExp2.GetSum());

 

       OK,只要搗鼓明白了這個(gè)臨時(shí)對象,那我們的好多問題都可以解決了。

                                             

青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            亚洲国产婷婷| 红桃视频一区| 亚洲一区二区三区激情| 国产欧美日韩亚洲一区二区三区| 亚洲欧美国产日韩天堂区| 欧美久久视频| 亚洲一区二区三区视频播放| 欧美一区国产一区| 国产一区二区三区直播精品电影| 欧美一区视频| 久久久精品日韩欧美| 亚洲人成人77777线观看| 亚洲精品国产视频| 欧美午夜精品久久久久久久| 一区二区三区高清| 久久激情久久| 亚洲欧美综合精品久久成人| 亚洲精品一区久久久久久| 欧美国产日韩在线观看| 久热精品视频在线观看一区| 欧美大色视频| 亚洲欧美视频在线| 亚洲国产精品久久久久婷婷884| 亚洲午夜激情| 欧美第一黄色网| 久久婷婷国产麻豆91天堂| 欧美日韩大陆在线| 欧美激情va永久在线播放| 国产免费一区二区三区香蕉精| 亚洲第一精品电影| 很黄很黄激情成人| 亚洲自拍偷拍一区| 亚洲欧美韩国| 欧美小视频在线| 一本色道综合亚洲| 欧美精品在线观看一区二区| 久久久亚洲高清| 黄色成人精品网站| 久久精品国产成人| 欧美激情亚洲| 欧美一级理论片| 国产精品一区久久久久| 亚洲一区二区三区精品动漫| 99re在线精品| 欧美三区在线| 午夜精品福利视频| 久久久精品国产免大香伊| 国产欧美日韩一区二区三区在线观看| 一本久久综合亚洲鲁鲁| 亚洲一区二区影院| 国产一区二区三区免费不卡| 亚洲一区二区三区影院| 国产精品免费网站在线观看| 久久aⅴ国产欧美74aaa| 欧美 日韩 国产一区二区在线视频| 欧美在线影院在线视频| 欧美激情精品久久久久| 亚洲欧美国产一区二区三区| 国产精品久久久99| 久久一区二区三区av| 日韩一级黄色片| 久久不射中文字幕| a4yy欧美一区二区三区| 国产综合av| 国产精品成人一区二区网站软件| 韩国在线视频一区| 猛干欧美女孩| 久久gogo国模啪啪人体图| 久久婷婷亚洲| 久久超碰97人人做人人爱| 99riav1国产精品视频| 亚洲电影网站| 开心色5月久久精品| 欧美xxxx在线观看| 免费日韩成人| 美女脱光内衣内裤视频久久网站| 99综合在线| 亚洲麻豆国产自偷在线| 一区二区三区在线观看欧美| 欧美日韩国产在线观看| 欧美福利电影在线观看| 久久亚洲高清| 久久色中文字幕| 久久深夜福利免费观看| 久久久精品日韩欧美| 国产日韩欧美一二三区| 亚洲精品综合久久中文字幕| 91久久久久久国产精品| 亚洲精品美女在线观看| 亚洲免费福利视频| 看片网站欧美日韩| 国产精品mv在线观看| 久久夜色精品亚洲噜噜国产mv| 久久亚洲欧美国产精品乐播| 欧美影院视频| 亚洲欧美另类中文字幕| 欧美一级久久久| 欧美成人午夜77777| 欧美视频在线免费| 韩国欧美一区| 99热在这里有精品免费| 欧美一级日韩一级| 亚洲国产精品成人精品| 亚洲一级黄色av| 久久综合狠狠综合久久综合88 | 久久精品国产久精国产爱| 国产精品嫩草影院av蜜臀| 欧美激情1区| 亚洲资源av| 亚洲精品日韩激情在线电影| 亚洲永久字幕| 国产精品久久久久久久7电影| 精品av久久久久电影| 亚洲欧美成人一区二区在线电影 | 欧美一区二区三区久久精品茉莉花 | 一区二区三区四区五区精品| 亚洲女同同性videoxma| 国产日韩亚洲| 一区二区不卡在线视频 午夜欧美不卡' | 日韩系列欧美系列| 老司机一区二区三区| 欧美激情一区二区三区不卡| 国产亚洲欧洲997久久综合| 亚洲自拍都市欧美小说| 国产精品久久久久一区二区三区共 | 欧美日本精品在线| 欧美大胆人体视频| 久热精品视频| 免费观看日韩| 亚洲免费观看在线观看| 亚洲视频精品在线| 欧美一级电影久久| 久久嫩草精品久久久精品一| 国产一区av在线| 国产农村妇女精品一二区| 久久亚洲综合网| 99精品国产在热久久| 亚洲一区国产| 欧美激情一区三区| 国产在线视频欧美一区二区三区| 久久综合狠狠| 午夜精品国产更新| 亚洲日本中文字幕| 欧美一区在线直播| 欧美视频在线观看一区| 欧美一级午夜免费电影| 浪潮色综合久久天堂| 欧美日一区二区在线观看| 激情成人在线视频| 亚洲女优在线| 在线亚洲免费视频| 99在线观看免费视频精品观看| 亚洲精品三级| 麻豆精品在线视频| 亚洲一区亚洲二区| 欧美日韩国产一中文字不卡| 亚洲国产美女久久久久| 久久精品99国产精品酒店日本| 亚洲精品小视频在线观看| 久久精品国产精品亚洲综合| 国产欧美日韩不卡| 国产精品激情| 亚洲国产女人aaa毛片在线| 欧美一级欧美一级在线播放| 亚洲精品日韩在线| 韩国av一区二区三区四区| 一本一道久久综合狠狠老精东影业| 亚洲激情成人| 欧美日韩综合视频| 亚洲嫩草精品久久| 久久噜噜亚洲综合| 久久午夜视频| 一区二区亚洲精品| 欧美精品一区视频| 亚洲女优在线| 欧美成人精品在线播放| 亚洲无限乱码一二三四麻| 黄色日韩精品| 欧美三级小说| 久久免费视频网| 亚洲一区二区精品在线观看| 欧美黑人国产人伦爽爽爽| 午夜精品婷婷| 日韩视频在线一区二区三区| 国产亚洲精品久久久久久| 欧美精品在线播放| 久久久女女女女999久久| 亚洲视频www| 91久久午夜| 另类成人小视频在线| 亚洲欧美视频一区| 亚洲精品中文字幕在线观看| 久久国产精彩视频| 亚洲精品欧美日韩专区| 噜噜噜躁狠狠躁狠狠精品视频| 亚洲欧美电影院| 一区二区高清| 99国产麻豆精品| 91久久精品国产91久久| 黄色一区二区三区四区|