📄 scc2692.c
字号:
// SCC2692.C: DUART module
// Author: Alex Duan
// Date: 2002-08-12
// Version: 1.0
///////////////////////////
//#include "DrvCom.h"
#include "SCC2692.h"
/*
*********************************************************************
* CONSTANTS *
*********************************************************************
*/
#define UBA 0xFFD0 // Uart Base Addr
#define MRA XBYTE[UBA + 0x0] // Mode Register A (MR1A, MR2A)
#define SRA XBYTE[UBA + 0x1] // Status Register A (SRA)
#define CSRA XBYTE[UBA + 0x1] // Clock Select Register A (CSRA)
#define BRG XBYTE[UBA + 0x2] // BRG Test
#define CRA XBYTE[UBA + 0x2] // Command Register A (CRA)
#define RHRA XBYTE[UBA + 0x3] // Rx Holding Register A (RHRA)
#define THRA XBYTE[UBA + 0x3] // Tx Holding Register A (THRA)
#define IPCR XBYTE[UBA + 0x4] // Input Port Change Register (IPCR)
#define ACR XBYTE[UBA + 0x4] // Aux. Control Register (ACR)
#define ISR XBYTE[UBA + 0x5] // Interrupt Status Register (ISR)(Read Only)
#define IMR XBYTE[UBA + 0x5] // Interrupt Mask Register (IMR) (Write Only)
#define CTU XBYTE[UBA + 0x6] // Counter/Timer Upper Value (CTU)
#define CRUA XBYTE[UBA + 0x6] // C/T Upper Preset Value (CRUR)
#define CTL XBYTE[UBA + 0x7] // Counter/Timer Lower Value (CTL)
#define CTLR XBYTE[UBA + 0x7] // C/T Lower Preset Value (CTLR)
#define MRB XBYTE[UBA + 0x8] // Mode Register B (MR1B, MR2B)
#define SRB XBYTE[UBA + 0x9] // Status Register B (SRB)
#define CSRB XBYTE[UBA + 0x9] // Clock Select Register B (CSRB)
#define TEST XBYTE[UBA + 0xA] // 1X/16X Test
#define CRB XBYTE[UBA + 0xA] // Command Register B (CRB)
#define RHRB XBYTE[UBA + 0xB] // Rx Holding Register B (RHRB)
#define THRB XBYTE[UBA + 0xB] // Tx Holding Register B (THRB)
#define INPORT XBYTE[UBA + 0xC] // Input Ports IP0 to IP6
#define OPCR XBYTE[UBA + 0xC] // Output Port Conf. Register (OPCR)
#define STARTC XBYTE[UBA + 0xE] // Start Counter Command
#define SETOP XBYTE[UBA + 0xE] // Set Output Port Bits Command
#define STOPC XBYTE[UBA + 0xF] // Stop Counter Command
#define RESETOP XBYTE[UBA + 0xF] // Reset Output Port Bits Command
#define TX_INTA uISR & 0x01 // TxRDYA INT
#define RX_INTA uISR & 0x02 // RxRDY/FFULLA INT
#define TX_INTB uISR & 0x10 // TxRDYB INT
#define RX_INTB uISR & 0x20 // RxRDY/FFULLB INT
#define RXA_BUF_SIZE 256 // UartA rx buffer size
#define TXA_BUF_SIZE 256 // UartA tx buffer size
#define RXB_BUF_SIZE 256 // UartB rx buffer size
#define TXB_BUF_SIZE 256 // UartB tx buffer size
/*
*********************************************************************
* STATIC GLOBAL VARIABLES *
*********************************************************************
*/
static BYTE xdata rxaBuf[RXA_BUF_SIZE]; // UartA rx buffer
static BYTE xdata txaBuf[TXA_BUF_SIZE]; // UartA tx buffer
static BYTE xdata rxbBuf[RXB_BUF_SIZE]; // UartB rx buffer
static BYTE xdata txbBuf[TXB_BUF_SIZE]; // UartB tx buffer
static BYTE rxaStart; // rxaBuf start index
static BYTE rxaStop; // rxaBuf stop index
static BYTE txaStart; // txaBuf start index
static BYTE txaStop; // txaBuf stop index
static BYTE rxbStart; // rxbBuf start index
static BYTE rxbStop; // rxbBuf stop index
static BYTE txbStart; // txbBuf start index
static BYTE txbStop; // txbBuf stop index
static BOOL bRxaLost; // Lost one buffer data
static BOOL bRxbLost; // Lost one buffer data
static BYTE rwIMR; // Use this variable only because the IMR are write only
// variables
static WORD code m_arBaud[]=//ACR.7=0
{
50,
110,
135,
200,
300,
600,
1200,
1050,
2400,
4800,
7200,
9600,
38400,
0
};
// Set Baud rate
BOOL uart_SetBaud(BYTE uPort, WORD uBaud)
{
BYTE i;
BOOL bRes = FALSE;
if(uBaud==19200)
{
ACR = 0xC0;
i = 0x0C;
bRes = TRUE;
}
else
{
ACR = 0x40;
for(i=0; m_arBaud[i]!=0; i++)
{
if(m_arBaud[i]==uBaud)
{
bRes = TRUE;
break;
}
}
}
if(bRes)
{
if(uPort==0)
CSRA = i | i<<4; // make send baud = receive baud
else
CSRB = i | i<<4;
}
return bRes;
}
// inialize
void uart_Init()
{
rxaStart=rxaStop=txaStart=txaStop=0;
rxbStart=rxbStop=txbStart=txbStop=0;
bRxaLost=bRxbLost=FALSE;
CRA = 0x10; // Reset MR pointer.
CRB = 0x10; //
MRA = 0x13; // 8 bit data, no parity
MRB = 0x13; //
MRA = 0x07; // normal, 1 stop bit
MRB = 0x07; //
CSRA = 0xBB; // 9600 baud rate
CSRB = 0xBB; //
ACR = 0x40; // External timer, reset delta brk
OPCR = 0x00; // Output Port normal
SETOP= 0xFF; // Output all zeros
CRA = 0x2A; // Reset Rx, disable Tx & Rx
CRB = 0x2A; //
CRA = 0x3A; // Reset Tx, disable Tx & Rx
CRB = 0x3A; //
CRA = 0x05; // Enable Tx & Rx
CRB = 0x05; //
IMR = 0x22; // Use TxRDYA/B, RxRDYA/B Interrupt
rwIMR= 0x22; // IMR's read/write backup
IT0 = 0; //
EX0 = 1; // INT0 Enable
}
// set data format
void uart_SetFormat(BYTE uPort, WORD uBaud, BYTE uDataLen, BYTE uParity, BYTE uStopLen)
{
BYTE uByte;
// Data bit length
if(uDataLen>8)uDataLen=8;
uByte = uDataLen - 5;
// parity
switch(uParity)
{
case 0: // no parity
uByte |= 0x10;
break;
case 1: // odd parity
uByte |= 0x04;
break;
case 2: // even parity
break;
}
if(uPort==0)// A
{
CRA = 0x10; // reset MR pointer
MRA = uByte;
if(uStopLen==1)
MRA = 0x07;
else if(uStopLen==2)
MRA = 0x0F;
else
MRA = 0x08;
}
else
{
CRB = 0x10; // reset MR pointer
MRB = uByte;
if(uStopLen==1)
MRB = 0x07;
else if(uStopLen==2)
MRB = 0x0F;
else
MRB = 0x08;
}
uart_SetBaud(uPort, uBaud);
}
/*
// get status and reset error status
BYTE uart_GetStatus(BYTE uPort)
{
BYTE uRes;
if(uPort==0)
{
uRes = SRA;
CRA = 0x45; // reset error status
bTxaLost=bRxaLost=FALSE;
return uRes;
}
else
{
uRes = SRB;
CRB = 0x45; // reset error status
bTxbLost=bRxbLost=FALSE;
return uRes;
}
}
*/
void uart_int(void) interrupt 0
{
BYTE uISR;
EX0 = 0;
uISR = ISR;
if(RX_INTA)
{
rxaBuf[rxaStop++] = RHRA;
if(rxaStop >= RXA_BUF_SIZE)rxaStop=0;
if(rxaStop==rxaStart)bRxaLost = TRUE;
}
if(TX_INTA)
{
if(txaStart!=txaStop)
{
THRA = txaBuf[txaStart++];
if(txaStart >= TXA_BUF_SIZE)txaStart=0;
}
else
{
rwIMR &= 0xFE;
IMR = rwIMR;
}
}
if(RX_INTB)
{
rxbBuf[rxbStop++] = RHRB;
if(rxbStop >= RXB_BUF_SIZE)rxbStop=0;
if(rxbStop==rxbStart)bRxbLost = TRUE;
}
if(TX_INTB)
{
if(txbStart!=txbStop)
{
THRB = txbBuf[txbStart++];
if(txbStart >= TXB_BUF_SIZE)txbStart=0;
}
else
{
rwIMR &= 0xEF;
IMR = rwIMR;
}
}
EX0 = 1;
}
/*
*************************************************
* Description: Get one byte from uart *
* Arguments: uPort: (0: uart A,1: uart B) *
pByte: address of returned byte *
* Returns: TRUE: Successful, FALSE: Failed *
*************************************************
*/
BOOL uart_GetByte(BYTE uPort, BYTE *pByte)
{
BOOL bRes = FALSE;
if(uPort==0)
{
if(rxaStart!=rxaStop)
{
*pByte = rxaBuf[rxaStart++];
if(rxaStart >= RXA_BUF_SIZE)rxaStart=0;
bRes = TRUE;
}
}
else
{
if(rxbStart!=rxbStop)
{
*pByte = rxbBuf[rxbStart++];
if(rxbStart >= RXB_BUF_SIZE)rxbStart=0;
bRes = TRUE;
}
}
return bRes;
}
/*
*************************************************
* Description: Send one byte *
* Arguments: uPort: (0: uart A,1: uart B) *
uByte: Byteto been sent *
* Returns: none *
*************************************************
*/
void uart_SendByte(BYTE uPort, BYTE uByte)
{
BYTE uTmp;
if(uPort==0)
{
uTmp = txaStop + 1;
if(uTmp >= TXA_BUF_SIZE)uTmp = 0;
while(uTmp==txaStart); // waiting...
txaBuf[txaStop] = uByte;
txaStop = uTmp;
if(!(rwIMR & 0x01))
{
rwIMR |= 0x01;
IMR = rwIMR;
}
}
else
{
uTmp = txbStop + 1;
if(uTmp >= TXB_BUF_SIZE)uTmp = 0;
while(uTmp==txbStart); // waiting...
txbBuf[txbStop] = uByte;
txbStop = uTmp;
if(!(rwIMR & 0x10))
{
rwIMR |= 0x10;
IMR = rwIMR;
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -