ARM实验指导书Word格式.docx
《ARM实验指导书Word格式.docx》由会员分享,可在线阅读,更多相关《ARM实验指导书Word格式.docx(46页珍藏版)》请在冰豆网上搜索。
ASL算术左移
ASR算术右移
ROR循环右移
RRX带扩展循环右称
实验内容
1、把内存中ramaddr开始的ramword个字清零
(1)用后变址法
ramaddrequ0x31000000
ramwordequ64
clrram
movr0,#0
movr1,#ramword
ldrr2,=ramaddr
clrram1
strr0,[r2],#4
subsr1,r1,#1
bneclrram1
movpc,lr
LTORG
(2)用前变址法
clrrambak
ldrr2,=ramaddr-4
clrram2
strr0,[r2,#4]!
bneclrram2
LTORG
2、把寄存器中,r0-r12的32位无符号32位数进行求和,和的低32位保存在r1中,高32位保存在r0中。
add13b
addsr1,r0,r1
movr0,#0
adcr0,r0,#0
addsr1,r1,r2
addsr1,r1,r3
。
。
以上程序在主程序完成初始化后调后。
打开寄存器,内存窗口等,观察程序执行前后的变化,及执行过程中的一些状态,并记录。
实验步骤
1、连接实验箱与计算机的串口线,打开超级终端,并设定为com1,115200,8,N,1,N
2、连接仿真调试电缆(并口到JTAG)
3、实验箱上电,并在vivi的指示下,按任意键,进入调试程序状态
4、打开ARM集成开发环境ADS,按要求编写或打开实验程序。
5、按内容要求编写,调试程序,并记录调试过程和数据。
6、调试完毕,整理实验箱,并放回原位。
实验思考题
1、在子程序调用时,子程序的下一条语句的地址保存在哪里?
2、编写程序计算r0-r12中16位二进制无符号数的和,每个寄存器中保存两个16位二进制无符号数。
实验报告要求
参见附录D
实验二ARM汇编语言控制串行口程序
2、掌握用ARM汇编语言设计简单程序
3、了解S3C2410中串行口的控制与编程方法
ARM实验箱,计算机,ADS程序开发软件,串口调试助手V2.2
S3C2410有3个通用异步串行接口,可以工作在DMA方式或中断模式,每个通道内部具有16字节的发送FIFO和接收FIFO,支持5-8位串行数据的发送与接收,可编程波特率,具有测试用的回环模式(LoopBack)。
1、串行接口相关寄存器
ULCON:
线控制器,用于控制帧的格式
UCON:
总控制器,可用于设置发送和接收模式
UFCON:
FIFO控制器,用于设置FIFO是否使能
UMCON:
MODEM控制器,用于设置是否AFC,用于在通过UFSTAT检测到FIFO满时,设置rts使得对方不再发送
UTRSTAT:
发送/接收状态,用于检测发送/接收缓冲是否空或满,非AFC和非FIFO时用程序检测此位以确定数据是否己发出
UERSTAT:
错误状态检测
UFSTAT:
用于检测FIFO是否为满
UMSTAT:
MODEN状态检测,用于检查cts状态以确定是否可以发数据
UTXH:
发数据于此
URXH:
收数据于此
UBRDIV:
用于设置波特率
下面将针对UART的各个控制寄存器逐一进行讲解
ULCONn(UARTLineControlRegister)
WordLength:
数据位长度
NumberofStopBit:
停止位数
ParityMode:
奇偶校验位类型
Infra-RedMode:
UART/红外模式选择(当以UART模式工作时,需设为“0”)
UCONn(UARTControlRegister)
ReceiveMode:
选择接收模式。
如果是采用DMA模式的话,还需要指定使用的DMA信道。
TransmitMode:
同上。
SendBreakSignal:
选择是否在传1帧资料中途发送Break信号。
LoopbackMode:
选择是否将UART置于Loopback测试模式。
RxErrorStatusInterruptEnable:
选择是否使能当发生接收异常时,是否产生接收错误中断。
RxTimeOutEnable:
是否使能接收超时中断。
RxInterruptType:
选择接收中断类型。
选择0:
Pulse(脉冲式/边沿式中断。
非FIFO模式时,一旦接收缓冲区中有资料,即产生一个中断;
为FIFO模式时,一旦当FIFO中的资料达到一定的触发水平后,即产生一个中断)
选择1:
Level(电平模式中断。
非FIFO模式时,只要接收缓冲区中有资料,即产生中断;
为FIFO模式时,只要FIFO中的资料达到触发水平后,即产生中断)
TxInterruptType:
类同于RxInterruptType
ClockSelection:
选择UART波特率发生器的时钟源。
UFCONn(UARTFIFOConrtolRegister)
FIFOEnable:
FIFO使能选择。
RxFIFOReset:
选择当复位接收FIFO时是否自动清除FIFO中的内容。
TxFIFOReset:
选择当复位发送FIFO时是否自动清除FIFO中的内容。
RxFIFOTriggerLevel:
选择接收FIFO的触发水平。
TxFIFOTriggerLevel:
选择发送FIFO的触发水平。
UMCONn(UARTModemControlRegister)
RequesttoSend:
如果在AFC模式下,该位将由UART控制器自动设置;
否则的话就必须由用户的软件来控制。
AutoFlowControl:
选择是否使能自动流控(AFC)。
UTRSTATn(UARTTX/RXStatusRegister)
Receivebufferdataready:
当接收缓冲寄存器从UART接收端口接收到有效资料时将自动置“1”。
反之为“0”则表示缓冲器中没有资料。
Transmitbufferempty:
当发送缓冲寄存器中为空,自动置“1”;
反之表明缓冲器中正有资料等待发送。
Transmitterempty:
当发送缓冲器中已经没有有效资料时,自动置“1”;
反之表明尚有资料未发送。
UERSTATn(UARTErrorStatusRegister)
OverrunError:
为“1”,表明发生Overrun错误。
FrameError:
为“1”。
表明发生Frame(帧)错误。
UFSTATn :
(UART FIFOStatusRegister)见图5-19
RxFIFOCount:
接收FIFO中当前存放的字节数。
TxFIFOCount:
发送FIFO中当前存放的字节数。
RxFIFOFull:
为“1“表明接收FIFO已满。
TxFIFOFull:
为“1“表明发送FIFO已满。
UMSTATn :
(UART FIFOStatusRegister)
CleartoSend:
为“0”表示CTS无效;
为“1”表示CTS有效。
DeltaCTS:
指示自从上次CPU访问该位后,nCTS的状态有无发生改变。
为“0”则说明不曾改变;
反之表明nCTS信号已经变化了。
UTXHn和URXHn分别是UART发送和接收资料寄存器
这两个寄存器存放着发送和接收的资料,当然只有一个字节8位资料。
需要注意的是在发生溢出错误的时候,接收的资料必须要被读出来,否则会引发下次溢出错误
2、串口波特率计算
每个UART控制器都有各自的波特率发生器来产生发送和接收资料所用的序列时钟,波特率发生器的时钟源可以CPU内部的系统时钟,也可以从CPU的UCLK管脚由外部取得时钟信号,并且可以通过UCONn选择各自的时钟源。
波特率产生的具体计算方法如下:
当选择CPU内部时钟时:
UBRDIVn=(int)(PCLK/(bps*16))-1,bps为所需要的波特率值,PCLK为CPU内部外设总线(APB)的工作时钟。
当需要得到更精确的波特率时,可以选择由UCLK引入的外部时钟来生成。
UBRDIVn=(int)(UCLK/(bps*16))-1
3、串口发送和接收程序设计步骤
串口数据发送
(1)、设置串口工作在中断和轮训模式
(2)、设置串口的数据位长度,停止位,是否有奇偶校验位
(3)、设置串口收发数据波特率
(4)、将数据写到发送寄存器
(5)、检测状态寄存器相关位判断是否发送完成
串口数据读取
(1)、设置串口工作在中断和轮询模式
(2)、设置串口收发数据位长度,停止位,是否有奇偶校验
(3)、设置串口收发数据的波特率
(4)、检测状态寄存器是否有数据
(5)、读取数据
1、设计一个程序从串口发送数据给计算机,发送的数据是ASCII码所有字符
UART
ldrr0,=GPHCON;
//设置RxD0,TxD0引脚
ldrr1,=0x2afaaa
strr1,[r0]
ldrr0,=GPHUP
ldrr1,=0x7ff
strr1,[r0];
//ThepullupfunctionisdisabledGPH[10:
0]
ldrr0,=UFCON0;
//禁用FIFO
ldrr1,=0x0
ldrr0,=UMCON0;
//禁用AFC
ldrr0,=ULCON0;
//设置线寄存器
ldrr1,=0x3;
//UARTLINECONFIG正常模式,无奇偶校验,一个停止位,8个数据位
ldrr0,=UCON0;
//设置Uart0控制器
ldrr1,=0x245;
//RX边沿触发,TX电平触发,禁用延时中断,使用RX错误中断,正常操作模式,中断请求或表决模式
ldrr0,=UBRDIV0;
//设置波特率为115200
ldrr1,=0x6;
//int(50700000/16/115200)-1=26由于PCLK=1/4FCLK,改为6
movr1,#100
Delay
subr1,r1,#0x1
bneDelay
;
//开中断
ldrr0,=INTMSK
ldrr1,[r0]
andr1,r1,#0xefffffff
MOVR5,#127;
//设置要打印的字符的个数
MOVR1,#0x0;
//设置要打印的字符
LOOP
LDRR3,=UTRSTAT0
LDRR2,[R3]
TSTR2,#0x04;
//判断发送缓冲区是否为空
BEQLOOP;
//为空则执行下边的语句,不为空则跳转到LOOP
LDRR0,=UTXH0
STRR1,[R0];
//向数据缓冲区放置要发送的数据
ADDR1,R1,#1
SUBR5,R5,#0x01;
//计数器减一
CMPR5,#0x0
BNELOOP
LOOP2BLOOP2
1、连接实验箱与计算机的串口线,打开计算机超级终端,并设定为com1,115200,8,1,0N。
(打开串口调试助手V2.2软件,并做相应设置。
)
1、把实验程序改成一个单独的代码段,存放在一个单独的文件中,并且使其功能与实验程序相同。
实验三ARMC语言程序设计基础
1、了解ARMC语言程序的特点
2、了解ARMC语言外部IO口地址的定义与使用方法
3、掌握用ARMC语言设计简单程序
1、开发ARM系统,使用C语言编程是大势所趋
在应用系统的程序设计中,若所有的编程任务均由汇编语言来完成,其工作量的巨大的,并且不易移植。
由于ARM的程序执行速度较高,存储器的存储速度和存储量也很高,因此,C语言的特点充分发挥,使得应用程序的开发时间大为缩短,代码移植十分方便,程序的重复使用率高,程序架构清晰易懂,管理较为容易等等。
因此,C语言在ARM系统开发中具有重要的地位。
2、ARMC语言的基本规则
在ARM的程序开发中,需要大量读写硬件寄存器,并且尽量缩短程序的执行时间的代码一般是用汇编语言来编写的,比如ARM的启动代码,ARM操作系统的移植代码等,除此之外,绝大多数可以使用C语言来完成。
ARM的开发环境是一个嵌入式集成开发环境,只不过这个开发环境和ARM的硬件紧密相关。
在使用C语言时,要用到和汇编语言的混合编程。
当汇编代码较为简洁,则可使用直接内嵌汇编的方法,否则,使用将汇编程序以文件的形式加入项目中,通过ATPCS的规定与C程序相互调用与访问。
ATPCS规定,请参阅ARM相关文档资料
满足ATPCS规定的汇编程序应满足下面3个条件:
在子程序编写中,必须遵守相应的ATPCS规则(函数的参数引用与返回)
堆栈的使用要遵守相应的ATPCS规则
在汇编编译器中使用–atpcs选项
汇编程序调用C程序
(1)汇编程序的设置要遵守ATPCS规则,保证程序调用时参数正确传递
(2)在汇编程序中使用IMPORT伪指令声明将要调用的C程序函数
(3)在调用C程序时,要正确设置入口参数,然后使用BL调用
C程序调用汇编程序
(2)在汇编程序中使用EXPORT伪指令声明本子程序,使其他程序可以调用此程序
(3)在C程序中使用extern关键字声明外部函数(声明要调用的汇编子程序)。
在C语言环境内开发应用程序,一般要一个汇编的启运程序,从汇编的启动程序,跳到C语言下的主程序,然后执行C程序,在C环境下读写硬件寄存器,一般是通过宏调用进行,在每个项目文件的Startup2410/INC目录下都有一个2410addr.h的头文件,那里定义了所有关于2410的硬件寄存器的宏,对宏的读写就能操作2410的硬件。
其它请参阅《嵌入式C语言程序设计》
1、用ARMC语言编写程序,控制GPIO的G口的两个LED灯,使其交替点亮。
实验电路如图所示。
通过控制GPG8,GPG9的高低电平就可以控制LED的亮暗。
rGPGDAT=rGPGDAT&
0xcff|0x200;
//0ch=1100b,D2亮,D1暗
0xcff|0x100;
//0ch=1100b,D2暗,D1亮
实验程序如下:
voidledflash(void)
{
inti;
rGPGDAT=rGPGDAT&
for(i=0;
i<
10000000;
i++);
//延时
0xcff|0x300;
//两个LED都暗
}
该程序每运行一次两个发光二极管各亮一次,重复执行,就可以看到LED闪烁的情况。
主程序(函数)的开始处必须设置GPG口的工作状态。
voidMain(void){
Target_Init();
rGPGCON=rGPGCON&
0xfff0ffff|0x00050000;
for(;
;
){ledflash();
2、用ARMC语言编写程序,编写一个流水灯程序。
实验箱中8个LED灯的内存映射地址是0x20000000。
产生流水灯效果,只要按顺序逐个点亮LED即可。
从图上可知,往这个地址写0,就可以点亮相应的二极管。
#defineoutled(*(volatileunsigned*)0x20000000)
#defineinputkey(*(volatileunsigned*)0x20000016)
voidledstep(void)
unsignedshortinti,j;
intk;
j=1;
for(i=8;
i>
0;
i--)
{
j=j*2;
//左移一位
outled=~j;
//取反输出(只有一位亮)
for(k=0;
k<
k++);
}
outled=255;
//把所有的发光二极管全部熄灭
重复执这个程序,就可以产生流水灯效果。
1、连接实验箱与计算机的串口线,打开计算机超级终端,并设定为com1,115200,8,1,0N
2、连接仿真调试电缆(并口到JTAG)。
3、实验箱上电,并在vivi的指示下,按任意键,进入调试程序状态。
1、设计一个程序,根据输入数字点亮相应个数的LED二极管。
如:
输入2,点亮2个发光二极管。
实验四键盘显示电路驱动程序设计
1、了解ARMC语言程序的结构特点
2、了解ARMC语言程序的编写方法
3、掌握用ARM编写HD7279控制程序方法
HD7279A专用键盘显示电路,真正的单片LED数码管显示和键盘接口芯片,无需外围电路,只需要外接少量的电阻等,即可构成完善的显示、键盘接口电路。
而与CPU的接口采用SPI串行接口方式,使用方便。
可方便的构成64按键,8位数码显示电路(共阴极结构)
HD7279A内部含有译码器,可直接受BCD码或16进制数据或七段显示码数据。
此外,还具有多种控制指令,如消隐,闪烁,左移,右移,段寻址等。
具有片选信号,可方便地实现多于8位的显示或多于64键的键盘接口。
HD7279的纯指令:
1、复位指令(A4H)
当HD7279A收到该指令后,将所有显示清除,所有设置的字符消隐、闪烁等属性也被一起清除。
执行后,芯片的状态与上电时一样。
2、测试指令(BFH)
该指令使所有的LED全部点亮,并处于闪烁状态,主要用于测试(检查LED是否坏)
3、左移指令(A1H)
使所有显示左移一位,消隐及闪烁属性不移位,最右边一位为空(暗)。
4、右移指令(A0H)
使所有显示右移一位,消隐及闪烁属性不移位,最左边一位为空(暗)。
5、循环左移指令(A3H)
使所有显示右移一位,消隐及闪烁属性不移位,最左边一位移到最右边。
6、循环右移指令(A2H)
使所有显示右移一位,消隐及闪烁属性不移位,最右边一位移到最左边。
HD7279带数据的指令:
1、下载数据按方式0译码
命令由两字节构成,前半部为指令。
a2,a1,a0为位地址,D3-D0为数据,译码值如图所示。
当前位小数点由DP控制,DP=1,小数点亮,DP=0,小数点暗。
2、下载数据按方式1译码
指令格式与指令1相同,译码表如下所示。
3、下载数据但不译码
指令格式如上图所示。
当指令第二字节的位为1时,相应段点亮。
4、闪烁控制88H
此命令控制各数码管的闪烁情况。
D8-D1中的位为1时,对应位闪烁。
上电默认不闪烁。
5、消隐控制98H
D8-D1控制数码管的消隐状态。
为1时,数码管消隐,为0时,正常显示。
输入的数据至少有一位为0。
输入全为0时,命令将被忽略。
5、段点亮命令
6、段消隐命令
7、读键盘命令
该指令从HD7279中读出当前按键编码。
编码范围是0-3FH。
当HD7279收到读指令时,此时按键无效,将返回0FFH。
1、编写程序控制HD7279显示12345678
HD7279驱动程序包含接口读写程序、HD7279发命令、收数据程序、初始化程序等,在ARM7279.C文件中给出。
在HD7