#ifndef COM_C
#define COM_C
#include "com.h"
#include "union.h"
#if !defined(_WIN32)
void BaudRate(int comPort, int baud)
{
unsigned int comBase = comPort==COM1 ? COM1_BASE_ADRR : COM2_BASE_ADRR;
outportb(comBase+COM_LCR, DLAB); // DLAB=1
outpw(comBase+COM_LSB, baud);
}
void DataFormat(int comPort, unsigned char format)
{
unsigned int comBase = comPort==COM1 ? COM1_BASE_ADRR : COM2_BASE_ADRR;
outportb(comBase+COM_LCR, (~DLAB)&format); // DLAB=0
}
void InterruptType(int comPort, unsigned char intType)
{
unsigned int comBase = comPort==COM1 ? COM1_BASE_ADRR : COM2_BASE_ADRR;
outportb(comBase+COM_MCR, 0x0b); // OUT2=RTS=DTR=0, needed
outportb(comBase+COM_IER, intType);
}
void interrupt ( *MountISR(int comPort, void interrupt (*pNew)(void)) )
{
void interrupt (*pOld)(void);
int intNo = comPort==0 ? COM1_INT_NO : COM2_INT_NO;
pOld = getvect(intNo);
setvect(intNo, pNew);
return pOld;
}
void COM1RX(unsigned char c)
{
static int idx = 0;
Sendunion.Sendstring[idx++] = c;
com1Rx_len++;
if(idx==58)
{
if(CRC16(Sendunion.Sendstring,56)==Sendunion.s1.CheckValue)
{
ReceiveDone=1;
com1Count ++;
idx=0 ;
}
}
}
void COM2RX(unsigned char c)
{
c=c;
}
static int com1TXLen, com1TXIdx, com2TXLen, com2TXIdx;
static unsigned char *pcom1TXBuf, *pcom2TXBuf;
int com1TX=0, com2TX=0, com1RX=0, com2RX=0, com1TXBusy=0, com2TXBusy=0;
void interrupt COM1ISR(void)
{
unsigned char intType;
intType = inport(COM1_BASE_ADRR+COM_IIR);
next_com1:
if(intType&INT_SCR_TX) //transmit interrupt ISR
{
if(com1TXIdx {
com1TX ++;
WriteCOM1(pcom1TXBuf[com1TXIdx++]);
}
else
com1TXBusy = 0;
}
if(intType&INT_SCR_RX) //receive interrupt ISR
{
com1RX ++;
COM1RX(ReadCOM1());
}
intType = inport(COM1_BASE_ADRR+COM_IIR);
if(!(intType&INT_SCR_NO))
goto next_com1;
outportb(0x20,0x20);
}
void interrupt COM2ISR(void)
{
unsigned char intType, c;
intType = inport(COM2_BASE_ADRR+COM_IIR);
next_com2:
if(intType&INT_SCR_TX) //transmit interrupt ISR
{
if(com2TXIdx {
com2TX ++;
WriteCOM2(pcom2TXBuf[com2TXIdx++]);
}
else
com2TXBusy = 0;
}
if(intType&INT_SCR_RX) //receive interrupt ISR
{
com2RX ++;
COM2RX(ReadCOM2());
}
intType = inport(COM2_BASE_ADRR+COM_IIR);
if(!(intType&INT_SCR_NO))
goto next_com2;
outportb(0x20,0x20);
}
void OpenCOM(int comPort, int baud, unsigned char format, unsigned char intType)
{
unsigned char oldIntMask = inportb(0x21);
disable();
BaudRate(comPort, baud);
DataFormat(comPort, format);
InterruptType(comPort, intType);
if(comPort==COM1)
{
MountISR(COM1, COM1ISR);
outportb(0x21, oldIntMask&~COM1_INT_MASK);
}
else
{
MountISR(COM2, COM2ISR);
outportb(0x21, oldIntMask&~COM2_INT_MASK);
}
enable();
}
void CloseCOM(int comPort)
{
unsigned int comBase = comPort==COM1 ? COM1_BASE_ADRR : COM2_BASE_ADRR;
unsigned char oldIntMask = inportb(0x21);
disable();
outportb(0x21, oldIntMask|(comPort==COM1 ? COM1_INT_MASK : COM2_INT_MASK));
outportb(comBase+COM_MCR, 0x00);
outportb(comBase+COM_IER, 0X00);
enable();
}
void StartSend(int comPort, unsigned char comTXBuf[], int lenBuf)
{
if(comPort==COM1)
{
com1TXIdx = 0;
com1TXLen = lenBuf;
pcom1TXBuf = comTXBuf;
if( com1TXIdx {
com1TX ++;
WriteCOM1(pcom1TXBuf[com1TXIdx++]);
com1TXBusy = 1;
}
}
else
{
com2TXIdx = 0;
com2TXLen = lenBuf;
pcom2TXBuf = comTXBuf;
if( com2TXIdx {
com2TX ++;
WriteCOM2(pcom2TXBuf[com2TXIdx++]);
com2TXBusy = 1;
}
}
}
#endif /* _WIN32 */
char* i2s(short int i, char s[])
{
char *p = (char*)&i;
#if EX_INV==1
s[0] = p[1]; s[1] = p[0];
#else
s[0] = p[0]; s[1] = p[1];
#endif
return s;
}
char* l2s(long l, char s[])
{
char *p = (char*)&l;
#if EX_INV==1
s[0] = p[3]; s[1] = p[2]; s[2] = p[1]; s[3] = p[0];
#else
s[0] = p[0]; s[1] = p[1]; s[2] = p[2]; s[3] = p[3];
#endif
return s;
}
char* f2s(float f, char s[])
{
char *p = (char*)&f;
#if EX_INV==1
s[0] = p[3]; s[1] = p[2]; s[2] = p[1]; s[3] = p[0];
#else
s[0] = p[0]; s[1] = p[1]; s[2] = p[2]; s[3] = p[3];
#endif
return s;
}
char* d2s(double d, char s[])
{
char *p = (char*)&d;
#if EX_INV==1
s[0] = p[7]; s[1] = p[6]; s[2] = p[5]; s[3] = p[4];
s[4] = p[3]; s[5] = p[2]; s[6] = p[1]; s[7] = p[0];
#else
s[0] = p[0]; s[1] = p[1]; s[2] = p[2]; s[3] = p[3];
s[4] = p[4]; s[5] = p[5]; s[6] = p[6]; s[7] = p[7];
#endif
return s;
}
short int s2i(char s[])
{
union{
short int i;
char c[2];
} u;
#if EX_INV==1
u.c[0] = s[1]; u.c[1] = s[0];
#else
u.c[0] = s[0]; u.c[1] = s[1];
#endif
return u.i;
}
long s2l(char s[])
{
union{
long l;
char c[4];
} u;
#if EX_INV==1
u.c[0] = s[3]; u.c[1] = s[2]; u.c[2] = s[1]; u.c[3] = s[0];
#else
u.c[0] = s[0]; u.c[1] = s[1]; u.c[2] = s[2]; u.c[3] = s[3];
#endif
return u.l;
}
float s2f(char s[])
{
union{
float f;
char c[4];
} u;
#if EX_INV==1
u.c[0] = s[3]; u.c[1] = s[2]; u.c[2] = s[1]; u.c[3] = s[0];
#else
u.c[0] = s[0]; u.c[1] = s[1]; u.c[2] = s[2]; u.c[3] = s[3];
#endif
return u.f;
}
double s2d(char s[])
{
union{
double d;
char c[8];
} u;
#if EX_INV==1
u.c[0] = s[7]; u.c[1] = s[6]; u.c[2] = s[5]; u.c[3] = s[4];
u.c[4] = s[3]; u.c[5] = s[2]; u.c[6] = s[1]; u.c[7] = s[0];
#else
u.c[0] = s[0]; u.c[1] = s[1]; u.c[2] = s[2]; u.c[3] = s[3];
u.c[4] = s[4]; u.c[5] = s[5]; u.c[6] = s[6]; u.c[7] = s[7];
#endif
return u.d;
}
unsigned char CheckSum(unsigned char data[], int length)
{
int i;
unsigned char sum=0;
for(i=0; i sum += data[i];
return sum;
}
unsigned int CheckSum1(unsigned char data[], int length, unsigned char sum)
{
return (CheckSum(data, length)==sum);
}
static unsigned short crc16_reverse_byte(unsigned char byte, unsigned short accum)
{
unsigned short genpoly = 0xA001;
unsigned short data = 0x0000;
int i;
data = data|byte;
for(i=0; i {
if((data^accum)&0x0001)
accum=(accum>>1)^genpoly;
else
accum>>=1;
data>>=1;
}
return accum;
}
unsigned short CRC16(unsigned char *frame, int frameLen)
{
unsigned short accum=0x0000;
int i;
for(i=0; i accum = crc16_reverse_byte(*(frame+i), accum);
return accum;
}
char* str2frm(char *str, char *frm, int len)
{
char c;
int i;
unsigned short crc;
frm[0]=0x01;
for(i=0; i {
c = str[i];
frm[i*2+1] = (c&0x0f)|0x30;
frm[i*2+2] = (c>>4)|0x30;
}
crc = CRC16(str, len);
c = (char)(crc%256);
frm[i*2+1] = (c&0x0f)|0x30;
frm[i*2+2] = (c>>4)|0x30;
c = (char)(crc>>8);
frm[i*2+3] = (c&0x0f)|0x30;
frm[i*2+4] = (c>>4)|0x30;
frm[i*2+5] = 0x04;
frm[i*2+6] = 0x00;
return frm;
}
char* frm2str(char *frm, char *str, int len)
{
int i;
for(i=0; i str[i] = (frm[i*2+1]&0x0f) | ((frm[i*2+2] str[i] = 0x00;
return str;
}
#endif /* COM_C */