|
個人認為,AVR系列的串口使用還是比較容易出錯,如果采用傳統的查詢方式太耗系統時間,而且現在關于AVR的教材大多給你的是查詢發送方式,中斷接收方式。
本例子是采用中斷接收,中斷發送方式。希望對大家有所幫助。
//ICC-AVR
// Target : M8
// Crystal: 4.0000Mhz
#include <iom8v.h>
#include <macros.h>
#define DISABLE_UARTTX() UCSRB&=~BIT(TXCIE)
#define ABLE_UARTTX() UCSRA|=BIT(TXC);UCSRB|=BIT(TXCIE)
unsigned char ucRecv;
unsigned char ucRecvOk;
unsigned char ucSendData[8]="Recv OK!";
unsigned char ucComSendCnt,ucComSendPtr;
void InitPort(void)
{
PORTB = 0xFF;
DDRB = 0x00;
PORTC = 0x7F; //m103 output only
DDRC = 0x00;
PORTD = 0xFE;
DDRD = 0x02;
}
//UART0 initialize
// desired baud rate: 2400
// actual: baud rate:2404 (0.2%)
void InitUart0(void)
{
UCSRB = 0x00; //disable while setting baud rate
UCSRA = 0x00;
UCSRC = BIT(URSEL) | 0x06;
UBRRL = 0x67; //set baud rate lo
UBRRH = 0x00; //set baud rate hi
UCSRB = 0x98;
}
#pragma interrupt_handler uart0_rx_isr:iv_USART0_RXC
void uart0_rx_isr(void)
{
unsigned char ucTmp;
//uart has received a character in UDR
ucTmp=UDR;
if (ucTmp=='A')
{
ucRecv=ucTmp;
ucRecvOk=0x01;
}
}
#pragma interrupt_handler uart0_tx_isr:iv_USART0_TXC
void uart0_tx_isr(void)
{
//character has been transmitted
if (ucComSendCnt!=0)
{
ucComSendPtr+=1;
UDR=ucSendData[ucComSendPtr];
ucComSendCnt-=1;
}else
{
//PORTB&=~BIT(PB_COM_LED); //串口指示燈滅
DISABLE_UARTTX();
//PORTB^=BIT(PB_COM_LED); //串口指示燈滅
}
}
//call this routine to initialize all peripherals
void InitMcu(void)
{
//stop errant interrupts until set up
CLI(); //disable all interrupts
InitPort();
InitUart0();
MCUCR = 0x00;
GICR = 0x00;
TIMSK = 0x00; //timer interrupt sources
SEI(); //re-enable interrupts
//all peripherals are now initialized
}
void main(void)
{
unsigned char i;
InitMcu();
while(1)
{
if (ucRecvOk==0x01)
{
CLI();
ucRecvOk=0;
SEI();
ucComSendCnt=7;
ucComSendPtr=0;
ABLE_UARTTX();
UDR=ucSendData[0];
}
}
}
|
-
-
m8 串口通訊.zip
2024-1-11 21:07 上傳
點擊文件名下載附件
下載積分: 黑幣 -5
44.24 KB, 下載次數: 4, 下載積分: 黑幣 -5
評分
-
查看全部評分
|