This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

SPI Communication Problems Concerning nRF52840

Now there is a project, nrf52840 uses SPI to communicate with other microcontrollers. Data is currently available, but it is suspected that each packet lacks a second byte. The corresponding modification of SPI mode eliminates the problem of SPI mode. Are there any other parameters that affect the results of the data?

SPI Communication Program Reference Sample Program (sdk15.0    examples\peripheral\spi\pca10040)

Parents Reply Children
  • All right. That's what I'm going to do. The day after tomorrow, I will connect the data source directly to the oscilloscope to monitor the data waveform, so that I can know where the problem is. Thank you for your reply.

  • HI Edvin,Now it turns out that the second byte data is missing when receiving data.

  • Can you test whether you will lose data when receiving data with SPI? The data received by SPI in my program is only 16 bytes, but the data transferred is actually 17 bytes. I lost the second byte data.

  • #define TEST_STRING "Nordic 1234567890123"
    static uint8_t       m_tx_buf[] = TEST_STRING;           /**< TX buffer. */
    static uint8_t       m_rx_buf[sizeof(TEST_STRING) + 1];    /**< RX buffer. */
    static const uint8_t m_length = sizeof(m_tx_buf);        /**< Transfer length. */
    
    static volatile bool spis_xfer_done; /**< Flag used to indicate that SPIS instance completed the transfer. */
    
    void spis_event_handler(nrf_drv_spis_event_t event)
    {
        static uint8_t MyString[DATA_BUFFER_SIZE];
        static uint8_t MyStringIndex = 0;
        int i, j;
        uint8_t *StartPointer, *NextPointer;
        if (event.evt_type == NRF_DRV_SPIS_XFER_DONE)
        {
            spis_xfer_done = true;
            if (MyStringIndex == DATA_BUFFER_SIZE)
             {
    //            NRF_LOG_INFO(" Transfer completed. Received: %d\n", MyStringIndex);
    
                //Find the first Data
                for (i = 0; i < DATA_BUFFER_SIZE; i ++)
                  if (MyString[i] == 0x80 || MyString[i] == 0x90 || MyString[i] == 0xa0)
                  break;
    
                if (i < DATA_BUFFER_SIZE)
                {
                  StartPointer = &MyString[i]; 
    
                while ((StartPointer != NULL) && (StartPointer < (&MyString[DATA_BUFFER_SIZE - 1])) && (StartPointer + 16 < (&MyString[DATA_BUFFER_SIZE - 1])) )
                {
                  NextPointer = StartPointer + 1;
                  //Find the ending of the data
                  for (j = 1; j < 16; j ++, NextPointer ++)
                  {
                    if (*NextPointer == 0x80 || *NextPointer == 0x90 || *NextPointer == 0xa0)
                    break;
                  }
    
                  //Show the data to RTT or UART
                  NRF_LOG_HEXDUMP_INFO(StartPointer, j);
                  StartPointer += j;
                }
    
                memset(MyString, 0, 100);
                MyStringIndex = 0;
              }
             }
             MyString[MyStringIndex] = m_rx_buf[0];
             MyStringIndex ++;
      }
    }
    
    int main(void)
    {
        // Enable the constant latency sub power mode to minimize the time it takes
        // for the SPIS peripheral to become active after the CSN line is asserted
        // (when the CPU is in sleep mode).
        NRF_POWER->TASKS_CONSTLAT = 1;
    
        bsp_board_init(BSP_INIT_LEDS);
     
        APP_ERROR_CHECK(NRF_LOG_INIT(NULL));
        NRF_LOG_DEFAULT_BACKENDS_INIT();
    
        NRF_LOG_INFO("SPIS example");
    
        nrf_drv_spis_config_t spis_config = NRF_DRV_SPIS_DEFAULT_CONFIG;
        spis_config.mode = NRF_SPIS_MODE_1;
        spis_config.csn_pin               = APP_SPIS_CS_PIN;
        spis_config.miso_pin              = APP_SPIS_MISO_PIN;
        spis_config.mosi_pin              = APP_SPIS_MOSI_PIN;
        spis_config.sck_pin               = APP_SPIS_SCK_PIN;
    
    
        APP_ERROR_CHECK(nrf_drv_spis_init(&spis, &spis_config, spis_event_handler));
    
        while (1)
        {
            spis_xfer_done = false;
    
            APP_ERROR_CHECK(nrf_drv_spis_buffers_set(&spis, m_tx_buf, 0, m_rx_buf, 20));
    
            while (!spis_xfer_done)
            {
                __WFE();
            }
    
            NRF_LOG_FLUSH();
    
    //        bsp_board_led_invert(BSP_BOARD_LED_0);
        }
    }

  • Try this driver instead.  it is much better and easier to use.  it has been used in many projects and hundreds of devices, sensors, flash memory, sd card...

    https://github.com/IOsonata/IOsonata/blob/master/ARM/Nordic/src/spi_nrf5x.cpp

    usage example

    https://github.com/IOsonata/IOsonata/blob/master/exemples/spi/spi_master_slave.cpp

Related