core/vil/io/vil_io_memory_chunk.cxx
Go to the documentation of this file.
00001 // This is core/vil/io/vil_io_memory_chunk.cxx
00002 #include "vil_io_memory_chunk.h"
00003 //:
00004 // \file
00005 // \author Tim Cootes
00006 // \verbatim
00007 //  Modifications
00008 //   Feb.2003 - Ian Scott - Upgraded IO to use vsl_block_binary io
00009 //   23 Oct.2003 - Peter Vanroose - Added support for 64-bit int pixels
00010 // \endverbatim
00011 
00012 #include <vsl/vsl_block_binary.h>
00013 #include <vsl/vsl_complex_io.h>
00014 
00015 #define write_case_macro(T)\
00016 vsl_b_write(os,unsigned(chunk.size()/sizeof(T ))); \
00017 vsl_block_binary_write(os,(const T*) chunk.const_data(),chunk.size()/sizeof(T))
00018 
00019 
00020 //: Binary save vil_memory_chunk to stream.
00021 void vsl_b_write(vsl_b_ostream &os, const vil_memory_chunk& chunk)
00022 {
00023   const short io_version_no = 3;
00024   vsl_b_write(os, io_version_no);
00025   vsl_b_write(os, int(chunk.pixel_format()));
00026 
00027   switch (vil_pixel_format_component_format(chunk.pixel_format()))
00028   {
00029 #if VXL_HAS_INT_64
00030     case VIL_PIXEL_FORMAT_UINT_64:
00031       write_case_macro(vxl_uint_64);
00032       break;
00033     case VIL_PIXEL_FORMAT_INT_64:
00034       write_case_macro(vxl_int_64);
00035       break;
00036 #endif
00037     case VIL_PIXEL_FORMAT_UINT_32:
00038       write_case_macro(vxl_uint_32);
00039       break;
00040     case VIL_PIXEL_FORMAT_INT_32:
00041       write_case_macro(vxl_int_32);
00042       break;
00043     case VIL_PIXEL_FORMAT_UINT_16:
00044       write_case_macro(vxl_uint_16);
00045       break;
00046     case VIL_PIXEL_FORMAT_INT_16:
00047       write_case_macro(vxl_int_16);
00048       break;
00049     case VIL_PIXEL_FORMAT_BYTE:
00050       write_case_macro(vxl_byte);
00051       break;
00052     case VIL_PIXEL_FORMAT_SBYTE:
00053       write_case_macro(vxl_sbyte);
00054       break;
00055     case VIL_PIXEL_FORMAT_FLOAT:
00056       write_case_macro(float);
00057       break;
00058     case VIL_PIXEL_FORMAT_DOUBLE:
00059       write_case_macro(double);
00060       break;
00061     case VIL_PIXEL_FORMAT_BOOL:
00062       write_case_macro(bool);
00063       break;
00064     case VIL_PIXEL_FORMAT_COMPLEX_FLOAT:
00065       write_case_macro(vcl_complex<float>);
00066       break;
00067     case VIL_PIXEL_FORMAT_COMPLEX_DOUBLE:
00068       write_case_macro(vcl_complex<double>);
00069       break;
00070     default:
00071       vcl_cerr << "I/O ERROR: vsl_b_write(vsl_b_istream&, vil_memory_chunk&)\n"
00072                << "           Unknown component type\n";
00073       return;
00074   }
00075 }
00076 
00077 #undef write_case_macro
00078 
00079 
00080 // This file never uses the fast versions of vsl_b_read_block, so just locally
00081 //implement the old slow version.
00082 #define read_case_macro_v1(T)\
00083 chunk.set_size(n*sizeof(T ),pixel_format); \
00084   for (unsigned i=0; i<n; ++i)\
00085     vsl_b_read(is, static_cast<T *>(chunk.data())[i]);
00086 
00087 #define read_case_macro_v2(T)\
00088 chunk.set_size(n*sizeof(T ),pixel_format); \
00089 vsl_block_binary_read_confirm_specialisation(is, false); \
00090   for (unsigned i=0; i<n; ++i)\
00091     vsl_b_read(is, static_cast<T *>(chunk.data())[i]);
00092 
00093 #define read_case_macro_v3(T)\
00094 chunk.set_size(n*sizeof(T ),pixel_format); \
00095 vsl_block_binary_read(is,static_cast<T *>(chunk.data()),n)
00096 
00097 
00098 //: Binary load vil_memory_chunk from stream.
00099 void vsl_b_read(vsl_b_istream &is, vil_memory_chunk& chunk)
00100 {
00101   if (!is) return;
00102 
00103   short w;
00104   vsl_b_read(is, w);
00105   int format;
00106   vil_pixel_format pixel_format;
00107   unsigned n;
00108   switch (w)
00109   {
00110    case 1:
00111     vsl_b_read(is, format); pixel_format=vil_pixel_format(format);
00112     vsl_b_read(is, n);
00113     switch (pixel_format)
00114     {
00115 #if VXL_HAS_INT_64
00116      case VIL_PIXEL_FORMAT_UINT_64:
00117       read_case_macro_v1(vxl_uint_64);
00118       break;
00119      case VIL_PIXEL_FORMAT_INT_64:
00120       read_case_macro_v1(vxl_int_64);
00121       break;
00122 #endif
00123      case VIL_PIXEL_FORMAT_UINT_32:
00124       read_case_macro_v1(vxl_uint_32);
00125       break;
00126      case VIL_PIXEL_FORMAT_INT_32:
00127       read_case_macro_v1(vxl_int_32);
00128       break;
00129      case VIL_PIXEL_FORMAT_UINT_16:
00130       read_case_macro_v1(vxl_uint_16);
00131       break;
00132      case VIL_PIXEL_FORMAT_INT_16:
00133       read_case_macro_v1(vxl_int_16);
00134       break;
00135      case VIL_PIXEL_FORMAT_BYTE:
00136       read_case_macro_v1(vxl_byte);
00137       break;
00138      case VIL_PIXEL_FORMAT_SBYTE:
00139       read_case_macro_v1(vxl_sbyte);
00140       break;
00141      case VIL_PIXEL_FORMAT_FLOAT:
00142       read_case_macro_v1(float);
00143       break;
00144      case VIL_PIXEL_FORMAT_DOUBLE:
00145       read_case_macro_v1(double);
00146       break;
00147      case VIL_PIXEL_FORMAT_BOOL:
00148       read_case_macro_v1(bool);
00149       break;
00150      // No version 1 complex images were ever written.
00151      default:
00152       vcl_cerr << "I/O ERROR: vsl_b_read(vsl_b_istream&, vil_memory_chunk&)\n"
00153                << "           Unknown pixel format "<< format << '\n';
00154       is.is().clear(vcl_ios::badbit); // Set an unrecoverable IO error on stream
00155       return;
00156     }
00157     break;
00158 
00159    case 2:
00160     vsl_b_read(is, format); pixel_format=vil_pixel_format(format);
00161     vsl_b_read(is, n);
00162     switch (pixel_format)
00163     {
00164 #if VXL_HAS_INT_64
00165      case VIL_PIXEL_FORMAT_UINT_64:
00166       read_case_macro_v3(vxl_uint_64);
00167       break;
00168      case VIL_PIXEL_FORMAT_INT_64:
00169       read_case_macro_v3(vxl_int_64);
00170       break;
00171 #endif
00172      case VIL_PIXEL_FORMAT_UINT_32:
00173       read_case_macro_v3(vxl_uint_32);
00174       break;
00175      case VIL_PIXEL_FORMAT_INT_32:
00176       read_case_macro_v3(vxl_int_32);
00177       break;
00178      case VIL_PIXEL_FORMAT_UINT_16:
00179       read_case_macro_v3(vxl_uint_16);
00180       break;
00181      case VIL_PIXEL_FORMAT_INT_16:
00182       read_case_macro_v3(vxl_int_16);
00183       break;
00184      case VIL_PIXEL_FORMAT_BYTE:
00185       read_case_macro_v2(vxl_byte);
00186       break;
00187      case VIL_PIXEL_FORMAT_SBYTE:
00188       read_case_macro_v2(vxl_sbyte);
00189       break;
00190      case VIL_PIXEL_FORMAT_FLOAT:
00191       read_case_macro_v3(float);
00192       break;
00193      case VIL_PIXEL_FORMAT_DOUBLE:
00194       read_case_macro_v3(double);
00195       break;
00196      case VIL_PIXEL_FORMAT_BOOL:
00197       read_case_macro_v3(bool);
00198       break;
00199      case VIL_PIXEL_FORMAT_COMPLEX_FLOAT:
00200       read_case_macro_v3(vcl_complex<float>);
00201       break;
00202      case VIL_PIXEL_FORMAT_COMPLEX_DOUBLE:
00203       read_case_macro_v3(vcl_complex<double>);
00204       break;
00205      default:
00206       vcl_cerr << "I/O ERROR: vsl_b_read(vsl_b_istream&, vil_memory_chunk&)\n"
00207                << "           Unknown pixel format "<< format << '\n';
00208        is.is().clear(vcl_ios::badbit); // Set an unrecoverable IO error on stream
00209       return;
00210     }
00211     break;
00212 
00213    case 3:
00214     vsl_b_read(is, format); pixel_format=vil_pixel_format(format);
00215     vsl_b_read(is, n);
00216     switch (pixel_format)
00217     {
00218 #if VXL_HAS_INT_64
00219      case VIL_PIXEL_FORMAT_UINT_64:
00220       read_case_macro_v3(vxl_uint_64);
00221       break;
00222      case VIL_PIXEL_FORMAT_INT_64:
00223       read_case_macro_v3(vxl_int_64);
00224       break;
00225 #endif
00226      case VIL_PIXEL_FORMAT_UINT_32:
00227       read_case_macro_v3(vxl_uint_32);
00228       break;
00229      case VIL_PIXEL_FORMAT_INT_32:
00230       read_case_macro_v3(vxl_int_32);
00231       break;
00232      case VIL_PIXEL_FORMAT_UINT_16:
00233       read_case_macro_v3(vxl_uint_16);
00234       break;
00235      case VIL_PIXEL_FORMAT_INT_16:
00236       read_case_macro_v3(vxl_int_16);
00237       break;
00238      case VIL_PIXEL_FORMAT_BYTE:
00239       read_case_macro_v3(vxl_byte);
00240       break;
00241      case VIL_PIXEL_FORMAT_SBYTE:
00242       read_case_macro_v3(vxl_sbyte);
00243       break;
00244      case VIL_PIXEL_FORMAT_FLOAT:
00245       read_case_macro_v3(float);
00246       break;
00247      case VIL_PIXEL_FORMAT_DOUBLE:
00248       read_case_macro_v3(double);
00249       break;
00250      case VIL_PIXEL_FORMAT_BOOL:
00251       read_case_macro_v3(bool);
00252       break;
00253      case VIL_PIXEL_FORMAT_COMPLEX_FLOAT:
00254       read_case_macro_v3(vcl_complex<float>);
00255       break;
00256      case VIL_PIXEL_FORMAT_COMPLEX_DOUBLE:
00257       read_case_macro_v3(vcl_complex<double>);
00258       break;
00259      default:
00260       vcl_cerr << "I/O ERROR: vsl_b_read(vsl_b_istream&, vil_memory_chunk&)\n"
00261                << "           Unknown pixel format "<< format << '\n';
00262        is.is().clear(vcl_ios::badbit); // Set an unrecoverable IO error on stream
00263       return;
00264     }
00265     break;
00266 
00267    default:
00268     vcl_cerr << "I/O ERROR: vsl_b_read(vsl_b_istream&, vil_memory_chunk&)\n"
00269              << "           Unknown version number "<< w << '\n';
00270     is.is().clear(vcl_ios::badbit); // Set an unrecoverable IO error on stream
00271     return;
00272   }
00273 }
00274 
00275 #undef read_case_macro
00276 
00277 //: Binary save vil_memory_chunk to stream  by pointer
00278 void vsl_b_write(vsl_b_ostream &os, const vil_memory_chunk* chunk_ptr)
00279 {
00280   bool not_null_ptr = (chunk_ptr!=0);
00281   vsl_b_write(os,not_null_ptr);
00282   if (not_null_ptr)
00283     vsl_b_write(os,*chunk_ptr);
00284 }
00285 
00286 //: Binary load vil_memory_chunk from stream  onto the heap
00287 void vsl_b_read(vsl_b_istream &is, vil_memory_chunk*& p)
00288 {
00289   delete p;
00290   bool not_null_ptr;
00291   vsl_b_read(is, not_null_ptr);
00292   if (not_null_ptr)
00293   {
00294     p = new vil_memory_chunk();
00295     vsl_b_read(is, *p);
00296   }
00297   else
00298     p = 0;
00299 }
00300 
00301 //: Print human readable summary of a vil_memory_chunk object to a stream
00302 void vsl_print_summary(vcl_ostream& os,const vil_memory_chunk& chunk)
00303 {
00304   os<<"vil_memory_chunk containing "<<chunk.size()<<" bytes of "<<chunk.pixel_format();
00305 }