cancel
Showing results for 
Search instead for 
Did you mean: 

My SPI clock produce 16bit rather than 8bit

WM_IR
Senior

I have a problem where my SPI clock produce 16bit, where I already set it to 8bit. I am not using any HAL driver, but I am learning from online course to develop my own driver from scratch.

I have a problem at SPI master slave.

The program is like this:

1. nucleo(master) will send 0x50 to arduino(slave)

2. when arduino received the 0x50, It will send back 0xF5 to nucleo.

I check the arduino code, it does transmit the 0xF5, just I dont know why the MISO just echoing back what MOSI has sent.

Example: MOSI sent 0x50, then MISO just send back 0x50. In this case, the master can send the data to the slave, and the slave can receive. Just the slave cannot send data to master.

Why my MISO line reflects back what the MOSI sent? It should send other data. Below is the result from my logic analyzer

0693W00000900cfQAA.jpg 

Then, below is my SPI send data code:

void SPI_SendData(SPI_RegDef_t *pSPIx, uint8_t *pTxBuffer, uint32_t Len)

{   

  while(Len > 0)

  {

  

   while(SPI_GetFlagStatus(pSPIx, SPI_TXE_FLAG) == FLAG_RESET);

   if(pSPIx->CR1 & (1 << SPI_CR1_CRCL))

   {

   //1. Load the data into Data Register(DR)

   pSPIx->DR = *((uint16_t*)pTxBuffer);

   //2. decrease len

   Len--;

   Len--; 

   //3.increment pTxBuffer in order to make it point to next data item

   (uint16_t*)pTxBuffer++; 

   }

   else

   {

   //8 bit data frame format

   //1. Load the data into Data Register(DR)

   pSPIx->DR = *pTxBuffer;  

   //2.kene decrease len

   Len--; 

   //3.increment pTxBuffer in order to make it point to next data item

   pTxBuffer++;

   }

  }

Anyone can help me on this issue?

1 ACCEPTED SOLUTION

Accepted Solutions

You need to be doing an 8-bit wide write to the SPI->DR register, the bus senses the width of the operation

ie *((volatile uint8_t *)&pSPIx->DR) = *pTxBuffer; 

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..

View solution in original post

3 REPLIES 3

You need to be doing an 8-bit wide write to the SPI->DR register, the bus senses the width of the operation

ie *((volatile uint8_t *)&pSPIx->DR) = *pTxBuffer; 

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
WM_IR
Senior

great! It works! but my code is halt at SPI want to receive dummy bits to clear the RXNE

Here is my SPI_receive code:

void SPI_ReceiveData(SPI_RegDef_t *pSPIx, uint8_t *pRxBuffer, uint32_t Len)

{

while(Len > 0)

  {

   //1. wait until RXNE is SET

   while(SPI_GetFlagStatus(pSPIx, SPI_RXNE_FLAG) == FLAG_RESET);

   //2. lepas TXE set, check dff or CRCL

   if(pSPIx->CR1 & (1 << SPI_CR1_CRCL))

   {

   //16 bit data frame format

   //1. load the data from Data Register(DR) to Rx Buffer address

   *((uint16_t*)pRxBuffer) = pSPIx->DR ; //this load 2 bytes of data DR into the RxBuffer

   //2. decrease len

   Len--;

   Len--;

   //3. pTxBuffer in order to make it point to next data item into other free memory address

   (uint16_t*)pRxBuffer++;

   }

   else

   {

   //8 bit data frame format

   //1. Load the data into Data Register(DR)

   *(pRxBuffer) = *((volatile uint8_t *)&pSPIx->DR);

   //2. decrease len

   Len--;

   //3. increment pTxBuffer in order to make it point to next data item

   pRxBuffer++;

   }

  }

}

WM_IR
Senior

is my code to load the data into Data Register (DR) is wrong?