1 #ifndef OBJECTIO__HPP
2 #define OBJECTIO__HPP
3 
4 /*  $Id: objectio.hpp 529139 2017-03-01 17:43:15Z gouriano $
5 * ===========================================================================
6 *
7 *                            PUBLIC DOMAIN NOTICE
8 *               National Center for Biotechnology Information
9 *
10 *  This software/database is a "United States Government Work" under the
11 *  terms of the United States Copyright Act.  It was written as part of
12 *  the author's official duties as a United States Government employee and
13 *  thus cannot be copyrighted.  This software/database is freely available
14 *  to the public for use. The National Library of Medicine and the U.S.
15 *  Government have not placed any restriction on its use or reproduction.
16 *
17 *  Although all reasonable efforts have been taken to ensure the accuracy
18 *  and reliability of the software and data, the NLM and the U.S.
19 *  Government do not and cannot warrant the performance or results that
20 *  may be obtained by using this software or data. The NLM and the U.S.
21 *  Government disclaim all warranties, express or implied, including
22 *  warranties of performance, merchantability or fitness for any particular
23 *  purpose.
24 *
25 *  Please cite the author in any work or product based on this material.
26 *
27 * ===========================================================================
28 *
29 * Author: Eugene Vasilchenko
30 *
31 * File Description:
32 *   !!! PUT YOUR DESCRIPTION HERE !!!
33 */
34 
35 #include <corelib/ncbistd.hpp>
36 #include <serial/objectiter.hpp>
37 
38 
39 /** @addtogroup ObjStreamSupport
40  *
41  * @{
42  */
43 
44 
45 BEGIN_NCBI_SCOPE
46 
47 class COStreamContainer;
48 
49 class NCBI_XSERIAL_EXPORT COStreamFrame
50 {
51 public:
52 
53     CObjectOStream& GetStream(void) const;
54 
55 protected:
56     COStreamFrame(CObjectOStream& stream);
57     ~COStreamFrame(void);
58     bool Good(void) const;
59 
60 private:
61     CObjectOStream& m_Stream;
62     size_t m_Depth;
63 
64     void* operator new(size_t size);
65     void* operator new[](size_t size);
66     //void operator delete(void* ptr);
67     //void operator delete[](void* ptr);
68 };
69 
70 class NCBI_XSERIAL_EXPORT CIStreamFrame
71 {
72 public:
73     CObjectIStream& GetStream(void) const;
74 
75 protected:
76     CIStreamFrame(CObjectIStream& stream);
77     ~CIStreamFrame(void);
78     bool Good(void) const;
79 
80 private:
81     CObjectIStream& m_Stream;
82     size_t m_Depth;
83 
84     void* operator new(size_t size);
85     void* operator new[](size_t size);
86     //void operator delete(void* ptr);
87     //void operator delete[](void* ptr);
88 };
89 
90 
91 /// Writing class members
92 ///
93 /// Suggested use:
94 ///    CObjectOStream& out;
95 ///    CObjectTypeInfo::CMemberIterator member;
96 ///    { // block for automatic call of COStreamClassMember destructor
97 ///        COStreamClassMember o(out, member);
98 ///        ... // write member object
99 ///    } // here COStreamClassMember destructor will be called
100 class NCBI_XSERIAL_EXPORT COStreamClassMember : public COStreamFrame
101 {
102     typedef COStreamFrame CParent;
103 public:
104     COStreamClassMember(CObjectOStream& out,
105                         const CObjectTypeInfo::CMemberIterator& member);
106     ~COStreamClassMember(void);
107 };
108 
109 
110 /// Reading (iterating through) members of the class (SET, SEQUENCE)
111 ///
112 /// Suggested use:
113 ///   CObjectIStream& in;
114 ///   CObjectTypeInfo classMemberType;
115 ///   for ( CIStreamClassMemberIterator i(in, classMemberType); i; ++i ) {
116 ///       CElementClass element;
117 ///       i >> element;
118 ///   }
119 class NCBI_XSERIAL_EXPORT CIStreamClassMemberIterator : public CIStreamFrame
120 {
121     typedef CIStreamFrame CParent;
122 public:
123     CIStreamClassMemberIterator(CObjectIStream& in,
124                                 const CObjectTypeInfo& classMemberType);
125     ~CIStreamClassMemberIterator(void);
126 
127     bool HaveMore(void) const;
128     DECLARE_OPERATOR_BOOL(HaveMore());
129 
130     void NextClassMember(void);
131     CIStreamClassMemberIterator& operator++(void);
132 
133     void ReadClassMember(const CObjectInfo& classMember);
134     void SkipClassMember(const CObjectTypeInfo& classMemberType);
135     void SkipClassMember(void);
136 
137     CObjectTypeInfoMI operator*(void) const;
138 
139 private:
140     void BeginClassMember(void);
141 
142     void IllegalCall(const char* message) const;
143     void BadState(void) const;
144 
145     void CheckState(void);
146 
147     const CMemberInfo* GetMemberInfo(void) const;
148 
149     CObjectTypeInfo m_ClassType;
150     TMemberIndex m_MemberIndex;
151 };
152 
153 
154 /// Reading (iterating through) elements of containers (SET OF, SEQUENCE OF).
155 ///
156 /// Suggested use:
157 ///   CObjectIStream& in;
158 ///   CObjectTypeInfo containerType;
159 ///   for ( CIStreamContainerIterator i(in, containerType); i; ++i ) {
160 ///       CElementClass element;
161 ///       i >> element;
162 ///   }
163 class NCBI_XSERIAL_EXPORT CIStreamContainerIterator : public CIStreamFrame
164 {
165     typedef CIStreamFrame CParent;
166 public:
167     CIStreamContainerIterator(CObjectIStream& in,
168                               const CObjectTypeInfo& containerType);
169     ~CIStreamContainerIterator(void);
170 
171     const CObjectTypeInfo& GetContainerType(void) const;
172     const CObjectTypeInfo  GetElementType(void) const;
173 
174     bool HaveMore(void) const;
175     DECLARE_OPERATOR_BOOL(HaveMore());
176 
177     void NextElement(void);
178     CIStreamContainerIterator& operator++(void);
179 
180     CObjectInfo ReadElement(TObjectPtr container);
181     void ReadElement(const CObjectInfo& element);
182     void SkipElement(const CObjectTypeInfo& elementType);
183     void SkipElement(void);
184 
185     void CopyElement(CObjectStreamCopier& copier,
186                      COStreamContainer& out);
187 
188 private:
189     const CContainerTypeInfo* GetContainerTypeInfo(void) const;
190 
191     void BeginElement(void);
192     void BeginElementData(void);
193     void BeginElementData(const CObjectTypeInfo& elementType);
194 
195     void IllegalCall(const char* message) const;
196     void BadState(void) const;
197 
198     enum EState {
199         eElementBegin,
200         eElementEnd,
201         eNoMoreElements,
202         eFinished,
203         eError // exception was thrown
204     };
205 
206     void CheckState(EState state);
207 
208     CObjectTypeInfo m_ContainerType;
209     TTypeInfo m_ElementTypeInfo;
210     EState m_State;
211     const CContainerTypeInfo* m_ContainerTypeInfo;
212     const CItemInfo* m_Container;
213 };
214 
215 template<typename T>
216 inline
operator >>(CIStreamContainerIterator & i,T & element)217 void operator>>(CIStreamContainerIterator& i, T& element)
218 {
219     i.ReadElement(ObjectInfo(element));
220 }
221 
222 /// Writing containers (SET OF, SEQUENCE OF).
223 ///
224 /// Suggested use:
225 ///    CObjectOStream& out;
226 ///    CObjectTypeInfo containerType;
227 ///    set<CElementClass> container;
228 ///    {
229 ///        COStreamContainer o(out, containerType);
230 ///        for ( set<CElementClass>::const_iterator i = container.begin();
231 ///              i != container.end(); ++i ) {
232 ///            const CElementClass& element = *i;
233 ///            o << element;
234 ///        }
235 ///    }
236 class NCBI_XSERIAL_EXPORT COStreamContainer : public COStreamFrame
237 {
238     typedef COStreamFrame CParent;
239 public:
240     COStreamContainer(CObjectOStream& out,
241                       const CObjectTypeInfo& containerType);
242     ~COStreamContainer(void);
243 
244     const CObjectTypeInfo& GetContainerType(void) const;
245 
246     void WriteElement(const CConstObjectInfo& element);
247     void WriteElement(CObjectStreamCopier& copier,
248                       CIStreamContainerIterator& in);
249     void WriteElement(CObjectStreamCopier& copier,
250                       CObjectIStream& in);
251 
252 private:
253     const CContainerTypeInfo* GetContainerTypeInfo(void) const;
254 
255     CObjectTypeInfo m_ContainerType;
256     TTypeInfo m_ElementTypeInfo;
257 };
258 
259 template<typename T>
260 inline
operator <<(COStreamContainer & o,const T & element)261 void operator<<(COStreamContainer& o, const T& element)
262 {
263     o.WriteElement(ConstObjectInfo(element));
264 }
265 
266 
267 /* @} */
268 
269 
270 #include <serial/impl/objectio.inl>
271 
272 END_NCBI_SCOPE
273 
274 #endif  /* OBJECTIO__HPP */
275