AVR单片机 实验七 UART传输实验
1 实验目的
通过实验,掌握UART各个控制寄存器的设置,并能使用串口发送数据和使用中断方式接收数据。
2 实验内容
(6) 设置UART的发送为查询方式,而接收则采中断方式。
(7) 将发送信号(TXD)接脚与接收接脚(RXD)相互连接,以进行自传自收数据的动作;并将数据传输结果显示于数码管。
实验电路:
3实现UART数据传输功能: (写出完整程序代码)
(1) 将PD0 (RXD)与PD1 (TXD)脚相互连接,由UART的TXD发送自己的学号后四码,而UART的RXD接收数据,并显示该学号后四码于数码管。
(2) 将PD0与PD1接脚的连接线移除,此时UART的RXD将接收不到数据,并显示”FAIL”于数码管。
原始程序码:
#include <iom16v.h>
#include <macros.h>
#include <stdio.h>
void Delay(int); //延时函数
void UART_TX(unsigned char); //UART发送数据函数
void Show(); //数码管动态显示函数
unsigned char num[4]={0xf9,0xc0,0xa4,0xf8}; //个人学号后4码
unsigned char err[4]={0x8e,0x88,0xf9,0xc7}; //错误信息:“FAIL”
unsigned char buf[4]={0xff,0xff,0xff,0xff}; //显示数组预设数码管全灭
unsigned char en[4]={0xfe,0xfd,0xfb,0xf7}; //4位数码管扫描码
unsigned char i,ix=0,flg=0,rcv;
int cnt=0,dly=0;
void main()
{
DDRA=0xff; //设PA0~PA7全部为输出
PORTA=0xff; //令数码管所有段灯皆不亮
DDRB=0xff; //设PB0~PB3为输出
PORTB=0xff; //关闭所有数码管
DDRD=0x02; //设PD0 (RXD)为输入, PD1 (TXD)为输出
PORTD=0x03; //设TXD起始为”Hi”, RXD上拉电阻有效
UCSRA=0x00; //设置USART起始状态
UCSRB=0x98; //致能TX and RX动作, 仅允许RX发生中断
UCSRC=0x86; //数据格式: 8-bit data, 1 stop bit, no parity bit
UBRRH=0x00; //设置baud rate=9600 bps
UBRRL=0x2f;
TCCR0=0x0c; //设T/C0为CTC模式,分频系数为256
TCNT0=0; //T/C0计数器内容清0
OCR0=31; //设置OCR0以产生约1ms的定时
TIMSK=0x02; //允许T/C0的比较匹配中断
SREG|=0x80; //致能中断
do{
for(i=0;i<4;i++)
{
UART_TX(num[i]);
Delay(1);
if(flg==1)
{
buf[i]=num[i];
flg=0;
}
else{
buf[i]=err[i];
}
}
Delay(100);
}while(1);
}
void Show() //数码管动态显示扫描函数
{
PORTB=PORTB|0x0f; //关闭所有数码管
PORTA=buf[ix]; //送出段码至数码管
PORTB=PORTB&en[ix]; //显示该位数码管
ix++; //数码管位指针切换至下一位
if(ix>3)
ix=0; //若已到最后1位, 则数码管位指针清0
}
void Delay(int val) //延时函数
{
dly=val;
while(dly>0); //等待设定的延时结束
}
void UART_TX(unsigned char data) //发送数据函数
{
while(!(UCSRA &(1<<UDRE))); //等待数据缓冲器是否已空
UDR=data; //发送数据
}
#pragma interrupt_handler USART_RXC: 12 //UART接收数据完成中断服务程序
void USART_RXC()
{
rcv=UDR; //接收数据
flg=1; //设置接收数据完成标志变量
}
#pragma interrupt_handler TC0_SUB: 20 //T/C0比较匹配中断服务程序
void TC0_SUB()
{
if(cnt>0)
cnt=cnt-1; //接收错误计时变量减1
if(dly>0)
dly=dly-1; //延时变量减1
Show(); //调用数码管动态显示函数
}