basic_binary_iprimitive.ipp 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. /////////1/////////2/////////3/////////4/////////5/////////6/////////7/////////8
  2. // basic_binary_iprimitive.ipp:
  3. // (C) Copyright 2002 Robert Ramey - http://www.rrsd.com .
  4. // Use, modification and distribution is subject to the Boost Software
  5. // License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
  6. // http://www.boost.org/LICENSE_1_0.txt)
  7. // See http://www.boost.org for updates, documentation, and revision history.
  8. #include <boost/assert.hpp>
  9. #include <cstddef> // size_t, NULL
  10. #include <cstring> // memcpy
  11. #include <boost/config.hpp>
  12. #if defined(BOOST_NO_STDC_NAMESPACE)
  13. namespace std{
  14. using ::size_t;
  15. using ::memcpy;
  16. } // namespace std
  17. #endif
  18. #include <boost/serialization/throw_exception.hpp>
  19. #include <boost/core/no_exceptions_support.hpp>
  20. #include <boost/archive/archive_exception.hpp>
  21. #include <boost/archive/basic_binary_iprimitive.hpp>
  22. namespace boost {
  23. namespace archive {
  24. //////////////////////////////////////////////////////////////////////
  25. // implementation of basic_binary_iprimitive
  26. template<class Archive, class Elem, class Tr>
  27. BOOST_ARCHIVE_OR_WARCHIVE_DECL void
  28. basic_binary_iprimitive<Archive, Elem, Tr>::init()
  29. {
  30. // Detect attempts to pass native binary archives across
  31. // incompatible platforms. This is not fool proof but its
  32. // better than nothing.
  33. unsigned char size;
  34. this->This()->load(size);
  35. if(sizeof(int) != size)
  36. boost::serialization::throw_exception(
  37. archive_exception(
  38. archive_exception::incompatible_native_format,
  39. "size of int"
  40. )
  41. );
  42. this->This()->load(size);
  43. if(sizeof(long) != size)
  44. boost::serialization::throw_exception(
  45. archive_exception(
  46. archive_exception::incompatible_native_format,
  47. "size of long"
  48. )
  49. );
  50. this->This()->load(size);
  51. if(sizeof(float) != size)
  52. boost::serialization::throw_exception(
  53. archive_exception(
  54. archive_exception::incompatible_native_format,
  55. "size of float"
  56. )
  57. );
  58. this->This()->load(size);
  59. if(sizeof(double) != size)
  60. boost::serialization::throw_exception(
  61. archive_exception(
  62. archive_exception::incompatible_native_format,
  63. "size of double"
  64. )
  65. );
  66. // for checking endian
  67. int i;
  68. this->This()->load(i);
  69. if(1 != i)
  70. boost::serialization::throw_exception(
  71. archive_exception(
  72. archive_exception::incompatible_native_format,
  73. "endian setting"
  74. )
  75. );
  76. }
  77. #ifndef BOOST_NO_CWCHAR
  78. #ifndef BOOST_NO_INTRINSIC_WCHAR_T
  79. template<class Archive, class Elem, class Tr>
  80. BOOST_ARCHIVE_OR_WARCHIVE_DECL void
  81. basic_binary_iprimitive<Archive, Elem, Tr>::load(wchar_t * ws)
  82. {
  83. std::size_t l; // number of wchar_t !!!
  84. this->This()->load(l);
  85. load_binary(ws, l * sizeof(wchar_t) / sizeof(char));
  86. ws[l] = L'\0';
  87. }
  88. #endif
  89. #endif
  90. template<class Archive, class Elem, class Tr>
  91. BOOST_ARCHIVE_OR_WARCHIVE_DECL void
  92. basic_binary_iprimitive<Archive, Elem, Tr>::load(std::string & s)
  93. {
  94. std::size_t l;
  95. this->This()->load(l);
  96. // borland de-allocator fixup
  97. #if BOOST_WORKAROUND(_RWSTD_VER, BOOST_TESTED_AT(20101))
  98. if(NULL != s.data())
  99. #endif
  100. s.resize(l);
  101. // note breaking a rule here - could be a problem on some platform
  102. if(0 < l)
  103. load_binary(&(*s.begin()), l);
  104. }
  105. template<class Archive, class Elem, class Tr>
  106. BOOST_ARCHIVE_OR_WARCHIVE_DECL void
  107. basic_binary_iprimitive<Archive, Elem, Tr>::load(char * s)
  108. {
  109. std::size_t l;
  110. this->This()->load(l);
  111. load_binary(s, l);
  112. s[l] = '\0';
  113. }
  114. #ifndef BOOST_NO_STD_WSTRING
  115. template<class Archive, class Elem, class Tr>
  116. BOOST_ARCHIVE_OR_WARCHIVE_DECL void
  117. basic_binary_iprimitive<Archive, Elem, Tr>::load(std::wstring & ws)
  118. {
  119. std::size_t l;
  120. this->This()->load(l);
  121. // borland de-allocator fixup
  122. #if BOOST_WORKAROUND(_RWSTD_VER, BOOST_TESTED_AT(20101))
  123. if(NULL != ws.data())
  124. #endif
  125. ws.resize(l);
  126. // note breaking a rule here - is could be a problem on some platform
  127. load_binary(const_cast<wchar_t *>(ws.data()), l * sizeof(wchar_t) / sizeof(char));
  128. }
  129. #endif
  130. template<class Archive, class Elem, class Tr>
  131. BOOST_ARCHIVE_OR_WARCHIVE_DECL
  132. basic_binary_iprimitive<Archive, Elem, Tr>::basic_binary_iprimitive(
  133. std::basic_streambuf<Elem, Tr> & sb,
  134. bool no_codecvt
  135. ) :
  136. #ifndef BOOST_NO_STD_LOCALE
  137. m_sb(sb),
  138. codecvt_null_facet(1),
  139. locale_saver(m_sb),
  140. archive_locale(sb.getloc(), & codecvt_null_facet)
  141. {
  142. if(! no_codecvt){
  143. m_sb.pubsync();
  144. m_sb.pubimbue(archive_locale);
  145. }
  146. }
  147. #else
  148. m_sb(sb)
  149. {}
  150. #endif
  151. // scoped_ptr requires that g be a complete type at time of
  152. // destruction so define destructor here rather than in the header
  153. template<class Archive, class Elem, class Tr>
  154. BOOST_ARCHIVE_OR_WARCHIVE_DECL
  155. basic_binary_iprimitive<Archive, Elem, Tr>::~basic_binary_iprimitive(){}
  156. } // namespace archive
  157. } // namespace boost