MS-DTU/MS-DTU-V1/User/uart_BDModule.c

585 lines
15 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*
*********************************************************************************************************
* IAR Development Kits
* on the
*
* Nano100
*
* Filename : uart_BDModule.h
* Version : V1.00
* Programmer(s) : Qian Xianghong
*********************************************************************************************************
*/
/*
*********************************************************************************************************
* INCLUDE FILES
*********************************************************************************************************
*/
#include "includes.h"
const uint8_t BD_APP = RF_APP_AJH;
const uint8_t BD_PROTOCOL_VER = RF_PROTOCOL_VER_2;
loopbuff_t CC200A_TaskM;
uint8_t CC200A_TaskM_Data[sizeof(uint8_t) * (4 + 1)] = {0};
#define RF_SelfPSN (dcBuff.configBottle.PSN)
uint8_t BD_RF_MAC_FN = 0;
uint8_t BD_RF_APP_PN = 0;
uint8_t BD_RF_APP_IDX = 0;
// 发送、接收帧
bd_frame_t BD_Send_Frame, BD_RecvFrame;
// 接收自检信息和反馈信息
volatile uint8_t BD_semZjxx = 0, BD_semFkxx = 0;
bd_zjxx_t BD_Zjxx;
bd_fkxx_t BD_Fkxx;
// 北斗初始化状态
uint8_t BD_initStatus = 0;
volatile uint8_t BD_hasPowered = 0;
// 计算校验和(异或)
uint8_t bd_cs_nor(uint8_t *message, int16_t len)
{
int16_t i;
uint8_t cs = 0;
for(i = 0; i < len; i++)
cs ^= message[i];
return cs;
}
// 初始化帧
void bd_initial_frame(bd_frame_t *frame, char *cmd)
{
memset((uint8_t *) frame, 0, sizeof(bd_frame_t));
frame->sof = BD_FRAME_SOF;
memmove(frame->cmd, cmd, 4);
frame->len = BD_MIN_FRAME_LEN; // 小端模式,发送时再转换成大端模式
}
// 追加负载数据
uint8_t bd_append_payload(bd_frame_t *frame, uint8_t payload_len, uint8_t *payload)
{
if(frame->len < BD_MIN_FRAME_LEN || frame->len + payload_len > BD_MAX_FRAME_LEN)
return 0;
if(payload_len > 0)
memmove(frame->bd_payload + (frame->len - BD_MIN_FRAME_LEN), payload, payload_len);
frame->len += payload_len;
return 1;
}
void bd_prepare_send(bd_frame_t *frame)
{
uint8_t *buf = (uint8_t *) frame;
uint16_t len = frame->len;
frame->len = htons(len); // 转换成大端模式
buf[len - 1] = bd_cs_nor(buf, len - 1); // 填写校验码
}
// 北斗物理层校验
uint8_t bd_phy_valid(bd_frame_t *frame)
{
// 通信信息帧
if(strncmp(frame->cmd, BD_TXXX, 4) == 0)
{
// 通信01、代码1、不回执0、通信0、无密钥0、保留00
if(frame->txxx.xxlb != 0x60 || ntohs(frame->txxx.bitLen) > 624)
return 0;
}
// 北斗帧校验成功
return 1;
}
// 物理层校验
uint8_t bd_rf_phy_valid(bd_rf_frame_t *frame)
{
if(frame->sof != RF_FRAME_SOF || frame->len < BD_RF_MIN_FRAME_LEN || frame->len > BD_RF_MAX_FRAME_LEN)
return 0;
if(frame->vendor_id != RF_MARK_LS || frame->app_id != BD_APP || frame->protocol_ver != BD_PROTOCOL_VER)
return 0;
if(rf_crc_16((uint8_t *) frame, frame->len) != 0)
return 0;
// 物理层校验成功
return 1;
}
// mac层校验
uint8_t bd_rf_mac_valid(bd_rf_frame_t *frame, uint8_t dir)
{
if(frame->dir != dir)
return 0;
// mac层校验成功
return 1;
}
// 重新寻找SOF
void BD_SearchSOF(uint8_t *buf, uint16_t fromPos, uint16_t *len)
{
uint16_t i;
for(i = fromPos; i < *len && buf[i] != BD_FRAME_SOF; i++)
{
}
*len -= i;
memmove(buf, buf + i, *len);
}
// 分析串口数据,组帧
char CC200A_recvBuff[100] = {0}; // 扩展内存
uint16_t CC200A_Idx = 0;
void CC200A_ParseFrame(uint8_t c)
{
if((CC200A_Idx==0)&&(c!='\n'))
return;
if(CC200A_Idx < 100)
CC200A_recvBuff[CC200A_Idx++] = c;
// 换行符
if((c == '\n')&&(CC200A_Idx>2))
{
// 丢掉\n前面的\r
if(CC200A_Idx > 0 && CC200A_recvBuff[CC200A_Idx - 1] == '\r')
CC200A_recvBuff[--CC200A_Idx] = 0;
// 先检查字符串(电话号码没有特征字符串)
if(strstr(CC200A_recvBuff, "RDY"))
{
//DTU_recvBuff[idx] = 0;
printf("CC200A RDY");
}
// 检查返回错误的字符串
if(strstr(CC200A_recvBuff,"ERROR"))
{
printf("CC200A ERROR");
}
// 没有所要的字符串,清空
memset(CC200A_recvBuff, 0, DTU_RECVBUFF_SIZE);
CC200A_Idx = 0;
}
}
// 等待DTU命令的返回检查期待的结果字符串
uint32_t CC200A_ParseResult(char *checkPattern, char *checkErrPattern, char *resultBuff, uint16_t waitSeconds)
{
uint8_t done = 0, timeOut;
uint32_t timeOutTick;
uint8_t u8DTU;
uint16_t count, idx = 0;
uint32_t ret = FALSE;
uint8_t strLen = strlen(checkPattern);
uint8_t errLen = strlen(checkErrPattern);
memset(DTU_recvBuff, 0, DTU_RECVBUFF_SIZE);
// 检测返回信息
do
{
timeOut = 1;
timeOutTick = GetDelayTick(waitSeconds * 1000);
while(!IsTickOut(timeOutTick))
{
if(LoopBuff_GetCount(&CC200A_TaskM))
{
timeOut = 0;
break;
}
}
if(!timeOut)
{
count = LoopBuff_GetCount(&DTU_TaskM);
while(count--)
{
// 取数据
memmove(&u8DTU, LoopBuff_GetDataPtr(&DTU_TaskM, DTU_TaskM.info.rdPtr), 1);
LoopBuff_RemoveItems(&DTU_TaskM, 1);
// if(u8DTU == '\n')
// printf("\\n");
// else if(u8DTU == '\r')
// printf("\\r");
// else
// printf("%c", u8DTU);
// 如果是检测发送的提示符(>),直接返回成功
if(strcmp(checkPattern, ">") == 0 && u8DTU == '>')
{
strcpy(resultBuff, ">");
ret = TRUE;
done = 1;
break;
}
// 换行符
if(u8DTU == '\n')
{
// 丢掉\n前面的\r
if(idx > 0 && DTU_recvBuff[idx - 1] == '\r')
DTU_recvBuff[--idx] = 0;
// 先检查字符串(电话号码没有特征字符串)
if((strLen > 0 && strstr(DTU_recvBuff, checkPattern)) || (strLen == 0 && idx > 0))
{
DTU_recvBuff[idx] = 0;
strcpy(resultBuff, DTU_recvBuff);
ret = TRUE;
done = 1;
break;
}
// 检查返回错误的字符串
if(errLen > 0 && strstr(DTU_recvBuff, checkErrPattern))
{
DTU_recvBuff[idx] = 0;
strcpy(resultBuff, DTU_recvBuff);
ret = FALSE;
done = 1;
break;
}
// 没有所要的字符串,清空
memset(DTU_recvBuff, 0, DTU_RECVBUFF_SIZE);
idx = 0;
continue;
}
if(idx < DTU_RECVBUFF_SIZE)
DTU_recvBuff[idx++] = u8DTU;
}
}
} while(!done && !timeOut);
return ret;
}
// 自检
uint8_t BD_Xtzj()
{
// uint8_t try_cnt;
// uint32_t stop_seconds;
// bd_initial_frame(&BD_Send_Frame, BD_XTZJ);
// bd_append_payload(&BD_Send_Frame, sizeof(bd_xtzj_t), BD_Send_Frame.bd_payload);
// bd_prepare_send(&BD_Send_Frame);
// for(try_cnt = 0; try_cnt < 1; try_cnt++)
// {
// // 清除返回标志
// BD_semZjxx = 0;
// // 发送命令
// UART_Transmit(&huart1, (uint8_t *) &BD_Send_Frame, ntohs(BD_Send_Frame.len));
// // 等待返回数据
// stop_seconds = rf_get_seconds() + 2;
// while(rf_get_seconds() < stop_seconds)
// {
// if(BD_semZjxx)
// {
// printf("\nBD Module self check returned.\n");
// if(BD_Zjxx.antennaErr)
// printf("\nThe antenna has error!\n");
// if(BD_Zjxx.boardErr)
// printf("\nThe board has error!\n");
// if(BD_Zjxx.cardErr)
// printf("\nThe card has error!\n");
// if(BD_Zjxx.channelErr)
// printf("\nThe channel has error!\n");
// if(BD_Zjxx.snErr)
// printf("\nThe serial no has error!\n");
// if(BD_Zjxx.dataErr)
// printf("\nThe data has error!\n");
// if(BD_Zjxx.chkErr)
// printf("\nThe check has error!\n");
// if(BD_Zjxx.idErr)
// printf("\nThe id has error!\n");
// if(BD_Zjxx.phyErr)
// printf("\nThe physical has error!\n");
// if(!BD_Zjxx.antennaErr && !BD_Zjxx.boardErr && !BD_Zjxx.cardErr && !BD_Zjxx.channelErr
// && !BD_Zjxx.snErr && !BD_Zjxx.dataErr && !BD_Zjxx.chkErr && !BD_Zjxx.idErr && !BD_Zjxx.phyErr)
// {
// return 1;
// }
// break;
// }
// delay_ms(200);
// }
// delay_ms(500);
// }
// return 0;
}
void CC200A_IRQHandler(USART_Handle *huart)
{
// uint8_t c = (uint8_t) huart->Instance->RDR;
// printf("%c", c);
// // 直接处理,分析并组帧
// CC200A_ParseFrame(c);
uint8_t u8DTU = (uint8_t) huart->Instance->RDR;
//if(DTU_uartPrint)
{
if(u8DTU == '\n')
printf("\\n\n");
else if(u8DTU == '\r')
printf("\\r");
else
printf("%c", u8DTU);
}
// 加入缓冲
//
// LoopBuff_PutItem(&CC200A_TaskM, &u8DTU);
if(u8DTU == 'Y')
printf("%c", u8DTU);
}
// 初始化
void CC200A_Init()
{
LL_GPIO_InitTypeDef GPIO_InitStruct = {0};
LL_AHB2_GRP1_EnableClock(LL_AHB2_GRP1_PERIPH_GPIOB);
/**USART3 GPIO Configuration
PB6 ------> USART1_TX
PB7 ------> USART1_RX
*/
GPIO_InitStruct.Pin = LL_GPIO_PIN_6|LL_GPIO_PIN_7;
GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_MEDIUM;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
GPIO_InitStruct.Alternate = LL_GPIO_AF_7;
LL_GPIO_Init(GPIOB, &GPIO_InitStruct);
}
void CC200A_Open()
{
LL_USART_InitTypeDef USART_InitStruct = {0};
// 用PSN的CRC校验值作为伪随机数的种子
//srand(rf_crc_16(dcBuff.configBottle.PSN, 6));
// BD_RF_MAC_FN = rand() % 256;
// BD_RF_APP_PN = rand() % 256;
// 分配循环缓冲
LoopBuff_Create(&CC200A_TaskM, sizeof(uint8_t), 4, 0, (uint32_t) CC200A_TaskM_Data);
//LL_USART_Disable(huart1.Instance);
huart1.RxISR = CC200A_IRQHandler;
// /* Peripheral clock enable */
// LL_APB2_GRP1_EnableClock(LL_APB2_GRP1_PERIPH_USART1);
// /* USART3 interrupt Init */
// NVIC_SetPriority(USART1_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),5, 0));
// NVIC_EnableIRQ(USART1_IRQn);
// USART_InitStruct.BaudRate = 115200;
// USART_InitStruct.DataWidth = LL_USART_DATAWIDTH_8B;
// USART_InitStruct.StopBits = LL_USART_STOPBITS_1;
// USART_InitStruct.Parity = LL_USART_PARITY_NONE;
// USART_InitStruct.TransferDirection = LL_USART_DIRECTION_TX_RX;
// USART_InitStruct.HardwareFlowControl = LL_USART_HWCONTROL_NONE;
// USART_InitStruct.OverSampling = LL_USART_OVERSAMPLING_16;
// LL_USART_Init(USART1, &USART_InitStruct);
// LL_USART_ConfigAsyncMode(USART1);
// SET_BIT(USART1->CR1, USART_CR1_PEIE | USART_CR1_RXNEIE);
// LL_USART_Enable(USART1);
}
// 初始化帧
void bd_rf_initial_frame(bd_rf_frame_t *frame)
{
memset((uint8_t *) frame, 0, sizeof(bd_rf_frame_t));
frame->len = BD_RF_MIN_FRAME_LEN;
}
// 追加负载数据
uint8_t bd_rf_append_payload(bd_rf_frame_t *frame, uint8_t payload_len, uint8_t *payload)
{
if(frame->len < BD_RF_MIN_FRAME_LEN || frame->len + payload_len > BD_RF_MAX_FRAME_LEN)
return 0;
if(payload_len > 0)
memmove(frame->app_payload + (frame->len - BD_RF_MIN_FRAME_LEN), payload, payload_len);
frame->len += payload_len;
return 1;
}
// 模块上电,设置硬件参数
void CC200A_PowerOn()
{
uint8_t i, count = 0;
char buff[40];
static uint8_t first = 1;
if(BD_hasPowered)
return;
printf("\nCC200A power on ...\n");
VCC_CC200A_ON();
VCC_CC200A_BCK_ON();
//delay_ms(2700);
if(CC200A_ParseResult("RDY", "", buff, 60))
{
printf("r RDY");
}
// if(DTU_ParseResult("+QURC: 5", "", buff, 30))
// {
// printf("r +QURC: 5");
// }
// if(DTU_ParseResult("+QURC: 0", "", buff, 30))
// {
// printf("r +QURC: 0");
// }
// if(DTU_ParseResult("+QURC: 3", "", buff, 30))
// {
// printf("r +QURC: 3");
// }
}
void CC200A_PowerOff()
{
// if(!BD_hasPowered)
// return;
BD_hasPowered = 0;
printf("\nCC200A_PowerOff ...\n");
VCC_CC200A_OFF();
VCC_CC200A_BCK_OFF();
delay_ms(200);
}
// 串口超时定时器
extern uint16_t DTU_tmrQPendLong; // 120s
//extern uint16_t DTU_tmrQPendShort; // 5s
extern uint16_t DTU_tmrQPendSpec; // 40s
// 应用层发送:数据
uint8_t CC200A_rf_app_send_data(uint8_t payload_len, uint8_t *payload)
{
// uint16_t i;
char cmd[80], buff[40];
//AT+QSMGT="TEST7",1,128,1,1,"TEST003"
sprintf(cmd, "AT+QSMGT=1,128,1,1,\"%s\"",payload);
if(!DTU_ExecuteCmd(cmd, "+QURC: 2", "ERROR", buff, DTU_tmrQPendSpec))
{
printf("\nsend err ...\n");
}
// break;
// if(strstr(buff, "+QIOPEN: 0,0"))
// {
// ret = TRUE;
// break;
// }
// uint8_t try_cnt;
// uint32_t stop_seconds;
// uint16_t crc;
// bd_rf_frame_t *rf = (bd_rf_frame_t *) BD_Send_Frame.txsq.bytes;
// S_RTC_TIME_DATA_T sRTC;
// // 初始化BD帧
// bd_initial_frame(&BD_Send_Frame, BD_TXSQ);
// // 初始化RF帧
// bd_rf_initial_frame(rf);
// // 应用层
// bd_rf_append_payload(rf, payload_len, payload);
// rf->app_pn = BD_RF_APP_PN;
// rf->app_idx = 0; // 暂不实现分包组包
// rf->app_tbc = 0;
// // net层
// rf->net_type = RF_NET_TYPE_DATA;
// // mac层
// rf->dir = RF_DIR_UP;
// rf->mac_type = RF_MAC_TYPE_DATA;
// rf->mac_ack_req = 0;
// rf->mac_fn = BD_RF_MAC_FN;
// // 物理层
// rf->sof = RF_FRAME_SOF;
// rf->vendor_id = RF_MARK_LS;
// rf->app_id = BD_APP;
// rf->protocol_ver = BD_PROTOCOL_VER;
// memmove(rf->srcPSN, RF_SelfPSN, 6);
// crc = rf_crc_16((uint8_t *) rf, rf->len - 2);
// ((uint8_t *) rf)[rf->len - 2] = crc >> 8;
// ((uint8_t *) rf)[rf->len - 1] = crc & 0xFF;
// // 通讯申请
// BD_Send_Frame.txsq.xxlb = 0x46; // 普通报文代码
// BD_Send_Frame.txsq.dstAddr[0] = (dcBuff.configDisplay.bdCommander >> 16) & 0xFF; // 指挥机卡号
// BD_Send_Frame.txsq.dstAddr[1] = (dcBuff.configDisplay.bdCommander >> 8) & 0xFF;
// BD_Send_Frame.txsq.dstAddr[2] = (dcBuff.configDisplay.bdCommander & 0xFF);
// BD_Send_Frame.txsq.bitLen = htons(rf->len * 8);
// // 追加通讯申请内容
// bd_append_payload(&BD_Send_Frame,
// sizeof(BD_Send_Frame.txsq) - sizeof(BD_Send_Frame.txsq.bytes) + payload_len + BD_RF_MIN_FRAME_LEN,
// (uint8_t *) &BD_Send_Frame.txsq);
// // 修改数据格式计算cs
// bd_prepare_send(&BD_Send_Frame);
// for(try_cnt = 0; try_cnt < 3; try_cnt++)
// {
// // 清除返回标志
// BD_semFkxx = 0;
// // 发送命令
// UART_Transmit(&huart1, (uint8_t *) &BD_Send_Frame, ntohs(BD_Send_Frame.len));
//// for(i = 0; i < ntohs(BD_Send_Frame.len); i++)
//// printf("%02X ", ((uint8_t *) &BD_Send_Frame)[i]);
//// printf("\n");
// // 等待返回数据s
// stop_seconds = rf_get_seconds() + 2;
// while(rf_get_seconds() < stop_seconds)
// {
// if(BD_semFkxx)
// {
// printf("\nBD Module feedback returned.\n");
// if(BD_Fkxx.fkbz == 0 && strncmp(BD_Fkxx.fjxx, BD_TXSQ, 4) == 0)
// {
// printf("\nThe message has send.\n");
// BD_RF_MAC_FN++;
// BD_RF_APP_PN++;
// // 记录发送成功的时间
// RTC_GetDateAndTime(&sRTC);
// DTU_succTime = Calc_SecondsFromYear(INITIAL_YEAR, sRTC.u32Year, sRTC.u32Month, sRTC.u32Day,
// sRTC.u32Hour, sRTC.u32Minute, sRTC.u32Second);
// return 1;
// }
// printf("\nThe message has not send.\n");
// break;
// }
// delay_ms(200);
// }
// delay_ms(500);
// }
return 0;
}