cancel
Showing results for 
Search instead for 
Did you mean: 

How to use rfalNfcvPollerTransceiveReq() for custom commands (e.g. D2/D3/D4/D5)?

MERSI
Associate III

 

Hi all,

I’m using an ST25R3916 with RFAL on an STM32 and I’m trying to talk to an NXP NTAG 5 Boost (ISO15693/NFC-V) using its custom commands: READ/WRITE SRAM (0xD2/0xD3) and READ/WRITE I²C (0xD5/0xD4).

Plain ISO15693 commands work fine (e.g., ReadSingleBlock / WriteSingleBlock). For example, reading config block 0x37 returns:

 

 
REQ: flags 0x22, CMD 0x20, UID=<8 bytes>, DATA=0x37 RSP: 00 08 DB CF 00

 

 

Now I’d like to send the NXP customs via rfalNfcvPollerTransceiveReq(), but I’m not getting a response (often RFAL_ERR_TIMEOUT).


What I’m calling now

For customs I call rfalNfcvPollerTransceiveReq(cmd, flags, param, uid, payload, payloadLen, rx, rxLen, &rcvLen) like this:

  • flags: RFAL_NFCV_REQ_FLAG_DEFAULT (0x02, high data rate, no option bit)

  • param: 0x04 (NXP manufacturer code)

  • uid: 8-byte UID (addressed mode)

  • payload and length per the NTAG 5 Boost datasheet (see below)

  • rx: buffer big enough + checking rcvLen

Example (READ SRAM, command 0xD2:(

 

 
uint8_t tx[2] = { startBlock, (uint8_t)(numBlocks - 1) }; // request N blocks uint8_t rx[1 + 4*64] = {0}; // RES_FLAGS + data uint16_t rcv = 0; ReturnCode rc = rfalNfcvPollerTransceiveReq( 0xD2, // READ SRAM RFAL_NFCV_REQ_FLAG_DEFAULT, // 0x02 0x04, // NXP mfg code uid, // addressed mode tx, sizeof(tx), rx, sizeof(rx), &rcv );
 

Similarly for WRITE SRAM (0xD3) and I²C bridge (0xD4/0xD5).


Datasheet framing I’m following (READ/WRITE SRAM)

From the NTAG 5 Boost user manual (table looks like this):

READ SRAM (0xD2) request

  • Flags (8)

  • READ SRAM (8) = 0xD2

  • Manuf. code (8) = 0x04

  • UID (64, optional if addressed mode)

  • Block Address (8)

  • Number of Blocks (8) — value is N-1 (so 0x00 means 1 block)

  • CRC16

READ SRAM response (no error)

  • Flags (8)

  • (Number of Blocks + 1) × 32 bits Data

  • CRC16

WRITE SRAM (0xD3) request

  • Flags (8)

  • WRITE SRAM (8) = 0xD3

  • Manuf. code (8) = 0x04

  • UID (optional)

  • Block Address (8)

  • Number of Blocks (8) — N-1

  • Data = N × 4 bytes

  • CRC16

Only Option_flag = 0 is supported for D2/D3. Datasheet also says SRAM must be enabled and not protected.

My payload lengths follow that (READ: 2 bytes payload; WRITE: 2 + 4*N).


What works vs. what fails

  • :white_heavy_check_mark: ISO15693 ReadSingleBlock/WriteSingleBlock via rfalNfcvPollerReadSingleBlock() / ...WriteSingleBlock() → OK

  • :cross_mark: NXP custom 0xD2/0xD3/0xD4/0xD5 via rfalNfcvPollerTransceiveReq() as above → mostly RFAL_ERR_TIMEOUT


Questions

  1. param field in rfalNfcvPollerTransceiveReq
    For customs should I always pass 0x04 (NXP mfg code)? Or should param be skipped (RFAL_NFCV_PARAM_SKIP) and the mfg code embedded somewhere else?

  2. Flags / Addressed mode
    Is RFAL_NFCV_REQ_FLAG_DEFAULT (0x02) correct for D2/D3/D4/D5?
    Should I also set RFAL_NFCV_REQ_FLAG_ADDRESS myself, or does RFAL add it automatically when uid != NULL?

  3. Option flag
    READ/WRITE SRAM specify “Only Option_flag = 0b is supported”. I’m keeping Option=0. Is that correct with RFAL (i.e., don’t set RFAL_NFCV_REQ_FLAG_OPTION)?

  4. Buffer sizes / rcvLen
    Is there any RFAL limit/quirk for rxBuf lengths on customs I should be aware of?

If anyone has a minimal working call for Custom Commands (e.g. NTAG 5 Boost 0xD2/0xD3) using rfalNfcvPollerTransceiveReq(), I’d really appreciate a short snippet showing the exact flags, param, and payload formatting.

Thanks!


MERSI_0-1755118326929.pngMERSI_1-1755118344726.png

 

0 REPLIES 0