cancel
Showing results for 
Search instead for 
Did you mean: 

STM32L476VE SPI HALF-DUPLEX MASTER MODE: UNABLE TO RECEIVE DATA

ARigo.1
Associate

Good Morning,

I encountered a problem concerning the SPI peripheral. When it is configured in half-duplex master mode, I'm able to transmit data but not to receive them.

Here's the inizialitazion code for SPI peripheral (auto-generated with MX Cube):

/* SPI1 init function */

void MX_SPI1_Init(void)

{

  hspi1.Instance = SPI1;

  hspi1.Init.Mode = SPI_MODE_MASTER;

  hspi1.Init.Direction = SPI_DIRECTION_1LINE;

  hspi1.Init.DataSize = SPI_DATASIZE_8BIT;

  hspi1.Init.CLKPolarity = SPI_POLARITY_HIGH;

  hspi1.Init.CLKPhase = SPI_PHASE_2EDGE;

  hspi1.Init.NSS = SPI_NSS_SOFT;

  hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_16;

  hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB;

  hspi1.Init.TIMode = SPI_TIMODE_DISABLE;

  hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;

  hspi1.Init.CRCPolynomial = 7;

  hspi1.Init.CRCLength = SPI_CRC_LENGTH_DATASIZE;

  hspi1.Init.NSSPMode = SPI_NSS_PULSE_DISABLE;

  if (HAL_SPI_Init(&hspi1) != HAL_OK)

  {

   Error_Handler();

  }

}

void HAL_SPI_MspInit(SPI_HandleTypeDef* spiHandle)

{

  GPIO_InitTypeDef GPIO_InitStruct = {0};

  if(spiHandle->Instance==SPI1)

  {

  /* USER CODE BEGIN SPI1_MspInit 0 */

  /* USER CODE END SPI1_MspInit 0 */

   /* SPI1 clock enable */

   __HAL_RCC_SPI1_CLK_ENABLE();

  

   __HAL_RCC_GPIOE_CLK_ENABLE();

   /**SPI1 GPIO Configuration   

   PE13   ------> SPI1_SCK

   PE15   ------> SPI1_MOSI 

   */

   GPIO_InitStruct.Pin = GPIO_PIN_13|GPIO_PIN_15;

   GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;

   GPIO_InitStruct.Pull = GPIO_NOPULL;

   GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;

   GPIO_InitStruct.Alternate = GPIO_AF5_SPI1;

   HAL_GPIO_Init(GPIOE, &GPIO_InitStruct);

  /* USER CODE BEGIN SPI1_MspInit 1 */

  /* USER CODE END SPI1_MspInit 1 */

  }

}

Here are the TX/RX functions:

/**

 * @brief Transmit data to SPI bus

 * @param spi_id: spi bus identifier

 * @param txData: pointer to transmission buffer of bytes to write on MOSI line

 * @param txDataSize: tx buffer length in bytes

 * @retval None

 */

void SPI_Transmit(spi_id_t spi_id, uint8_t *txData, uint16_t txDataSize)

{

SPI_HandleTypeDef *hspi;

GPIO_Port_Pin_t chipSelect;

switch (spi_id)

{

case SPI1_ID:

hspi = &hspi1;

chipSelect = SPI1_CS;

break;

case SPI2_ID:

hspi = &hspi2;

chipSelect = SPI2_CS;

break;

case SPI3_ID:

break;

default:

break;

}

/* Select slave */

GPIO_Reset(chipSelect);

if (HAL_SPI_Transmit(hspi, txData, txDataSize, TIMEOUT_100MS) != HAL_OK)

{

Error_Handler();

}

/* Deselect slave */

GPIO_Set(chipSelect);

}

/**

 * @brief Receive data on SPI bus

 * @param spi_id: spi bus identifier

 * @param txData: pointer to transmission buffer of bytes to write on MOSI line (e.g. register from which data are meant to be read)

 * @param txDataSize: tx buffer length in bytes

 * @param rxData: pointer to receive buffer where to put read data

 * @param rxDataSize: rx buffer length in bytes

 * @retval None

 */

void SPI_Receive(spi_id_t spi_id, uint8_t *txData, uint16_t txDataSize, uint8_t *rxData, uint16_t rxDataSize)

{

SPI_HandleTypeDef *hspi;

GPIO_Port_Pin_t chipSelect;

switch (spi_id)

{

case SPI1_ID:

hspi = &hspi1;

chipSelect = SPI1_CS;

break;

case SPI2_ID:

hspi = &hspi2;

chipSelect = SPI2_CS;

break;

case SPI3_ID:

break;

default:

break;

}

/* Select slave */

GPIO_Reset(chipSelect);

if (HAL_SPI_Transmit(hspi, txData, txDataSize, TIMEOUT_100MS) != HAL_OK)

{

Error_Handler();

}

if (HAL_SPI_Receive(hspi, rxData, rxDataSize, TIMEOUT_100MS) != HAL_OK)

{

Error_Handler();

}

/* Deselect slave */

GPIO_Set(chipSelect);

}

  • When I call the TX function SPI_Transmit(), data are correctly transmitted on the MOSI line
  • When I call the RX function SPI_Receive(), at first it is executed correctly ( HAL_SPI_Transmit() function correctly transmits the first part of the data, from MASTER to SLAVE ), but then a HAL_TIMEOUT ERROR is generated inside HAL_SPI_Receive() when data are meant to be transmitted from SLAVE to MASTER; I checked the SCL line and MASTER does not generate the CLOCK signal for receiving data

I thought of solving the problem by means of using FULL-DUPLEX MASTER mode and connecting MOSI and MISO lines togheter, but I'm afraid of possible short circuits when the SLAVE is writing data (I don't know if the MOSI line is in high impedance state or if it is forcing the line HIGH/LOW).

What might be the cause?

Thank you so much. Kind regards.

0 REPLIES 0