00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "cmtmessage.h"
00021
00022 namespace xsens {
00023
00024 #ifdef _LOG_CMT_MSG
00025 #define MSGLOG CMTLOG
00026 #else
00027 #define MSGLOG(...)
00028 #endif
00029
00030 #ifndef CMT_OUTPUTSETTINGS_DATAFORMAT_DOUBLE
00031 #define CMT_OUTPUTSETTINGS_DATAFORMAT_DOUBLE 0x00000300
00032 #endif
00033
00034
00035
00036 Message::Message(const uint8_t msgId, const uint16_t length, const uint16_t maxLength)
00037 {
00038 if (maxLength < CMT_MAXMSGLEN)
00039 m_maxLength = CMT_MAXMSGLEN;
00040 else
00041 m_maxLength = maxLength;
00042 m_buffer = (MessageHeader*) new char[m_maxLength];
00043 MSGLOG("Message(%02x, %hu, %hu): buffer = %p\n",(int32_t) msgId, length, m_maxLength,m_buffer);
00044 memset(m_buffer,0,m_maxLength);
00045
00046 m_buffer->m_preamble = CMT_PREAMBLE;
00047 m_buffer->m_messageId = msgId;
00048 m_buffer->m_busId = CMT_BID_MASTER;
00049
00050 if (length >= 255)
00051 {
00052 m_buffer->m_length = CMT_EXTLENCODE;
00053
00054 m_buffer->m_datlen.m_extended.m_length.m_high = (uint8_t) (length >> 8);
00055 m_buffer->m_datlen.m_extended.m_length.m_low = (uint8_t) length;
00056
00057 m_checksum = &(((uint8_t*) m_buffer)[length + CMT_LEN_MSGEXTHEADER]);
00058 m_checksum[0] = -(msgId + CMT_EXTLENCODE + (uint8_t)length + (length >> 8));
00059 }
00060 else
00061 {
00062 m_buffer->m_length = (uint8_t) length;
00063 m_checksum = &(((uint8_t*) m_buffer)[length + CMT_LEN_MSGHEADER]);
00064 m_checksum[0] = -(msgId + (uint8_t) length);
00065 }
00066 m_checksum[0] -= CMT_BID_MASTER;
00067
00068 m_autoUpdateChecksum = true;
00069 }
00070
00071
00072
00073 Message::Message(const uint8_t* source, const uint16_t size, const uint16_t maxLength)
00074 {
00075 const MessageHeader* tmp = (MessageHeader*) source;
00076 uint16_t length;
00077
00078 if (maxLength < CMT_MAXMSGLEN)
00079 m_maxLength = CMT_MAXMSGLEN;
00080 else
00081 m_maxLength = maxLength;
00082
00083 if (tmp->m_length == CMT_EXTLENCODE)
00084 length = ((uint16_t) tmp->m_datlen.m_extended.m_length.m_high * 256 + (uint16_t) tmp->m_datlen.m_extended.m_length.m_low) + CMT_LEN_MSGEXTHEADERCS;
00085 else
00086 length = tmp->m_length + CMT_LEN_MSGHEADERCS;
00087 if (size && size < length)
00088 length = size;
00089
00090 if ((uint32_t) length > m_maxLength)
00091 m_maxLength = length;
00092
00093 m_buffer = (MessageHeader*) new char[m_maxLength];
00094 MSGLOG("Message(%02x%02x%02x%02x%02x%02x, %hu, %hu): buffer = %p\n",source[0],source[1],source[2],source[3],source[4],source[5], size, m_maxLength,m_buffer);
00095 if (length < m_maxLength)
00096 memset(&(((uint8_t*) m_buffer)[length]),0,m_maxLength-length);
00097
00098 memcpy(m_buffer,source,length);
00099
00100 m_checksum = &(((uint8_t*) m_buffer)[length-1]);
00101
00102 m_autoUpdateChecksum = true;
00103 }
00104
00105 Message::Message(const Message& src)
00106 {
00107 m_maxLength = src.m_maxLength;
00108 m_buffer = (MessageHeader*) new char[m_maxLength];
00109 memcpy(m_buffer,src.m_buffer,m_maxLength);
00110 ptrdiff_t add = (uint8_t*) src.m_checksum - (uint8_t*) src.m_buffer;
00111 m_checksum = (uint8_t*) m_buffer + add;
00112 m_autoUpdateChecksum = true;
00113 }
00114
00115
00116
00117 Message::~Message()
00118 {
00119 MSGLOG("~Message(): buffer = %p\n",m_buffer);
00120 LSTCHKDELNUL(m_buffer);
00121 }
00122
00123
00124
00125 void Message::clear(void)
00126 {
00127 memset(m_buffer,0,m_maxLength);
00128 m_checksum = &(((uint8_t*) m_buffer)[CMT_LEN_MSGHEADER]);
00129 m_buffer->m_preamble = CMT_PREAMBLE;
00130 m_buffer->m_busId = CMT_BID_MASTER;
00131 m_checksum[0] = (uint8_t) (-CMT_BID_MASTER);
00132 }
00133
00134
00135
00136 double Message::getDataDouble(const uint16_t offset) const
00137 {
00138 double ret;
00139 uint8_t* dest = (uint8_t*) &ret;
00140 uint8_t* src = &(getDataStart()[offset]);
00141 dest[0] = src[7]; dest[1] = src[6]; dest[2] = src[5]; dest[3] = src[4];
00142 dest[4] = src[3]; dest[5] = src[2]; dest[6] = src[1]; dest[7] = src[0];
00143
00144 return ret;
00145 }
00146
00147
00148
00149 float Message::getDataFloat(const uint16_t offset) const
00150 {
00151 float ret;
00152 uint8_t* dest = (uint8_t*) &ret;
00153 uint8_t* src = &(getDataStart()[offset]);
00154 dest[0] = src[3];
00155 dest[1] = src[2];
00156 dest[2] = src[1];
00157 dest[3] = src[0];
00158
00159 return ret;
00160 }
00161
00162
00163
00164 double Message::getDataF1220(const uint16_t offset) const
00165 {
00166 double ret;
00167 int32_t tmp;
00168 uint8_t* dest = (uint8_t*) &tmp;
00169 uint8_t* src = &(getDataStart()[offset]);
00170 dest[0] = src[3];
00171 dest[1] = src[2];
00172 dest[2] = src[1];
00173 dest[3] = src[0];
00174
00175 ret = ((double) tmp)/1048576.0;
00176 return ret;
00177 }
00178
00179
00180 union Itypes {
00181 int64_t i64;
00182 struct {
00183 int32_t i1,i0;
00184 } i32;
00185 struct {
00186 int16_t s3,s2,s1,s0;
00187 } i16;
00188 struct {
00189 signed char b7,b6,b5,b4,b3,b2,b1,b0;
00190 } i8;
00191
00192 double d;
00193 struct {
00194 float f1,f0;
00195 } f32;
00196 };
00197
00198
00199
00200 double Message::getDataFP1632(const uint16_t offset) const
00201 {
00202
00203 int16_t fpint;
00204 int32_t fpfrac;
00205
00206 uint8_t* dest = (uint8_t*) &fpfrac;
00207 uint8_t* src = &(getDataStart()[offset]);
00208 dest[3] = *(src++);
00209 dest[2] = *(src++);
00210 dest[1] = *(src++);
00211 dest[0] = *(src++);
00212
00213 dest = (uint8_t*) &fpint;
00214 dest[1] = *(src++);
00215 dest[0] = *(src++);
00216
00217 Itypes fp;
00218 fp.i32.i0 = fpint;
00219 fp.i32.i1 = fpfrac;
00220
00221 return (double) fp.i64 / 4294967296.0;
00222 }
00223
00224
00225
00226
00227 double Message::getDataFPValue(const uint64_t outputSettings, const uint16_t offset) const
00228 {
00229 switch (outputSettings & CMT_OUTPUTSETTINGS_DATAFORMAT_MASK)
00230 {
00231 case CMT_OUTPUTSETTINGS_DATAFORMAT_FLOAT:
00232 return getDataFloat(offset);
00233
00234 case CMT_OUTPUTSETTINGS_DATAFORMAT_DOUBLE:
00235 return getDataDouble(offset);
00236
00237 case CMT_OUTPUTSETTINGS_DATAFORMAT_FP1632:
00238 return getDataFP1632(offset);
00239
00240 case CMT_OUTPUTSETTINGS_DATAFORMAT_F1220:
00241 return getDataF1220(offset);
00242 }
00243 return 0.0;
00244 }
00245
00246
00247
00248
00249 void Message::getDataFPValue(double *dest, const uint64_t outputSettings, uint16_t offset, const int16_t numValues) const
00250 {
00251 for (uint16_t i=0; i<numValues; i++) {
00252 switch (outputSettings & CMT_OUTPUTSETTINGS_DATAFORMAT_MASK)
00253 {
00254 case CMT_OUTPUTSETTINGS_DATAFORMAT_FLOAT:
00255 *dest++ = getDataFloat(offset);
00256 offset += 4;
00257 break;
00258
00259 case CMT_OUTPUTSETTINGS_DATAFORMAT_DOUBLE:
00260 *dest++ = getDataDouble(offset);
00261 offset += 8;
00262 break;
00263
00264 case CMT_OUTPUTSETTINGS_DATAFORMAT_FP1632:
00265 *dest++ = getDataFP1632(offset);
00266 offset += 6;
00267 break;
00268
00269 case CMT_OUTPUTSETTINGS_DATAFORMAT_F1220:
00270 *dest++ = getDataF1220(offset);
00271 offset += 4;
00272 }
00273 }
00274 }
00275
00276
00277
00278 uint32_t Message::getDataLong(const uint16_t offset) const
00279 {
00280 uint32_t ret;
00281 uint8_t* dest = (uint8_t*) &ret;
00282 uint8_t* src = &(getDataStart()[offset]);
00283 dest[0] = src[3];
00284 dest[1] = src[2];
00285 dest[2] = src[1];
00286 dest[3] = src[0];
00287
00288 return ret;
00289 }
00290
00291
00292
00293 uint16_t Message::getDataShort(const uint16_t offset) const
00294 {
00295 uint16_t ret;
00296 uint8_t* dest = (uint8_t*) &ret;
00297 uint8_t* src = &(getDataStart()[offset]);
00298 dest[0] = src[1];
00299 dest[1] = src[0];
00300
00301 return ret;
00302 }
00303
00304
00305
00306 uint16_t Message::getDataSize(void) const
00307 {
00308 if (m_buffer->m_length == 255)
00309 return ((uint16_t) m_buffer->m_datlen.m_extended.m_length.m_high * 256 + (uint16_t) m_buffer->m_datlen.m_extended.m_length.m_low);
00310 else
00311 return m_buffer->m_length;
00312 }
00313
00314
00315
00316 uint8_t* Message::getDataStart(void) const
00317 {
00318 if (m_buffer->m_length == 255)
00319 {
00320 return const_cast<uint8_t*>(m_buffer->m_datlen.m_extended.m_data);
00321 }
00322 else
00323 return const_cast<uint8_t*>(m_buffer->m_datlen.m_data);
00324 }
00325
00326
00327
00328 uint16_t Message::getTotalMessageSize(void) const
00329 {
00330 if (m_buffer->m_length == 255)
00331 return ((uint16_t) m_buffer->m_datlen.m_extended.m_length.m_high * 256 + (uint16_t) m_buffer->m_datlen.m_extended.m_length.m_low) + CMT_LEN_MSGEXTHEADERCS;
00332 else
00333 return m_buffer->m_length + CMT_LEN_MSGHEADERCS;
00334 }
00335
00336
00337 bool Message::isChecksumOk(void) const
00338 {
00339 if (getTotalMessageSize() > m_maxLength)
00340 return false;
00341 return calcChecksum() == m_checksum[0];
00342 }
00343
00344
00345
00346 XsensResultValue Message::loadFromString(const uint8_t* source, const uint16_t size)
00347 {
00348 MSGLOG(__FUNCTION__ " size=%hu, first 7 bytes: %02x %02x %02x %02x %02x %02x %02x\n",size,source[0],source[1],source[2],source[3],source[4],source[5],source[6]);
00349 if (size > m_maxLength)
00350 {
00351 MSGLOG(__FUNCTION__ " returns XRV_PARAMINVALID\n");
00352 return XRV_PARAMINVALID;
00353 }
00354 memcpy(m_buffer,source,size);
00355 m_checksum = ((uint8_t*) m_buffer) + size-1;
00356
00357 if (m_buffer->m_length == CMT_EXTLENCODE)
00358 {
00359 if (((uint16_t) m_buffer->m_datlen.m_extended.m_length.m_high * 256 + (uint16_t) m_buffer->m_datlen.m_extended.m_length.m_low) > size-CMT_LEN_MSGEXTHEADERCS)
00360 {
00361 MSGLOG(__FUNCTION__ " returns XRV_DATACORRUPT (extended length)\n");
00362 return XRV_DATACORRUPT;
00363 }
00364 }
00365 else
00366 {
00367 if (m_buffer->m_length > size-CMT_LEN_MSGHEADERCS)
00368 {
00369 MSGLOG(__FUNCTION__ " returns XRV_DATACORRUPT (normal length)\n");
00370 return XRV_DATACORRUPT;
00371 }
00372 }
00373
00374 if (m_checksum[0] != calcChecksum())
00375 {
00376 MSGLOG(__FUNCTION__ " returns XRV_CHECKSUMFAULT\n");
00377 return XRV_CHECKSUMFAULT;
00378 }
00379
00380 MSGLOG(__FUNCTION__ " returns XRV_OK\n");
00381 return XRV_OK;
00382 }
00383
00384
00385 void Message::resizeData(const uint16_t newSize)
00386 {
00387 int32_t index, oldLength;
00388
00389 MSGLOG("Message.resizeData(%hu): buffer = %p\n",newSize,m_buffer);
00390
00391 if ((uint32_t) (newSize + CMT_LEN_MSGEXTHEADERCS) > m_maxLength)
00392 {
00393 uint16_t newLen = (uint16_t) (m_maxLength+m_maxLength);
00394 if ((newSize + CMT_LEN_MSGEXTHEADERCS) > newLen)
00395 newLen = newSize + CMT_LEN_MSGEXTHEADERCS;
00396 m_buffer = (MessageHeader*) realloc(m_buffer,newLen);
00397 m_maxLength = newLen;
00398 }
00399
00400 MSGLOG("Message.resizeData after realloc(%hu): buffer = %p\n",m_maxLength,m_buffer);
00401
00402 if (newSize >= CMT_EXTLENCODE)
00403 {
00404 if (m_buffer->m_length < CMT_EXTLENCODE)
00405 {
00406
00407 for (index = (int32_t) m_buffer->m_length; index >= 0; --index)
00408 m_buffer->m_datlen.m_extended.m_data[index] =
00409 m_buffer->m_datlen.m_data[index];
00410
00411 oldLength = m_buffer->m_length;
00412 m_buffer->m_length = CMT_EXTLENCODE;
00413 }
00414 else
00415 {
00416 oldLength = ((uint16_t) m_buffer->m_datlen.m_extended.m_length.m_high * 256 + (uint16_t) m_buffer->m_datlen.m_extended.m_length.m_low);
00417 }
00418 m_buffer->m_datlen.m_extended.m_length.m_high = (uint8_t) (newSize >> 8);
00419 m_buffer->m_datlen.m_extended.m_length.m_low = (uint8_t) newSize;
00420
00421 for (index = oldLength; index < newSize; ++index)
00422 m_buffer->m_datlen.m_extended.m_data[index] = 0;
00423
00424 m_checksum = &m_buffer->m_datlen.m_extended.m_data[newSize];
00425 }
00426 else
00427 {
00428 if (m_buffer->m_length == CMT_EXTLENCODE)
00429 {
00430 oldLength = ((uint16_t) m_buffer->m_datlen.m_extended.m_length.m_high * 256 + (uint16_t) m_buffer->m_datlen.m_extended.m_length.m_low);
00431
00432 for (index = 0; index < newSize; ++index)
00433 m_buffer->m_datlen.m_data[index] =
00434 m_buffer->m_datlen.m_extended.m_data[index];
00435 }
00436 else
00437 oldLength = m_buffer->m_length;
00438 m_buffer->m_length = (uint8_t) newSize;
00439 for (index = oldLength; index < newSize; ++index)
00440 m_buffer->m_datlen.m_data[index] = 0;
00441 m_checksum = &m_buffer->m_datlen.m_data[newSize];
00442 }
00443 if (m_autoUpdateChecksum)
00444 recomputeChecksum();
00445 MSGLOG("Message.resizeData end(%hu): buffer = %p\n",m_maxLength,m_buffer);
00446 }
00447
00448
00449
00450 void Message::setBusId(const uint8_t busId)
00451 {
00452 if (m_autoUpdateChecksum)
00453 m_checksum[0] += m_buffer->m_busId - busId;
00454 m_buffer->m_busId = busId;
00455 }
00456
00457
00458
00459 void Message::setDataBuffer(const uint8_t* data, const uint16_t offset,
00460 const uint16_t count)
00461 {
00462 if (getDataSize() < offset+count)
00463 resizeData(offset+count);
00464
00465 if (count > 0)
00466 {
00467 uint8_t * dest = &(getDataStart()[offset]);
00468 for (uint16_t i = 0;i < count;++i)
00469 {
00470 if (m_autoUpdateChecksum)
00471 m_checksum[0] += dest[i] - data[i];
00472 dest[i] = data[i];
00473 }
00474 }
00475 }
00476
00477
00478 void Message::setDataByte(const uint8_t data, const uint16_t offset)
00479 {
00480 if (getDataSize() < offset + 1)
00481 resizeData(offset+1);
00482
00483 uint8_t* dest = &(getDataStart()[offset]);
00484 if (m_autoUpdateChecksum)
00485 m_checksum[0] += dest[0] - data;
00486 dest[0] = data;
00487 }
00488
00489
00490 void Message::setDataDouble(const double data, const uint16_t offset)
00491 {
00492 if (getDataSize() < offset+8)
00493 resizeData(offset+8);
00494
00495 uint8_t* dest = &(getDataStart()[offset]);
00496 const uint8_t* cdata = (const uint8_t*) &data;
00497 if (m_autoUpdateChecksum)
00498 m_checksum[0] += dest[0] + dest[1] + dest[2] + dest[3]
00499 + dest[4] + dest[5] + dest[6] + dest[7]
00500 - cdata[0] - cdata[1] - cdata[2] - cdata[3]
00501 - cdata[4] - cdata[5] - cdata[6] - cdata[7];
00502
00503 const uint8_t* src = (const uint8_t*) &data;
00504 dest[0] = src[7]; dest[1] = src[6]; dest[2] = src[5]; dest[3] = src[4];
00505 dest[4] = src[3]; dest[5] = src[2]; dest[6] = src[1]; dest[7] = src[0];
00506 }
00507
00508
00509 void Message::setDataFloat(const float data, const uint16_t offset)
00510 {
00511 if (getDataSize() < offset+4)
00512 resizeData(offset+4);
00513
00514 uint8_t* dest = &(getDataStart()[offset]);
00515 const uint8_t* cdata = (const uint8_t*) &data;
00516 if (m_autoUpdateChecksum)
00517 m_checksum[0] += dest[0] + dest[1] + dest[2] + dest[3]
00518 - cdata[0] - cdata[1] - cdata[2] - cdata[3];
00519
00520 const uint8_t* src = (const uint8_t*) &data;
00521 dest[0] = src[3];
00522 dest[1] = src[2];
00523 dest[2] = src[1];
00524 dest[3] = src[0];
00525 }
00526
00527
00528 void Message::setDataF1220(const double data, const uint16_t offset)
00529 {
00530 int32_t val = (int32_t) (data*1048576.0);
00531 setDataLong(val,offset);
00532 }
00533
00534
00535
00536 void Message::setDataFP1632(const double data, const uint16_t offset)
00537 {
00538 if (getDataSize() < offset+6)
00539 resizeData(offset+6);
00540
00541 Itypes fp;
00542 fp.d = data;
00543 int32_t dexp = ((fp.i32.i0 & (0x7fffffffL)) >> 20) - 1023;
00544
00545 int16_t fpint;
00546 int32_t fpfrac;
00547
00548 if (dexp <= 14)
00549 {
00550 fp.i16.s0 = (fp.i16.s0 & 0x000F) | 0x0010;
00551 if (data < 0)
00552 fp.i64 = -fp.i64;
00553 if (dexp > -32)
00554 fp.i64 = fp.i64 >> (20-dexp);
00555 else
00556 fp.i64 = fp.i64 >> 52;
00557 fpint = fp.i16.s1;
00558 fpfrac = fp.i32.i1;
00559 }
00560 else
00561 {
00562 if (data < 0)
00563 {
00564 fpint = ((int16_t) (0x8000));
00565 fpfrac = 0;
00566 }
00567 else
00568 {
00569 fpint = 0x7fff;
00570 fpfrac = -1;
00571 }
00572 }
00573
00574 uint8_t* src = (uint8_t*) &fpfrac;
00575 uint8_t* dest = &(getDataStart()[offset]);
00576
00577 *(dest++) = src[3];
00578 *(dest++) = src[2];
00579 *(dest++) = src[1];
00580 *(dest++) = src[0];
00581
00582 src = (uint8_t*) &fpint;
00583 *(dest++) = src[1];
00584 *(dest++) = src[0];
00585 }
00586
00587
00588 void Message::setDataFPValue(const uint64_t outputSettings, const double data, const uint16_t offset)
00589 {
00590 switch (outputSettings & CMT_OUTPUTSETTINGS_DATAFORMAT_MASK)
00591 {
00592 case CMT_OUTPUTSETTINGS_DATAFORMAT_FLOAT:
00593 return setDataFloat((const float)data, offset);
00594
00595 case CMT_OUTPUTSETTINGS_DATAFORMAT_DOUBLE:
00596 return setDataDouble(data, offset);
00597
00598 case CMT_OUTPUTSETTINGS_DATAFORMAT_FP1632:
00599 return setDataFP1632(data, offset);
00600
00601 case CMT_OUTPUTSETTINGS_DATAFORMAT_F1220:
00602 return setDataF1220(data, offset);
00603 }
00604 }
00605
00606
00607 void Message::setDataFPValue(const uint64_t outputSettings, const double *data, uint16_t offset, const uint16_t numValues)
00608 {
00609 for (uint16_t i=0; i<numValues; i++) {
00610 switch (outputSettings & CMT_OUTPUTSETTINGS_DATAFORMAT_MASK)
00611 {
00612 case CMT_OUTPUTSETTINGS_DATAFORMAT_FLOAT:
00613 setDataFloat((float)data[i], offset);
00614 offset += 4;
00615 break;
00616
00617 case CMT_OUTPUTSETTINGS_DATAFORMAT_DOUBLE:
00618 setDataDouble(data[i], offset);
00619 offset += 8;
00620 break;
00621
00622 case CMT_OUTPUTSETTINGS_DATAFORMAT_FP1632:
00623 setDataFP1632(data[i], offset);
00624 offset += 6;
00625 break;
00626
00627 case CMT_OUTPUTSETTINGS_DATAFORMAT_F1220:
00628 setDataF1220(data[i], offset);
00629 offset += 4;
00630 }
00631 }
00632 }
00633
00634
00635 void Message::setDataLong(const uint32_t data, const uint16_t offset)
00636 {
00637 if (getDataSize() < offset+4)
00638 resizeData(offset+4);
00639
00640 uint8_t* dest = &(getDataStart()[offset]);
00641 if (m_autoUpdateChecksum)
00642 m_checksum[0] +=(uint8_t)(dest[0] + dest[1] + dest[2] + dest[3] - (data & 0xFF)-
00643 ((data >> 8) & 0xFF) - ((data >> 16) & 0xFF) - ((data >> 24) & 0xFF));
00644
00645 const uint8_t* src = (const uint8_t*) &data;
00646 dest[0] = src[3];
00647 dest[1] = src[2];
00648 dest[2] = src[1];
00649 dest[3] = src[0];
00650 }
00651
00652
00653 void Message::setDataShort(const uint16_t data, const uint16_t offset)
00654 {
00655 if (getDataSize() < offset+2)
00656 resizeData(offset+2);
00657
00658 uint8_t* dest = &(getDataStart()[offset]);
00659 if (m_autoUpdateChecksum)
00660 m_checksum[0] += dest[0] + dest[1] - (data & 255) - (data >> 8);
00661
00662 const uint8_t* src = (const uint8_t*) &data;
00663 dest[0] = src[1];
00664 dest[1] = src[0];
00665 }
00666
00667
00668
00669 void Message::setMessageId(const uint8_t msgId)
00670 {
00671 if (m_autoUpdateChecksum)
00672 m_checksum[0] += m_buffer->m_messageId - msgId;
00673 m_buffer->m_messageId =msgId;
00674 }
00675
00676
00677
00678 void Message::operator = (const Message& src)
00679 {
00680 if (m_maxLength != src.m_maxLength)
00681 {
00682 LSTCHKDELNUL(m_buffer);
00683 m_maxLength = src.m_maxLength;
00684 m_buffer = (MessageHeader*) new char[m_maxLength];
00685 }
00686 memcpy(m_buffer,src.m_buffer,m_maxLength);
00687 ptrdiff_t add = (uint8_t*) src.m_checksum - (uint8_t*) src.m_buffer;
00688 m_checksum = (uint8_t*) m_buffer + add;
00689 }
00690
00691
00692
00693 void Message::deleteData(uint16_t size, uint16_t offset)
00694 {
00695 if (size == 0)
00696 return;
00697 uint16_t oldSize = getDataSize();
00698 uint16_t newSize;
00699 if (offset >= oldSize)
00700 return;
00701
00702 if (oldSize > offset + size)
00703 newSize = oldSize - size;
00704 else
00705 newSize = offset;
00706
00707
00708 uint8_t* address = getDataBuffer();
00709 for (uint16_t i = offset; i < newSize; ++i)
00710 address[i] = address[i+size];
00711
00712
00713 resizeData(newSize);
00714 }
00715
00716
00717
00718 void Message::insertData(uint16_t size, uint16_t offset)
00719 {
00720 if (size == 0)
00721 return;
00722
00723 uint16_t oldSize = getDataSize();
00724 resizeData(oldSize + size);
00725
00726 uint8_t* address = getDataBuffer();
00727 for (uint16_t i = oldSize-1; i >= offset && i < oldSize; --i)
00728 address[i+size] = address[i];
00729 }
00730
00731
00732
00733 uint8_t computeChecksum(const uint8_t* buffer, uint32_t length)
00734 {
00735 uint8_t cs = 0;
00736 while (length--)
00737 cs -= *(buffer++);
00738
00739 return cs;
00740 }
00741
00742 }