in Drivers/STM32U5xx_HAL/Src/stm32u5xx_hal_spi.c [2873:3111]
void HAL_SPI_IRQHandler(SPI_HandleTypeDef *hspi)
{
uint32_t itsource = hspi->Instance->IER;
uint32_t itflag = hspi->Instance->SR;
uint32_t trigger = itsource & itflag;
uint32_t cfg1 = hspi->Instance->CFG1;
uint32_t handled = 0UL;
HAL_SPI_StateTypeDef State = hspi->State;
#if defined (__GNUC__)
__IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->RXDR));
#endif /* __GNUC__ */
/* SPI in mode Transmitter and Receiver ------------------------------------*/
if (HAL_IS_BIT_CLR(trigger, SPI_FLAG_OVR) && HAL_IS_BIT_CLR(trigger, SPI_FLAG_UDR) && \
HAL_IS_BIT_SET(trigger, SPI_FLAG_DXP))
{
hspi->TxISR(hspi);
hspi->RxISR(hspi);
handled = 1UL;
}
/* SPI in mode Receiver ----------------------------------------------------*/
if (HAL_IS_BIT_CLR(trigger, SPI_FLAG_OVR) && HAL_IS_BIT_SET(trigger, SPI_FLAG_RXP) && \
HAL_IS_BIT_CLR(trigger, SPI_FLAG_DXP))
{
hspi->RxISR(hspi);
handled = 1UL;
}
/* SPI in mode Transmitter -------------------------------------------------*/
if (HAL_IS_BIT_CLR(trigger, SPI_FLAG_UDR) && HAL_IS_BIT_SET(trigger, SPI_FLAG_TXP) && \
HAL_IS_BIT_CLR(trigger, SPI_FLAG_DXP))
{
hspi->TxISR(hspi);
handled = 1UL;
}
if (handled != 0UL)
{
return;
}
/* SPI End Of Transfer: DMA or IT based transfer */
if (HAL_IS_BIT_SET(trigger, SPI_FLAG_EOT))
{
/* Clear EOT/TXTF/SUSP flag */
__HAL_SPI_CLEAR_EOTFLAG(hspi);
__HAL_SPI_CLEAR_TXTFFLAG(hspi);
__HAL_SPI_CLEAR_SUSPFLAG(hspi);
/* Disable EOT interrupt */
__HAL_SPI_DISABLE_IT(hspi, SPI_IT_EOT);
/* DMA Normal Mode */
if (HAL_IS_BIT_CLR(cfg1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN) ||
((State != HAL_SPI_STATE_BUSY_RX) && (hspi->hdmarx->Mode != DMA_LINKEDLIST_CIRCULAR)) ||
((State != HAL_SPI_STATE_BUSY_TX) && (hspi->hdmatx->Mode != DMA_LINKEDLIST_CIRCULAR)))
{
/* For the IT based receive extra polling maybe required for last packet */
if (HAL_IS_BIT_CLR(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN))
{
/* Pooling remaining data */
while (hspi->RxXferCount != 0UL)
{
/* Receive data in 32 Bit mode */
if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
{
*((uint32_t *)hspi->pRxBuffPtr) = *((__IO uint32_t *)&hspi->Instance->RXDR);
hspi->pRxBuffPtr += sizeof(uint32_t);
}
/* Receive data in 16 Bit mode */
else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
{
#if defined (__GNUC__)
*((uint16_t *)hspi->pRxBuffPtr) = *prxdr_16bits;
#else
*((uint16_t *)hspi->pRxBuffPtr) = *((__IO uint16_t *)&hspi->Instance->RXDR);
#endif /* __GNUC__ */
hspi->pRxBuffPtr += sizeof(uint16_t);
}
/* Receive data in 8 Bit mode */
else
{
*((uint8_t *)hspi->pRxBuffPtr) = *((__IO uint8_t *)&hspi->Instance->RXDR);
hspi->pRxBuffPtr += sizeof(uint8_t);
}
hspi->RxXferCount--;
}
}
/* Call SPI Standard close procedure */
SPI_CloseTransfer(hspi);
hspi->State = HAL_SPI_STATE_READY;
if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
{
#if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
hspi->ErrorCallback(hspi);
#else
HAL_SPI_ErrorCallback(hspi);
#endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
return;
}
}
#if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
/* Call appropriate user callback */
if (State == HAL_SPI_STATE_BUSY_TX_RX)
{
hspi->TxRxCpltCallback(hspi);
}
else if (State == HAL_SPI_STATE_BUSY_RX)
{
hspi->RxCpltCallback(hspi);
}
else if (State == HAL_SPI_STATE_BUSY_TX)
{
hspi->TxCpltCallback(hspi);
}
#else
/* Call appropriate user callback */
if (State == HAL_SPI_STATE_BUSY_TX_RX)
{
HAL_SPI_TxRxCpltCallback(hspi);
}
else if (State == HAL_SPI_STATE_BUSY_RX)
{
HAL_SPI_RxCpltCallback(hspi);
}
else if (State == HAL_SPI_STATE_BUSY_TX)
{
HAL_SPI_TxCpltCallback(hspi);
}
#endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
else
{
/* End of the appropriate call */
}
return;
}
if (HAL_IS_BIT_SET(itflag, SPI_FLAG_SUSP) && HAL_IS_BIT_SET(itsource, SPI_FLAG_EOT))
{
/* Abort on going, clear SUSP flag to avoid infinite looping */
__HAL_SPI_CLEAR_SUSPFLAG(hspi);
return;
}
/* SPI in Error Treatment --------------------------------------------------*/
if ((trigger & (SPI_FLAG_MODF | SPI_FLAG_OVR | SPI_FLAG_FRE | SPI_FLAG_UDR)) != 0UL)
{
/* SPI Overrun error interrupt occurred ----------------------------------*/
if ((trigger & SPI_FLAG_OVR) != 0UL)
{
SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_OVR);
__HAL_SPI_CLEAR_OVRFLAG(hspi);
}
/* SPI Mode Fault error interrupt occurred -------------------------------*/
if ((trigger & SPI_FLAG_MODF) != 0UL)
{
SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_MODF);
__HAL_SPI_CLEAR_MODFFLAG(hspi);
}
/* SPI Frame error interrupt occurred ------------------------------------*/
if ((trigger & SPI_FLAG_FRE) != 0UL)
{
SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_FRE);
__HAL_SPI_CLEAR_FREFLAG(hspi);
}
/* SPI Underrun error interrupt occurred ------------------------------------*/
if ((trigger & SPI_FLAG_UDR) != 0UL)
{
SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_UDR);
__HAL_SPI_CLEAR_UDRFLAG(hspi);
}
if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
{
/* Disable SPI peripheral */
__HAL_SPI_DISABLE(hspi);
/* Disable all interrupts */
__HAL_SPI_DISABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_RXP | SPI_IT_TXP | SPI_IT_MODF |
SPI_IT_OVR | SPI_IT_FRE | SPI_IT_UDR));
/* Disable the SPI DMA requests if enabled */
if (HAL_IS_BIT_SET(cfg1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN))
{
/* Disable the SPI DMA requests */
CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN);
/* Abort the SPI DMA Rx channel */
if (hspi->hdmarx != NULL)
{
/* Set the SPI DMA Abort callback :
will lead to call HAL_SPI_ErrorCallback() at end of DMA abort procedure */
hspi->hdmarx->XferAbortCallback = SPI_DMAAbortOnError;
if (HAL_OK != HAL_DMA_Abort_IT(hspi->hdmarx))
{
SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
}
}
/* Abort the SPI DMA Tx channel */
if (hspi->hdmatx != NULL)
{
/* Set the SPI DMA Abort callback :
will lead to call HAL_SPI_ErrorCallback() at end of DMA abort procedure */
hspi->hdmatx->XferAbortCallback = SPI_DMAAbortOnError;
if (HAL_OK != HAL_DMA_Abort_IT(hspi->hdmatx))
{
SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
}
}
}
else
{
/* Restore hspi->State to Ready */
hspi->State = HAL_SPI_STATE_READY;
/* Call user error callback */
#if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
hspi->ErrorCallback(hspi);
#else
HAL_SPI_ErrorCallback(hspi);
#endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
}
}
return;
}
}