Jack Hansdampf / mbed-mqtt-GSOE1

Dependents:   ESP8266MQTT

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers Payload.cpp Source File

Payload.cpp

00001 /**************************************************************************************
00002  * Copyright (c) 2016, Tomoaki Yamaguchi
00003  *
00004  * All rights reserved. This program and the accompanying materials
00005  * are made available under the terms of the Eclipse Public License v1.0
00006  * and Eclipse Distribution License v1.0 which accompany this distribution.
00007  *
00008  * The Eclipse Public License is available at
00009  *    http://www.eclipse.org/legal/epl-v10.html
00010  * and the Eclipse Distribution License is available at
00011  *   http://www.eclipse.org/org/documents/edl-v10.php.
00012  *
00013  * Contributors:
00014  *    Tomoaki Yamaguchi - initial API and implementation and/or initial documentation
00015  **************************************************************************************/
00016 
00017 #include <sys/stat.h>
00018 #include <stdlib.h>
00019 #include <stdio.h>
00020 #include <string.h>
00021 #include <fcntl.h>
00022 
00023 #include "LMqttsnClientApp.h"
00024 #include "Payload.h"
00025 
00026 using namespace std;
00027 using namespace linuxAsyncClient;
00028 
00029 
00030 extern uint16_t getUint16(const uint8_t* pos);
00031 extern uint32_t getUint32(const uint8_t* pos);
00032 extern float    getFloat32(const uint8_t* pos);
00033 
00034 extern void setUint16(uint8_t* pos, uint16_t val);
00035 extern void setUint32(uint8_t* pos, uint32_t val);
00036 extern void setFloat32(uint8_t* pos, float val);
00037 
00038 /*=====================================
00039         Class Payload
00040   =====================================*/
00041 Payload::Payload(){
00042     _buff = _pos = 0;
00043     _len = 0;
00044     _elmCnt = 0;
00045     _memDlt = 0;
00046 }
00047 
00048 Payload::Payload(uint16_t len){
00049     _buff = (uint8_t*)calloc(len, sizeof(uint8_t));
00050     if(_buff == 0){
00051         exit(-1);
00052     }
00053     _pos = _buff;
00054     _elmCnt = 0;
00055     _len = len;
00056     _memDlt = 1;
00057 }
00058 
00059 Payload::~Payload(){
00060     if(_memDlt){
00061         free(_buff);
00062     }
00063 }
00064 
00065 void Payload::init(){
00066     _pos = _buff;
00067     _elmCnt = 0;
00068 }
00069 
00070 uint16_t Payload::getAvailableLength(){
00071     return _len - (_pos - _buff);
00072 }
00073 
00074 uint16_t Payload::getLen(){
00075     return _pos - _buff;
00076 }
00077 
00078 uint8_t* Payload::getRowData(){
00079     return _buff;
00080 }
00081 
00082 /*======================
00083  *     setter
00084  ======================*/
00085 int8_t Payload::set_uint32(uint32_t val){
00086     if(getAvailableLength() < 6){
00087         return -1;
00088     }
00089     if(val < 128){
00090         *_pos++ = (uint8_t)val;
00091     }else if(val < 256){
00092         *_pos++ = MSGPACK_UINT8;
00093         *_pos++ = (uint8_t)val;
00094     }else if(val < 65536){
00095         *_pos++ = MSGPACK_UINT16;
00096         setUint16(_pos,(uint16_t) val);
00097         _pos += 2;
00098     }else{
00099         *_pos++ = MSGPACK_UINT32;
00100         setUint32(_pos, val);
00101         _pos += 4;
00102     }
00103     _elmCnt++;
00104     return 0;
00105 }
00106 
00107 int8_t Payload::set_int32(int32_t val){
00108     if(getAvailableLength() < 6){
00109             return -1;
00110     }
00111     if((val > -32) && (val < 0)){
00112         *_pos++ = val | MSGPACK_NEGINT;
00113     }else if((val >= 0) && (val < 128)){
00114         *_pos++ = val;
00115     }else if(val > -128 && val < 128){
00116         *_pos++ = MSGPACK_INT8;
00117         *_pos++ = (uint8_t)val;
00118     }else if(val > -32768 && val < 32768){
00119         *_pos++ = MSGPACK_INT16;
00120         setUint16(_pos, (uint16_t)val);
00121         _pos += 2;
00122     }else{
00123         *_pos++ = MSGPACK_INT32;
00124         setUint32(_pos, (uint32_t)val);
00125         _pos += 4;
00126     }
00127     _elmCnt++;
00128     return 0;
00129 }
00130 
00131 int8_t Payload::set_float(float val){
00132     if(getAvailableLength() < 6){
00133             return -1;
00134     }
00135     *_pos++ = MSGPACK_FLOAT32;
00136     setFloat32(_pos, val);
00137     _pos += 4;
00138     _elmCnt++;
00139     return 0;
00140 }
00141 
00142 int8_t Payload::set_str(char* val){
00143     return set_str((const char*) val);
00144 }
00145 
00146 int8_t Payload::set_str(const char* val){
00147     if(getAvailableLength() < strlen(val) + 3){
00148         return -1;
00149     }else if(strlen(val) < 32){
00150         *_pos++ = (uint8_t)strlen(val) | MSGPACK_FIXSTR;
00151     }else if(strlen(val) < 256){
00152         *_pos++ = MSGPACK_STR8;
00153         *_pos++ = (uint8_t)strlen(val);
00154     }else if(strlen(val) < 65536){
00155         *_pos++ = MSGPACK_STR16;
00156         setUint16(_pos, (uint16_t)strlen(val));
00157         _pos += 2;
00158     }
00159     memcpy(_pos, val, strlen(val));
00160     _pos += strlen(val);
00161     return 0;
00162 }
00163 
00164 int8_t Payload::set_array(uint8_t val){
00165     if(getAvailableLength() < (uint16_t)val+ 1){
00166         return -1;
00167     }
00168     if(val < 16){
00169         *_pos++ = MSGPACK_ARRAY15 | val;
00170     }else{
00171         *_pos++ = MSGPACK_ARRAY16;
00172         setUint16(_pos,(uint16_t)val);
00173         _pos += 2;
00174     }
00175     _elmCnt++;
00176     return 0;
00177 }
00178 
00179 int8_t Payload::set_bool(bool val){
00180     if (getAvailableLength() < 1){
00181             return -1;
00182     }
00183     if (val){
00184         *_pos++ = MSGPACK_TRUE;
00185     }else {
00186         *_pos++ = MSGPACK_FALSE;
00187     }
00188     _elmCnt++;
00189     return 0;
00190 }
00191 /*======================
00192  *     getter
00193  ======================*/
00194 uint8_t Payload::getArray(uint8_t index){
00195     uint8_t rc = 0;
00196     uint8_t* val = getBufferPos(index);
00197     if(val != 0){
00198         if(*val == MSGPACK_ARRAY15){
00199             rc = *val & 0x0F;
00200         }else if(*val == MSGPACK_ARRAY16){
00201             rc = (uint8_t)getUint16(val + 1);
00202         }
00203     }
00204     return rc;
00205 }
00206 
00207 bool Payload::get_bool(uint8_t index){
00208     uint8_t* val = getBufferPos(index);
00209     if (*val == MSGPACK_FALSE){
00210         return false;
00211     }else{
00212         return true;
00213     }
00214 }
00215 
00216 uint32_t Payload::get_uint32(uint8_t index){
00217     uint32_t rc = 0;
00218     uint8_t* val = getBufferPos(index);
00219     if(val != 0){
00220         if(*val == MSGPACK_UINT32){
00221             rc = getUint32(val + 1);
00222         }else if(*val == MSGPACK_UINT16){
00223             rc = (uint32_t)getUint16(val + 1);
00224         }else if(*val == MSGPACK_UINT8){
00225             rc = (uint32_t)*(val + 1);
00226         }else if(*val < 128){
00227             rc = (uint32_t)*val;
00228         }
00229     }
00230     return rc;
00231 }
00232 
00233 int32_t Payload::get_int32(uint8_t index){
00234     int32_t rc = 0;
00235     uint8_t* val = getBufferPos(index);
00236     if(val != 0){
00237         if(*val == MSGPACK_INT32){
00238             rc = (int32_t) getUint32(val + 1);
00239         }else if(*val == MSGPACK_INT16){
00240             uint16_t d16 = getUint16(val + 1);
00241             if(d16 >= 32768){
00242                 rc = d16 - 65536;
00243             }else{
00244                 rc = (int32_t)d16;
00245             }
00246         }else if(*val == MSGPACK_INT8){
00247             rc = (int32_t)*(val + 1);
00248         }else if((*val & MSGPACK_NEGINT) == MSGPACK_NEGINT){
00249             *val &= ~MSGPACK_NEGINT;
00250             rc = ((int32_t)*val) * -1;
00251         }else{
00252             rc = (int32_t) *val;
00253         }
00254     }
00255     return rc;
00256 }
00257 
00258 float Payload::get_float(uint8_t index){
00259     uint8_t* val = getBufferPos(index);
00260     if(val != 0){
00261         if(*val == MSGPACK_FLOAT32){
00262             return getFloat32(val + 1);
00263         }
00264     }
00265     return 0;
00266 }
00267 
00268 const char* Payload::get_str(uint8_t index, uint16_t* len){
00269     uint8_t* val = getBufferPos(index);
00270     if(val != 0){
00271         if(*val == MSGPACK_STR16){
00272             *len = getUint16(val + 1);
00273             return (const char*)(val + 3);
00274         }else if(*val == MSGPACK_STR8){
00275             *len = *(val + 1);
00276             return (const char*)(val + 2);
00277         }else if( (*val & 0xf0) == MSGPACK_FIXSTR ){
00278             *len = *val & 0x0f;
00279             return (const char*)(val + 1);
00280         }
00281     }
00282     *len = 0;
00283     return (const char*) 0;
00284 
00285 }
00286 
00287 
00288 uint8_t* Payload::getBufferPos(uint8_t index){
00289     uint8_t* bpos = 0;
00290     uint8_t* pos = _buff;
00291 
00292     for(uint8_t i = 0; i <= index; i++){
00293         bpos = pos;
00294         switch(*pos){
00295         case MSGPACK_FALSE:
00296         case MSGPACK_TRUE:
00297             pos++;
00298             break;
00299         case MSGPACK_UINT8:
00300         case MSGPACK_INT8:
00301             pos += 2;
00302             break;
00303         case MSGPACK_UINT16:
00304         case MSGPACK_INT16:
00305         case MSGPACK_ARRAY16:
00306             pos += 3;
00307             break;
00308         case MSGPACK_UINT32:
00309         case MSGPACK_INT32:
00310         case MSGPACK_FLOAT32:
00311             pos += 5;
00312             break;
00313         case MSGPACK_STR8:
00314             pos += *(pos + 1) + 2;
00315             break;
00316         case MSGPACK_STR16:
00317             pos += getUint16(pos + 1) + 3;
00318             break;
00319         default:
00320             if((*pos < MSGPACK_POSINT) ||
00321                 ((*pos & 0xf0) == MSGPACK_NEGINT) ||
00322                 ((*pos & 0xf0) == MSGPACK_ARRAY15)) {
00323                 pos++;
00324             }else if((*pos & 0xf0) == MSGPACK_FIXSTR){
00325                 pos += (*pos & 0x0f) + 1;
00326             }
00327         }
00328         /*
00329         if((pos - _buff) >= _len){
00330             return 0;
00331         }
00332         */
00333     }
00334     return bpos;
00335 }
00336 
00337 void Payload::setRowData(uint8_t* payload, uint16_t payloadLen){
00338     if(_memDlt){
00339             free(_buff);
00340             _memDlt = 0;
00341     }
00342     _buff = payload;
00343     _len = payloadLen;
00344     _pos = _buff + _len;
00345 }
00346 
00347 
00348