Teuchos Package Browser (Single Doxygen Collection) Version of the Day
Teuchos_SerializerHelpers.hpp
Go to the documentation of this file.
00001 // @HEADER
00002 // ***********************************************************************
00003 //
00004 //                    Teuchos: Common Tools Package
00005 //                 Copyright (2004) Sandia Corporation
00006 //
00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
00008 // license for use of this work by or on behalf of the U.S. Government.
00009 //
00010 // Redistribution and use in source and binary forms, with or without
00011 // modification, are permitted provided that the following conditions are
00012 // met:
00013 //
00014 // 1. Redistributions of source code must retain the above copyright
00015 // notice, this list of conditions and the following disclaimer.
00016 //
00017 // 2. Redistributions in binary form must reproduce the above copyright
00018 // notice, this list of conditions and the following disclaimer in the
00019 // documentation and/or other materials provided with the distribution.
00020 //
00021 // 3. Neither the name of the Corporation nor the names of the
00022 // contributors may be used to endorse or promote products derived from
00023 // this software without specific prior written permission.
00024 //
00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00036 //
00037 // Questions? Contact Michael A. Heroux (maherou@sandia.gov)
00038 //
00039 // ***********************************************************************
00040 // @HEADER
00041 
00042 #ifndef TEUCHOS_SERIALIZER_HELPERS_HPP
00043 #define TEUCHOS_SERIALIZER_HELPERS_HPP
00044 
00045 #include "Teuchos_Serializer.hpp"
00046 #include "Teuchos_Array.hpp"
00047 
00048 namespace Teuchos {
00049 
00053 template <typename Ordinal, typename T>
00054 class ReferenceTypeSerializationBuffer {
00055 public:
00057   ReferenceTypeSerializationBuffer(
00058     const Serializer<Ordinal,T> &serializer
00059     ,const Ordinal count, T*const buffer[]
00060     );
00064   ~ReferenceTypeSerializationBuffer();
00066   char* getCharBuffer() const;
00068   Ordinal getBytes() const;
00069 private:
00070   const Serializer<Ordinal,T>  &serializer_;
00071   Ordinal                      count_;
00072   T*const                      *buffer_;
00073   Array<char>                  charBuffer_;
00074   // Not defined and not to be called
00075   ReferenceTypeSerializationBuffer();
00076   ReferenceTypeSerializationBuffer(const ReferenceTypeSerializationBuffer&);
00077   ReferenceTypeSerializationBuffer& operator=(const ReferenceTypeSerializationBuffer&);
00078 };
00079 
00083 template <typename Ordinal, typename T>
00084 class ConstReferenceTypeSerializationBuffer {
00085 public:
00087   ConstReferenceTypeSerializationBuffer(
00088     const Serializer<Ordinal,T> &serializer
00089     ,const Ordinal count, const T*const buffer[]
00090     );
00094   ~ConstReferenceTypeSerializationBuffer();
00096   const char* getCharBuffer() const;
00098   Ordinal getBytes() const;
00099 private:
00100   const Serializer<Ordinal,T>  &serializer_;
00101   Ordinal                      count_;
00102   const T*const                *buffer_;
00103   Ordinal                      bytes_;
00104   Array<char>                  charBuffer_;
00105   // Not defined and not to be called
00106   ConstReferenceTypeSerializationBuffer();
00107   ConstReferenceTypeSerializationBuffer(const ConstReferenceTypeSerializationBuffer&);
00108   ConstReferenceTypeSerializationBuffer& operator=(const ConstReferenceTypeSerializationBuffer&);
00109 };
00110 
00115 template <typename Ordinal, typename T>
00116 class ReferenceTypeDeserializationBuffer {
00117 public:
00119   ReferenceTypeDeserializationBuffer(
00120     const Serializer<Ordinal,T> &serializer
00121     ,const Ordinal bytes, char charBuffer[]
00122     );
00126   ~ReferenceTypeDeserializationBuffer();
00128   T*const* getBuffer() const;
00130   Ordinal getCount() const;
00131 private:
00132   typedef Array<RCP<T> >  buffer_ptr_t;
00133   typedef Array<T*>               buffer_t;
00134   const Serializer<Ordinal,T>  &serializer_;
00135   Ordinal                      bytes_;
00136   char                         *charBuffer_;
00137   buffer_ptr_t                 buffer_ptr_;
00138   buffer_t                     buffer_;
00139   // Not defined and not to be called
00140   ReferenceTypeDeserializationBuffer();
00141   ReferenceTypeDeserializationBuffer(const ReferenceTypeDeserializationBuffer&);
00142   ReferenceTypeDeserializationBuffer& operator=(const ReferenceTypeDeserializationBuffer&);
00143 };
00144 
00149 template <typename Ordinal, typename T>
00150 class ConstReferenceTypeDeserializationBuffer {
00151 public:
00153   ConstReferenceTypeDeserializationBuffer(
00154     const Serializer<Ordinal,T> &serializer
00155     ,const Ordinal bytes, const char charBuffer[]
00156     );
00160   ~ConstReferenceTypeDeserializationBuffer();
00162   const T*const* getBuffer() const;
00164   Ordinal getCount() const;
00165 private:
00166   typedef Array<RCP<T> >  buffer_ptr_t;
00167   typedef Array<T*>               buffer_t;
00168   const Serializer<Ordinal,T>  &serializer_;
00169   Ordinal                      bytes_;
00170   const char                   *charBuffer_;
00171   buffer_ptr_t                 buffer_ptr_;
00172   buffer_t                     buffer_;
00173   // Not defined and not to be called
00174   ConstReferenceTypeDeserializationBuffer();
00175   ConstReferenceTypeDeserializationBuffer(const ConstReferenceTypeDeserializationBuffer&);
00176   ConstReferenceTypeDeserializationBuffer& operator=(const ConstReferenceTypeDeserializationBuffer&);
00177 };
00178 
00179 // /////////////////////////////////////
00180 // Template implementations
00181 
00182 //
00183 // ReferenceTypeSerializationBuffer
00184 //
00185 
00186 template <typename Ordinal, typename T>
00187 ReferenceTypeSerializationBuffer<Ordinal,T>::ReferenceTypeSerializationBuffer(
00188   const Serializer<Ordinal,T> &serializer
00189   ,const Ordinal count, T*const buffer[]
00190   )
00191   :serializer_(serializer), count_(count), buffer_(buffer)
00192 {
00193   const Ordinal bytes = serializer_.getBufferSize(count_);
00194   charBuffer_.resize(bytes);
00195   serializer_.serialize(count_,buffer_,bytes,&charBuffer_[0]);
00196 }
00197 
00198 template <typename Ordinal, typename T>
00199 ReferenceTypeSerializationBuffer<Ordinal,T>::~ReferenceTypeSerializationBuffer()
00200 {
00201   serializer_.deserialize(charBuffer_.size(),&charBuffer_[0],count_,buffer_);
00202 }
00203 
00204 template <typename Ordinal, typename T>
00205 char* ReferenceTypeSerializationBuffer<Ordinal,T>::getCharBuffer() const
00206 {
00207   typedef ReferenceTypeSerializationBuffer<Ordinal,T>* this_ptr_t;
00208   return &(const_cast<this_ptr_t>(this)->charBuffer_)[0];
00209   // The above const_cast is a better alternative to declaring charBuffer_ to
00210   // be mutable, in my opinion.
00211 }
00212 
00213 template <typename Ordinal, typename T>
00214 Ordinal ReferenceTypeSerializationBuffer<Ordinal,T>::getBytes() const
00215 {
00216   return charBuffer_.size();
00217 }
00218 
00219 //
00220 // ConstReferenceTypeSerializationBuffer
00221 //
00222 
00223 template <typename Ordinal, typename T>
00224 ConstReferenceTypeSerializationBuffer<Ordinal,T>::ConstReferenceTypeSerializationBuffer(
00225   const Serializer<Ordinal,T> &serializer
00226   ,const Ordinal count, const T*const buffer[]
00227   )
00228   :serializer_(serializer), count_(count), buffer_(buffer)
00229 {
00230   const Ordinal bytes = serializer_.getBufferSize(count_);
00231   charBuffer_.resize(bytes);
00232   serializer_.serialize(count_,buffer_,bytes,&charBuffer_[0]);
00233 }
00234 
00235 template <typename Ordinal, typename T>
00236 ConstReferenceTypeSerializationBuffer<Ordinal,T>::~ConstReferenceTypeSerializationBuffer()
00237 {
00238   // No need to copy back from the char[] buffer!
00239 }
00240 
00241 template <typename Ordinal, typename T>
00242 const char* ConstReferenceTypeSerializationBuffer<Ordinal,T>::getCharBuffer() const
00243 {
00244   return &charBuffer_[0];
00245 }
00246 
00247 template <typename Ordinal, typename T>
00248 Ordinal ConstReferenceTypeSerializationBuffer<Ordinal,T>::getBytes() const
00249 {
00250   return charBuffer_.size();
00251 }
00252 
00253 //
00254 // ReferenceTypeDeserializationBuffer
00255 //
00256 
00257 template <typename Ordinal, typename T>
00258 ReferenceTypeDeserializationBuffer<Ordinal,T>::ReferenceTypeDeserializationBuffer(
00259   const Serializer<Ordinal,T> &serializer
00260   ,const Ordinal bytes, char charBuffer[]
00261   )
00262   :serializer_(serializer),bytes_(bytes),charBuffer_(charBuffer)
00263 {
00264   const Ordinal extent = serializer_.getBufferSize(1);
00265   const Ordinal count = bytes_ / extent;
00266 #ifdef TEUCHOS_DEBUG
00267   TEST_FOR_EXCEPT( !( bytes_ % extent == 0 ) );
00268 #endif
00269   buffer_ptr_.resize(count);
00270   buffer_.resize(count);
00271   for( int i = 0; i < count; ++i ) {
00272     buffer_ptr_[i] = serializer_.createObj();
00273     buffer_[i] = &*buffer_ptr_[i];
00274   }
00275   serializer_.deserialize(
00276     bytes_,charBuffer_,count,&buffer_[0]
00277     );
00278 }
00279 
00280 template <typename Ordinal, typename T>
00281 ReferenceTypeDeserializationBuffer<Ordinal,T>::~ReferenceTypeDeserializationBuffer()
00282 {
00283   serializer_.serialize(
00284     buffer_.size(),&buffer_[0],bytes_,charBuffer_
00285     );
00286 }
00287 
00288 template <typename Ordinal, typename T>
00289 T*const* ReferenceTypeDeserializationBuffer<Ordinal,T>::getBuffer() const
00290 {
00291   typedef ReferenceTypeDeserializationBuffer<Ordinal,T>* this_ptr_t;
00292   return &(const_cast<this_ptr_t>(this)->buffer_)[0];
00293   // The above const_cast is a better alternative to declaring buffer_ to be
00294   // mutable, in my opinion.
00295 }
00296 
00297 template <typename Ordinal, typename T>
00298 Ordinal ReferenceTypeDeserializationBuffer<Ordinal,T>::getCount() const
00299 {
00300   return buffer_.size();
00301 }
00302 
00303 //
00304 // ConstReferenceTypeDeserializationBuffer
00305 //
00306 
00307 template <typename Ordinal, typename T>
00308 ConstReferenceTypeDeserializationBuffer<Ordinal,T>::ConstReferenceTypeDeserializationBuffer(
00309   const Serializer<Ordinal,T> &serializer
00310   ,const Ordinal bytes, const char charBuffer[]
00311   )
00312   :serializer_(serializer),bytes_(bytes),charBuffer_(charBuffer)
00313 {
00314   const Ordinal extent = serializer_.getBufferSize(1);
00315   const Ordinal count = bytes_ / extent;
00316 #ifdef TEUCHOS_DEBUG
00317   TEST_FOR_EXCEPT( !( bytes_ % extent == 0 ) );
00318 #endif
00319   buffer_ptr_.resize(count);
00320   buffer_.resize(count);
00321   for( int i = 0; i < count; ++i ) {
00322     buffer_ptr_[i] = serializer_.createObj();
00323     buffer_[i] = &*buffer_ptr_[i];
00324   }
00325   serializer_.deserialize(
00326     bytes_,charBuffer_,count,&buffer_[0]
00327     );
00328 }
00329 
00330 template <typename Ordinal, typename T>
00331 ConstReferenceTypeDeserializationBuffer<Ordinal,T>::~ConstReferenceTypeDeserializationBuffer()
00332 {
00333   // We don't need to serialized back into charBuffer_[] since it is constant!
00334 }
00335 
00336 template <typename Ordinal, typename T>
00337 const T*const* ConstReferenceTypeDeserializationBuffer<Ordinal,T>::getBuffer() const
00338 {
00339   return &buffer_[0];
00340 }
00341 
00342 template <typename Ordinal, typename T>
00343 Ordinal ConstReferenceTypeDeserializationBuffer<Ordinal,T>::getCount() const
00344 {
00345   return buffer_.size();
00346 }
00347 
00348 } // namespace Teuchos
00349 
00350 #endif // TEUCHOS_SERIALIZER_HELPERS_HPP
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines