#include "rs485_read_data.h"
|
#include "rs485_data_analysis_pro.h"
|
#include "tim.h"
|
#include "billing.h"
|
#include "gpio.h"
|
#include "uart.h"
|
#include "linked_list.h"
|
|
/****ÕûÌå¿ØÖÆË¼Â·******************
|
*RS485ÕûÌå¿ØÖÆ·ÖΪÉϵ硢·¢ËͶÁȡָÁî¡¢µÈ´ý½ÓÊÕÊý¾Ý²¢´¦ÀíÈý¸ö״̬»ú²½Ö裻¿ÉÒÔʵÏֵȴý³¬Ê±ÅжϺͶà´ÎÖØ¶Á¡£
|
*Õë¶ÔmodbusµØÖ··ÖµÄ±È½Ï¿ª£¬²»ÄÜÒ»´ÎÐÔ¶ÁÈ¡µÄÇé¿ö£¬·ÖRS485_MODBUS_STEP_STATUS_T¶ÁÈ¡£¬ÊÂÏÈÅäÖÃ×îºóÒ»¸öSTEP£¬ËùÓÐÐͺŵĵÚÒ»¸ö²½Öè¶¼ÊÇSTEP1£¬
|
*µ±³É¹¦¶Áȡһ´ÎÖ¸ÁîÖ®ºó£¬Åжϵ±Ç°STEPÊÇ·ñ´óÓÚµÈÓÚ×îºóÒ»¸öSTEP£¬ÊÇÔò±íʾȫ²¿¶ÁÈ¡Íê³É£¬·ñ´ú±íÐèÒª¼ÌÐø·¢ËÍÏÂÒ»¸öSTEPµÄ¶ÁȡָÁ
|
*
|
**********************************/
|
|
|
__IO RS485_COM_CTRL_PARA_T rs485_com_ctrl_pata_g={
|
.status = RS485_COM_IDLE, \
|
.reread_num_cnt =0, \
|
};
|
|
RS485_COM_UART_PARA_T rs485_com_uart_data_g ={
|
.recv_flag = RESET, \
|
};
|
|
|
|
void RS485_read_data_GPIO_Init(void)
|
{
|
InputtIO(RS485_SYNC_PORT,RS485_SYNC_PIN,IN_NORMAL);
|
OutputIO(RS485_PWR_PORT,RS485_PWR_PIN,OUT_PUSHPULL);
|
OutputIO(RS485_RE_PORT,RS485_RE_PIN,OUT_PUSHPULL);
|
OutputIO(PWR_OUTPUT1_PORT,PWR_OUTPUT1_PIN,OUT_PUSHPULL);
|
OutputIO(PWR_OUTPUT2_PORT,PWR_OUTPUT2_PIN,OUT_PUSHPULL);
|
OutputIO(PWR_BOOST_EN_PORT,PWR_BOOST_EN_PIN,OUT_PUSHPULL);
|
OutputIO(PWR_OUTPUT_9V_PORT,PWR_OUTPUT_9V_PIN,OUT_PUSHPULL);
|
OutputIO(PWR_OUTPUT_12V_PORT,PWR_OUTPUT_12V_PIN,OUT_PUSHPULL);
|
|
RS485_PWR_OFF;
|
RS485_RE_REC_ENABLE;
|
PWR_OUTPUT1_OFF;
|
PWR_OUTPUT2_OFF;
|
PWR_BOOST_DIABLE;
|
PWR_OUTPUT_9V_OFF;
|
PWR_OUTPUT_12V_OFF;
|
}
|
|
void RS485_UART_GPIO_Init(void)
|
{
|
CMU_PERCLK_SetableEx(PADCLK, ENABLE); //PADʱÖÓ£¨GPIO£©Ê¹Äܺ¯Êý
|
CMU_PERCLK_SetableEx(UART1CLK,ENABLE);
|
CMU_PERCLK_SetableEx(DMACLK, ENABLE);
|
AltFunIO(RS485_READ_DATA_TX_PORT, RS485_READ_DATA_TX_PIN, ALTFUN_NORMAL);
|
AltFunIO(RS485_READ_DATA_RX_PORT, RS485_READ_DATA_RX_PIN, ALTFUN_NORMAL);
|
|
}
|
|
void RS485_UART_GPIO_sleep(void)
|
{
|
CMU_PERCLK_SetableEx(UART1CLK,DISABLE);
|
CloseIO(RS485_READ_DATA_TX_PORT, RS485_READ_DATA_TX_PIN);
|
CloseIO(RS485_READ_DATA_RX_PORT, RS485_READ_DATA_RX_PIN);
|
}
|
|
|
void RS485_read_data_RX_DMA_check(void)
|
{
|
uint16_t timeout_cnt = 0,dma_recv_cnt;
|
uint32_t dma_mar_reg_read = DMA_CHxMAR_Read(DMA_CH3);
|
|
if(dma_mar_reg_read != (uint32)RS485_read_data_recv_buff){
|
delay_ms(2);
|
while(dma_mar_reg_read != DMA_CHxMAR_Read(DMA_CH3)){
|
dma_mar_reg_read = DMA_CHxMAR_Read(DMA_CH3);
|
delay_ms(2);
|
if(timeout_cnt++ > 100)
|
break;
|
}
|
}
|
else
|
return ;
|
|
dma_recv_cnt = dma_mar_reg_read - (uint32)RS485_read_data_recv_buff;
|
if(dma_recv_cnt)
|
{
|
rs485_com_uart_data_g.recv_length = dma_recv_cnt;
|
arrayA_2_arrayB(RS485_read_data_recv_buff , rs485_com_uart_data_g.recv_buf, dma_recv_cnt, LITTLE_ENDIAN) ;
|
rs485_com_uart_data_g.recv_flag = SET;//½ÓÊÕÍê³É
|
}
|
|
}
|
|
|
|
|
|
//¸ù¾ÝÉ豸´úÂë´¦Àí£¬²¢·µ»Ø¹©µçÑÓʱʱ¼äÕûÊýÃë
|
uint8_t rs485GetDelayTime(uint16_t device_code)
|
{
|
//ÓÉÓÚ±¾Éí¹¤×÷ÖÜÆÚÊÇ1ÃëÒ»´Î£¬ËùÒÔÑÓʱµÄ²½½øÊÇ1000ms£¬ ±ÈÈçÊýÖµÔÚ0-1000msÖ®¼ä£¬Êµ¼ÊÑÓʱ¶¼Îª1Ãë×óÓÒ£¬ ÊýÖµÔÚ1000-2000msÖ®¼ä£¬Êµ¼ÊÑÓʱ¶¼Îª2Ãë×óÓÒ
|
switch (device_code){
|
case SIZHUMODBUS1: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP1; return 1;
|
case SIZHUMODBUS2: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP1; return 1;
|
case SIZHUMODBUS3: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP1;return 1;
|
case SIZHUMODBUSV2_0: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP1;return 1;
|
case TIANXINCUSTOM: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP1;return 1;
|
case TIANXINMODBUS: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP1;return 1;
|
|
case EKMODBUS: rs485_com_ctrl_pata_g.modbus_last_status = MODBUS_STEP3;return 1;
|
//?ÐèÒª²¹³ä......
|
default:return 100;
|
}
|
}
|
|
//¸ù¾ÝÉ豸´úÂë·¢ËͶÁȡ֡
|
void rs485SendReadData(uint16_t device_code,uint8_t slaveAddress)
|
{
|
switch (device_code){
|
case SIZHUMODBUS1: break;
|
case SIZHUMODBUS2: break;
|
case SIZHUMODBUS3: break;
|
case SIZHUMODBUSV2_0: sendModbusReadFrame(slaveAddress,501,49);break;
|
case TIANXINCUSTOM: break;
|
case TIANXINMODBUS: break;
|
|
case EKMODBUS:
|
if(rs485_com_ctrl_pata_g.modbus_step_status ==MODBUS_STEP1)
|
sendModbusReadFrame(slaveAddress,100,4);
|
else if(rs485_com_ctrl_pata_g.modbus_step_status ==MODBUS_STEP2)
|
sendModbusReadFrame(slaveAddress,306,4);
|
else if(rs485_com_ctrl_pata_g.modbus_step_status ==MODBUS_STEP3)
|
sendModbusReadFrame(slaveAddress,326,4);
|
break;
|
//?ÐèÒª²¹³ä......
|
default:break;
|
}
|
}
|
|
|
RS485_COM_STATUS_T rs485ComPwrOnHandle(void)
|
{
|
uint8_t delay_time_s;
|
uint8_t RS485_sync_status =0;
|
uint8_t count_i = 0;
|
|
//jIO¿Ú³õʼ»¯
|
RS485_read_data_GPIO_Init();
|
|
RS485_sync_status = RS485_SYNC_IO_READ;
|
while(RS485_sync_status){
|
count_i ++;
|
delay_ms(10);
|
RS485_sync_status = RS485_SYNC_IO_READ;
|
if(count_i > 10)
|
break;
|
}
|
if(RS485_sync_status)
|
return RS485_COM_IDLE;
|
|
//´ò¿ª¹©µç
|
if(flow_meter_para_g.output_voltage_code == RS485_V1_5V){
|
PWR_OUTPUT1_ON;
|
PWR_OUTPUT2_OFF;
|
delay_ms(1);
|
PWR_OUTPUT_9V_OFF;
|
PWR_OUTPUT_12V_OFF;
|
}else if(flow_meter_para_g.output_voltage_code == RS485_V1_9V){
|
PWR_OUTPUT1_ON;
|
PWR_OUTPUT2_OFF;
|
delay_ms(1);
|
PWR_OUTPUT_9V_ON;
|
PWR_OUTPUT_12V_OFF;
|
}else if(flow_meter_para_g.output_voltage_code == RS485_V1_12V){
|
PWR_OUTPUT1_ON;
|
PWR_OUTPUT2_OFF;
|
delay_ms(1);
|
PWR_OUTPUT_9V_OFF;
|
PWR_OUTPUT_12V_ON;
|
}else if(flow_meter_para_g.output_voltage_code == RS485_V2_5V){
|
PWR_OUTPUT1_OFF;
|
PWR_OUTPUT2_ON;
|
delay_ms(1);
|
PWR_OUTPUT_9V_OFF;
|
PWR_OUTPUT_12V_OFF;
|
}
|
delay_ms(1);
|
PWR_BOOST_ENABLE;
|
|
//´ò¿ª¶¨Ê±Æ÷Öжϣ¬²»Í¬É豸¹©µçÑÓʱ²»µÈ£¬Òª²»Òª¿¼Âǹ©µçºó¿ÉÒÔÁ¢Âí¶ÁÈ¡µÄÇé¿ö£¿
|
delay_time_s = rs485GetDelayTime(flow_meter_para_g.flow_meter_code);
|
rs485_com_ctrl_pata_g.pwr_delay_status = RESET;
|
rs485_com_ctrl_pata_g.pwr_delay_time_out_cnt = 0;
|
|
//²ÎÊý״̬ÖÃλ
|
rs485_com_ctrl_pata_g.reread_num_cnt = RS485_REREAD_NUM;
|
rs485_com_ctrl_pata_g.reread_wait_time_cnt = RS485_REREAD_WATI_TIME;
|
|
rs485_com_ctrl_pata_g.pwr_delay_time_out_cnt = delay_time_s;
|
|
rs485_com_ctrl_pata_g.modbus_step_status = MODBUS_STEP1;
|
|
return RS485_COM_SEND;
|
|
}
|
|
|
RS485_COM_STATUS_T rs485ComSendHandle(void)
|
{
|
uint32_t BaudRate;
|
UART_ParityBitTypeDef ParityBit;
|
UART_StopBitTypeDef StopBit;
|
|
//ÑÓʱÏÈ--£¬ Èç¹ûÑÓʱ1Ã룬ÏÈ--¾ÍµÈÓÚ0ÁË£¬ ÔÙÅжÏ==0¾Í¿ÉÒÔ¶ÁÈ¡Êý¾Ý¡£ÒòΪÉϵ絽·¢ËÍÊý¾Ý°´×´Ì¬»úÖ´ÐУ¬±¾Éí¾Í²îÁËÒ»¸öÑ»·ÖÜÆÚµÄʱ¼ä£¨ÖÜÆÚ1Ã룩
|
if(rs485_com_ctrl_pata_g.pwr_delay_time_out_cnt){
|
rs485_com_ctrl_pata_g.pwr_delay_time_out_cnt--;
|
}
|
|
if(rs485_com_ctrl_pata_g.pwr_delay_time_out_cnt == 0) //ÑÓʱµ½0¾Í¿ÉÒÔ·¢ËͶÁȡָÁî
|
{
|
//´®¿ÚÅäÖÃ
|
RS485_UART_GPIO_Init();
|
switch(flow_meter_para_g.baudrate_code ){
|
case BAUDRATE_1200:BaudRate = 1200; break;
|
case BAUDRATE_2400:BaudRate = 2400; break;
|
case BAUDRATE_4800:BaudRate = 4800; break;
|
case BAUDRATE_9600:BaudRate = 9600; break;
|
case BAUDRATE_19200:BaudRate = 19200; break;
|
case BAUDRATE_56000:BaudRate = 56000; break;
|
case BAUDRATE_57600:BaudRate = 57600; break;
|
case BAUDRATE_115200:BaudRate = 115200; break;
|
default:BaudRate = 9600; break;
|
}
|
switch(flow_meter_para_g.parity_bit ){
|
case PARITY_NONE:ParityBit = NONE; break;
|
case PARITY_ODD:ParityBit = ODD; break;
|
case PARITY_EVEN:ParityBit = EVEN; break;
|
default:ParityBit = NONE; break;
|
}
|
|
RS485_read_data_uart_Init(BaudRate,ParityBit,OneBit);
|
RS485_read_data_RX_DMA_CH3_Init();
|
|
RS485_PWR_ON;
|
delay_us(10);
|
rs485SendReadData(flow_meter_para_g.flow_meter_code,flow_meter_para_g.slave_address);
|
rs485_com_ctrl_pata_g.reread_wait_time_cnt = RS485_REREAD_WATI_TIME; //ÖØÖõȴýÏìӦʱ¼ä
|
return RS485_COM_WAIT_ANSWER;
|
}
|
}
|
|
|
#define RS485_READ_ERR_ALARM_TIMES 2 //Á¬ÐøRS485_READ_ERR_ALARM_TIMES´Îʧ°Ü±¨¾¯RS485Òì³£
|
RS485_COM_STATUS_T rs485ComWaitAnswerHandle(void)
|
{
|
static uint8_t RS485_err_cnt =0 ; //¶Áȡʧ°Ü¼ÆÊý
|
|
ErrorStatus read_ok = FAIL;
|
//¼ì²é´®¿ÚÊý¾Ý
|
RS485_read_data_RX_DMA_check();
|
|
//·ÖÎöÊý¾Ý,Èç¹û³É¹¦¶Áµ½Êý¾Ýread_ok = PASS
|
if(rs485_com_uart_data_g.recv_flag == SET){
|
rs485_com_uart_data_g.recv_flag =RESET;
|
|
read_ok = rs485ComDataAnalysis(rs485_com_uart_data_g,SIZHUMODBUSV2_0,1,rs485_com_ctrl_pata_g ) ;//?É豸´úÂë¡¢´Ó»úµØÖ·Èë²ÎÒª¸Ä
|
}
|
|
if(read_ok==PASS){
|
if(rs485_com_ctrl_pata_g.modbus_step_status >= rs485_com_ctrl_pata_g.modbus_last_status) {
|
//?´ú±íͨѶȫ²¿³É¹¦£¬½øÐÐÏàÓ¦µÄ´¦Àí
|
//¹Ø±ÕµçÔ´¡¢¹Ø±Õ´®¿Ú
|
RS485_PWR_OFF;
|
RS485_RE_REC_ENABLE;
|
PWR_BOOST_DIABLE;
|
PWR_OUTPUT1_OFF;
|
PWR_OUTPUT2_OFF;
|
PWR_OUTPUT_9V_OFF;
|
PWR_OUTPUT_12V_OFF;
|
RS485_UART_GPIO_sleep();
|
__SYS_STATUS_BYTES_STATUS(RS485_err, RESET, ALARM_ID_READ_485_ABNORMAL);
|
RS485_err_cnt =0 ;
|
return RS485_COM_IDLE;
|
}
|
else{
|
rs485_com_ctrl_pata_g.modbus_step_status ++;
|
return RS485_COM_SEND;
|
}
|
}
|
|
if((--rs485_com_ctrl_pata_g.reread_wait_time_cnt)==0){
|
if((--rs485_com_ctrl_pata_g.reread_num_cnt)==0){
|
//?³¬Ê±ÇÒÖØ¶Á´ÎÊýÓÃÍ꣬´ú±íͨѶ×îÖÕÒÔʧ°Ü¸æÖÕ£¬½øÐÐÏàÓ¦µÄ´¦Àí
|
//¹Ø±ÕµçÔ´¡¢¹Ø±Õ´®¿Ú£¬RS485ͨѶʧ°Ü+1,
|
RS485_PWR_OFF;
|
RS485_RE_REC_ENABLE;
|
PWR_BOOST_DIABLE;
|
PWR_OUTPUT1_OFF;
|
PWR_OUTPUT2_OFF;
|
PWR_OUTPUT_9V_OFF;
|
PWR_OUTPUT_12V_OFF;
|
RS485_UART_GPIO_sleep();
|
if(RS485_err_cnt < 250){
|
if( ++RS485_err_cnt >= RS485_READ_ERR_ALARM_TIMES)
|
__SYS_STATUS_ALARM_BYTES_SET(RS485_err);
|
}
|
|
return RS485_COM_IDLE;
|
}else{
|
//³¬Ê±µ«ÊÇÖØ¸´´ÎÊý»¹ÓУ¬·µ»ØÖØÐ·¢ËͶÁÈ¡Êý¾Ý
|
return RS485_COM_SEND;
|
}
|
}
|
|
return RS485_COM_WAIT_ANSWER;
|
}
|
|
|
|
void rs485ReadDataPro(FUN_START_CTRL_PARA_T * sys_fun_run_ctrl_p)
|
{
|
if((sys_fun_run_ctrl_p->rs485_ctrl_flag.start_flag ==SET)&&(sys_fun_run_ctrl_p->valve_ctrl_flag.running_flag == RESET)&&(sys_fun_run_ctrl_p->wrc_ctrl_flag.running_flag == RESET))//ÅжÏ485²É¼¯±êʶ
|
{
|
sys_fun_run_ctrl_p->rs485_ctrl_flag.start_flag = RESET;
|
if(rs485_com_ctrl_pata_g.status == RS485_COM_IDLE)
|
{
|
rs485_com_ctrl_pata_g.status = RS485_COM_PWR_ON;
|
sys_fun_run_ctrl_p->rs485_ctrl_flag.running_flag = SET;
|
}
|
|
}
|
|
switch (rs485_com_ctrl_pata_g.status){
|
|
case RS485_COM_IDLE: break;
|
case RS485_COM_PWR_ON: rs485_com_ctrl_pata_g.status = rs485ComPwrOnHandle();break;
|
case RS485_COM_SEND: rs485_com_ctrl_pata_g.status = rs485ComSendHandle();break;
|
case RS485_COM_WAIT_ANSWER: rs485_com_ctrl_pata_g.status = rs485ComWaitAnswerHandle();break;
|
|
default:;
|
}
|
|
if(rs485_com_ctrl_pata_g.status == RS485_COM_IDLE){
|
if(sys_fun_run_ctrl_p->rs485_ctrl_flag.running_flag ==SET){
|
sys_fun_run_ctrl_p->rs485_ctrl_flag.running_flag = RESET;
|
RS485_trigger_settle_flag = SET; //RS485²É¼¯Ö®ºó´¥·¢Ò»´Î½áËã
|
}
|
}
|
}
|