]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/libs/serialization/test/test_cyclic_ptrs.cpp
update sources to v12.2.3
[ceph.git] / ceph / src / boost / libs / serialization / test / test_cyclic_ptrs.cpp
1 /////////1/////////2/////////3/////////4/////////5/////////6/////////7/////////8
2 // test_cyclic_ptrs.cpp
3
4 // (C) Copyright 2002 Robert Ramey - http://www.rrsd.com .
5 // Use, modification and distribution is subject to the Boost Software
6 // License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
7 // http://www.boost.org/LICENSE_1_0.txt)
8
9 // should pass compilation and execution
10
11 #include <cstddef> // NULL
12 #include <fstream>
13
14 #include <cstdio> // remove
15 #include <boost/config.hpp>
16 #if defined(BOOST_NO_STDC_NAMESPACE)
17 namespace std{
18 using ::remove;
19 }
20 #endif
21
22 #include "test_tools.hpp"
23 #include <boost/core/no_exceptions_support.hpp>
24
25 #include <boost/serialization/nvp.hpp>
26 #include <boost/serialization/version.hpp>
27 #include <boost/serialization/base_object.hpp>
28
29 #include "A.hpp"
30 #include "A.ipp"
31
32 ///////////////////////////////////////////////////////
33 // class with a member which refers to itself
34 class J : public A
35 {
36 private:
37 friend class boost::serialization::access;
38 template<class Archive>
39 void serialize(Archive &ar, const unsigned int /* file_version */){
40 ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(A);
41 ar & BOOST_SERIALIZATION_NVP(j);
42 }
43 public:
44 bool operator==(const J &rhs) const;
45 J *j;
46 J(J *_j) : j(_j) {}
47 J() : j(NULL){}
48 };
49
50 BOOST_CLASS_VERSION(J, 6)
51
52 bool J::operator==(const J &rhs) const
53 {
54 return static_cast<const A &>(*this) == static_cast<const A &>(rhs);
55 }
56
57 ///////////////////////////////////////////////////////
58 // class with members that refer to each other
59 // this is an example of a class that, as written, cannot
60 // be serialized with this system. The problem is that the
61 // serialization of the first member - j1 , provokes serialization
62 // of those objects which it points to either directly or indirectly.
63 // When those objects are subsequently serialized, it is discovered
64 // that have already been serialized through pointers. This is
65 // detected by the system and an exception - pointer_conflict -
66 // is thrown. Permiting this to go undetected would result in the
67 // creation of multiple equal objects rather than the original
68 // structure.
69 class K
70 {
71 J j1;
72 J j2;
73 J j3;
74 friend class boost::serialization::access;
75 template<class Archive>
76 void serialize(
77 Archive &ar,
78 const unsigned int /* file_version */
79 ){
80 ar & BOOST_SERIALIZATION_NVP(j1);
81 ar & BOOST_SERIALIZATION_NVP(j2);
82 ar & BOOST_SERIALIZATION_NVP(j3);
83 }
84 public:
85 bool operator==(const K &rhs) const;
86 K();
87 };
88
89 K::K()
90 : j1(&j2), j2(&j3), j3(&j1)
91 {
92 }
93
94 bool K::operator==(const K &rhs) const
95 {
96 return
97 j1.j == & j2
98 && j2.j == & j3
99 && j3.j == & j1
100 && j1 == rhs.j1
101 && j2 == rhs.j2
102 && j3 == rhs.j3
103 ;
104 }
105
106 int test1(){
107 const char * testfile = boost::archive::tmpnam(NULL);
108 BOOST_REQUIRE(NULL != testfile);
109
110 J j1, j2;
111 {
112 test_ostream os(testfile, TEST_STREAM_FLAGS);
113 test_oarchive oa(os, TEST_ARCHIVE_FLAGS);
114 oa << BOOST_SERIALIZATION_NVP(j1);
115 }
116 {
117 // try to read the archive
118 test_istream is(testfile, TEST_STREAM_FLAGS);
119 test_iarchive ia(is, TEST_ARCHIVE_FLAGS);
120 ia >> BOOST_SERIALIZATION_NVP(j2);
121 }
122 BOOST_CHECK(j1 == j2);
123 std::remove(testfile);
124 return EXIT_SUCCESS;
125 }
126
127 int test2(){
128 const char * testfile = boost::archive::tmpnam(NULL);
129 BOOST_REQUIRE(NULL != testfile);
130
131 J *j1 = new J;
132 j1->j = j1;
133 J *j2 = reinterpret_cast<J *>(0xBAADF00D);
134 {
135 test_ostream os(testfile, TEST_STREAM_FLAGS);
136 test_oarchive oa(os, TEST_ARCHIVE_FLAGS);
137 oa << BOOST_SERIALIZATION_NVP(j1);
138 }
139 {
140 // try to read the archive
141 test_istream is(testfile, TEST_STREAM_FLAGS);
142 test_iarchive ia(is, TEST_ARCHIVE_FLAGS);
143 ia >> BOOST_SERIALIZATION_NVP(j2);
144 }
145 BOOST_CHECK(*j1 == *j2);
146 delete j1;
147 BOOST_CHECK(j2 == j2->j);
148 std::remove(testfile);
149 return EXIT_SUCCESS;
150 }
151
152 int test3(){
153 const char * testfile = boost::archive::tmpnam(NULL);
154 BOOST_REQUIRE(NULL != testfile);
155
156 K k;
157 boost::archive::archive_exception exception(
158 boost::archive::archive_exception::no_exception
159 );
160 {
161 test_ostream os(testfile, TEST_STREAM_FLAGS);
162 test_oarchive oa(os, TEST_ARCHIVE_FLAGS);
163 BOOST_TRY {
164 oa << BOOST_SERIALIZATION_NVP(k);
165 }
166 BOOST_CATCH (boost::archive::archive_exception ae){
167 exception = ae;
168 }
169 BOOST_CATCH_END
170 BOOST_CHECK(
171 exception.code == boost::archive::archive_exception::pointer_conflict
172 );
173 }
174 // if exception wasn't invoked
175 if(exception.code == boost::archive::archive_exception::no_exception){
176 // try to read the archive
177 test_istream is(testfile, TEST_STREAM_FLAGS);
178 test_iarchive ia(is, TEST_ARCHIVE_FLAGS);
179 exception = boost::archive::archive_exception(
180 boost::archive::archive_exception::no_exception
181 );
182 BOOST_TRY {
183 ia >> BOOST_SERIALIZATION_NVP(k);
184 }
185 BOOST_CATCH (boost::archive::archive_exception ae){
186 exception = ae;
187 }
188 BOOST_CATCH_END
189 BOOST_CHECK(
190 exception.code == boost::archive::archive_exception::pointer_conflict
191 );
192 }
193 std::remove(testfile);
194 return EXIT_SUCCESS;
195 }
196
197 int test_main( int /* argc */, char* /* argv */[] ){
198 test1();
199 test2();
200 test3();
201 return EXIT_SUCCESS;
202 }
203
204 // EOF