1. 程式人生 > >兩片STM32使用HAL完成SPI全雙工主從通訊

兩片STM32使用HAL完成SPI全雙工主從通訊

SPI是一種非常簡單易用的全雙工主從式通訊協議。

本文使用兩片STM32F429,一個作為主機,一個作為從機完成SPI的全雙工通訊測試。

在STM32的HAL庫中簡化了SPI主機端的傳送接收,但是HAL庫沒有提供一個簡單的SPI從機程式碼介面,這樣就需要自己拼接介面來完成全雙工的通訊。以下都以實現全雙工通訊為目的進行配置和編寫:

主機端:

禁止使用SPI的硬體片選訊號,因為這個訊號是SPI使能了之後就一直為低,直到禁止了SPI之後才為高。可以使用某一個普通IO來充當片選訊號。

這裡選用一個較低的速率來通訊,在HAL庫的spi標頭檔案中有說明各個模式下SPI的最大速度。

從機端:

主從的速率要一樣,從機開啟SPI中斷

硬體連線:

主機                        從機

CS                          CS

CLK                        CLK

MISO                      MISO

MOSI                      MOSI

接收和傳送都是直連不需要交叉。

主機程式碼:

  /* USER CODE BEGIN 3 */
		HAL_GPIO_WritePin(SPI1_NSS_GPIO_Port, SPI1_NSS_Pin, GPIO_PIN_RESET);
		
		HAL_SPI_TransmitReceive(&hspi1, txbuf, rxbuf, 1, 0xFF);
		HAL_GPIO_WritePin(SPI1_NSS_GPIO_Port, SPI1_NSS_Pin, GPIO_PIN_SET);
		HAL_Delay(500);
  }
  /* USER CODE END 3 */

從機程式碼:

現在while之前開啟spi接收中斷:

  /* USER CODE BEGIN 2 */
	HAL_SPI_Receive_IT(&hspi1, rxbuf, 1);
  /* USER CODE END 2 */

在中斷中使用阻塞函式把資料傳送出去:

/* USER CODE BEGIN 4 */
void HAL_SPI_RxCpltCallback(SPI_HandleTypeDef *hspi)
{
	if (hspi == &hspi1)
	{
		HAL_SPI_Transmit(&hspi1, txbuf, 1, 0xFFFF);
		HAL_SPI_Receive_IT(&hspi1, rxbuf, 1);
	}
}
/* USER CODE END 4 */

使用邏輯分析儀可以看到主機在傳送的同時也收到了從機返回的資料。

可能在中斷裡呼叫阻塞傳送不是很好,如果有更好的方法歡迎指正。

另外在一片stm32上使用兩個SPI介面模擬主從機通訊好像不能正常工作。