STM32F4在半双工/单工模式下停用SPI的正确方法
Posted
技术标签:
【中文标题】STM32F4在半双工/单工模式下停用SPI的正确方法【英文标题】:Correct way to deactivate SPI in half-duplex/simplex mode STM32F4 【发布时间】:2021-07-17 05:03:39 【问题描述】:我正在尝试在一定时间后将 STM32F4 从从机更改为主机,以主机身份发送消息,然后返回从机。我发现将 SPI 配置为 slave_rxonly 并启用 SPI 将导致时钟在我将设备配置回主机后立即意外发送时钟。没有我发送任何数据。我假设它是因为我要么错误地初始化外围设备,要么错误地取消初始化它
这是我的主循环。
while (1)
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
MX_SPI1_Init(); /* This configures master */
HAL_Delay(10);
sendHelloWorld();
configSlave(); /* Configures slave mode */
__HAL_SPI_ENABLE(&hspi1); /* Enabling the device in this mode generates a continous clock during master init */
HAL_Delay(100);
HAL_SPI_DeInit(&hspi1); /* Disables SPI and de-initializes the peripheral */
我的主配置:
hspi1.Instance = SPI1;
hspi1.Init.Mode = SPI_MODE_MASTER;
hspi1.Init.Direction = SPI_DIRECTION_2LINES;
hspi1.Init.DataSize = SPI_DATASIZE_8BIT;
hspi1.Init.CLKPolarity = SPI_POLARITY_LOW;
hspi1.Init.CLKPhase = SPI_PHASE_1EDGE;
hspi1.Init.NSS = SPI_NSS_SOFT;
hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_256;
hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB;
hspi1.Init.TIMode = SPI_TIMODE_DISABLE;
hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;
hspi1.Init.CRCPolynomial = 10;
if (HAL_SPI_Init(&hspi1) != HAL_OK)
Error_Handler();
我的奴隶配置:
if(HAL_SPI_DeInit(&hspi1) != HAL_ERROR)
/* SPI1 parameter configuration*/
hspi1.Instance = SPI1;
hspi1.Init.Mode = SPI_MODE_SLAVE;
hspi1.Init.Direction = SPI_DIRECTION_2LINES_RXONLY;
hspi1.Init.DataSize = SPI_DATASIZE_8BIT;
hspi1.Init.CLKPolarity = SPI_POLARITY_LOW;
hspi1.Init.CLKPhase = SPI_PHASE_1EDGE;
hspi1.Init.NSS = SPI_NSS_SOFT;
hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB;
hspi1.Init.TIMode = SPI_TIMODE_DISABLE;
hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;
hspi1.Init.CRCPolynomial = 10;
if (HAL_SPI_Init(&hspi1) != HAL_OK)
Error_Handler();
这是我的逻辑分析仪的波形。一旦我在启用 SPI 作为从设备后运行函数 MX_SPI1_Init() ,就会生成时钟。橙色是时钟,如您所见 - 从 10 毫秒延迟开始 - 它在初始化为主机后立即启用。
有什么想法吗?我一直在与这个问题作斗争一个多星期,并尝试了很多方法
【问题讨论】:
【参考方案1】:可能是垃圾 HAL 功能意外临时更改为 master rx-only。各种 HAL 函数按照它们写入寄存器的顺序是幼稚的,并且会产生这样的故障。在重新配置之前尝试调用HAL_SPI_DeInit
。或者干脆完全放弃 HAL。
Master RX-only 总是必须盲目地输出时钟。如果您想控制何时发送时钟,请使用主 tx 和 rx 模式,然后写入您想要读取的相同数量的虚拟数据。如果您希望 MOSI 保持三态而不发送虚拟数据,那么您可以在执行此操作时将引脚更改为 GPIO 模式。
【讨论】:
是的。 HAL 一直很痛苦,我很可能不得不创建自己的实现,但是,我认为事先试验 HAL 会更容易。 ST社区有人告诉我永远不要禁用SPI(SPE reg),只需更改主/从配置。这解决了它,但我认为这不应该是正确的方法。 如果这解决了您的问题,您能否接受左侧带有绿色勾号的答案?谢谢。以上是关于STM32F4在半双工/单工模式下停用SPI的正确方法的主要内容,如果未能解决你的问题,请参考以下文章