ARM嵌入式系统原理与应用-第4章-ARM汇编语言及C语言程序设计基础.pptx
- 【下载声明】
1. 本站全部试题类文档,若标题没写含答案,则无答案;标题注明含答案的文档,主观题也可能无答案。请谨慎下单,一旦售出,不予退换。
2. 本站全部PPT文档均不含视频和音频,PPT中出现的音频或视频标识(或文字)仅表示流程,实际无音频或视频文件。请谨慎下单,一旦售出,不予退换。
3. 本页资料《ARM嵌入式系统原理与应用-第4章-ARM汇编语言及C语言程序设计基础.pptx》由用户(三亚风情)主动上传,其收益全归该用户。163文库仅提供信息存储空间,仅对该用户上传内容的表现方式做保护处理,对上传内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知163文库(点击联系客服),我们立即给予删除!
4. 请根据预览情况,自愿下载本文。本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
5. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007及以上版本和PDF阅读器,压缩文件请下载最新的WinRAR软件解压。
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- ARM 嵌入式 系统 原理 应用 汇编语言 语言程序设计 基础
- 资源描述:
-
1、第4章 ARM汇编语言及C语言程序设计基础本章内容简介4.1 ARM汇编的语句汇编的语句格式格式4.2 ARM汇编的程序汇编的程序结构结构4.3 ARM汇编语言程序设计汇编语言程序设计举举例例4.4 ARM C 语言基础及混合编语言基础及混合编程程4.5 ARM 汇编语言实验基础汇编语言实验基础4.1 ARM汇编的语句格式ARM汇编语言基本的的语句格式如下:汇编语言基本的的语句格式如下:符号符号 指令、伪指令或伪操作指令、伪指令或伪操作 ;注释;注释 一些相同的基本特征一些相同的基本特征1、一条指令一行。、一条指令一行。2、使用标号(、使用标号(label)给内存单元提供名称,从第一列)给内存
2、单元提供名称,从第一列开始书写。开始书写。3、指令必须从第二列或能区分标号的地方开始书写。、指令必须从第二列或能区分标号的地方开始书写。4、注释跟在指定的注释字符后面(、注释跟在指定的注释字符后面(ARM使用的是使用的是“;”),一直书写到行尾。),一直书写到行尾。4.1.1符号命名规则1符号由大小写字母、数字及下划线组成,符号不能用数字开头。2符号区分大小写,同名的大、小写符号会被编译器认为是两个不同的符号。3符号在其作用范围内必须唯一。4自定义的符号名不能与系统的保留字相同。5符号名不应与指令或伪指令同名。4.1.2 ARM汇编语言伪操作 伪操作(Directive)是ARM汇编语言程序里
3、的一些特殊的指令助记符,其作用主要是为完成汇编程序做各种准备工作,对源程序运行汇编程序处理,而不是在计算机运行期间由处理器执行。表4-1 ARM汇编常用伪操作列表操作符语法格式功能描述ARMARM指示编译器处理的是32位ARM指令CODE32CODE32指示编译器处理的是32位ARM指令THUMBTHUMB指示编译器处理的是16位THUMB指令CODE16CODE16指示编译器处理的是16位THUMB指令AREA AREA nameattrattr段属性定义ENTRYENTRY声明程序的入口点ENDEND源程序结尾标识EQUname EQU expr,type定义常量或标号名称EXPORTEX
4、PORT name声明全局标号IMPORTIMPORT name外部符号声明4.1.3 ARM汇编语言伪指令伪指令是ARM处理器支持的汇编语言程序里的特殊助记符,它不在处理器运行期间由机器执行,只是在汇编时将被合适的机器指令代替成ARM或Thumb指令,从而实现真正的指令操作。ARM汇编语言伪指令如表3-2所示 表4-2 ARM汇编语言伪指令列表伪指令语法格式功能ADRADRcond register,=expression 它将基于PC相对偏移的地址值或基于寄存器相对偏移的地址值读取到寄存器中。ADRLADRLcondregister,=expression它将基于PC相对偏移的地址值或基于
5、寄存器相对偏移的地址值读取到寄存器中。LDRLDRcond register,=expression将一个32位的常数或者一个地址值读取到寄存器中,可以看作是加载寄存器的内容。NOPNOPNOP是空操作伪指令,在汇编时将会被替代成ARM中的空操作4.1.3 ARM汇编语言伪指令1、ADR伪指令-小范围的地址读取在汇编编译器编译源程序时,ADR伪指令被编译器替换成一条合适的指令。通常,编译器用一条ADD指令或SUB指令来实现该ADR伪指令的功能,若不能用一条指令实现,则产生错误,编译失败。ADR伪指令中的地址是基于PC或寄存器的,当ADR伪指令中的地址是基于PC时,该地址与ADR伪指令必须在同一
6、个代码段中。4.1.3 ARM汇编语言伪指令示例:LOOP MOV r0,#10;LOOP为行标,指示某一行代码ADR r4,LOOP;将LOOP地址放入r4(相对地址);因为pc值为当前指令地址值加8字节替换成本ADR伪指令将被编译器编译为;SUB r4,PC,#0 xc4.1.3 ARM汇编语言伪指令2、ADRL伪指令-中等范围的地址读取地址表达式expr的取值范围:当地址值是字节对齐时,其取指范围为:-64K64K;当地址值是字对齐时,其取指范围为:-256K256K;4.1.3 ARM汇编语言伪指令示例:LOOP MOV r0,#10;LOOP为行标,指示某一行代码ADRL r4,LO
7、OP;将LOOP地址放入r4(相对地址);因为pc值为当前指令地址值加8字节替换成本ADR伪指令将被编译器编译为;SUB r4,PC,#0 xc;NOP (MOV r0,r0)4.1.3 ARM汇编语言伪指令3、LDR伪指令-大范围的地址读取在汇编编译源程序时,LDR伪指令被编译器替换成一条合适的指令。若加载的常数未超出MOV或MVN的范围,则使用MOV或MVN指令代替该LDR伪指令,否则汇编器将常量放入文字池,并使用一条程序相对偏移的LDR指令从文字池读出常量。4.1.3 ARM汇编语言伪指令示例:LDR r1,=0 xff;将0 xff读取到r1中;编译后得到MOV r1,0 xff示例:
8、LDR r1,=ADDR;将外部地址ADDR读取到R1中;汇编后将得到:;LDR r1,PC,OFFSET_TO_LPOOL;LPOOL DCD ADDR4.2 ARM汇编的程序结构 在ARM(Thumb)汇编语言程序中,以程序段为单位组织代码。段是相对独立的指令或数据序列,具有特定的名称。段可以分为代码段和数据段,代码段的内容为执行代码,数据段存放代码运行时需要用到的数据。一个汇编程序至少应该有一个代码段,当程序较长时,可以分割为多个代码段和数据段,多个段在程序编译链接时最终形成一个可执行的映象文件。【例4-1】汇编语言源程序的基本格式AREA EXAMPLE,CODE,READONLY ;
9、定义段的名称和属性,表示了一个段的开始ENTRY ;标识程序的入口点 start ;以下为具体指令MOVR0,#10MOVR1,#3ADDR0,R0,R1END ;标识源文件的结束。1、顺序程序设计2、分支程序设计示例CMP R1,#3;比较R1和#3ADDHIR0,R0,R1;if R13 then R0=R0+R1ADDLSR0,R0,#3;if R13 then ENDADDR0,R0,#3;R0=R0+3END示例LOOPADD R0,R0,R1;R0=R0+R1CMP R0,#3;比较R0和#3BLSLOOP;if R0R2 跳转到 ADD_END ;分支的实现 ADD R0,R0,
10、R1;R0R0+R1 ADD R1,R1,#1;R1R1+1 B LOOP;无条件跳转至LOOP ;循环的实现ADD_END ;行标定义 B ADD_END;无条件跳转ADD_END END;代码结束【例4-3】给出了一个输出Hello World的程序AREA HelloWorld,CODE,READONLY;声明代码段SWI_WriteC EQU&0;输出R0中的字符,&0为预定义的输出代码段入口SWI_Exit EQU&11;程序结束&11为预定义程序结束代码入口ENTRY;代码的入口START ADRR1,TEXT;R1“Hello World”LOOP LDRB R0,R1,#1;读
11、取下一个字节 CMPR0,#0;检查文本终点 SWINESWI_WriteC;若非终点,则打印 BNELOOP;并返回LOOP SWISWI_Exit;执行结束TEXT =“Hello World”,&0a,&0d,0ENDAREA BlkCpy,CODE,READONLY;声明代码段;声明代码段SWI_WriteC EQU&0;输出;输出R0中的字符中的字符SWI_ExitEQU&11;程序结束;程序结束ENTRY;代码的入口;代码的入口ADRR1,TABLE1;R1TABLE1ADRR2,TABLE2;R2TABLE2ADRR3,T1END;R3T1ENDLOOP1LDRR0,R1,#4;
12、读取;读取TABLE1的第一个字的第一个字STRR0,R2,#4;拷贝到;拷贝到TABLE2CMPR1,R3;结束?;结束?BLTLOOP1;若非,则再拷贝;若非,则再拷贝ADRR1,TABLE2;R1TABLE2LOOP2LDRBR0,R1,#1;读取下一个字;读取下一个字CMPR0,#0;检查文本终点;检查文本终点SWINE SWI_WriteC;若非终点,则打印;若非终点,则打印BNELOOP2;并返回;并返回LOOP2SWISWI_Exit;执行结束;执行结束TABLE1=“This is the right string!”,&0a,&0d,0T1ENDALIGN;保证字对准;保证字
13、对准TABLE2=“This is the wrong string!”,0END;程序源代码结束;程序源代码结束4.4 ARM C 语言基础及混合编程4.4.1 ATPCS概述4.4.2 基本ATPCS4.4.3 支持ARM程序和Thumb 程序混合使用的ATPCS4.4.4 C语言及汇编语言混合编程4.4.1 ATPCS概述4.4.1 ATPCS概述 如果汇编代码比较简单,则可以直接利用内嵌汇编的如果汇编代码比较简单,则可以直接利用内嵌汇编的方式进行混合编程;方式进行混合编程;如果汇编代码比较复杂,则可以将汇编程序和如果汇编代码比较复杂,则可以将汇编程序和C程序程序分别以文件的形式加到一个
14、工程里,通过分别以文件的形式加到一个工程里,通过ATPCS标准来标准来完成汇编程序和完成汇编程序和C程序之间的调用。程序之间的调用。4.4.1 ATPCS概述 为了使不同编译器产生的程序和汇编语言编写的程序能灵为了使不同编译器产生的程序和汇编语言编写的程序能灵活地混合,活地混合,ARM公司定义了一系列过程调用的规则,称为公司定义了一系列过程调用的规则,称为ATPCS(ARM-Thumb Procedure Call Standard)。)。这些基本规则包括子程序调用过程中寄存器的使用规则、这些基本规则包括子程序调用过程中寄存器的使用规则、数据栈的使用规则和参数的传递规则。数据栈的使用规则和参数
15、的传递规则。4.4.1 ATPCS概述 如果程序遵守如果程序遵守ATPCS,则程序中,则程序中ARM子程序和子程序和Thumb子子程序可互相调用。程序可互相调用。具体做法是:在编译和汇编时,通过使用具体做法是:在编译和汇编时,通过使用/interwork选项选项可以使编译器生成的目标代码遵守支持可以使编译器生成的目标代码遵守支持ATPCS。对于对于C程序,编译选项为程序,编译选项为apcs/interwork。对于汇编程序,。对于汇编程序,必须保证编写的代码本身遵守必须保证编写的代码本身遵守ATPCS。4.4.2 基本基本ATPCS1.寄存器的使用规则寄存器R0R1R2R3R4R5R6R7R8
16、R9R10R11R12R13R14R15ATPCS名称a1a2a3a4v1v2v3v4WRv5v6SBv7SLv8FP静态基址寄存器SB,数据栈限制指针SL和桢指针FP 2.数据栈的使用规则;3.参数传递的规则。4.4.3 ARM程序和程序和Thumb程序程序的的混合混合使用使用在编译或汇编时,使用/intework告诉编译器或汇编器生成的目标代码遵守支持ARM程序和Thumb程序混合使用的ATPCS,它用在以下场合:程序中存在ARM程序调用Thumb程序的情况;程序中存在Thumb程序调用ARM程序的情况;需要连接器来进行ARM状态和Thumb状态切换的情况;在下述情况下使用选项nointe
17、rwork:程序中不包含Thumb程序;用户自己进行ARM程序和Thumb程序切换。需要注意的是:在同一个C/C+程序中不能同时有ARM指令和Thumb指令。C语言和ARM汇编语言之间相互调用 当链接器发现有当链接器发现有ARM子程序与子程序与Thumb子程序相互调用时,子程序相互调用时,编译器将修改相应的调用和返回代码,或者添加一段编译器将修改相应的调用和返回代码,或者添加一段veneers代码(链接器生成的用于程序状态转换的代码段)来完成程代码(链接器生成的用于程序状态转换的代码段)来完成程序状态的转换。序状态的转换。C语言和语言和ARM汇编语言之间相互调用包含三部分内容:汇汇编语言之间相
18、互调用包含三部分内容:汇编语言程序访问编语言程序访问C语言全局变量、语言全局变量、C语言程序调用汇编语言程语言程序调用汇编语言程序、汇编语言程序调用序、汇编语言程序调用C语言程序。语言程序。C语言和ARM汇编语言之间相互调用 汇编语言程序可通过地址间接访问在汇编语言程序可通过地址间接访问在C语言程序中声明的语言程序中声明的全局变量。具体做法是使用全局变量。具体做法是使用IMPORT关键词引入全局变量,关键词引入全局变量,再利用再利用LDR和和STR指令根据全局变量的地址来进行访问。指令根据全局变量的地址来进行访问。具体做法是使用具体做法是使用IMPORT关键词引入全局变量,再利用关键词引入全局
19、变量,再利用LDR和和STR指令根据全局变量的地址来进行访问。指令根据全局变量的地址来进行访问。unsigned charLDRB/STRBunsigned shortLDRH/STRHunsigned intLDR/STRcharLDRSB/STRSBshortLDRSH/STRSH 对于不同类型的变量,需要选用不同选项的对于不同类型的变量,需要选用不同选项的LDRLDR和和STRSTR指令,列表如下:指令,列表如下:对于结构体,如果知道各个成员的偏移量,则可通对于结构体,如果知道各个成员的偏移量,则可通过过LDR/STR指令进行访问。如果结构体所占空间小于指令进行访问。如果结构体所占空间小
20、于8个字,则可用个字,则可用LDM和和STM一次性读写。一次性读写。AREA globals,CODE,READONLYEXPORT asmsubroutine;用用EXPORT伪操作声明该变量可伪操作声明该变量可 被其它文件引用被其它文件引用;相当于声明了一个全局变量相当于声明了一个全局变量IMPORT globvar;globvar是是C程序中声明的全局变量程序中声明的全局变量;用用IMPRORT伪操作声明该变量是伪操作声明该变量是 在其它文件中定义的在其它文件中定义的;在本文件中可能要用到该变量在本文件中可能要用到该变量asmsubroutineLDR R1,=globvar;从文字池读
21、出从文字池读出globvar的地址,将其的地址,将其 保存到保存到R1LDR R0,R1ADD R0,R0,#2STR R0,R1;将修改后的值返回将修改后的值返回MOV PC,LREND例:例:C语言和ARM汇编语言之间相互调用 首先,为保证程序调用时参数的正确传递,汇编语言程序首先,为保证程序调用时参数的正确传递,汇编语言程序的设计要遵守的设计要遵守ATPCS。其次,汇编语言程序需要使用其次,汇编语言程序需要使用EXPORT伪操作声明本程序伪操作声明本程序可被其它程序调用。可被其它程序调用。同时,在同时,在C语言程序中使用语言程序中使用extern关键词声明来该汇编语关键词声明来该汇编语言
22、程序。言程序。1.内嵌汇编 内嵌汇编器内嵌汇编器armcc和和armcpp用来支持完整的用来支持完整的ARM指令集,指令集,tcc和和tcpp用来支持用来支持Thumb指令集。指令集。内嵌的汇编指令包括大部分内嵌的汇编指令包括大部分ARM指令和指令和Thumb指令,但指令,但不能直接引用不能直接引用C语言的变量定义,数据交换必须通过函数过语言的变量定义,数据交换必须通过函数过程调用标准程调用标准ATPCS(ARM-Thumb Procedure Call Standard)进行。)进行。嵌入式汇编在形式上表现为独立定义的函数体。嵌入式汇编在形式上表现为独立定义的函数体。1.内嵌汇编-内嵌汇编指
23、令 _asm(“指令指令;指令指令”);语法格式语法格式:u 其中其中“_asm”是是ARM C编译器使用的关键字,编译器使用的关键字,“_”是是两个下划线。两个下划线。u 指令之间用指令之间用“;”分隔。分隔。u 如果一条指令占据多行,在行尾可使用连字符如果一条指令占据多行,在行尾可使用连字符“”。u 汇编命令段中可使用汇编命令段中可使用C语言的注释语句。如果有多条汇编语言的注释语句。如果有多条汇编指令嵌入,则可用指令嵌入,则可用“”将它们归为一条语句,将它们归为一条语句,注意注意1.内嵌汇编-内嵌汇编注意事项 对于寄存器对于寄存器R0R3、LR和和PC的使用要格外小心。的使用要格外小心。编
24、译器在计算表达式时可能会将寄存器编译器在计算表达式时可能会将寄存器R0R3、R12和和R14用于子程序调用,因此在内嵌的汇编指令中,不要将用于子程序调用,因此在内嵌的汇编指令中,不要将这些寄存器同时指定为物理寄存器。这些寄存器同时指定为物理寄存器。_asmMOVR0,xADDy,R0,x/y/*(x/y)的结果覆盖了的结果覆盖了R0*/例:例:1.内嵌汇编-内嵌汇编注意事项 不要使用寄存器寻址变量。不要使用寄存器寻址变量。int bad_f(int x)_asmADD R0,R0,#1/*将发生寄存器冲突,将发生寄存器冲突,R0 中保存的中保存的x的值将不变的值将不变*/return x;例:
25、例:1.内嵌汇编-内嵌汇编注意事项 使用内嵌汇编时,编译器会自动保存和恢复可能用到的寄使用内嵌汇编时,编译器会自动保存和恢复可能用到的寄存器,用户无须在程序中再作这些工作。读物理寄存器(除存器,用户无须在程序中再作这些工作。读物理寄存器(除PSR寄存器之外)之前必须先进行写入。寄存器之外)之前必须先进行写入。int f(int x)_asmSTMFD SP,R0;由于由于SP出现了写前先读,因出现了写前先读,因 此对此对R0的保存是非法的的保存是非法的ADDR0,x,#1EORx,R0,xLDMFD SP!,R0;对对R0的恢复没有必要的恢复没有必要 return x;例:例:1.内嵌汇编-内
展开阅读全文