can_sample.c 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. #include "rtconfig.h"
  2. #ifdef BSP_USING_CAN
  3. #include <rtdevice.h>
  4. #include "drv_can.h"
  5. #define LOG_TAG "can_drv"
  6. #include "drv_log.h"
  7. #include "fcan.h"
  8. #include "fio_mux.h"
  9. #include "interrupt.h"
  10. #include "fcpu_info.h"
  11. /*can test example*/
  12. static rt_device_t can_dev; /* CAN device handle */
  13. static struct rt_semaphore rx_sem;
  14. static rt_err_t can_rx_call(rt_device_t dev, rt_size_t size)
  15. {
  16. /* The CAN generates an interrupt after receiving data, calls this callback function, and then sends the received semaphore */
  17. rt_sem_release(&rx_sem);
  18. return RT_EOK;
  19. }
  20. static void can_rx_thread(void *parameter)
  21. {
  22. int i;
  23. rt_err_t res = RT_EOK;
  24. struct rt_can_msg rxmsg = {0};
  25. rt_device_set_rx_indicate(can_dev, can_rx_call);
  26. while (1)
  27. {
  28. /* The hdr value is - 1, which means reading data directly from the uselist */
  29. rxmsg.hdr_index = -1;
  30. /* Blocking waiting to receive semaphore */
  31. res = rt_sem_take(&rx_sem, RT_WAITING_FOREVER);
  32. RT_ASSERT(res == RT_EOK);
  33. /* Read a frame of data from CAN */
  34. rt_device_read(can_dev, 0, &rxmsg, sizeof(rxmsg));
  35. /* Print data ID and conten */
  36. rt_kprintf("ID:%x\n", rxmsg.id);
  37. rt_kprintf("DATA: ");
  38. for (i = 0; i < 8; i++)
  39. {
  40. rt_kprintf("%2x ", rxmsg.data[i]);
  41. }
  42. rt_kprintf("\n");
  43. }
  44. }
  45. int can_sample(int argc, char *argv[])
  46. {
  47. struct rt_can_msg msg = {0};
  48. rt_err_t res = RT_EOK;;
  49. rt_thread_t thread;
  50. char can_name[RT_NAME_MAX];
  51. if (argc == 2)
  52. {
  53. rt_strncpy(can_name, argv[1], RT_NAME_MAX);
  54. }
  55. else
  56. {
  57. rt_strncpy(can_name, "CAN0", RT_NAME_MAX);
  58. }
  59. /* Find CAN device */
  60. can_dev = rt_device_find(can_name);
  61. if (!can_dev)
  62. {
  63. rt_kprintf("Find %s failed.\n", can_name);
  64. return -RT_ERROR;
  65. }
  66. /* Initialize CAN receive signal quantity */
  67. res = rt_sem_init(&rx_sem, "rx_sem", 0, RT_IPC_FLAG_FIFO);
  68. RT_ASSERT(res == RT_EOK);
  69. /* Open the CAN device in the way of interrupt reception and transmission */
  70. res = rt_device_open(can_dev, RT_DEVICE_FLAG_INT_TX | RT_DEVICE_FLAG_INT_RX);
  71. rt_device_control(can_dev, RT_CAN_CMD_SET_BAUD, CAN1MBaud);
  72. RT_ASSERT(res == RT_EOK);
  73. #ifdef RT_CAN_USING_HDR
  74. struct rt_can_filter_item items[4] =
  75. {
  76. RT_CAN_FILTER_ITEM_INIT(0x3, 0, 0, 0, 0, RT_NULL, RT_NULL),
  77. RT_CAN_FILTER_ITEM_INIT(0x3, 0, 0, 0, 0, RT_NULL, RT_NULL),
  78. RT_CAN_FILTER_ITEM_INIT(0x3, 0, 0, 0, 0, RT_NULL, RT_NULL),
  79. RT_CAN_FILTER_ITEM_INIT(0x3, 0, 0, 0, 0, RT_NULL, RT_NULL)
  80. };
  81. struct rt_can_filter_config cfg = {4, 1, items}; /* There are 4 filter tables in total */
  82. /* Set the hardware filter table. After setting, only frames with id=0x03 can be received*/
  83. res = rt_device_control(can_dev, RT_CAN_CMD_SET_FILTER, &cfg);
  84. RT_ASSERT(res == RT_EOK);
  85. #endif
  86. /* Create data receiving thread */
  87. thread = rt_thread_create("can_rx", can_rx_thread, RT_NULL, 4096, 25, 10);
  88. if (thread != RT_NULL)
  89. {
  90. res = rt_thread_startup(thread);
  91. RT_ASSERT(res == RT_EOK);
  92. }
  93. else
  94. {
  95. rt_kprintf("Create can_rx thread failed.\n");
  96. }
  97. msg.id = 0x78; /* ID = 0x78 */
  98. msg.ide = RT_CAN_STDID; /* Standard format */
  99. msg.rtr = RT_CAN_DTR; /* Data frame */
  100. msg.len = 8; /* Data length is 8 */
  101. /* Send CAN data */
  102. for (int i = 0; i < 1; i++)
  103. {
  104. /* 8-byte data to be sent */
  105. msg.data[0] = 0x00 + i;
  106. msg.data[1] = 0x11 + i;
  107. msg.data[2] = 0x22 + i;
  108. msg.data[3] = 0x33 + i;
  109. msg.data[4] = 0x44 + i;
  110. msg.data[5] = 0x55 + i;
  111. msg.data[6] = 0x66 + i;
  112. msg.data[7] = 0x77 + i;
  113. rt_device_write(can_dev, 0, &msg, sizeof(msg));
  114. }
  115. return res;
  116. }
  117. /* Enter can_sample command for testing */
  118. MSH_CMD_EXPORT(can_sample, can device sample);
  119. #endif