#include "bsp_can.h" #include "bsp_queue.h" #include "kit_time.h" #include "kit_math.h" #include "kit_debug.h" /***********************************************同步接口*********************************************/ KitResult bsp_can_sync_send(CanDev dev, uint32_t id, uint8_t *buf, uint8_t len, CanIde ide, CanRtr rtr) { CanMsg msg; uint32_t dly = 0; KitResult res = kKitResult_Ok; KIT_ASSERT_PARAM(dev <= kCanDev_End); KIT_ASSERT_PARAM(((buf != NULL) && (len > 0) && (len < 9)) || ((buf == NULL) && (len == 0))); msg.ide = ide; msg.rtr = rtr; msg.len = len; msg.id.value = id; kit_copy_buf(msg.data.byte, buf, len); while(drv_can_send(dev, &msg) != kKitResult_Ok) { kit_time_dly_ms(1); if(++dly > 5) { res = kKitResult_TimeOut; break; } } KIT_ASSERT_RES(dev, res); return res; } KitResult bsp_can_ext_data_sync_send(CanDev dev, uint32_t id, uint8_t *buf, uint8_t len) { KIT_ASSERT_PARAM(((buf != NULL) && (len > 0) && (len < 9)) || ((buf == NULL) && (len == 0))); return bsp_can_sync_send(dev, id, buf, len, kCanIde_Ext, kCanRtr_Data); } KitResult bsp_can_std_data_sync_send(CanDev dev, uint32_t id, uint8_t *buf, uint8_t len) { KIT_ASSERT_PARAM(((buf != NULL) && (len > 0) && (len < 9)) || ((buf == NULL) && (len == 0))); return bsp_can_sync_send(dev, id, buf, len, kCanIde_Std, kCanRtr_Data); } KitResult bsp_can_ext_data_series_sync_send(CanDev dev, uint32_t id, uint32_t add_value, uint8_t *buf, uint16_t len) { uint16_t remainder, quotient; KitResult res = kKitResult_Ok; KIT_ASSERT_PARAM((len > 0) && (buf != NULL)); quotient = len >> 3; remainder = len % 8; for(len = 0; len < quotient; len++) { res |= bsp_can_ext_data_sync_send(dev, id, (uint8_t *)(buf + (len << 3)), 8); id += add_value; } if(0 != remainder) { res |= bsp_can_ext_data_sync_send(dev, id, (uint8_t *)(buf + (len << 3)), remainder); } return res; } /***********************************************异步接口*********************************************/ #if STM32F40_41xxx bool is_can_it_start[kCanDev_End] = {false, false}; QUEUE_STATIC_INIT_CCM(can0_tx_queue, 300, sizeof(CanMsg)); QUEUE_STATIC_INIT_CCM(can1_tx_queue, 300, sizeof(CanMsg)); QueueItem * const can_tx_queue[kCanDev_End] = {&can0_tx_queue, &can1_tx_queue}; #else QUEUE_STATIC_INIT(can0_tx_queue, 200, sizeof(CanMsg)); #if STM32F10X_CL bool is_can_it_start[kCanDev_End] = {false, false}; QUEUE_STATIC_INIT(can1_tx_queue, 200, sizeof(CanMsg)); QueueItem * const can_tx_queue[kCanDev_End] = {&can0_tx_queue, &can1_tx_queue}; #else bool is_can_it_start[kCanDev_End] = {false}; QueueItem * const can_tx_queue[kCanDev_End] = {&can0_tx_queue}; #endif #endif KitResult bsp_can_async_send(CanDev dev, uint32_t id, uint8_t *buf, uint8_t len, CanIde ide, CanRtr rtr) { CanMsg *msg; uint32_t cnt = 0; KitResult res = kKitResult_Error; KIT_ASSERT_PARAM((dev <= kCanDev_End) && (msg != NULL)); //当mailbox空闲时,优先使用mailbox发送 //一但开启中断发送,始终都用中断直至队列为空 if((drv_can_get_mailbox(dev) < 3) && (is_can_it_start[dev] == false)) { res = bsp_can_sync_send(dev, id, buf, len, ide, rtr); } else { while(((bsp_queue_push_pointer(can_tx_queue[dev], (void** )&msg)) != kKitResult_Ok) && (cnt++ < 5)) { kit_time_dly_ms(1); } if(cnt < 5) { msg->len = len; msg->id.value = id; msg->ide = ide; msg->rtr = rtr; kit_copy_buf(msg->data.byte, buf, len); is_can_it_start[dev] = true; drv_can_ctrl_interrupt(dev, kCanInterrupt_Tx, true); res = kKitResult_Ok; } } return res; } KitResult bsp_can_ext_data_async_send(CanDev dev, uint32_t id, uint8_t *buf, uint8_t len) { KIT_ASSERT_PARAM(((buf != NULL) && (len > 0) && (len < 9)) || ((buf == NULL) && (len == 0))); return bsp_can_async_send(dev, id, buf, len, kCanIde_Ext, kCanRtr_Data); } KitResult bsp_can_std_data_async_send(CanDev dev, uint32_t id, uint8_t *buf, uint8_t len) { KIT_ASSERT_PARAM(((buf != NULL) && (len > 0) && (len < 9)) || ((buf == NULL) && (len == 0))); return bsp_can_async_send(dev, id, buf, len, kCanIde_Std, kCanRtr_Data); } KitResult bsp_can_ext_data_series_async_send(CanDev dev, uint32_t id, uint32_t add_value, uint8_t *buf, uint16_t len) { uint16_t remainder, quotient; KitResult res = kKitResult_Ok; KIT_ASSERT_PARAM(len > 0); KIT_ASSERT_PARAM(buf != NULL); quotient = len >> 3; remainder = len % 8; for(len = 0; len < quotient; len++) { res |= bsp_can_ext_data_async_send(dev, id, (uint8_t *)(buf + (len << 3)), 8); id += add_value; } if(0 != remainder) { res |= bsp_can_ext_data_async_send(dev, id, (uint8_t *)(buf + (len << 3)), remainder); } return res; } void bsp_can_async_poll(CanDev dev) { CanMsg *msg; while(drv_can_get_mailbox(dev) < 3) { if(bsp_queue_pop_pointer(can_tx_queue[dev], (void **)&msg) == kKitResult_Ok) { drv_can_send(dev, msg); } else { is_can_it_start[dev] = false; drv_can_ctrl_interrupt(dev, kCanInterrupt_Tx, false); break; } } }