00001
00002
00003
00004
00005
00006
00007 #ifndef ZBSDTHELPER_H
00008 #define ZBSDTHELPER_H
00009
00010 #include <zbsHash.h>
00011 #include <bitshuffle/bitshuffle.h>
00012 namespace CAFE_BSHELPER {
00013
00014 using boost::multi_index_container;
00015 using namespace boost::multi_index;
00016
00017 bsreadContainer_set bsdt;
00018
00019 std::vector<BSChannel> bsrdV;
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 enum bsdtIndex {BS_INT8=0, BS_UINT8, BS_INT16, BS_UINT16,
00037 BS_INT32, BS_UINT32, BS_INT64, BS_UINT64,
00038 BS_FLOAT32, BS_FLOAT64, BS_BOOL, BS_STRING, BS_CHAR=BS_STRING};
00039
00040 void bsdtInsert() {
00041 bsdt.insert(bsreadContainer(BS_INT8, "int8"));
00042 bsdt.insert(bsreadContainer(BS_UINT8, "uint8"));
00043 bsdt.insert(bsreadContainer(BS_INT16, "int16"));
00044 bsdt.insert(bsreadContainer(BS_UINT16, "uint16"));
00045 bsdt.insert(bsreadContainer(BS_INT32, "int32"));
00046 bsdt.insert(bsreadContainer(BS_UINT32, "uint32"));
00047 bsdt.insert(bsreadContainer(BS_INT64, "int64"));
00048 bsdt.insert(bsreadContainer(BS_UINT64, "uint64"));
00049 bsdt.insert(bsreadContainer(BS_FLOAT32,"float32"));
00050 bsdt.insert(bsreadContainer(BS_FLOAT64,"float64"));
00051 bsdt.insert(bsreadContainer(BS_BOOL, "bool"));
00052 bsdt.insert(bsreadContainer(BS_STRING, "string"));
00053 bsdt.insert(bsreadContainer(BS_CHAR, "string"));
00054 }
00055
00056
00057 int getByteSize(unsigned int dt) {
00058 #define __METHOD__ "getByteSize (unsigned int)"
00059 switch(dt) {
00060 case BS_INT8:
00061 return sizeof(int8_t);
00062 case BS_UINT8:
00063 case BS_BOOL:
00064 return sizeof(uint8_t);
00065 case BS_INT16:
00066 return sizeof(int16_t);
00067 case BS_UINT16:
00068 return sizeof(uint16_t);
00069 case BS_INT32:
00070 return sizeof(int32_t);
00071 case BS_UINT32:
00072 return sizeof(uint32_t);
00073 case BS_INT64:
00074 return sizeof(int64_t);
00075 case BS_UINT64:
00076 return sizeof(uint64_t);
00077 case BS_FLOAT32:
00078 return sizeof(float);
00079 case BS_FLOAT64:
00080 return sizeof(double);
00081 case BS_STRING:
00082 return sizeof(char);
00083 default:
00084 std::cout << __FILE__ << "//" << __LINE__ << "//" << __METHOD__ << std::endl;
00085 std::cout << "Enumerated input value " << dt << " is outside allowed band: " << BS_INT8 << " and " << BS_STRING << std::endl;
00086 print_out_by<by_bsID>(bsdt);
00087 std::cout << "Returning byte size of 1" << std::endl;
00088 return 1;
00089 }
00090 #undef __METHOD__
00091 }
00092
00093
00094 int getByteSize(std::string dt) {
00095 #define __METHOD__ "getByteSize (string)"
00096 bsreadContainer_set_by_name & name_index = bsdt.get<by_bsName> ();
00097 bsreadContainer_set_by_name::iterator it_name;
00098 unsigned int bsdtIndex;
00099
00100
00101 it_name = name_index.find(dt);
00102 if ( (it_name) != name_index.end() ) {
00103 bsdtIndex=(*it_name).by_bsID;
00104 return getByteSize(bsdtIndex);
00105 }
00106
00107 std::cout << __FILE__ << "//" << __LINE__ << "//" << __METHOD__ << std::endl;
00108 std::cout << "string value " << dt << " is not recognized " << std::endl;
00109 print_out_by<by_bsID>(bsdt);
00110 std::cout << "Returning byte size of 1" << std::endl;
00111 return 1;
00112
00113 #undef __METHOD__
00114 }
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00129 void printBits(int const size, void const * const ptr)
00130 {
00131 unsigned char *b= (unsigned char *) ptr;
00132 unsigned char byte;
00133 int i, j;
00134 for (i=size-1; i>=0; i--) {
00135 for (j=7; j>=0; j--) {
00136 byte =(b[i]>>j ) &1;
00137 printf("%u", byte);
00138 }
00139 }
00140 puts("");
00141 return;
00142 }
00143
00144
00145
00151 int unfoldPreBlob(const char * data, long &uncompressedSize, int &blockSize) {
00152
00153
00154 uncompressedSize = ( ((data[7] <<0) & 0x7f) | ((data[7]<<0) & 0x80) | (data[6]<<8) | (data[5]<<16) | (data[4]<<24)
00155 | ((long long) data[3]<<32) | ((long long) data[2]<<40) | ((long long) data[1]<<48) | ((long long) data[0]<<56) ) ;
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173 blockSize= ( ((data[11]<<0)) | ((data[11]<<0)& 0x80) | (data[10]<<8) | (data[9]<<16) | (data[8]<<24) );
00174
00175
00176
00177
00178
00179 return ICAFE_NORMAL;;
00180 }
00181
00182
00188 template <class CTYPE> class DataBitset {
00189 public:
00190 DataBitset (){};
00191 ~DataBitset (){};
00192 CTYPE unfold(char * data, size_t start, size_t end, std::string encoding )
00193 {
00194
00195 if (encoding=="big") {
00196
00197 for (short n=start; n < end; n++) {
00198 i = (i << 8) + data[n];
00199 }
00200 }
00201 else {
00202
00203 for (short n = end; n >= start; n--) {
00204 i = (i << 8) + data[n];
00205 }
00206 }
00207
00208 return i;
00209 }
00210 private:
00211 CTYPE i;
00212 };
00213
00214
00220 template <class CTYPE> class IntegerBitsetV {
00221 public:
00222 IntegerBitsetV (){};
00223 ~IntegerBitsetV (){};
00224
00225 CTYPE unfold(char * data, unsigned int nelem, std::string encoding, std::vector<CTYPE> &valV )
00226 {
00227 valV.clear();
00228 valV.reserve(nelem);
00229 cSize=sizeof(CTYPE);
00230 idx=0;
00231 if (encoding=="big") {
00232 switch (cSize) {
00233 case 1:
00234 for (unsigned int i=0; i<nelem; ++i) {
00235 idx=i*cSize;
00236 iVal=data[i];
00237 valV.push_back(iVal);
00238 }
00239 break;
00240 case 2:
00241 for (unsigned int i=0; i<nelem; ++i) {
00242 idx=i*cSize;
00243 iVal=( ( (data[idx+1]<<0) & 0x7f) | ((data[idx+1]<<0) & 0x80) | (data[idx]<<8) );
00244 valV.push_back(iVal);
00245 }
00246 break;
00247 case 4:
00248 for (unsigned int i=0; i<nelem; ++i) {
00249 idx=i*cSize;
00250 iVal=( ( (data[idx+3]<<0) & 0x7f) | ((data[idx+3]<<0) & 0x80) | (data[idx+2]<<8) | (data[idx+1]<<16) | (data[idx]<<24));
00251 valV.push_back(iVal);
00252 }
00253 break;
00254 case 8:
00255 for (unsigned int i=0; i<nelem; ++i) {
00256 idx=i*cSize;
00257 iVal=( ( (data[idx+7]<<0) & 0x7f) | ((data[idx+7]<<0) & 0x80) | (data[idx+6]<<8) | (data[idx+5]<<16) | (data[idx+4]<<24)
00258 | ((long long) data[idx+3]<<32) | ((long long) data[idx+2]<<40) | ((long long) data[idx+1]<<48) | ((long long) data[idx]<<56) ) ;
00259 valV.push_back(iVal);
00260 }
00261 default:
00262 std::cout << "Cannot process element of size " << cSize << " bytes" << std::endl;
00263 }
00264 }
00265 else {
00266 switch (cSize) {
00267 case 1:
00268 for (unsigned int i=0; i<nelem; ++i) {
00269 idx=i*cSize;
00270 iVal=data[i];
00271 valV.push_back(iVal);
00272 }
00273 break;
00274 case 2:
00275 for (unsigned int i=0; i<nelem; ++i) {
00276 idx=i*cSize;
00277 iVal=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) );
00278 valV.push_back(iVal);
00279 }
00280 break;
00281 case 4:
00282 for (unsigned int i=0; i<nelem; ++i) {
00283 idx=i*cSize;
00284 iVal=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) | (data[idx+2]<<16) | (data[idx+3]<<24));
00285 valV.push_back(iVal);
00286 }
00287 break;
00288 case 8:
00289 for (unsigned int i=0; i<nelem; ++i) {
00290 idx=i*cSize;
00291 iVal=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) | (data[idx+2]<<16) | (data[idx+3]<<24)
00292 | ((long long) data[idx+4]<<32) | ((long long) data[idx+5]<<40) | ((long long) data[idx+6]<<48) | ((long long) data[idx+7]<<56) ) ;
00293 valV.push_back(iVal);
00294 }
00295 default:
00296 std::cout << "Cannot process element of size " << cSize << " bytes" << std::endl;
00297 }
00298 }
00299 return valV[0];
00300 }
00301 private:
00302 unsigned int cSize;
00303 unsigned int idx;
00304 CTYPE iVal;
00305 };
00306
00307
00308
00314 template <class CTYPE> class IntegerBitset {
00315 public:
00316 IntegerBitset (){};
00317 ~IntegerBitset (){};
00318
00319 CTYPE * unfold(char * data, unsigned int nelem, std::string encoding )
00320 {
00321
00322 cSize=sizeof(CTYPE);
00323 idx=0;
00324 iVal=new CTYPE[nelem];
00325
00326 if (encoding=="big") {
00327 switch (cSize) {
00328 case 1:
00329 for (unsigned int i=0; i<nelem; ++i) {
00330 idx=i*cSize;
00331 iVal[i]= ( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) );
00332 }
00333 break;
00334 case 2:
00335 for (unsigned int i=0; i<nelem; ++i) {
00336 idx=i*cSize;
00337 iVal[i]=( ( (data[idx+1]<<0) & 0x7f) | ((data[idx+1]<<0) & 0x80) | (data[idx]<<8) );
00338
00339
00340
00341
00342
00343
00344 }
00345
00346 break;
00347 case 4:
00348 for (unsigned int i=0; i<nelem; ++i) {
00349 idx=i*cSize;
00350 iVal[i]=( ( (data[idx+3]<<0) & 0x7f) | ((data[idx+3]<<0) & 0x80) | (data[idx+2]<<8) | (data[idx+1]<<16) | (data[idx]<<24));
00351 }
00352 break;
00353 case 8:
00354 for (unsigned int i=0; i<nelem; ++i) {
00355 idx=i*cSize;
00356 iVal[i]=( ( (data[idx+7]<<0) & 0x7f) | ((data[idx+7]<<0) & 0x80) | (data[idx+6]<<8) | (data[idx+5]<<16) | (data[idx+4]<<24)
00357 | ((long long) data[idx+3]<<32) | ((long long) data[idx+2]<<40) | ((long long) data[idx+1]<<48) | ((long long) data[idx]<<56) ) ;
00358 }
00359 default:
00360 std::cout << "Cannot process element of size " << cSize << " bytes" << std::endl;
00361 }
00362 }
00363 else {
00364 switch (cSize) {
00365 case 1:
00366 for (unsigned int i=0; i<nelem; ++i) {
00367 idx=i*cSize;
00368 iVal[i]= ( ((data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) );
00369 }
00370 break;
00371 case 2:
00372 for (unsigned int i=0; i<nelem; ++i) {
00373 idx=i*cSize;
00374 iVal[i]=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) );
00375 }
00376 break;
00377 case 4:
00378 for (unsigned int i=0; i<nelem; ++i) {
00379 idx=i*cSize;
00380 iVal[i]=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) | (data[idx+2]<<16) | (data[idx+3]<<24));
00381 }
00382 break;
00383 case 8:
00384 for (unsigned int i=0; i<nelem; ++i) {
00385 idx=i*cSize;
00386 iVal[i]=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) | (data[idx+2]<<16) | (data[idx+3]<<24)
00387 | ((long long) data[idx+4]<<32) | ((long long) data[idx+5]<<40) | ((long long) data[idx+6]<<48) | ((long long) data[idx+7]<<56) ) ;
00388 }
00389 default:
00390 std::cout << "Cannot process element of size " << cSize << " bytes" << std::endl;
00391 }
00392 }
00393 return iVal;
00394 }
00395
00396
00397
00398 CTYPE unfoldScalar(char * data, std::string encoding )
00399 {
00400 cSize=sizeof(CTYPE);
00401 idx=0;
00402
00403 if (encoding=="big") {
00404 switch (cSize) {
00405 case 1:
00406 idx=0;
00407 iValScalar= data[idx]<<0;
00408 break;
00409 case 2:
00410 idx=0;
00411 iValScalar=( (data[idx+1]<<0) | (data[idx]<<8) );
00412 break;
00413 case 4:
00414 idx=0;
00415 iValScalar=( ( (data[idx+3]<<0) & 0x7f) | ((data[idx+3]<<0) & 0x80) | (data[idx+2]<<8) | (data[idx+1]<<16) | (data[idx]<<24));
00416 break;
00417 case 8:
00418 idx=0;
00419 iValScalar=( ( (data[idx+7]<<0) & 0x7f) | ((data[idx+7]<<0) & 0x80) | (data[idx+6]<<8) | (data[idx+5]<<16) | (data[idx+4]<<24)
00420 | ((long long) data[idx+3]<<32) | ((long long) data[idx+2]<<40) | ((long long) data[idx+1]<<48) | ((long long) data[idx]<<56) ) ;
00421 default:
00422 std::cout << "Cannot process element of size " << cSize << " bytes" << std::endl;
00423 }
00424 }
00425 else {
00426 switch (cSize) {
00427 case 1:
00428 idx=0;
00429 iValScalar= (data[idx]<<0) ;
00430 break;
00431 case 2:
00432 idx=0;
00433 iValScalar=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) );
00434 break;
00435 case 4:
00436 idx=0;
00437 iValScalar=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) | (data[idx+2]<<16) | (data[idx+3]<<24));
00438 break;
00439 case 8:
00440 idx=0;
00441 iValScalar=( ( (data[idx]<<0) & 0x7f) | ((data[idx]<<0) & 0x80) | (data[idx+1]<<8) | (data[idx+2]<<16) | (data[idx+3]<<24)
00442 | ((long long) data[idx+4]<<32) | ((long long) data[idx+5]<<40) | ((long long) data[idx+6]<<48) | ((long long) data[idx+7]<<56) ) ;
00443 default:
00444 std::cout << "Cannot process element of size " << cSize << " bytes" << std::endl;
00445 }
00446 }
00447 return iValScalar;
00448 }
00449
00450 private:
00451 unsigned int cSize;
00452 unsigned int idx;
00453 CTYPE * iVal;
00454 CTYPE iValScalar;
00455 };
00456
00457
00458
00459
00460
00461
00462
00463
00464
00465
00466
00467
00473 template <class CTYPE> class FloatBitset {
00474 public:
00475 FloatBitset (){};
00476 ~FloatBitset (){};
00477 CTYPE * unfold(char * data, unsigned int nelem, std::string encoding) {
00478 cSize=sizeof(CTYPE);
00479 val=new CTYPE[nelem];
00480
00481 if (encoding=="big") {
00482 for (unsigned int i=0; i<nelem; ++i) {
00483 start=i*cSize; end=(i+1)*cSize;
00484
00485 inst=0;
00486
00487 for (size_t char_nbr = start; char_nbr < end ; char_nbr++) {
00488
00489 idx=(nelem*cSize)-1-char_nbr;
00490
00491
00492 bar.c[inst]=data[idx];
00493 ++inst;
00494 }
00495
00496
00497 val[nelem-1-i]=bar.v;
00498
00499 }
00500 }
00501
00502
00503 else {
00504 for (unsigned int i=0; i<nelem; ++i) {
00505 start=i*cSize; end=(i+1)*cSize;
00506 inst=0;
00507
00508 for (size_t char_nbr = start; char_nbr < end ; char_nbr++) {
00509 bar.c[inst]=data[char_nbr];
00510 ++inst;
00511 }
00512 val[i]=bar.v;
00513 }
00514 }
00515 return val;
00516 }
00517
00518 CTYPE unfoldScalar(char * data, std::string encoding) {
00519 cSize=sizeof(CTYPE);
00520
00521 if (encoding=="big") {
00522 start=0; end=cSize;
00523 inst=0;
00524 for (size_t char_nbr = start; char_nbr < end ; char_nbr++) {
00525 idx=cSize-1-char_nbr;
00526 bar.c[inst]=data[idx];
00527 ++inst;
00528 }
00529 }
00530
00531
00532 else {
00533
00534 start=0; end=cSize;
00535 inst=0;
00536
00537 for (size_t char_nbr = start; char_nbr < end ; char_nbr++) {
00538 bar.c[inst]=data[char_nbr];
00539 ++inst;
00540 }
00541
00542
00543 }
00544 return bar.v;
00545 };
00546
00547
00548
00549
00550
00551
00552
00553
00554
00555
00556
00557
00558
00559
00560
00561
00562
00563
00564
00565
00566
00567 private:
00568 union dUnion{char c[sizeof(CTYPE)]; CTYPE v;} bar;
00569 CTYPE * val;
00570 unsigned int cSize;
00571 int start;
00572 int end;
00573 int inst;
00574 int idx;
00575 };
00576
00577
00578
00579
00585 template <class CTYPE> class FloatBitsetV {
00586 public:
00587 FloatBitsetV (){};
00588 ~FloatBitsetV (){};
00589 CTYPE unfold(char * data, unsigned int nelem, std::string encoding, std::vector<CTYPE> &valV) {
00590
00591
00592
00593
00594 cSize=sizeof(CTYPE);
00595
00596
00597 if (encoding=="big") {
00598 for (unsigned int i=0; i<nelem; ++i) {
00599
00600 start=i*cSize; end=(i+1)*cSize;
00601 std::cout << start << " // " << end << std::endl;
00602 inst=0;
00603 for (size_t char_nbr = start; char_nbr < end ; char_nbr++) {
00604 idx=(nelem*cSize)-1-char_nbr;
00605 bar.c[inst]=data[idx];
00606 ++inst;
00607 }
00608
00609 std::cout << bar.v << " [" << (nelem-1-i) << "] " ;
00610 valV[nelem-1-i]=bar.v;
00611 std::cout << valV[nelem-1-i] << " [" << (nelem-1-i) << "] " ;
00612
00613
00614
00615 }
00616 } else {
00617 for (unsigned int i=0; i<nelem; ++i) {
00618 start=i*cSize; end=(i+1)*cSize;
00619 inst=0;
00620 for (size_t char_nbr = start; char_nbr < end ; char_nbr++) {
00621 bar.c[inst]=data[char_nbr];
00622 ++inst;
00623 }
00624 std::cout << bar.v << " [" << i << "] " ;
00625 valV[i]=bar.v;
00626
00627 }
00628 }
00629 std::cout << std::endl;
00630 return valV[0];
00631 }
00632
00633 private:
00634 union dUnion{char c[sizeof(CTYPE)]; CTYPE v;} bar;
00635 unsigned int cSize;
00636 int start;
00637 int end;
00638 int inst;
00639 int idx;
00640 };
00641
00642
00643
00647 int bitshuffleDecompress( const char * data, char* & regen_buffer, int sizeData, int dtByteSize) {
00648 #define __METHOD__ "bitshuffleDecompress"
00649 long uncompressedSize=0; int blockSize=0;
00650 int localDebug=0;
00651
00652 int sizeBlob = sizeData-BSREAD_PREBLOB_BYTES;
00653 if (sizeBlob <1) {
00654 std::cout << __FILE__ << "//" << __LINE__ << "//" << __METHOD__ << std::endl;
00655 std::cout << "WARNING: data size " << sizeData << " is less than BSREAD_PREBLOB_BYTES " << BSREAD_PREBLOB_BYTES << std::endl;
00656 std::cout << "This should not happen. Probably we are trying to decompress uncompressed data! " << std::endl;
00657 return ECAFE_BITSHUFF_BADCOUNT;
00658 }
00659
00660 unfoldPreBlob(data, uncompressedSize, blockSize);
00661
00662
00663
00664 int dataNelem=uncompressedSize/dtByteSize;
00665
00666 regen_buffer = (char *) malloc(uncompressedSize);
00667 if (regen_buffer == NULL) {
00668 std::cout << __FILE__ << "//" << __LINE__ << "//" << __METHOD__ << std::endl;
00669 std::cout << "FAILED TO ALLOC MEM of size: " << uncompressedSize << std::endl;
00670 return ECAFE_BITSHUFF_ALLOCMEM;
00671 }
00672
00673 char * dataBlob = new char[sizeBlob];
00674 int ij=0;
00675 if(localDebug) std::cout << " BSREAD_PREBLOB_BYTES " << BSREAD_PREBLOB_BYTES <<std::endl;
00676 if(localDebug) std::cout << " sizeData " << sizeData <<std::endl;
00677 if(localDebug) std::cout << " sizeBlob " << sizeBlob <<std::endl;
00678 if(localDebug) std::cout << " dataNelem " << dataNelem <<std::endl;
00679 if(localDebug) std::cout << " dtByteSize " << dtByteSize <<std::endl;
00680 for (int char_nbr = BSREAD_PREBLOB_BYTES; char_nbr < sizeData; char_nbr++) {
00681 dataBlob[ij]=data[char_nbr];
00682 ++ij;
00683 }
00684
00685 const int decompressed_size = bshuf_decompress_lz4((const char *) dataBlob, regen_buffer, dataNelem, dtByteSize, 0);
00686 delete [] dataBlob;
00687 if(localDebug) std::cout << " " << " decompressed_size " << decompressed_size << std::endl;
00688 if (decompressed_size < 0) {return ECAFE_BITSHUFF_DECOMPRESS;}
00689 else if (decompressed_size == 0){
00690 if(localDebug)std::cout << "0 decompressed size! Should have a positive number for successful deompression?" <<std::endl;
00691 }
00692 else {
00693 if(localDebug)std::cout << "We successfully decompressed some data!" <<std::endl;
00694 }
00695
00696
00697
00698
00699
00700
00701
00702
00703
00704
00705
00706
00707
00708 return ICAFE_NORMAL;
00709 #undef __METHOD__
00710 }
00711
00712 }
00713 #endif