真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

c語言函數(shù)調(diào)用過程(棧幀的創(chuàng)建與銷毀)-創(chuàng)新互聯(lián)

從匯編的角度解析函數(shù)調(diào)用過程

為貴溪等地區(qū)用戶提供了全套網(wǎng)頁設計制作服務,及貴溪網(wǎng)站建設行業(yè)解決方案。主營業(yè)務為網(wǎng)站設計、成都網(wǎng)站建設、貴溪網(wǎng)站設計,以傳統(tǒng)方式定制建設網(wǎng)站,并提供域名空間備案等一條龍服務,秉承以專業(yè)、用心的態(tài)度為用戶提供真誠的服務。我們深信只要達到每一位用戶的要求,就會得到認可,從而選擇與我們長期合作。這樣,我們也可以走得更遠!

看看下面這個簡單函數(shù)的調(diào)用過程:

int Add(int x,int y)
{
    int sum = 0;
    sum = x + y;
    return sum;
}

int main ()
{
    int a = 10;
    int b = 12;
    int ret = 0;
    ret = Add(a,b);
    return 0;
}

今天主要用匯編代碼去講述這個過程,首先介紹幾個寄存器和簡單的匯編指令的意思。
先看幾個函數(shù)調(diào)用過程涉及到的寄存器:
(1)esp:棧指針寄存器(extended stack pointer),其內(nèi)存放著一個指針,該指針永遠指向系統(tǒng)棧最上面一個棧幀的棧頂。
(2)ebp:基址指針寄存器(extended base pointer),其內(nèi)存放著一個指針,該指針永遠指向系統(tǒng)棧最上面一個棧幀的底部。
(3)eax 是”累加器”(accumulator), 它是很多加法乘法指令的缺省寄存器。
(4)ebx 是”基地址”(base)寄存器, 在內(nèi)存尋址時存放基地址。
(5)ecx 是計數(shù)器(counter), 是重復(REP)前綴指令和LOOP指令的內(nèi)定計數(shù)器。
(6)edx 則總是被用來放整數(shù)除法產(chǎn)生的余數(shù)。
(7)esi/edi分別叫做”源/目標索引寄存器”(source/destination index),因為在很多字符串操作指令中, DS:ESI指向源串,而ES:EDI指向目標串.
在32位平臺上,ESP每次減少4字節(jié)。
再看幾條簡單的匯編指令:
mov :數(shù)據(jù)傳送指令,也是最基本的編程指令,用于將一個數(shù)據(jù)從源地址傳送到目標地址(寄存器間的數(shù)據(jù)傳送本質(zhì)上也是一樣的)
sub:減法指令
lea:取偏移地址
push:實現(xiàn)壓入操作的指令是PUSH指令
pop:實現(xiàn)彈出操作的指令
call:用于保存當前指令的下一條指令并跳轉(zhuǎn)到目標函數(shù)。
這些指令當然能看懂最好,可以讓你很深刻的理解函數(shù)調(diào)用過程,不能看懂就只能通過我的描述去理解了。
進行分析之前,先來了解下內(nèi)存地址空間的分布:
c語言函數(shù)調(diào)用過程(棧幀的創(chuàng)建與銷毀)
??臻g是向低地址增長的,主要是用來保存函數(shù)棧幀。 ??臻g的大小很有限,僅有區(qū)區(qū)幾MB大小
匯編代碼實現(xiàn):
main函數(shù)匯編代碼:

int main ()
{
011B26E0  push        ebp  
011B26E1  mov         ebp,esp 
011B26E3  sub         esp,0E4h 
011B26E9  push        ebx  
011B26EA  push        esi  
011B26EB  push        edi  
011B26EC  lea         edi,[ebp-0E4h] 
011B26F2  mov         ecx,39h 
011B26F7  mov         eax,0CCCCCCCCh 
011B26FC  rep stos    dword ptr es:[edi] 
    int a = 10;
011B26FE  mov         dword ptr [a],0Ah 
    int b = 12;
011B2705  mov         dword ptr [b],0Ch 
    int ret = 0;
011B270C  mov         dword ptr [ret],0 
    ret = Add(a,b);
011B2713  mov         eax,dword ptr [b] 
011B2716  push        eax  
011B2717  mov         ecx,dword ptr [a] 
011B271A  push        ecx  
011B271B  call        @ILT+640(_Add) (11B1285h) 
011B2720  add         esp,8 
011B2723  mov         dword ptr [ret],eax 
    return 0;
011B2726  xor         eax,eax 
}
011B2728  pop         edi  
011B2729  pop         esi  
011B272A  pop         ebx  
011B272B  add         esp,0E4h 
011B2731  cmp      
@ILT+450(__RTC_CheckEsp) (11B11C7h) 
011B2738  mov         esp,ebp 
011B273A  pop         ebp  
011B273B  ret

Add函數(shù)匯編代碼

int Add(int x,int y)
{
011B26A0  push        ebp  
011B26A1  mov         ebp,esp 
011B26A3  sub         esp,0CCh 
011B26A9  push        ebx  
011B26AA  push        esi  
011B26AB  push        edi  
011B26AC  lea         edi,[ebp-0CCh] 
011B26B2  mov         ecx,33h 
011B26B7  mov         eax,0CCCCCCCCh 
011B26BC  rep stos    dword ptr es:[edi] 
    int sum = 0;
011B26BE  mov         dword ptr [sum],0 
    sum = x + y;
011B26C5  mov         eax,dword ptr [x] 
011B26C8  add         eax,dword ptr [y] 
011B26CB  mov         dword ptr [sum],eax 
    return sum;
011B26CE  mov         eax,dword ptr [sum] 
}
011B26D1  pop         edi  
011B26D2  pop         esi  
011B26D3  pop         ebx  
011B26D4  mov         esp,ebp 
011B26D6  pop         ebp  
011B26D7  ret

下面圖中詳細描述了調(diào)用過程地址變化(此處所有地址是取自32位windows系統(tǒng)vs編輯器下的調(diào)試過程。):

c語言函數(shù)調(diào)用過程(棧幀的創(chuàng)建與銷毀)

過程描述:
1、參數(shù)拷貝(參數(shù)實例化)。
2、保存當前指令的下一條指令,并跳轉(zhuǎn)到被調(diào)函數(shù)。
這些操作均在main函數(shù)中進行。

接下來是調(diào)用Add函數(shù)并執(zhí)行的一些操作,包括:
1、移動ebp、esp形成新的棧幀結構。
2、壓棧(push)形成臨時變量并執(zhí)行相關操作。
3、return一個值。
這些操作在Add函數(shù)中進行。

被調(diào)函數(shù)完成相關操作后需返回到原函數(shù)中執(zhí)行下一條指令,操作如下:
1、出棧(pop)。
2、回復main函數(shù)的棧幀結構。(pop )
3、返回main函數(shù)
這些操作也在Add函數(shù)中進行。 至此,在main函數(shù)中調(diào)用Add函數(shù)的整個過程已經(jīng)完成。
總結起來整個過程就三步:
1)根據(jù)調(diào)用的函數(shù)名找到函數(shù)入口;
2)在棧中審請調(diào)用函數(shù)中的參數(shù)及函數(shù)體內(nèi)定義的變量的內(nèi)存空間
3)函數(shù)執(zhí)行完后,釋放函數(shù)在棧中的審請的參數(shù)和變量的空間,最后返回值(如果有的話)
如果你學了微機原理,你會想到cpu中斷處理過程,是的,函數(shù)調(diào)用過程和中斷處理過程一模一樣。

函數(shù)調(diào)用約定:
這里再補充一下各種調(diào)用規(guī)定的基本內(nèi)容。
_stdcall調(diào)用約定

所有參數(shù)按照從右到左壓入堆棧,由被調(diào)用的子程序清理堆棧

_cdecl調(diào)用約定(The C default calling convention,C調(diào)用規(guī)定)

參數(shù)也是從右到左壓入堆棧,但由調(diào)用者清理堆棧。

_fastcall調(diào)用約定

顧名思義,_fastcall的目的主要是為了更快的調(diào)用函數(shù)。它主要依靠寄存器傳遞參數(shù),剩下的參數(shù)依然按照從右到左的順序壓入堆棧,并由被調(diào)用的子程序清理堆棧。

本篇博文是按調(diào)用約定stdcall 調(diào)用函數(shù)。

csdn博客地址:http://blog.csdn.net/qq_38646470

另外有需要云服務器可以了解下創(chuàng)新互聯(lián)scvps.cn,海內(nèi)外云服務器15元起步,三天無理由+7*72小時售后在線,公司持有idc許可證,提供“云服務器、裸金屬服務器、高防服務器、香港服務器、美國服務器、虛擬主機、免備案服務器”等云主機租用服務以及企業(yè)上云的綜合解決方案,具有“安全穩(wěn)定、簡單易用、服務可用性高、性價比高”等特點與優(yōu)勢,專為企業(yè)上云打造定制,能夠滿足用戶豐富、多元化的應用場景需求。


當前名稱:c語言函數(shù)調(diào)用過程(棧幀的創(chuàng)建與銷毀)-創(chuàng)新互聯(lián)
當前URL:http://weahome.cn/article/cogpjh.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部