常用ARM及匯編指令_第1頁(yè)
常用ARM及匯編指令_第2頁(yè)
常用ARM及匯編指令_第3頁(yè)
常用ARM及匯編指令_第4頁(yè)
常用ARM及匯編指令_第5頁(yè)
免費(fèi)預(yù)覽已結(jié)束,剩余22頁(yè)可下載查看

下載本文檔

版權(quán)說(shuō)明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

1、常用AR幄匯編指令用ARM指令及匯編包括3指令集介紹5ARM數(shù)據(jù)處理指令包括8ARM為指令介紹11ARM匯編程序設(shè)計(jì)及一叱格式要求說(shuō)明 .14用ARM指令及匯編包括1、ARMt理器尋址方式2、指令集介紹3、偽指令4、ARM匚編程序設(shè)計(jì)5、C與匯編混合編程ARM處理器尋址方式1、寄存器尋址:操作數(shù)的值在寄存器中,指令中的地址碼字段指出的是寄存器 編號(hào),指令執(zhí)行時(shí)直接取出寄存器值操作MOV R1, R2;R2-R1SUB R0, R1,R2;R1-R2 - R02、立即尋址:立即尋址指令中的操作碼字段后面的地址碼部分就是操作數(shù)本身, 也就是說(shuō),數(shù)據(jù)就包含在指令當(dāng)中,取出指令就取出了可以立即使用的操

2、作數(shù) SUBS R0,R0,#1;R0-1 - R0MOV R0,#0xff00;0xff00 - R0注:立即數(shù)要以#為前綴,表示16進(jìn)制數(shù)值時(shí)以0x表示3、寄存器偏移尋址:是ARM旨令集特有的尋址方式,當(dāng)?shù)?2操作數(shù)是寄存器偏 移方式時(shí),第2個(gè)寄存器操作數(shù)在與第1個(gè)操作數(shù)結(jié)合之前選擇進(jìn)行移位操作 MOV R0,R2,LSL #3;R2的值左移3位,結(jié)果存入 R0,即R0= R2* 8ANDS R1,R1,R2,LSL R3 ;R2的值左移R3位,然后和R1相與操作,結(jié)果放 入R1寄存器偏移尋址可采用的移位操作如下、LSL(Logical Shift Left)邏輯左移,寄存器中字的低端空出

3、補(bǔ) 0、LSR(Logical Shift Right)邏輯右移,寄存器中字的高端空出補(bǔ)0(3)、ASR(Arthmetic Shift Right) 算術(shù)右移,移位中保持符號(hào)位不變,即如果源操作數(shù)為正數(shù),字高端空出補(bǔ) 0,否則補(bǔ)1(4)、ROR(Rotate Right)循環(huán)右移,由字的低端移出的位填入高端空出的位(5)、RRX(Rotate Right eXtended by 1 place) ,操作數(shù)右移一位,左側(cè)空位由CPSR勺C填充4、寄存器間接尋址:寄存器間接尋址指令中的地址碼給出的是一個(gè)通用寄存器 的編號(hào),所需要的操作數(shù)保存在寄存器指定地址的存儲(chǔ)單元中,即寄存器為操 作數(shù)的地址指

4、針LDR R1,R2;將R2中的數(shù)值作為地址,取出此地址中的數(shù)據(jù)保存在R1中SWP R1,R1,R2;將R2中的數(shù)值作為地址,取出此地址中的數(shù)值與R1中的值交換5、基址尋址:將基址寄存器的內(nèi)容與指令中給出的偏移量相加,形成操作數(shù)的 有效地址,基址尋址用于訪問基址附近的存儲(chǔ)單元,常用于查表,數(shù)組操作, 功能部件寄存器訪問等。LDR R2,R3,#0x0FR3的數(shù)值加0x0F作為地址,取出此地址的數(shù)值保存在R2中STR R1,R0,#-2;將R0中的數(shù)值減2作為地址,把 R1中的內(nèi)容保存到此地址位置6、多寄存器尋址:一次可以傳送幾個(gè)寄存器值,允許一條指令傳送16個(gè)寄存器的任何子集或所有寄存器LDM

5、IA R1!,R2-R7,R12;將R1所指向的地址白數(shù)據(jù)讀出到 R2-R7, R12, R1自動(dòng)更新STMIA R0!,R3-R6,R10;將R3-R6,R10中的數(shù)值保存到 R0指向的地址,R0自動(dòng)更新7、堆棧尋址:堆棧是特定順序進(jìn)行存取的存儲(chǔ)區(qū),堆棧尋址時(shí)隱含的使用一個(gè) 專門的寄存器(堆棧指針),指向一塊存儲(chǔ)區(qū)域(堆棧),存儲(chǔ)器堆??煞譃?兩種:向上生長(zhǎng):向高地址方向生長(zhǎng),稱為遞增堆棧向下生長(zhǎng):向低地址方向生長(zhǎng),稱為遞減堆棧如此可結(jié)合出四中情況:1、滿遞增:堆棧通過增大存儲(chǔ)器的地址向上增長(zhǎng),堆棧指針指向內(nèi)含有效數(shù)據(jù)項(xiàng)的最高地址,指令如 LDMFA STMFA2、空遞增:堆棧通過增大存儲(chǔ)器

6、的地址向上增長(zhǎng),堆棧指針指向堆棧上的第一個(gè)空位置,指令如 LDMEA STMEA3、滿遞減:堆棧通過減小存儲(chǔ)器的地址向下增長(zhǎng),堆棧指針指向內(nèi)含有效數(shù)據(jù)項(xiàng)的最低地址,指令如 LDMFD STMFD4、空遞減:堆棧通過減小存儲(chǔ)器的地址向下增長(zhǎng),堆棧指針指向堆棧下的第一個(gè)空位置,指令如 LDMED STMEDSTMFD SP!,R1-R7,LR;將 R1-R7, LR入棧,滿遞減堆棧LDMFD SP!,R1-R7,LR;數(shù)據(jù)出棧,放入 R1-R7,LR寄存器,滿遞減堆棧8、塊拷貝尋址:多寄存器傳送指令用于一塊數(shù)據(jù)從存儲(chǔ)器的某一位置拷貝到另 一位置STMIA R0!,R1-R7;將R1-R7的數(shù)據(jù)保存

7、到存儲(chǔ)器中,存儲(chǔ)器指針在保存第一個(gè)值之后增加,方向?yàn)橄蛏显鲩L(zhǎng)STMIB R0!,R1-R7;將R1-R7的數(shù)據(jù)保存到存儲(chǔ)器中,存儲(chǔ)器指針在保存第一個(gè)值之前增加,方向?yàn)橄蛏显鲩L(zhǎng)SIMDA R0!,R1-R7;將R1-R7的數(shù)據(jù)保存到存儲(chǔ)器中,存儲(chǔ)器指針在保存第一個(gè)值之后增加,方向?yàn)橄蛳略鲩L(zhǎng)STMDB R0!,R1-R7;將R1-R7的數(shù)據(jù)保存到存儲(chǔ)器中,存儲(chǔ)器指針在保存第一個(gè)值之前增加,方向?yàn)橄蛳略鲩L(zhǎng)不論是向上還是向下遞增,存儲(chǔ)時(shí)高編號(hào)的寄存器放在高地址的內(nèi)存,出來(lái)時(shí), 高地址的內(nèi)容給編號(hào)高的寄存器9、相對(duì)尋址:是基址尋址的一種變通,由程序計(jì)數(shù)器PC提供基準(zhǔn)地址,指令中的地址碼字段作為偏移量,兩

8、者相加后得到的地址即為操作數(shù)的有效地址BL ROUTE1 ;調(diào)用至ij ROUTE1子程序BEQ LOOP ;條件跳轉(zhuǎn)至I LOOP標(biāo)號(hào)處指令集介紹指令格式: S,其中 內(nèi)的項(xiàng)是必須的,內(nèi)的項(xiàng)是可選的opcode指令助記符,如LDR, STR等cond執(zhí)行條件,如EQ, NE等S是否影響CPSFW存器的值,書寫時(shí)影響CPSR否則不影響Rd目標(biāo)寄存器Rn第一個(gè)操作數(shù)的寄存器指令格式舉例如下:LDRR0,R1 條件執(zhí)行)BEQ DATAEVENADDS R1,R1,#1operand2第二個(gè)操作數(shù);讀取R1地址上的存儲(chǔ)器單元內(nèi)容,執(zhí)行條件 AL(無(wú);跳轉(zhuǎn)指令,執(zhí)行條件EQ即相等跳轉(zhuǎn)到DATAEVE

9、N;加法指令,R1+1 = R1影響CPSFW存器,帶有SSUBNES R1,R1,#0xD ;條件執(zhí)行減法運(yùn)算(NE3 , R1-0xD = R1 ,影響 CPSRif存器,帶有S條件碼表?xiàng)l件碼助記符標(biāo)志含義相等EQZ=1NEZ=0不相等CS/HSC=1無(wú)符號(hào)數(shù)大于或等于CC/LOC=0無(wú)符號(hào)數(shù)小于MIN=1負(fù)數(shù)PLN=0正數(shù)VSV=1溢出VCV=0沒有溢出HIC=1,Z=0無(wú)符號(hào)數(shù)大于LSC=0,Z=1無(wú)符號(hào)數(shù)小于或等于GEN=V帶符號(hào)數(shù)大于或等于LTN!=V帶符號(hào)數(shù)小于GTZ=0,N=V帶符號(hào)數(shù)大于LEZ=1,N!=V帶符號(hào)數(shù)小于或等于AL任何無(wú)條件執(zhí)行(指令默認(rèn)條件)條件碼應(yīng)用舉例:1

10、、比較兩個(gè)值大小,C代碼如下:if(ab) a+;else b+;寫出相應(yīng)的ARM旨令代碼如下:設(shè)R0為a, R1為bCMP R0, R1; R0 與 R1 比較ADDHI R0,R0,#1;若 R0R WJ R0=R0+1ADDLS R1,R1,#1;若 R0 R0 ,影響 CPSFfr的值A(chǔ)DC R1,R1,R3;(R1、R0) = (R1、R0)+(R3、R2)SBC旨令:帶借位減法指令,用寄存器 Rn減去操作數(shù)2,再減去CPSFfr的C條件標(biāo)志位的非(即若C標(biāo)志清零,則結(jié)果減去1),結(jié)果保存在Rd中使用SBC實(shí)現(xiàn)64位減法SUBS R0,R0,R2SBC R1,R1,R3;使用 SBC

11、現(xiàn) 64 位減法,(R1,R0) - (R3,R2)AND旨令:按位與操作ANDS R0,R0,#0x01 ;取出最低位數(shù)據(jù)ORR旨令:按位或操作ORR R0,R0,#0x0F;將 R0的低 4 位置 1EOR旨令是進(jìn)行異或操作,BIC指令是位清除指令(遇1清0)TST:位測(cè)試指令TST R0,#0x01;判斷R0的最低位是否是為0TEQ相等測(cè)試指令TEQR0,R1;比較R0與R1是否相等,也可看作相減,相等則為0,Z=1MUL旨令:乘法指令MUL R1,R2,R3;R1=R2*R3MULS R0,R3,R7 ; R0=R3*R7,同時(shí)設(shè)置 CPSRfr的 N位和 Z位MLA乘加指令,將操作數(shù)

12、1和操作數(shù)2相乘再加上第3個(gè)操作數(shù),結(jié)果的低32位存入到Rd中UMUL是64位無(wú)符號(hào)乘法指令UMULL R0,R1,R5,R8; (R1、R0) = R5 * R8BL指令:帶鏈接的跳轉(zhuǎn)指令,指令將下一條指令拷貝到R14 (即LR)鏈接寄存器中,然后跳轉(zhuǎn)到指定地址運(yùn)行BL指令用于子程序調(diào)用,例如:BL DELAYBX指令:帶狀態(tài)切換的跳轉(zhuǎn)指令,例如 BX R0 ;跳轉(zhuǎn)到R0指定的地址,并根據(jù)R0的最低位來(lái)切換處理器的狀態(tài)MCR ARMS存器到協(xié)處理器寄存器的數(shù)據(jù)傳送指令MRC協(xié)處理器寄存器到ARMS存器的數(shù)據(jù)傳送指令MRC/MCR令格式如下:MRC/MCR cond coproc,opcode

13、1,Rd,CRn,CRm,opcode2coproc是指令操作的協(xié)處理器名,標(biāo)準(zhǔn)名為 pn, n為0-15opcode1協(xié)處理器的特定操作碼Rd MRCM乍時(shí),作為目標(biāo)寄存器的協(xié)處理器寄存器,MCRS作時(shí),作為ARM處理器的寄存器CRn存放第1個(gè)操作數(shù)的協(xié)處理器寄存器CRm存放第2個(gè)操作數(shù)的協(xié)處理器寄存器opcode2可選的協(xié)處理器特定操作碼MRC/MCR令舉例如下:mcr/mrc p15,0,r0,c1,c0,0SWI指令:SWI指令用于產(chǎn)生中斷,從而實(shí)現(xiàn)用戶模式變換到管理模式,CPSRS存到管理模式的SPSRfr,執(zhí)行轉(zhuǎn)移到SWI向量SWI 0x123456 ;軟中斷,中斷立即數(shù) 0x12

14、3456在SWI異常中斷處理程序中,取出 SWI立即數(shù)的步驟為:首先確定引起軟中斷的SWI指令是ARM旨令還是THUM指令,這可通過對(duì)SPS時(shí)問得到,然后要取 得該SWI指令的地址,這可通過訪問LR寄存器得到,接著讀出指令,分解出立 即數(shù)程序代碼如下:T_bit EQU 0x20SWI_HanderSTMFD SP!,R0-R3,R12,LRMRS R0,SPSRSTMFD SP!,R0TST R0, #T_bit為 THUMBLDRNEH R0,LR,#-2斷的指令碼(16位)BICNE R0,R0,#0xFF00LDREQ R0,LR,#-4的指令碼(32位)BICEQ R0,R0,#0x

15、FF000000BL C_SWI_HandlerLDMFD SP!,R0-R3,R12,PCA;0010 0000;現(xiàn)場(chǎng)保護(hù);讀取SPSR;保存SPSR;測(cè)試T標(biāo)志位,0為ARM 1;若是THUM指令,讀出產(chǎn)生中;取得THUM指令的8位立即數(shù);若是ARM旨令,讀取產(chǎn)生中斷;取得ARMt令的24位立即數(shù);SWI異常中斷返回MRS旨令:讀狀態(tài)寄存器指令,在 ARMfe理器中,只有MRS旨令可以從狀態(tài)寄存 器CPSRE SPSR賣出到通用寄存器MRS R1,CPSRMRS R2,SPSR;將CPSR犬態(tài)寄存器讀取,;將SPSR犬態(tài)寄存器讀取,保存到 R1保存到 R2MRSE用:1、使能IRQ中斷 E

16、NABLE_IRQMRS R0,CPSR BIC R0,R0,#0x80 MSR CPSR,R0 MOV PC,LR;1000 00002、禁止IRQ中斷 DISABLE_IRQ MRS R0,CPSR ORR R0,R0,#0x80MSR CPSR,R0 MOV PC,LRMSR寫狀態(tài)寄存器指令,在 ARMt理器中,只有MSR旨令可以直接設(shè)置狀態(tài)寄 存器 CPSRE SPSRARMfe指令介紹ARMW旨令不是ARM旨令集中的指令,只是為了編程方便編譯器定義了偽指令A(yù)RM*址讀取偽指令有四條,分別是ADR偽指令A(yù)DRL 偽指令LDR偽指令NOP 偽指令作用的范圍不一樣,由小到大:ADR ADR

17、L LDRADR ADRL旨令將基于PC相對(duì)偏移的地址讀取到存儲(chǔ)器中,例如ADR R0 , DISP_TAB ;加載轉(zhuǎn)換表地址LDR R1, R0,R2;使用R2作為參數(shù),進(jìn)行查表DISP_TABDCB0xc0,0xf9,0xa4,0x99,0x92,0x82,0xf8,0x80LDR偽指令用于加載32位的立即數(shù)或一個(gè)地址值到指定寄存器,前加 =LDR R0,=0x123456;力口載 32 位立即數(shù) 0x123456LDR R0,=DATA_BUF+60 ;力口載 DATA_BU地址+60NO選空操作偽指令宏是一段獨(dú)立的程序代碼,它是通過偽指令定義的,在程序中使用宏指令即可 調(diào)用宏,當(dāng)程序被

18、匯編時(shí),匯編程序?qū)?duì)每個(gè)調(diào)用進(jìn)行展開,用宏定義取代源 程序中的宏指令符號(hào)定義偽指令1、全局變量聲明:GBLA GBLL和GBLS2、局部變量聲明:LCLA LCLL和LCLS3、變量賦值:SETA SETL和SETS4、為一個(gè)通用寄存器列表定義名稱:RLIST5、為一個(gè)協(xié)處理器的寄存器定義名稱:CN6、為一個(gè)協(xié)處理器定義名稱:CP最后一個(gè)字符A代表算術(shù)變量,初始值為0, L代表邏輯變量,初值為FALSES代表字符串,初值為空偽指令應(yīng)用舉例如下:MACRO;聲明一個(gè)宏SENDDAT $dat LCLA bitno .bitno SETA 8.MENDRLIST指令格式: name RLIST r

19、eglistLoReg;宏的原型$表示后面是變量;聲明一個(gè)局部算術(shù)變量;設(shè)置變量值為8;結(jié)束,例如:LoReg RLIST R0-R7;定義寄存器列表CN指令的用法:nameCNexpr ,其中name!1要定義的協(xié)處理器的寄存器名稱,expr對(duì)應(yīng)的協(xié)處理器的寄存器編號(hào),數(shù)值范圍0 15MemSet CN 1;將協(xié)處理器的寄存器1名稱定義為 MemSetCP指令的用法,舉例如下:DivRun CP 5;將協(xié)處理器5名稱定義為DivRun數(shù)據(jù)定義偽指令:1、聲明一個(gè)文字池:LTORG2、定義一個(gè)結(jié)構(gòu)化的內(nèi)存表的首地址:MAP或A3、定義結(jié)構(gòu)化內(nèi)存表中的一個(gè)數(shù)據(jù)域:FIELD或#4、分配一塊內(nèi)存空

20、間,并用0初始化:SPACE或5、分配一段字節(jié)內(nèi)存單元,并用指定的數(shù)據(jù)初始化:DCB6、分配一段字的內(nèi)存單元,并用指令的數(shù)據(jù)初始化:DCD和DCDU7、分配一段雙字的內(nèi)存單元,并用 64位整數(shù)數(shù)據(jù)初始化:DCQ和DCQU8、分配一段半字的內(nèi)存單元,并用指定的數(shù)據(jù)初始化:DCW和DCWULTORGffl于聲明一個(gè)文子池,在使用LDR偽指令時(shí),要在適當(dāng)?shù)牡刂芳尤隠TORG 聲明文子池,這樣就會(huì)把要加載的數(shù)據(jù)保存在文子池內(nèi),再用ARM勺加載指令讀出數(shù)據(jù)(若沒有使用LTORG?明文子池,則匯編器會(huì)在程序末尾自動(dòng)聲明) LTORGS指令應(yīng)用舉例如下: .LDR R0,=0x12345678ADD R1,

21、R1,R0MOV PC,LRLTORG;聲明文子池DCD 0x333 DCD 0x555MAP用于定義一個(gè)結(jié)構(gòu)化的內(nèi)存表的首地址,a與MAPI義MAP 0x00, R9;定義內(nèi)存表的首地址為 R9FIELD用于定義一個(gè)結(jié)構(gòu)化內(nèi)存表的數(shù)據(jù)域,#與FIELD同義人 _ISR_STARTADDRESS ;人 is synonym for MAPHandleReset #4;定義數(shù)據(jù)域 HandleReset ,長(zhǎng)度為4字節(jié)SPACES于分配一塊內(nèi)存單元,并用 0初始化,f SPAC的義 偽指令應(yīng)用舉例如下:AREA DataRAM,DATA,READWROTE;聲明一數(shù)據(jù)段,名為 DataRAMDa

22、taBuf SPACE 1000;分配 1000 字節(jié)空間DCBft指令格式:label DCB expr,expr .加的代表可有可無(wú),DCD DCWf令格式與DCBS本相同ASSER必?cái)嘌藻e(cuò)誤偽指令,在匯編編譯器對(duì)匯編程序的第二遍掃描中,若其中ASSER除件不成立,ASSERT;指令將報(bào)告該錯(cuò)誤信息ASSERT TopTemp ;斷言 Top 不等于 TempASSERT :DEF:ENDIAN_CHANGE匯編控制偽指令1、條件匯編控制:IF、ELSE和ENDIFIF、ELSE和ENDIF偽指令能夠根據(jù)條件把一段代碼包括在匯編程序內(nèi)或?qū)⑵?排除在程序之外與IF同義,|與ELSE同義,與E

23、NDIF同義偽指令應(yīng)用舉例如下:CONFIG = 16;代表 IFBL _rt_udiv_1|代表ELSEBL _rt_div0;代表 ENDIF2、MACRO: MENDMACROS MEND偽指令用于宏定義,MACR淺示宏定義的開始,MENDS示宏定 義的結(jié)束,用MACRO: MEND!義的一段代碼,稱為宏定義體,偽指令應(yīng)用如下: MACROCSI_SETB;宏名為CSI_SETB無(wú)參數(shù)LDR R0,=rPDATG ;讀取 GPG0 口的值LDR R1,R0ORR R1,R1,#0x01 ;CSI 置位操作STR R1,R0;輸出控制MEND3、WHILE 和 WENDWHILE和WEND

24、S指令用于根據(jù)條件重復(fù) 編相同的或幾乎相同的一段源程序 偽指令應(yīng)用舉例WHILE no 5no SETA no+1.WEND雜項(xiàng)偽指令:在匯編程序設(shè)計(jì)較為常用,如段定義偽指令,入口點(diǎn)設(shè)置偽指令, 包含文件偽指令,標(biāo)號(hào)導(dǎo)出或引入聲明1、邊界對(duì)齊:ALIGN2、段定義:AREA3、指令集定義:CODE1褥口 CODE324、匯編結(jié)束:END5、程序入口: ENTRY6、常量定義:EQU7、聲明一個(gè)符號(hào)可以被其它文件引用:EXPORTS GLOBAL8、聲明一個(gè)外部符號(hào):IMPORT和EXTERN9、包含文件:GET和INCLUDE10、給特定的寄存器命名:RNARM匯編程序設(shè)計(jì)及一些格式要求說(shuō)明一

25、般地,ARM程序文件名的后綴名如下:匯編文件:*S引入文件:*INCC程序:*c頭文件: *h匯編語(yǔ)句格式:標(biāo)號(hào) ;注釋1、所有標(biāo)號(hào)必須在一行的頂格書寫,其后面不要加:2、所有指令均不能頂格書寫3、ARM匚編器對(duì)標(biāo)識(shí)符大小寫敏感,書寫標(biāo)號(hào)及指令時(shí)字母大小要一致, 在ARM 匯編程序中,一個(gè)ARM旨令,偽指令,寄存器名可以全部為大寫字母,也可以全部為小寫字母,但不要大小寫混合使用4、注釋使用;或者,能示開始到此行結(jié)束,注釋可以在一行頂格書寫(對(duì)ADSE編格式,只支持;)5、源程序中允許空行6、如果單行太長(zhǎng),可以使用字符/將其分行,/后不能有任何字符,包括空 格7、對(duì)于變量的設(shè)置,常量的定義,其標(biāo)

26、識(shí)符必須在一行的頂格書寫標(biāo)號(hào):在ARM匚編中,標(biāo)號(hào)代表一個(gè)地址,根據(jù)標(biāo)號(hào)生成方式,可以分為以下3種1、基于PC的標(biāo)號(hào),例如:BL LEDTEST2、基于寄存器的標(biāo)號(hào),例如: MAP 0x00,R93、絕對(duì)地址,例如: LDR R0,=WTCON局部標(biāo)號(hào):主要用于局部范圍代碼中,對(duì)宏定義也非常有用,格式如下:N routname N是局部標(biāo)號(hào),為0 99routname是局部標(biāo)號(hào)作用范圍的名稱局部標(biāo)號(hào)引用格式: F | B A | T N routname 其中:%表示局部標(biāo)號(hào)引用操作F指示編譯器只向前搜索B指示編譯器只向后搜索A指示編譯器搜索宏的所有嵌套層次T指示編譯器搜索宏的當(dāng)前層應(yīng)用舉例如

27、下:mov r1, #160subs r1,r1, #1bne %B0宏定義及其作用:使用宏定義可以提高程序的可讀性,簡(jiǎn)化程序代碼和同步修改,宏首先要 定義,然后再使用,當(dāng)源程序被匯編時(shí),匯編器將展開每一個(gè)宏調(diào)用,用宏定 義體代表程序中的宏調(diào)用,并使用實(shí)際的參數(shù)值代替宏定義時(shí)的形式參數(shù) 宏定義應(yīng)用舉例如下:MACRO;宏定義CALL $FUNCTION , $DAT1 , $DAT2 ;宏名稱為 CALL 帶有 3 個(gè)參數(shù)IMPORT $FUNCTION;聲明外部子程序MOV R0, $DAT1 ;設(shè)置子程序參數(shù),R0 = $DAT1MOV R1, $DAT2 ;BLFUNCTION ; 調(diào)用

28、子程序MEND;宏定義結(jié)束匯編預(yù)處理后,宏調(diào)用將被展開,程序清單如下:IMPORT FADD1MOVR0, #3MOVR1, #3BLFADD1子程序的調(diào)用:使用BL指令進(jìn)行調(diào)用,該指令會(huì)把返回的 PC值保存在LR示例如下:BL DELAYDELAY .MOV PC,LR當(dāng)子程序指令完畢后,使用MOV,B/BX , STMF/指令返回,STMFD5與LDMFD 配套使用STMFD SP! , R0-R7, LRLDMFD SP! , R0-R7,PC ARM7TDMI (-S)是沒有BLX指令的,但可以通過以下幾條程序?qū)崿F(xiàn)其功能ADR R1 , DELAY+1MOV LR , PC ;保存返回

29、地址到LRBXR1;跳轉(zhuǎn)并切換指令集 該程序要注意的是3級(jí)流水線,PC執(zhí)行到哪里是關(guān)鍵特殊寄存器定義及應(yīng)用:基于 ARMS的芯片一般有片內(nèi)外設(shè),它們通過其特殊寄存器訪問示例如下:WDTC EQU 0XE000000;寄存器定義.LDR R0, =WDTC ;加載立即數(shù)要加= MOV R1,#0x12STR R1,R0WDTC = 0x12散轉(zhuǎn)功能是匯編程序常用的一種算法,其示例如下:CMP R0, #MAXINDEX;判斷索引號(hào)是否超過最大索引值A(chǔ)DDLO PC , PC , R0 , LSL #2;若沒有超出,則跳轉(zhuǎn)到相應(yīng)位置BERROR;若已經(jīng)超出,則進(jìn)行出錯(cuò)處理;散轉(zhuǎn)表,對(duì)應(yīng)索引號(hào)為0

30、NBFUN1BFUN2BFUN3查表操作是匯編程序常用的一種操作,其示例如下:LDR R3, =DISP_TAB;取得表頭LDR R2 , R3, R5, LSL #2;根據(jù) R5的值查表,取出相應(yīng)的值;下表為0-F 的自模 DISR_TABDCD 0xC0, 0xF9,0xA4,0x99,0x92,0xA1,0xC6,0x83DCD 0x82. 0xF80x80,0x90,0x88,0x86, 0x8E , 0xFF長(zhǎng)跳轉(zhuǎn)功能的實(shí)現(xiàn):ARM勺B和BL指令不能全空間跳轉(zhuǎn),但通過對(duì) PC進(jìn)行復(fù)制,實(shí)現(xiàn)32位地址的跳轉(zhuǎn)ADD LR , PC , #4;保存返回地址,即 RET_FUNLDR PC

31、, PC , # -4; 跳轉(zhuǎn)到 LADR_FUNDCD LADR_FUNRET_FUN .也可以使用偽指令LDR PC, =LADR_FUN實(shí)現(xiàn)長(zhǎng)跳轉(zhuǎn)匯編程序一個(gè)完整的例子:ABC EQU 0x12AREA Example , CODE , READONLY ;聲明一個(gè)代碼段Example;入口處;裝載地址,并切換到THUM獻(xiàn)態(tài)ENTRYCODE32ADR R0, THUMB_START + 1設(shè)置第0位為1BX R0;CODE16;聲明16位代碼THUMB_STARTMOV R1, #ABCADD R1, R1 , #0x10BTHUMB_STARTEND外圍部件控制:在AR段芯片中,其外

32、圍部件的控制寄存器,一般會(huì)設(shè)置“置 位/復(fù)位”寄存器,這樣可以方便的實(shí)現(xiàn)位操作,而不影響到其它位,操作示例 如下:LDR R0 , =GPIO_BASEMOV R1 , #0x00STR R1 ,R0 , #0x04 MOV R1 ,#0x10STR R1 ,R0 , #0x0CC與匯編混合編程在需要C與匯編混合編程時(shí),可使用直接內(nèi)存匯編的方法混合編程,或者將匯 編文件以文件的形式加入項(xiàng)目中內(nèi)嵌匯編的語(yǔ)法:_asm指令;指令/*注釋*/ 指令應(yīng)用舉例:_inlinevoid enable_IRQ(void)1 一int temp_asm/嵌入?yún)R編代碼(MRS tmp , CPSR/ 讀取CPS

33、R 勺值BIC tmp , tmp, #0x80/IRQ 中斷禁止位I清零,即允許中斷MSR CPSR , tmp/ 設(shè)置CPSR 勺值 ARM編譯器特定的關(guān)鍵詞asm告訴編譯器下面的代碼是用匯編寫的_inline :聲明該函數(shù)在其被調(diào)用的地方展開_irq :聲明該函數(shù)可以被用做irq或者fiq異常的中斷處理程序pure:聲明一個(gè)函數(shù),其結(jié)果僅僅依賴于其輸入?yún)?shù),而且它沒有負(fù)效應(yīng)_int64 :是 long long 的同義詞二volatile :告訴編譯器該對(duì)象可能在程序之外被修改_weak用于限定一個(gè)對(duì)象,該對(duì)象如果連接時(shí)不存在,不會(huì)報(bào)錯(cuò)內(nèi)嵌匯編的指令用法:1、不能直接向PC寄存器賦值,程

34、序跳轉(zhuǎn)只能使用 B或BL指令實(shí)現(xiàn),但是只 有B可以使用C程序中的標(biāo)號(hào),BL不能2、在內(nèi)嵌匯編指令中,常量前面的 #可以省略3、所有的內(nèi)存分配均由C編譯器完成,內(nèi)嵌匯編器不支持內(nèi)嵌匯編程序用于內(nèi) 存分配的偽指令以上的常見的注意事項(xiàng)內(nèi)嵌匯編器與 armasm 匯編器的差異1、內(nèi)嵌匯編器不支持通過. 指示符 或pc獲取 當(dāng)前指令地址, 不支持LDR Rn , =expr 偽指令2、使用Mov Rn , expr指令向寄存器賦值,不支持標(biāo)號(hào)表達(dá)式,不支持 ADR 和ADRL不支持BX;不能向PC賦值3、N、Z、C和V標(biāo)志中的C不具有真實(shí)意義內(nèi)存匯編還有一些注意事項(xiàng):1、不要使用寄存器代替變量,盡管有時(shí)

35、候寄存器明顯對(duì)應(yīng)某個(gè)變量 int had_f (int x)._asm一ADD R0,R0, #1/發(fā)生寄存器沖突,實(shí)際上x的值沒有變化 return(x); 使用IMPORT偽指令來(lái)引入全局變量,并利用LDR和STR指令根據(jù)全局變量的 地址訪問它們下面例子是一個(gè)匯編代碼的函數(shù),它讀取全局變量glovbvar ,將其加1后返回AREA globats , CODE , READONLYEXPORT asmsubroutimeIMPORT glovbvarasmsubroutimeLDR R1, =glovbvarLDR R0, R1ADD R0 , R0 , #1STR R0 , R1MOV PC,LRENDC與匯編相互調(diào)用寄存器的使用規(guī)則為:子程序間通過寄存器 R0 - R3來(lái)傳遞參數(shù),使用R4 - R11 來(lái)保存局部變量,R12用作過程調(diào)用中間臨時(shí)寄存器,記作IP, R13用作堆 棧指針,R14作為鏈接寄存器,記作LR, R15是程序計(jì)數(shù)器子程序參數(shù)傳遞規(guī)則:當(dāng)寄存器不超過 4個(gè)時(shí),使用R0 - R3來(lái)傳遞參數(shù),當(dāng) 超過4個(gè)時(shí),可以使用堆棧來(lái)傳遞參數(shù),入棧的順序與參數(shù)順序相反,即最后 一個(gè)字?jǐn)?shù)據(jù)先入棧子程序結(jié)果返回規(guī)則:結(jié)果為一個(gè) 32位的整數(shù)時(shí),可以通過寄存器 R0返回,如果是64位,通過R0和R1返回,對(duì)于位數(shù)更多

溫馨提示

  • 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

評(píng)論

0/150

提交評(píng)論