Thumb指令集之: ARM和Thumb的混合編程
在實現(xiàn)ARM代碼和Thumb代碼轉(zhuǎn)換時,大部分的ARM指令有等價的Thumb指令,只有少數(shù)指令沒有。如加載字節(jié)指令(LDR)不支持自動變址,軟中斷指令不能條件執(zhí)行。
在編寫Thumb代碼時要注意以下幾點。
①匯編器需要知道什么時候產(chǎn)生ARM代碼、什么時候產(chǎn)生Thumb代碼,程序中使用CODE32和CODE16偽操作提供給編譯器這些信息。
②由于處理器上電執(zhí)行是在ARM狀態(tài)下完成的,所以要使用Thumb指令必須由ARM指令調(diào)用Thumb指令,這一過程是通過“BXLR”指令來實現(xiàn)的。需要注意的是,在使用“BXLR”指令前,要對寄存器LR做正確的初始化。
③在ARM和Thumb混合編程時,常使用ALIGN偽操作保證內(nèi)存地址對齊。
11.10.2互交子程序
編寫ARM/Thumb互交代碼時,下面兩點需要注意。
①對于C/C++子程序而言,只要在編譯時指定--apcs/interwork選項,匯編器會生成合適的返回代碼,使得程序返回到和調(diào)用程序相同的狀態(tài)。
②在匯編語言子程序中,用戶必須自己編寫相應的返回代碼,使得程序返回到和調(diào)用程序相同的狀態(tài)。
如果目標代碼包含以下內(nèi)容,應該在編譯或匯編時使用--apcs/interwork選項使處理器能夠在ARM和Thumb代碼間進行正確的切換,這種情況包含以下4種。
①需要返回到ARM狀態(tài)的Thumb子程序。
②需要返回到Thumb狀態(tài)的ARM子程序。
③間接調(diào)用ARM子程序的Thumb子程序。
④間接調(diào)用Thumb子程序的ARM子程序。
如果在程序連接階段,連接器發(fā)現(xiàn)ARM子程序和Thumb子程序間存在相互調(diào)用,而源文件在編譯時沒有使用--apcs/interwork選項,則連接器將報告以下錯誤。
Error:L6239E:CannotcallARMsymbol'arm_function'innon-interworkingobject
armsub.ofromTHUMBcodeinthumbmain.o(.text)
其中,“arm_function”為需要進行狀態(tài)切換的子程序名。
在這種情況下,用戶必須使用--apcs/interwork選項重新對源文件進行編譯。
但在下面兩種情況下,不必指定--apcs/interwork選項。
①在Thumb狀態(tài)下,發(fā)生異常中斷時,處理器自動切換到ARM狀態(tài),這時不需要添加狀態(tài)切換代碼。
②當異常發(fā)生在Thumb狀態(tài)時,從異常返回不需要添加狀態(tài)切換的Veneer代碼。
1.使用匯編語言實現(xiàn)互交
對于匯編程序來說,可以有兩種方法來實現(xiàn)程序狀態(tài)的切換。第一種方法是利用連接器提供的交互子程序Veneer來實現(xiàn)程序狀態(tài)的切換,這時用戶可以使用指令BL來調(diào)用子程序;另一種方法是用戶自己編寫狀態(tài)切換的程序。
在ARMv4版本及其以前的版本中,可以使用BX指令實現(xiàn)程序狀態(tài)的切換。
從ARMv5版本開始,下面的指令也可以用來實現(xiàn)程序的狀態(tài)切換。
·BX(BranchandeXchange)
·BLX、LDR、LDM和POP
下面的兩個偽操作用來區(qū)分源程序中的ARM代碼和Thumb代碼。
·CODE16
·CODE32
下面簡單介紹用于狀態(tài)切換的指令和偽操作,更詳細的信息請分別參見相關章節(jié)。
(1)BX指令
ARM狀態(tài)下的BX指令,使程序跳轉(zhuǎn)到指令中指定的參數(shù)Rm指定的地址執(zhí)行程序,Rm的第0位拷貝到CPSR中T位,位[31∶1]移入PC。若Rm的bit[0]為1,則跳轉(zhuǎn)時自動將CPSR中的標志位T置位,即把目標地址的代碼解釋為Thumb代碼;若Rm的位bit[0]為0,則跳轉(zhuǎn)時自動將CPSR中的標志位T復位,即把目標地址代碼解釋為ARM代碼。指令的語法格式如下。
BX{cond>}Rm>
①cond>
為指令編碼中的條件域。它指示指令在什么條件下執(zhí)行。當cond>忽略時,指令為無條件執(zhí)行(cond=AL(Alway))。
②Rm>
包含跳轉(zhuǎn)指令的目標地址。如果Rm的bit[0]=0,目標地址處指令為ARM指令;如果Rm的bit[0]=1,目標地址處指令為Thumb指令。
指令操作的偽代碼。
指令操作的偽代碼如下面程序段所示。
IfconditionPassed{cond}then
TFlag=Rm[0]
PC=RmAND0xfffffffe
Thumb狀態(tài)下的BX指令,用于ARM和Thumb代碼間的相互調(diào)用。
指令的語法格式。
BXRm>
其中Rm>為目標地址寄存器,包含程序的跳轉(zhuǎn)地址。BX指令的目標地址寄存器可以是r0~r15中的任意寄存器。
注意 | 如果Rm[1:0]=0b10,不滿足ARM指令的內(nèi)存對齊方式。指令的執(zhí)行結果不可預知。如果該指令使用r15作為目標寄存器,其操作方式和使用其他寄存器相同。 |
c++相關文章:c++教程
評論