Hi,
I am using CAN COM API provided by the official, I demonstrated the "callback" demo, it's no problem. However when I combined that with FreeRtos project, there is always an error at Callback function. I just learn FreeRtos for several days, so is there anyone can help me check the code, and give some suggestion.
this is my code:
/* FreeRTOS kernel includes. */
#include "FreeRTOS.h"
#include "task.h"
#include "queue.h"
#include "timers.h"
#include "event_groups.h"
/* Freescale includes. */
#include "fsl_device_registers.h"
#include "fsl_debug_console.h"
#include "board.h"
/* User include. */
#include "can.h"
#include "pin_mux.h"
#include <stdbool.h>
/*******************************************************************************
* Definitions
******************************************************************************/
#define B0 (1 << 0)
#define B1 (1 << 1)
#define TICKRATE_HZ (1000) /* 1000 ticks per second */
#define TRANSMIT_PERIOD (100) /* milliseconds between transmission */
#define ECHO_BUFFER_LENGTH 20
#define CAN0_IRQ CAN0_IRQ0_IRQn
#define CAN1_IRQ CAN1_IRQ0_IRQn
#define CAN0_NVIC_PRIO 0
/* The software timer period. */
#define SW_TIMER_PERIOD_MS (1000 / portTICK_PERIOD_MS)
/*******************************************************************************
* Variables
******************************************************************************/
can_handle_t g_canHandle0;
can_handle_t g_canHandle1;
volatile bool CAN0rxBufferEmpty = true;
volatile bool CAN0rxOnGoing = false;
/* handle for non-blocking receive for message buffer 0 */
static can_mb_transfer_t mb0rxfer;
/*******************************************************************************
* Prototypes
******************************************************************************/
static void write_task_1(void *pvParameters);
/* USART user callback */
void CAN0_Callback(CAN_Type *base, can_handle_t *handle, status_t status, uint32_t result, void *userData);
void SwTimerCallback(TimerHandle_t xTimer);
/*******************************************************************************
* Globals
******************************************************************************/
/*******************************************************************************
* Code
******************************************************************************/
/*!
* @brief Main function
*/
int main(void)
{
can_config_t config;
can_frame_t rxmb0msg;
TimerHandle_t SwTimerHandle = NULL;
/* Define the init structure for the output LED pin*/
gpio_pin_config_t led_config = {
kGPIO_DigitalOutput, 0,
};
/* Board pin, clock, debug console init */
/* attach 12 MHz clock to FLEXCOMM0 (debug console) */
CLOCK_AttachClk(BOARD_DEBUG_UART_CLK_ATTACH);
CLOCK_EnableClock(kCLOCK_Gpio0);
CLOCK_EnableClock(kCLOCK_Gpio1);
CLOCK_EnableClock(kCLOCK_Gpio2);
CLOCK_EnableClock(kCLOCK_Gpio3);
/* attach 12 MHz clock to FLEXCOMM0 (debug console) */
CLOCK_AttachClk(BOARD_DEBUG_UART_CLK_ATTACH);
BOARD_InitPins();
BOARD_BootClockFROHF96M();
BOARD_InitDebugConsole();
/* Init output LED GPIO. */
GPIO_PinInit(GPIO, BOARD_LED1_GPIO_PORT, BOARD_LED1_GPIO_PIN, &led_config);
GPIO_WritePinOutput(GPIO, BOARD_LED1_GPIO_PORT, BOARD_LED1_GPIO_PIN, 1);
GPIO_PinInit(GPIO, BOARD_LED2_GPIO_PORT, BOARD_LED2_GPIO_PIN, &led_config);
GPIO_WritePinOutput(GPIO, BOARD_LED2_GPIO_PORT, BOARD_LED2_GPIO_PIN, 1);
GPIO_PinInit(GPIO, BOARD_LED3_GPIO_PORT, BOARD_LED3_GPIO_PIN, &led_config);
GPIO_WritePinOutput(GPIO, BOARD_LED3_GPIO_PORT, BOARD_LED3_GPIO_PIN, 1);
/* configure for 4Mbps data 1Mbps nominal, CAN-FD */
CAN_GetDefaultConfig(&config);
config.baseAddress = 0x20010000;
config.nominalBaudRate = 1000000;
config.dataBaudRate = 4000000;
config.timestampClock_Hz = 100000;
/* Set CAN0 interrupt priority higher. */
NVIC_SetPriority(CAN0_IRQ, CAN0_NVIC_PRIO+1);
EnableIRQ(CAN0_IRQ);
CAN_Init(CAN0, &config, SystemCoreClock);
/* receive 0x100 in CAN0 rx message buffer 0 by setting mask 0 */
CAN_SetRxIndividualMask(CAN0, 0, CAN_RX_MB_STD(0x52, 0));
/* receive 0x100 in CAN0 rx message buffer 0 by setting mask 1 */
CAN_SetRxIndividualMask(CAN0, 1, CAN_RX_MB_STD(0x57, 0));
/* receive 0x00000200 (29-bit id) in CAN1 rx message buffer 1 by setting mask 3 */
CAN_SetRxExtIndividualMask(CAN0, 3, CAN_RX_MB_EXT_LOW(0x200, 1), CAN_RX_MB_EXT_HIGH(0x200, 1));
//Creat a handler to get Interrupt
CAN_TransferCreateHandle(CAN0, &g_canHandle0, CAN0_Callback, NULL);
/* enable CAN 0 */
CAN_Enable(CAN0, true);
mb0rxfer.frame = &rxmb0msg;
mb0rxfer.mbIdx = 0;
CAN_TransferReceiveNonBlocking(CAN0, &g_canHandle0, &mb0rxfer);
xTaskCreate(write_task_1, "WRITE_TASK_1", configMINIMAL_STACK_SIZE + 38, NULL, tskIDLE_PRIORITY + 2, NULL);
/* Start scheduling. */
vTaskStartScheduler();
for (;;)
;
}
void SwTimerCallback(TimerHandle_t xTimer){
GPIO_TogglePinsOutput(GPIO, BOARD_LED2_GPIO_PORT, 1u << BOARD_LED2_GPIO_PIN);
}
/* CAN user callback */
void CAN0_Callback(CAN_Type *base, can_handle_t *handle, status_t status, uint32_t result, void *userData)
{
can_frame_t *rxmsg;
BaseType_t reschedule;
//if handle from CAN0
if(handle == &g_canHandle0)
{
/* message received into message buffer */
if (status == (status_t)kStatus_CAN_RxIdle)
{
/* get received message */
rxmsg = handle->mbFrameBuf[result];
/* toggle LED3 */
GPIO_TogglePinsOutput(GPIO, BOARD_LED3_GPIO_PORT, 1u << BOARD_LED3_GPIO_PIN);
/* receive next message using this callback */
CAN_TransferReceiveNonBlocking(CAN0, &g_canHandle0, &mb0rxfer);
}
else if (status == (status_t)kStatus_CAN_RxFifoIdle)
{
/* result holds the fifo number */
/* get the message from handle->rxFifoFrameBuf[result] */
}
}
// xSemaphoreGiveFromISR(handle->semaphore, &reschedule);
// portYIELD_FROM_ISR(1);
xTaskResumeFromISR(write_task_1);
}
/*!
* @brief write_task_1 function work_task mean the
*/
static void write_task_1(void *pvParameters)
{
while (1)
{
GPIO_TogglePinsOutput(GPIO, BOARD_LED1_GPIO_PORT, 1u << BOARD_LED1_GPIO_PIN);
vTaskDelay(1000);
}
}