X_NUCLEO_NFC02A1 library for M24LR

Dependencies:   ST_INTERFACES

Dependents:   HelloWorld_NFC02A1_mbedOS HelloWorld_NFC02A1laatste HelloWorld_NFC02A1

Fork of X_NUCLEO_NFC02A1 by ST Expansion SW Team

X-NUCLEO-NFC02A1 Dynamic NFC Tag Expansion Board Firmware Package

Introduction

This firmware package includes Components Device Drivers, Board Support Package and example applications for STMicroelectronics X-NUCLEO-NFC02A1 Dynamic NFC Tag Expansion Board based on M24LR.

Firmware Library

Class X_NUCLEO_NFC02A1 is intended to represent the Dynamic NFC Tag Expansion Board with the same name.
It provides an API to access to the M24LR component and to the three onboard LEDs.
It is intentionally implemented as a singleton because only one X_NUCLEO_NFC02A1 at a time might be deployed in a HW component stack.
The library also provides an implementation of the NDEF library API for M24LR, providing an simple way to read/write NDEF formatted messages from/to the M24LR dynamic NFC tag.

Example application

Hello World is a simple application to program and read an URI from the NFC tag.

Committer:
Davidroid
Date:
Wed Jul 12 12:34:12 2017 +0000
Revision:
8:7c4cf671960b
Parent:
6:8c1eca41b3a9
Updated to fit ARM mbed coding style.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
rosarium 0:71bff5ad0a49 1 /**
rosarium 0:71bff5ad0a49 2 ******************************************************************************
rosarium 0:71bff5ad0a49 3 * @file NdefNfcTagM24LR.cpp
rosarium 0:71bff5ad0a49 4 * @author AMG Central Lab
giovannivisentini 6:8c1eca41b3a9 5 * @version V2.0.0
giovannivisentini 6:8c1eca41b3a9 6 * @date 19 May 2017
rosarium 0:71bff5ad0a49 7 * @brief Wrapper class of the NDefLib library to write/read NDEF messages.
rosarium 0:71bff5ad0a49 8 ******************************************************************************
rosarium 0:71bff5ad0a49 9 * @attention
rosarium 0:71bff5ad0a49 10 *
rosarium 0:71bff5ad0a49 11 * <h2><center>&copy; COPYRIGHT(c) 2016 STMicroelectronics</center></h2>
rosarium 0:71bff5ad0a49 12 *
rosarium 0:71bff5ad0a49 13 * Redistribution and use in source and binary forms, with or without modification,
rosarium 0:71bff5ad0a49 14 * are permitted provided that the following conditions are met:
rosarium 0:71bff5ad0a49 15 * 1. Redistributions of source code must retain the above copyright notice,
rosarium 0:71bff5ad0a49 16 * this list of conditions and the following disclaimer.
rosarium 0:71bff5ad0a49 17 * 2. Redistributions in binary form must reproduce the above copyright notice,
rosarium 0:71bff5ad0a49 18 * this list of conditions and the following disclaimer in the documentation
rosarium 0:71bff5ad0a49 19 * and/or other materials provided with the distribution.
rosarium 0:71bff5ad0a49 20 * 3. Neither the name of STMicroelectronics nor the names of its contributors
rosarium 0:71bff5ad0a49 21 * may be used to endorse or promote products derived from this software
rosarium 0:71bff5ad0a49 22 * without specific prior written permission.
rosarium 0:71bff5ad0a49 23 *
rosarium 0:71bff5ad0a49 24 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
rosarium 0:71bff5ad0a49 25 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
rosarium 0:71bff5ad0a49 26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
rosarium 0:71bff5ad0a49 27 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
rosarium 0:71bff5ad0a49 28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
rosarium 0:71bff5ad0a49 29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
rosarium 0:71bff5ad0a49 30 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
rosarium 0:71bff5ad0a49 31 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
rosarium 0:71bff5ad0a49 32 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
rosarium 0:71bff5ad0a49 33 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
rosarium 0:71bff5ad0a49 34 *
rosarium 0:71bff5ad0a49 35 ******************************************************************************
rosarium 0:71bff5ad0a49 36 */
rosarium 0:71bff5ad0a49 37
rosarium 0:71bff5ad0a49 38
rosarium 0:71bff5ad0a49 39 #include <cmath>
rosarium 0:71bff5ad0a49 40 #include "NDefNfcTagM24LR.h"
rosarium 0:71bff5ad0a49 41
rosarium 0:71bff5ad0a49 42
rosarium 0:71bff5ad0a49 43 /* wait 1sec, driver is configured to let 200ms for command to complete */
rosarium 0:71bff5ad0a49 44 /* which is enough for all commands except GetSession if RF session is already opened */
rosarium 0:71bff5ad0a49 45 /* Smartphone generally releases the session within the second, anyway the user can modify this value */
rosarium 0:71bff5ad0a49 46 #define OPENSESSION_NTRIALS 5
rosarium 0:71bff5ad0a49 47
rosarium 0:71bff5ad0a49 48 #define CC_FILE_LENGTH_BYTE 15
rosarium 0:71bff5ad0a49 49
rosarium 0:71bff5ad0a49 50
rosarium 0:71bff5ad0a49 51 #define NFCT5_MAGICNUMBER_E1_CCFILE 0xE1
rosarium 0:71bff5ad0a49 52 #define NFCT5_MAGICNUMBER_E2_CCFILE 0xE2
rosarium 0:71bff5ad0a49 53 #define NFCT5_EXTENDED_CCFILE 0xFF
rosarium 0:71bff5ad0a49 54 #define NFCT5_VERSION_V1_0 0x40
rosarium 0:71bff5ad0a49 55 #define NFCT5_READ_ACCESS 0x0C
rosarium 0:71bff5ad0a49 56 #define NFCT5_WRITE_ACCESS 0x03
rosarium 0:71bff5ad0a49 57
rosarium 0:71bff5ad0a49 58 #define NFCT5_NDEF_MSG_TLV 0x03
rosarium 0:71bff5ad0a49 59 #define NFCT5_PROPRIETARY_TLV 0xFD
rosarium 0:71bff5ad0a49 60 #define NFCT5_TERMINATOR_TLV 0xFE
rosarium 0:71bff5ad0a49 61 #define NFCT5_3_BYTES_L_TLV 0xFF
rosarium 0:71bff5ad0a49 62
rosarium 0:71bff5ad0a49 63
rosarium 0:71bff5ad0a49 64 #define NDEF_MAX_SIZE NFC_DEVICE_MAX_NDEFMEMORY
rosarium 0:71bff5ad0a49 65
rosarium 0:71bff5ad0a49 66 #define NDEF_SIZE_OFFSET 0
rosarium 0:71bff5ad0a49 67 #define FIRST_RECORD_OFFSET 2
rosarium 0:71bff5ad0a49 68
rosarium 0:71bff5ad0a49 69 #ifndef MIN
rosarium 0:71bff5ad0a49 70 #define MIN(x, y) (((x) < (y)) ? (x) : (y))
rosarium 0:71bff5ad0a49 71 #endif
rosarium 0:71bff5ad0a49 72
rosarium 0:71bff5ad0a49 73 #define NFCTAG_4M_SIZE 0x200
rosarium 0:71bff5ad0a49 74 #define NFCTAG_16M_SIZE 0x800
rosarium 0:71bff5ad0a49 75 #define NFCTAG_64M_SIZE 0x2000
rosarium 0:71bff5ad0a49 76
rosarium 0:71bff5ad0a49 77 #define MAX_NDEF_MEM 0x200
rosarium 0:71bff5ad0a49 78 #define M24LR_MAX_SIZE NFCTAG_4M_SIZE
rosarium 0:71bff5ad0a49 79 #define M24LR_NDEF_MAX_SIZE MIN(M24LR_MAX_SIZE,MAX_NDEF_MEM)
rosarium 0:71bff5ad0a49 80 #define NFC_DEVICE_MAX_NDEFMEMORY M24LR_NDEF_MAX_SIZE
Davidroid 8:7c4cf671960b 81
rosarium 0:71bff5ad0a49 82 /**
rosarium 0:71bff5ad0a49 83 * @brief This function read the data stored in NDEF file at defined offset.
rosarium 0:71bff5ad0a49 84 * @param Offset : Offset in the NDEF file.
rosarium 0:71bff5ad0a49 85 * @param DataSize : Number of byte to read.
rosarium 0:71bff5ad0a49 86 * @param pData : pointer on buffer to store read data.
rosarium 0:71bff5ad0a49 87 * @retval NDEF_ERROR_MEMORY_INTERNAL : Size not compatible with memory.
rosarium 0:71bff5ad0a49 88 * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported.
rosarium 0:71bff5ad0a49 89 * @retval NDEF_ERROR : No NDEF in the tag.
rosarium 0:71bff5ad0a49 90 * @retval NDEF_OK : The operation is completed.
rosarium 0:71bff5ad0a49 91 */
Davidroid 8:7c4cf671960b 92 uint16_t NDefNfcTagM24LR::ReadData( uint16_t Offset , uint16_t DataSize , uint8_t* pData )
rosarium 0:71bff5ad0a49 93 {
rosarium 0:71bff5ad0a49 94 uint16_t status = NDEF_ERROR;
rosarium 0:71bff5ad0a49 95 uint8_t atlv_detect[4];
rosarium 0:71bff5ad0a49 96 uint8_t index = 0;
rosarium 0:71bff5ad0a49 97
rosarium 0:71bff5ad0a49 98 /* If too many data to write return error */
Davidroid 8:7c4cf671960b 99 if ( DataSize > NDEF_MAX_SIZE ) {
rosarium 0:71bff5ad0a49 100 return NDEF_ERROR_MEMORY_INTERNAL;
rosarium 0:71bff5ad0a49 101 }
rosarium 0:71bff5ad0a49 102
rosarium 0:71bff5ad0a49 103 /* Detect NDEF message in memory */
rosarium 0:71bff5ad0a49 104 status = NfcType5_NDEFDetection( );
Davidroid 8:7c4cf671960b 105 if ( status != NDEF_OK ) {
rosarium 0:71bff5ad0a49 106 return status;
rosarium 0:71bff5ad0a49 107 }
rosarium 0:71bff5ad0a49 108
rosarium 0:71bff5ad0a49 109 /* Read TL of Type 5 */
rosarium 0:71bff5ad0a49 110 status = NDefReadByte(CCFileStruct.NDEF_offset, 4, atlv_detect);
Davidroid 8:7c4cf671960b 111 if ( status != NDEF_OK ){
rosarium 0:71bff5ad0a49 112 return status;
rosarium 0:71bff5ad0a49 113 }
rosarium 0:71bff5ad0a49 114
Davidroid 8:7c4cf671960b 115 if ( atlv_detect[1] == NFCT5_3_BYTES_L_TLV ) {
Davidroid 8:7c4cf671960b 116 index = 2;
Davidroid 8:7c4cf671960b 117 }
giovannivisentini 5:900640bf1cff 118
Davidroid 8:7c4cf671960b 119 if (Offset==0 && DataSize>=2) {
Davidroid 8:7c4cf671960b 120 if ( atlv_detect[1] == NFCT5_3_BYTES_L_TLV ) {
Davidroid 8:7c4cf671960b 121 pData[0] = atlv_detect[2];
Davidroid 8:7c4cf671960b 122 pData[1] = atlv_detect[3];
Davidroid 8:7c4cf671960b 123 } else {
Davidroid 8:7c4cf671960b 124 pData[0] = 0x00;
Davidroid 8:7c4cf671960b 125 pData[1] = atlv_detect[1];
Davidroid 8:7c4cf671960b 126 }
Davidroid 8:7c4cf671960b 127 DataSize -= 2;
Davidroid 8:7c4cf671960b 128 pData += 2;
rosarium 0:71bff5ad0a49 129 }
giovannivisentini 5:900640bf1cff 130
rosarium 0:71bff5ad0a49 131 /* Check CC file is in the correct mode to proceed */
Davidroid 8:7c4cf671960b 132 if ( CCFileStruct.State == TT5_INITIALIZED ) {
rosarium 0:71bff5ad0a49 133 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 134 }
rosarium 0:71bff5ad0a49 135
Davidroid 8:7c4cf671960b 136 if (DataSize > 0) {
rosarium 0:71bff5ad0a49 137 /* Read NDEF */
Davidroid 8:7c4cf671960b 138 if ( NDefReadByte(CCFileStruct.NDEF_offset + index + Offset, DataSize, pData) != NFC_SUCCESS ) {
rosarium 0:71bff5ad0a49 139 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 140 }
rosarium 0:71bff5ad0a49 141 }
rosarium 0:71bff5ad0a49 142
rosarium 0:71bff5ad0a49 143 return NDEF_OK;
rosarium 0:71bff5ad0a49 144 }
rosarium 0:71bff5ad0a49 145
rosarium 0:71bff5ad0a49 146 /**
rosarium 0:71bff5ad0a49 147 * @brief This function writes data in NDEF file at defined offset.
rosarium 0:71bff5ad0a49 148 * @param Offset : Offset in the NDEF file.
rosarium 0:71bff5ad0a49 149 * @param DataSize : Number of byte to write.
rosarium 0:71bff5ad0a49 150 * @param pData : pointer on buffer to copy.
rosarium 0:71bff5ad0a49 151 * @retval NDEF_ERROR_MEMORY_INTERNAL : Size not compatible with memory.
rosarium 0:71bff5ad0a49 152 * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported.
rosarium 0:71bff5ad0a49 153 * @retval NDEF_ERROR : No NDEF in the tag.
rosarium 0:71bff5ad0a49 154 * @retval NDEF_OK : The operation is completed.
rosarium 0:71bff5ad0a49 155 */
rosarium 0:71bff5ad0a49 156 uint16_t NDefNfcTagM24LR::WriteData( uint16_t Offset , uint32_t DataSize , uint8_t *pData )
rosarium 0:71bff5ad0a49 157 {
rosarium 0:71bff5ad0a49 158 uint8_t atlv[4];
rosarium 0:71bff5ad0a49 159 uint8_t index = 0;
rosarium 0:71bff5ad0a49 160 uint16_t NDEF_Size = 0;
rosarium 0:71bff5ad0a49 161 bool status;
rosarium 0:71bff5ad0a49 162
rosarium 0:71bff5ad0a49 163 /* Do not include length bytes */
rosarium 0:71bff5ad0a49 164 DataSize -= FIRST_RECORD_OFFSET;
rosarium 0:71bff5ad0a49 165
rosarium 0:71bff5ad0a49 166 /* If too many data to write return error */
Davidroid 8:7c4cf671960b 167 if ( DataSize > NDEF_MAX_SIZE ) {
rosarium 0:71bff5ad0a49 168 return NDEF_ERROR_MEMORY_INTERNAL;
rosarium 0:71bff5ad0a49 169 }
rosarium 0:71bff5ad0a49 170
rosarium 0:71bff5ad0a49 171 /* Detect NDEF message in memory */
Davidroid 8:7c4cf671960b 172 if ( NfcType5_NDEFDetection( ) != NDEF_OK ) {
rosarium 0:71bff5ad0a49 173 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 174 }
rosarium 0:71bff5ad0a49 175
rosarium 0:71bff5ad0a49 176 /* Extract NDEF Size from buffer */
rosarium 0:71bff5ad0a49 177 NDEF_Size = (uint16_t)(pData[0] << 8);
rosarium 0:71bff5ad0a49 178 NDEF_Size = NDEF_Size | (uint16_t)(pData[1] );
rosarium 0:71bff5ad0a49 179
rosarium 0:71bff5ad0a49 180 /* If entire NDEF is written, update Length of Type 5 */
Davidroid 8:7c4cf671960b 181 if ( DataSize == NDEF_Size ) {
rosarium 0:71bff5ad0a49 182 /* Check if L is on 3 or 1 byte */
Davidroid 8:7c4cf671960b 183 if ( NDEF_Size >= NFCT5_3_BYTES_L_TLV ) {
rosarium 0:71bff5ad0a49 184 /* First init L with 0, will be updated at the end */
rosarium 0:71bff5ad0a49 185 atlv[1] = 0x00;
rosarium 0:71bff5ad0a49 186 atlv[2] = 0x00;
rosarium 0:71bff5ad0a49 187 atlv[3] = 0x00;
rosarium 0:71bff5ad0a49 188 status = NDefWriteByte( (atlv + 1), 3, (CCFileStruct.NDEF_offset + 1));
rosarium 0:71bff5ad0a49 189 index += 4;
Davidroid 8:7c4cf671960b 190 } else {
rosarium 0:71bff5ad0a49 191 /* First inti L with 0, will be updated at the end */
rosarium 0:71bff5ad0a49 192 atlv[1] = 0x00;
rosarium 0:71bff5ad0a49 193 status = NDefWriteByte( (atlv + 1), 1, (CCFileStruct.NDEF_offset + 1));
rosarium 0:71bff5ad0a49 194 index += 2;
rosarium 0:71bff5ad0a49 195 }
rosarium 0:71bff5ad0a49 196 }
rosarium 0:71bff5ad0a49 197
rosarium 0:71bff5ad0a49 198 /* Start write NDEF message to EEPROM */
rosarium 0:71bff5ad0a49 199 status = NDefWriteByte( (pData + FIRST_RECORD_OFFSET), DataSize, CCFileStruct.NDEF_offset + index + Offset);
Davidroid 8:7c4cf671960b 200 if ( status != NFC_SUCCESS ) {
rosarium 0:71bff5ad0a49 201 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 202 }
rosarium 0:71bff5ad0a49 203
rosarium 0:71bff5ad0a49 204 /* If entire NDEF is written, update Length of Type 5 */
Davidroid 8:7c4cf671960b 205 if ( DataSize == NDEF_Size ) {
rosarium 0:71bff5ad0a49 206 /* Check if L is on 3 or 1 byte */
Davidroid 8:7c4cf671960b 207 if ( NDEF_Size >= NFCT5_3_BYTES_L_TLV ) {
rosarium 0:71bff5ad0a49 208 /* Update Length value */
rosarium 0:71bff5ad0a49 209 atlv[1] = NFCT5_3_BYTES_L_TLV;
rosarium 0:71bff5ad0a49 210 atlv[2] = pData[0];
rosarium 0:71bff5ad0a49 211 atlv[3] = pData[1];
rosarium 0:71bff5ad0a49 212 status = NDefWriteByte( (atlv + 1), 3, (CCFileStruct.NDEF_offset + 1));
Davidroid 8:7c4cf671960b 213 } else {
rosarium 0:71bff5ad0a49 214 /* Update Length value */
rosarium 0:71bff5ad0a49 215 atlv[1] = pData[1];
rosarium 0:71bff5ad0a49 216 status = NDefWriteByte( (atlv + 1), 1, (CCFileStruct.NDEF_offset + 1));
rosarium 0:71bff5ad0a49 217 }
rosarium 0:71bff5ad0a49 218
rosarium 0:71bff5ad0a49 219 /* Write Terminator TLV */
rosarium 0:71bff5ad0a49 220 atlv[0] = NFCT5_TERMINATOR_TLV;
rosarium 0:71bff5ad0a49 221 status = NDefWriteByte( atlv, 1, CCFileStruct.NDEF_offset + index + NDEF_Size);
rosarium 0:71bff5ad0a49 222 }
rosarium 0:71bff5ad0a49 223
rosarium 0:71bff5ad0a49 224 return NDEF_OK;
rosarium 0:71bff5ad0a49 225 }
rosarium 0:71bff5ad0a49 226
rosarium 0:71bff5ad0a49 227 /**
rosarium 0:71bff5ad0a49 228 * @brief This functions writes CCFile in EEPROM.
Davidroid 8:7c4cf671960b 229 * @param pCCBuffer : pointer on the buffer containnig CC file.
rosarium 0:71bff5ad0a49 230 * @retval NFCTAG status.
rosarium 0:71bff5ad0a49 231 */
rosarium 0:71bff5ad0a49 232 uint16_t NDefNfcTagM24LR::NfcType5_WriteCCFile( const uint8_t * const pCCBuffer )
rosarium 0:71bff5ad0a49 233 {
rosarium 0:71bff5ad0a49 234 bool ret_value;
rosarium 0:71bff5ad0a49 235
rosarium 0:71bff5ad0a49 236 /* Write first block of CCFile */
rosarium 0:71bff5ad0a49 237 ret_value = NDefWriteByte( pCCBuffer, 0x4, 0x00);
rosarium 0:71bff5ad0a49 238
rosarium 0:71bff5ad0a49 239 /* If extended memory writes the next 4 bytes */
Davidroid 8:7c4cf671960b 240 if ( (pCCBuffer[2] == 0x00) && (ret_value == NFC_SUCCESS) ) {
rosarium 0:71bff5ad0a49 241 ret_value = NDefWriteByte( pCCBuffer + 4, 4, 0x04);
rosarium 0:71bff5ad0a49 242 }
rosarium 0:71bff5ad0a49 243
Davidroid 8:7c4cf671960b 244 if ( ret_value != NFC_SUCCESS ) {
rosarium 0:71bff5ad0a49 245 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 246 }
rosarium 0:71bff5ad0a49 247
Davidroid 8:7c4cf671960b 248 return NDEF_OK;
rosarium 0:71bff5ad0a49 249 }
rosarium 0:71bff5ad0a49 250
Davidroid 8:7c4cf671960b 251 /**
Davidroid 8:7c4cf671960b 252 * @brief This functions reads CCFile from EEPROM.
Davidroid 8:7c4cf671960b 253 * @param pCCBuffer : pointer on the buffer containnig CC file.
Davidroid 8:7c4cf671960b 254 * @retval NFCTAG status.
Davidroid 8:7c4cf671960b 255 */
rosarium 0:71bff5ad0a49 256 uint16_t NDefNfcTagM24LR::NfcType5_ReadCCFile( uint8_t * const pCCBuffer )
rosarium 0:71bff5ad0a49 257 {
rosarium 0:71bff5ad0a49 258 bool ret_value;
rosarium 0:71bff5ad0a49 259
rosarium 0:71bff5ad0a49 260 /* Read 4 bytes of CC File */
rosarium 0:71bff5ad0a49 261 ret_value = NDefReadByte(0x00, 4, pCCBuffer);
rosarium 0:71bff5ad0a49 262
rosarium 0:71bff5ad0a49 263 /* If extended memory reads the next 4 bytes */
Davidroid 8:7c4cf671960b 264 if ( (pCCBuffer[2] == 0x00) && (ret_value == NFC_SUCCESS) ) {
rosarium 0:71bff5ad0a49 265 ret_value = NDefReadByte(0x04, 4, pCCBuffer + 4 );
rosarium 0:71bff5ad0a49 266 }
rosarium 0:71bff5ad0a49 267
Davidroid 8:7c4cf671960b 268 if ( ret_value != NFC_SUCCESS ) {
rosarium 0:71bff5ad0a49 269 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 270 }
rosarium 0:71bff5ad0a49 271
rosarium 0:71bff5ad0a49 272 return NDEF_OK;
rosarium 0:71bff5ad0a49 273 }
Davidroid 8:7c4cf671960b 274
Davidroid 8:7c4cf671960b 275 /**
Davidroid 8:7c4cf671960b 276 * @brief This functions initializes Nfc Type.
Davidroid 8:7c4cf671960b 277 * @param None.
Davidroid 8:7c4cf671960b 278 * @retval NFCTAG status.
Davidroid 8:7c4cf671960b 279 */
rosarium 0:71bff5ad0a49 280 uint16_t NDefNfcTagM24LR::NfcType5_TT5Init( void )
rosarium 0:71bff5ad0a49 281 {
rosarium 4:0287f5476fe0 282 bool ret_value ;
rosarium 0:71bff5ad0a49 283 uint16_t status;
rosarium 0:71bff5ad0a49 284 uint8_t accbuffer[8];
rosarium 0:71bff5ad0a49 285 uint8_t cdata;
rosarium 0:71bff5ad0a49 286
rosarium 0:71bff5ad0a49 287 /* Prepare buffer to update CCFile */
rosarium 0:71bff5ad0a49 288 accbuffer[0] = CCFileStruct.MagicNumber;
rosarium 0:71bff5ad0a49 289 accbuffer[1] = CCFileStruct.Version;
rosarium 0:71bff5ad0a49 290 accbuffer[2] = CCFileStruct.MemorySize;
rosarium 0:71bff5ad0a49 291 accbuffer[3] = CCFileStruct.TT5Tag;
rosarium 0:71bff5ad0a49 292 CCFileStruct.NDEF_offset = 0x04;
rosarium 0:71bff5ad0a49 293
rosarium 0:71bff5ad0a49 294 /* If extended memory prepare the length bytes */
Davidroid 8:7c4cf671960b 295 if ( CCFileStruct.MemorySize == NFCT5_EXTENDED_CCFILE ) {
rosarium 0:71bff5ad0a49 296 accbuffer[6] = (uint8_t)(CCFileStruct.ExtMemorySize >> 8);
rosarium 0:71bff5ad0a49 297 accbuffer[7] = (uint8_t)(CCFileStruct.ExtMemorySize & 0xFF);
rosarium 0:71bff5ad0a49 298 CCFileStruct.NDEF_offset = 0x08;
rosarium 0:71bff5ad0a49 299 }
rosarium 0:71bff5ad0a49 300
rosarium 0:71bff5ad0a49 301 /* Update CCFile */
rosarium 0:71bff5ad0a49 302 status = NfcType5_WriteCCFile( accbuffer );
Davidroid 8:7c4cf671960b 303 if ( status != NDEF_OK ) {
rosarium 0:71bff5ad0a49 304 return status;
rosarium 0:71bff5ad0a49 305 }
rosarium 0:71bff5ad0a49 306
rosarium 0:71bff5ad0a49 307 /* Update NDEF TLV for INITIALIZED state */
rosarium 0:71bff5ad0a49 308 /* Update T */
rosarium 0:71bff5ad0a49 309 cdata = NFCT5_NDEF_MSG_TLV;
rosarium 0:71bff5ad0a49 310 ret_value = NDefWriteByte( &cdata, 1, CCFileStruct.NDEF_offset);
Davidroid 8:7c4cf671960b 311 if ( ret_value != NFC_SUCCESS ) {
rosarium 0:71bff5ad0a49 312 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 313 }
rosarium 0:71bff5ad0a49 314
rosarium 0:71bff5ad0a49 315 /* Update L */
rosarium 0:71bff5ad0a49 316 cdata = 0x00;
rosarium 0:71bff5ad0a49 317 ret_value = NDefWriteByte( &cdata, 1, (CCFileStruct.NDEF_offset + 1));
Davidroid 8:7c4cf671960b 318 if ( ret_value != NFC_SUCCESS ) {
rosarium 0:71bff5ad0a49 319 return NDEF_ERROR;
rosarium 0:71bff5ad0a49 320 }
rosarium 0:71bff5ad0a49 321
rosarium 0:71bff5ad0a49 322 return NDEF_OK;
rosarium 0:71bff5ad0a49 323 }
rosarium 0:71bff5ad0a49 324
Davidroid 8:7c4cf671960b 325 /**
Davidroid 8:7c4cf671960b 326 * @brief This functions detects Nfc Tyoe.
Davidroid 8:7c4cf671960b 327 * @param None.
Davidroid 8:7c4cf671960b 328 * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported.
Davidroid 8:7c4cf671960b 329 * @retval NDEF_OK : The operation is completed.
Davidroid 8:7c4cf671960b 330 */
rosarium 0:71bff5ad0a49 331 uint16_t NDefNfcTagM24LR::NfcType5_NDEFDetection( void )
rosarium 0:71bff5ad0a49 332 {
rosarium 0:71bff5ad0a49 333 uint8_t acc_buffer[8];
rosarium 0:71bff5ad0a49 334 uint8_t atlv_detect[4];
rosarium 0:71bff5ad0a49 335 uint16_t status;
rosarium 0:71bff5ad0a49 336 uint32_t memory_size;
rosarium 0:71bff5ad0a49 337
rosarium 0:71bff5ad0a49 338 CCFileStruct.State = TT5_NO_NDEF;
rosarium 0:71bff5ad0a49 339
rosarium 0:71bff5ad0a49 340 /* Read CCFile */
rosarium 0:71bff5ad0a49 341 status = NfcType5_ReadCCFile( acc_buffer );
Davidroid 8:7c4cf671960b 342 if ( status != NDEF_OK ) {
rosarium 0:71bff5ad0a49 343 return status;
rosarium 0:71bff5ad0a49 344 }
rosarium 0:71bff5ad0a49 345
rosarium 0:71bff5ad0a49 346 /* Check Byte 0 is equal to magic number */
Davidroid 8:7c4cf671960b 347 if ( ( acc_buffer[0] != NFCT5_MAGICNUMBER_E1_CCFILE ) && ( acc_buffer[0] != NFCT5_MAGICNUMBER_E2_CCFILE ) ) {
rosarium 0:71bff5ad0a49 348 return NDEF_ERROR_NOT_FORMATED;
Davidroid 8:7c4cf671960b 349 } else if ( ( (acc_buffer[1]&0xFC) != 0x40 ) ) { /* Check Version number */
rosarium 0:71bff5ad0a49 350 return NDEF_ERROR_NOT_FORMATED;
rosarium 0:71bff5ad0a49 351 }
rosarium 0:71bff5ad0a49 352
rosarium 0:71bff5ad0a49 353 /* Check if CCFile is on 4 Bytes or 8 Bytes */
Davidroid 8:7c4cf671960b 354 if ( acc_buffer[2] == 0x00 ) {
rosarium 0:71bff5ad0a49 355 /* Update CCFIle structure */
rosarium 0:71bff5ad0a49 356 CCFileStruct.MemorySize = 0x0;
rosarium 0:71bff5ad0a49 357 CCFileStruct.ExtMemorySize = (uint16_t)acc_buffer[6];
rosarium 0:71bff5ad0a49 358 CCFileStruct.ExtMemorySize = ( CCFileStruct.ExtMemorySize << 8 ) | acc_buffer[7];
rosarium 0:71bff5ad0a49 359 memory_size = CCFileStruct.ExtMemorySize;
rosarium 0:71bff5ad0a49 360 CCFileStruct.NDEF_offset = 8;
Davidroid 8:7c4cf671960b 361 } else {
rosarium 0:71bff5ad0a49 362 /* Update CCFIle structure */
rosarium 0:71bff5ad0a49 363 CCFileStruct.MemorySize = acc_buffer[2];
rosarium 0:71bff5ad0a49 364 CCFileStruct.ExtMemorySize = 0x0;
rosarium 0:71bff5ad0a49 365 memory_size = CCFileStruct.MemorySize;
rosarium 0:71bff5ad0a49 366 CCFileStruct.NDEF_offset = 4;
rosarium 0:71bff5ad0a49 367 }
rosarium 0:71bff5ad0a49 368
rosarium 0:71bff5ad0a49 369 /* Update CCFIle structure */
rosarium 0:71bff5ad0a49 370 CCFileStruct.MagicNumber = acc_buffer[0];
rosarium 0:71bff5ad0a49 371 CCFileStruct.Version = acc_buffer[1];
rosarium 0:71bff5ad0a49 372 CCFileStruct.TT5Tag = acc_buffer[3];
rosarium 0:71bff5ad0a49 373
rosarium 0:71bff5ad0a49 374 /* Search for position of NDEF TLV in memory and tag status */
Davidroid 8:7c4cf671960b 375 while( ( NDefReadByte(CCFileStruct.NDEF_offset, 4, atlv_detect) == NFC_SUCCESS ) && ( CCFileStruct.NDEF_offset < memory_size ) ) {
rosarium 0:71bff5ad0a49 376 /* Detect first NDEF Message in memory */
Davidroid 8:7c4cf671960b 377 if ( atlv_detect[0] == NFCT5_NDEF_MSG_TLV ) {
Davidroid 8:7c4cf671960b 378 if ( atlv_detect[1] == 0x00 ) {
rosarium 0:71bff5ad0a49 379 CCFileStruct.State = TT5_INITIALIZED;
Davidroid 8:7c4cf671960b 380 } else {
Davidroid 8:7c4cf671960b 381 if ( CCFileStruct.Version & 0x3 ) {
rosarium 0:71bff5ad0a49 382 CCFileStruct.State = TT5_READ;
Davidroid 8:7c4cf671960b 383 } else {
rosarium 0:71bff5ad0a49 384 CCFileStruct.State = TT5_READ_WRITE;
rosarium 0:71bff5ad0a49 385 }
rosarium 0:71bff5ad0a49 386 }
rosarium 0:71bff5ad0a49 387 return NDEF_OK;
Davidroid 8:7c4cf671960b 388 } else if ( atlv_detect[0] == NFCT5_PROPRIETARY_TLV ) { /* If Proprietary NDEF jump to end of proprietary message */
Davidroid 8:7c4cf671960b 389 if ( atlv_detect[1] == NFCT5_3_BYTES_L_TLV ) {
rosarium 0:71bff5ad0a49 390 CCFileStruct.NDEF_offset = CCFileStruct.NDEF_offset + ( (uint32_t)atlv_detect[2] << 8 ) + atlv_detect[3];
rosarium 0:71bff5ad0a49 391 continue;
Davidroid 8:7c4cf671960b 392 } else {
rosarium 0:71bff5ad0a49 393 CCFileStruct.NDEF_offset = CCFileStruct.NDEF_offset + atlv_detect[1];
rosarium 0:71bff5ad0a49 394 continue;
rosarium 0:71bff5ad0a49 395 }
Davidroid 8:7c4cf671960b 396 } else if ( atlv_detect[0] == NFCT5_TERMINATOR_TLV ) { /* if Terminator no NDEF detected */
rosarium 0:71bff5ad0a49 397 return NDEF_ERROR_NOT_FORMATED;
rosarium 0:71bff5ad0a49 398 }
Davidroid 8:7c4cf671960b 399
rosarium 0:71bff5ad0a49 400 CCFileStruct.NDEF_offset++;
rosarium 0:71bff5ad0a49 401 }
rosarium 0:71bff5ad0a49 402
rosarium 0:71bff5ad0a49 403 return NDEF_ERROR_NOT_FORMATED;
rosarium 0:71bff5ad0a49 404 }
rosarium 0:71bff5ad0a49 405
Davidroid 8:7c4cf671960b 406 /**
Davidroid 8:7c4cf671960b 407 * @brief This functions opens a session.
Davidroid 8:7c4cf671960b 408 * @param force : force the opening.
Davidroid 8:7c4cf671960b 409 * @retval true.
Davidroid 8:7c4cf671960b 410 */
giovannivisentini 6:8c1eca41b3a9 411 bool NDefNfcTagM24LR::open_session(bool force) {
Davidroid 8:7c4cf671960b 412 uint16_t status = NfcType5_NDEFDetection();
rosarium 0:71bff5ad0a49 413
Davidroid 8:7c4cf671960b 414 if ( status != NDEF_OK ) {
Davidroid 8:7c4cf671960b 415 CCFileStruct.MagicNumber = NFCT5_MAGICNUMBER_E1_CCFILE;
Davidroid 8:7c4cf671960b 416 CCFileStruct.Version = NFCT5_VERSION_V1_0;
Davidroid 8:7c4cf671960b 417 CCFileStruct.MemorySize = ( M24LR_MAX_SIZE / 8 ) & 0xFF;
Davidroid 8:7c4cf671960b 418 CCFileStruct.TT5Tag = 0x05;
Davidroid 8:7c4cf671960b 419 /* Init of the Type Tag 5 component (M24LR) */
Davidroid 8:7c4cf671960b 420 while ( NfcType5_TT5Init( ) != NDEF_OK );
Davidroid 8:7c4cf671960b 421 }
rosarium 0:71bff5ad0a49 422
Davidroid 8:7c4cf671960b 423 mIsSessionOpen = 1;
Davidroid 8:7c4cf671960b 424
Davidroid 8:7c4cf671960b 425 return true;
rosarium 0:71bff5ad0a49 426 }
rosarium 0:71bff5ad0a49 427
Davidroid 8:7c4cf671960b 428
Davidroid 8:7c4cf671960b 429 /**
Davidroid 8:7c4cf671960b 430 * @brief This functions closes a session.
Davidroid 8:7c4cf671960b 431 * @param None.
Davidroid 8:7c4cf671960b 432 * @retval true.
Davidroid 8:7c4cf671960b 433 */
giovannivisentini 6:8c1eca41b3a9 434 bool NDefNfcTagM24LR::close_session()
rosarium 4:0287f5476fe0 435 {
rosarium 4:0287f5476fe0 436 return true;
rosarium 0:71bff5ad0a49 437 }
rosarium 4:0287f5476fe0 438
Davidroid 8:7c4cf671960b 439 /**
Davidroid 8:7c4cf671960b 440 * @brief This functions writes bytes.
Davidroid 8:7c4cf671960b 441 * @param byffer : the buffer containing data.
Davidroid 8:7c4cf671960b 442 * @param length: the length of the buffer in bytes.
Davidroid 8:7c4cf671960b 443 * @param offset: the offset of the buffer in bytes.
Davidroid 8:7c4cf671960b 444 * @retval true if written, false otherwise.
Davidroid 8:7c4cf671960b 445 */
Davidroid 8:7c4cf671960b 446 bool NDefNfcTagM24LR::writeByte(const uint8_t *buffer, uint16_t length, uint16_t offset,
Davidroid 8:7c4cf671960b 447 byteOperationCallback_t callback,CallbackStatus_t *callbackStatus)
rosarium 4:0287f5476fe0 448 {
Davidroid 8:7c4cf671960b 449 if (WriteData(offset, length, (uint8_t*)buffer)== NDEF_OK) {
rosarium 4:0287f5476fe0 450 callback(callbackStatus,true,buffer,length);
rosarium 4:0287f5476fe0 451 return true;
rosarium 4:0287f5476fe0 452 }
Davidroid 8:7c4cf671960b 453
rosarium 4:0287f5476fe0 454 callback(callbackStatus,false,buffer,length);
rosarium 4:0287f5476fe0 455 return false;
rosarium 4:0287f5476fe0 456 }
rosarium 0:71bff5ad0a49 457
Davidroid 8:7c4cf671960b 458 /**
Davidroid 8:7c4cf671960b 459 * @brief This functions reads bytes.
Davidroid 8:7c4cf671960b 460 * @param byteOffset : the offset of the buffer in bytes.
Davidroid 8:7c4cf671960b 461 * @param length: the length of the buffer in bytes.
Davidroid 8:7c4cf671960b 462 * @param buffer : the buffer containing data.
Davidroid 8:7c4cf671960b 463 * @param callback : a function to call after reading data.
Davidroid 8:7c4cf671960b 464 * @param callbackStatus : the status of the callback.
Davidroid 8:7c4cf671960b 465 * @retval true if read, false otherwise.
Davidroid 8:7c4cf671960b 466 */
Davidroid 8:7c4cf671960b 467 bool NDefNfcTagM24LR::readByte(const uint16_t byteOffset, const uint16_t length,
Davidroid 8:7c4cf671960b 468 uint8_t *buffer, byteOperationCallback_t callback, CallbackStatus_t *callbackStatus)
Davidroid 8:7c4cf671960b 469 {
Davidroid 8:7c4cf671960b 470
Davidroid 8:7c4cf671960b 471 //first it reads the 2 byte for the length then when it will have the callback it reads the real message
Davidroid 8:7c4cf671960b 472 if (ReadData(byteOffset, length, (uint8_t*)buffer)== NDEF_OK){
Davidroid 8:7c4cf671960b 473 callback(callbackStatus,true,buffer,length);
Davidroid 8:7c4cf671960b 474 return true;
Davidroid 8:7c4cf671960b 475 }
Davidroid 8:7c4cf671960b 476
Davidroid 8:7c4cf671960b 477 callback(callbackStatus,false,buffer,length);
Davidroid 8:7c4cf671960b 478 return false;
Davidroid 8:7c4cf671960b 479 }
Davidroid 8:7c4cf671960b 480
Davidroid 8:7c4cf671960b 481 /**
Davidroid 8:7c4cf671960b 482 * @brief This functions writes bytes.
Davidroid 8:7c4cf671960b 483 * @param byffer : the buffer containing data.
Davidroid 8:7c4cf671960b 484 * @param length: the length of the buffer in bytes.
Davidroid 8:7c4cf671960b 485 * @param offset: the offset of the buffer in bytes.
Davidroid 8:7c4cf671960b 486 * @retval NFCTAG status.
Davidroid 8:7c4cf671960b 487 */
Davidroid 8:7c4cf671960b 488 uint16_t NDefNfcTagM24LR::NDefWriteByte(const uint8_t *buffer, uint16_t length, uint16_t offset)
Davidroid 8:7c4cf671960b 489 {
giovannivisentini 5:900640bf1cff 490 uint16_t status;
Davidroid 8:7c4cf671960b 491 do {
giovannivisentini 5:900640bf1cff 492 uint8_t writeLength =(uint8_t) std::min<uint16_t>(0xFF,length);
Davidroid 8:7c4cf671960b 493 status = mDevice.update_binary(offset, writeLength, (uint8_t*)buffer);
giovannivisentini 5:900640bf1cff 494 offset+=writeLength;
giovannivisentini 5:900640bf1cff 495 buffer+=writeLength;
giovannivisentini 5:900640bf1cff 496 length-=writeLength;
Davidroid 8:7c4cf671960b 497 } while (status==NDEF_OK && length!=0);
Davidroid 8:7c4cf671960b 498
giovannivisentini 5:900640bf1cff 499 return status;
rosarium 0:71bff5ad0a49 500 }
rosarium 0:71bff5ad0a49 501
Davidroid 8:7c4cf671960b 502 /**
Davidroid 8:7c4cf671960b 503 * @brief This functions reads bytes.
Davidroid 8:7c4cf671960b 504 * @param byteOffset : the offset of the buffer in bytes.
Davidroid 8:7c4cf671960b 505 * @param length: the length of the buffer in bytes.
Davidroid 8:7c4cf671960b 506 * @param buffer : the buffer containing data.
Davidroid 8:7c4cf671960b 507 * @retval NFCTAG status.
Davidroid 8:7c4cf671960b 508 */
Davidroid 8:7c4cf671960b 509 uint16_t NDefNfcTagM24LR::NDefReadByte(uint16_t byteOffset, uint16_t length, uint8_t *buffer)
Davidroid 8:7c4cf671960b 510 {
giovannivisentini 5:900640bf1cff 511 uint16_t status;
Davidroid 8:7c4cf671960b 512 do {
giovannivisentini 5:900640bf1cff 513 uint8_t readBuffer = (uint8_t)std::min<uint16_t>(0xFF,length);
giovannivisentini 6:8c1eca41b3a9 514 status= mDevice.read_binary(byteOffset, readBuffer, (uint8_t*)buffer);
giovannivisentini 5:900640bf1cff 515 byteOffset+=readBuffer;
giovannivisentini 5:900640bf1cff 516 buffer+=readBuffer;
giovannivisentini 5:900640bf1cff 517 length-=readBuffer;
Davidroid 8:7c4cf671960b 518 } while (status==NDEF_OK && length!=0);
Davidroid 8:7c4cf671960b 519
giovannivisentini 5:900640bf1cff 520 return status;
rosarium 0:71bff5ad0a49 521 }
rosarium 0:71bff5ad0a49 522
Davidroid 8:7c4cf671960b 523
rosarium 0:71bff5ad0a49 524 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/