我正在用C语言开发STM32F1xx,直到现在我还在尝试使用“CANopenNode主控”实现CANopen堆栈,并且使用了2个中断。
第一种是进程同步TPDO和RPDO的计时器中断,第二种是可以接收到的消息,但在完成所有配置后,这种中断(fifo0)不起作用
定时器周期为1毫秒。
我使用NVIC赋予优先级和次优先级,并启用每次中断的IRQ。
我把可以接收fifo0的高优先级(第一个)。
我把罐头装好了(我想)
但它不像计时器中断那样工作正常。
要验证每次总线上有来自我节点以外的其他节点的帧时回调都不起作用;:
一。我刚刚在回调函数中使用了printf,但它不起作用。
2。我一直检查Instance->RF0R的值,它总是等于0。
//HeaderCanini是指向hcan的指针。
CANmodule->CANbaseAddress = *(HeaderCaninit);
CANmodule->CANbaseAddress.Instance = HeaderCaninit->Instance;
switch (CANbitRate)
{
case 1000: CANmodule->CANbaseAddress.Init.Prescaler = 2;
break;
case 500: CANmodule->CANbaseAddress.Init.Prescaler = 4;// in our example we choose a prescaler 4 with other setting to get the 1Mb/s
break;
default:
case 250: CANmodule->CANbaseAddress.Init.Prescaler = 8;
break;
case 125: CANmodule->CANbaseAddress.Init.Prescaler = 16;
break;
case 100: CANmodule->CANbaseAddress.Init.Prescaler = 20;
break;
case 50: CANmodule->CANbaseAddress.Init.Prescaler = 40;
break;
case 20: CANmodule->CANbaseAddress.Init.Prescaler = 100;
break;
case 10: CANmodule->CANbaseAddress.Init.Prescaler = 200;
break;
}
CANmodule->CANbaseAddress.Init.SyncJumpWidth =CAN_SJW_1TQ; // changed by VJ, old value = CAN_SJW_1tq;//chngeD by aziz grib and we follow our CAN setting to get 1Mb/s
CANmodule->CANbaseAddress.Init.TimeSeg1 = CAN_BS1_4TQ; // changed by VJ, old value = CAN_BS1_3tq;// changed by GA to follow CAN transmit example = CAN_BS1_4TQ
CANmodule->CANbaseAddress.Init.TimeSeg2 = CAN_BS2_1TQ; ``
CANmodule->CANbaseAddress.Init.AutoRetransmission= DISABLE; // No Automatic retransmision//AG:if the first transmission fail the seconde is done automatically
CANmodule->CANbaseAddress.Init.Mode = CAN_MODE_NORMAL;
CANmodule->CANbaseAddress.Init.TimeTriggeredMode = DISABLE;
CANmodule->CANbaseAddress.Init.ReceiveFifoLocked = DISABLE;
CANmodule->CANbaseAddress.Init.TransmitFifoPriority = DISABLE;
memset(&CAN_FilterInitStruct, 0, sizeof (CAN_FilterInitStruct));
//CAN_FilterInitStruct.FilterNumber = 0; // for STM32F4
CAN_FilterInitStruct.FilterMaskIdHigh = 0x0000;
CAN_FilterInitStruct.FilterIdLow = 0x0000;
CAN_FilterInitStruct.FilterIdHigh = 0x0000;
CAN_FilterInitStruct.FilterMaskIdLow = 0x0000;
CAN_FilterInitStruct.FilterFIFOAssignment = CAN_RX_FIFO0;
CAN_FilterInitStruct.FilterMode = CAN_FILTERMODE_IDMASK;
CAN_FilterInitStruct.FilterScale = CAN_FILTERSCALE_32BIT;
CAN_FilterInitStruct.FilterActivation = DISABLE;
CAN_FilterInitStruct.FilterBank = 0;
CAN_FilterInitStruct.SlaveStartFilterBank = 14;
if (HAL_CAN_Init(&CANmodule->CANbaseAddress) != HAL_OK)
{
// TRACE_DEBUG_WP("res=%d\n\r", result);
return CO_ERROR_PARAMETERS; /* CO- Return Init failed */
}
HAL_CAN_ConfigFilter(&CANmodule->CANbaseAddress, &CAN_FilterInitStruct);
CAN_OperatingModeRequest(CANmodule->CANbaseAddress, CAN_Mode_Normal);
if (HAL_CAN_Start(&CANmodule->CANbaseAddress) != HAL_OK)
{
/* Start Error */
Error_Handler();
printf("--------------------------CANstart_error-------------
--------");
}
//这是NVIC设置
static void MX_NVIC_Init(void)
{
/* TIM4_IRQn interrupt configuration */
HAL_NVIC_SetPriority(TIM4_IRQn, 0, 1);
HAL_NVIC_EnableIRQ(TIM4_IRQn);
/* CAN1_RX1_IRQn interrupt configuration */
HAL_NVIC_SetPriority(CAN1_RX1_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(CAN1_RX1_IRQn);
/* CAN1_SCE_IRQn interrupt configuration */
HAL_NVIC_SetPriority(CAN1_SCE_IRQn, 1, 2);
HAL_NVIC_EnableIRQ(CAN1_SCE_IRQn);
/* EXTI9_5_IRQn interrupt configuration */
HAL_NVIC_SetPriority(EXTI9_5_IRQn, 15, 15);
HAL_NVIC_EnableIRQ(EXTI9_5_IRQn);
}
//总的来说我做了
HAL_CAN_ActivateNotification(&CO->CANmodule[0]->CANbaseAddress,CAN_IT_TX_MAILBOX_EMPTY|CAN_IT_RX_FIFO0_MSG_PENDING);
//在函数回调中
void HAL_CAN_RxFifo0MsgPendingCallback(CAN_HandleTypeDef *hcan)
{
printf("TIMI");// it does not work
/* Get RX message */
CO_CANinterrupt_Rx(CO->CANmodule[0]);
}
预期结果:
我打印了一份必须执行的文件。
回调函数中的函数也应该被执行。
最佳答案
我决定在CubeMx上选择USB0-CAN-u回调中断,而不是Rx0中断,这样一切都会好起来。