新聞中心

EEPW首頁 > 嵌入式系統(tǒng) > 設(shè)計應(yīng)用 > ARM之---在C語言中內(nèi)嵌匯編語言

ARM之---在C語言中內(nèi)嵌匯編語言

作者: 時間:2016-11-11 來源:網(wǎng)絡(luò) 收藏
開發(fā)Arm程序的時候,大多數(shù)時候使用C/C++語言就可以了,但匯編語言在某些情況下能夠?qū)崿F(xiàn)一些C語言無法實現(xiàn)的功能,這時候就要調(diào)用一些匯編語言的程序.我們需要大概了解一下在C語言中如何嵌入?yún)R編語言.

1.內(nèi)嵌匯編語言的語法:

本文引用地址:http://m.butianyuan.cn/article/201611/316885.htm

__asm

{

指令[;指令]

......

[指令]

}

2.舉例:使能/禁止IRQ中斷

__inline void enable_IRQ(void)

{

int tmp;

__asm//嵌入?yún)R編代碼

{

MRStmp,CPSR//讀取CPSR的值

BICtmp,tmp,#0x80//將IRQ中斷禁止位I清零,即允許IRQ中斷

MSRCPSR_c,tmp//設(shè)置CPSR的值

}

}

__inline void disable_IRQ(void)

{

int tmp;

__asm

{

MRStmp,CPSR

ORRtmp,tmp,#Ox80

MSRCPSR_c,tmp

}

}

3.舉例:字符串復(fù)制

void my-strcpy(const char *src,char *dst)

{

int ch;

__asm

{

loop:

#ifndef __thumb

LDRB ch,[src],#1

STRB ch,[dst],#1

#else

LDRB ch,[src]

ADDsrc,#1

STRB ch,[dst]

ADDdst,#1

#endif

CMP ch,#0

BNE loop

}

}

int main(void)

{

const char *a="Hello world!";

char b[20];

__asm

{

MOVR0,a

MOVR1,b

BL my_strcpy,{R0,R1}

}

return(0);

}

4.內(nèi)嵌匯編的指令用法:

.操作書: 內(nèi)嵌的匯編指令中作為操作數(shù)的寄存器和常量可以是C表達(dá)式.這些表達(dá)式可以是char,short或int等類型,而且這些表達(dá)式都是作為無符號數(shù)進(jìn)行操作的.若要有符號數(shù),用戶需要自己處理與符號有關(guān)的操作.編譯器將會計算這些表達(dá)式的值,并為其分配寄存器.

.物理寄存器:內(nèi)嵌匯編中使用物理寄存器是有限制的:

_ 不能直接向PC(程序計數(shù)器)寄存器中賦值,程序跳轉(zhuǎn)只能通過B或BL指令來實現(xiàn).

_ 使用物理寄存器的指令中,不要使用過于復(fù)雜的C表達(dá)式

_ 盡可能少的使用物理寄存器

.常量: 在內(nèi)嵌匯編指令中,常量前面的"#"可以省略

.標(biāo)號: C程序中的標(biāo)號可以被內(nèi)嵌的匯編指令使用.但是只有指令B可以使用C程序中的標(biāo)號,而指令BL則不能使用.

.內(nèi)存單元的分配:所有內(nèi)存分配均由C編譯器完成,分配的內(nèi)存單元通過變量供內(nèi)嵌匯編器使用.內(nèi)嵌匯編器不支持內(nèi)嵌匯編程序中用于內(nèi)存分配的偽指令.

5.內(nèi)嵌匯編注意事項:

.必須小心使用物理寄存器,如R0~R3,IP,LR,CPSR中的標(biāo)志位,避免發(fā)生沖突.

例如:

__asm

{

MOVR0,x

ADDy,R0,x/y

}

改成下面代碼會比較妥當(dāng):

__asm

{

MOV var,x

ADD y,var,x/y

}

.不要使用寄存器代替變量.

.使用內(nèi)嵌匯編無需保存和恢復(fù)寄存器.事實上,除了CPSR,SPSR寄存器,對物理寄存器先讀后寫都會引起匯編報錯.

.匯編語言中","號作為操作數(shù)分隔符.如果有C表達(dá)式作為操作數(shù),若表達(dá)式中包含有",",則必須使用()將其規(guī)約為一個匯編操作數(shù),例如:

__asm
{

ADD x,y,(f(),z)//"f(),z"為帶有","的C表達(dá)式.

}

6.不同數(shù)據(jù)類型對應(yīng)的匯編指令:

unsigned charLDRB/STRB

unsigned shortLDRH/STRH

unsigned int LDR/STR

char LDRSB/STRSB

short LDRSH/STRSH

7.訪問C程序的變量:

AREAglobals,CODE,READONLY

EXPORTasmsubroutine

IMPORTglobalvar;聲明的外部變量

asmsubroutine

LDRR1,=blobalval

LDRR0,[R1]

ADDR0,R0,#1

STRR0,[R1]

MOVPC,LR

END



關(guān)鍵詞: ARMC語言內(nèi)嵌匯編語

評論


技術(shù)專區(qū)

關(guān)閉