使用中断时STM32 SPI丢弃数据

亚历克

我正在尝试使用中断通过SPI发送可变大小的字节数组。该系统由两个核STM32L432板组成。发送器板工作正常,但是接收器板出现问题。具体来说,我注意到很多时候会丢弃一些字节。除了CubeMX提供的默认初始化之外,我的init函数还具有以下设置:

// Trigger RXNE when the FIFO is 1/4 full
LL_SPI_SetRxFIFOThreshold(sw.spi_sw2pc,LL_SPI_RX_FIFO_TH_QUARTER);

// Enable RXNE interrupt
LL_SPI_EnableIT_RXNE(sw.spi_sw2pc);

// Enable SPI
if((SPI3->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
{
    // If disabled, I enable it
    SET_BIT(sw.spi_sw2pc->CR1, SPI_CR1_SPE);
}

SPI设置为以10 Mbit / s的速度工作。通讯速度可能太快了吗?

以下是IRQ处理程序和回调。

IRQ处理程序

void SPI3_IRQHandler(void)
{
  /* USER CODE BEGIN SPI3_IRQn 0 */
  /* Check RXNE flag value in ISR register */
    if(LL_SPI_IsActiveFlag_RXNE(SPI3))
    {
        /* Call function Slave Reception Callback */
        SW_rx_callback();
    }

  /* USER CODE END SPI3_IRQn 0 */
  /* USER CODE BEGIN SPI3_IRQn 1 */

  /* USER CODE END SPI3_IRQn 1 */
}

打回来

void SW_rx_callback(void)
{
    // RXNE flag is cleared by reading data in DR register

    while(LL_SPI_IsActiveFlag_RXNE(SPI3))
        recv_buffer[recv_buffer_index++] = LL_SPI_ReceiveData8(SPI3);

    if(LL_SPI_GetRxFIFOLevel(SPI3) == LL_SPI_RX_FIFO_EMPTY)
    {
        // If there are no more data
        new_data_arrived = true;
        memset(recv_buffer,'\0',recv_buffer_index);
        recv_buffer_index = 0;
    }

}

预先感谢您的帮助。

10 Mbit的SPI意味着您每秒将有1.25百万个中断(在8位传输的情况下),这足以处理中断,尤其是与HAL结合使用时。

STM32L4xx的速度非常快(80MHz),但是在这种情况下,这意味着每个中断调用的时间不能超过64个周期。但是调用中断需要12个周期,退出中断需要10个周期(处于理想状态,总线上没有等待状态),因此,如果您的中断代码需要42个或更多个周期,则可以确保丢失某些字节。

这是我的建议:

  • 首先尝试启用一些编译器优化,以加速代码。
  • 更改中断例程并从中断处理程序中删除所有不必要的内容(使用SW FIFO并在主循环中处理接收到的数据)
  • 但是,根据您的情况,最好的解决方案是使用DMA传输。

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章