淺析C語言中的棧操作
時間(jian):2016-12-13作者:華清遠見
匯編/C語言中的'數據棧'跟數據結構中的'邏輯棧'類似都是遵循先進后(hou)出后(hou)進先出原則,但是在實際操作過程中的基本單(dan)位(wei)不同: 1.在數據(ju)結構(gou)中的(de)(de)'邏輯(ji)棧'按照使用者自己的(de)(de)需求定義(yi)大小及(ji)基本單位。例如可以存放(fang)10個(ge)char型(xing),也可以存放(fang)20個(ge)結構(gou)體等(deng)。 2.在(zai)匯編或C語言本(ben)身的'數(shu)據(ju)棧'中棧大(da)小由編譯器指定(ding),遵循(xun)FIFO規(gui)則的基本(ben)單位是棧幀,即每調(diao)用一個函(han)數(shu)都會(hui)有一個新的棧幀加入,而函(han)數(shu)返回則以棧幀為單位出(chu)棧。 棧幀(zhen)也(ye)叫過(guo)程活(huo)動記錄,是編譯器用(yong)來(lai)實現過(guo)程/函(han)(han)數調用(yong)的一(yi)種數據結(jie)構。其實就(jiu)是一(yi)個函(han)(han)數執行的環(huan)境:函(han)(han)數參數、函(han)(han)數的局部(bu)變量、函(han)(han)數執行完后返回到哪(na)里等等。 因此,在同一個(ge)棧(zhan)幀內(nei)數據的(de)訪問(wen)可以(yi)使隨機的(de),匯(hui)編中可以(yi)通(tong)過(guo)ebp 指針向(xiang)(xiang)上(shang)或(huo)向(xiang)(xiang)下任(ren)意偏移(yi)就可以(yi)訪問(wen)當前(qian)函數內(nei)部(bu)的(de)所有局部(bu)變量,或(huo)向(xiang)(xiang)上(shang)偏移(yi)就可以(yi)訪問(wen)調用者對當前(qian)函數的(de)傳參。(因為棧(zhan)的(de)增長空間是從高地址(zhi)到低地址(zhi)。) 下面(mian)是(shi)函數(shu)調用過(guo)程中的操作: 當(dang)發生函數調用(yong)的時候,棧空(kong)間中存放的數據是這樣的: 1、調(diao)(diao)用者(zhe)函數(shu)(shu)(shu)把被(bei)調(diao)(diao)函數(shu)(shu)(shu)所(suo)需要的(de)參數(shu)(shu)(shu)按(an)照與被(bei)調(diao)(diao)函數(shu)(shu)(shu)的(de)形參順序相反的(de)順序壓入棧中,即:從右向左依次把被(bei)調(diao)(diao)函數(shu)(shu)(shu)所(suo)需要的(de)參數(shu)(shu)(shu)壓入棧; 2、調用(yong)(yong)者函數(shu)使用(yong)(yong)call指(zhi)令(ling)調用(yong)(yong)被調函數(shu),并把call指(zhi)令(ling)的下一條指(zhi)令(ling)的地(di)址當(dang)成返回地(di)址壓(ya)入棧中(zhong)(這個壓(ya)棧操作(zuo)隱(yin)含在call指(zhi)令(ling)中(zhong)); 3、在被(bei)調(diao)函數(shu)中,被(bei)調(diao)函數(shu)會先(xian)保存調(diao)用者函數(shu)的(de)棧底(di)(di)地址(push ebp),然后再保存調(diao)用者函數(shu)的(de)棧頂地址,即(ji):當前被(bei)調(diao)函數(shu)的(de)棧底(di)(di)地址(mov ebp,esp); 4、在被(bei)調函(han)數(shu)中(zhong)(zhong),從ebp的(de)位(wei)置(zhi)處開始存(cun)放(fang)被(bei)調函(han)數(shu)中(zhong)(zhong)的(de)局部變(bian)(bian)(bian)(bian)量(liang)(liang)(liang)(liang)和臨時變(bian)(bian)(bian)(bian)量(liang)(liang)(liang)(liang),并(bing)且這(zhe)些變(bian)(bian)(bian)(bian)量(liang)(liang)(liang)(liang)的(de)地(di)址(zhi)按照(zhao)定(ding)義時的(de)順序依(yi)次減小,即:這(zhe)些變(bian)(bian)(bian)(bian)量(liang)(liang)(liang)(liang)的(de)地(di)址(zhi)是按照(zhao)棧(zhan)的(de)延(yan)伸方(fang)向排(pai)列的(de),先定(ding)義的(de)變(bian)(bian)(bian)(bian)量(liang)(liang)(liang)(liang)先入棧(zhan),后(hou)定(ding)義的(de)變(bian)(bian)(bian)(bian)量(liang)(liang)(liang)(liang)后(hou)入棧(zhan); 所以,發生函數調用時,入棧的順序為:
發表評論
|