test_shared_ptr_132.cpp 6.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230
  1. /////////1/////////2/////////3/////////4/////////5/////////6/////////7/////////8
  2. // test_shared_ptr.cpp
  3. // (C) Copyright 2002 Robert Ramey- http://www.rrsd.com - David Tonge .
  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. //
  8. // See http://www.boost.org for updates, documentation, and revision history.
  9. #include <cstddef> // NULL
  10. #include <fstream>
  11. #include <cstdio> // remove
  12. #include <boost/config.hpp>
  13. #if defined(BOOST_NO_STDC_NAMESPACE)
  14. namespace std{
  15. using ::remove;
  16. }
  17. #endif
  18. #include "test_tools.hpp"
  19. #include <boost/serialization/shared_ptr_132.hpp>
  20. #include <boost/serialization/shared_ptr.hpp>
  21. #include <boost/serialization/weak_ptr.hpp>
  22. #include <boost/serialization/split_member.hpp>
  23. #include <boost/preprocessor/stringize.hpp>
  24. #include <boost/serialization/nvp.hpp>
  25. #include <boost/serialization/export.hpp>
  26. // This is a simple class. It contains a counter of the number
  27. // of objects of this class which have been instantiated.
  28. class A
  29. {
  30. private:
  31. friend class boost::serialization::access;
  32. int x;
  33. template<class Archive>
  34. void save(Archive & ar, const unsigned int /* file_version */) const {
  35. ar << BOOST_SERIALIZATION_NVP(x);
  36. }
  37. template<class Archive>
  38. void load(Archive & ar, const unsigned int /* file_version */) {
  39. ar >> BOOST_SERIALIZATION_NVP(x);
  40. }
  41. BOOST_SERIALIZATION_SPLIT_MEMBER()
  42. public:
  43. static int count;
  44. bool operator==(const A & rhs) const {
  45. return x == rhs.x;
  46. }
  47. A(){++count;} // default constructor
  48. virtual ~A(){--count;} // default destructor
  49. };
  50. BOOST_SERIALIZATION_SHARED_PTR(A)
  51. // B is a subclass of A
  52. class B : public A
  53. {
  54. private:
  55. friend class boost::serialization::access;
  56. template<class Archive>
  57. void save(Archive & ar, const unsigned int /* file_version */ )const {
  58. ar << BOOST_SERIALIZATION_BASE_OBJECT_NVP(A);
  59. }
  60. template<class Archive>
  61. void load(Archive & ar, const unsigned int /* file_version */){
  62. ar >> BOOST_SERIALIZATION_BASE_OBJECT_NVP(A);
  63. }
  64. BOOST_SERIALIZATION_SPLIT_MEMBER()
  65. public:
  66. static int count;
  67. B() : A() {};
  68. virtual ~B() {};
  69. };
  70. // B needs to be exported because its serialized via a base class pointer
  71. BOOST_SHARED_POINTER_EXPORT(B)
  72. BOOST_SERIALIZATION_SHARED_PTR(B)
  73. int A::count = 0;
  74. template<class T>
  75. void save(const char * testfile, const T & spa)
  76. {
  77. test_ostream os(testfile, TEST_STREAM_FLAGS);
  78. test_oarchive oa(os, TEST_ARCHIVE_FLAGS);
  79. oa << BOOST_SERIALIZATION_NVP(spa);
  80. }
  81. template<class T>
  82. void load(const char * testfile, T & spa)
  83. {
  84. test_istream is(testfile, TEST_STREAM_FLAGS);
  85. test_iarchive ia(is, TEST_ARCHIVE_FLAGS);
  86. ia >> BOOST_SERIALIZATION_NVP(spa);
  87. }
  88. // trivial test
  89. template<class T>
  90. void save_and_load(const T & spa)
  91. {
  92. const char * testfile = boost::archive::tmpnam(NULL);
  93. BOOST_REQUIRE(NULL != testfile);
  94. save(testfile, spa);
  95. // note that we're loading to a current version of shared_ptr
  96. // regardless of the orignal saved type - this tests backward
  97. // archive compatibility
  98. boost::shared_ptr<A> spa1;
  99. load(testfile, spa1);
  100. BOOST_CHECK(
  101. (spa.get() == NULL && spa1.get() == NULL)
  102. || * spa == * spa1
  103. );
  104. std::remove(testfile);
  105. }
  106. template<class T>
  107. void save2(
  108. const char * testfile,
  109. const T & first,
  110. const T & second
  111. ){
  112. test_ostream os(testfile, TEST_STREAM_FLAGS);
  113. test_oarchive oa(os, TEST_ARCHIVE_FLAGS);
  114. oa << BOOST_SERIALIZATION_NVP(first);
  115. oa << BOOST_SERIALIZATION_NVP(second);
  116. }
  117. template<class T>
  118. void load2(
  119. const char * testfile,
  120. T & first,
  121. T & second)
  122. {
  123. test_istream is(testfile, TEST_STREAM_FLAGS);
  124. test_iarchive ia(is, TEST_ARCHIVE_FLAGS);
  125. ia >> BOOST_SERIALIZATION_NVP(first);
  126. ia >> BOOST_SERIALIZATION_NVP(second);
  127. }
  128. // Run tests by serializing two shared_ptrs into an archive,
  129. // clearing them (deleting the objects) and then reloading the
  130. // objects back from an archive.
  131. template<class T>
  132. void save_and_load2(T & first, T & second)
  133. {
  134. const char * testfile = boost::archive::tmpnam(NULL);
  135. BOOST_REQUIRE(NULL != testfile);
  136. save2(testfile, first, second);
  137. // Clear the pointers, thereby destroying the objects they contain
  138. first.reset();
  139. second.reset();
  140. boost::shared_ptr<A> first1, second1;
  141. load2(testfile, first1, second1);
  142. BOOST_CHECK(first1 == second1);
  143. std::remove(testfile);
  144. }
  145. template<class T>
  146. void save3(
  147. const char * testfile,
  148. const T & first,
  149. const T & second,
  150. const T & third
  151. ){
  152. test_ostream os(testfile, TEST_STREAM_FLAGS);
  153. test_oarchive oa(os, TEST_ARCHIVE_FLAGS);
  154. oa << BOOST_SERIALIZATION_NVP(third);
  155. oa << BOOST_SERIALIZATION_NVP(first);
  156. oa << BOOST_SERIALIZATION_NVP(second);
  157. }
  158. template<class T>
  159. void load3(
  160. const char * testfile,
  161. T & first,
  162. T & second,
  163. T & third
  164. ){
  165. test_istream is(testfile, TEST_STREAM_FLAGS);
  166. test_iarchive ia(is, TEST_ARCHIVE_FLAGS);
  167. // note that we serialize the weak pointer first
  168. ia >> BOOST_SERIALIZATION_NVP(third);
  169. // inorder to test that a temporarily solitary weak pointer
  170. // correcttly restored.
  171. ia >> BOOST_SERIALIZATION_NVP(first);
  172. ia >> BOOST_SERIALIZATION_NVP(second);
  173. }
  174. // This does the tests
  175. int test_main(int /* argc */, char * /* argv */[])
  176. {
  177. // These are our shared_ptrs
  178. boost_132::shared_ptr<A> spa;
  179. // trivial test 1
  180. save_and_load(spa);
  181. //trivial test 2
  182. spa.reset();
  183. spa = boost_132::shared_ptr<A>(new A);
  184. save_and_load(spa);
  185. // Try to save and load pointers to As, to a text archive
  186. spa = boost_132::shared_ptr<A>(new A);
  187. boost_132::shared_ptr<A> spa1 = spa;
  188. save_and_load2(spa, spa1);
  189. // Try to save and load pointers to Bs, to a text archive
  190. spa = boost_132::shared_ptr<A>(new B);
  191. save_and_load(spa);
  192. spa1 = spa;
  193. save_and_load2(spa, spa1);
  194. // obj of type B gets destroyed
  195. // as smart_ptr goes out of scope
  196. return EXIT_SUCCESS;
  197. }