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

nRF52 receiving data from 24L01 incorrectly

Hi,

I am using a 24L01+(as PTX) communicating with a nrf52832(as PRX).

I can have these two device communicating, where nrf52832 can receive data from 24L01+.

However, the data nrf52832 received is not the exactly same as the data 24L01+ has transmitted. For example, the 24L01+ is transmitting a 3-byte data(e.g. 0x123456) to nRF52832, while the data nRF52832 received is 0x2468AC. As you can see, 0x2468AC = 0x123456 <- 1. However, in another test, the 24L01+ transmitted 0x676767, while the nRF52832 received 0xCECECF.

Any suggestion would be appreciated. 

Best regards!

Parents
  • ESB packet format is byte sized. Except data control, just before the payload : It uses 9 bits. One bit more than a byte. Coincidentally you are one bit shifted.

    Problem : It is Softdevice who build the ESB packet. Not the SDK lib. The SDK lib just send 2 complete bytes (payload size as one byte, and packet id + noAck as separed byte, then not 9 bits compliant suggesting a conversion by Softdevice) and payload to Softdevice. With no source code, you can not check or modify Softdevice behavior. The only interact is registers modifications.

    Not a solution, but may helps you.

  • nRF52 using SoftDevice to transmit ESB packet? In the test, I didn't download the SoftDevice to the module. 

    If I should modify the registers, what registers should I need to do with? I look for it at the production specification of nRF52832, but it seems that it has no related registers about ESB, but it does have some about radio.

    Maybe I should modify these radio register, right? I am a little confused.

    Thanks.

  • Your are true. I am false. ESB does not need Softdevice. It is not Softdevice registers, but CPU registers.

    Nordic proprietary protocols
     Example applications that show how to use Gazell and Enhanced ShockBurst (ESB) proprietary protocols.
     These examples do not require a SoftDevice.
    And it is a good new for me. Because i am in pain with ESB too. And I try to solve an other problem. It means that my problem comes from me, or SDK. Not Softdevice. So i can solve by myself !

    But my remark about packet sizing was correct. With ESB regular packet, you have one bit more than byte sized. While ShockBurst is byte sized. I think the only setting for selecting ESB on nRF24L01 is EN_AA. You disable it on your example. And nrf_esb SDK manage only ESB protocol. Not Shockburst.

    Registers used by ESB SDK are : 

    NRF_RADIO->MODECNF0
    NRF_RADIO->PCNF0
    NRF_RADIO->PCNF1
    NRF_RADIO->BASE0
    NRF_RADIO->BASE1
    NRF_RADIO->PREFIX0
    NRF_RADIO->PREFIX1
    NRF_RADIO->TXPOWER
    NRF_RADIO->MODE
    NRF_RADIO->CRCINIT
    NRF_RADIO->CRCPOLY
    NRF_RADIO->CRCCNF
    NRF_ESB_SYS_TIMER->PRESCALER
    NRF_ESB_SYS_TIMER->BITMODE
    NRF_ESB_SYS_TIMER->SHORTS
    NRF_ESB_SYS_TIMER->TASKS_CLEAR
    NRF_ESB_SYS_TIMER->CC[]
    NRF_ESB_SYS_TIMER->EVENTS_COMPARE[]
    NRF_ESB_SYS_TIMER->TASKS_STOP
    NRF_PPI->CH[].EEP
    NRF_PPI->CH[].TEP
    NRF_PPI->CHENSET
    NRF_RADIO->SHORTS
    NRF_RADIO->INTENSET
    NRF_RADIO->TXADDRESS
    NRF_RADIO->RXADDRESSES
    NRF_RADIO->FREQUENCY
    NRF_RADIO->PACKETPTR
    NRF_RADIO->EVENTS_ADDRESS
    NRF_RADIO->EVENTS_PAYLOAD
    NRF_RADIO->EVENTS_DISABLED
    NRF_RADIO->TASKS_TXEN
    NRF_RADIO->TASKS_RXEN
    NRF_RADIO->PACKETPTR
    .. etc ...

    ... a lot ... Take a look at nRF5_SDK_15.0.0\components\proprietary_rf\esb\nrf_esb.c file. It may helps you.

    I suspect your config, as API config, generate a misconfig (or incompatible with you nRF24L01 setup) config by registers (SDK job). But what register ? I don't know. And i don't know if you can setup a ShockBurst mode by registers (without SDK).

    I will try your setup. Please tell me your TX_ADDRESS, TX_ADR_WIDTH. And I notice you did not setup payload size on nRF24L01 side (PW_P0).

  • I test same config as you. Only address and channel is my own.

    Good news ... I send 0x123456 from nRF24 ... and i receive 0x2468AC to nRF52 !!! Like you. So it is just a SDK register settings problem (or nRF24 incompatible config). Time to lunch. I will make some modifications afternoon.

  • I receive 0x2468AD, but it is inconstant. I receive only one packet, for three or four sending (low power, and no packet reprtition).
    The radio event register for RX receiving is NRF_RADIO->EVENTS_DISABLED, and NRF_RADIO->INTENSET & RADIO_INTENSET_DISABLED_Msk (I know, the name did not help to found ...). Current received datas are on NRF_RADIO->PACKETPTR register.
    The auto-ack behavior is coded on SDK. Then, sometimes CPU call a function who read payload for ack checking, other times CPU call function that store payload on a custom specific FIFO (defined inside the same API).
    You can found the code that manage new received packet at "on_radio_disabled_rx" function. And 'rx_fifo_push_rfbuf(NRF_RADIO->RXMATCH, p_pipe_info->pid);' decode new received buffer.
    I can see some problems :
    - As configured, nRF52 manage ACK. But your nRF24 setup don't care about ACK. It is not your problem for now, but it can be if you don't manage ACK by your own on nRF24 side.
    Strangely, the SDK test is : 

    if ((m_config_local.selective_auto_ack == false) || ((m_rx_payload_buffer[1] & 0x01) == 1))
    ack = true;

    That says if no_ack packet flag is true, then manage ACK. Strange ... I notice some no_ack bit inversions pretty much everywhere on ESB SDK. And it is difficult to understand when all are named 'no_ack'. Maybe it works with nRF52 ... luckily.
    But don't comply with nRF24L01 datasheet : "Setting the flag high tells the receiver that the packet is not to be auto acknowledged.". Unless if nRF52 CPU invert it internaly ...
    - What happens if I use CRC16 ? Same result. I receive 0x2468AD, but very few.
    - If I enable ESB on nRF24, or dynamic payload (because enabling dynamic payload RF24_DYNPD enable automaticaly ESB), I receive nothig.
    - If I send 0xF23456, I receive 0xE468AD. No CRC error. Payload is 1 shifted and 1 added.
    - Function rx_fifo_push_rfbuf decode payload buffer as :
    1 byte : payload size
    1 byte : packet id + packet no_ack flag
    n bytes : payload
    Problem : You setup nRF24 as ShockBurst, not ESB. So normaly, sent packet miss 9 bits of data control, just before the payload.
    How on earth the nRF52 CPU receive the right payload with only 1 bit shifted, while it miss 9 bits ???
    How on earth the nRF52 CPU check CRC8 and accept the packet with improper data, improper format and improper packet size ?
    I think that data control still present. Despite configuration.
    "CRC is calculated over the address, PacketControl Field and Payload" (datasheet).
    Conclusion :
    On-air packet is conform to nRF52 setup, because CRC check is ok. But, strangely, NRF_RADIO->PACKETPTR contains a shifted payload, while payload was correct at CRC check.
    If anybody know how nRF52 manage payload on this process, it can help to find registers configuration problem. Page 205 of nRF52832 datasheet, this process is called "packet disassembler".

Reply
  • I receive 0x2468AD, but it is inconstant. I receive only one packet, for three or four sending (low power, and no packet reprtition).
    The radio event register for RX receiving is NRF_RADIO->EVENTS_DISABLED, and NRF_RADIO->INTENSET & RADIO_INTENSET_DISABLED_Msk (I know, the name did not help to found ...). Current received datas are on NRF_RADIO->PACKETPTR register.
    The auto-ack behavior is coded on SDK. Then, sometimes CPU call a function who read payload for ack checking, other times CPU call function that store payload on a custom specific FIFO (defined inside the same API).
    You can found the code that manage new received packet at "on_radio_disabled_rx" function. And 'rx_fifo_push_rfbuf(NRF_RADIO->RXMATCH, p_pipe_info->pid);' decode new received buffer.
    I can see some problems :
    - As configured, nRF52 manage ACK. But your nRF24 setup don't care about ACK. It is not your problem for now, but it can be if you don't manage ACK by your own on nRF24 side.
    Strangely, the SDK test is : 

    if ((m_config_local.selective_auto_ack == false) || ((m_rx_payload_buffer[1] & 0x01) == 1))
    ack = true;

    That says if no_ack packet flag is true, then manage ACK. Strange ... I notice some no_ack bit inversions pretty much everywhere on ESB SDK. And it is difficult to understand when all are named 'no_ack'. Maybe it works with nRF52 ... luckily.
    But don't comply with nRF24L01 datasheet : "Setting the flag high tells the receiver that the packet is not to be auto acknowledged.". Unless if nRF52 CPU invert it internaly ...
    - What happens if I use CRC16 ? Same result. I receive 0x2468AD, but very few.
    - If I enable ESB on nRF24, or dynamic payload (because enabling dynamic payload RF24_DYNPD enable automaticaly ESB), I receive nothig.
    - If I send 0xF23456, I receive 0xE468AD. No CRC error. Payload is 1 shifted and 1 added.
    - Function rx_fifo_push_rfbuf decode payload buffer as :
    1 byte : payload size
    1 byte : packet id + packet no_ack flag
    n bytes : payload
    Problem : You setup nRF24 as ShockBurst, not ESB. So normaly, sent packet miss 9 bits of data control, just before the payload.
    How on earth the nRF52 CPU receive the right payload with only 1 bit shifted, while it miss 9 bits ???
    How on earth the nRF52 CPU check CRC8 and accept the packet with improper data, improper format and improper packet size ?
    I think that data control still present. Despite configuration.
    "CRC is calculated over the address, PacketControl Field and Payload" (datasheet).
    Conclusion :
    On-air packet is conform to nRF52 setup, because CRC check is ok. But, strangely, NRF_RADIO->PACKETPTR contains a shifted payload, while payload was correct at CRC check.
    If anybody know how nRF52 manage payload on this process, it can help to find registers configuration problem. Page 205 of nRF52832 datasheet, this process is called "packet disassembler".

Children
  • Some news ...
    My problem is the opposite. I want to use nrf52 as TX and nrf24 as RX. Of course, it does not work. I found no complete setup or example on the web. Only incomplete, bugged files, only nrf24 side or only nrf52 side.
    But after looking to my and your problems, and spending hours on datasheet and nrf_esb, I am conviced that I can make ESB by my own without NRF SDK. I will save time, after loosing a lot !
    Not the first time ... I spend days to try to use v13 nrf_log, app_uart, nrf_drv_uart, nrf_serial, ... now I know they are rubish ! For each lib, conclusion is the same : bad design, not API level, bugged, too complicated (risky), poor performances, too immature for some nrfx.
    If we needs to learn datasheet and analyse SDK code for each lib, and it's interfaces changes quicker than the hardware, what are these libs ?
    Among libs I try, only BLE libs works without major problems. Fortunately ! Maybe NRF SDK is good for complicated features only.

    So I handle radio IRQ by my own now, and I can get raw data. With your setup, I get :

    NRF_RADIO->CRCSTATUS=1
    NRF_RADIO->RXMATCH=0
    NRF_RADIO->RXCRC=0xFE
    NRF_RADIO->PCNF0 = 0x00010100 = 0000 0000 0000 0001 0000 0001 0000 0000 : S0LEN=1, S1LEN=1
    NRF_RADIO->PCNF1 = 0x01030606 = 0000 0001 0000 0011 0000 0110 0000 0110
    NRF_RADIO->PACKETPTR=0xFF002468AC

    S0LEN + S1LEN = 9bits, as configured by SDK. That is correct. If I increase S1LEN to compensate shifting, CRC is rejected. So, the problem comes after CRC check, on packet disassembly.

    Conclusion : CRC is ok, but payload is not conform to CRC check and original message. As I say on last message, we need to know what appens on CPU "packet disassembler" process. Which register can interfer with this process (PCNF0, PCNF1, ...) ?
    How this process extract the 9 bits of data control, to make two bytes on PACKETPTR ?

    Additionally, with my own lib, I get complete and rigth packet for each nRF24 transmission. Unlike nrf_esb, that get only one RX for 3 or 4 TX (I don't know why, and I do not care now).

Related