📄 sart.c
字号:
/* //////////////////////////////////////////////////////////////////////////
// sart.c - source file for lme2200 API
//
// Copyright 2005, Leaguer MicroElectronics Co., Ltd
// www.leaguerme.com
//////////////////////////////////////////////////////////////////////////// */
#include <REG922.H>
#include "sart.h"
#include "timer.h"
#define uint unsigned int
#define uchar unsigned char
#define MAX_FRAME_SZ 28
#define STAT_PREAMBLE 1
#define STAT_SYNC 2
#define STAT_SYNC1 3
#define STAT_DATALEN 4
#define STAT_DATA 5
#define FRAME_PREAMBLE 0xFE
#define FRAME_SYNC 0x68
#define FRAME_END 0x16
idata uchar amr_frame[MAX_FRAME_SZ]; // amr frame rx buffer
//bit amr_recved; // amr frame received flag
// variables used during amr frame reception
idata uchar amr_stat;
idata uchar amr_len;
idata uchar amr_count;
idata uchar uart_buf[16];
idata uchar uart_wptr, uart_rptr;
/*=============================================================================*/
void uart_init()
{
SCON =0xd0; // select BRG as UART Baud Rate Gen
SSTAT=0xe0;
BRGR0=0xf0; // setup BRG for 9600 baud @ 7.373MHz external Crystal
BRGR1=0x02;
// BRGR0=0xf0; // setup BRG for 4800 baud @ 7.373MHz external Crystal
// BRGR1=0x05;
// BRGR0=0xf0; // setup BRG for 2400 baud @ 7.373MHz external Crystal
// BRGR1=0x0b;
BRGCON = 0x03; // enable BRG
IP0H = 0x12; //中断优先级,串口3级,定时器0为2级,外为1级
IP0 = 0x14;
TI = 0; // do not allow transmit
EA = 1;
ES = 1;
amr_stat = STAT_PREAMBLE; //<-------------设接收的初始计数1
// amr_recved = 0;
D_SYNC = 1;//--------------设同步输入无效
uart_wptr = 0;
uart_rptr = 0;
}
/*=============================================================================*/
/* Serial port ISR */
void serial_int (void) interrupt 4
{
//unsigned char c;
/*
* The interrupt was generated. First, check the RI flag to see if it was
* because a new character was received.
*/
if (RI == 1) { /* it was a receive interrupt */
RI = 0; /* clear the received interrupt flag */
uart_buf[uart_wptr++] = SBUF;
uart_wptr &= 0x0f;
}
#ifdef xxx
else if (TI == 1) /* otherwise, assume it was a transmit interrupt */
{
TI = 0; /* clear the transmit interrupt flag */
if (chr != '\0') /* if there's something in the local buffer... */
{
if (chr == '\r') chr = '\n'; /* convert <CR> to <LF> */
SBUF = chr; /* put the character into the transmit buffer */
chr = '\0';
}
}
#endif
}
/*=============================================================================*/
int uart_recved()
{
if (uart_wptr == uart_rptr) return 0;
return 1;
}
/*=============================================================================*/
// Call this function only when uart_recved() is true
unsigned char uart_getchar(void)
{
uchar c;
c = uart_buf[uart_rptr++];
uart_rptr &= 0x0f;
return c;
}
/*
int uart_processed()
{
amr_recved = 0;
uart_wptr = 0;
uart_rptr = 0;
return 1;
}
*/
/*=============================================================================*/
int recv_amr_frame(void)
{
uchar c;
c = uart_getchar();
// uart_sendchar(c);
if (amr_stat == STAT_PREAMBLE) { //1
// Searching for preamble...
if (c == FRAME_PREAMBLE) { //fe uart_sendchar(c);
amr_stat = STAT_SYNC;
amr_count = 0;
}
}
else if (amr_stat == STAT_SYNC) { //2 检测到68
// Searching for frame sync ...
amr_count++;
if (c == FRAME_SYNC) { //68
amr_count = 0;
amr_stat = STAT_SYNC1; //3 uart_sendchar(c);
}
else if (amr_count >= 4) {
// re-start
amr_stat = STAT_PREAMBLE; //1
}
}
/*
else if (amr_stat == STAT_SYNC1) { //3
// Receive address bytes
amr_frame[amr_count++] = c;
if (amr_count == 7) { //4个表地址+C+L
if (c == FRAME_SYNC) { // 68uart_sendchar(c);
amr_count = 0;
amr_stat = STAT_DATALEN; //4
}
else amr_stat = STAT_PREAMBLE; //1
}
} */
else if (amr_stat == STAT_SYNC1) {//3
amr_frame[amr_count++] = c; //收数据
if (amr_count == 6) {
amr_len = c + 1; //收取长度值
amr_count = 0;
amr_stat = STAT_DATA; // uart_sendchar(c);
}
}
else if (amr_stat == STAT_DATA) { //5
amr_frame[6+amr_count++] = c;
if (amr_count == amr_len) {
amr_count = 0;
amr_stat = STAT_PREAMBLE; //1
if (c == FRAME_END){ //16h uart_sendchar(c);
// uart_sendblock(amr_frame,amr_len+6);
return 1;
}
}
}
return 0;
}
/*=============================================================================*/
// Transmit a single byte
void uart_sendchar(uchar chr)
{
// unsigned char i , a;
/* Disable serial interrupts for a while */
ES = 0;
/*
* Clear the Transmit Interrupt flag to prepare the serial port
* to send a new character.
*/
TI = 0;
ACC=chr; /*从缓冲中发送串行口数据*/
TB8=P; /*--------------------- *偶校验位设置*/
SBUF=ACC;
/* Wait until tx buffer is empty */
while (TI != 1) {;}
// Clear it
TI = 0;
/* Enable serial interrupts*/
ES = 1;
}
/*=============================================================================*/
void uart_sendblock(uchar buf[], int len)
{
uchar i;
for (i = 0; i < len; i++) uart_sendchar(buf[i]);
}
/*=============================================================================*/
// Sync transmit/receiving
/*=============================================================================*/
void sync_sendchar(uchar c)
{
int i;
EA = 0;
SDATA = 1;
while (D_RDY == 0); // wait for D_RDY to become high
D_SYNC = 0;
for (i = 0; i < 8; i++) {
SDATA=(c & 0x01) ? 1:0 ; // put data bit
SCLK=0;
SCLK=0;
SCLK=0;
SCLK=0;
c >>= 1; // next bit
SCLK=1;
SCLK=1;
SCLK=1;
SCLK=1;
}
D_SYNC = 1;
SDATA=1;
EA = 1;
}
/*=============================================================================*/
int sync_recved()
{
return (RX_RDY == 0) ? 1 : 0;
}
/*=============================================================================*/
int sync_data_ready()
{
return (D_RDY == 0) ? 1 : 0;
}
/*=============================================================================*/
// Call this function only when sync_recved() returns 1
int sync_getchar(void)
{
uchar l;
int c;
EA = 0;
D_SYNC = 1;
// while(D_RDY!=0);
for (l = 0; l < 8; l++) {
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
SCLK = 0;
c >>= 1;
if (SDATA) c |= 0x80;
else c &= 0x7f;
SCLK = 1;
SCLK = 1;
SCLK = 1;
SCLK = 1;
}
D_SYNC = 1;
EA = 1;
return c;
}
/*=============================================================================*/
int sync_getblock(uchar buf[], int len)
{
unsigned char i;
for (i = 0; i < len; i++) {
if (sync_data_ready()) buf[i] = sync_getchar();
else return -1;
}
return len;
}
/*$$$$$$$$$$$$$$$$$$$$$$$$$$$$<<<<<软件说明>>>>>$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$* /
!!!!!!重复特别注意:写表的地址必须从串口写入才有效!!!!!
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
/*$$$$$$$$$$$$$$$$$$$$$$$$$$$$<<<<<软件说明>>>>>$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -