More than one peripheral can shared the same interrupt vector, but since both has different drivers they we must call their corresponding HAL_<driver>_IRQHandler
, in this example TIM6 and CAN0 shares the same vector but uses different IRQ functions. There is no need to determine which one causes the interrupt, since the same functions do that.
#include "bsp.h"
int main(void)
{
TIM_HandleTypeDef TIM_Handler; /*TIM initial structure*/
HAL_Init(); /*Init HAL library*/
__HAL_RCC_TIM16_CLK_ENABLE(); /*Enable clock on TIM16*/
/*configure timer 16 with a preesvlare of 1000 y and overflow count of 10000
by default the timer get a Tfrec of 16MHz*/
TIM_Handler.Instance = TIM16; /*Tiomer TIM to configure*/
TIM_Handler.Init.Prescaler = 1000; /*preescaler Tfre / Prescaler*/
TIM_Handler.Init.CounterMode = TIM_COUNTERMODE_UP; /*count from 0 to overflow value*/
TIM_Handler.Init.Period = 10000; /*limit count (overflow)*/
/*use the previous parameters to set configuration on TIM16*/
HAL_TIM_Base_Init( &TIM_Handler );
/* Declaramos las opciones para configurar el modulo FDCAN1 para transmitir al bus CAN a 100Kbps
y sample point de 75% */
CANHandler.Instance = FDCAN1;
CANHandler.Init.Mode = FDCAN_MODE_NORMAL;
CANHandler.Init.FrameFormat = FDCAN_FRAME_CLASSIC;
:
HAL_FDCAN_Init( &CANHandler);
/* Change FDCAN instance from initialization mode to normal mode */
HAL_FDCAN_Start( &CANHandler);
/* Declaramos las opciones para configurar los parametros de transmision CAN */
CANTxHeader.IdType = FDCAN_STANDARD_ID;
CANTxHeader.FDFormat = FDCAN_CLASSIC_CAN;
CANTxHeader.TxFrameType = FDCAN_DATA_FRAME;
CANTxHeader.Identifier = 0x1EF;
CANTxHeader.DataLength = FDCAN_DLC_BYTES_8;
/*activamos la interrupcion por transmision en el buffer0 cuando este se vacia*/
HAL_FDCAN_ActivateNotification( &CANHandler, FDCAN_IT_TX_FIFO_EMPTY, FDCAN_TX_BUFFER0 );
/*Enable interrupt vector TIM16_FDCAN_IT0_IRQn where the CPU will jump in any of
the interrupt event for boths CAN and TIM16 peripherals */
HAL_NVIC_SetPriority( TIM16_FDCAN_IT0_IRQn, 2, 0 );/*se fija la prioridad a nivel 2*/
HAL_NVIC_EnableIRQ( TIM16_FDCAN_IT0_IRQn );
/*init the timer count from 0 and enable its interrupt*/
HAL_TIM_Base_Start_IT( &TIM_Handler );
/*transmit one message*/
HAL_FDCAN_AddMessageToTxFifoQ( &CANHandler, &CANTxHeader, message );
while (1)
{
}
}
/*Since both drivers uses their own IRQ function, then they also will use their corresponding callbacks*/
/*Timer TIM timeout callback*/
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
/*Application code for the TIM6 interupt*/
}
/*CAN caalback for trnasmition completes*/
void HAL_FDCAN_TxBufferCompleteCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t BufferIndexes)
{
/*Application code for the TIM6 interupt*/
}
ints.c
/*Both peripherals share the same vctor interrupt but each one has its own IRQ handler rutine*/
void TIM16_FDCAN_IT0_IRQHandler( void )
{
/*Handle the inerrupt and call the callbacks functions for TIM*/
HAL_TIM_IRQHandler( &Tim6Handler );
/*Handle the inerrupt and call the callbacks functions for CAN*/
HAL_FDCAN_IRQHandler( $Can0Handler );
}