PN532 NFC library for Seeed Studio's NFC Shield

Fork of PN532 by Yihui Xiong

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers NdefRecord.cpp Source File

NdefRecord.cpp

00001 
00002 #include <string>
00003 #include <string.h>
00004 #include <stdlib.h>
00005 
00006 #include "NdefRecord.h"
00007 #include "PN532_debug.h"
00008 
00009 NdefRecord::NdefRecord()
00010 {
00011     //DMSG("NdefRecord Constructor 1");
00012     _tnf = 0;
00013     _typeLength = 0;
00014     _payloadLength = 0;
00015     _idLength = 0;
00016     _type = (uint8_t *)NULL;
00017     _payload = (uint8_t *)NULL;
00018     _id = (uint8_t *)NULL;
00019 }
00020 
00021 NdefRecord::NdefRecord(const NdefRecord& rhs)
00022 {
00023     //DMSG("NdefRecord Constructor 2 (copy)");
00024 
00025     _tnf = rhs._tnf;
00026     _typeLength = rhs._typeLength;
00027     _payloadLength = rhs._payloadLength;
00028     _idLength = rhs._idLength;
00029     _type = (uint8_t *)NULL;
00030     _payload = (uint8_t *)NULL;
00031     _id = (uint8_t *)NULL;
00032 
00033     if (_typeLength)
00034     {
00035         _type = (uint8_t*)malloc(_typeLength);
00036         memcpy(_type, rhs._type, _typeLength);
00037     }
00038 
00039     if (_payloadLength)
00040     {
00041         _payload = (uint8_t*)malloc(_payloadLength);
00042         memcpy(_payload, rhs._payload, _payloadLength);
00043     }
00044 
00045     if (_idLength)
00046     {
00047         _id = (uint8_t*)malloc(_idLength);
00048         memcpy(_id, rhs._id, _idLength);
00049     }
00050 
00051 }
00052 
00053 // TODO NdefRecord::NdefRecord(tnf, type, payload, id)
00054 
00055 NdefRecord::~NdefRecord()
00056 {
00057     //DMSG("NdefRecord Destructor");
00058     if (_typeLength)
00059     {
00060         free(_type);
00061     }
00062 
00063     if (_payloadLength)
00064     {
00065         free(_payload);
00066     }
00067 
00068     if (_idLength)
00069     {
00070         free(_id);
00071     }
00072 }
00073 
00074 NdefRecord& NdefRecord::operator=(const NdefRecord& rhs)
00075 {
00076     //DMSG("NdefRecord ASSIGN");
00077 
00078     if (this != &rhs)
00079     {
00080         // free existing
00081         if (_typeLength)
00082         {
00083             free(_type);
00084         }
00085 
00086         if (_payloadLength)
00087         {
00088             free(_payload);
00089         }
00090 
00091         if (_idLength)
00092         {
00093             free(_id);
00094         }
00095 
00096         _tnf = rhs._tnf;
00097         _typeLength = rhs._typeLength;
00098         _payloadLength = rhs._payloadLength;
00099         _idLength = rhs._idLength;
00100 
00101         if (_typeLength)
00102         {
00103             _type = (uint8_t*)malloc(_typeLength);
00104             memcpy(_type, rhs._type, _typeLength);
00105         }
00106 
00107         if (_payloadLength)
00108         {
00109             _payload = (uint8_t*)malloc(_payloadLength);
00110             memcpy(_payload, rhs._payload, _payloadLength);
00111         }
00112 
00113         if (_idLength)
00114         {
00115             _id = (uint8_t*)malloc(_idLength);
00116             memcpy(_id, rhs._id, _idLength);
00117         }
00118     }
00119     return *this;
00120 }
00121 
00122 // size of records in uint8_ts
00123 int NdefRecord::getEncodedSize()
00124 {
00125     int size = 2; // tnf + typeLength
00126     if (_payloadLength > 0xFF)
00127     {
00128         size += 4;
00129     }
00130     else
00131     {
00132         size += 1;
00133     }
00134 
00135     if (_idLength)
00136     {
00137         size += 1;
00138     }
00139 
00140     size += (_typeLength + _payloadLength + _idLength);
00141 
00142     return size;
00143 }
00144 
00145 void NdefRecord::encode(uint8_t *data, bool firstRecord, bool lastRecord)
00146 {
00147     // assert data > getEncodedSize()
00148 
00149     uint8_t* data_ptr = &data[0];
00150 
00151     *data_ptr = getTnfuint8_t(firstRecord, lastRecord);
00152     data_ptr += 1;
00153 
00154     *data_ptr = _typeLength;
00155     data_ptr += 1;
00156 
00157     if (_payloadLength <= 0xFF) {  // short record
00158         *data_ptr = _payloadLength;
00159         data_ptr += 1;
00160     } else { // long format
00161         // 4 uint8_ts but we store length as an int
00162         data_ptr[0] = 0x0; // (_payloadLength >> 24) & 0xFF;
00163         data_ptr[1] = 0x0; // (_payloadLength >> 16) & 0xFF;
00164         data_ptr[2] = (_payloadLength >> 8) & 0xFF;
00165         data_ptr[3] = _payloadLength & 0xFF;
00166         data_ptr += 4;
00167     }
00168 
00169     if (_idLength)
00170     {
00171         *data_ptr = _idLength;
00172         data_ptr += 1;
00173     }
00174 
00175     //DMSG(2);
00176     memcpy(data_ptr, _type, _typeLength);
00177     data_ptr += _typeLength;
00178 
00179     memcpy(data_ptr, _payload, _payloadLength);
00180     data_ptr += _payloadLength;
00181 
00182     if (_idLength)
00183     {
00184         memcpy(data_ptr, _id, _idLength);
00185         data_ptr += _idLength;
00186     }
00187 }
00188 
00189 uint8_t NdefRecord::getTnfuint8_t(bool firstRecord, bool lastRecord)
00190 {
00191     int value = _tnf;
00192 
00193     if (firstRecord) { // mb
00194         value = value | 0x80;
00195     }
00196 
00197     if (lastRecord) { //
00198         value = value | 0x40;
00199     }
00200 
00201     // chunked flag is always false for now
00202     // if (cf) {
00203     //     value = value | 0x20;
00204     // }
00205 
00206     if (_payloadLength <= 0xFF) {
00207         value = value | 0x10;
00208     }
00209 
00210     if (_idLength) {
00211         value = value | 0x8;
00212     }
00213 
00214     return value;
00215 }
00216 
00217 uint8_t NdefRecord::getTnf()
00218 {
00219     return _tnf;
00220 }
00221 
00222 void NdefRecord::setTnf(uint8_t tnf)
00223 {
00224     _tnf = tnf;
00225 }
00226 
00227 unsigned int NdefRecord::getTypeLength()
00228 {
00229     return _typeLength;
00230 }
00231 
00232 int NdefRecord::getPayloadLength()
00233 {
00234     return _payloadLength;
00235 }
00236 
00237 unsigned int NdefRecord::getIdLength()
00238 {
00239     return _idLength;
00240 }
00241 
00242 string NdefRecord::getType()
00243 {
00244     char type[_typeLength + 1];
00245     memcpy(type, _type, _typeLength);
00246     type[_typeLength] = '\0'; // null terminate
00247     return string(type);
00248 }
00249 
00250 // this assumes the caller created type correctly
00251 void NdefRecord::getType(uint8_t* type)
00252 {
00253     memcpy(type, _type, _typeLength);
00254 }
00255 
00256 void NdefRecord::setType(const uint8_t * type, const unsigned int numuint8_ts)
00257 {
00258     if(_typeLength)
00259     {
00260         free(_type);
00261     }
00262 
00263     _type = (uint8_t*)malloc(numuint8_ts);
00264     memcpy(_type, type, numuint8_ts);
00265     _typeLength = numuint8_ts;
00266 }
00267 
00268 // assumes the caller sized payload properly
00269 void NdefRecord::getPayload(uint8_t *payload)
00270 {
00271     memcpy(payload, _payload, _payloadLength);
00272 }
00273 
00274 void NdefRecord::setPayload(const uint8_t * payload, const int numuint8_ts)
00275 {
00276     if (_payloadLength)
00277     {
00278         free(_payload);
00279     }
00280 
00281     _payload = (uint8_t*)malloc(numuint8_ts);
00282     memcpy(_payload, payload, numuint8_ts);
00283     _payloadLength = numuint8_ts;
00284 }
00285 
00286 string NdefRecord::getId()
00287 {
00288     char id[_idLength + 1];
00289     memcpy(id, _id, _idLength);
00290     id[_idLength] = '\0'; // null terminate
00291     return string(id);
00292 }
00293 
00294 void NdefRecord::getId(uint8_t *id)
00295 {
00296     memcpy(id, _id, _idLength);
00297 }
00298 
00299 void NdefRecord::setId(const uint8_t * id, const unsigned int numuint8_ts)
00300 {
00301     if (_idLength)
00302     {
00303         free(_id);
00304     }
00305 
00306     _id = (uint8_t*)malloc(numuint8_ts);
00307     memcpy(_id, id, numuint8_ts);
00308     _idLength = numuint8_ts;
00309 }
00310 
00311 void NdefRecord::print()
00312 {
00313     DMSG("  NDEF Record");
00314     DMSG("    TNF 0x");
00315     DMSG_HEX(_tnf);
00316     DMSG(" ");
00317     switch (_tnf) {
00318     case TNF_EMPTY:
00319         DMSG("Empty");
00320         break;
00321     case TNF_WELL_KNOWN:
00322         DMSG("Well Known");
00323         break;
00324     case TNF_MIME_MEDIA:
00325         DMSG("Mime Media");
00326         break;
00327     case TNF_ABSOLUTE_URI:
00328         DMSG("Absolute URI");
00329         break;
00330     case TNF_EXTERNAL_TYPE:
00331         DMSG("External");
00332         break;
00333     case TNF_UNKNOWN:
00334         DMSG("Unknown");
00335         break;
00336     case TNF_UNCHANGED:
00337         DMSG("Unchanged");
00338         break;
00339     case TNF_RESERVED:
00340         DMSG("Reserved");
00341         break;
00342     default:
00343         DMSG("\n");
00344     }
00345     DMSG("    Type Length 0x");
00346     DMSG_HEX(_typeLength);
00347     DMSG("    Payload Length 0x");
00348     DMSG_HEX(_payloadLength);
00349     if (_idLength)
00350     {
00351         DMSG("    Id Length 0x");
00352         DMSG_HEX(_idLength);
00353     }
00354     DMSG("    Type ");PrintHexChar(_type, _typeLength);
00355     // TODO chunk large payloads so this is readable
00356     DMSG("    Payload ");PrintHexChar(_payload, _payloadLength);
00357     if (_idLength)
00358     {
00359         DMSG("    Id ");PrintHexChar(_id, _idLength);
00360     }
00361     DMSG("    Record is ");
00362     DMSG_INT(getEncodedSize());
00363 }