uart2_rec.c 7.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290
  1. /*
  2. * Copyright (c) 2025 Wingcool Technology Co., Ltd
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. */
  6. #include <soc.h>
  7. #include <board.h>
  8. #include <device.h>
  9. #include <drivers/uart.h>
  10. #include <aem_core_if.h>
  11. #include <logging/log.h>
  12. //#include <gps/gps.h>
  13. LOG_MODULE_REGISTER(uart2_rec, LOG_LEVEL_INF);
  14. #define CONFIG_UART2_REC_DEV_NAME "uart2_rec"
  15. #define UART2_REC_DEV_NAME CONFIG_UART_2_NAME
  16. #define UART_FIFO_MAX 256
  17. #define REC_DATA_BUFFER_SIZE 256
  18. #define PRODUCT_INFO_SIZE 64
  19. #define WRITE_KEY_SIZE 160
  20. // 定义命令
  21. #define DEVICE_ID_CMD 0xB1
  22. #define PROJECT_ID_CMD 0xB2
  23. #define WRITE_KEY_CMD 0xB3
  24. #define IS_KEY_INSIDE_CMD 0xB4
  25. #define SET_TIME_CMD 0xC1
  26. // 定义帧头和帧尾
  27. #define FRAME_HEADER1 0xAA
  28. #define FRAME_HEADER2 0x55
  29. #define FRAME_TAIL1 0x55
  30. #define FRAME_TAIL2 0xAA
  31. struct uart2_rec_data {
  32. const struct device *uart_gpio_dev;
  33. uint8_t rec_data[REC_DATA_BUFFER_SIZE];
  34. //gps_notify_t notify;
  35. };
  36. static struct uart2_rec_data uart2_rec_data;
  37. uint8_t bySetTimeStep = 0;
  38. extern uint8_t bySetHour;
  39. extern uint8_t bySetMinute;
  40. extern uint8_t bySetWeekday;
  41. extern uint16_t wSetYear;
  42. extern uint8_t bySetMonth;
  43. extern uint8_t bySetDay;
  44. extern void uart2_poll_out_ch(int c); // UART2发送一个字节
  45. extern bool aem_read_aem_key_record(aem_key_w_record_t *record); // 读取AEM KEY记录
  46. extern bool aem_defender_factory_write_key(uint8_t * data, uint16_t len); // 写入KEY
  47. extern uint16_t aem_factory_get_product_info(uint8_t *data, uint16_t in_len); // 获取产品信息
  48. // 计算累加和校验值
  49. //1 字节,对命令码、数据长度和数据内容的所有字节进行累加求和,取低8位作为校验值,用于检测数据在传输过程中是否出错
  50. uint8_t calculate_checksum(uint8_t cmd, uint8_t *data, uint8_t data_len)
  51. {
  52. uint8_t checksum = cmd + data_len;
  53. for (uint8_t i = 0; i < data_len; i++) {
  54. checksum += data[i];
  55. }
  56. return checksum;
  57. }
  58. // 发送一帧数据
  59. void send_frame(uint8_t cmd, uint8_t *data, uint8_t data_len)
  60. {
  61. uint8_t checksum = calculate_checksum(cmd, data, data_len);
  62. // 发送帧头
  63. uart2_poll_out_ch(FRAME_HEADER1);
  64. uart2_poll_out_ch(FRAME_HEADER2);
  65. // 发送命令码
  66. uart2_poll_out_ch(cmd);
  67. // 发送数据长度
  68. uart2_poll_out_ch(data_len);
  69. // 发送数据内容
  70. for (uint8_t i = 0; i < data_len; i++) {
  71. uart2_poll_out_ch(data[i]);
  72. }
  73. // 发送累加和校验值
  74. uart2_poll_out_ch(checksum);
  75. // 发送帧尾
  76. uart2_poll_out_ch(FRAME_TAIL1);
  77. uart2_poll_out_ch(FRAME_TAIL2);
  78. }
  79. // 检查一帧数据是否正确
  80. bool check_receive_frame(uint8_t *data)
  81. {
  82. uint8_t calculated_checksum;
  83. uint8_t data_len = data[3];
  84. // 帧头
  85. if (data[0] != FRAME_HEADER1)
  86. {
  87. return false; // 帧头错误
  88. }
  89. if (data[1] != FRAME_HEADER2)
  90. {
  91. return false; // 帧头错误
  92. }
  93. // 计算本地累加和校验值
  94. calculated_checksum = calculate_checksum(data[2], data + 4, data_len);
  95. if (data[data_len + 4] != calculated_checksum) {
  96. return false; // 累加和校验错误
  97. }
  98. // 读取帧尾
  99. if (data[data_len + 5] != FRAME_TAIL1 || data[data_len + 6] != FRAME_TAIL2) {
  100. return false; // 帧尾错误
  101. }
  102. return true; // 接收成功
  103. }
  104. static uint8_t byAACnt = 2;
  105. static bool bReceiveFrameDone = false;
  106. static void uart_fifo_callback(const struct device *dev, void *user_data)
  107. {
  108. uint8_t rx_buff[UART_FIFO_MAX];
  109. uint8_t tx_buff[UART_FIFO_MAX];
  110. int read_size;
  111. static uint8_t cnt;
  112. aem_key_w_record_t *key_record = NULL;
  113. printk("uart_fifo_callback start\n");
  114. uart_irq_update(dev);
  115. if (uart_irq_rx_ready(dev)) {
  116. read_size = uart_fifo_read(dev, rx_buff, UART_FIFO_MAX);
  117. printk("read_size: %d\n", read_size);
  118. if (read_size == UART_FIFO_MAX)
  119. printk("uart fifo buffer overflow\n");
  120. for (int i = 0; i < read_size; i++)
  121. {
  122. switch (rx_buff[i]) {
  123. case FRAME_HEADER1:
  124. byAACnt++;
  125. if (byAACnt > 2)
  126. {
  127. byAACnt = 1;
  128. cnt = 0;
  129. bReceiveFrameDone = false;
  130. }
  131. else if (byAACnt == 2)
  132. {
  133. bReceiveFrameDone = true;
  134. }
  135. uart2_rec_data.rec_data[cnt++] = rx_buff[i];
  136. break;
  137. default:
  138. uart2_rec_data.rec_data[cnt++] = rx_buff[i];
  139. /* protection data cannot exceed boundary */
  140. if (cnt >= REC_DATA_BUFFER_SIZE)
  141. cnt--;
  142. break;
  143. }
  144. }
  145. if (bReceiveFrameDone && check_receive_frame(uart2_rec_data.rec_data))
  146. {
  147. printk("receive frame success\n");
  148. switch (uart2_rec_data.rec_data[2])
  149. {
  150. case DEVICE_ID_CMD:
  151. aem_factory_get_product_info(tx_buff, PRODUCT_INFO_SIZE);
  152. send_frame(PROJECT_ID_CMD, tx_buff, PRODUCT_INFO_SIZE);
  153. break;
  154. case PROJECT_ID_CMD:
  155. tx_buff[0] = 0x0F;
  156. tx_buff[1] = 0x6B;
  157. tx_buff[2] = 0x3B;
  158. tx_buff[3] = 0xD8;
  159. send_frame(PROJECT_ID_CMD, tx_buff, 4);
  160. break;
  161. case WRITE_KEY_CMD:
  162. //uart_fifo_fill(dev,rx_buff,read_size);
  163. tx_buff[0] = 0;
  164. if (aem_defender_factory_write_key(uart2_rec_data.rec_data, WRITE_KEY_SIZE))
  165. {
  166. tx_buff[0] = 0xAA;
  167. }
  168. send_frame(WRITE_KEY_CMD, tx_buff, 1);
  169. break;
  170. case IS_KEY_INSIDE_CMD:
  171. tx_buff[0] = 0;
  172. aem_read_aem_key_record(key_record);
  173. if (key_record != NULL)
  174. {
  175. if (key_record->is_pass)
  176. tx_buff[0] = 0xAA;
  177. }
  178. send_frame(IS_KEY_INSIDE_CMD, tx_buff, 1);
  179. break;
  180. case SET_TIME_CMD:
  181. bySetMinute = uart2_rec_data.rec_data[4];
  182. bySetHour = uart2_rec_data.rec_data[5];
  183. bySetDay = uart2_rec_data.rec_data[6];
  184. bySetWeekday = uart2_rec_data.rec_data[7];
  185. bySetMonth = uart2_rec_data.rec_data[8];
  186. wSetYear = uart2_rec_data.rec_data[9];
  187. bySetTimeStep = 1;
  188. send_frame(SET_TIME_CMD, tx_buff, 0);
  189. break;
  190. default:
  191. break;
  192. }
  193. }
  194. }
  195. }
  196. /*
  197. static void uart2_rec_enable(const struct device *dev)
  198. {
  199. struct uart2_rec_data *data = (struct uart2_rec_data *)dev->data;
  200. printk("uart2_rec_enable\n");
  201. uart_irq_rx_enable(data->uart_gpio_dev);
  202. }
  203. static void uart2_rec_disable(const struct device *dev)
  204. {
  205. struct uart2_rec_data *data = (struct uart2_rec_data *)dev->data;
  206. printk("uart2_rec_disable\n");
  207. uart_irq_rx_disable(data->uart_gpio_dev);
  208. }
  209. static void uart2_rec_register_notify(const struct device *dev, gps_notify_t notify)
  210. {
  211. printk("uart2_rec_register_notify\n");
  212. struct uart2_rec_data *data = (struct uart2_rec_data *)dev->data;
  213. data->notify = notify;
  214. }
  215. static void uart2_rec_unregister_notify(const struct device *dev, gps_notify_t notify)
  216. {
  217. struct uart2_rec_data *data = (struct uart2_rec_data *)dev->data;
  218. data->notify = NULL;
  219. }
  220. static const struct gps_dev_driver_api uart2_rec_api = {
  221. .enable = uart2_rec_enable,
  222. .disable = uart2_rec_disable,
  223. .inquiry = NULL,
  224. .register_notify = uart2_rec_register_notify,
  225. .unregister_notify = uart2_rec_unregister_notify,
  226. };
  227. */
  228. static int uart2_rec_init(const struct device *dev)
  229. {
  230. struct uart2_rec_data *data = (struct uart2_rec_data *)dev->data;
  231. printk("uart2_rec_init\n");
  232. data->uart_gpio_dev = device_get_binding(UART2_REC_DEV_NAME);
  233. if (data->uart_gpio_dev == NULL) {
  234. printk("Couldn't find uart2\n");
  235. return -ENODEV;
  236. }
  237. uart_irq_callback_set(data->uart_gpio_dev, uart_fifo_callback);
  238. uart_irq_rx_enable(data->uart_gpio_dev);
  239. return 0;
  240. }
  241. #if IS_ENABLED(CONFIG_UART_ACTS)
  242. DEVICE_DEFINE(uart2_rec, CONFIG_UART2_REC_DEV_NAME, &uart2_rec_init, NULL, &uart2_rec_data, NULL, POST_KERNEL, 60, NULL);
  243. #endif