齊晶薇
(哈爾濱遠東理工學院,黑龍江 哈爾濱 150025)
現階段廣泛采用的計算機軟件開發語言,如C語言,由于其具備較高的編程效率,在各個行業軟件研究開發中得到了廣泛應用.作為一種低級語言,匯編語言與高級語言相比,又具有無可比擬的運行速度優勢.在這兩種計算機語言進行混編時,如何使兩者實現有效連接,就成為計算機編程人員需要著力探究的問題.
在現階段計算機軟件研究開發中,在同一個應用系統中采取兩種或多種不同類型的計算機編碼語言,已經成為可能,并獲得了實踐的認可.作為計算機語言而言,即便一種語言具備再強的功能,但總有該項語言的弱點和不足,呈現出局限性和先進性并存的特征.
例如,數據庫語言,與C語言、Fortran等計算機高級語言形式相比,其在數據管理方面性能突出,但在計算能力及運行速度等層面又遠遠不及后兩者.計算機匯編語言,作為一種低級語言,又具備了較快的運行速度,在存儲空間占用上,小于C語言等高級語言,更為重要的一點是,匯編語言具備對計算機硬件進行訪問控制的能力[1].因此,不同的計算機語言各有其優劣,將不同計算機語言進行混合編程,則可以吸取各種語言的優勢及特長,為計算機編程用戶提供更具針對性的編程需求.例如,在計算機編程中,將大部分程序采用高級語言的形式進行編寫,在計算機程序的一些重點部分,需要多次運行的部位,其對運行速度和效率具有較高的要求時,或者需要對計算機硬件進行直接訪問時,此時就可采用匯編語言進行編程.如此一來,可以發揮出各自語言的優點,既達到了多種計算機語言綜合運用的目的,又能使計算機編程效率提升,縮短研發周期.
不同計算機語言混合編程在進行連接時,應考慮并解決的基本問題有以下幾方面:
計算機高級語言在經過編譯之后,往往會產生格式為OBJ的文件,與之相應地,計算機匯編語言在經過編譯之后,同樣會產生OBJ格式的文件,借助連接程序,通過將兩者加以連接,從而構成了具備執行條件的EXE文件,在EXE文件形成后,連接程序就已將其裝入計算機內存系統中,等待執行.從這一流程可以看到,在存儲器分配環節,主要是由連接程序加以掌控的,因此,用戶可以忽略這一環節.
但涉及到Basic語言時,因為其承擔解釋程序的任務,因此,情況就要稍顯復雜,此時應從計算機存儲器中找到匯編語言的存放位置,再將相關信息加以傳送,使Basic語言能夠有效接收.
匯編語言和計算機高級語言之間呈現出一種彼此依存的關系,一般而言,可將匯編語言視為計算機高級語言所具備的外部過程,在對匯編語言進行調用時,由計算機高級語言采取函數方式或過程方式進行[2].而匯編語言和計算機高級語言這兩種程序在進行參數傳遞時,常采用堆棧的方式進行,具體而言,就是調用程序首先將參數在堆棧中進行依次壓入,當調用程序被啟用,此時堆棧中被壓入的參數再依次彈出,轉變為操作數,以備使用.
因此,要使參數有效傳遞,需要對計算機不同語言所具有的生成方式、堆棧結構及其參數入棧方式加以明確.Pascal、Fortran、Basic等高級語言在參數入棧的順序上和參數表中參數的順序相一致,也就是采用自左至右的方式,C語言在參數入棧順序上則采取自右至左的相反順序.
Pascal語言作為一種計算機高級語言,可將匯編語言看做是其外部過程,匯編語言在寫法上與外部調用過程相同,在進行匯編語言程序編寫時,首先要有公共程序名稱,即public procedure name.在對程序段進行定義編寫時,要采用public組合型加以說明解釋,程序運行結束后,在返回上采用ret指令,又因為參數傳遞時采用的是堆棧方式,因此,在程序返回處理時,通常要使返回指令帶有常數,這樣即可越過參數區.
除了調用匯編語言過程之外,Pascal語言還要對過程的定義加以解決.在對調用過程進行定義時,可以使用語句$include:’name’,在這一語句中,文件名為 name,以 name作為Pascal語言調用函數或過程名,此時對程序進行編譯時,include語句如碰到編譯程序,編譯程序就能夠對Pascal語言文件加以編譯處理.
在對匯編語言進行調用時,Pascal程序可以根據參數順序依次將變量壓入堆棧,在堆棧中變量以字作為單位,并將段地址及偏移地址加以保存,Pascal程序中的參數獲取借助BP寄存器得以實現.
3.2.1 C語言程序中匯編碼集成方法
與Pascal語言與匯編語言間的關系相同,C語言與匯編語言連接時,匯編程序也是以外部過程的形式存在,然后借助函數及過程,C語言達到對匯編語言程序進行調用的目的.一般而言,在混合編程過程中,C語言與匯編語言的混編方法有以下兩種:
3.2.1.1 將匯編程序從C語言中直接加以調用
如混編過程中需要多次使用匯編代碼時,較常采用此方法.該方法的實現過程主要分為以下幾步:將匯編子程序進行編寫,使其具備特定功能;采用C函數的形式,將匯編子程序從C程序中加以調用.在這一過程中,尤其應注意以下幾個要點:①采用C函數形式對匯編子程序進行調用時,需要對函數加以顯式說明,主要通過將“Extern”作為C程序中的關鍵字這一方式實現;②存儲模式如不同,則匯編語言在格式上也要加以區別,例如,小模式下的C程序,需要采用近過程進行匯編,相應地,大模式下的C程序,就應采用遠過程進行匯編;③在參數獲取中,由于遠過程匯編方式下,其返回地址需要占用四個字節,而在借助BP寄存器進行參數壓入時,這一過程又需要占用二個字節,因此,遠過程匯編方式下,要從BP+6對應的單元來獲取首個參數.在近過程匯編方式下,從BP+4對應的單元獲取首個參數;④BP寄存器在匯編程序中的保護問題.在子過程變量的存放上,Turbo C對DI及SI存放方式不加阻攔,而當兩個或兩個以上的變量存入BP寄存器中時,BP寄存器會將多出的變量部分轉移到堆棧中加以存儲.這一匯編過程可以用以下程序加以說明:


⑤返回值問題.C數據在返回位置上,每個數據類型都占有一個標準,通常具有極小模式、小模式、中模式(AX)及緊湊模式、大模式、巨模式(DX:AX),以AX為返回值位置的數據類型有char;enum;unsigned char;short int,這些數據類型的返回數據要在RET指令前加以放置.采用遠過程定義匯編子程序,在過程名上要借助PUBLIC偽指令,將其作公共類型定義.下面用實例加以說明:

為更為全面地對此連接方法加以說明,可再列舉一個實例.例如,在計算機中將兩個整型數據鍵入,并將整型數據之間的差加以顯示.數據的鍵入及顯示部分采用C語言編寫,而數據之差采用匯編語言編寫.此實例的程序編寫如下所示:

3.2.1.2 內聯匯編
內聯匯編的方法指的是在C語言程序中直接插入匯編語言的代碼,因此,也被稱為嵌入式匯編方法,C語言編譯器基本都支持此方法.內聯匯編的連接方式主要是借助“asm”這一C語言中的關鍵字加以實現,將匯編語言的代碼直接放置在asm之后,此時再通過C語言編譯程序實現匯編指令的傳送及匯編步驟.內聯匯編具有簡單直接等特點,無須考慮參數傳遞及外鏈命名等方面,但涉及到對不同的目標平臺加以編譯時,內聯匯編的方法就不具備可移植性.下面列舉相關實例:

結合這一實例,在內聯匯編中,要注意以下幾個要點:①匯編語言的代碼應將C語言變量進行初始化后再加以使用,在匯編類型上要用ptr加以指示;②C語言以分號結束語句,匯編語言結束語句采用換行時,此時嵌入C語言程序中的匯編指令可以不用分號(;)結束;③采用C語言中的return指令進行返回,而不是按照asm中的ret指令;④C程序中不能嵌入偽指令,如DW,DB等;⑤宏指令及宏操作符也不能嵌入C程序,如ENDM,IRP,MACRO,%,,&等.
3.2.2 C語言程序和匯編子程序間的連接
集成環境下,如對由C語言及匯編語言混編而成的程序加以編譯及連接,首先要采用MASM.EXE這一宏匯編方式對匯編語言加以編譯,得到OBJ格式文件.在生成OBJ文件后,將其嵌入C語言程序中,經連接后,即可得到EXE文件.在C語言程序中嵌入OBJ文件的步驟為:于Turbo C中編輯格式為*.Prj的工程文件,以文件名列表,作為文件內容,如mymasm.obj等;選擇project name這一位于project中的選項,然后采用(*)格式鍵入工程文件的名稱,即可實現C語言程序與匯編子程序間的連接[5].
不同計算機語言混合編程能夠實現語言間的調用,借助參數傳遞,一方面充分利用了匯編語言的優勢,另一方面又為諸如C程序等計算機高級語言性能的發揮提供了空間,在社會各行業的計算機軟件研發中,多語言混合編程已顯示出其重要價值.本文主要對Pascal語言、C語言與匯編語言的連接方法進行了闡述,希望為計算機語言接口技術的深入研究提供借鑒參考.
〔1〕周謐.C/C++與FORTRAN混合編程技術及其應用研究[J].科技創新與應用,2015(13):76.
〔2〕張喆,鄭賓.基于N I TestStand的多語言混合編程技術研究[J].電子測試,2012(11):78-83.
〔3〕孟祥娜.匯編語言與C語言混合編程方法探討[J].電腦編程技巧與維護,2014(22):26-27.
〔4〕王茹.ARM匯編語言與C/C++語言混合編程實現方法[J].電大理工,2012(2):27-29.
〔5〕金微.匯編語言與C語言混合編程的接口技術[J].無線互聯科技,2013(9):109+111.