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

SPIM: MOSI line not consistent with Tx data buffer

I am using the SPIM example in the nRF52840 SDK.  It uses SPI_INSTANCE 3.  I am doing a simple SPI Write of 2 bytes.

I get SS, SCK, working properly.  MOSI is transitioning but it is not related to anything in the Tx buffer.  I have tried both NRFX_SPIM_XFER_TRX and NRFX_SPIM_XFER_TX function calls.

Any help would be appreciated.

Below is an excerpt of some of the relevant code: 

m_tx_buf[0] = 0x55; /**< TX buffer. */
m_tx_buf[1] = 0xAA; /**< TX buffer. */
m_tx_buf[2] = 0x55; /**< TX buffer. */

m_rx_buf[0] = 0x11; /**< TX buffer. */
m_rx_buf[1] = 0x66; /**< TX buffer. */
m_rx_buf[2] = 0x11; /**< TX buffer. */

tx_length = 2; /**< Transfer length. */
rx_length = 0; /**< Transfer length. */

// nrfx_spim_xfer_desc_t xfer_desc_WREN = NRFX_SPIM_XFER_TX(m_tx_buf, tx_length);
nrfx_spim_xfer_desc_t xfer_desc_WREN = NRFX_SPIM_XFER_TRX(m_tx_buf, tx_length, m_rx_buf, rx_length);

----------------------------

nrfx_spim_config_t spi_config = NRFX_SPIM_DEFAULT_CONFIG;
spi_config.frequency = NRF_SPIM_FREQ_1M;
spi_config.ss_pin = NRFX_SPIM_SS_PIN;
spi_config.miso_pin = NRFX_SPIM_MISO_PIN;
spi_config.mosi_pin = NRFX_SPIM_MOSI_PIN;
spi_config.sck_pin = NRFX_SPIM_SCK_PIN;
spi_config.mode = NRF_SPIM_MODE_3; // clk normally high, rising edge
spi_config.bit_order = NRF_SPIM_BIT_ORDER_MSB_FIRST;
// spi_config.dcx_pin = NRFX_SPIM_DCX_PIN;
spi_config.use_hw_ss = true;
spi_config.ss_active_high = false;
APP_ERROR_CHECK(nrfx_spim_init(&spi, &spi_config, spim_event_handler, NULL));

----------------------------------

while (1)
{
     // Reset rx buffer and transfer done flag
     // memset(m_rx_buf, 0, rx_length);
    spi_xfer_done = false;

   APP_ERROR_CHECK(nrfx_spim_xfer(&spi, &xfer_desc_WREN, 0));

   while (!spi_xfer_done)
   {
      _   _WFE();
    }

}

  • Ok, thank you for your help.  I can now get MOSI to work the way your example does. In the process however I found that part of my problem is my understanding of the following function:

    nrfx_spim_xfer_desc_t xfer_desc = NRFX_SPIM_XFER_TRX(m_tx_buf, m_length1, m_rx_buf, m_length2);

    My expectation is that this function transmits the number of bytes defined by m_length1.  However both m_length1 and m_length2 have an affect on the number of transmitted bytes in different ways. I don't understand this.

    Also, if I just want to transmit, why do I need to define m_rx_buf?  And what function would I use if I just want to receive bytes?  

  • Hi,

    NRFX_SPIM_XFER_TRX() as the name suggests, sends and receives data.  m_length1 (tx_length) and m_length2 (rx_length) is therefore the size of the buffer that the data is sent from and where it's received respectively. If you only want to send data then the correct function to use would be NRFX_SPIM_XFER_TX(), and NRFX_SPIM_XFER_RX() if you only want to receive data.

    regards 

    Jared

  • Thank you for the clarification.  SPI memory devices need to be commanded to read from a specific address before it will output data.  So if the devices read command is 3 bytes, and then outputs data, your Rx buffer needs to be 3 bytes larger than the data you expect to read since your NRFX_SPIM_XFER_TRX() function starts clocking in data while it is still writing the read command.  This is not obvious and should be better documented.  However with your help I  have now figured it out.

    Thanks!  

Related