can_process.c 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168
  1. #include "can_process.h"
  2. #include "uart_process.h"
  3. #include "crc_cal.h"
  4. #include "stdlib.h"
  5. #include "stdio.h"
  6. #include "string.h"
  7. /**********局部函数定义**********/
  8. uint8_t cd_ReadChar(CAN_Buf_TypeDef * ptCANRx, uint8_t ucNum)
  9. {
  10. uint8_t ucData;
  11. uint16_t i;
  12. i = ucNum;
  13. if ((*ptCANRx).ucBufCnt >= ucNum)
  14. {
  15. i += (*ptCANRx).ucBufRdInde;
  16. if (i >= (*ptCANRx).ucBufSize)
  17. {
  18. i -=((*ptCANRx).ucBufSize);
  19. }
  20. }
  21. else
  22. {
  23. i=0;
  24. }
  25. ucData = *((*ptCANRx).pcBufAddr + i);
  26. return ucData;
  27. }
  28. void cd_DelChar(CAN_Buf_TypeDef * ptCANRx, uint8_t ucNum)
  29. {
  30. uint16_t i;
  31. if ((*ptCANRx).ucBufCnt >= ucNum)
  32. {
  33. __HAL_CAN_DISABLE_IT(&hcan, CAN_IT_FMP0);//关接收中断
  34. (*ptCANRx).ucBufCnt -= ucNum;
  35. __HAL_CAN_ENABLE_IT(&hcan, CAN_IT_FMP0);//开接收中断
  36. i = ucNum;
  37. i += (*ptCANRx).ucBufRdInde;
  38. if (i >= (*ptCANRx).ucBufSize)
  39. {
  40. i -= (*ptCANRx).ucBufSize;
  41. }
  42. (*ptCANRx).ucBufRdInde = i;
  43. }
  44. else
  45. {
  46. __HAL_CAN_DISABLE_IT(&hcan, CAN_IT_FMP0);//关接收中断
  47. i = (*ptCANRx).ucBufCnt;
  48. (*ptCANRx).ucBufCnt = 0;
  49. __HAL_CAN_ENABLE_IT(&hcan, CAN_IT_FMP0);//开接收中断
  50. i += (*ptCANRx).ucBufRdInde;
  51. if (i >= (*ptCANRx).ucBufSize)
  52. {
  53. i -= (*ptCANRx).ucBufSize;
  54. }
  55. (*ptCANRx).ucBufRdInde = i;
  56. }
  57. }
  58. //数据解析处理
  59. void DataProcess(uint16_t ID, uint8_t Mode, uint16_t Cmd, uint8_t* Data)
  60. {
  61. }
  62. /*********************End*******************/
  63. /************全局函数定义*******************/
  64. //CAN数据解析,严格按照协议格式
  65. void CAN_RxData_Process(CAN_Buf_TypeDef* ptCANRx, uint16_t TimeOutCnt)
  66. {
  67. uint8_t Mode, CmdLength, DataLength;
  68. static uint8_t Data[255], CRC_Buf[255];
  69. uint16_t Cmd, i;
  70. uint32_t CrcResult, CrcData;
  71. uint8_t FrameBegin1, FrameBegin2;
  72. if(ptCANRx->ucBufCnt >= 11)
  73. {
  74. //读取帧头
  75. FrameBegin1 = cd_ReadChar(ptCANRx, 0);
  76. CRC_Buf[0] = FrameBegin1;
  77. FrameBegin2 = cd_ReadChar(ptCANRx, 1);
  78. CRC_Buf[1] = FrameBegin2;
  79. if((FrameBegin1 == FRAME_BEGIN1) && (FrameBegin2 == FRAME_BEGIN2))
  80. {
  81. CRC_Buf[2] = (uint8_t)((ptCANRx->ucBufID >> 8) & 0xFF);
  82. CRC_Buf[3] = (uint8_t)(ptCANRx->ucBufID & 0xFF);
  83. //读取帧模式
  84. Mode = cd_ReadChar(ptCANRx, 2);
  85. CRC_Buf[4] = Mode;
  86. if((Mode == MODE_READ) || (Mode == MODE_WRITE) || (Mode == MODE_REPORT))
  87. {
  88. //读取命令段长度和命令字
  89. CmdLength = cd_ReadChar(ptCANRx, 3);
  90. CRC_Buf[5] = CmdLength;
  91. Cmd = (cd_ReadChar(ptCANRx, 4) << 8) + cd_ReadChar(ptCANRx, 5);
  92. CRC_Buf[6] = (uint8_t)((Cmd >> 8) & 0xFF);
  93. CRC_Buf[7] = (uint8_t)(Cmd & 0xFF);
  94. DataLength = cd_ReadChar(ptCANRx, 5);
  95. if((CmdLength - DataLength) == 2)
  96. {
  97. if(ptCANRx->ucBufCnt < (CmdLength + 9))//帧头2bytes + 模式1byte + 命令段长度1byte + 校验位4bytes + 帧尾1byte
  98. {
  99. if(ptCANRx->IsWaitRX_Flag == FALSE)
  100. {
  101. ptCANRx->DelayTimeCnt = HAL_GetTick();
  102. ptCANRx->IsWaitRX_Flag = TRUE;
  103. }
  104. if((HAL_GetTick() - ptCANRx->DelayTimeCnt) > TimeOutCnt)//超时,单位ms
  105. {
  106. cd_DelChar(ptCANRx, ptCANRx->ucBufCnt);
  107. ptCANRx->IsWaitRX_Flag = FALSE;
  108. }
  109. return;
  110. }
  111. else
  112. {
  113. ptCANRx->IsWaitRX_Flag = FALSE;
  114. //接收到完整正确数据包
  115. for(i=0; i<DataLength; i++)//读取数据段
  116. {
  117. Data[i] = cd_ReadChar(ptCANRx, 6 + i);
  118. CRC_Buf[8 + i] = Data[i];
  119. }
  120. CrcData = (cd_ReadChar(ptCANRx, 6 + DataLength) << 24) + \
  121. (cd_ReadChar(ptCANRx, 7 + DataLength) << 16) + \
  122. (cd_ReadChar(ptCANRx, 8 + DataLength) << 8) + \
  123. cd_ReadChar(ptCANRx, 9 + DataLength);
  124. CrcResult = CRC32_Calculate(CRC_Buf, 8 + DataLength);
  125. if((CrcData - CrcResult) == 0) // 比较校验
  126. {
  127. //数据处理
  128. DataProcess(ptCANRx->ucBufID, Mode, Cmd, Data);//Mode为帧模式,Cmd为命令字,Data为数据段
  129. //数据转发UART3
  130. CRC_Buf[8 + DataLength] = cd_ReadChar(ptCANRx, 6 + DataLength);
  131. CRC_Buf[9 + DataLength] = cd_ReadChar(ptCANRx, 7 + DataLength);
  132. CRC_Buf[10 + DataLength] = cd_ReadChar(ptCANRx, 8 + DataLength);
  133. CRC_Buf[11 + DataLength] = cd_ReadChar(ptCANRx, 9 + DataLength);
  134. CRC_Buf[12 + DataLength] = FRAME_END;
  135. UART_SendData(&UART_TxBuff_Struct3, CRC_Buf, DataLength + 13);
  136. //清除缓存
  137. cd_DelChar(ptCANRx, CmdLength + 9);
  138. //通信指示
  139. HAL_GPIO_TogglePin(LED_Display_GPIO_Port, LED_Display_Pin);
  140. return;
  141. }
  142. cd_DelChar(ptCANRx, 1);
  143. }
  144. }
  145. else
  146. {
  147. cd_DelChar(ptCANRx, 1);
  148. }
  149. }
  150. else
  151. {
  152. cd_DelChar(ptCANRx, 1);
  153. }
  154. }
  155. else
  156. {
  157. cd_DelChar(ptCANRx, 1);
  158. }
  159. }
  160. }
  161. /********************End********************/