NB-IoT
Dependencies: NDefLib X_NUCLEO_NFC02A1 hdc1080 mbed
Fork of HelloWorld_NFC02A1 by
Revision 0:892175366555, committed 2016-07-27
- Comitter:
- rosarium
- Date:
- Wed Jul 27 09:25:33 2016 +0000
- Child:
- 1:11ae12d41082
- Commit message:
- first release of the complete mbed library for HelloWorld_NFC02A1
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Lib_NDEF/lib_NDEF.cpp Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,591 @@
+/**
+ ******************************************************************************
+ * @file lib_NDEF.c
+ * @author MMY Application Team
+ * @version $Revision: 1583 $
+ * @date $Date: 2016-02-03 15:06:51 +0100 (Wed, 03 Feb 2016) $
+ * @brief This file help to manage NDEF file, to parse and identify them.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT 2015 STMicroelectronics</center></h2>
+ *
+ * Licensed under ST MYLIBERTY SOFTWARE LICENSE AGREEMENT (the "License");
+ * You may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.st.com/myliberty
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+ * AND SPECIFICALLY DISCLAIMING THE IMPLIED WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************
+ */
+
+/* Includes ------------------------------------------------------------------*/
+#include "lib_NDEF.h"
+#include <stdint.h>
+#include <string.h>
+/** @addtogroup NFC_libraries
+ * @{
+ * @brief <b>This is the library used to manage the content of the TAG (data)
+ * But also the specific feature of the tag, for instance
+ * password, gpo... </b>
+ */
+
+
+/** @addtogroup libNFC_FORUM
+ * @{
+ * @brief This part of the library manage data which follow NFC forum organisation.
+ */
+
+/** @defgroup libNDEF_Private_Functions
+ * @{
+ */
+
+
+
+/**
+ * @brief This function check that the tag contain a NDEF message.
+ * @retval NDEF_OK : There is a NDEF file stored in tag.
+ * @retval NDEF_ERROR : No NDEF in the tag.
+ */
+uint16_t NDEF::NDEF_IsNDEFPresent( void )
+{
+ uint16_t FileSize;
+ uint8_t uNDEFHeader [0x2];
+
+ /* Check NDEF existence */
+ ReadData( NDEF_SIZE_OFFSET, 2, uNDEFHeader );
+ FileSize = (uint16_t)( (uNDEFHeader[0x00]<<8) | uNDEFHeader[0x01] );
+
+ if( FileSize != 0 )
+ return NDEF_OK;
+ else
+ return NDEF_ERROR;
+}
+
+/**
+ * @brief This function identify the type of record.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ * @param pPayload : pointer on the payload.
+ * @retval Status : Status of the operation.
+ */
+uint16_t NDEF::NDEF_IdentifySPRecord( sRecordInfo *pRecordStruct, uint8_t* pPayload )
+{
+ uint16_t status = NDEF_ERROR;
+ uint16_t SizeOfRecordHeader, TypeNbByte, PayloadLengthField, IDLengthField, IDNbByte;
+
+ /* Is ID length field present */
+ if( (*pPayload) & IL_Mask )
+ {
+ IDLengthField = ID_LENGTH_FIELD;
+ }
+ else
+ {
+ IDLengthField = 0;
+ }
+
+ /* it's a SR */
+ if( (*pPayload) & SR_Mask )
+ {
+ TypeNbByte = pPayload[1];
+ PayloadLengthField = 1;
+ if( IDLengthField == ID_LENGTH_FIELD )
+ IDNbByte = pPayload[3];
+ else
+ IDNbByte = 0;
+ }
+ else
+ {
+ TypeNbByte = pPayload[1];
+ PayloadLengthField = 4;
+ if( IDLengthField == ID_LENGTH_FIELD )
+ IDNbByte = pPayload[6];
+ else
+ IDNbByte = 0;
+ }
+
+ SizeOfRecordHeader = RECORD_FLAG_FIELD + TYPE_LENGTH_FIELD + PayloadLengthField + IDLengthField + TypeNbByte + IDNbByte;
+
+ /* it's a SR */
+ if( pPayload[0] & SR_Mask )
+ {
+ pRecordStruct->RecordFlags = pPayload[0];
+ pRecordStruct->TypeLength = TypeNbByte;
+ pRecordStruct->PayloadLength3 = 0;
+ pRecordStruct->PayloadLength2 = 0;
+ pRecordStruct->PayloadLength1 = 0;
+ pRecordStruct->PayloadLength0 = pPayload[2];
+ pRecordStruct->IDLength = IDNbByte;
+ memcpy( pRecordStruct->Type, &pPayload[3+IDNbByte], TypeNbByte );
+ memcpy( pRecordStruct->ID, &pPayload[3+IDNbByte+TypeNbByte], IDNbByte );
+ pRecordStruct->PayloadOffset = SizeOfRecordHeader;
+ }
+ else
+ {
+ pRecordStruct->RecordFlags = pPayload[0];
+ pRecordStruct->TypeLength = TypeNbByte;
+ pRecordStruct->PayloadLength3 = pPayload[2];
+ pRecordStruct->PayloadLength2 = pPayload[3];
+ pRecordStruct->PayloadLength1 = pPayload[4];
+ pRecordStruct->PayloadLength0 = pPayload[5];
+ pRecordStruct->IDLength = IDNbByte;
+ memcpy( pRecordStruct->Type, &pPayload[6+IDNbByte], TypeNbByte );
+ memcpy( pRecordStruct->ID, &pPayload[6+IDNbByte+TypeNbByte], IDNbByte );
+ pRecordStruct->PayloadOffset = SizeOfRecordHeader;
+ }
+
+ pRecordStruct->PayloadBufferAdd = (uint32_t)( pPayload + SizeOfRecordHeader );
+
+ status = NDEF_ParseRecordHeader( pRecordStruct );
+
+ return status;
+}
+
+/**
+ * @brief This function parse the record header and dispatch regarding TNF value.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ * @retval NDEF_OK : record identified and structure filled.
+ * @retval NDEF_ERROR : Not supported.
+ */
+uint16_t NDEF::NDEF_ParseRecordHeader( sRecordInfo *pRecordStruct )
+{
+ uint16_t status = NDEF_OK;
+
+ switch( (pRecordStruct->RecordFlags & TNF_Mask) )
+ {
+ case TNF_WellKnown:
+ NDEF_ParseWellKnownType( pRecordStruct );
+ break;
+
+ case TNF_MediaType:
+ NDEF_ParseMediaType( pRecordStruct );
+ break;
+
+ case TNF_NFCForumExternal:
+ NDEF_ParseForumExternalType( pRecordStruct);
+ break;
+
+ default:
+ /* currently not supported or unknown*/
+ pRecordStruct->NDEF_Type = UNKNOWN_TYPE;
+ status = NDEF_ERROR;
+ }
+ return status;
+}
+
+/**
+ * @brief This function parse the Well Known type record.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ */
+void NDEF::NDEF_ParseWellKnownType( sRecordInfo *pRecordStruct )
+{
+ uint8_t* pPayload;
+
+ pPayload = (uint8_t*)( pRecordStruct->PayloadBufferAdd );
+
+ if( !memcmp( &(pRecordStruct->Type), SMART_POSTER_TYPE_STRING, pRecordStruct->TypeLength ) )
+ {
+ /* special case where we have to parse others records */
+ pRecordStruct->NDEF_Type = SMARTPOSTER_TYPE;
+ NDEF_ParseSP( pRecordStruct );
+ }
+
+ else if( !memcmp( &(pRecordStruct->Type), URI_TYPE_STRING, pRecordStruct->TypeLength ) )
+ {
+ /* it's an URI Type check if it's an URL or SMS or ... */
+ /* check identifier */
+ if( *pPayload == URI_ID_0x00 )
+ {
+ NDEF_ParseURI( pRecordStruct );
+ }
+ else if( (*pPayload > URI_ID_0x00) && (*pPayload < URI_RFU) )
+ {
+ /* email special case */
+ if( *pPayload == (uint8_t) URI_ID_0x06 )
+ {
+ pRecordStruct->NDEF_Type = URI_EMAIL_TYPE;
+ }
+ else
+ {
+ pRecordStruct->NDEF_Type = WELL_KNOWN_ABRIDGED_URI_TYPE;
+ }
+ }
+ else
+ {
+ pRecordStruct->NDEF_Type = UNKNOWN_TYPE;
+ }
+ }
+
+ else if( !memcmp( &(pRecordStruct->Type), TEXT_TYPE_STRING, pRecordStruct->TypeLength ) )
+ {
+ pRecordStruct->NDEF_Type = TEXT_TYPE;
+ }
+ else
+ pRecordStruct->NDEF_Type = UNKNOWN_TYPE;
+}
+
+/**
+ * @brief This function parse the Media type record.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ */
+void NDEF::NDEF_ParseMediaType( sRecordInfo *pRecordStruct )
+{
+ if( !memcmp( &(pRecordStruct->Type), VCARD_TYPE_STRING, pRecordStruct->TypeLength ) )
+ pRecordStruct->NDEF_Type = VCARD_TYPE;
+ else if( !memcmp( &(pRecordStruct->Type), XVCARD_TYPE_STRING, pRecordStruct->TypeLength ) )
+ pRecordStruct->NDEF_Type = VCARD_TYPE;
+ else if( !memcmp( &(pRecordStruct->Type), XVCARD2_TYPE_STRING, pRecordStruct->TypeLength ) )
+ pRecordStruct->NDEF_Type = VCARD_TYPE;
+ else
+ pRecordStruct->NDEF_Type = UNKNOWN_TYPE;
+}
+
+/**
+ * @brief This function parse the Forum External type record.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ */
+void NDEF::NDEF_ParseForumExternalType( sRecordInfo *pRecordStruct )
+{
+ if( !memcmp( &(pRecordStruct->Type), M24SR_DISCOVERY_APP_STRING, pRecordStruct->TypeLength ) )
+ pRecordStruct->NDEF_Type = M24SR_DISCOVERY_APP_TYPE;
+ else
+ pRecordStruct->NDEF_Type = UNKNOWN_TYPE;
+}
+
+/**
+ * @brief This function parse the URI type record.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ */
+void NDEF::NDEF_ParseURI( sRecordInfo *pRecordStruct )
+{
+ uint8_t* pPayload;
+
+ pPayload = (uint8_t*)( pRecordStruct->PayloadBufferAdd );
+ pPayload++; /* to skip URI identifier first URI payload byte */
+
+ if( !memcmp( pPayload, SMS_TYPE_STRING, strlen(SMS_TYPE_STRING) ) )
+ {
+ pRecordStruct->NDEF_Type = URI_SMS_TYPE;
+ }
+ else if( !memcmp( pPayload, GEO_TYPE_STRING, strlen(GEO_TYPE_STRING) ) )
+ {
+ pRecordStruct->NDEF_Type = URI_GEO_TYPE;
+ }
+ else
+ pRecordStruct->NDEF_Type = UNKNOWN_TYPE;
+}
+
+/**
+ * @brief This function parse the Smart Poster.
+ * @param pRecordStruct : pointer on the record structure to fill.
+ */
+void NDEF::NDEF_ParseSP( sRecordInfo *pRecordStruct )
+{
+ uint8_t* pPayload;
+ uint32_t PayloadSize = 0;
+ uint32_t SPPayloadSize = 0;
+ uint32_t OffsetInSPPayload = 0;
+ uint32_t RecordPosition = 0;
+ sRecordInfo *pSPRecordStruct;
+
+ /* initialize variable with size of the payload and poiter on data */
+ PayloadSize = ((uint32_t)(pRecordStruct->PayloadLength3) << 24) | ((uint32_t)(pRecordStruct->PayloadLength2) << 16) |
+ ((uint32_t)(pRecordStruct->PayloadLength1) << 8) | pRecordStruct->PayloadLength0;
+
+ pPayload = (uint8_t*)( pRecordStruct->PayloadBufferAdd );
+
+ pSPRecordStruct = SPRecordStructAdd[0];
+
+ /* Initailize the number of record find in the SP payload */
+ pRecordStruct->NbOfRecordInSPPayload = 0;
+
+ do
+ {
+ pSPRecordStruct = SPRecordStructAdd[RecordPosition];
+ /* identify the record in the SP payload */
+ if( NDEF_IdentifySPRecord( pSPRecordStruct, pPayload ) == NDEF_OK )
+ {
+ /* store add of structure that will contain the other record information */
+ pRecordStruct->NbOfRecordInSPPayload++;
+ pRecordStruct->SPRecordStructAdd[RecordPosition] = pSPRecordStruct;
+
+ /* After SPRecord + First Record check if we are at the end of NDEF file */
+ SPPayloadSize = ((uint32_t)(pSPRecordStruct->PayloadLength3) << 24) | ((uint32_t)(pSPRecordStruct->PayloadLength2) << 16) |
+ ((uint32_t)(pSPRecordStruct->PayloadLength1) << 8) | pSPRecordStruct->PayloadLength0;
+
+ OffsetInSPPayload += pSPRecordStruct->PayloadOffset + SPPayloadSize;
+ pPayload += OffsetInSPPayload;
+ }
+ else /* Recommended Action Record for example */
+ {
+ SPPayloadSize = 0;
+ }
+ RecordPosition++;
+ }
+ while( (OffsetInSPPayload < PayloadSize) && RecordPosition<SP_MAX_RECORD); /* there is another record */
+}
+
+/**
+ * @}
+ */
+
+/** @defgroup libNDEF_Public_Functions
+ * @{
+ */
+
+
+/**
+ * @brief This function identify the NDEF message stored in tag.
+ * @param pRecordStruct : Structure to fill with record information.
+ * @param pNDEF : pointer on the NDEF message data.
+ * @retval NDEF_OK : record struct filled.
+ * @retval NDEF_ERROR : record struct not updated.
+ */
+uint16_t NDEF::NDEF_IdentifyNDEF( sRecordInfo *pRecordStruct, uint8_t* pNDEF )
+{
+ uint16_t status = NDEF_ERROR;
+ uint16_t SizeOfRecordHeader, TypeNbByte, PayloadLengthField, IDLengthField, IDNbByte;
+ uint32_t PayloadSize;
+
+ /* check NDEF present */
+ if( NDEF_IsNDEFPresent() != NDEF_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ /* Analyse record layout */
+ ReadData( FIRST_RECORD_OFFSET, 1, pNDEF );
+
+ /* Is ID length field present */
+ if( (*pNDEF) & IL_Mask )
+ {
+ IDLengthField = ID_LENGTH_FIELD;
+ }
+ else
+ {
+ IDLengthField = 0;
+ }
+
+ /* it's a SR */
+ if( (*pNDEF) & SR_Mask )
+ {
+ /* Analyse short record layout */
+ ReadData( FIRST_RECORD_OFFSET, 4, pNDEF );
+ TypeNbByte = pNDEF[1];
+ PayloadLengthField = 1;
+ if( IDLengthField == ID_LENGTH_FIELD )
+ IDNbByte = pNDEF[3];
+ else
+ IDNbByte = 0;
+ }
+ else
+ {
+ /* Analyse normal record layout */
+ ReadData( FIRST_RECORD_OFFSET, 7, pNDEF );
+ TypeNbByte = pNDEF[1];
+ PayloadLengthField = 4;
+ if( IDLengthField == ID_LENGTH_FIELD )
+ IDNbByte = pNDEF[6];
+ else
+ IDNbByte = 0;
+ }
+
+ SizeOfRecordHeader = RECORD_FLAG_FIELD + TYPE_LENGTH_FIELD + PayloadLengthField + IDLengthField + TypeNbByte + IDNbByte;
+
+ /* Read record header */
+ ReadData( FIRST_RECORD_OFFSET, SizeOfRecordHeader, pNDEF );
+ /* it's a SR */
+ if( pNDEF[0] & SR_Mask )
+ {
+ pRecordStruct->RecordFlags = pNDEF[0];
+ pRecordStruct->TypeLength = TypeNbByte;
+ pRecordStruct->PayloadLength3 = 0;
+ pRecordStruct->PayloadLength2 = 0;
+ pRecordStruct->PayloadLength1 = 0;
+ pRecordStruct->PayloadLength0 = pNDEF[2];
+ pRecordStruct->IDLength = IDNbByte;
+ memcpy( pRecordStruct->Type, &pNDEF[3+IDNbByte], TypeNbByte );
+ memcpy( pRecordStruct->ID, &pNDEF[3+IDNbByte+TypeNbByte], IDNbByte );
+ pRecordStruct->PayloadOffset = SizeOfRecordHeader;
+ }
+ else
+ {
+ pRecordStruct->RecordFlags = pNDEF[0];
+ pRecordStruct->TypeLength = TypeNbByte;
+ pRecordStruct->PayloadLength3 = pNDEF[2];
+ pRecordStruct->PayloadLength2 = pNDEF[3];
+ pRecordStruct->PayloadLength1 = pNDEF[4];
+ pRecordStruct->PayloadLength0 = pNDEF[5];
+ pRecordStruct->IDLength = IDNbByte;
+ memcpy( pRecordStruct->Type, &pNDEF[6+IDNbByte], TypeNbByte );
+ memcpy( pRecordStruct->ID, &pNDEF[6+IDNbByte+TypeNbByte], IDNbByte );
+ pRecordStruct->PayloadOffset = SizeOfRecordHeader;
+ }
+
+ PayloadSize = ((uint32_t)(pRecordStruct->PayloadLength3) << 24) | ((uint32_t)(pRecordStruct->PayloadLength2) << 16) |
+ ((uint32_t)(pRecordStruct->PayloadLength1) << 8) | pRecordStruct->PayloadLength0;
+
+ /* read Payload */
+ status = ReadData( (uint16_t)((FIRST_RECORD_OFFSET) + pRecordStruct->PayloadOffset) , PayloadSize , pNDEF );
+
+ if( status != NDEF_OK )
+ return NDEF_ERROR;
+ else
+ pRecordStruct->PayloadBufferAdd = (uint32_t)(pNDEF);
+
+ NDEF_ParseRecordHeader( pRecordStruct );
+
+ return NDEF_OK;
+}
+
+/**
+ * @brief This function read the NDEF content of the TAG.
+ * @param pNDEF : pointer on the buffer to store NDEF data.
+ * @retval NDEF_OK : NDEF file data retrieve and store in the buffer.
+ * @retval NDEF_ERROR : not able to read NDEF from tag.
+ * @retval NDEF_ERROR_MEMORY_INTERNAL : Cannot read tag.
+ * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported or not present.
+ * @retval NDEF_ERROR_MEMORY_TAG : Size not compatible with memory.
+ * @retval NDEF_ERROR_LOCKED : Tag locked, cannot be read.
+ */
+uint16_t NDEF::NDEF_ReadNDEF( uint8_t* pNDEF )
+{
+ uint16_t status = NDEF_ERROR;
+ uint16_t NDEF_Size = 0;
+
+ status = ReadData( 0, 2, pNDEF );
+
+ if( status == NDEF_OK )
+ {
+ NDEF_Size = (uint16_t)(*pNDEF << 8);
+ NDEF_Size = NDEF_Size | (uint16_t)(*++pNDEF );
+
+ status = ReadData( 0, NDEF_Size + 2, --pNDEF );
+ }
+
+ return status;
+}
+
+/**
+ * @brief This function write the NDEF in the TAG.
+ * @param pNDEF : pointer on the buffer containing the NDEF data.
+ * @retval NDEF_OK : NDEF file data written in the tag.
+ * @retval NDEF_ERROR : not able to store NDEF in tag.
+ * @retval NDEF_ERROR_MEMORY_INTERNAL : Cannot write to tag.
+ * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported or not present.
+ * @retval NDEF_ERROR_MEMORY_TAG : Size not compatible with memory.
+ * @retval NDEF_ERROR_LOCKED : Tag locked, cannot be write.
+ */
+uint16_t NDEF::NDEF_WriteNDEF( uint8_t *pNDEF )
+{
+ uint16_t status = NDEF_ERROR;
+ uint16_t NDEF_Size = 0;
+
+ NDEF_Size = (uint16_t)(*pNDEF << 8);
+ NDEF_Size = NDEF_Size | (uint16_t)(*++pNDEF );
+
+ status = WriteData( 0, NDEF_Size + 2, --pNDEF );
+
+ return status;
+}
+
+/**
+ * @brief This function identify the NDEF message stored in tag.
+ * @param pRecordStruct : Structure to fill with record information.
+ * @param pNDEF : pointer on the NDEF message data.
+ * @retval NDEF_OK : record struct filled.
+ * @retval NDEF_ERROR : record struct not updated.
+ */
+uint16_t NDEF::NDEF_IdentifyBuffer( sRecordInfo *pRecordStruct, uint8_t* pNDEF )
+{
+ uint16_t SizeOfRecordHeader, TypeNbByte, PayloadLengthField, IDLengthField, IDNbByte;
+
+ /* Is ID length field present */
+ if( (*pNDEF) & IL_Mask )
+ {
+ IDLengthField = ID_LENGTH_FIELD;
+ }
+ else
+ {
+ IDLengthField = 0;
+ }
+
+ /* it's a SR */
+ if( (*pNDEF) & SR_Mask )
+ {
+ /* Analyse short record layout */
+ TypeNbByte = pNDEF[1];
+ PayloadLengthField = 1;
+ if( IDLengthField == ID_LENGTH_FIELD )
+ IDNbByte = pNDEF[3];
+ else
+ IDNbByte = 0;
+ }
+ else
+ {
+ /* Analyse normal record layout */
+ TypeNbByte = pNDEF[1];
+ PayloadLengthField = 4;
+ if( IDLengthField == ID_LENGTH_FIELD )
+ IDNbByte = pNDEF[6];
+ else
+ IDNbByte = 0;
+ }
+
+ SizeOfRecordHeader = RECORD_FLAG_FIELD + TYPE_LENGTH_FIELD + PayloadLengthField + IDLengthField + TypeNbByte + IDNbByte;
+
+ /* it's a SR */
+ if( pNDEF[0] & SR_Mask )
+ {
+ pRecordStruct->RecordFlags = pNDEF[0];
+ pRecordStruct->TypeLength = TypeNbByte;
+ pRecordStruct->PayloadLength3 = 0;
+ pRecordStruct->PayloadLength2 = 0;
+ pRecordStruct->PayloadLength1 = 0;
+ pRecordStruct->PayloadLength0 = pNDEF[2];
+ pRecordStruct->IDLength = IDNbByte;
+ memcpy( pRecordStruct->Type, &pNDEF[3+IDNbByte], TypeNbByte );
+ memcpy( pRecordStruct->ID, &pNDEF[3+IDNbByte+TypeNbByte], IDNbByte );
+ pRecordStruct->PayloadOffset = SizeOfRecordHeader;
+ }
+ else
+ {
+ pRecordStruct->RecordFlags = pNDEF[0];
+ pRecordStruct->TypeLength = TypeNbByte;
+ pRecordStruct->PayloadLength3 = pNDEF[2];
+ pRecordStruct->PayloadLength2 = pNDEF[3];
+ pRecordStruct->PayloadLength1 = pNDEF[4];
+ pRecordStruct->PayloadLength0 = pNDEF[5];
+ pRecordStruct->IDLength = IDNbByte;
+ memcpy( pRecordStruct->Type, &pNDEF[6+IDNbByte], TypeNbByte );
+ memcpy( pRecordStruct->ID, &pNDEF[6+IDNbByte+TypeNbByte], IDNbByte );
+ pRecordStruct->PayloadOffset = SizeOfRecordHeader;
+ }
+
+ pRecordStruct->PayloadBufferAdd = (uint32_t)(&pNDEF[pRecordStruct->PayloadOffset]);
+
+ NDEF_ParseRecordHeader( pRecordStruct );
+
+ return NDEF_OK;
+}
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Lib_NDEF/lib_NDEF.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,297 @@
+/**
+ ******************************************************************************
+ * @file lib_NDEF.h
+ * @author MMY Application Team
+ * @version $Revision: 1329 $
+ * @date $Date: 2015-11-05 10:34:25 +0100 (Thu, 05 Nov 2015) $
+ * @brief This file help to manage NDEF file.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT 2015 STMicroelectronics</center></h2>
+ *
+ * Licensed under ST MYLIBERTY SOFTWARE LICENSE AGREEMENT (the "License");
+ * You may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.st.com/myliberty
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+ * AND SPECIFICALLY DISCLAIMING THE IMPLIED WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************
+ */
+
+/* Define to prevent recursive inclusion -------------------------------------*/
+#ifndef __LIB_NDEF_H
+#define __LIB_NDEF_H
+
+
+/* Includes ------------------------------------------------------------------*/
+/* include file which match the HW configuration */
+//#include "common.h"
+//#include "lib_wrapper.h"
+#include <stdint.h>
+#include "tagtype5_wrapper.h"
+
+#define NDEF_ACTION_COMPLETED 0x9000
+
+#ifndef errorchk
+#define errorchk(fCall) if (status = (fCall), status != NDEF_ACTION_COMPLETED) \
+ {goto Error;} else
+#endif
+
+/* Error codes for Higher level */
+
+
+#define NFCTAG_4M_SIZE 0x200
+#define NFCTAG_16M_SIZE 0x800
+#define NFCTAG_64M_SIZE 0x2000
+#ifndef MIN
+#define MIN(x, y) (((x) < (y)) ? (x) : (y))
+#endif
+
+/* Exported constants --------------------------------------------------------*/
+#define MAX_NDEF_MEM 0x200
+#define M24LR_MAX_SIZE NFCTAG_4M_SIZE
+#define M24LR_NDEF_MAX_SIZE MIN(M24LR_MAX_SIZE,MAX_NDEF_MEM)
+#define NFC_DEVICE_MAX_NDEFMEMORY M24LR_NDEF_MAX_SIZE
+
+#define NDEF_OK 0x00
+#define NDEF_ERROR 1
+#define NDEF_ERROR_MEMORY_TAG 2
+#define NDEF_ERROR_MEMORY_INTERNAL 3
+#define NDEF_ERROR_LOCKED 4
+#define NDEF_ERROR_NOT_FORMATED 5
+
+#define NDEF_MAX_SIZE NFC_DEVICE_MAX_NDEFMEMORY
+
+#define NDEF_SIZE_OFFSET 0
+#define FIRST_RECORD_OFFSET 2
+
+#define RECORD_FLAG_FIELD 1
+#define TYPE_LENGTH_FIELD 1
+#define ID_LENGTH_FIELD 1
+
+
+#define MB_Mask ((uint8_t)(0x80))
+#define ME_Mask ((uint8_t)(0x40))
+#define CF_Mask ((uint8_t)(0x20))
+#define SR_Mask ((uint8_t)(0x10))
+#define IL_Mask ((uint8_t)(0x08))
+#define TNF_Mask ((uint8_t)(0x07))
+
+#define TNF_Empty 0x00
+#define TNF_WellKnown 0x01
+#define TNF_MediaType 0x02
+#define TNF_AbsoluteURI 0x03
+#define TNF_NFCForumExternal 0x04
+#define TNF_Unknown 0x05
+#define TNF_Unchanged 0x06
+#define TNF_Reserved 0x07
+
+#define SP_MAX_RECORD 4
+
+#define AAR_TYPE_STRING "android.com:pkg"
+#define AAR_TYPE_STRING_LENGTH 15
+
+#define M24SR_DISCOVERY_APP_STRING "st.com:m24sr_discovery_democtrl"
+#define M24SR_DISCOVERY_APP_STRING_LENGTH 31
+
+#define VCARD_TYPE_STRING "text/vcard"
+#define VCARD_TYPE_STRING_LENGTH 10
+
+#define XVCARD_TYPE_STRING "text/x-vCard"
+#define XVCARD_TYPE_STRING_LENGTH 12
+
+#define XVCARD2_TYPE_STRING "text/x-vcard"
+#define XVCARD2_TYPE_STRING_LENGTH 12
+
+#define SMART_POSTER_TYPE_STRING "Sp"
+#define SMART_POSTER_TYPE_STRING_LENGTH 2
+
+#define URI_TYPE_STRING "U"
+#define URI_TYPE_STRING_LENGTH 1
+
+#define SMS_TYPE_STRING "sms:"
+#define SMS_TYPE_STRING_LENGTH 4
+
+#define GEO_TYPE_STRING "geo:"
+#define GEO_TYPE_STRING_LENGTH 4
+
+#define URI_LATITUDE_END ","
+#define URI_LATITUDE_END_LENGTH 1
+
+#define EMAIL_TYPE_STRING "mailto:"
+#define EMAIL_TYPE_STRING_LENGTH 7
+
+#define URI_FIRST_DATA_END "?"
+#define URI_FIRST_DATA_END_LENGTH 1
+
+#define SUBJECT_BEGIN_STRING "subject="
+#define SUBJECT_BEGIN_STRING_LENGTH 8
+
+#define MESSAGE_BEGIN_STRING "body="
+#define MESSAGE_BEGIN_STRING_LENGTH 5
+
+#define URI_SECOND_DATA_END "&"
+#define URI_SECOND_DATA_END_LENGTH 1
+
+#define TEXT_TYPE_STRING "T"
+#define TEXT_TYPE_STRING_LENGTH 1
+
+#define ISO_ENGLISH_CODE_STRING "en"
+#define ISO_ENGLISH_CODE_STRING_LENGTH 2
+
+
+#define URI_ID_0x00 0x00
+#define URI_ID_0x01 0x01
+#define URI_ID_0x02 0x02
+#define URI_ID_0x03 0x03
+#define URI_ID_0x04 0x04
+#define URI_ID_0x05 0x05
+#define URI_ID_0x06 0x06
+#define URI_ID_0x07 0x07
+#define URI_ID_0x08 0x08
+#define URI_ID_0x09 0x09
+#define URI_ID_0x0A 0x0A
+#define URI_ID_0x0B 0x0B
+#define URI_ID_0x0C 0x0C
+#define URI_ID_0x0D 0x0D
+#define URI_ID_0x0E 0x0E
+#define URI_ID_0x0F 0x0F
+#define URI_ID_0x10 0x10
+#define URI_ID_0x11 0x11
+#define URI_ID_0x12 0x12
+#define URI_ID_0x13 0x13
+#define URI_ID_0x14 0x14
+#define URI_ID_0x15 0x15
+#define URI_ID_0x16 0x16
+#define URI_ID_0x17 0x17
+#define URI_ID_0x18 0x18
+#define URI_ID_0x19 0x19
+#define URI_ID_0x1A 0x1A
+#define URI_ID_0x1B 0x1B
+#define URI_ID_0x1C 0x1C
+#define URI_ID_0x1D 0x1D
+#define URI_ID_0x1E 0x1E
+#define URI_ID_0x1F 0x1F
+#define URI_ID_0x20 0x20
+#define URI_ID_0x21 0x21
+#define URI_ID_0x22 0x22
+#define URI_ID_0x23 0x23
+#define URI_RFU 0x24
+
+#define URI_ID_0x01_STRING "http://www.\0"
+#define URI_ID_0x02_STRING "https://www.\0"
+#define URI_ID_0x03_STRING "http://\0"
+#define URI_ID_0x04_STRING "https://\0"
+#define URI_ID_0x05_STRING "tel:\0"
+#define URI_ID_0x06_STRING "mailto:\0"
+#define URI_ID_0x07_STRING "ftp://anonymous:anonymous@\0"
+#define URI_ID_0x08_STRING "ftp://ftp.\0"
+#define URI_ID_0x09_STRING "ftps://\0"
+#define URI_ID_0x0A_STRING "sftp://\0"
+#define URI_ID_0x0B_STRING "smb://\0"
+#define URI_ID_0x0C_STRING "nfs://\0"
+#define URI_ID_0x0D_STRING "ftp://\0"
+#define URI_ID_0x0E_STRING "dav://\0"
+#define URI_ID_0x0F_STRING "news:\0"
+#define URI_ID_0x10_STRING "telnet://\0"
+#define URI_ID_0x11_STRING "imap:\0"
+#define URI_ID_0x12_STRING "rtsp://\0"
+#define URI_ID_0x13_STRING "urn:\0"
+#define URI_ID_0x14_STRING "pop:\0"
+#define URI_ID_0x15_STRING "sip:\0"
+#define URI_ID_0x16_STRING "sips:\0"
+#define URI_ID_0x17_STRING "tftp:\0"
+#define URI_ID_0x18_STRING "btspp://\0"
+#define URI_ID_0x19_STRING "btl2cap://\0"
+#define URI_ID_0x1A_STRING "btgoep://\0"
+#define URI_ID_0x1B_STRING "tcpobex://\0"
+#define URI_ID_0x1C_STRING "irdaobex://\0"
+#define URI_ID_0x1D_STRING "file://\0"
+#define URI_ID_0x1E_STRING "urn:epc:id:\0"
+#define URI_ID_0x1F_STRING "urn:epc:tag\0"
+#define URI_ID_0x20_STRING "urn:epc:pat:\0"
+#define URI_ID_0x21_STRING "urn:epc:raw:\0"
+#define URI_ID_0x22_STRING "urn:epc:\0"
+#define URI_ID_0x23_STRING "urn:nfc:\0"
+
+typedef enum
+{
+ UNKNOWN_TYPE = 0,
+ VCARD_TYPE,
+ WELL_KNOWN_ABRIDGED_URI_TYPE,
+ URI_SMS_TYPE,
+ URI_GEO_TYPE,
+ URI_EMAIL_TYPE,
+ SMARTPOSTER_TYPE,
+ URL_TYPE,
+ TEXT_TYPE,
+ BT_TYPE,
+ /* list of "external type" known by this demo, other external type will be addressed as UNKNWON_TYPE */
+ M24SR_DISCOVERY_APP_TYPE
+} NDEF_TypeDef;
+
+//typedef struct sRecordInfo sRecordInfo;
+typedef struct sRecordInfo
+{
+ uint8_t RecordFlags;
+ uint8_t TypeLength;
+ uint8_t PayloadLength3;
+ uint8_t PayloadLength2;
+ uint8_t PayloadLength1;
+ uint8_t PayloadLength0;
+ uint8_t IDLength;
+ uint8_t Type[0xFF];
+ uint8_t ID[0xFF];
+ uint16_t PayloadOffset;
+ uint32_t PayloadBufferAdd; /* add where payload content has been stored */
+ NDEF_TypeDef NDEF_Type; /* to store identification ID for application */
+ sRecordInfo *SPRecordStructAdd[SP_MAX_RECORD]; /*in case of smart poster array to store add of other sRecordInfo struct */
+ uint8_t NbOfRecordInSPPayload;
+}sRecordInfo;
+
+class NDEF : public NFCType5 {
+public:
+
+uint16_t NDEF_IsNDEFPresent( void );
+ uint16_t NDEF_ParseRecordHeader( sRecordInfo *pRecordStruct );
+ void NDEF_ParseWellKnownType( sRecordInfo *pRecordStruct );
+void NDEF_ParseMediaType( sRecordInfo *pRecordStruct );
+void NDEF_ParseForumExternalType( sRecordInfo *pRecordStruct );
+ void NDEF_ParseURI( sRecordInfo *pRecordStruct );
+void NDEF_ParseSP( sRecordInfo *pRecordStruct );
+uint16_t NDEF_IdentifySPRecord( sRecordInfo *pRecordStruct, uint8_t* pPayload );
+uint16_t NDEF_IdentifyNDEF( sRecordInfo *pRecordStruct, uint8_t* pNDEF );
+uint16_t NDEF_ReadNDEF( uint8_t* pNDEF );
+uint16_t NDEF_WriteNDEF( uint8_t *pNDEF );
+uint16_t NDEF_IdentifyBuffer( sRecordInfo *pRecordStruct, uint8_t* pNDEF );
+
+void NDEF_initialize(void);
+uint8_t NDEF_Buffer [NDEF_MAX_SIZE];
+
+NDEF()
+{
+ SPRecordStructAdd[0] = &SPRecordStruct1;
+ SPRecordStructAdd[1] = &SPRecordStruct2;
+ SPRecordStructAdd[2] = &SPRecordStruct3;
+ SPRecordStructAdd[3] = &SPRecordStruct4;
+
+}
+
+/* In case of smart Poster composed with different record, 3 records supported so far */
+sRecordInfo SPRecordStruct1, SPRecordStruct2, SPRecordStruct3, SPRecordStruct4;
+sRecordInfo *SPRecordStructAdd[SP_MAX_RECORD];
+};
+
+#endif /* __LIB_NDEF_H */
+
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Lib_NDEF/lib_NDEF_URI.cpp Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,550 @@
+/**
+ ******************************************************************************
+ * @file lib_NDEF_URI.c
+ * @author MMY Application Team
+ * @version $Revision: 1583 $
+ * @date $Date: 2016-02-03 15:06:51 +0100 (Wed, 03 Feb 2016) $
+ * @brief This file help to manage NDEF file that represent URI.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT 2015 STMicroelectronics</center></h2>
+ *
+ * Licensed under ST MYLIBERTY SOFTWARE LICENSE AGREEMENT (the "License");
+ * You may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.st.com/myliberty
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+ * AND SPECIFICALLY DISCLAIMING THE IMPLIED WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************
+ */
+/* Includes ------------------------------------------------------------------*/
+#include "lib_NDEF_URI.h"
+#include <string.h>
+
+/** @addtogroup NFC_libraries
+ * @{
+ * @brief <b>This is the library used to manage the content of the TAG (data)
+ * But also the specific feature of the tag, for instance
+ * password, gpo... </b>
+ */
+
+
+/** @addtogroup libNFC_FORUM
+ * @{
+ * @brief This part of the library manage data which follow NFC forum organisation.
+ */
+
+/**
+ * @brief This buffer contains the data send/received by TAG
+ */
+extern uint8_t NDEF_Buffer [];
+
+
+
+/**
+ * @brief This function read the URI information and store data in a structure.
+ * @param pRecordStruct : Pointer on the record structure.
+ * @param pURI : pointer on the structure to fill.
+ */
+void NDEF_URI::NDEF_Parse_WellKnowType( sRecordInfo *pRecordStruct, sURI_Info* pURI )
+{
+ uint32_t PayloadSize;
+ uint8_t Offset;
+ uint8_t* pPayload;
+
+ pPayload = (uint8_t*)(pRecordStruct->PayloadBufferAdd);
+
+ switch( *pPayload )
+ {
+ case URI_ID_0x01:
+ memcpy( pURI->protocol, URI_ID_0x01_STRING, strlen(URI_ID_0x01_STRING) );
+ Offset = strlen( URI_ID_0x01_STRING );
+ break;
+
+ case URI_ID_0x02:
+ memcpy( pURI->protocol, URI_ID_0x02_STRING, strlen(URI_ID_0x02_STRING) );
+ Offset = strlen( URI_ID_0x02_STRING );
+ break;
+
+ case URI_ID_0x03:
+ memcpy( pURI->protocol, URI_ID_0x03_STRING, strlen(URI_ID_0x03_STRING) );
+ Offset = strlen( URI_ID_0x03_STRING );
+ break;
+
+ case URI_ID_0x04:
+ memcpy( pURI->protocol, URI_ID_0x04_STRING, strlen(URI_ID_0x04_STRING) );
+ Offset = strlen( URI_ID_0x04_STRING );
+ break;
+
+ case URI_ID_0x05:
+ memcpy( pURI->protocol, URI_ID_0x05_STRING, strlen(URI_ID_0x05_STRING) );
+ Offset = strlen( URI_ID_0x05_STRING );
+ break;
+
+ case URI_ID_0x06:
+ memcpy( pURI->protocol, URI_ID_0x06_STRING, strlen(URI_ID_0x06_STRING) );
+ Offset = strlen( URI_ID_0x06_STRING );
+ break;
+
+ case URI_ID_0x07:
+ memcpy( pURI->protocol, URI_ID_0x07_STRING, strlen(URI_ID_0x07_STRING) );
+ Offset = strlen( URI_ID_0x07_STRING );
+ break;
+
+ case URI_ID_0x08:
+ memcpy( pURI->protocol, URI_ID_0x08_STRING, strlen(URI_ID_0x08_STRING) );
+ Offset = strlen( URI_ID_0x08_STRING );
+ break;
+
+ case URI_ID_0x09:
+ memcpy( pURI->protocol, URI_ID_0x09_STRING, strlen(URI_ID_0x09_STRING) );
+ Offset = strlen( URI_ID_0x09_STRING );
+ break;
+
+ case URI_ID_0x0A:
+ memcpy( pURI->protocol, URI_ID_0x0A_STRING, strlen(URI_ID_0x0A_STRING) );
+ Offset = strlen( URI_ID_0x0A_STRING );
+ break;
+
+ case URI_ID_0x0B:
+ memcpy( pURI->protocol, URI_ID_0x0B_STRING, strlen(URI_ID_0x0B_STRING) );
+ Offset = strlen( URI_ID_0x0B_STRING );
+ break;
+
+ case URI_ID_0x0C:
+ memcpy( pURI->protocol, URI_ID_0x0C_STRING, strlen(URI_ID_0x0C_STRING) );
+ Offset = strlen( URI_ID_0x0C_STRING );
+ break;
+
+ case URI_ID_0x0D:
+ memcpy( pURI->protocol, URI_ID_0x0D_STRING, strlen(URI_ID_0x0D_STRING) );
+ Offset = strlen( URI_ID_0x0D_STRING );
+ break;
+
+ case URI_ID_0x0E:
+ memcpy( pURI->protocol, URI_ID_0x0E_STRING, strlen(URI_ID_0x0E_STRING) );
+ Offset = strlen( URI_ID_0x0E_STRING );
+ break;
+
+ case URI_ID_0x0F:
+ memcpy( pURI->protocol, URI_ID_0x0F_STRING, strlen(URI_ID_0x0F_STRING) );
+ Offset = strlen( URI_ID_0x0F_STRING );
+ break;
+
+ case URI_ID_0x10:
+ memcpy( pURI->protocol, URI_ID_0x10_STRING, strlen(URI_ID_0x10_STRING) );
+ Offset = strlen( URI_ID_0x10_STRING );
+ break;
+
+ case URI_ID_0x11:
+ memcpy( pURI->protocol, URI_ID_0x11_STRING, strlen(URI_ID_0x11_STRING) );
+ Offset = strlen( URI_ID_0x11_STRING );
+ break;
+
+ case URI_ID_0x12:
+ memcpy( pURI->protocol, URI_ID_0x12_STRING, strlen(URI_ID_0x12_STRING) );
+ Offset = strlen( URI_ID_0x12_STRING );
+ break;
+
+ case URI_ID_0x13:
+ memcpy( pURI->protocol, URI_ID_0x13_STRING, strlen(URI_ID_0x13_STRING) );
+ Offset = strlen( URI_ID_0x13_STRING );
+ break;
+
+ case URI_ID_0x14:
+ memcpy( pURI->protocol, URI_ID_0x14_STRING, strlen(URI_ID_0x14_STRING) );
+ Offset = strlen( URI_ID_0x14_STRING );
+ break;
+
+ case URI_ID_0x15:
+ memcpy( pURI->protocol, URI_ID_0x15_STRING, strlen(URI_ID_0x15_STRING) );
+ Offset = strlen( URI_ID_0x15_STRING );
+ break;
+
+ case URI_ID_0x16:
+ memcpy( pURI->protocol, URI_ID_0x16_STRING, strlen(URI_ID_0x16_STRING) );
+ Offset = strlen( URI_ID_0x16_STRING );
+ break;
+
+ case URI_ID_0x17:
+ memcpy( pURI->protocol, URI_ID_0x17_STRING, strlen(URI_ID_0x17_STRING) );
+ Offset = strlen( URI_ID_0x17_STRING );
+ break;
+
+ case URI_ID_0x18:
+ memcpy( pURI->protocol, URI_ID_0x18_STRING, strlen(URI_ID_0x18_STRING) );
+ Offset = strlen( URI_ID_0x18_STRING );
+ break;
+
+ case URI_ID_0x19:
+ memcpy( pURI->protocol, URI_ID_0x19_STRING, strlen(URI_ID_0x19_STRING) );
+ Offset = strlen( URI_ID_0x19_STRING );
+ break;
+
+ case URI_ID_0x1A:
+ memcpy( pURI->protocol, URI_ID_0x1A_STRING, strlen(URI_ID_0x1A_STRING) );
+ Offset = strlen( URI_ID_0x1A_STRING );
+ break;
+
+ case URI_ID_0x1B:
+ memcpy( pURI->protocol, URI_ID_0x1B_STRING, strlen(URI_ID_0x1B_STRING) );
+ Offset = strlen( URI_ID_0x1B_STRING );
+ break;
+
+ case URI_ID_0x1C:
+ memcpy( pURI->protocol, URI_ID_0x1C_STRING, strlen(URI_ID_0x1C_STRING) );
+ Offset = strlen( URI_ID_0x1C_STRING );
+ break;
+
+ case URI_ID_0x1D:
+ memcpy( pURI->protocol, URI_ID_0x1D_STRING, strlen(URI_ID_0x1D_STRING) );
+ Offset = strlen( URI_ID_0x1D_STRING );
+ break;
+
+ case URI_ID_0x1E:
+ memcpy( pURI->protocol, URI_ID_0x1E_STRING, strlen(URI_ID_0x1E_STRING) );
+ Offset = strlen( URI_ID_0x1E_STRING );
+ break;
+
+ case URI_ID_0x1F:
+ memcpy( pURI->protocol, URI_ID_0x1F_STRING, strlen(URI_ID_0x1F_STRING) );
+ Offset = strlen( URI_ID_0x1F_STRING );
+ break;
+
+ case URI_ID_0x20:
+ memcpy( pURI->protocol, URI_ID_0x20_STRING, strlen(URI_ID_0x20_STRING) );
+ Offset = strlen( URI_ID_0x20_STRING );
+ break;
+
+ case URI_ID_0x21:
+ memcpy( pURI->protocol, URI_ID_0x21_STRING, strlen(URI_ID_0x21_STRING) );
+ Offset = strlen( URI_ID_0x21_STRING );
+ break;
+
+ case URI_ID_0x22:
+ memcpy( pURI->protocol, URI_ID_0x22_STRING, strlen(URI_ID_0x22_STRING) );
+ Offset = strlen( URI_ID_0x22_STRING );
+ break;
+
+ case URI_ID_0x23:
+ memcpy( pURI->protocol, URI_ID_0x23_STRING, strlen(URI_ID_0x23_STRING) );
+ Offset = strlen( URI_ID_0x23_STRING );
+ break;
+
+ default:
+ Offset = 0;
+ /* Should not happened */
+ break;
+ }
+ /* add end of string character */
+ pURI->protocol[Offset] = '\0';
+
+ pPayload++; /* go after well know byte */
+
+ PayloadSize = ((uint32_t)(pRecordStruct->PayloadLength3) << 24) | ((uint32_t)(pRecordStruct->PayloadLength2) << 16) |
+ ((uint32_t)(pRecordStruct->PayloadLength1) << 8) | pRecordStruct->PayloadLength0;
+
+ PayloadSize = PayloadSize - 1; /* remove well know byte */
+
+ memcpy( pURI->URI_Message, pPayload, PayloadSize );
+ /* add end of string character */
+ pURI->URI_Message[PayloadSize] = '\0';
+
+}
+
+/**
+ * @}
+ */
+
+/** @defgroup libURI_Public_Functions
+ * @{
+ * @brief This file is used to manage URI (stored or loaded in tag)
+ */
+
+/**
+ * @brief This function read NDEF and retrieve URI information if any.
+ * @param pRecordStruct : Pointer on the record structure.
+ * @param pURI : pointer on the structure to fill.
+ * @retval NDEF_OK : URI information from NDEF have been retrieved.
+ * @retval NDEF_ERROR : Not able to retrieve URI information.
+ */
+uint16_t NDEF_URI::NDEF_ReadURI( sRecordInfo *pRecordStruct, sURI_Info *pURI )
+{
+ uint16_t status = NDEF_ERROR;
+ sRecordInfo *pSPRecordStruct;
+ uint32_t PayloadSize, RecordPosition;
+ uint8_t* pData;
+
+ if( pRecordStruct->NDEF_Type == WELL_KNOWN_ABRIDGED_URI_TYPE )
+ {
+ NDEF_Parse_WellKnowType( pRecordStruct, pURI );
+ status = NDEF_OK;
+ }
+ else if( pRecordStruct->NDEF_Type == SMARTPOSTER_TYPE )
+ {
+ for( RecordPosition = 0; RecordPosition < pRecordStruct->NbOfRecordInSPPayload; RecordPosition++ )
+ {
+ pSPRecordStruct = pRecordStruct->SPRecordStructAdd[RecordPosition];
+ if( pSPRecordStruct->NDEF_Type == WELL_KNOWN_ABRIDGED_URI_TYPE )
+ {
+ NDEF_Parse_WellKnowType( pSPRecordStruct, pURI );
+ status = NDEF_OK;
+ }
+ if( pSPRecordStruct->NDEF_Type == TEXT_TYPE )
+ {
+ PayloadSize = ((uint32_t)(pSPRecordStruct->PayloadLength3) << 24) | ((uint32_t)(pSPRecordStruct->PayloadLength2) << 16) |
+ ((uint32_t)(pSPRecordStruct->PayloadLength1) << 8) | pSPRecordStruct->PayloadLength0;
+
+ /* The instruction content the UTF-8 language code that is not used here */
+ pData = (uint8_t*)pSPRecordStruct->PayloadBufferAdd;
+ PayloadSize -= *pData + 1; /* remove not usefull data */
+ pData += *pData + 1;
+
+ memcpy( pURI->Information, pData, PayloadSize );
+ }
+ }
+ }
+ else
+ {
+ status = NDEF_ERROR;
+ }
+
+ return status;
+}
+
+/**
+ * @brief This function prepare the NDEF message with the URI data given in the structure.
+ * @param pURI : pointer on structure that contain the URI information.
+ * @param pNDEFMessage : pointer on the NDEF message.
+ * @param size : to store the size of the NDEF message generated.
+ */
+void NDEF_URI::NDEF_PrepareURIMessage( sURI_Info *pURI, uint8_t *pNDEFMessage, uint16_t *size )
+{
+ uint32_t uriSize, totalSize, Offset = 0;
+ uint32_t infoSize = 0;
+ char type;
+
+ /* An URI can be included in a smart poster to add text to give instruction to user for instance */
+
+ /* URI (smart poster) Record Header */
+/************************************/
+/* 7 | 6 | 5 | 4 | 3 | 2 1 0 */
+/*----------------------------------*/
+/* MB ME CF SR IL TNF */ /* <---- CF=0, IL=0 and SR=1 TNF=1 NFC Forum Well-known type*/
+/*----------------------------------*/
+/* TYPE LENGTH */
+/*----------------------------------*/
+/* PAYLOAD LENGTH 3 */ /* <---- Used only if SR=0 */
+/*----------------------------------*/
+/* PAYLOAD LENGTH 2 */ /* <---- Used only if SR=0 */
+/*----------------------------------*/
+/* PAYLOAD LENGTH 1 */ /* <---- Used only if SR=0 */
+/*----------------------------------*/
+/* PAYLOAD LENGTH 0 */
+/*----------------------------------*/
+/* ID LENGTH */ /* <---- Not Used */
+/*----------------------------------*/
+/* TYPE */
+/*----------------------------------*/
+/* ID */ /* <---- Not Used */
+/************************************/
+
+ /* We need to know the URI type in order to define if an abreviation is available */
+ type = getUriType( pURI->protocol );
+
+ /* URI : 1+URI for abreviate protocol*/
+ if( type != URI_ID_0x00 )
+ uriSize = 1 + strlen(pURI->URI_Message);
+ else /*: 1+protocol+URI else*/
+ uriSize = 1 + strlen(pURI->protocol) + strlen(pURI->URI_Message);
+
+ /* Check if a Smart poster is needed */
+ if( pURI->Information[0] != '\0' )
+ {
+ /* Info : 1+2+info */
+ infoSize = 1 + ISO_ENGLISH_CODE_STRING_LENGTH + strlen(pURI->Information);
+ /* Total */
+ totalSize = 4 + uriSize + 4 + infoSize;
+ if( uriSize > 255 ) totalSize += 3; /* Normal URI size */
+ if( infoSize > 255 ) totalSize += 3; /* Normal Info size */
+
+ /* SmartPoster header */
+ if( totalSize > 255 )
+ {
+ pNDEFMessage[Offset++] = 0xC1;
+ pNDEFMessage[Offset++] = SMART_POSTER_TYPE_STRING_LENGTH;
+ pNDEFMessage[Offset++] = (totalSize & 0xFF000000) >> 24;
+ pNDEFMessage[Offset++] = (totalSize & 0x00FF0000) >> 16;
+ pNDEFMessage[Offset++] = (totalSize & 0x0000FF00) >> 8;
+ pNDEFMessage[Offset++] = totalSize & 0x000000FF;
+ }
+ else
+ {
+ pNDEFMessage[Offset++] = 0xD1;
+ pNDEFMessage[Offset++] = SMART_POSTER_TYPE_STRING_LENGTH;
+ pNDEFMessage[Offset++] = (uint8_t)totalSize;
+ }
+ memcpy( &pNDEFMessage[Offset], SMART_POSTER_TYPE_STRING, SMART_POSTER_TYPE_STRING_LENGTH );
+ Offset += SMART_POSTER_TYPE_STRING_LENGTH;
+ }
+
+ /* URI header */
+ pNDEFMessage[Offset] = 0x81;
+ if( uriSize < 256 ) pNDEFMessage[Offset] |= 0x10; // Set the SR bit
+ if( pURI->Information[0] == '\0' ) pNDEFMessage[Offset] |= 0x40; // Set the ME bit
+ Offset++;
+
+ pNDEFMessage[Offset++] = URI_TYPE_STRING_LENGTH;
+ if( uriSize > 255 )
+ {
+ pNDEFMessage[Offset++] = (uriSize & 0xFF000000) >> 24;
+ pNDEFMessage[Offset++] = (uriSize & 0x00FF0000) >> 16;
+ pNDEFMessage[Offset++] = (uriSize & 0x0000FF00) >> 8;
+ pNDEFMessage[Offset++] = uriSize & 0x000000FF;
+ }
+ else
+ {
+ pNDEFMessage[Offset++] = (uint8_t)uriSize;
+ }
+ memcpy( &pNDEFMessage[Offset], URI_TYPE_STRING, URI_TYPE_STRING_LENGTH );
+ Offset += URI_TYPE_STRING_LENGTH;
+
+ pNDEFMessage[Offset++] = type;
+ if( type == URI_ID_0x00 ) // No abreviation
+ {
+ memcpy( &pNDEFMessage[Offset], pURI->protocol, strlen(pURI->protocol) );
+ Offset += strlen(pURI->protocol);
+ }
+
+ memcpy( &pNDEFMessage[Offset], pURI->URI_Message, strlen(pURI->URI_Message) );
+ Offset += strlen(pURI->URI_Message);
+
+ /* Information header */
+ if( pURI->Information[0] != '\0' )
+ {
+ if( infoSize > 255 )
+ {
+ pNDEFMessage[Offset++] = 0x41;
+ pNDEFMessage[Offset++] = TEXT_TYPE_STRING_LENGTH;
+ pNDEFMessage[Offset++] = (infoSize & 0xFF000000) >> 24;
+ pNDEFMessage[Offset++] = (infoSize & 0x00FF0000) >> 16;
+ pNDEFMessage[Offset++] = (infoSize & 0x0000FF00) >> 8;
+ pNDEFMessage[Offset++] = infoSize & 0x000000FF;
+ }
+ else
+ {
+ pNDEFMessage[Offset++] = 0x51;
+ pNDEFMessage[Offset++] = TEXT_TYPE_STRING_LENGTH;
+ pNDEFMessage[Offset++] = (uint8_t)infoSize;
+ }
+
+ memcpy( &pNDEFMessage[Offset], TEXT_TYPE_STRING, TEXT_TYPE_STRING_LENGTH );
+ Offset+=TEXT_TYPE_STRING_LENGTH;
+ pNDEFMessage[Offset++] = ISO_ENGLISH_CODE_STRING_LENGTH; /* UTF-8 with x byte language code */
+ memcpy( &pNDEFMessage[Offset], ISO_ENGLISH_CODE_STRING, ISO_ENGLISH_CODE_STRING_LENGTH );
+ Offset += ISO_ENGLISH_CODE_STRING_LENGTH;
+
+ /* Information payload */
+ memcpy( &pNDEFMessage[Offset], pURI->Information, strlen(pURI->Information) );
+ Offset += strlen(pURI->Information);
+ }
+
+ *size = Offset;
+
+}
+/**
+ * @brief This function write the NDEF file with the URI data given in the structure.
+ * @param pURI : pointer on structure that contain the URI information.
+ * @retval NDEF_OK : NDEF file data written in the tag.
+ * @retval NDEF_ERROR : not able to store NDEF in tag.
+ * @retval NDEF_ERROR_MEMORY_INTERNAL : Cannot write to tag.
+ * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported or not present.
+ * @retval NDEF_ERROR_MEMORY_TAG : Size not compatible with memory.
+ * @retval NDEF_ERROR_LOCKED : Tag locked, cannot be write.
+ */
+uint16_t NDEF_URI::NDEF_WriteURI( sURI_Info *pURI )
+{
+ uint16_t status = NDEF_ERROR, Offset = 0;
+
+ NDEF_PrepareURIMessage( pURI, &NDEF_Buffer[FIRST_RECORD_OFFSET], &Offset );
+
+ /* Write NDEF */
+ NDEF_Buffer[0] = (Offset & 0xFF00) >> 8;
+ NDEF_Buffer[1] = Offset & 0x00FF;
+
+ status = WriteData( 0x00, Offset + FIRST_RECORD_OFFSET, NDEF_Buffer );
+
+ return status;
+}
+
+char NDEF_URI::getUriType( char *protocol )
+{
+ if( !memcmp( protocol, URI_ID_0x01_STRING, strlen(URI_ID_0x01_STRING) ) ) return URI_ID_0x01;
+ else if( !memcmp( protocol, URI_ID_0x02_STRING, strlen(URI_ID_0x02_STRING) ) ) return URI_ID_0x02;
+ else if( !memcmp( protocol, URI_ID_0x03_STRING, strlen(URI_ID_0x03_STRING) ) ) return URI_ID_0x03;
+ else if( !memcmp( protocol, URI_ID_0x04_STRING, strlen(URI_ID_0x04_STRING) ) ) return URI_ID_0x04;
+ else if( !memcmp( protocol, URI_ID_0x05_STRING, strlen(URI_ID_0x05_STRING) ) ) return URI_ID_0x05;
+ else if( !memcmp( protocol, URI_ID_0x06_STRING, strlen(URI_ID_0x06_STRING) ) ) return URI_ID_0x06;
+ else if( !memcmp( protocol, URI_ID_0x07_STRING, strlen(URI_ID_0x07_STRING) ) ) return URI_ID_0x07;
+ else if( !memcmp( protocol, URI_ID_0x08_STRING, strlen(URI_ID_0x08_STRING) ) ) return URI_ID_0x08;
+ else if( !memcmp( protocol, URI_ID_0x09_STRING, strlen(URI_ID_0x09_STRING) ) ) return URI_ID_0x09;
+ else if( !memcmp( protocol, URI_ID_0x0A_STRING, strlen(URI_ID_0x0A_STRING) ) ) return URI_ID_0x0A;
+ else if( !memcmp( protocol, URI_ID_0x0B_STRING, strlen(URI_ID_0x0B_STRING) ) ) return URI_ID_0x0B;
+ else if( !memcmp( protocol, URI_ID_0x0C_STRING, strlen(URI_ID_0x0C_STRING) ) ) return URI_ID_0x0C;
+ else if( !memcmp( protocol, URI_ID_0x0D_STRING, strlen(URI_ID_0x0D_STRING) ) ) return URI_ID_0x0D;
+ else if( !memcmp( protocol, URI_ID_0x0E_STRING, strlen(URI_ID_0x0E_STRING) ) ) return URI_ID_0x0E;
+ else if( !memcmp( protocol, URI_ID_0x0F_STRING, strlen(URI_ID_0x0F_STRING) ) ) return URI_ID_0x0F;
+ else if( !memcmp( protocol, URI_ID_0x10_STRING, strlen(URI_ID_0x10_STRING) ) ) return URI_ID_0x10;
+ else if( !memcmp( protocol, URI_ID_0x11_STRING, strlen(URI_ID_0x11_STRING) ) ) return URI_ID_0x11;
+ else if( !memcmp( protocol, URI_ID_0x12_STRING, strlen(URI_ID_0x12_STRING) ) ) return URI_ID_0x12;
+ else if( !memcmp( protocol, URI_ID_0x13_STRING, strlen(URI_ID_0x13_STRING) ) ) return URI_ID_0x13;
+ else if( !memcmp( protocol, URI_ID_0x14_STRING, strlen(URI_ID_0x14_STRING) ) ) return URI_ID_0x14;
+ else if( !memcmp( protocol, URI_ID_0x15_STRING, strlen(URI_ID_0x15_STRING) ) ) return URI_ID_0x15;
+ else if( !memcmp( protocol, URI_ID_0x16_STRING, strlen(URI_ID_0x16_STRING) ) ) return URI_ID_0x16;
+ else if( !memcmp( protocol, URI_ID_0x17_STRING, strlen(URI_ID_0x17_STRING) ) ) return URI_ID_0x17;
+ else if( !memcmp( protocol, URI_ID_0x18_STRING, strlen(URI_ID_0x18_STRING) ) ) return URI_ID_0x18;
+ else if( !memcmp( protocol, URI_ID_0x19_STRING, strlen(URI_ID_0x19_STRING) ) ) return URI_ID_0x19;
+ else if( !memcmp( protocol, URI_ID_0x1A_STRING, strlen(URI_ID_0x1A_STRING) ) ) return URI_ID_0x1A;
+ else if( !memcmp( protocol, URI_ID_0x1B_STRING, strlen(URI_ID_0x1B_STRING) ) ) return URI_ID_0x1B;
+ else if( !memcmp( protocol, URI_ID_0x1C_STRING, strlen(URI_ID_0x1C_STRING) ) ) return URI_ID_0x1C;
+ else if( !memcmp( protocol, URI_ID_0x1D_STRING, strlen(URI_ID_0x1D_STRING) ) ) return URI_ID_0x1D;
+ else if( !memcmp( protocol, URI_ID_0x1E_STRING, strlen(URI_ID_0x1E_STRING) ) ) return URI_ID_0x1E;
+ else if( !memcmp( protocol, URI_ID_0x1F_STRING, strlen(URI_ID_0x1F_STRING) ) ) return URI_ID_0x1F;
+ else if( !memcmp( protocol, URI_ID_0x20_STRING, strlen(URI_ID_0x20_STRING) ) ) return URI_ID_0x20;
+ else if( !memcmp( protocol, URI_ID_0x21_STRING, strlen(URI_ID_0x21_STRING) ) ) return URI_ID_0x21;
+ else if( !memcmp( protocol, URI_ID_0x22_STRING, strlen(URI_ID_0x22_STRING) ) ) return URI_ID_0x22;
+ else if( !memcmp( protocol, URI_ID_0x23_STRING, strlen(URI_ID_0x23_STRING) ) ) return URI_ID_0x23;
+ else return URI_ID_0x00; // No abreviation for this protocol
+}
+
+NFCTAG_StatusTypeDef NDEF_URI::NFCTAG_ReadData( uint8_t * const pData, const uint16_t TarAddr, const uint16_t Size )
+{
+ return(mM24LRp->i2c_ReadData(pData, TarAddr, Size ));
+}
+NFCTAG_StatusTypeDef NDEF_URI::NFCTAG_WriteData( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t Size )
+{
+ return(mM24LRp->i2c_WriteData( pData, TarAddr, Size ));
+}
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Lib_NDEF/lib_NDEF_URI.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,72 @@
+/**
+ ******************************************************************************
+ * @file lib_NDEF_URI.h
+ * @author MMY Application Team
+ * @version $Revision: 1582 $
+ * @date $Date: 2016-02-03 15:06:14 +0100 (Wed, 03 Feb 2016) $
+ * @brief This file help to manage URI NDEF file.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT 2015 STMicroelectronics</center></h2>
+ *
+ * Licensed under ST MYLIBERTY SOFTWARE LICENSE AGREEMENT (the "License");
+ * You may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.st.com/myliberty
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+ * AND SPECIFICALLY DISCLAIMING THE IMPLIED WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************
+ */
+
+/* Define to prevent recursive inclusion -------------------------------------*/
+#ifndef __LIB_NDEF_URI_H
+#define __LIB_NDEF_URI_H
+
+
+
+/* Includes ------------------------------------------------------------------*/
+#include "lib_NDEF.h"
+#include "m24lr.h"
+typedef struct
+{
+ char protocol[80];
+ char URI_Message[400];
+ char Information[400];
+}sURI_Info;
+
+typedef struct sRecordInfo sRecordInfo_t;
+
+class NDEF_URI : public NDEF
+{
+public:
+uint16_t NDEF_ReadURI(sRecordInfo *pRecordStruct, sURI_Info *pURI);
+uint16_t NDEF_WriteURI(sURI_Info *pURI);
+void NDEF_Parse_WellKnowType( sRecordInfo *pRecordStruct, sURI_Info* pURI );
+
+virtual NFCTAG_StatusTypeDef NFCTAG_ReadData( uint8_t * const pData, const uint16_t TarAddr, const uint16_t Size );
+virtual NFCTAG_StatusTypeDef NFCTAG_WriteData( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t Size );
+
+void NDEF_PrepareURIMessage( sURI_Info *pURI, uint8_t *pNDEFMessage, uint16_t *size );
+char getUriType( char *protocol );
+
+NFCTAG_StatusTypeDef (*ReadDataPtr)( uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte );
+NFCTAG_StatusTypeDef (*WriteDataPtr)( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte );
+
+void setM24LR (M24LR *m24LRr) {mM24LRp=m24LRr; }
+M24LR *mM24LRp;
+
+};
+
+
+#endif /* __LIB_NDEF_URI_H */
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Lib_NDEF/tagtype5_wrapper.cpp Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,427 @@
+/**
+ ******************************************************************************
+ * @file tagtype5_wrapper.c
+ * @author MMY Application Team
+ * @version $Revision: 1638 $
+ * @date $Date: 2016-02-10 16:41:05 +0100 (Wed, 10 Feb 2016) $
+ * @brief Interface for tagtype5 in order to use NDEF lib
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT 2015 STMicroelectronics</center></h2>
+ *
+ * Licensed under ST MYLIBERTY SOFTWARE LICENSE AGREEMENT (the "License");
+ * You may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.st.com/myliberty
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+ * AND SPECIFICALLY DISCLAIMING THE IMPLIED WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************
+ */
+
+/* Includes ------------------------------------------------------------------*/
+#include "tagtype5_wrapper.h"
+#include "lib_NDEF.h"
+
+
+/**
+ * @brief This function read the data stored in NDEF file at defined offset.
+ * @param Offset : Offset in the NDEF file.
+ * @param DataSize : Number of byte to read.
+ * @param pData : pointer on buffer to store read data.
+ * @retval NDEF_ERROR_MEMORY_INTERNAL : Size not compatible with memory.
+ * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported.
+ * @retval NDEF_ERROR : No NDEF in the tag.
+ * @retval NDEF_OK : The operation is completed.
+ */
+uint16_t NFCType5::ReadData( uint16_t Offset , uint16_t DataSize , uint8_t* pData )
+{
+ uint16_t status = NDEF_ERROR;
+ uint8_t atlv_detect[4];
+ uint8_t index = 0;
+
+ /* Do not include length bytes */
+ DataSize -= FIRST_RECORD_OFFSET;
+
+ /* If too many data to write return error */
+ if( DataSize > NDEF_MAX_SIZE )
+ {
+ return NDEF_ERROR_MEMORY_INTERNAL;
+ }
+
+ /* Detect NDEF message in memory */
+ status = NfcType5_NDEFDetection( );
+ if( status != NDEF_OK )
+ {
+ return status;
+ }
+
+ /* Read TL of Type 5 */
+ status = NFCTAG_ReadData( atlv_detect, CCFileStruct.NDEF_offset, 4 );
+ if( status != NDEF_OK )
+ {
+ return status;
+ }
+
+ /* Check if L is on 3 or 1 byte and update length in buffer */
+ if( atlv_detect[1] == NFCT5_3_BYTES_L_TLV )
+ {
+ pData[0] = atlv_detect[2];
+ pData[1] = atlv_detect[3];
+ index += 4;
+ }
+ else
+ {
+ pData[0] = 0x00;
+ pData[1] = atlv_detect[1];
+ index += 2;
+ }
+
+ /* Check CC file is in the correct mode to proceed */
+ if( CCFileStruct.State == TT5_INITIALIZED )
+ {
+ return NDEF_ERROR;
+ }
+
+ if( ((Offset == 0) && (DataSize > 0)) || (Offset > 0) )
+ {
+ /* Read NDEF */
+ if( NFCTAG_ReadData( (pData + FIRST_RECORD_OFFSET), CCFileStruct.NDEF_offset + index + Offset, DataSize ) != NFCTAG_OK )
+ {
+ return NDEF_ERROR;
+ }
+ }
+
+ return NDEF_OK;
+}
+
+/**
+ * @brief This function writes data in NDEF file at defined offset.
+ * @param Offset : Offset in the NDEF file.
+ * @param DataSize : Number of byte to write.
+ * @param pData : pointer on buffer to copy.
+ * @retval NDEF_ERROR_MEMORY_INTERNAL : Size not compatible with memory.
+ * @retval NDEF_ERROR_NOT_FORMATED : CCFile data not supported.
+ * @retval NDEF_ERROR : No NDEF in the tag.
+ * @retval NDEF_OK : The operation is completed.
+ */
+uint16_t NFCType5::WriteData( uint16_t Offset , uint32_t DataSize , uint8_t *pData )
+{
+ uint8_t atlv[4];
+ uint8_t index = 0;
+ uint16_t NDEF_Size = 0;
+ NFCTAG_StatusTypeDef status;
+
+ /* Do not include length bytes */
+ DataSize -= FIRST_RECORD_OFFSET;
+
+ /* If too many data to write return error */
+ if( DataSize > NDEF_MAX_SIZE )
+ {
+ return NDEF_ERROR_MEMORY_INTERNAL;
+ }
+
+ /* Detect NDEF message in memory */
+ if( NfcType5_NDEFDetection( ) != NDEF_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ /* Extract NDEF Size from buffer */
+ NDEF_Size = (uint16_t)(pData[0] << 8);
+ NDEF_Size = NDEF_Size | (uint16_t)(pData[1] );
+
+ /* If entire NDEF is written, update Length of Type 5 */
+ if( DataSize == NDEF_Size )
+ {
+ /* Check if L is on 3 or 1 byte */
+ if( NDEF_Size >= NFCT5_3_BYTES_L_TLV )
+ {
+ /* First init L with 0, will be updated at the end */
+ atlv[1] = 0x00;
+ atlv[2] = 0x00;
+ atlv[3] = 0x00;
+
+ status = NFCTAG_WriteData( (atlv + 1), (CCFileStruct.NDEF_offset + 1), 3 );
+
+ index += 4;
+ }
+ else
+ {
+ /* First inti L with 0, will be updated at the end */
+ atlv[1] = 0x00;
+
+ status = NFCTAG_WriteData( (atlv + 1), (CCFileStruct.NDEF_offset + 1), 1 );
+
+ index += 2;
+ }
+ }
+
+ /* Start write NDEF message to EEPROM */
+ status = NFCTAG_WriteData( (pData + FIRST_RECORD_OFFSET), CCFileStruct.NDEF_offset + index + Offset, DataSize );
+ if( status != NFCTAG_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ /* If entire NDEF is written, update Length of Type 5 */
+ if( DataSize == NDEF_Size )
+ {
+ /* Check if L is on 3 or 1 byte */
+ if( NDEF_Size >= NFCT5_3_BYTES_L_TLV )
+ {
+ /* Update Length value */
+ atlv[1] = NFCT5_3_BYTES_L_TLV;
+ atlv[2] = pData[0];
+ atlv[3] = pData[1];
+
+ status = NFCTAG_WriteData( (atlv + 1), (CCFileStruct.NDEF_offset + 1), 3 );
+ }
+ else
+ {
+ /* Update Length value */
+ atlv[1] = pData[1];
+
+ status = NFCTAG_WriteData( (atlv + 1), (CCFileStruct.NDEF_offset + 1), 1 );
+ }
+
+ /* Write Terminator TLV */
+ atlv[0] = NFCT5_TERMINATOR_TLV;
+ status = NFCTAG_WriteData( atlv, CCFileStruct.NDEF_offset + index + NDEF_Size, 1 );
+ }
+
+ return NDEF_OK;
+}
+
+/**
+ * @brief This functions writes CCFile in EEPROM.
+ * @Param pCCBuffer : pointer on the buffer containnig CC file.
+ * @retval NFCTAG status.
+ */
+uint16_t NFCType5::NfcType5_WriteCCFile( const uint8_t * const pCCBuffer )
+{
+ NFCTAG_StatusTypeDef ret_value;
+
+ /* Write first block of CCFile */
+ ret_value = NFCTAG_WriteData( pCCBuffer, 0x00, 0x4 );
+
+ /* If extended memory writes the next 4 bytes */
+ if( (pCCBuffer[2] == 0x00) && (ret_value == NFCTAG_OK) )
+ {
+ ret_value = NFCTAG_WriteData( pCCBuffer + 4, 0x04, 4 );
+ }
+
+ if( ret_value != NFCTAG_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ return NDEF_OK;
+}
+
+/**
+ * @brief This functions reads CCFile in EEPROM.
+ * @Param pCCBuffer : pointer on the buffer to store CC file.
+ * @retval NFCTAG status.
+ */
+uint16_t NFCType5::NfcType5_ReadCCFile( uint8_t * const pCCBuffer )
+{
+ NFCTAG_StatusTypeDef ret_value;
+
+ /* Read 4 bytes of CC File */
+ ret_value = NFCTAG_ReadData( pCCBuffer, 0x00, 4 );
+
+ /* If extended memory reads the next 4 bytes */
+ if( (pCCBuffer[2] == 0x00) && (ret_value == NFCTAG_OK) )
+ {
+ ret_value = NFCTAG_ReadData( pCCBuffer + 4, 0x04, 4 );
+ }
+
+ if( ret_value != NFCTAG_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ return NDEF_OK;
+}
+
+/**
+ * @brief This function initialize memory in Tag Type 5.
+ * @retval NFCTAG status.
+ */
+uint16_t NFCType5::NfcType5_TT5Init( void )
+{
+ NFCTAG_StatusTypeDef ret_value = NFCTAG_OK;
+ uint16_t status;
+ uint8_t accbuffer[8];
+ uint8_t cdata;
+
+ /* Prepare buffer to update CCFile */
+ accbuffer[0] = CCFileStruct.MagicNumber;
+ accbuffer[1] = CCFileStruct.Version;
+ accbuffer[2] = CCFileStruct.MemorySize;
+ accbuffer[3] = CCFileStruct.TT5Tag;
+ CCFileStruct.NDEF_offset = 0x04;
+
+ /* If extended memory prepare the length bytes */
+ if( CCFileStruct.MemorySize == NFCT5_EXTENDED_CCFILE )
+ {
+ accbuffer[6] = (uint8_t)(CCFileStruct.ExtMemorySize >> 8);
+ accbuffer[7] = (uint8_t)(CCFileStruct.ExtMemorySize & 0xFF);
+ CCFileStruct.NDEF_offset = 0x08;
+ }
+
+ /* Update CCFile */
+ status = NfcType5_WriteCCFile( accbuffer );
+ if( status != NDEF_OK )
+ {
+ return status;
+ }
+
+ /* Update NDEF TLV for INITIALIZED state */
+ /* Update T */
+ cdata = NFCT5_NDEF_MSG_TLV;
+ ret_value = NFCTAG_WriteData( &cdata, CCFileStruct.NDEF_offset, 1 );
+ if( ret_value != NFCTAG_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ /* Update L */
+ cdata = 0x00;
+ ret_value = NFCTAG_WriteData( &cdata, (CCFileStruct.NDEF_offset + 1), 1 );
+ if( ret_value != NFCTAG_OK )
+ {
+ return NDEF_ERROR;
+ }
+
+ return NDEF_OK;
+}
+
+/**
+ * @brief This function detects an NDEF message Tag Type 5 in EEPROM.
+ * @retval NDEF_OK : NDEF message Tag Type 5 detected.
+ * @retval NDEF_ERROR_NOT_FORMATED : Device is not an NFC Tag Type 5 Tag.
+ * @retval NDEF_NO_NDEF_DETECTED : No NDEF Detected.
+ */
+uint16_t NFCType5::NfcType5_NDEFDetection( void )
+{
+ uint8_t acc_buffer[8];
+ uint8_t atlv_detect[4];
+ uint16_t status;
+ uint32_t memory_size;
+
+ CCFileStruct.State = TT5_NO_NDEF;
+
+ /* Read CCFile */
+ status = NfcType5_ReadCCFile( acc_buffer );
+ if( status != NDEF_OK )
+ {
+ return status;
+ }
+
+ /* Check Byte 0 is equal to magic number */
+ if( ( acc_buffer[0] != NFCT5_MAGICNUMBER_E1_CCFILE ) && ( acc_buffer[0] != NFCT5_MAGICNUMBER_E2_CCFILE ) )
+ {
+ return NDEF_ERROR_NOT_FORMATED;
+ }
+ /* Check Version number */
+ else if( ( (acc_buffer[1]&0xFC) != 0x40 ) )
+ {
+ return NDEF_ERROR_NOT_FORMATED;
+ }
+
+ /* Check if CCFile is on 4 Bytes or 8 Bytes */
+ if( acc_buffer[2] == 0x00 )
+ {
+ /* Update CCFIle structure */
+ CCFileStruct.MemorySize = 0x0;
+ CCFileStruct.ExtMemorySize = (uint16_t)acc_buffer[6];
+ CCFileStruct.ExtMemorySize = ( CCFileStruct.ExtMemorySize << 8 ) | acc_buffer[7];
+ memory_size = CCFileStruct.ExtMemorySize;
+ CCFileStruct.NDEF_offset = 8;
+ }
+ else
+ {
+ /* Update CCFIle structure */
+ CCFileStruct.MemorySize = acc_buffer[2];
+ CCFileStruct.ExtMemorySize = 0x0;
+ memory_size = CCFileStruct.MemorySize;
+ CCFileStruct.NDEF_offset = 4;
+ }
+
+ /* Update CCFIle structure */
+ CCFileStruct.MagicNumber = acc_buffer[0];
+ CCFileStruct.Version = acc_buffer[1];
+ CCFileStruct.TT5Tag = acc_buffer[3];
+
+ /* Search for position of NDEF TLV in memory and tag status */
+ while( ( NFCTAG_ReadData( atlv_detect, CCFileStruct.NDEF_offset, 4 ) == NFCTAG_OK ) && ( CCFileStruct.NDEF_offset < memory_size ) )
+ {
+ /* Detect first NDEF Message in memory */
+ if( atlv_detect[0] == NFCT5_NDEF_MSG_TLV )
+ {
+ if( atlv_detect[1] == 0x00 )
+ {
+ CCFileStruct.State = TT5_INITIALIZED;
+ }
+ else
+ {
+ if( CCFileStruct.Version & 0x3 )
+ {
+ CCFileStruct.State = TT5_READ;
+ }
+ else
+ {
+ CCFileStruct.State = TT5_READ_WRITE;
+ }
+ }
+ return NDEF_OK;
+ }
+ /* If Proprietary NDEF jump to end of proprietary message */
+ else if( atlv_detect[0] == NFCT5_PROPRIETARY_TLV )
+ {
+ if( atlv_detect[1] == NFCT5_3_BYTES_L_TLV )
+ {
+ CCFileStruct.NDEF_offset = CCFileStruct.NDEF_offset + ( (uint32_t)atlv_detect[2] << 8 ) + atlv_detect[3];
+ continue;
+ }
+ else
+ {
+ CCFileStruct.NDEF_offset = CCFileStruct.NDEF_offset + atlv_detect[1];
+ continue;
+ }
+ }
+ /* if Terminator no NDEF detected */
+ else if( atlv_detect[0] == NFCT5_TERMINATOR_TLV )
+ {
+ return NDEF_ERROR_NOT_FORMATED;
+ }
+
+ CCFileStruct.NDEF_offset++;
+ }
+
+ return NDEF_ERROR_NOT_FORMATED;
+}
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/Lib_NDEF/tagtype5_wrapper.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,118 @@
+/**
+ ******************************************************************************
+ * @file tagtype5_wrapper.h
+ * @author MMY Application Team
+ * @version $Revision: 1638 $
+ * @date $Date: 2016-02-10 16:41:05 +0100 (Wed, 10 Feb 2016) $
+ * @brief Interface for tagtype5 in order to use NDEF lib
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT 2015 STMicroelectronics</center></h2>
+ *
+ * Licensed under ST MYLIBERTY SOFTWARE LICENSE AGREEMENT (the "License");
+ * You may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.st.com/myliberty
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+ * AND SPECIFICALLY DISCLAIMING THE IMPLIED WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************
+ */
+
+/* Define to prevent recursive inclusion -------------------------------------*/
+#ifndef __TAGTYPE5_WRAPPER_H
+#define __TAGTYPE5_WRAPPER_H
+
+#include <stdint.h>
+#include "common.h"
+
+typedef enum
+{
+ TT5_NO_NDEF = 0,
+ TT5_INITIALIZED,
+ TT5_READ_WRITE,
+ TT5_READ
+} TT5_State;
+
+/**
+ * @brief CCfile structure
+ */
+typedef struct
+{
+ uint8_t MagicNumber; /* Magic Number should be E1h or E2h */
+ uint8_t Version;
+ uint8_t MemorySize;
+ uint8_t TT5Tag;
+ uint8_t rsved1;
+ uint8_t rsved2;
+ uint16_t ExtMemorySize;
+ TT5_State State;
+ uint32_t NDEF_offset;
+}sCCFileInfo;
+
+/* Exported constants --------------------------------------------------------*/
+#define NFCT5_MAGICNUMBER_E1_CCFILE 0xE1
+#define NFCT5_MAGICNUMBER_E2_CCFILE 0xE2
+#define NFCT5_EXTENDED_CCFILE 0xFF
+#define NFCT5_VERSION_V1_0 0x40
+#define NFCT5_READ_ACCESS 0x0C
+#define NFCT5_WRITE_ACCESS 0x03
+
+#define NFCT5_NDEF_MSG_TLV 0x03
+#define NFCT5_PROPRIETARY_TLV 0xFD
+#define NFCT5_TERMINATOR_TLV 0xFE
+#define NFCT5_3_BYTES_L_TLV 0xFF
+
+/* Exported macro ------------------------------------------------------------*/
+/* External variables --------------------------------------------------------*/
+/* Exported functions ------------------------------------------------------- */
+
+//typedef enum
+//{
+// NFCTAG_OK = 0,
+// NFCTAG_ERROR = 1,
+// NFCTAG_BUSY = 2,
+// NFCTAG_TIMEOUT = 3
+//} NFCTAG_StatusTypeDef;
+class NFCType5 {
+
+
+ public:
+sCCFileInfo CCFileStruct;
+
+
+uint16_t NfcType5_WriteCCFile( const uint8_t * const pCCBuffer );
+uint16_t NfcType5_ReadCCFile( uint8_t * const pCCBuffer );
+uint16_t NfcType5_TT5Init( void );
+uint16_t NfcType5_NDEFDetection( void );
+
+
+virtual NFCTAG_StatusTypeDef NFCTAG_ReadData( uint8_t * const pData, const uint16_t TarAddr, const uint16_t Size )=0;
+virtual NFCTAG_StatusTypeDef NFCTAG_WriteData( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t Size )=0;
+
+uint16_t ReadData( uint16_t Offset , uint16_t DataSize , uint8_t* pData );
+uint16_t WriteData( uint16_t Offset , uint32_t DataSize , uint8_t *pData );
+
+};
+#endif /* __TAGTYPE5_WRAPPER_H */
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/X_NUCLEO_NFC02A1/Common/common.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,60 @@
+/**
+ ******************************************************************************
+ * @file common.h
+ * @author AST
+ * @version V1.0.0
+ * @date 1 April 2015
+ * @brief Header file containing generic component definitions
+ * and I/O functions.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT(c) 2015 STMicroelectronics</center></h2>
+ *
+ * Redistribution and use in source and binary forms, with or without modification,
+ * are permitted provided that the following conditions are met:
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * 3. Neither the name of STMicroelectronics nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ ******************************************************************************
+ */
+
+
+/* Prevent recursive inclusion -----------------------------------------------*/
+
+#ifndef __COMMON_H__
+#define __COMMON_H__
+#include <stdint.h>
+
+/* Types ---------------------------------------------------------------------*/
+
+/**
+ * @brief NFCTAG status enumerator definition
+ */
+typedef enum
+{
+ NFCTAG_OK = 0,
+ NFCTAG_ERROR = 1,
+ NFCTAG_BUSY = 2,
+ NFCTAG_TIMEOUT = 3
+} NFCTAG_StatusTypeDef;
+typedef NFCTAG_StatusTypeDef (*ReadFnDataPtr)( uint8_t * const, const uint16_t, const uint16_t ) ;
+typedef NFCTAG_StatusTypeDef (*WriteFnDataPtr)( const uint8_t * const, const uint16_t, const uint16_t) ;
+#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/X_NUCLEO_NFC02A1/Interfaces/X_NUCLEO_NFC02A1.cpp Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,74 @@
+/**
+ ******************************************************************************
+ * @file X_NUCLEO_NFC02A1.h
+ * @author ST Central Labs
+ * @date 05 Nov 2015
+ * @brief Singleton class that controls all the electronics inside the
+ * X_NUCLEO_NFC02A1 expansion board
+ ******************************************************************************
+ *
+ * COPYRIGHT(c) 2015 STMicroelectronics
+ *
+ * Redistribution and use in source and binary forms, with or without modification,
+ * are permitted provided that the following conditions are met:
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * 3. Neither the name of STMicroelectronics nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ ******************************************************************************
+ */
+
+#include <X_NUCLEO_NFC02A1.h>
+
+const uint8_t X_NUCLEO_NFC02A1::M24LR_ADDR= 0xAE; //0xAC; //rp
+const uint8_t X_NUCLEO_NFC02A1::M24LR_ADDR_DATA = 0xA6;
+const PinName X_NUCLEO_NFC02A1::DEFAULT_SDA_PIN=D14;
+const PinName X_NUCLEO_NFC02A1::DEFAULT_SDL_PIN=D15;
+
+
+const PinName X_NUCLEO_NFC02A1::DEFAULT_GPO_PIN=D12;
+const PinName X_NUCLEO_NFC02A1::DEFAULT_RF_DISABLE_PIN=D11;
+const PinName X_NUCLEO_NFC02A1::DEFAULT_LED1_PIN=D5;
+const PinName X_NUCLEO_NFC02A1::DEFAULT_LED2_PIN=D4;
+const PinName X_NUCLEO_NFC02A1::DEFAULT_LED3_PIN=D2;
+
+X_NUCLEO_NFC02A1 *X_NUCLEO_NFC02A1::mInstance = NULL;
+
+X_NUCLEO_NFC02A1* X_NUCLEO_NFC02A1::Instance(DevI2C &devI2C,
+ const PinName &gpoName,
+ const PinName &RFDisableName, const PinName &led1Name,
+ const PinName &led2Name, const PinName &led3Name) {
+ if (mInstance == NULL) { // the first time
+ mInstance = new X_NUCLEO_NFC02A1(devI2C,gpoName,
+ RFDisableName,led1Name,led2Name,led3Name);
+ if (mInstance != NULL) { //allocation ok
+ const int status = mInstance->mM24LR.Initialization();
+ //if (status != NFC_SUCCESS) { //initialization failed
+ if (status != 0) {
+ delete mInstance;
+ error(
+ "Failed to init X_NUCLEO_NFC02A1 expansion board!\r\nError:0x%X\r\n",
+ status);
+ } //if init
+ } //if instance !=NULL
+ } //if instance
+ return mInstance;
+}
+
+
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/X_NUCLEO_NFC02A1/Interfaces/X_NUCLEO_NFC02A1.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,153 @@
+/**
+ ******************************************************************************
+ * @file X_NUCLEO_NFC02A1.cpp
+ * @author ST Central Labs
+ * @version V1.0.0
+ * @date 05 Nov 2015
+ * @brief Singleton class that controls all the electronics inside the
+ * X_NUCLEO_NFC02A1 expansion board.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT(c) 2015 STMicroelectronics</center></h2>
+ *
+ * Redistribution and use in source and binary forms, with or without modification,
+ * are permitted provided that the following conditions are met:
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * 3. Neither the name of STMicroelectronics nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ ******************************************************************************
+ */
+
+#ifndef X_NUCLEO_NFC02A1_H_
+#define X_NUCLEO_NFC02A1_H_
+#include <stdint.h>
+
+#include "mbed.h"
+
+#include "m24lr/m24lr.h"
+
+/**
+ * Singleton class that controls all the electronics inside the X_NUCLEO_NFC02A1 expansion board.
+ */
+class X_NUCLEO_NFC02A1 {
+
+public:
+
+private:
+ /**
+ * Ponter to the singleton instance, NULL if not allocated.
+ */
+ static X_NUCLEO_NFC02A1 *mInstance;
+ /**
+ * I2C address of the M24LR chip.
+ */
+ static const uint8_t M24LR_ADDR;
+
+ static const uint8_t M24LR_ADDR_DATA;
+
+ /**
+ * Constructor
+ * @param devI2C I2C channel used to communicate with the board.
+ * @param eventCallback Function that will be called when the gpo pin status change.
+ * @param gpoName Name of the gpio pin of the M24LR chip.
+ * @param RFDisableName Pin that controls the rf antenna status.
+ * @param led1Name Pin to control the led1 status.
+ * @param led2Name Pin to control the led1 status.
+ * @param led3Name Pin to control the led1 status.
+ */
+ X_NUCLEO_NFC02A1(DevI2C &devI2C,
+ const PinName &gpoName, const PinName &RFDisableName,
+ const PinName &led1Name, const PinName &led2Name,
+ const PinName &led3Name):
+ mM24LR(M24LR_ADDR, M24LR_ADDR_DATA, devI2C),
+ mNfcLed1(led1Name),mNfcLed2(led2Name),mNfcLed3(led3Name){}
+
+public:
+ static const PinName DEFAULT_SDA_PIN; //!< Default pin used for the M24LR SDA signal.
+ static const PinName DEFAULT_SDL_PIN; //!< Default pin used for the M24LR SDL signal.
+ static const PinName DEFAULT_GPO_PIN; //!< Default pin used for the M24LR GPO signal.
+ static const PinName DEFAULT_RF_DISABLE_PIN; //!< Default pin used for M24LR RF_DISABLE signal.
+ static const PinName DEFAULT_LED1_PIN; //!< Default pin to control the led 1.
+ static const PinName DEFAULT_LED2_PIN; //!< Default pin to control the led 2.
+ static const PinName DEFAULT_LED3_PIN; //!< Default pin to control the led 3.
+
+ /**
+ * Create or return an instance of X_NUCLEO_NFC02A1.
+ * @param devI2C I2C channel used to communicate with the board.
+ * @param eventCallback Function that will be called when the gpo pin status change.
+ * @param gpoName Name of the gpio pin of the M24LR chip.
+ * @param RFDisableName Pin that controls the rf antenna status.
+ * @param led1Name Pin to control the led1 status.
+ * @param led2Name Pin to control the led1 status.
+ * @param led3Name Pin to control the led1 status.
+ */
+ static X_NUCLEO_NFC02A1* Instance(DevI2C &devI2C,
+ const PinName &gpoName = DEFAULT_GPO_PIN,
+ const PinName &RFDisableName = DEFAULT_RF_DISABLE_PIN,
+ const PinName &led1Name = DEFAULT_LED1_PIN,
+ const PinName &led2Name = DEFAULT_LED2_PIN,
+ const PinName &led3Name = DEFAULT_LED3_PIN);
+
+ /**
+ * @return board led1.
+ */
+ DigitalOut& getLed1() {
+ return mNfcLed1;
+ }
+
+ /**
+ * @return board led2.
+ */
+ DigitalOut& getLed2() {
+ return mNfcLed2;
+ }
+
+ /**
+ * @return board led3.
+ */
+ DigitalOut& getLed3() {
+ return mNfcLed3;
+ }
+
+ /**
+ * @return NFC Chip.
+ */
+ M24LR& getNFCTagM24LR() {
+ return mM24LR;
+ }
+
+ M24LR* getM24LR() {
+ return &mM24LR;
+ }
+
+ virtual ~X_NUCLEO_NFC02A1() {
+ }
+
+private:
+ M24LR mM24LR;
+
+ DigitalOut mNfcLed1;
+ DigitalOut mNfcLed2;
+ DigitalOut mNfcLed3;
+
+};
+#endif /* X_NUCLEO_NFC02A1_H_ */
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/X_NUCLEO_NFC02A1/X_NUCLEO_COMMON/DevI2C/DevI2C.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,188 @@
+/**
+ ******************************************************************************
+ * @file DevI2C.h
+ * @author AST / EST / AMG-CL
+ * @version V0.0.2
+ * @date 25-July-2016
+ * @brief Header file for a special I2C class DevI2C which provides some
+ * helper function for on-board communication
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT(c) 2014 STMicroelectronics</center></h2>
+ *
+ * Redistribution and use in source and binary forms, with or without modification,
+ * are permitted provided that the following conditions are met:
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * 3. Neither the name of STMicroelectronics nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ ******************************************************************************
+ */
+
+/* Define to prevent from recursive inclusion --------------------------------*/
+#ifndef __DEV_I2C_H
+#define __DEV_I2C_H
+
+/* Includes ------------------------------------------------------------------*/
+#include "mbed.h"
+
+/* Classes -------------------------------------------------------------------*/
+/** Helper class DevI2C providing functions for multi-register I2C communication
+ * common for a series of I2C devices
+ */
+class DevI2C : public I2C
+{
+ public:
+
+ /** Create a DevI2C Master interface, connected to the specified pins
+ *
+ * @param sda I2C data line pin
+ * @param scl I2C clock line pin
+ */
+ DevI2C(PinName sda, PinName scl) : I2C(sda, scl) {}
+
+ /**
+ * @brief Writes a buffer towards the I2C peripheral device.
+ * @param pBuffer pointer to the byte-array data to send
+ * @param DeviceAddr specifies the peripheral device slave address.
+ * @param RegisterAddr specifies the internal address register
+ * where to start writing to (must be correctly masked).
+ * @param NumByteToWrite number of bytes to be written.
+ * @retval 0 if ok,
+ * @retval -1 if an I2C error has occured, or
+ * @retval -2 on temporary buffer overflow (i.e. NumByteToWrite was too high)
+ * @note On some devices if NumByteToWrite is greater
+ * than one, the RegisterAddr must be masked correctly!
+ */
+ int i2c_write(uint8_t* pBuffer, uint8_t DeviceAddr, uint8_t RegisterAddr,
+ uint16_t NumByteToWrite)
+ {
+ int ret;
+ uint8_t tmp[TEMP_BUF_SIZE];
+
+ if(NumByteToWrite >= TEMP_BUF_SIZE) return -2;
+
+ /* First, send device address. Then, send data and STOP condition */
+ tmp[0] = RegisterAddr;
+ memcpy(tmp+1, pBuffer, NumByteToWrite);
+
+ ret = write(DeviceAddr, (const char*)tmp, NumByteToWrite+1, false);
+
+ if(ret) return -1;
+ return 0;
+ }
+
+ /**
+ * @brief Writes a buffer towards the I2C peripheral device.
+ * @param pBuffer pointer to the byte-array data to send
+ * @param DeviceAddr specifies the peripheral device slave address.
+ * @param RegisterAddr specifies the internal address register
+ * where to start writing to (must be correctly masked).
+ * @param NumByteToWrite number of bytes to be written.
+ * @retval 0 if ok,
+ * @retval -1 if an I2C error has occured, or
+ * @retval -2 on temporary buffer overflow (i.e. NumByteToWrite was too high)
+ * @note On some devices if NumByteToWrite is greater
+ * than one, the RegisterAddr must be masked correctly!
+ */
+ int i2c_write(uint8_t* pBuffer, uint8_t DeviceAddr, uint16_t RegisterAddr,
+ uint16_t NumByteToWrite)
+ {
+ int ret;
+ uint8_t tmp[TEMP_BUF_SIZE];
+
+ if(NumByteToWrite >= TEMP_BUF_SIZE) return -2;
+
+ /* First, send device address. Then, send data and STOP condition */
+ tmp[0] = (RegisterAddr >> 8) & 0xFF;
+ tmp[1] = (RegisterAddr) & 0xFF;
+ memcpy(tmp+2, pBuffer, NumByteToWrite);
+
+ ret = write(DeviceAddr, (const char*)tmp, NumByteToWrite+2, false);
+
+ if(ret) return -1;
+ return 0;
+ }
+ /**
+ * @brief Reads a buffer from the I2C peripheral device.
+ * @param pBuffer pointer to the byte-array to read data in to
+ * @param DaviceAddr specifies the peripheral device slave address.
+ * @param RegisterAddr specifies the internal address register
+ * where to start reading from (must be correctly masked).
+ * @param NumByteToRead number of bytes to be read.
+ * @retval 0 if ok,
+ * @retval -1 if an I2C error has occured
+ * @note On some devices if NumByteToWrite is greater
+ * than one, the RegisterAddr must be masked correctly!
+ */
+ int i2c_read(uint8_t* pBuffer, uint8_t DeviceAddr, uint16_t RegisterAddr,
+ uint16_t NumByteToRead)
+ {
+ int ret;
+ uint8_t reg_addr[2];
+ reg_addr[0] = (RegisterAddr >> 8) & 0xFF;
+ reg_addr[1] = (RegisterAddr) & 0xFF;
+ /* Send device address, with no STOP condition */
+ ret = write(DeviceAddr, (const char*)reg_addr, 2, true);
+ if(!ret) {
+ /* Read data, with STOP condition */
+ ret = read(DeviceAddr, (char*)pBuffer, NumByteToRead, false);
+ }
+
+ if(ret)
+ return -1;
+ else
+ return 0;
+ }
+
+ /**
+ * @brief Reads a buffer from the I2C peripheral device.
+ * @param pBuffer pointer to the byte-array to read data in to
+ * @param DaviceAddr specifies the peripheral device slave address.
+ * @param RegisterAddr specifies the internal address register
+ * where to start reading from (must be correctly masked).
+ * @param NumByteToRead number of bytes to be read.
+ * @retval 0 if ok,
+ * @retval -1 if an I2C error has occured
+ * @note On some devices if NumByteToWrite is greater
+ * than one, the RegisterAddr must be masked correctly!
+ */
+ int i2c_read(uint8_t* pBuffer, uint8_t DeviceAddr, uint8_t RegisterAddr,
+ uint16_t NumByteToRead)
+ {
+ int ret;
+
+ /* Send device address, with no STOP condition */
+ ret = write(DeviceAddr, (const char*)&RegisterAddr, 1, true);
+ if(!ret) {
+ /* Read data, with STOP condition */
+ ret = read(DeviceAddr, (char*)pBuffer, NumByteToRead, false);
+ }
+
+ if(ret) return -1;
+ return 0;
+ }
+
+private:
+ static const unsigned int TEMP_BUF_SIZE = 32;
+};
+
+#endif /* __DEV_I2C_H */
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/X_NUCLEO_NFC02A1/m24lr/m24lr.cpp Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,983 @@
+#include "m24lr.h"
+
+uint8_t M24LR::NfctagInitialized = 0;
+
+
+/**
+ * @brief This function activate Energy Harvesting mode
+ */
+void M24LR::Enable_EnergyHarvesting( void )
+{
+ /* Initialise M24LR Board */
+
+ /* Enable Energy Harvesting */
+ i2c_SetEH( );
+
+ /* Store configuration in non Volatile Memory */
+ i2c_Enable_EH_mode();
+ i2c_WriteEH_Cfg( M24LR_EH_Cfg_6MA );
+
+}
+/**
+ * @brief Set M24LR nfctag Initialization
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::Initialization( void )
+{
+ uint8_t nfctag_id = 0;
+
+ if( NfctagInitialized == 0 )
+ {
+
+ /* M24LR Init */
+ if( i2c_Init() != NFCTAG_OK )
+ {
+ return NFCTAG_ERROR;
+ }
+
+ /* Check M24LR driver ID */
+ i2c_ReadID(&nfctag_id);
+ if( (nfctag_id == I_AM_M24LR04) || (nfctag_id == I_AM_M24LR16) || (nfctag_id == I_AM_M24LR64) )
+ {
+ NfctagInitialized = 1;
+ // Nfctag_Drv = &M24lr_i2c_Drv;
+ // Nfctag_Drv->pData = &M24lr_i2c_ExtDrv;
+ }
+ else
+ {
+ NfctagInitialized = 0;
+ // Nfctag_Drv = NULL;
+ // NfctagInitialized = 0;
+ return NFCTAG_ERROR;
+ }
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Set M24LR Initialization
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_Init( void )
+{
+ /* Configure the low level interface */
+ return(NFCTAG_OK);
+ // return mM24LR_IO.Init( );
+}
+
+/**
+ * @brief Read M24LR ID
+ * @param pICRef : pointer to store ID
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadID( uint8_t * const pData )
+{
+ uint8_t *pBuffer = (uint8_t *)pData;
+ NFCTAG_StatusTypeDef status;
+ /* Read ICRef on device */
+ //return M24LR_i2c_ReadRegister( pICRef, M24LR_ICREF_REG, 1 );
+ /* Before calling this function M24LR must be ready, here is a check to detect an issue */
+ status = i2c_ReadRegister(pBuffer, M24LR_ICREF_REG, 1);
+
+ if (status == 0)
+ return NFCTAG_OK;
+ return NFCTAG_TIMEOUT;
+
+}
+
+/**
+ * @brief Check M24LR availability
+ * @param Trials : number of max tentative tried
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_IsDeviceReady( const uint32_t Trials )
+{
+ /* Test i2c with M24LR */
+ // return mM24LR_IO.IsDeviceReady( M24LR_ADDR_DATA_I2C, Trials );
+ uint8_t status = 1;
+ char buffer;
+ while (status != 0) {
+ /* for device is ready address in M24Lr is M24LR_ADDR_DATA_I2C */
+ status = dev_I2C.read(i2c_address_data, &buffer, 1, false);
+ }
+ if ( status == 0 )
+ return NFCTAG_OK;
+ else
+ return NFCTAG_TIMEOUT;
+
+}
+
+/**
+ * @brief Configure M24LR GPO
+ * @param ITConf : 0x01 = RFBUSY, 0x02 = RFWIP
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ConfigureGPO( const uint16_t ITConf )
+{
+ NFCTAG_StatusTypeDef status = NFCTAG_ERROR;
+
+ /* Configure GPO function on M24LR */
+ if( (ITConf & M24LR_IT_BUSY_MASK) == M24LR_IT_BUSY_MASK )
+ {
+ status = i2c_SetRFBUSY( );
+ }
+ else if( (ITConf & M24LR_IT_WIP_MASK) == M24LR_IT_WIP_MASK )
+ {
+ status = i2c_SetRFWIP( );
+ }
+ return status;
+}
+
+/**
+ * @brief Configure GPO as RF WriteInProgress
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_SetRFWIP( void )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+ status = i2c_ReadRegister(®_value, M24LR_CFG_REG, 1);
+
+
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Update register value for WIP configuration */
+ reg_value |= M24LR_CFG_WIPBUSY_MASK;
+
+ /* Write CFG register */
+ return i2c_WriteRegister( ®_value, M24LR_CFG_REG, 1 );
+}
+
+
+/**
+ * @brief Get Configuration of M24LR GPO
+ * @param GPOStatus : 0x01 = RFBUSY, 0x02 = RFWIP
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_GetGPOStatus( uint16_t * const pGPOStatus )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract RF WIP/BUSY information */
+ if( (reg_value & M24LR_CFG_WIPBUSY_MASK) == M24LR_CFG_WIPBUSY_MASK )
+ {
+ *pGPOStatus = M24LR_IT_WIP_MASK;
+ }
+ else
+ {
+ *pGPOStatus = M24LR_IT_BUSY_MASK;
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Read N bytes starting from specified I2C address
+ * @param pData : pointer of the data to store
+ * @param TarAddr : I2C data memory address to read
+ * @param NbByte : number of bytes to read
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadData( uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte )
+{
+ int status;
+ /* Before calling this function M24LR must be ready, here is a check to detect an issue */
+ if( i2c_IsDeviceReady( 1 ) != NFCTAG_OK )
+ {
+ return NFCTAG_TIMEOUT;
+ }
+ /* Rosarium : To check M24LR_ADDR_DATA_I2C is this case */
+ /* return M24lr_IO_MemRead( pData, M24LR_ADDR_DATA_I2C, TarAddr, NbByte ); */
+ status = dev_I2C.i2c_read(pData, i2c_address_data, TarAddr, NbByte);
+ if ( status == 0 )
+ return NFCTAG_OK;
+ else
+ return NFCTAG_TIMEOUT;
+}
+
+/**
+ * @brief Write N data bytes starting from specified I2C Address
+ * @brief if I2C_Write_Lock bit = 0 or I2C_Password present => ack (modification OK)
+ * @brief if I2C_Write_Lock bit = 1 and no I2C_Password present => No ack (no modification)
+ * @param pData : pointer of the data to write
+ * @param TarAddr : I2C data memory address to write
+ * @param NbByte : number of bytes to write
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_WriteData( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte )
+{
+ int status;
+ uint8_t align_mem_offset;
+ uint16_t bytes_to_write = NbByte;
+ uint16_t mem_addr = TarAddr;
+ uint8_t *pdata_index = (uint8_t *)pData;
+
+ /* Before calling this function M24LR must be ready, here is a check to detect an issue */
+ if( i2c_IsDeviceReady( 1 ) != NFCTAG_OK )
+ {
+ return NFCTAG_TIMEOUT;
+ }
+
+ /* M24LR can write a maximum of 4 bytes in EEPROM per i2c communication */
+ do
+ {
+ /* To write data in M24LR, data must be aligned on the same row in memory */
+ /* align_mem_offset is used to copy only Bytes that are on the same row in memory */
+ if( bytes_to_write > M24LR_PAGEWRITE_NBBYTE )
+ {
+ /* DataSize higher than max page write, copy data by page */
+ align_mem_offset = M24LR_PAGEWRITE_NBBYTE - (mem_addr % M24LR_PAGEWRITE_NBBYTE);
+ }
+ else
+ {
+ /* DataSize lower or equal to max page write, copy only last bytes */
+ align_mem_offset = bytes_to_write;
+ }
+ /* Write align_mem_offset bytes in memory */
+ /* Rosarium to Check as the address here is 0xA6 rather than 0xAE */
+ /* Rosarium dev_I2C.i2c_write(pdata_index, M24LR_ADDR_DATA_I2C, mem_addr, align_mem_offset); */
+ status = dev_I2C.i2c_write(pdata_index, i2c_address_data, mem_addr, align_mem_offset);
+
+ /* update index, dest address, size for next write */
+ pdata_index += align_mem_offset;
+ mem_addr += align_mem_offset;
+ bytes_to_write -= align_mem_offset;
+ /* Poll until EEPROM is available */
+ while( i2c_IsDeviceReady( 1 ) != NFCTAG_OK ) {};
+ }
+ while( ( bytes_to_write > 0 ) && ( status == NFCTAG_OK ) );
+ if ( status == 0 )
+ return NFCTAG_OK;
+ else
+ return NFCTAG_ERROR;
+}
+
+/**
+ * @brief Read N register bytes starting from specified I2C address
+ * @param pData : pointer of the data to store
+ * @param TarAddr : I2C memory address to read
+ * @param NbByte : number of bytes to read
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadRegister( uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte )
+{
+ /* Before calling read function M24LR must be ready, here is a check to detect an issue */
+ int status;
+
+ /* Before calling any read function M24LR must be ready, here is a check to detect an issue */
+ if( i2c_IsDeviceReady( 1 ) != NFCTAG_OK )
+ {
+ return NFCTAG_TIMEOUT;
+ }
+ /* Read actual value of register */
+ status = dev_I2C.i2c_read(pData, i2c_address_syst, TarAddr, NbByte);
+
+ if ( status == 0 )
+ return NFCTAG_OK;
+ else
+ return NFCTAG_TIMEOUT;
+}
+
+/**
+ * @brief Write N bytes to specific register
+ * @param pData : pointer of the data to write
+ * @param TarAddr : I2C register address to write
+ * @param NbByte : number of bytes to write
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_WriteRegister( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte )
+{
+ int status;
+ uint8_t align_mem_offset;
+ uint16_t bytes_to_write = NbByte;
+ uint16_t mem_addr = TarAddr;
+ uint8_t *pdata_index = (uint8_t *)pData;
+
+ /* Before calling this function M24LR must be ready, here is a check to detect an issue */
+ if( i2c_IsDeviceReady( 1 ) != NFCTAG_OK )
+ {
+ return NFCTAG_TIMEOUT;
+ }
+
+ /* M24LR can write a maximum of 4 bytes in EEPROM per i2c communication */
+ do
+ {
+ /* To write data in M24LR, data must be aligned on the same row in memory */
+ /* align_mem_offset is used to copy only Bytes that are on the same row in memory */
+ if( bytes_to_write > M24LR_PAGEWRITE_NBBYTE )
+ {
+ /* DataSize higher than max page write, copy data by page */
+ align_mem_offset = M24LR_PAGEWRITE_NBBYTE - (mem_addr % M24LR_PAGEWRITE_NBBYTE);
+ }
+ else
+ {
+ /* DataSize lower or equal to max page write, copy only last bytes */
+ align_mem_offset = bytes_to_write;
+ }
+ /* Write align_mem_offset bytes in register */
+ // status = M24lr_IO_MemWrite( pdata_index, M24LR_ADDR_SYST_I2C, mem_addr, align_mem_offset );
+ status = dev_I2C.i2c_write(pdata_index, i2c_address_syst, mem_addr, align_mem_offset);
+ /* update index, dest address, size for next write */
+ pdata_index += align_mem_offset;
+ mem_addr += align_mem_offset;
+ bytes_to_write -= align_mem_offset;
+ /* Poll until EEPROM is available */
+ while( i2c_IsDeviceReady( 1 ) != NFCTAG_OK ) {};
+ }
+ while( ( bytes_to_write > 0 ) && ( status == NFCTAG_OK ) );
+
+ if ( status == 0 )
+ return NFCTAG_OK;
+ else
+ return NFCTAG_ERROR;
+}
+
+/**
+ * @brief Read M24LR UID
+ * @param UID : M24LR_UID pointer of the UID to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadUID( M24LR_UID * const pUid )
+{
+ uint8_t areg_value[8];
+ uint8_t i;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of UID registers */
+ status = i2c_ReadRegister( areg_value, M24LR_UID_REG, 8 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Store information in 2 WORD */
+ pUid->MSB_UID = 0;
+
+ for( i = 0; i < 4; i++ )
+ {
+ pUid->MSB_UID = (pUid->MSB_UID << 8) | areg_value[7 - i];
+ }
+
+ pUid->LSB_UID = 0;
+
+ for( i = 0; i < 4; i++ )
+ {
+ pUid->LSB_UID = (pUid->LSB_UID << 8) | areg_value[3 - i];
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Read DSFID
+ * @param pData : pointer of the DSFID to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadDSFID( uint8_t * const pDsfid )
+{
+ /* Read actual value of DSFID register */
+ return i2c_ReadRegister( pDsfid, M24LR_DSFID_REG, 1 );
+}
+
+/**
+ * @brief Read AFI
+ * @param pData : pointer of the AFI to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadAFI( uint8_t * const pAfi )
+{
+ /* Read actual value of AFI register */
+ return i2c_ReadRegister( pAfi, M24LR_AFI_REG, 1 );
+}
+
+/**
+ * @brief Read status of I2C Lock Sectors
+ * @param Lock_sector : M24LR_Lock_Sectors pointer of the I2c lock sector status to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadI2CLockSector( M24LR_Lock_Sectors * const pLock_sector )
+{
+ uint8_t areg_value[8];
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of I2c Write Lock registers */
+ status = i2c_ReadRegister( areg_value, M24LR_LOCK_REG, 8 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Dispatch information to corresponding struct member */
+ pLock_sector->sectors_63_56 = areg_value[7];
+ pLock_sector->sectors_55_48 = areg_value[6];
+ pLock_sector->sectors_47_40 = areg_value[5];
+ pLock_sector->sectors_39_32 = areg_value[4];
+ pLock_sector->sectors_31_24 = areg_value[3];
+ pLock_sector->sectors_23_16 = areg_value[2];
+ pLock_sector->sectors_15_8 = areg_value[1];
+ pLock_sector->sectors_7_0 = areg_value[0];
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Lock I2C write on an EEPROM Sectors
+ * @brief Need a presentation of I2C Password to be effective
+ * @param Sector : EEPROM Sector number to lock (between 0 to 63)
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_I2CLockSector( const uint8_t Sector )
+{
+ NFCTAG_StatusTypeDef status;
+ uint8_t reg_value = 0;
+ uint16_t sector_write_lock_addr;
+
+ /* Compute register address */
+ sector_write_lock_addr = M24LR_LOCK_REG | (Sector >> 3);
+
+ /* Read actual WriteLockStatus */
+ status = i2c_ReadRegister( ®_value, sector_write_lock_addr, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Compute and update new WriteLockStatus */
+ reg_value |= 1 << ( Sector % 8 );
+
+ /* Write WriteLock register */
+ return i2c_WriteRegister( ®_value, sector_write_lock_addr, 1 );
+}
+
+/**
+ * @brief UnLock I2C write on a EEPROM Sector
+ * @brief Need an presentation of I2C Password to be effective
+ * @param pSector : EEPROM Sector number to unlock (between 0 to 63)
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_I2CUnlockSector( const uint8_t Sector )
+{
+ NFCTAG_StatusTypeDef status;
+ uint8_t reg_value = 0;
+ uint16_t sector_write_lock_addr;
+
+ /* Compute register address */
+ sector_write_lock_addr = M24LR_LOCK_REG | (Sector >> 3);
+
+ /* Read actual WriteLockStatus */
+ status = i2c_ReadRegister( ®_value, sector_write_lock_addr, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Compute and update new WriteLockStatus */
+ reg_value &= ~( 1 << ( Sector % 8 ) );
+
+ /* Write WriteLock register */
+ return i2c_WriteRegister( ®_value, sector_write_lock_addr, 1 );
+}
+
+/**
+ * @brief Present I2C password, authorize I2C write
+ * @param PassWord : Password value on 32bits
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_PresentI2CPassword( const uint32_t PassWord )
+{
+ uint8_t ai2c_message[9] = {0};
+ uint8_t i;
+
+ /* Build I2C Message with Password + Validation code 0x09 + Password */
+ ai2c_message[4] = 0x09;
+ i = 0;
+ while( i < 4 )
+ {
+ ai2c_message[i] = ( PassWord >> (i * 8) ) & 0xFF;
+ ai2c_message[i + 5] = ( PassWord >> (i * 8) ) & 0xFF;
+ i++;
+ };
+
+ /* Present password to M24LR */
+ return i2c_WriteRegister( ai2c_message, M24LR_I2C_PWD_REG, 9 );
+}
+
+/**
+ * @brief Write new I2C password
+ * @brief Need to present good I2CPassword before using this function
+ * @param PassWord : new I2C PassWord value on 32bits
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_WriteI2CPassword( const uint32_t PassWord )
+{
+ uint8_t ai2c_message[9] = {0};
+ uint8_t i;
+
+ /* Build I2C Message with Password + Validation code 0x07 + Password */
+ ai2c_message[4] = 0x07;
+ i = 0;
+ while( i < 4 )
+ {
+ ai2c_message[i] = ( PassWord >> (i * 8) ) & 0xFF;
+ ai2c_message[i + 5] = ( PassWord >> (i * 8) ) & 0xFF;
+ i++;
+ };
+
+ /* Write Password to register */
+ return i2c_WriteRegister( ai2c_message, M24LR_I2C_PWD_REG, 9 );
+}
+
+/**
+ * @brief Read SectorSecurityStatus (defining RF access allowed)
+ * @param SectorNb : Sector number to get RF security status
+ * @param pData : M24LR_SECTOR_SEC pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadSSSx( const uint8_t SectorNb, M24LR_SECTOR_SEC * const pData )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+ uint16_t sector_security_addr;
+
+ /* Compute Sector Security register address */
+ sector_security_addr = M24LR_SSS_REG | SectorNb;
+
+ /* Read actual value of SectorSecurityStatus register */
+ status = i2c_ReadRegister( ®_value, sector_security_addr, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract Sector Security Status configuration */
+ pData->SectorLock = reg_value & M24LR_SSS_LOCK_MASK;
+ pData->RW_Protection = (reg_value & M24LR_SSS_RW_MASK) >> 1;
+ pData->PassCtrl = (reg_value & M24LR_SSS_PASSCTRL_MASK) >> 3;
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Write SectorSecurityStatus (defining RF access allowed)
+ * @brief Need an presentation of I2C Password to be effective
+ * @param SectorNb : Sector number to set RF security
+ * @param pData : M24LR_SECTOR_SEC pointer of the data to write
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_WriteSSSx( const uint8_t SectorNb, const M24LR_SECTOR_SEC * const pData )
+{
+ uint8_t reg_value;
+ uint16_t sector_security_addr;
+
+ /* Compute Sector Security register address */
+ sector_security_addr = M24LR_SSS_REG | SectorNb;
+
+ /* Update Sector Security Status */
+ reg_value = (pData->PassCtrl << 3) & M24LR_SSS_PASSCTRL_MASK;
+ reg_value |= ((pData->RW_Protection << 1) & M24LR_SSS_RW_MASK);
+ reg_value |= (pData->SectorLock & M24LR_SSS_LOCK_MASK);
+
+ /* Write SectorSecurityStatus register */
+ return i2c_WriteRegister( ®_value, sector_security_addr, 1 );
+}
+
+/**
+ * @brief Read Memory Size info
+ * @param SizeInfo : M24LR_Mem_Size pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadMemSize( M24LR_Mem_Size * const pSizeInfo )
+{
+ uint8_t areg_value[3];
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of Mem_Size register */
+ status = i2c_ReadRegister( areg_value, M24LR_MEMSIZE_REG, 3 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract Mem information */
+ pSizeInfo->BlockSize = areg_value[2];
+ pSizeInfo->Mem_Size = areg_value[1];
+ pSizeInfo->Mem_Size = (pSizeInfo->Mem_Size << 8) | areg_value[0];
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Get GPO Configuration status
+ * @param Rf_Wip_Busy : M24LR_GPO_STATUS pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_GetRF_WIP_BUSY( M24LR_GPO_STATUS * const pRf_Wip_Busy )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract RF WIP/BUSY information */
+ if( (reg_value & M24LR_CFG_WIPBUSY_MASK) == M24LR_CFG_WIPBUSY_MASK )
+ {
+ *pRf_Wip_Busy = M24LR_GPO_WIP;
+ }
+ else
+ {
+ *pRf_Wip_Busy = M24LR_GPO_BUSY;
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Configure GPO as RF Busy
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_SetRFBUSY( void )
+{
+ uint8_t reg_value;
+ int status;
+
+ /* Read actual value of CFG register */
+ status = dev_I2C.i2c_read( ®_value, i2c_address_syst, (uint16_t)M24LR_CFG_REG, 1 );
+ if( status != 0 )
+ {
+ return NFCTAG_TIMEOUT;
+ }
+
+ /* Update register value for BUSY configuration */
+ reg_value &= !M24LR_CFG_WIPBUSY_MASK;
+
+ /* Write CFG register */
+ status = i2c_WriteRegister( ®_value, M24LR_CFG_REG, 1 );
+ if ( status == 0 )
+ return NFCTAG_OK;
+ else
+ return NFCTAG_TIMEOUT;
+}
+
+
+/**
+ * @brief Get Energy harvesting mode status
+ * @param EH_mode : M24LR_EH_MODE_STATUS pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_Read_EH_mode( M24LR_EH_MODE_STATUS * const pEH_mode )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract EH_mode configuration */
+ if( (reg_value & M24LR_CFG_EHMODE_MASK) == M24LR_CFG_EHMODE_MASK )
+ {
+ *pEH_mode = M24LR_EH_MODE_DISABLE;
+ }
+ else
+ {
+ *pEH_mode = M24LR_EH_MODE_ENABLE;
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Enable Energy harvesting mode
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_Enable_EH_mode( void )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Update EH_mode */
+ reg_value &= ~M24LR_CFG_EHMODE_MASK;
+
+ /* Write CFG register */
+ return i2c_WriteRegister( ®_value, M24LR_CFG_REG, 1 );
+}
+
+/**
+ * @brief Disable Energy harvesting mode
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_Disable_EH_mode( void )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Update EH_mode */
+ reg_value |= M24LR_CFG_EHMODE_MASK;
+
+ /* Write CFG register */
+ return i2c_WriteRegister( ®_value, M24LR_CFG_REG, 1 );
+}
+
+/**
+ * @brief Read Vout sink current configuration status for Energy Harvesting
+ * @param EH_Cfg : M24LR_EH_CFG_VOUT pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ReadEH_Cfg( M24LR_EH_CFG_VOUT * const pEH_Cfg )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract Vout configuration for EH information */
+ reg_value &= (M24LR_CFG_EHCFG1_MASK | M24LR_CFG_EHCFG0_MASK);
+ switch( reg_value )
+ {
+ case 0:
+ *pEH_Cfg = M24LR_EH_Cfg_6MA;
+ break;
+ case 1:
+ *pEH_Cfg = M24LR_EH_Cfg_3MA;
+ break;
+ case 2:
+ *pEH_Cfg = M24LR_EH_Cfg_1MA;
+ break;
+ case 3:
+ *pEH_Cfg = M24LR_EH_Cfg_300UA;
+ break;
+
+ default:
+ *pEH_Cfg = M24LR_EH_Cfg_6MA;
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Write Vout sink current configuration status for Energy Harvesting
+ * @param EH_Cfg : M24LR_EH_CFG_VOUT value to configure Vout
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_WriteEH_Cfg( const M24LR_EH_CFG_VOUT EH_Cfg )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CFG register */
+ status = i2c_ReadRegister( ®_value, M24LR_CFG_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Update Vout configuration */
+ reg_value &= ~(M24LR_CFG_EHCFG1_MASK | M24LR_CFG_EHCFG0_MASK);
+ reg_value |= EH_Cfg;
+
+ /* Write CFG register */
+ return i2c_WriteRegister( ®_value, M24LR_CFG_REG, 1 );
+}
+
+/**
+ * @brief Get Energy Harvesting status
+ * @param EH_Val : M24LR_EH_STATUS pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_GetEH( M24LR_EH_STATUS * const pEH_Val )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CTRL register */
+ status = i2c_ReadRegister( ®_value, M24LR_CTRL_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Extract EH information */
+ if( (reg_value & M24LR_CTRL_EHEN_MASK) == M24LR_CTRL_EHEN_MASK )
+ {
+ *pEH_Val = M24LR_EH_ENABLE;
+ }
+ else
+ {
+ *pEH_Val = M24LR_EH_DISABLE;
+ }
+
+ return NFCTAG_OK;
+}
+
+/**
+ * @brief Enable Energy Harvesting
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_SetEH( void )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CTRL register */
+ status = i2c_ReadRegister( ®_value, M24LR_CTRL_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Update EH configuration */
+ reg_value |= M24LR_CTRL_EHEN_MASK;
+
+ /* Write CTRL Register */
+ return i2c_WriteRegister( ®_value, M24LR_CTRL_REG, 1 );
+}
+
+/**
+ * @brief Disable Energy Harvesting
+ * @param None
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_ResetEH( void )
+{
+ uint8_t reg_value;
+ NFCTAG_StatusTypeDef status;
+
+ /* Read actual value of CTRL register */
+ status = i2c_ReadRegister( ®_value, M24LR_CTRL_REG, 1 );
+ if( status != NFCTAG_OK )
+ {
+ return status;
+ }
+
+ /* Update EH configuration */
+ reg_value &= ~M24LR_CTRL_EHEN_MASK;
+
+ /* Write CTRL register */
+ return i2c_WriteRegister( ®_value, M24LR_CTRL_REG, 1 );
+}
+
+/**
+ * @brief Check if RF Field is present in front of M24LR
+ * @param pRF_Field : M24LR_FIELD_STATUS pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_GetRFField( M24LR_FIELD_STATUS * const pRF_Field )
+{
+ NFCTAG_StatusTypeDef status;
+ uint8_t reg_value = 0;
+
+ /* Read actual value of CTRL register */
+ status = i2c_ReadRegister( ®_value, M24LR_CTRL_REG, 1 );
+
+ /* Extract RF Field information */
+ if( status == NFCTAG_OK )
+ {
+ if( (reg_value & M24LR_CTRL_FIELD_MASK) == M24LR_CTRL_FIELD_MASK )
+ {
+ *pRF_Field = M24LR_FIELD_ON;
+ }
+ else
+ {
+ *pRF_Field = M24LR_FIELD_OFF;
+ }
+
+ return NFCTAG_OK;
+ }
+
+ return status;
+}
+
+/**
+ * @brief Check if Write Timing is good
+ * @param pT_Prog : M24LR_T_PROG_STATUS pointer of the data to store
+ * @retval NFCTAG enum status
+ */
+NFCTAG_StatusTypeDef M24LR::i2c_GetTProg( M24LR_T_PROG_STATUS * const pT_Prog )
+{
+ NFCTAG_StatusTypeDef status;
+ uint8_t reg_value = 0;
+
+ /* Read actual value of CTRL register */
+ status = i2c_ReadRegister( ®_value, M24LR_CTRL_REG, 1 );
+
+ /* Extract T-Prog information */
+ if( status == NFCTAG_OK )
+ {
+ if( (reg_value & M24LR_CTRL_TPROG_MASK) == M24LR_CTRL_TPROG_MASK )
+ {
+ *pT_Prog = M24LR_T_PROG_OK;
+ }
+ else
+ {
+ *pT_Prog = M24LR_T_PROG_NO;
+ }
+
+ return NFCTAG_OK;
+ }
+ else
+ return status;
+}
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/**
+ * @}
+ */
+
+/******************* (C) COPYRIGHT 2016 STMicroelectronics *****END OF FILE****/
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/X_NUCLEO_NFC02A1/m24lr/m24lr.h Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,223 @@
+#ifndef __M24LR_H
+#define __M24LR_H
+
+#include "common.h"
+#include "DevI2C.h"
+//#include "lib_NDEF_URI.h"
+ /* Exported constants --------------------------------------------------------*/
+/** @defgroup M24LR_Exported_Constants
+ * @{
+ */
+#define I_AM_M24LR04 0x5A
+#define I_AM_M24LR16 0x4E
+#define I_AM_M24LR64 0x5E
+
+#ifndef NULL
+#define NULL (void *) 0
+#endif
+
+#define M24LR_PAGEWRITE_NBBYTE 4
+
+#define M24LR_ADDR_DATA_I2C 0xA6
+#define M24LR_ADDR_SYST_I2C 0xAE
+#define M24LR_I2C_TIMEOUT 200 /* I2C Time out (ms), this is the maximum time needed by M24LR to complete any command */
+
+#define M24LR_IT_BUSY_MASK 0x01
+#define M24LR_IT_WIP_MASK 0x02
+
+/* Registers address */
+#define M24LR_SSS_REG 0x0000
+#define M24LR_LOCK_REG 0x0800
+#define M24LR_I2C_PWD_REG 0x0900
+#define M24LR_CFG_REG 0x0910
+#define M24LR_AFI_REG 0x0912
+#define M24LR_DSFID_REG 0x0913
+#define M24LR_UID_REG 0x0914
+#define M24LR_ICREF_REG 0x091C
+#define M24LR_MEMSIZE_REG 0x091D
+#define M24LR_CTRL_REG 0x0920
+
+/* Registers mask */
+#define M24LR_SSS_LOCK_MASK 0x01
+#define M24LR_SSS_RW_MASK 0x06
+#define M24LR_SSS_PASSCTRL_MASK 0x18
+#define M24LR_LOCK_MASK 0x0F
+
+#define M24LR_CFG_EHCFG0_MASK 0x01
+#define M24LR_CFG_EHCFG1_MASK 0x02
+#define M24LR_CFG_EHMODE_MASK 0x04
+#define M24LR_CFG_WIPBUSY_MASK 0x08
+
+#define M24LR_CTRL_EHEN_MASK 0x01
+#define M24LR_CTRL_FIELD_MASK 0x02
+#define M24LR_CTRL_TPROG_MASK 0x80
+
+
+/**
+ * @brief M24LR VOUT Configuration enumerator definition
+ */
+typedef enum
+{
+ M24LR_EH_Cfg_6MA = 0,
+ M24LR_EH_Cfg_3MA,
+ M24LR_EH_Cfg_1MA,
+ M24LR_EH_Cfg_300UA
+} M24LR_EH_CFG_VOUT;
+
+/**
+ * @brief M24LR FIELD status enumerator definition
+ */
+typedef enum
+{
+ M24LR_FIELD_OFF = 0,
+ M24LR_FIELD_ON
+} M24LR_FIELD_STATUS;
+
+/**
+ * @brief M24LR TT-PROG status enumerator definition
+ */
+typedef enum
+{
+ M24LR_T_PROG_NO = 0,
+ M24LR_T_PROG_OK
+} M24LR_T_PROG_STATUS;
+
+/**
+ * @brief M24LR Energy Harvesting status enumerator definition
+ */
+typedef enum
+{
+ M24LR_EH_DISABLE = 0,
+ M24LR_EH_ENABLE
+} M24LR_EH_STATUS;
+
+/**
+ * @brief M24LR Energy Harvesting mode enumerator definition
+ */
+typedef enum
+{
+ M24LR_EH_MODE_ENABLE = 0,
+ M24LR_EH_MODE_DISABLE
+} M24LR_EH_MODE_STATUS;
+
+/**
+ * @brief M24LR GPO status enumerator definition
+ */
+typedef enum
+{
+ M24LR_GPO_BUSY = 0,
+ M24LR_GPO_WIP
+} M24LR_GPO_STATUS;
+
+/**
+ * @brief M24LR Memory information structure definition
+ */
+typedef struct
+{
+ uint8_t BlockSize;
+ uint16_t Mem_Size;
+} M24LR_Mem_Size;
+
+/**
+ * @brief M24LR I2C Write Lock register structure definition
+ */
+typedef struct
+{
+ uint8_t sectors_7_0;
+ uint8_t sectors_15_8;
+ uint8_t sectors_23_16;
+ uint8_t sectors_31_24;
+ uint8_t sectors_39_32;
+ uint8_t sectors_47_40;
+ uint8_t sectors_55_48;
+ uint8_t sectors_63_56;
+} M24LR_Lock_Sectors;
+
+/**
+ * @brief M24LR UID information structure definition
+ */
+typedef struct
+{
+ uint32_t MSB_UID;
+ uint32_t LSB_UID;
+} M24LR_UID;
+
+/**
+ * @brief M24LR Sector Security register structure definition
+ */
+typedef struct
+{
+ uint8_t SectorLock;
+ uint8_t RW_Protection;
+ uint8_t PassCtrl;
+} M24LR_SECTOR_SEC;
+
+
+ /**
+ * @}
+ */
+
+class M24LR {
+public:
+ NFCTAG_StatusTypeDef i2c_Init( void );
+ NFCTAG_StatusTypeDef i2c_ReadID( uint8_t * const pICRef );
+ NFCTAG_StatusTypeDef i2c_IsDeviceReady( const uint32_t Trials );
+ NFCTAG_StatusTypeDef i2c_ConfigureGPO( const uint16_t ITConf );
+ NFCTAG_StatusTypeDef i2c_GetGPOStatus( uint16_t * const pGPOStatus );
+ NFCTAG_StatusTypeDef i2c_ReadData( uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte );
+ NFCTAG_StatusTypeDef i2c_WriteData( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte );
+ NFCTAG_StatusTypeDef i2c_ReadRegister( uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte );
+ NFCTAG_StatusTypeDef i2c_WriteRegister( const uint8_t * const pData, const uint16_t TarAddr, const uint16_t NbByte );
+
+
+ /* Extended Functions */
+ NFCTAG_StatusTypeDef i2c_ReadUID( M24LR_UID * const pUid );
+ NFCTAG_StatusTypeDef i2c_ReadDSFID( uint8_t * const pDsfid );
+ NFCTAG_StatusTypeDef i2c_ReadAFI( uint8_t * const pAfi );
+ NFCTAG_StatusTypeDef i2c_ReadI2CLockSector( M24LR_Lock_Sectors * const pLock_sector );
+ NFCTAG_StatusTypeDef i2c_I2CLockSector( const uint8_t Sector );
+ NFCTAG_StatusTypeDef i2c_I2CUnlockSector( const uint8_t Sector );
+ NFCTAG_StatusTypeDef i2c_PresentI2CPassword( const uint32_t PassWord );
+ NFCTAG_StatusTypeDef i2c_WriteI2CPassword( const uint32_t PassWord );
+ NFCTAG_StatusTypeDef i2c_ReadSSSx( const uint8_t SectorNb, M24LR_SECTOR_SEC * const pData );
+ NFCTAG_StatusTypeDef i2c_WriteSSSx( const uint8_t SectorNb, const M24LR_SECTOR_SEC * const pData );
+ NFCTAG_StatusTypeDef i2c_ReadMemSize( M24LR_Mem_Size * const pSizeInfo );
+ NFCTAG_StatusTypeDef i2c_GetRF_WIP_BUSY( M24LR_GPO_STATUS * const pRf_Wip_Busy );
+ NFCTAG_StatusTypeDef i2c_SetRFBUSY( void );
+ NFCTAG_StatusTypeDef i2c_SetRFWIP( void );
+ NFCTAG_StatusTypeDef i2c_Read_EH_mode( M24LR_EH_MODE_STATUS * const pEH_mode );
+ NFCTAG_StatusTypeDef i2c_Enable_EH_mode( void );
+ NFCTAG_StatusTypeDef i2c_Disable_EH_mode( void );
+ NFCTAG_StatusTypeDef i2c_ReadEH_Cfg( M24LR_EH_CFG_VOUT * const pEH_Cfg );
+ NFCTAG_StatusTypeDef i2c_WriteEH_Cfg( const M24LR_EH_CFG_VOUT EH_Cfg );
+ NFCTAG_StatusTypeDef i2c_GetEH( M24LR_EH_STATUS * const pEH_Val );
+ NFCTAG_StatusTypeDef i2c_SetEH( void );
+ NFCTAG_StatusTypeDef i2c_ResetEH( void );
+ NFCTAG_StatusTypeDef i2c_GetRFField( M24LR_FIELD_STATUS * const pRF_Field );
+ NFCTAG_StatusTypeDef i2c_GetTProg( M24LR_T_PROG_STATUS * const pT_Prog );
+
+ void Enable_EnergyHarvesting( void );
+ NFCTAG_StatusTypeDef Initialization( void );
+
+ M24LR(uint8_t const address, uint8_t const addressData, DevI2C &devI2C ):
+ i2c_address_syst(address), i2c_address_data(addressData), dev_I2C(devI2C) {}
+
+ static uint8_t NfctagInitialized;
+ // M24LR_IO mM24LR_IO;
+ uint8_t i2c_address_syst;
+
+ uint8_t i2c_address_data;
+ DevI2C dev_I2C;
+ friend class NDEF_URI;
+ //NDEF_URI mM24LR_URI;
+ //M24LR *ptr;
+// ReadFnDataPtr i2c_ReadData;
+// WriteFnDataPtr i2c_WriteData;
+
+};
+
+
+
+
+#endif /* __M24LR_H */
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp Wed Jul 27 09:25:33 2016 +0000
@@ -0,0 +1,95 @@
+/**
+ ******************************************************************************
+ * @file main.cpp
+ * @author ST Central Labs
+ * @version V1.0.0
+ * @date 21 Dic 2015
+ * @brief This demo writes an ndef message with an url inside.
+ ******************************************************************************
+ * @attention
+ *
+ * <h2><center>© COPYRIGHT(c) 2015 STMicroelectronics</center></h2>
+ *
+ * Redistribution and use in source and binary forms, with or without modification,
+ * are permitted provided that the following conditions are met:
+ * 1. Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ * 3. Neither the name of STMicroelectronics nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ ******************************************************************************
+ */
+
+#include "mbed.h"
+
+#include "X_NUCLEO_NFC02A1.h"
+#include "DevI2C.h"
+#include "m24lr.h"
+#include "lib_NDEF_URI.h"
+/**
+ * Write a Ndef URI message linking to st.com site.
+ */
+int main(void)
+{
+
+ sURI_Info URI;
+ NDEF_URI mNDEF_URI;
+ M24LR *mM24LRp;
+
+ /*use default board pinout*/
+ DevI2C i2cChannel(X_NUCLEO_NFC02A1::DEFAULT_SDA_PIN,X_NUCLEO_NFC02A1::DEFAULT_SDL_PIN);
+ X_NUCLEO_NFC02A1 *nfcNucleo = X_NUCLEO_NFC02A1::Instance(i2cChannel,
+ X_NUCLEO_NFC02A1::DEFAULT_GPO_PIN,X_NUCLEO_NFC02A1::DEFAULT_RF_DISABLE_PIN,
+ X_NUCLEO_NFC02A1::DEFAULT_LED1_PIN,X_NUCLEO_NFC02A1::DEFAULT_LED2_PIN,
+ X_NUCLEO_NFC02A1::DEFAULT_LED3_PIN);
+
+ mM24LRp = nfcNucleo->getM24LR();
+ mNDEF_URI.setM24LR(mM24LRp);
+ /* Enable Energy Harvesting */
+ mM24LRp->Enable_EnergyHarvesting();
+
+ printf("System Initialization done: !\n\r");
+
+ /* Check if no NDEF detected, init mem in Tag Type 5 */
+ if( mNDEF_URI.NfcType5_NDEFDetection() != NDEF_OK)
+ {
+ mNDEF_URI.CCFileStruct.MagicNumber = NFCT5_MAGICNUMBER_E1_CCFILE;
+ mNDEF_URI.CCFileStruct.Version = NFCT5_VERSION_V1_0;
+ mNDEF_URI.CCFileStruct.MemorySize = ( M24LR_MAX_SIZE / 8 ) & 0xFF;
+ mNDEF_URI.CCFileStruct.TT5Tag = 0x05;
+
+ /* Init of the Type Tag 5 component (M24LR) */
+ while( mNDEF_URI.NfcType5_TT5Init( ) != NFCTAG_OK);
+ }
+
+ /* Set the LED2 on to indicate Init done */
+ nfcNucleo->getLed2()=1;
+
+ /* Prepare URI NDEF message content */
+ strcpy( URI.protocol,URI_ID_0x01_STRING );
+ strcpy( URI.URI_Message,"st.com/st25" );
+ strcpy( URI.Information,"\0" );
+
+ /* Write NDEF to EEPROM */
+ while( mNDEF_URI.NDEF_WriteURI( &URI ) != NDEF_OK);
+
+ /* Set the LED3 on to indicate Programing done */
+ nfcNucleo->getLed3()=1;
+}
+
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mbed.bld Wed Jul 27 09:25:33 2016 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_official/code/mbed/builds/f9eeca106725 \ No newline at end of file
