⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 rs485.c

📁 ARM平台上的RS485通信,接受发送都使用中断方式
💻 C
📖 第 1 页 / 共 3 页
字号:
//****************************************************************************************
//** 文件名:Rs485.c

//** 创建人:

//** 日期:2004.12.27

//** 描述:Rs485 drivers
//**
//** 版本:1.0
//**************************************************************************************
//文件主要完成Rs485通信,以及打印机的驱动


//#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <ctype.h>
#include <math.h>
#include "..\inc\44b.h"
#include "..\inc\def.h"
#include "..\inc\rs485.h"
#include "..\inc\file.h"
#include "..\inc\dev.h"
#include "..\inc\commdrv.h"

#define Rs485BaudRate  		115200
#define RS485_Offline		0
#define RS485_Online		1
#define RS485_Wait                  2
#define NULL_SIZE   		3
#define CONF_SIZE   		9
#define DATA_SIZE   		12
#define SET_SIZE    		8
#define Rs485_Buffer_Size           6
#define Rs485_TxBuf_Size	         50
extern setparatype setpara;
extern void	msc_wait(uint16 i);
extern uint8 t100mscount,t1mcount,bagflag;
extern uint8 alarmstate[9],flag_shsbp,flag_Nibp;
extern int8  saveecg[1200],saveple[1200],saverep[1200];
extern int16 saveep,savepp,saverp;
extern uint16 heartrate,sbp,mbp,lastmbp,dbp,cuffpress,spo2,pulse,resp,temp,stval;

extern uint8 flag_print,printalarm_flag,flag_clralapara,printbusy_flag,alarmitem,flag_newnibp;
extern rtctype systime,calender;
extern uint16 printlasttime;

uint8 rtcall=0,flag_rtc=0;
uint8 ID_SIZE;//=((uint8)setpara.netnum)<<4;	
uint8 *Rs485_TxString,Rs485_ReData[95];
uint8 Rs485_TxNum=0;					//重发数据缓冲区
uint8 Rs485_RxByte=0xf0,Rs485_Last=0;			//接收命令存储器
uint8 Rs485_RxPtr[Rs485_Buffer_Size];			//接收字符串缓冲区				
uint8 Rs485_CommData=1;					//命令数据指示器
uint8 Rs485_ReSendTime=0;				//重发次数
uint8 Rs485_State;				//RS485状寄存器
uint8 Rs485_TxbufNum=0, Rs485_RxBufNum=0;               //缓冲区报文数
uint8 stateh=1;						//压缩用
uint8 statel=1;						//压缩用
uint8 d1,n1,n2;
uint8 *BagEnd;
uint8 TapAll[95];
uint8 Rs485_Txbuffer[Rs485_TxBuf_Size][95];	//发送报文缓冲区
uint8 headptr=0,ppptr=0,bbptr=0;		//演示发送指针
uint8 Rs485_Rxflag=0,Rs485_Txflag=0,realnum=0,real=1;//一些位标志
int8 ppp[50],Rs485_Ecg1[12],Rs485_Ecg2[12],Rs485_Ecg3[12],Rs485_Ecg4[12],Rs485_Brea[6],Rs485_Pul[12];//实时情况下数据保存缓冲器
uint16 Rs485_Ecgrp1=0,Rs485_Ecgrp2=0,Rs485_Ecgrp3=0,Rs485_Ecgrp4=0,Rs485_Brearp=0,Rs485_Pulrp=0;//实时发送指针

int8 print_Ecg1[24],print_Ecg2[24],print_Ecg3[24],print_Ecg4[24],print_Brea[24],print_Pul[24];	//打印机发送缓冲器
uint16 print_Ecgrp1=0,print_Ecgrp2=0,print_Ecgrp3=0,print_Ecgrp4=0,print_Brearp=0,print_Pulrp=0,time=10;//打印机处理指针
char print_Txbuffer[30][76];								//打印机发送缓冲区
uint8 print_TxbufNum=0, print_RxBufNum=0;						//打印机发送指针
uint8 printalarmstate=0; 								//
uint8 flag_timeprint=0;
uint8 timeprintcount=0,timecount=0;

//********************************************************************
//函数名:void Rs485_BagAcc(uint8  Bag[])
//输入:uint8  Bag[]
//输出:无
//函数功能:Rs485发送缓冲区添加一个抱文
//全局变量:
//********************************************************************
void Rs485_BagAcc(uint8  Bag[])
{	
	uint8 i,m;
	m=Bag[1]+2;
	for(i=0;i<m;i++)
	{
		Rs485_Txbuffer[Rs485_RxBufNum][i]=Bag[i];
	}
	for(i=m;i<95;i++)
	{
		Rs485_Txbuffer[Rs485_RxBufNum][i]=0;
	}
	Rs485_RxBufNum++;
	if(Rs485_RxBufNum==Rs485_TxBuf_Size) Rs485_RxBufNum=0;
}



//********************************************************************
//函数名:void print_BagAcc(uint8  Bag[])
//输入:uint8  Bag[]
//输出:无
//函数功能:打印机发送缓冲区添加一个抱文
//全局变量:
//********************************************************************
void print_BagAcc(char  Bag[])
{	
	uint8 i,m;
	m=Bag[1]+2;
	for(i=0;i<m;i++)
	{
		print_Txbuffer[print_RxBufNum][i]=Bag[i];
	}
	for(i=m;i<75;i++)
	{
		print_Txbuffer[print_RxBufNum][i]=0;
	}
	print_RxBufNum++;
	if(print_RxBufNum==30) print_RxBufNum=0;
}






//************************* Rs485--RS485 **************************

//*****************************************************************
//函数名:Rs485_RxInt(void)
//输入:无
//输出:无
//函数功能:串口读中断函数
//全局变量:
//******************************************************************
void __irq Rs485_RxInt(void)
{
	CLI();
	Rs485_Rxflag=0;
	if(Rs485_CommData==1)
	{
	Rs485_RxByte= RdURXH1();
	if((Rs485_RxByte==0x15||Rs485_RxByte==0x19)&&Rs485_RxByte==rtcall)
		{flag_rtc=1;rtcall=0;}
	else rtcall=Rs485_RxByte;
	}

	if(Rs485_State==RS485_Offline)
		{
			Rs485_Reset();
		}
	else	
		{	
		 if(!(Rs485_RxByte==0x15||Rs485_RxByte==0x19)||flag_rtc==1)
			Rs485_WaitComm();
		}
	rI_ISPC=BIT_URXD1 ;   //clear pending bits,Default value=0x0000000
		STI();
}




//********************************************************************
//函数名:void __irq Rs485_TxInt(void)
//输入:
//输出:无
//函数功能:串口中断发送程序
//全局变量:NULL
//********************************************************************
void __irq Rs485_TxInt(void)
{
	CLI();
	Rs485_Txflag=0;
	if(Rs485_TxNum!=0)
    {	
	Rs485_TxNum--;
	WrUTXH1(*Rs485_TxString++);
	rI_ISPC=BIT_UTXD1;
    }
    else
    {	
	rINTMSK|=BIT_UTXD1;
	msc_wait(1500);	
	Rs485_SendToRec();
	Rs485_CommState();
	rI_ISPC=BIT_UTXD1;
    }	
	STI();
}




//--------------------------------------------------------------//
//                  Init and Enable  Rs485                      //
//-------------------------------------------------------------//
//**************************************************************
//函数名:void Rs485_Init(int32 Rs485_baud)
//输入:int32 Rs485_baud
//输出:无
//功能描述:Rs485初始化
//全局变量:
//**************************************************************
void Rs485_Init(int32 Rs485_baud)
{
	int32 i;
	rUFCON1=0;		//disable FIFO
  	rUMCON1=0;		//disable MODEM
  	rULCON1=3;		//8位数据位、1位停止位
	rUCON1=0x245;	//rx/tx=edge,disable timeout int.,enable rx error int.,normal,interrupt or polling
	rUBRDIV1=((int32)(MCLK/16.0/Rs485_baud+0.5)-1);
  	rPCONC|=0x0ff00000;	//串口1的发送口是PC12,串口1的接收口是PC13
  	rPUPC|=0x3400;	
	rINTMSK&=~BIT_URXD1;	
	rINTMSK|=BIT_UTXD1;
//	rINTMSK|=BIT_UERR01;
	rI_ISPC=BIT_UTXD1;
  	SetIntr(&pISR_URXD1,Rs485_RxInt,BIT_URXD1);
	SetIntr(&pISR_UTXD1,Rs485_TxInt,BIT_UTXD1);	
	Rs485_TxNum=0;
	Rs485_Ecgrp1=0;
	ID_SIZE=((uint8)setpara.netnum)<<4;
	Rs485_State=RS485_Online;
	Rs485_SendToRec();
	Rs485_CommState();		//串口处于命令接收状态
	for(i=0;i<100;i++);
}


//*****************************************************************
//** 函数名:void Rs485_SendByte(uint8U ucUart_Ch,uint8 ucData)
//** 输 入:
//**       uint8U ucData:需要输出的数据.
//** 输 出: Null
//** 功能描述:由Rs485中输出数据.
//** 全局变量:Null
//*****************************************************************
void Rs485_SendByte(uint8 data)
{ 
    while(!(rUTRSTAT1 & 0x2));  //Wait until THR is empty.
    rUTXH1=data;
}


//*****************************************************************
//** 函数名:void Rs485_SendString(uuint8 *pcTemp,uint8 m)
//** 输 入:
//**       uint8U *pucData:需要输出的字符串.uint8 m  字符串长度
//** 输 出: Null
//** 功能描述:发送一个字符串
//** 全局变量:Null
//*****************************************************************
void Rs485_SendString(uint8 *pcTemp,uint8 m)
{	
	if(m!=0)
	{
		 m+=2;
	}
	while(m--)
		{Rs485_SendByte(*pcTemp++);}
}

//*****************************************************************
//** 函数名:void Rs485_CommState(void)   
//** 输 入:
//**        Null
//** 输 出: Null
//** 功能描述:置Rs485为接发命令状态
//** 全局变量:Null
//*****************************************************************

void Rs485_CommState(void)
{	
	rULCON1|=0x38; 		//RS485处于接收命令状态
	Rs485_CommData=1;
}


//*****************************************************************
//** 函数名:void Rs485_DataState(void)   
//** 输 入:
//**        Null
//** 输 出: Null
//** 功能描述:置Rs485为接收数据状态
//** 全局变量:Null
//*****************************************************************

void Rs485_DataState(void)
{
	rULCON1&=0x37;		//RS485处于接收数据状态
	Rs485_CommData=0;
}


//*****************************************************************
//** 函数名:void RS485_SendOneBag(void)   
//** 输 入:NULL
//**        
//** 输 出:NULL
//** 功能描述:发送一个数据报文
//** 全局变量:
//*****************************************************************
void Rs485_SendOneBag(void)
{	
	uint8 j;
	for(j=0;j<Rs485_Txbuffer[Rs485_TxbufNum][1]+2;j++)
		{
		Rs485_ReData[j]=Rs485_Txbuffer[Rs485_TxbufNum][j];
		}

	Rs485_TxString=Rs485_ReData;
	Rs485_TxNum=Rs485_ReData[1]+2;
	while(!(rUTRSTAT1 & 0x4));
	rINTMSK &= ~BIT_UTXD1;
	Rs485_Txbuffer[Rs485_TxbufNum][0]=0;
	Rs485_TxbufNum++;
	if(Rs485_TxbufNum==Rs485_TxBuf_Size)  Rs485_TxbufNum=0;
	Rs485_ReSendTime=0;
}




//*************************************************************
//函数名:void Rs485_Rtc(void)
//输入:NULL
//输出:NULL
//功能描述:校正时间
//全局变量:实时时间寄存器
//*************************************************************
void Rs485_Rtc(void)
{
	rtctype rtcclear;
	ReadRtc(&rtcclear);
	if(rtcclear.min<30) rtcclear.min=0;
	else 
	{
	      rtcclear.min=0;
	      rtcclear.hour++;
	      if(rtcclear.hour>23) 
              {
		rtcclear.hour=0;
            	rtcclear.day++;
            	if(rtcclear.day>GetDaynum(rtcclear.year,rtcclear.mon))
            	{
              		rtcclear.day=1;
              		rtcclear.mon++;
              		if(rtcclear.mon>12)
              		{
              			rtcclear.mon=1;
              			rtcclear.year++;
              			if(rtcclear.year>2099) rtcclear.year=2000;
			}
		 }
		}
	}
	WriteRtc(&rtcclear);
}



//****************************************************************
//函数名:void Rs485_Reset(void)
//输入:NULL
//输出:NULL
//功能描述:Rs485通信复位
//全局变量:Rs485_State
//*****************************************************************
void Rs485_Reset(void)
{
	Rs485_State=RS485_Online;
	Rs485_SendToRec();
	Rs485_CommState();
}






//***************************************************************
//函数名:void Rs485_ReStart(void)
//输入:无
//输出:无
//功能描述:报文发送失败重发一次
//全局变量:*Rs485_ReData
//*******************************************************************
void Rs485_ReStart(void)
{
	if(Rs485_ReSendTime%2==0)
	{
		Rs485_ReSendTime++;
		Rs485_TxString=Rs485_ReData;
		Rs485_TxNum=Rs485_ReData[1]+2;
		while(!(rUTRSTAT1 & 0x4));		
		rINTMSK &= ~BIT_UTXD1;
	}
}



//*****************************************************************
//** 函数名:void RS485_SendComm(uint8 n)   
//** 输 入:uint8 n
//**        
//** 输 出: Null
//** 功能描述:返回命令,与中央台握手
//** 全局变量:Null
//*****************************************************************
void Rs485_SendComm(uint8 num)
{
	Rs485_SendByte(num);
}








//***************************************************************
//函数名:uint8 Rs485_DataAccr(uint8 data,uint8 m)
//输入:uint8 data 压入的数据   uint8 m  压入的位置
//输出:uint8 m
//功能描述:波纹数据压缩数据的填入,半字节
//全局变量:
//***************************************************************
uint8 Rs485_DataAccr(uint8 data,uint8 m)
{
		if(statel)
			{
				if(stateh)
				{
					m++;
					TapAll[m]=data&0x0f;
					stateh=0;
				}
				else {TapAll[m]+=(data&0x0f)<<4;stateh=1;}
			}
		else {TapAll[m]=data&0xf;statel=1;}
		return m;
}






//***************************************************************
//函数名:void Rs485_Dec(int8 data1,int8 data2)
//输入:uint8 data1 data2
//输出:
//功能描述:两数相减
//全局变量:d1,n1,n2
//***************************************************************
void Rs485_Dec(int8 data1,int8 data2)
{
	int8 temp;
	temp=data2-data1;
	if(temp>=-6&&temp<=6)	d1=temp+7;
	else if(temp>=-22&&temp<=-7) {d1=14;n1=-(temp+7);}
	else if(temp>=7&&temp<=22)   {d1=15;n1=temp-7;}
	else {d1=0;n1=temp&0x0f;n2=(temp>>4)&0x0f;}
}


//***************************************************************
//函数名:uint8 Rs485_DataAdd(uint8 num)
//输入:uint8 num 压入位置
//输出:uint8 num
//功能描述:波纹数据压缩数据的填入,一个数据对应的数据
//全局变量:
//***************************************************************
uint8 Rs485_DataAdd(uint8 num)
{

	if(d1>0&&d1<=13) {num=Rs485_DataAccr(d1,num);}
	if(d1==14||d1==15) {num=Rs485_DataAccr(d1,num);num=Rs485_DataAccr(n1,num);}
	if(d1==0) {num=Rs485_DataAccr(d1,num);num=Rs485_DataAccr(n1,num);num=Rs485_DataAccr(n2,num);}
	return (num);	
}





//***************************************************************
//函数名:uint8 TapHeart(uint8 num)
//输入:uint8 num 抱文序号
//输出:uint8 num
//功能描述:心电数据打包(demo数据)
//全局变量:
//***************************************************************
uint8 TapHeart(uint8 num)
{
	uint8 *head1,*head2,*head3,*head4;
	uint8 i,j,m;
	uint8 buf2[4],tt[4];
	head1=(uint8 *)(0xc000000+0x3f000);
	head2=(uint8 *)(0xc000000+0x3f000+90);
	head3=(uint8 *)(0xc000000+0x3f000+180);
	head4=(uint8 *)(0xc000000+0x3f000+270);
	TapAll[3]=*(head1+headptr);tt[0]=*(head1+headptr);
	TapAll[4]=*(head2+headptr);tt[1]=*(head2+headptr);
	TapAll[5]=*(head3+headptr);tt[2]=*(head3+headptr);
	TapAll[6]=*(head4+headptr);tt[3]=*(head4+headptr);
	headptr++;
	if(headptr==90) headptr=0;
	m=6;
	for(i=1;i<12;i++)
	{

		buf2[0]=*(head1+headptr);
		buf2[1]=*(head2+headptr);
		buf2[2]=*(head3+headptr);
		buf2[3]=*(head4+headptr);
		headptr++;
		if(headptr==90) headptr=0;
		for(j=0;j<4;j++)
		{
			Rs485_Dec(tt[j],buf2[j]);
			m=Rs485_DataAdd(m);
			tt[j]=buf2[j];		
		}
	}
	return (m);
}

//***************************************************************
//函数名:uint8 TapBrea(uint8 tnum,uint8 num)
//输入:uint8 num   uint8 tnum
//输出:uint8 num
//功能描述:呼吸波数据打包(demo数据)
//全局变量:
//***************************************************************
uint8 TapBrea(uint8 tnum,uint8 num)
{
	int8 *head;
	uint8 i,m;
	int8 buf2,tt;
	head=(int8 *)(0xc000000+0x3f000+450);
	m=num;
	if(bbptr==180) bbptr=0;
	tt=(*(head+bbptr))/4;
	bbptr++;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -