Skip to main content
Mena Mourice
Associate
April 14, 2017
Solved

STM32F0 SPI Read and Write

  • April 14, 2017
  • 2 replies
  • 1537 views
Posted on April 14, 2017 at 14:44

i'm trying to communicate with NRF24L01 RFmodule, it seems that spi init. is ok , but when i'm trying to read for example theREG_RF_CH Registry (0x05) it should return the reset value (0x02) but that does not happen !! it return 0x00 for the first time then atthe second time i trying to read the same registry it return the correct value!! i assume that the RX FIFO store the value at first time then give me it in the second time !!

my code as below:

static void SPI1_Init(void){
 RCC->AHBENR |= RCC_AHBENR_GPIOAEN; /* Enable GPIOA clock */
 RCC->AHBENR |= RCC_AHBENR_GPIOBEN; /* Enable GPIOB clock */
 RCC->APB2ENR |= RCC_APB2ENR_SPI1EN; /* Enable SPI1 clock */
 
 /* Configure PA6 to MISO, PA7 to MOSI, PB3 to SCK */
 GPIOA->AFR[0] &= ~((15ul << 4* 6) | (15ul << 4* 7));
 GPIOA->AFR[0] |= (( 0ul << 4* 6) | ( 0ul << 4* 7));
 GPIOB->AFR[0] &= ~(15ul << 4* 3);
 GPIOB->AFR[0] |= ( 0ul << 4* 3);
 
 GPIOA->MODER &= ~(( 3ul << 2* 6) | ( 3ul << 2* 7));
 GPIOA->MODER |= (( 2ul << 2* 6) | ( 2ul << 2* 7));
 GPIOB->MODER &= ~( 3ul << 2* 3);
 GPIOB->MODER |= ( 2ul << 2* 3);
SPI1->CR1 = 0x00000000; /* Reset SPI1 CR1 Registry*/
 SPI1->CR1 = (( 0ul << 0) | /* CPHA=0 */
 ( 0ul << 1) | /* CPOL=0 */
 ( 1ul << 2) | /* MSTR=1 */
 ( 4ul << 3) | /* BR (fPCLK/32) ~= 1.5 Mbit/sec */
 ( 0ul << 7) | /* LSBFIRST */
 ( 0ul << 8) | /* SSI */
 ( 1ul << 9)); /* SSM */
 SPI1->CR2 = 0x00000000; /* Reset SPI1 CR2 Registry*/
 SPI1->CR2 |= (SPI_CR2_NSSP | SPI_CR2_DS_0 | SPI_CR2_DS_1 | SPI_CR2_DS_2 | SPI_CR2_FRXTH);
 SPI1->CRCPR = 0x0007;
 SPI1->CR1 |= SPI_CR1_SPE; /* Enable SPI1 */
}
uint8_t SPI1_WriteRead_byte (uint8_t wr) {
 uint8_t data=0;
 while ((SPI1->SR & SPI_SR_TXE) != SPI_SR_TXE);
 *(uint8_t *)&(SPI1->DR) = wr;
 data = SPI1->DR;
 return data;
}�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?

#spi #stm32-f0
This topic has been closed for replies.
Best answer by S.Ma
Posted on April 14, 2017 at 18:29

First, if it is byte communication, when reading, make sure it is an 8 bit read

before 

data = SPI1->DR;

after

 data = *(uint8_t *)&(SPI1->DR);

When the communication starts, the SPI is waiting to send data (TXE=1)... and at that time, there is nothing yet to read, until 8 SPI SCK clock pulses have been generated. Then RXNE = 1 and DR can be read.

Try to wait for RXNE flag before reading the received data.

If that works, then next step will be to wonder how not to pause the SPI clock between bytes...

2 replies

S.Ma
S.MaBest answer
Principal
April 14, 2017
Posted on April 14, 2017 at 18:29

First, if it is byte communication, when reading, make sure it is an 8 bit read

before 

data = SPI1->DR;

after

 data = *(uint8_t *)&(SPI1->DR);

When the communication starts, the SPI is waiting to send data (TXE=1)... and at that time, there is nothing yet to read, until 8 SPI SCK clock pulses have been generated. Then RXNE = 1 and DR can be read.

Try to wait for RXNE flag before reading the received data.

If that works, then next step will be to wonder how not to pause the SPI clock between bytes...

Mena Mourice
Associate
April 17, 2017
Posted on April 17, 2017 at 17:06

Thanks

Centauris.Alpha

for your Help, you are right, the correct code is:

uint8_t SPI1_WriteRead_byte (uint8_t wr) {

uint8_t data=0;

while ((SPI1->SR & SPI_SR_TXE) != SPI_SR_TXE);

*((__IO uint8_t *)&SPI1->DR) = wr;

while ((SPI1->SR & SPI_SR_BSY) == SPI_SR_BSY);

while ((SPI1->SR & SPI_SR_RXNE) != SPI_SR_RXNE);

data = *((__IO uint8_t *)&SPI1->DR);

return data;

}