CLHEP VERSION Reference Documentation
   
CLHEP Home Page     CLHEP Documentation     CLHEP Bug Reports

DoubConv.cc

Go to the documentation of this file.
00001 #include "CLHEP/Random/DoubConv.hh"
00002 
00003 #include <sstream>
00004 #include <iomanip>
00005 
00006 namespace CLHEP {
00007 
00008 bool DoubConv::byte_order_known = false;
00009 int  DoubConv::byte_order[8];
00010 
00011 void DoubConv::fill_byte_order () {
00012   double x = 1.0;
00013   int t30 = 1 << 30;
00014   int t22 = 1 << 22;
00015   x *= t30;
00016   x *= t22;
00017   double y = 1;
00018   double z = 1;
00019   x *= z;
00020   for (int k=0; k<6; k++) {
00021     x += y*z;
00022     y += 1;
00023     z *= 256;
00024   }
00025   // x, in IEEE format, would now be 0x4330060504030201
00026   union DB8 {
00027     unsigned char b[8];
00028     double d;
00029   };
00030   DB8 xb;
00031   xb.d = x;
00032   int n;
00033   static const int UNSET = -1; 
00034   for (n=0; n<8; n++) {
00035     byte_order[n] = UNSET;
00036   }
00037   int order;
00038   for (n=0; n<8; n++) {
00039     switch ( xb.b[n] ) {
00040       case 0x43:
00041         order = 0;
00042         break;
00043       case 0x30:
00044         order = 1;
00045         break;
00046       case 0x06:
00047         order = 2;
00048         break;
00049       case 0x05:
00050         order = 3;
00051         break;
00052       case 0x04:
00053         order = 4;
00054         break;
00055       case 0x03:
00056         order = 5;
00057         break;
00058       case 0x02:
00059         order = 6;
00060         break;
00061       case 0x01:
00062         order = 7;
00063         break;
00064       default:
00065         throw DoubConvException(
00066                 "Cannot determine byte-ordering of doubles on this system");
00067     } 
00068     if (byte_order[n] != UNSET) {
00069         throw DoubConvException(
00070                 "Confusion in byte-ordering of doubles on this system");
00071     }    
00072     byte_order[n] = order;
00073     byte_order_known = true;
00074   }
00075   return;
00076 }
00077 
00078 std::string DoubConv::d2x(double d) {
00079   if ( !byte_order_known ) fill_byte_order ();
00080   DB8 db;
00081   db.d = d;
00082   std::ostringstream ss;
00083   for (int i=0; i<8; ++i) {
00084     int k = byte_order[i];
00085     ss << std::hex << std::setw(2) << std::setfill('0') << (int)db.b[k];
00086   }
00087   return ss.str();
00088 }
00089 
00090 std::vector<unsigned long> DoubConv::dto2longs(double d) {
00091   std::vector<unsigned long> v(2);
00092   if ( !byte_order_known ) fill_byte_order ();
00093   DB8 db;
00094   db.d = d;
00095   v[0] =   ((static_cast<unsigned long>(db.b[byte_order[0]])) << 24)
00096          | ((static_cast<unsigned long>(db.b[byte_order[1]])) << 16)
00097          | ((static_cast<unsigned long>(db.b[byte_order[2]])) <<  8)
00098          | ((static_cast<unsigned long>(db.b[byte_order[3]]))      );
00099   v[1] =   ((static_cast<unsigned long>(db.b[byte_order[4]])) << 24)
00100          | ((static_cast<unsigned long>(db.b[byte_order[5]])) << 16)
00101          | ((static_cast<unsigned long>(db.b[byte_order[6]])) <<  8)
00102          | ((static_cast<unsigned long>(db.b[byte_order[7]]))      );
00103   return v; 
00104 }
00105 
00106 double DoubConv::longs2double (const std::vector<unsigned long> & v) {
00107   DB8 db;
00108   unsigned char bytes[8];
00109   if ( !byte_order_known ) fill_byte_order ();
00110   bytes[0] = static_cast<unsigned char>((v[0] >> 24) & 0xFF);
00111   bytes[1] = static_cast<unsigned char>((v[0] >> 16) & 0xFF);
00112   bytes[2] = static_cast<unsigned char>((v[0] >>  8) & 0xFF);
00113   bytes[3] = static_cast<unsigned char>((v[0]      ) & 0xFF);
00114   bytes[4] = static_cast<unsigned char>((v[1] >> 24) & 0xFF);
00115   bytes[5] = static_cast<unsigned char>((v[1] >> 16) & 0xFF);
00116   bytes[6] = static_cast<unsigned char>((v[1] >>  8) & 0xFF);
00117   bytes[7] = static_cast<unsigned char>((v[1]      ) & 0xFF);
00118   for (int i=0; i<8; ++i) {
00119     db.b[byte_order[i]] =  bytes[i];
00120   }  
00121   return db.d;
00122 }
00123 
00124 } // end namespace HepMC

Generated on 15 Nov 2012 for CLHEP by  doxygen 1.4.7