I'm trying to write an SPI driver using the stm32 LL libraries (for the STML4 system). I'm testing the SPI driver by writing 2 bytes to the MOSI line and listen for 1 byte on the MISO line. Using an oscilloscope I was able to verify the 2 bytes were correctly transmitted and the SPI slave device responds with a byte. See attached screenshot:
In the image, I am probing the SCLK and MISO lines. Clearly, the last 8 bits on the MISO line is 0b01110011 which is the expected data. The driver I wrote does not reflect this and is always reading a 0 from the SPI DR register. I'm having issues trying to run the code in debug mode due to the SPI peripheral (maybe I'm missing something) and can't output values using printf (don't have access to a UART interface). I was hoping for some ideas on what issues there could be.
void spi_transmit_receive( SPI_TypeDef* spi, uint8_t* tx, uint8_t* rx, uint16_t size )
{
if( !LL_SPI_IsEnabled( spi ) )
{
LL_SPI_Enable( spi );
}
if( size > 1 )
{
LL_SPI_SetRxFIFOThreshold( spi, LL_SPI_RX_FIFO_HALF_FULL );
}
else
{
LL_SPI_SetRxFIFOThreshold( spi, LL_SPI_RX_FIFO_QUARTER_FULL );
}
uint8_t* rx_ptr = rx;
uint8_t* tx_ptr = tx;
uint16_t tx_count = size;
uint16_t rx_count = size;
while( tx_count > 0 || rx_count > 0 )
{
if( tx_count > 0 && LL_SPI_IsActiveFlag_TXE( spi ) )
{
if( tx_count > 1 )
{
LL_SPI_TransmitData16( spi, *((uint16_t*)tx_ptr) );
tx_ptr += sizeof( uint16_t );
tx_count -= 2;
}
else
{
LL_SPI_TransmitData8( spi, *tx_ptr );
tx_count -= 1;
}
}
if( rx_count > 0 && LL_SPI_IsActiveFlag_RXNE( spi ) )
{
if( rx_count > 1 )
{
*((uint16_t*)rx_ptr) = LL_SPI_ReceiveData16( spi );
rx_ptr += sizeof( uint16_t );
rx_count -= 2;
if( rx_count <= 1 )
{
// Switch to 8 bit mode for last 8 bits
LL_SPI_SetRxFIFOThreshold( spi, LL_SPI_RX_FIFO_QUARTER_FULL );
}
}
else
{
*rx_ptr = LL_SPI_ReceiveData8( spi );
//rx_ptr += sizeof(uint8_t);
rx_count -= 1;
}
}
}
while( LL_SPI_IsActiveFlag_BSY( spi ) ) {}
LL_SPI_Disable( spi );
}