Bytes.h

Go to the documentation of this file.
00001 /* @(#)root/base:$Id: Bytes.h 29788 2009-08-14 22:47:46Z pcanal $ */
00002 
00003 /*************************************************************************
00004  * Copyright (C) 1995-2000, Rene Brun and Fons Rademakers.               *
00005  * All rights reserved.                                                  *
00006  *                                                                       *
00007  * For the licensing terms see $ROOTSYS/LICENSE.                         *
00008  * For the list of contributors see $ROOTSYS/README/CREDITS.             *
00009  *************************************************************************/
00010 
00011 #ifndef ROOT_Bytes
00012 #define ROOT_Bytes
00013 
00014 
00015 //////////////////////////////////////////////////////////////////////////
00016 //                                                                      //
00017 // Bytes                                                                //
00018 //                                                                      //
00019 // A set of inline byte handling routines.                              //
00020 //                                                                      //
00021 // The set of tobuf() and frombuf() routines take care of packing a     //
00022 // basic type value into a buffer in network byte order (i.e. they      //
00023 // perform byte swapping when needed). The buffer does not have to      //
00024 // start on a machine (long) word boundary.                             //
00025 //                                                                      //
00026 // For __GNUC__ on linux on i486 processors and up                      //
00027 // use the `bswap' opcode provided by the GNU C Library.                //
00028 //                                                                      //
00029 // The set of host2net() and net2host() routines convert a basic type   //
00030 // value from host to network byte order and vice versa. On BIG ENDIAN  //
00031 // machines this is a no op.                                            //
00032 //                                                                      //
00033 //////////////////////////////////////////////////////////////////////////
00034 
00035 #ifndef ROOT_Rtypes
00036 #include "Rtypes.h"
00037 #endif
00038 
00039 #ifndef __CINT__
00040 #include <string.h>
00041 #endif
00042 
00043 #if (defined(__linux) || defined(__APPLE__)) && \
00044     (defined(__i386__) || defined(__x86_64__)) && \
00045      defined(__GNUC__)
00046 #define R__USEASMSWAP
00047 #endif
00048 
00049 //Big bug in inline byte swapping code with Intel's icc
00050 #if defined(__INTEL_COMPILER) && __INTEL_COMPILER < 1000
00051 #undef R__USEASMSWAP
00052 #endif
00053 
00054 #if defined(R__USEASMSWAP) && !defined(__CINT__)
00055 #include "Byteswap.h"
00056 #endif
00057 
00058 //______________________________________________________________________________
00059 inline void tobuf(char *&buf, Bool_t x)
00060 {
00061    UChar_t x1 = x;
00062    *buf++ = x1;
00063 }
00064 
00065 inline void tobuf(char *&buf, UChar_t x)
00066 {
00067    *buf++ = x;
00068 }
00069 
00070 inline void tobuf(char *&buf, UShort_t x)
00071 {
00072 #ifdef R__BYTESWAP
00073 # if defined(R__USEASMSWAP)
00074    *((UShort_t *)buf) = Rbswap_16(x);
00075 # else
00076    // To work around a stupid optimization bug in MSVC++ 6.0
00077    const UShort_t *intermediary = &x;
00078    char *sw = (char *) intermediary;
00079    buf[0] = sw[1];
00080    buf[1] = sw[0];
00081 # endif
00082 #else
00083    memcpy(buf, &x, sizeof(UShort_t));
00084 #endif
00085    buf += sizeof(UShort_t);
00086 }
00087 
00088 inline void tobuf(char *&buf, UInt_t x)
00089 {
00090 #ifdef R__BYTESWAP
00091 # if defined(R__USEASMSWAP)
00092    *((UInt_t *)buf) = Rbswap_32(x);
00093 # else
00094    // To work around a stupid optimization bug in MSVC++ 6.0
00095    const UInt_t *intermediary = &x;
00096    char *sw = (char *)intermediary;
00097    buf[0] = sw[3];
00098    buf[1] = sw[2];
00099    buf[2] = sw[1];
00100    buf[3] = sw[0];
00101 # endif
00102 #else
00103    memcpy(buf, &x, sizeof(UInt_t));
00104 #endif
00105    buf += sizeof(UInt_t);
00106 }
00107 
00108 inline void tobuf(char *&buf, ULong_t x)
00109 {
00110 #ifdef R__BYTESWAP
00111    // To work around a stupid optimization bug in MSVC++ 6.0
00112    const ULong_t *intermediary = &x;
00113    char *sw = (char *)intermediary;
00114    if (sizeof(ULong_t) == 8) {
00115       buf[0] = sw[7];
00116       buf[1] = sw[6];
00117       buf[2] = sw[5];
00118       buf[3] = sw[4];
00119       buf[4] = sw[3];
00120       buf[5] = sw[2];
00121       buf[6] = sw[1];
00122       buf[7] = sw[0];
00123    } else {
00124       buf[0] = 0;
00125       buf[1] = 0;
00126       buf[2] = 0;
00127       buf[3] = 0;
00128       buf[4] = sw[3];
00129       buf[5] = sw[2];
00130       buf[6] = sw[1];
00131       buf[7] = sw[0];
00132    }
00133 #else
00134    if (sizeof(ULong_t) == 8) {
00135       memcpy(buf, &x, 8);
00136    } else {
00137       buf[0] = 0;
00138       buf[1] = 0;
00139       buf[2] = 0;
00140       buf[3] = 0;
00141       memcpy(buf+4, &x, 4);
00142    }
00143 #endif
00144    buf += 8;
00145 }
00146 
00147 inline void tobuf(char *&buf, Long_t x)
00148 {
00149 #ifdef R__BYTESWAP
00150    // To work around a stupid optimization bug in MSVC++ 6.0
00151    const Long_t *intermediary = &x;
00152    char *sw = (char *)intermediary;
00153    if (sizeof(Long_t) == 8) {
00154       buf[0] = sw[7];
00155       buf[1] = sw[6];
00156       buf[2] = sw[5];
00157       buf[3] = sw[4];
00158       buf[4] = sw[3];
00159       buf[5] = sw[2];
00160       buf[6] = sw[1];
00161       buf[7] = sw[0];
00162    } else {
00163       if (x < 0) {
00164          buf[0] = (char) -1;
00165          buf[1] = (char) -1;
00166          buf[2] = (char) -1;
00167          buf[3] = (char) -1;
00168       } else {
00169          buf[0] = 0;
00170          buf[1] = 0;
00171          buf[2] = 0;
00172          buf[3] = 0;
00173       }
00174       buf[4] = sw[3];
00175       buf[5] = sw[2];
00176       buf[6] = sw[1];
00177       buf[7] = sw[0];
00178    }
00179 #else
00180    if (sizeof(Long_t) == 8) {
00181       memcpy(buf, &x, 8);
00182    } else {
00183       if (x < 0) {
00184          buf[0] = (char) -1;
00185          buf[1] = (char) -1;
00186          buf[2] = (char) -1;
00187          buf[3] = (char) -1;
00188       } else {
00189          buf[0] = 0;
00190          buf[1] = 0;
00191          buf[2] = 0;
00192          buf[3] = 0;
00193       }
00194       memcpy(buf+4, &x, 4);
00195    }
00196 #endif
00197    buf += 8;
00198 }
00199 
00200 inline void tobuf(char *&buf, ULong64_t x)
00201 {
00202 #ifdef R__BYTESWAP
00203 # if defined(R__USEASMSWAP)
00204    *((ULong64_t *)buf) = Rbswap_64(x);
00205 # else
00206    // To work around a stupid optimization bug in MSVC++ 6.0
00207    const ULong64_t *intermediary = &x;
00208    char *sw = (char *)intermediary;
00209    buf[0] = sw[7];
00210    buf[1] = sw[6];
00211    buf[2] = sw[5];
00212    buf[3] = sw[4];
00213    buf[4] = sw[3];
00214    buf[5] = sw[2];
00215    buf[6] = sw[1];
00216    buf[7] = sw[0];
00217 # endif
00218 #else
00219    memcpy(buf, &x, sizeof(ULong64_t));
00220 #endif
00221    buf += sizeof(ULong64_t);
00222 }
00223 
00224 inline void tobuf(char *&buf, Float_t x)
00225 {
00226 #ifdef R__BYTESWAP
00227 # if defined(R__USEASMSWAP)
00228    union {
00229       volatile UInt_t  i;
00230       volatile Float_t f;
00231    } u;
00232    u.f = x;
00233    *((UInt_t *)buf) = Rbswap_32(u.i);
00234 # else
00235    union {
00236       volatile char    c[4];
00237       volatile Float_t f;
00238    } u;
00239    u.f = x;
00240    buf[0] = u.c[3];
00241    buf[1] = u.c[2];
00242    buf[2] = u.c[1];
00243    buf[3] = u.c[0];
00244 # endif
00245 #else
00246    memcpy(buf, &x, sizeof(Float_t));
00247 #endif
00248    buf += sizeof(Float_t);
00249 }
00250 
00251 inline void tobuf(char *&buf, Double_t x)
00252 {
00253 #ifdef R__BYTESWAP
00254 # if defined(R__USEASMSWAP)
00255    union {
00256       volatile ULong64_t l;
00257       volatile Double_t  d;
00258    } u;
00259    u.d = x;
00260    *((ULong64_t *)buf) = Rbswap_64(u.l);
00261 # else
00262    union {
00263       volatile char     c[8];
00264       volatile Double_t d;
00265    } u;
00266    u.d = x;
00267    buf[0] = u.c[7];
00268    buf[1] = u.c[6];
00269    buf[2] = u.c[5];
00270    buf[3] = u.c[4];
00271    buf[4] = u.c[3];
00272    buf[5] = u.c[2];
00273    buf[6] = u.c[1];
00274    buf[7] = u.c[0];
00275 # endif
00276 #else
00277    memcpy(buf, &x, sizeof(Double_t));
00278 #endif
00279    buf += sizeof(Double_t);
00280 }
00281 
00282 inline void frombuf(char *&buf, Bool_t *x)
00283 {
00284    UChar_t x1;
00285    x1 = *buf++;
00286    *x = (Bool_t) (x1 != 0);
00287 }
00288 
00289 inline void frombuf(char *&buf, UChar_t *x)
00290 {
00291    *x = *buf++;
00292 }
00293 
00294 inline void frombuf(char *&buf, UShort_t *x)
00295 {
00296 #ifdef R__BYTESWAP
00297 # if defined(R__USEASMSWAP)
00298    *x = Rbswap_16(*((UShort_t *)buf));
00299 # else
00300    char *sw = (char *)x;
00301    sw[0] = buf[1];
00302    sw[1] = buf[0];
00303 # endif
00304 #else
00305    memcpy(x, buf, sizeof(UShort_t));
00306 #endif
00307    buf += sizeof(UShort_t);
00308 }
00309 
00310 inline void frombuf(char *&buf, UInt_t *x)
00311 {
00312 #ifdef R__BYTESWAP
00313 # if defined(R__USEASMSWAP)
00314    *x = Rbswap_32(*((UInt_t *)buf));
00315 # else
00316    char *sw = (char *)x;
00317    sw[0] = buf[3];
00318    sw[1] = buf[2];
00319    sw[2] = buf[1];
00320    sw[3] = buf[0];
00321 # endif
00322 #else
00323    memcpy(x, buf, sizeof(UInt_t));
00324 #endif
00325    buf += sizeof(UInt_t);
00326 }
00327 
00328 inline void frombuf(char *&buf, ULong_t *x)
00329 {
00330 #ifdef R__BYTESWAP
00331    char *sw = (char *)x;
00332    if (sizeof(ULong_t) == 8) {
00333       sw[0] = buf[7];
00334       sw[1] = buf[6];
00335       sw[2] = buf[5];
00336       sw[3] = buf[4];
00337       sw[4] = buf[3];
00338       sw[5] = buf[2];
00339       sw[6] = buf[1];
00340       sw[7] = buf[0];
00341    } else {
00342       sw[0] = buf[7];
00343       sw[1] = buf[6];
00344       sw[2] = buf[5];
00345       sw[3] = buf[4];
00346    }
00347 #else
00348    if (sizeof(ULong_t) == 8) {
00349       memcpy(x, buf, 8);
00350    } else {
00351       memcpy(x, buf+4, 4);
00352    }
00353 #endif
00354    buf += 8;
00355 }
00356 
00357 inline void frombuf(char *&buf, ULong64_t *x)
00358 {
00359 #ifdef R__BYTESWAP
00360 # if defined(R__USEASMSWAP)
00361    *x = Rbswap_64(*((ULong64_t *)buf));
00362 # else
00363    char *sw = (char *)x;
00364    sw[0] = buf[7];
00365    sw[1] = buf[6];
00366    sw[2] = buf[5];
00367    sw[3] = buf[4];
00368    sw[4] = buf[3];
00369    sw[5] = buf[2];
00370    sw[6] = buf[1];
00371    sw[7] = buf[0];
00372 # endif
00373 #else
00374    memcpy(x, buf, sizeof(ULong64_t));
00375 #endif
00376    buf += sizeof(ULong64_t);
00377 }
00378 
00379 inline void frombuf(char *&buf, Float_t *x)
00380 {
00381 #ifdef R__BYTESWAP
00382 # if defined(R__USEASMSWAP)
00383    // Use a union to allow strict-aliasing
00384    union {
00385       volatile UInt_t  i;
00386       volatile Float_t f;
00387    } u;
00388    u.i = Rbswap_32(*((UInt_t *)buf));
00389    *x = u.f;
00390 # else
00391    union {
00392       volatile char    c[4];
00393       volatile Float_t f;
00394    } u;
00395    u.c[0] = buf[3];
00396    u.c[1] = buf[2];
00397    u.c[2] = buf[1];
00398    u.c[3] = buf[0];
00399    *x = u.f;
00400 # endif
00401 #else
00402    memcpy(x, buf, sizeof(Float_t));
00403 #endif
00404    buf += sizeof(Float_t);
00405 }
00406 
00407 inline void frombuf(char *&buf, Double_t *x)
00408 {
00409 #ifdef R__BYTESWAP
00410 # if defined(R__USEASMSWAP)
00411    // Use a union to allow strict-aliasing
00412    union {
00413       volatile ULong64_t l;
00414       volatile Double_t  d;
00415    } u;
00416    u.l = Rbswap_64(*((ULong64_t *)buf));
00417    *x = u.d;
00418 # else
00419    union {
00420       volatile char     c[8];
00421       volatile Double_t d;
00422    } u;
00423    u.c[0] = buf[7];
00424    u.c[1] = buf[6];
00425    u.c[2] = buf[5];
00426    u.c[3] = buf[4];
00427    u.c[4] = buf[3];
00428    u.c[5] = buf[2];
00429    u.c[6] = buf[1];
00430    u.c[7] = buf[0];
00431    *x = u.d;
00432 # endif
00433 #else
00434    memcpy(x, buf, sizeof(Double_t));
00435 #endif
00436    buf += sizeof(Double_t);
00437 }
00438 
00439 inline void tobuf(char *&buf, Char_t x)   { tobuf(buf, (UChar_t) x); }
00440 inline void tobuf(char *&buf, Short_t x)  { tobuf(buf, (UShort_t) x); }
00441 inline void tobuf(char *&buf, Int_t x)    { tobuf(buf, (UInt_t) x); }
00442 inline void tobuf(char *&buf, Long64_t x) { tobuf(buf, (ULong64_t) x); }
00443 
00444 inline void frombuf(char *&buf, Char_t *x)   { frombuf(buf, (UChar_t *) x); }
00445 inline void frombuf(char *&buf, Short_t *x)  { frombuf(buf, (UShort_t *) x); }
00446 inline void frombuf(char *&buf, Int_t *x)    { frombuf(buf, (UInt_t *) x); }
00447 inline void frombuf(char *&buf, Long_t *x)   { frombuf(buf, (ULong_t *) x); }
00448 inline void frombuf(char *&buf, Long64_t *x) { frombuf(buf, (ULong64_t *) x); }
00449 
00450 
00451 //______________________________________________________________________________
00452 #ifdef R__BYTESWAP
00453 inline UShort_t host2net(UShort_t x)
00454 {
00455 #if defined(R__USEASMSWAP)
00456    return Rbswap_16(x);
00457 #else
00458    return (((x & 0x00ff) << 8) | ((x & 0xff00) >> 8));
00459 #endif
00460 }
00461 
00462 inline UInt_t host2net(UInt_t x)
00463 {
00464 #if defined(R__USEASMSWAP)
00465    return Rbswap_32(x);
00466 #else
00467    return (((x & 0x000000ffU) << 24) | ((x & 0x0000ff00U) <<  8) |
00468            ((x & 0x00ff0000U) >>  8) | ((x & 0xff000000U) >> 24));
00469 #endif
00470 }
00471 
00472 inline ULong_t host2net(ULong_t x)
00473 {
00474 #ifdef R__B64
00475 # if defined(R__USEASMSWAP)
00476    return Rbswap_64(x);
00477 # else
00478    char sw[sizeof(ULong_t)];
00479    void *tmp = sw;
00480    *(ULong_t *)tmp = x;
00481 
00482    char *sb = (char *)&x;
00483    sb[0] = sw[7];
00484    sb[1] = sw[6];
00485    sb[2] = sw[5];
00486    sb[3] = sw[4];
00487    sb[4] = sw[3];
00488    sb[5] = sw[2];
00489    sb[6] = sw[1];
00490    sb[7] = sw[0];
00491    return x;
00492 # endif
00493 #else
00494    return (ULong_t)host2net((UInt_t) x);
00495 #endif
00496 }
00497 
00498 inline ULong64_t host2net(ULong64_t x)
00499 {
00500 #if defined(R__USEASMSWAP)
00501    return Rbswap_64(x);
00502 #else
00503    char sw[sizeof(ULong64_t)];
00504    void *tmp = sw;
00505    *(ULong64_t *)tmp = x;
00506 
00507    char *sb = (char *)&x;
00508    sb[0] = sw[7];
00509    sb[1] = sw[6];
00510    sb[2] = sw[5];
00511    sb[3] = sw[4];
00512    sb[4] = sw[3];
00513    sb[5] = sw[2];
00514    sb[6] = sw[1];
00515    sb[7] = sw[0];
00516    return x;
00517 #endif
00518 }
00519 
00520 inline Float_t host2net(Float_t xx)
00521 {
00522    // Use a union to allow strict-aliasing
00523    union {
00524       volatile UInt_t  i;
00525       volatile Float_t f;
00526    } u;
00527    u.f = xx;
00528 #if defined(R__USEASMSWAP)
00529    u.i = Rbswap_32(u.i);
00530 #else
00531    u.i = (((u.i & 0x000000ffU) << 24) | ((u.i & 0x0000ff00U) <<  8) |
00532           ((u.i & 0x00ff0000U) >>  8) | ((u.i & 0xff000000U) >> 24));
00533 #endif
00534    return u.f;
00535 }
00536 
00537 inline Double_t host2net(Double_t x)
00538 {
00539 #if defined(R__USEASMSWAP)
00540    // Use a union to allow strict-aliasing
00541    union {
00542       volatile ULong64_t l;
00543       volatile Double_t  d;
00544    } u;
00545    u.d = x;
00546    u.l = Rbswap_64(u.l);
00547    return u.d;
00548 # else
00549    char sw[sizeof(Double_t)];
00550    void *tmp = sw;
00551    *(Double_t *)tmp = x;
00552 
00553    char *sb = (char *)&x;
00554    sb[0] = sw[7];
00555    sb[1] = sw[6];
00556    sb[2] = sw[5];
00557    sb[3] = sw[4];
00558    sb[4] = sw[3];
00559    sb[5] = sw[2];
00560    sb[6] = sw[1];
00561    sb[7] = sw[0];
00562    return x;
00563 #endif
00564 }
00565 #else  /* R__BYTESWAP */
00566 inline UShort_t host2net(UShort_t x)   { return x; }
00567 inline UInt_t   host2net(UInt_t x)     { return x; }
00568 inline ULong_t  host2net(ULong_t x)    { return x; }
00569 inline ULong_t  host2net(ULong64_t x)  { return x; }
00570 inline Float_t  host2net(Float_t x)    { return x; }
00571 inline Double_t host2net(Double_t x)   { return x; }
00572 #endif
00573 
00574 inline Short_t  host2net(Short_t x)    { return host2net((UShort_t)x); }
00575 inline Int_t    host2net(Int_t x)      { return host2net((UInt_t)x); }
00576 inline Long_t   host2net(Long_t x)     { return host2net((ULong_t)x); }
00577 inline Long64_t host2net(Long64_t x)   { return host2net((ULong64_t)x); }
00578 
00579 inline UShort_t  net2host(UShort_t x)  { return host2net(x); }
00580 inline Short_t   net2host(Short_t x)   { return host2net(x); }
00581 inline UInt_t    net2host(UInt_t x)    { return host2net(x); }
00582 inline Int_t     net2host(Int_t x)     { return host2net(x); }
00583 inline ULong_t   net2host(ULong_t x)   { return host2net(x); }
00584 inline Long_t    net2host(Long_t x)    { return host2net(x); }
00585 inline ULong64_t net2host(ULong64_t x) { return host2net(x); }
00586 inline Long64_t  net2host(Long64_t x)  { return host2net(x); }
00587 inline Float_t   net2host(Float_t x)   { return host2net(x); }
00588 inline Double_t  net2host(Double_t x)  { return host2net(x); }
00589 
00590 #endif

Generated on Tue Jul 5 14:10:18 2011 for ROOT_528-00b_version by  doxygen 1.5.1