cancel
Showing results for 
Search instead for 
Did you mean: 

[STM32F10x] Problem with SPI first bit received from slave

dark_killer_1796
Associate II
Posted on April 22, 2015 at 23:49

Hi everyone, I am getting problem with my SPI first bit received from slave.

I have 2 boards as master and slave. The SPI is configured as 8 bit full duplex mode, soft NSS, receive interrupt at slave. Master will send a byte to slave and wait for the reply. Slave will get that byte from master (in interrupt routine) , and then sends back a byte. The problem is that when master sends first byte, slave receives succesfully and then it sends back a byte but master can't receive it. That just happped with the first byte, the next bytes after are correct. For example if my Slave_Tx_Buffer = {0x01, 0x02, 0x03,0x04, 0x05} , I can only receive the result 0,1,2,3,4. I think it was shifted right one byte. I don't know why. Thank you for your help. Master routines:

while (TxIdx < BufferSize)
{
/* Wait for SPI1 Tx buffer empty */
while (SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_TXE) == RESET);
/* Send SPI1 data */
SPI_I2S_SendData(SPI1, SPI1_Buffer_Tx[TxIdx++]); 
/* Wait for SPI1 data reception */
while (SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_RXNE) == RESET);
/* Read SPIy received data */
SPI1_Buffer_Rx[RxIdx++] = SPI_I2S_ReceiveData(SPI1);
}

Slave Interrupt

void SPI2_IRQHandler(void)
{
if (SPI_I2S_GetITStatus(SPI2, SPI_I2S_IT_RXNE) != RESET); 
{ 
/* Store SPI_SLAVE received data */
SPI2_Buffer_Rx[RxIdx++] = SPI_I2S_ReceiveData(SPI2);
/*Send data back to SPI1*/
SPI_I2S_SendData(SPI2, SPI2_Buffer_Tx[TxIdx++]); 
}
}

2 REPLIES 2
Posted on April 23, 2015 at 01:04

a) There is generally a one word/byte lag in responses from slave devices

b) One should read the DR prior to sending the initial byte so as to clear any hanging RXNE status.

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
dark_killer_1796
Associate II
Posted on April 23, 2015 at 01:50

Can you explain me this ? I read from ST Standard Peripheral. This code is for SPI Full Duplex , SPI1 is master, SPI2 is slave

while (TxIdx < BufferSize)
{
/* Wait for SPI1 Tx buffer empty */
while (SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_TXE) == RESET);
/* Send SPI2 data */
SPI_I2S_SendData(SPI2, SPIz_Buffer_Tx[TxIdx++]); //send slave first
/* Send SPI1 data */
SPI_I2S_SendData(SPI1, SPI1_Buffer_Tx[TxIdx]); //send master after
/* Wait for SPI2 data reception */
while (SPI_I2S_GetFlagStatus(SPI2, SPI_I2S_FLAG_RXNE) == RESET);
/* Read SPI2 received data */
SPI2_Buffer_Rx[RxIdx] = SPI_I2S_ReceiveData(SPI2);
/* Wait for SPI1 data reception */
while (SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_RXNE) == RESET);
/* Read SPI1 received data */
SPI1_Buffer_Rx[RxIdx] = SPI_I2S_ReceiveData(SPI1);
}

As I see in that code, after wait for TXE =1, write the slave data first, after that write the master data after. Everything goes right (I tested). But if I change to write the master data first, then the slave data after like this

/* Wait for SPI1 Tx buffer empty */
while (SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_TXE) == RESET);
/* Send SPI1 data */
SPI_I2S_SendData(SPI1, SPI1_Buffer_Tx[TxIdx]); //send master first
/* Send SPI2 data */
SPI_I2S_SendData(SPI2, SPI2_Buffer_Tx[TxIdx++]); //send slave after

the error happened with first byte. The slave receive data is correct {data1, data2, data3...} but the master receive data is shifted right one byte. { 0, data1, data2, data3..} I can't explain why. Can you give me some idea ?