home *** CD-ROM | disk | FTP | other *** search
/ Liren Large Software Subsidy 7 / 07.iso / c / c083 / 12.ddi / CLASSINC.PAK / OBJSTRM.H < prev    next >
Encoding:
C/C++ Source or Header  |  1993-12-02  |  50.4 KB  |  1,408 lines

  1. /*------------------------------------------------------------------------*/
  2. /*                                                                        */
  3. /*  OBJSTRM.H                                                             */
  4. /*                                                                        */
  5. /*  Copyright (c) 1992, 1993 Borland International                        */
  6. /*  All Rights Reserved                                                   */
  7. /*                                                                        */
  8. /*------------------------------------------------------------------------*/
  9.  
  10. #if !defined( __CLASSLIB_OBJSTRM_H )
  11. #define __CLASSLIB_OBJSTRM_H
  12.  
  13. #if !defined( __IOSTREAM_H )
  14. #include <iostream.h>
  15. #endif  // __IOSTREAM_H
  16.  
  17. #if !defined( __FSTREAM_H )
  18. #include <fstream.h>
  19. #endif  // __FSTREAM_H
  20.  
  21. #if !defined( __SYSTYPES_H )
  22. #include <systypes.h>
  23. #endif  // __SYSTYPES_H
  24.  
  25. #if !defined( __TYPEINFO_H )
  26. #include <typeinfo.h>
  27. #endif  // __TYPEINFO_H
  28.  
  29. #if !defined( __CHECKS_H )
  30. #include <checks.h>
  31. #endif  // __CHECKS_H
  32.  
  33. #if !defined( __CLASSLIB_DEFS_H )
  34. #include "classlib\defs.h"
  35. #endif  // __CLASSLIB_DEFS_H
  36.  
  37. #if !defined( __CLASSLIB_STREAMBL_H )
  38. #include "classlib\streambl.h"
  39. #endif  // __CLASSLIB_STREAMBL_H
  40.  
  41. #if !defined( __CLASSLIB_VECTIMP_H )
  42. #include "classlib\vectimp.h"
  43. #endif  // __CLASSLIB_VECTIMP_H
  44.  
  45. #if defined( BI_CLASSLIB_NO_po )
  46. #pragma option -po-
  47. #endif
  48.  
  49. /*------------------------------------------------------------------------*/
  50. /*                                                                        */
  51. /*  The __link() macro forces the compiler to link in a static instance   */
  52. /*  of class TStreamableClass, which in turn registers its associated     */
  53. /*  TStreamable object with the stream manager.  Applications that do     */
  54. /*  not use streaming won't use __link(), and that will reduce the amount */
  55. /*  of code that is linked into the application.                          */
  56. /*                                                                        */
  57. /*------------------------------------------------------------------------*/
  58.  
  59. struct fLink
  60. {
  61.     struct fLink *f;
  62.     class TStreamableClass *t;
  63. };
  64.  
  65. #define __link( s )             \
  66.   extern TStreamableClass s;    \
  67.   static fLink force ## s =     \
  68.     { (fLink *)&force ## s, (TStreamableClass *)&s };
  69.  
  70. typedef unsigned P_id_type;
  71.  
  72. class _BIDSCLASS _RTTI TStreamable;
  73. class _BIDSCLASS TStreamableTypes;
  74. class _BIDSCLASS opstream;
  75. class _BIDSCLASS ipstream;
  76.  
  77. class _EXPCLASS string;
  78.  
  79. ipstream _BIDSFAR& _BIDSENTRY _BIDSFUNC operator >> ( ipstream _BIDSFAR& is,
  80.                                                       string _BIDSFAR& str );
  81.  
  82. opstream _BIDSFAR& _BIDSENTRY _BIDSFUNC operator << ( opstream _BIDSFAR& os,
  83.                                                       const string _BIDSFAR& str );
  84.  
  85. /* -----------------------------------------------------------------------*/
  86. /*                                                                        */
  87. /*  _TYPENAME(obj) provides a macro for getting the type name from a      */
  88. /*  pointer to an object. If runtime type information is available, this  */
  89. /*  macro uses the typeid of the object to get its name. If runtime type  */
  90. /*  information is not available, it uses the CastableID() for the object.*/
  91. /*                                                                        */
  92. /* -----------------------------------------------------------------------*/
  93.  
  94. #if defined( BI_NO_RTTI )
  95. #   define _TYPENAME(obj) (obj)->CastableID()
  96. #else
  97. #   define _TYPENAME(obj) typeid(*obj).name()
  98. #endif
  99.  
  100. /* -----------------------------------------------------------------------*/
  101. /*                                                                        */
  102. /*  class TStreamable                                                     */
  103. /*                                                                        */
  104. /*  This is the base class from which all streamable objects must be      */
  105. /*  derived.                                                              */
  106. /*                                                                        */
  107. /* -----------------------------------------------------------------------*/
  108.  
  109. enum StreamableInit { streamableInit };
  110.  
  111. class _BIDSCLASS _RTTI TStreamableBase
  112. {
  113.  
  114. public:
  115.  
  116.     virtual ~TStreamableBase();
  117.  
  118. #if defined( BI_NO_RTTI )
  119.     typedef const char *Type_id;
  120.     virtual void *FindBase( Type_id id ) const;
  121.  
  122. public:
  123.  
  124.     virtual Type_id CastableID() const = 0;
  125.     virtual void *MostDerived() const = 0;
  126. #endif  // BI_NO_RTTI
  127.  
  128. };
  129.  
  130. class _BIDSCLASS _RTTI TStreamable : public TStreamableBase
  131. {
  132.  
  133.     friend class _BIDSCLASS _RTTI TOldStreamer;
  134.  
  135. protected:
  136.  
  137.     virtual const char *streamableName() const = 0;
  138.  
  139.     virtual void *read( ipstream& );
  140.     virtual void write( opstream& );
  141.  
  142. #if defined( BI_NO_RTTI )
  143. public:
  144.     virtual void *FindBase( Type_id id ) const;
  145. protected:
  146.     virtual Type_id CastableID() const { return streamableName(); }
  147.     virtual void *MostDerived() const { return 0; }
  148. #endif
  149. };
  150.  
  151. class _BIDSCLASS _RTTI TStreamer
  152. {
  153.  
  154.     friend class ipstream;
  155.     friend class opstream;
  156.  
  157. public:
  158.  
  159.     TStreamableBase *GetObject() const { return object; }
  160.  
  161. protected:
  162.  
  163.     TStreamer( TStreamableBase *obj ) : object(obj) {}
  164.  
  165.     virtual const char *StreamableName() const = 0;
  166.  
  167.     virtual void *Read( ipstream&, uint32 ) const = 0;
  168.     virtual void Write( opstream& ) const = 0;
  169.  
  170. private:
  171.  
  172.     virtual uint32 ClassVersion() const = 0;
  173.  
  174.     TStreamableBase *object;
  175.  
  176. };
  177.  
  178. class _BIDSCLASS _RTTI TOldStreamer : public TStreamer
  179. {
  180.  
  181. public:
  182.  
  183.     TOldStreamer( TStreamable *obj ) : TStreamer(obj) {};
  184.  
  185. protected:
  186.  
  187.     virtual const char *StreamableName() const
  188.         {
  189.         return STATIC_CAST(TStreamable *,GetObject())->streamableName();
  190.         }
  191.  
  192.     virtual void *Read( ipstream& is, uint32 ) const
  193.         {
  194.         return STATIC_CAST(TStreamable *,GetObject())->read( is );
  195.         }
  196.  
  197.     virtual void Write( opstream& os ) const
  198.         {
  199.         STATIC_CAST(TStreamable *,GetObject())->write( os );
  200.         }
  201.  
  202. private:
  203.  
  204.     virtual uint32 ClassVersion() const
  205.         {
  206.         return 0;
  207.         }
  208.  
  209. };
  210.  
  211. class _BIDSCLASS _RTTI TNewStreamer : public TStreamer
  212. {
  213.  
  214. public:
  215.  
  216.     TNewStreamer( TStreamableBase *obj ) : TStreamer(obj) {};
  217.  
  218. protected:
  219.  
  220.     virtual const char *StreamableName() const
  221.         {
  222.         return _TYPENAME(GetObject());
  223.         }
  224.  
  225. };
  226.  
  227. /* ------------------------------------------------------------------------*/
  228. /*                                                                         */
  229. /*   class TPWrittenObjects                                                */
  230. /*                                                                         */
  231. /*   Maintains a database of all objects that have been written to the     */
  232. /*   current persistent stream.                                            */
  233. /*                                                                         */
  234. /*   Used by opstream when it writes a pointer from a stream to save the   */
  235. /*   address and ID of the object being written.                           */
  236. /*                                                                         */
  237. /* ------------------------------------------------------------------------*/
  238.  
  239. class _BIDSCLASS TPWrittenObjects
  240. {
  241.  
  242.     friend opstream;
  243.  
  244. public:
  245.  
  246.     void RemoveAll();
  247.  
  248.     class _BIDSCLASS TPWObj
  249.     {
  250.  
  251.     public:
  252.  
  253.         TPWObj() : Address(0), Ident(0) {}
  254.         TPWObj( const void *adr, P_id_type id ) : 
  255.             Address(adr), Ident(id) {}
  256.  
  257.         friend int operator == ( const TPWObj& o1, const TPWObj& o2 )
  258.             { return o1.Address == o2.Address; }
  259.  
  260.         friend int operator < ( const TPWObj& o1, const TPWObj& o2 )
  261.             { return o1.Address < o2.Address; }
  262.  
  263.         const void *Address;
  264.         P_id_type Ident;
  265.  
  266.     };
  267.  
  268. private:
  269.  
  270.     TPWrittenObjects();
  271.  
  272.     void RegisterObject( TStreamableBase *adr );
  273.     void RegisterVB( const TStreamableBase *adr );
  274.     P_id_type FindObject( TStreamableBase *adr );
  275.     P_id_type FindVB( TStreamableBase *adr );
  276.  
  277.     P_id_type CurId;
  278.  
  279.     TSVectorImp<TPWObj> Data;
  280.  
  281. };
  282.  
  283. /* ------------------------------------------------------------------------*/
  284. /*                                                                         */
  285. /*   class TPReadObjects                                                   */
  286. /*                                                                         */
  287. /*   Maintains a database of all objects that have been read from the      */
  288. /*   current persistent stream.                                            */
  289. /*                                                                         */
  290. /*   Used by ipstream when it reads a pointer from a stream to determine   */
  291. /*   the address of the object being referred to.                          */
  292. /*                                                                         */
  293. /* ------------------------------------------------------------------------*/
  294.  
  295. class _BIDSCLASS TPReadObjects
  296. {
  297.  
  298.     friend ipstream;
  299.  
  300. public:
  301.  
  302.     void RemoveAll();
  303.  
  304. private:
  305.  
  306.     TPReadObjects();
  307.  
  308.     void RegisterObject( TStreamableBase *adr );
  309.     TStreamableBase *Find( P_id_type id );
  310.  
  311.     TCVectorImp<TStreamableBase *> Data;
  312.  
  313. };
  314.  
  315. /* ------------------------------------------------------------------------*/
  316. /*                                                                         */
  317. /*   class pstream                                                         */
  318. /*                                                                         */
  319. /*   Base class for handling streamable objects.                           */
  320. /*                                                                         */
  321. /* ------------------------------------------------------------------------*/
  322.  
  323. class _BIDSCLASS pstream
  324. {
  325.  
  326.     friend TStreamableTypes;
  327.     friend TStreamableClass;
  328.  
  329. public:
  330.  
  331.     enum PointerTypes { ptNull, ptIndexed, ptObject };
  332.  
  333.     _Cdecl pstream( streambuf _BIDSFAR * );
  334.     virtual _Cdecl ~pstream();
  335.  
  336.     int _Cdecl rdstate() const;
  337.     int _Cdecl eof() const;
  338.     int _Cdecl fail() const;
  339.     int _Cdecl bad() const;
  340.     int _Cdecl good() const;
  341.     void _Cdecl clear( int = 0 );
  342.     _Cdecl operator void *() const;
  343.     int _Cdecl operator ! () const;
  344.  
  345.     streambuf _BIDSFAR * _Cdecl rdbuf() const;
  346.  
  347.     static void initTypes();
  348.  
  349.     static void registerType( TStreamableClass *ts );
  350.  
  351. protected:
  352.  
  353.     _Cdecl pstream();
  354.  
  355.     streambuf _BIDSFAR *bp;
  356.     int state;
  357.  
  358.     void _Cdecl init( streambuf _BIDSFAR * );
  359.     void _Cdecl setstate( int );
  360.  
  361.     static TStreamableTypes *types;
  362.  
  363. };
  364.  
  365. /* ------------------------------------------------------------------------*/
  366. /*                                                                         */
  367. /*   class ipstream                                                        */
  368. /*                                                                         */
  369. /*   Base class for reading streamable objects                             */
  370. /*                                                                         */
  371. /* ------------------------------------------------------------------------*/
  372.  
  373. class _BIDSCLASS ipstream : virtual public pstream
  374. {
  375.  
  376.     friend class TStreamableClass;
  377.  
  378. public:
  379.  
  380.     _Cdecl ipstream( streambuf _BIDSFAR * );
  381.  
  382.     streampos _Cdecl tellg();
  383.     ipstream& _Cdecl seekg( streampos );
  384.     ipstream& _Cdecl seekg( streamoff, ios::seek_dir );
  385.  
  386.     uint8 _Cdecl readByte();
  387.     void _Cdecl readBytes( void _BIDSFAR *, size_t );
  388.     void _Cdecl freadBytes( void _BIDSFARDATA *data, size_t sz );
  389.  
  390.     uint32 _Cdecl readWord();
  391.     uint16 _Cdecl readWord16();
  392.     uint32 _Cdecl readWord32();
  393.  
  394.     char _BIDSFAR * _Cdecl readString();
  395.     char _BIDSFAR * _Cdecl readString( char _BIDSFAR *, unsigned );
  396.     char _BIDSFARDATA *freadString();
  397.     char _BIDSFARDATA *freadString( char _BIDSFARDATA *buf, unsigned maxLen );
  398.  
  399.     friend ipstream& _Cdecl operator >> ( ipstream&, signed char& );
  400.     friend ipstream& _Cdecl operator >> ( ipstream&, unsigned char& );
  401.     friend ipstream& _Cdecl operator >> ( ipstream&, char& );
  402.     friend ipstream& _Cdecl operator >> ( ipstream&, signed short& );
  403.     friend ipstream& _Cdecl operator >> ( ipstream&, unsigned short& );
  404.     friend ipstream& _Cdecl operator >> ( ipstream&, signed int& );
  405.     friend ipstream& _Cdecl operator >> ( ipstream&, unsigned int& );
  406.     friend ipstream& _Cdecl operator >> ( ipstream&, signed long& );
  407.     friend ipstream& _Cdecl operator >> ( ipstream&, unsigned long& );
  408.     friend ipstream& _Cdecl operator >> ( ipstream&, float& );
  409.     friend ipstream& _Cdecl operator >> ( ipstream&, double& );
  410.     friend ipstream& _Cdecl operator >> ( ipstream&, long double& );
  411.  
  412.     uint32 getVersion() const;
  413.  
  414.     TStreamableBase _BIDSFAR *readObject( TStreamableBase _BIDSFAR *&mem, ModuleId mid = GetModuleId() );
  415.     TStreamableBase _BIDSFAR *readObjectPointer( TStreamableBase _BIDSFAR *&mem, ModuleId mid = GetModuleId() );
  416.  
  417.     TStreamableBase _BIDSFAR * _Cdecl find( P_id_type );
  418.     void _Cdecl registerObject( TStreamableBase _BIDSFAR *adr );
  419.  
  420. protected:
  421.  
  422.     _Cdecl ipstream();
  423.  
  424.     const ObjectBuilder _BIDSFAR * _Cdecl readPrefix( ModuleId mid );
  425.     void _Cdecl readData( const ObjectBuilder _BIDSFAR *,
  426.                           TStreamableBase _BIDSFAR *& );
  427.     void _Cdecl readSuffix();
  428.  
  429.     void readVersion();
  430.  
  431. private:
  432.  
  433.     TPReadObjects objs;
  434.     uint32 version;
  435.  
  436. };
  437.  
  438. /* ------------------------------------------------------------------------*/
  439. /*                                                                         */
  440. /*   class opstream                                                        */
  441. /*                                                                         */
  442. /*   Base class for writing streamable objects                             */
  443. /*                                                                         */
  444. /* ------------------------------------------------------------------------*/
  445.  
  446. class _BIDSCLASS opstream : virtual public pstream
  447. {
  448.  
  449. public:
  450.  
  451.     _Cdecl opstream( streambuf _BIDSFAR * );
  452.     _Cdecl ~opstream();
  453.  
  454.     streampos _Cdecl tellp();
  455.     opstream& _Cdecl seekp( streampos );
  456.     opstream& _Cdecl seekp( streamoff, ios::seek_dir );
  457.     opstream& _Cdecl flush();
  458.  
  459.     void _Cdecl writeByte( uint8 );
  460.     void _Cdecl writeBytes( const void _BIDSFAR *, size_t );
  461.     void _Cdecl fwriteBytes( const void _BIDSFARDATA *data, size_t sz );
  462.  
  463.     void _Cdecl writeWord( uint32 );
  464.     void _Cdecl writeWord16( uint16 );
  465.     void _Cdecl writeWord32( uint32 );
  466.  
  467.     void _Cdecl writeString( const char _BIDSFAR * );
  468.     void _Cdecl fwriteString( const char _BIDSFARDATA * str );
  469.  
  470.     friend opstream& _Cdecl operator << ( opstream&, signed char );
  471.     friend opstream& _Cdecl operator << ( opstream&, unsigned char );
  472.     friend opstream& _Cdecl operator << ( opstream&, char );
  473.     friend opstream& _Cdecl operator << ( opstream&, signed short );
  474.     friend opstream& _Cdecl operator << ( opstream&, unsigned short );
  475.     friend opstream& _Cdecl operator << ( opstream&, signed int );
  476.     friend opstream& _Cdecl operator << ( opstream&, unsigned int );
  477.     friend opstream& _Cdecl operator << ( opstream&, signed long );
  478.     friend opstream& _Cdecl operator << ( opstream&, unsigned long );
  479.     friend opstream& _Cdecl operator << ( opstream&, float );
  480.     friend opstream& _Cdecl operator << ( opstream&, double );
  481.     friend opstream& _Cdecl operator << ( opstream&, long double );
  482.  
  483.     void writeObject( const TStreamableBase _BIDSFAR *t, int isPtr = 0, ModuleId mid = GetModuleId() );
  484.     void writeObjectPointer( const TStreamableBase _BIDSFAR *t, ModuleId mid = GetModuleId() );
  485.  
  486.     P_id_type _Cdecl findObject( TStreamableBase _BIDSFAR *adr );
  487.     void _Cdecl registerObject( TStreamableBase _BIDSFAR *adr );
  488.  
  489.     P_id_type _Cdecl findVB( TStreamableBase _BIDSFAR *adr );
  490.     void _Cdecl registerVB( TStreamableBase _BIDSFAR *adr );
  491.  
  492. protected:
  493.  
  494.     _Cdecl opstream();
  495.  
  496.     void _Cdecl writePrefix( const TStreamableBase _BIDSFAR * );
  497.     void _Cdecl writeData( const TStreamableBase _BIDSFAR *, ModuleId mid );
  498.     void _Cdecl writeSuffix( const TStreamableBase _BIDSFAR * );
  499.  
  500. private:
  501.  
  502.     void writeVersion();
  503.  
  504.     TPWrittenObjects *objs;
  505.  
  506. };
  507.  
  508. /* ------------------------------------------------------------------------*/
  509. /*                                                                         */
  510. /*   class fpbase                                                          */
  511. /*                                                                         */
  512. /*   Base class for handling streamable objects on file streams            */
  513. /*                                                                         */
  514. /* ------------------------------------------------------------------------*/
  515.  
  516. class _BIDSCLASS fpbase : virtual public pstream
  517. {
  518.  
  519. public:
  520.  
  521.     _Cdecl fpbase();
  522.     _Cdecl fpbase( const char _BIDSFAR *, int, int = filebuf::openprot );
  523.     _Cdecl fpbase( int );
  524.     _Cdecl fpbase( int, char _BIDSFAR *, int );
  525.  
  526.     void _Cdecl open( const char _BIDSFAR *, int, int = filebuf::openprot );
  527.     void _Cdecl attach( int );
  528.     void _Cdecl close();
  529.     void _Cdecl setbuf( char _BIDSFAR *, int );
  530.     filebuf _BIDSFAR * _Cdecl rdbuf();
  531.  
  532. private:
  533.  
  534.     filebuf buf;
  535.  
  536. };
  537.  
  538. /* ------------------------------------------------------------------------*/
  539. /*                                                                         */
  540. /*   class ifpstream                                                       */
  541. /*                                                                         */
  542. /*   Base class for reading streamable objects from file streams           */
  543. /*                                                                         */
  544. /* ------------------------------------------------------------------------*/
  545.  
  546. class _BIDSCLASS ifpstream : public fpbase, public ipstream
  547. {
  548.  
  549. public:
  550.  
  551.     _Cdecl ifpstream();
  552.     _Cdecl ifpstream( const char _BIDSFAR *,
  553.                       int = ios::in,
  554.                       int = filebuf::openprot
  555.                     );
  556.     _Cdecl ifpstream( int );
  557.     _Cdecl ifpstream( int, char _BIDSFAR *, int );
  558.  
  559.     filebuf _BIDSFAR * _Cdecl rdbuf();
  560.     void _Cdecl open( const char _BIDSFAR *,
  561.                       int = ios::in,
  562.                       int = filebuf::openprot
  563.                     );
  564.  
  565. };
  566.  
  567. /* ------------------------------------------------------------------------*/
  568. /*                                                                         */
  569. /*   class ofpstream                                                       */
  570. /*                                                                         */
  571. /*   Base class for writing streamable objects to file streams             */
  572. /*                                                                         */
  573. /* ------------------------------------------------------------------------*/
  574.  
  575. class _BIDSCLASS ofpstream : public fpbase, public opstream
  576. {
  577.  
  578. public:
  579.  
  580.     _Cdecl ofpstream();
  581.     _Cdecl ofpstream( const char _BIDSFAR *,
  582.                       int = ios::out,
  583.                       int = filebuf::openprot
  584.                     );
  585.     _Cdecl ofpstream( int );
  586.     _Cdecl ofpstream( int, char _BIDSFAR *, int );
  587.  
  588.     filebuf _BIDSFAR * _Cdecl rdbuf();
  589.     void _Cdecl open( const char _BIDSFAR *,
  590.                       int = ios::out,
  591.                       int = filebuf::openprot
  592.                     );
  593.  
  594. };
  595.  
  596. /* ------------------------------------------------------------------------*/
  597. /*                                                                         */
  598. /*   Inline functions                                                      */
  599. /*                                                                         */
  600. /* ------------------------------------------------------------------------*/
  601.  
  602. inline pstream::pstream( streambuf _BIDSFAR *sb )
  603. {
  604.     init( sb );
  605. }
  606.  
  607. inline int pstream::rdstate() const
  608. {
  609.     return state;
  610. }
  611.  
  612. inline int pstream::eof() const
  613. {
  614.     return state & ios::eofbit;
  615. }
  616.  
  617. inline int pstream::fail() const
  618. {
  619.     return state & (ios::failbit | ios::badbit | ios::hardfail);
  620. }
  621.  
  622. inline int pstream::bad() const
  623. {
  624.     return state & (ios::badbit | ios::hardfail);
  625. }
  626.  
  627. inline int pstream::good() const
  628. {
  629.     return state == 0;
  630. }
  631.  
  632. inline void pstream::clear( int i )
  633. {
  634.     state = (i & 0xFF) | (state & ios::hardfail);
  635. }
  636.  
  637. inline pstream::operator void _BIDSFAR *() const
  638. {
  639.     return fail() ? 0 : (void *)this;
  640. }
  641.  
  642. inline int pstream::operator! () const
  643. {
  644.     return fail();
  645. }
  646.  
  647. inline streambuf _BIDSFAR * pstream::rdbuf() const
  648. {
  649.     return bp;
  650. }
  651.  
  652. inline pstream::pstream()
  653. {
  654. }
  655.  
  656. inline void pstream::init( streambuf *sbp )
  657. {
  658.     state = 0;
  659.     bp = sbp;
  660. }
  661.  
  662. inline void pstream::setstate( int b )
  663. {
  664.     state |= (b&0xFF);
  665. }
  666.  
  667. inline ipstream::ipstream( streambuf _BIDSFAR *sb )
  668. {
  669.     pstream::init( sb );
  670.     readVersion();
  671. }
  672.  
  673. inline ipstream::ipstream()
  674. {
  675.     if( bp != 0 )
  676.         readVersion();
  677. }
  678.  
  679. inline TStreamableBase *ipstream::find( P_id_type id )
  680. {
  681.     return objs.Find( id );
  682. }
  683.  
  684. inline void ipstream::registerObject( TStreamableBase *adr )
  685. {
  686.     objs.RegisterObject( adr );
  687. }
  688.  
  689. inline uint32 ipstream::getVersion() const
  690. {
  691.     return version;
  692. }
  693.  
  694. inline void pstream::registerType( TStreamableClass *ts )
  695. {
  696.     types->RegisterType( GetModuleId(), *ts );
  697. }
  698.  
  699. inline opstream::~opstream()
  700. {
  701.     delete objs;
  702. }
  703.  
  704. inline void opstream::writeWord( uint32 word32 )
  705. {
  706.     writeWord32( word32 );
  707. }
  708.  
  709. inline void opstream::writeSuffix( const TStreamableBase * )
  710. {
  711.     writeByte( ']' );
  712. }
  713.  
  714. inline P_id_type opstream::findObject( TStreamableBase *adr )
  715. {
  716.     return objs->FindObject( adr );
  717. }
  718.  
  719. inline void opstream::registerObject( TStreamableBase *adr )
  720. {
  721.     objs->RegisterObject( adr );
  722. }
  723.  
  724. inline P_id_type opstream::findVB( TStreamableBase *adr )
  725. {
  726.     return objs->FindVB( adr );
  727. }
  728.  
  729. inline void opstream::registerVB( TStreamableBase *adr )
  730. {
  731.     objs->RegisterVB( adr );
  732. }
  733.  
  734. inline fpbase::fpbase()
  735. {
  736.     pstream::init( &buf );
  737. }
  738.  
  739. inline fpbase::fpbase( const char *name, int omode, int prot )
  740. {
  741.     pstream::init( &buf );
  742.     open( name, omode, prot );
  743. }
  744.  
  745. inline fpbase::fpbase( int f ) : buf( f )
  746. {
  747.     pstream::init( &buf );
  748. }
  749.  
  750. inline fpbase::fpbase( int f, char *b, int len ) : buf( f, b, len )
  751. {
  752.     pstream::init( &buf );
  753. }
  754.  
  755. inline filebuf *fpbase::rdbuf()
  756. {
  757.     return &buf;
  758. }
  759.  
  760. inline ifpstream::ifpstream()
  761. {
  762. }
  763.  
  764. inline ifpstream::ifpstream( const char* name, int omode, int prot ) :
  765.     fpbase( name, omode | ios::in | ios::binary, prot )
  766. {
  767. }
  768.  
  769. inline ifpstream::ifpstream( int f ) : fpbase( f )
  770. {
  771. }
  772.  
  773. inline ifpstream::ifpstream(int f, char* b, int len) : fpbase(f, b, len)
  774. {
  775. }
  776.  
  777. inline filebuf *ifpstream::rdbuf()
  778. {
  779.     return fpbase::rdbuf();
  780. }
  781.  
  782. inline void ifpstream::open( const char _BIDSFAR *name, int omode, int prot )
  783. {
  784.     fpbase::open( name, omode | ios::in | ios::binary, prot );
  785.     readVersion();
  786. }
  787.  
  788. inline ofpstream::ofpstream()
  789. {
  790. }
  791.  
  792. inline ofpstream::ofpstream( const char* name, int omode, int prot ) :
  793.     fpbase( name, omode | ios::out | ios::binary, prot )
  794. {
  795. }
  796.  
  797. inline ofpstream::ofpstream( int f ) : fpbase( f )
  798. {
  799. }
  800.  
  801. inline ofpstream::ofpstream(int f, char* b, int len) : fpbase(f, b, len)
  802. {
  803. }
  804.  
  805. inline filebuf *ofpstream::rdbuf()
  806. {
  807.     return fpbase::rdbuf();
  808. }
  809.  
  810. inline void ofpstream::open( const char _BIDSFAR *name, int omode, int prot )
  811. {
  812.     fpbase::open( name, omode | ios::out | ios::binary, prot );
  813. }
  814.  
  815. inline ipstream& _Cdecl operator >> ( ipstream& ps, signed char &ch )
  816. {
  817.     ch = ps.readByte();
  818.     return ps;
  819. }
  820.  
  821. inline ipstream& _Cdecl operator >> ( ipstream& ps, unsigned char &ch )
  822. {
  823.     ch = ps.readByte();
  824.     return ps;
  825. }
  826.  
  827. inline ipstream& _Cdecl operator >> ( ipstream& ps, char &ch )
  828. {
  829.     ch = ps.readByte();
  830.     return ps;
  831. }
  832.  
  833. inline ipstream& _Cdecl operator >> ( ipstream& ps, signed short &sh )
  834. {
  835.     sh = ps.readWord16();
  836.     return ps;
  837. }
  838.  
  839. inline ipstream& _Cdecl operator >> ( ipstream& ps, unsigned short &sh )
  840. {
  841.     sh = ps.readWord16();
  842.     return ps;
  843. }
  844.  
  845. inline ipstream& _Cdecl operator >> ( ipstream& ps, signed int &i )
  846. {
  847.     i = (int)(ps.readWord32());
  848.     return ps;
  849. }
  850.  
  851. inline ipstream& _Cdecl operator >> ( ipstream& ps, unsigned int &i )
  852. {
  853.     i = (unsigned int)(ps.readWord32());
  854.     return ps;
  855. }
  856.  
  857. inline ipstream& _Cdecl operator >> ( ipstream& ps, signed long &l )
  858. {
  859.     ps.readBytes( &l, sizeof(l) );
  860.     return ps;
  861. }
  862.  
  863. inline ipstream& _Cdecl operator >> ( ipstream& ps, unsigned long &l )
  864. {
  865.     ps.readBytes( &l, sizeof(l) );
  866.     return ps;
  867. }
  868.  
  869. inline ipstream& _Cdecl operator >> ( ipstream& ps, float &f )
  870. {
  871.     ps.readBytes( &f, sizeof(f) );
  872.     return ps;
  873. }
  874.  
  875. inline ipstream& _Cdecl operator >> ( ipstream& ps, double &d )
  876. {
  877.     ps.readBytes( &d, sizeof(d) );
  878.     return ps;
  879. }
  880.  
  881. inline ipstream& _Cdecl operator >> ( ipstream& ps, long double &l )
  882. {
  883.     ps.readBytes( &l, sizeof(l) );
  884.     return ps;
  885. }
  886.  
  887. inline opstream& _Cdecl operator << ( opstream& ps, signed char ch )
  888. {
  889.     ps.writeByte( ch );
  890.     return ps;
  891. }
  892.  
  893. inline opstream& _Cdecl operator << ( opstream& ps, unsigned char ch )
  894. {
  895.     ps.writeByte( ch );
  896.     return ps;
  897. }
  898.  
  899. inline opstream& _Cdecl operator << ( opstream& ps, char ch )
  900. {
  901.     ps.writeByte( ch );
  902.     return ps;
  903. }
  904.  
  905. inline opstream& _Cdecl operator << ( opstream& ps, signed short sh )
  906. {
  907.     ps.writeWord16( sh );
  908.     return ps;
  909. }
  910.  
  911. inline opstream& _Cdecl operator << ( opstream& ps, unsigned short sh )
  912. {
  913.     ps.writeWord16( sh );
  914.     return ps;
  915. }
  916.  
  917. inline opstream& _Cdecl operator << ( opstream& ps, signed int i )
  918. {
  919.     ps.writeWord32( i );
  920.     return ps;
  921. }
  922.  
  923. inline opstream& _Cdecl operator << ( opstream& ps, unsigned int i )
  924. {
  925.     ps.writeWord32( i );
  926.     return ps;
  927. }
  928.  
  929. inline opstream& _Cdecl operator << ( opstream& ps, signed long l )
  930. {
  931.     ps.writeBytes( &l, sizeof(l) );
  932.     return ps;
  933. }
  934.  
  935. inline opstream& _Cdecl operator << ( opstream& ps, unsigned long l )
  936. {
  937.     ps.writeBytes( &l, sizeof(l) );
  938.     return ps;
  939. }
  940.  
  941. inline opstream& _Cdecl operator << ( opstream& ps, float f )
  942. {
  943.     ps.writeBytes( &f, sizeof(f) );
  944.     return ps;
  945. }
  946.  
  947. inline opstream& _Cdecl operator << ( opstream& ps, double d )
  948. {
  949.     ps.writeBytes( &d, sizeof(d) );
  950.     return ps;
  951. }
  952.  
  953. inline opstream& _Cdecl operator << ( opstream& ps, long double l )
  954. {
  955.     ps.writeBytes( &l, sizeof(l) );
  956.     return ps;
  957. }
  958.  
  959. template <class Base> void WriteBaseObject( Base *base, opstream& out )
  960. {
  961.     Base::Streamer strmr(base);
  962.     out << strmr.ClassVersion();
  963.     strmr.Write( out );
  964. }
  965.  
  966. template <class Base> void ReadBaseObject( Base *base, ipstream& in )
  967. {
  968.     uint32 version = 0;
  969.     if( in.getVersion() > 0 )
  970.         in >> version;
  971.     Base::Streamer(base).Read( in, version );
  972. }
  973.  
  974. template <class Base> void WriteVirtualBase( Base *base, opstream& out )
  975. {
  976.     if( !out.good() )
  977.         return;
  978.     if( out.findVB( base ) != 0 )
  979.         {
  980.         out.writeByte( pstream::ptIndexed );    // use ptIndexed to indicate
  981.                                                 // that we've already seen
  982.                                                 // this virtual base. Don't
  983.                                                 // need to actually write it.
  984.         }
  985.     else
  986.         {
  987.         Base::Streamer strmr(base);
  988.         out.registerObject( (TStreamableBase *)((char *)base + 1) );
  989.         out.writeByte( pstream::ptObject );
  990.         out.writeWord32( strmr.ClassVersion() );
  991.         strmr.Write( out );
  992.         }
  993. }
  994.  
  995. template <class Base> void ReadVirtualBase( Base *base, ipstream& in )
  996. {
  997.     char ch;
  998.     in >> ch;
  999.     switch( ch )
  1000.         {
  1001.         case pstream::ptIndexed:
  1002.             {
  1003.             break;      // We've already read this virtual base
  1004.             }
  1005.         case pstream::ptObject:
  1006.             {
  1007.             uint32 ver = 0;
  1008.             if( in.getVersion() > 0 )
  1009.                 ver = in.readWord32();
  1010.             Base::Streamer strmr(base);
  1011.             // register the address
  1012.             in.registerObject(strmr.GetObject());
  1013.             strmr.Read( in, ver );
  1014.             break;
  1015.             }
  1016.         }
  1017. }
  1018.  
  1019. /*  Individual Components for Streamable Declarations */
  1020.  
  1021. #define DECLARE_STREAMER( exp, cls, ver )                           \
  1022. public:                                                             \
  1023.     class exp Streamer : public TNewStreamer                        \
  1024.         {                                                           \
  1025.         public:                                                     \
  1026.                                                                     \
  1027.         Streamer( TStreamableBase *obj );                           \
  1028.                                                                     \
  1029.         virtual uint32 ClassVersion() const                         \
  1030.             { return ver; }                                         \
  1031.                                                                     \
  1032.         virtual void Write( opstream& ) const;                      \
  1033.         virtual void *Read( ipstream&, uint32 ) const;              \
  1034.                                                                     \
  1035.         cls *GetObject() const                                      \
  1036.             {                                                       \
  1037.             return object;                                          \
  1038.             }                                                       \
  1039.                                                                     \
  1040.         static TStreamer *Build( TStreamableBase *obj )             \
  1041.             {                                                       \
  1042.             return new Streamer( obj ? obj : new cls(streamableInit) ); \
  1043.             }                                                       \
  1044.                                                                     \
  1045.         private:                                                    \
  1046.             cls *object;                                            \
  1047.                                                                     \
  1048.         };                                                          \
  1049.     friend Streamer;                                                \
  1050.     friend void ReadBaseObject( cls *, ipstream& );                 \
  1051.     friend void WriteBaseObject( cls *, opstream& );                \
  1052.     friend void ReadVirtualBase( cls *, ipstream& );                \
  1053.     friend void WriteVirtualBase( cls *, opstream& )
  1054.  
  1055. #define DECLARE_STREAMER_FROM_BASE( exp, cls, base )                \
  1056. public:                                                             \
  1057.     class exp Streamer : public base::Streamer                      \
  1058.         {                                                           \
  1059.         public:                                                     \
  1060.                                                                     \
  1061.         Streamer( TStreamableBase *obj ) : base::Streamer(obj){}    \
  1062.                                                                     \
  1063.         cls *GetObject() const                                      \
  1064.             {                                                       \
  1065.             return object;                                          \
  1066.             }                                                       \
  1067.                                                                     \
  1068.         static TStreamer *Build( TStreamableBase *obj )             \
  1069.             {                                                       \
  1070.             return new Streamer( obj ? obj : new cls(streamableInit) ); \
  1071.             }                                                       \
  1072.                                                                     \
  1073.         private:                                                    \
  1074.             cls *object;                                            \
  1075.                                                                     \
  1076.         };                                                          \
  1077.     friend Streamer;                                                \
  1078.     friend void ReadBaseObject( cls *, ipstream& );                 \
  1079.     friend void WriteBaseObject( cls *, opstream& );                \
  1080.     friend void ReadVirtualBase( cls *, ipstream& );                \
  1081.     friend void WriteVirtualBase( cls *, opstream& )
  1082.  
  1083. #define DECLARE_ABSTRACT_STREAMER( exp, cls, ver )                  \
  1084. public:                                                             \
  1085.     class exp Streamer : public TNewStreamer                        \
  1086.         {                                                           \
  1087.         public:                                                     \
  1088.                                                                     \
  1089.         Streamer( TStreamableBase *obj );                           \
  1090.                                                                     \
  1091.         virtual uint32 ClassVersion() const                         \
  1092.             { return ver; }                                         \
  1093.                                                                     \
  1094.         virtual void Write( opstream& ) const;                      \
  1095.         virtual void *Read( ipstream&, uint32 ) const;              \
  1096.                                                                     \
  1097.         cls *GetObject() const                                      \
  1098.             {                                                       \
  1099.             return object;                                          \
  1100.             }                                                       \
  1101.                                                                     \
  1102.         private:                                                    \
  1103.             cls *object;                                            \
  1104.                                                                     \
  1105.         };                                                          \
  1106.     friend Streamer;                                                \
  1107.     friend void ReadBaseObject( cls *, ipstream& );                 \
  1108.     friend void WriteBaseObject( cls *, opstream& );                \
  1109.     friend void ReadVirtualBase( cls *, ipstream& );                \
  1110.     friend void WriteVirtualBase( cls *, opstream& )
  1111.       
  1112.  
  1113. #define DECLARE_STREAMABLE_OPS( cls )                               \
  1114. static ipstream& readRef( ipstream& is, cls& cl );                  \
  1115. friend inline ipstream& operator >> ( ipstream& is, cls& cl )       \
  1116.     { return cls::readRef( is, cl ); }                              \
  1117. static ipstream& readPtr( ipstream& is, cls*& cl );                 \
  1118. friend inline ipstream& operator >> ( ipstream& is, cls*& cl )      \
  1119.     { return cls::readPtr( is, cl ); }                              \
  1120. static opstream& writeRef( opstream& is, const cls& cl );           \
  1121. friend inline opstream& operator << ( opstream& os, const cls& cl ) \
  1122.     { return cls::writeRef( os, cl ); }                             \
  1123. static opstream& writePtr( opstream& is, const cls* cl );           \
  1124. friend inline opstream& operator << ( opstream& os, const cls* cl ) \
  1125.     { return cls::writePtr( os, cl ); }
  1126.  
  1127. #define DECLARE_STREAMABLE_CTOR( cls )                              \
  1128. public:                                                             \
  1129.     cls ( StreamableInit )
  1130.  
  1131. #if defined( BI_NO_RTTI )
  1132. #define DECLARE_CASTABLE                                            \
  1133. public:                                                             \
  1134.     virtual void *FindBase( Type_id id ) const;                     \
  1135. public:                                                             \
  1136.     virtual Type_id CastableID() const;                             \
  1137.     virtual void *MostDerived() const { return (void *)this; }      \
  1138.     static Type_id CastableIdent
  1139. #else
  1140. #define DECLARE_CASTABLE friend class Type_info
  1141. #endif
  1142.  
  1143. #define DECLARE_STREAMABLE( exp, cls, ver )                         \
  1144.     DECLARE_CASTABLE;                                               \
  1145.     DECLARE_STREAMER( exp, cls, ver );                              \
  1146.     DECLARE_STREAMABLE_OPS( cls );                                  \
  1147.     DECLARE_STREAMABLE_CTOR( cls )
  1148.  
  1149. #define DECLARE_STREAMABLE_FROM_BASE( exp, cls, base )              \
  1150.     DECLARE_CASTABLE;                                               \
  1151.     DECLARE_STREAMER_FROM_BASE( exp, cls, base );                   \
  1152.     DECLARE_STREAMABLE_OPS( cls );                                  \
  1153.     DECLARE_STREAMABLE_CTOR( cls )
  1154.  
  1155. #define DECLARE_ABSTRACT_STREAMABLE( exp, cls, ver )                \
  1156.     DECLARE_CASTABLE;                                               \
  1157.     DECLARE_ABSTRACT_STREAMER( exp, cls, ver );                     \
  1158.     DECLARE_STREAMABLE_OPS( cls );                                  \
  1159.     DECLARE_STREAMABLE_CTOR( cls )
  1160.  
  1161.  
  1162. #if !defined( BI_NO_RTTI )
  1163.  
  1164. #define IMPLEMENT_CASTABLE( cls )
  1165. #define IMPLEMENT_CASTABLE1( cls, base1 )
  1166. #define IMPLEMENT_CASTABLE2( cls, base1, base2 )
  1167. #define IMPLEMENT_CASTABLE3( cls, base1, base2, base3 )
  1168. #define IMPLEMENT_CASTABLE4( cls, base1, base2, base3, base4 )
  1169. #define IMPLEMENT_CASTABLE5( cls, base1, base2, base3, base4, base5 )
  1170.  
  1171. #else   // BI_NO_RTTI
  1172.  
  1173. #define IMPLEMENT_CASTABLE_ID( cls )                                \
  1174. TStreamableBase::Type_id cls::CastableIdent = #cls;                 \
  1175. TStreamableBase::Type_id cls::CastableID() const                    \
  1176. {                                                                   \
  1177.     return cls::CastableIdent;                                      \
  1178. }                                                                   \
  1179.  
  1180. #define IMPLEMENT_CASTABLE( cls )                                   \
  1181. IMPLEMENT_CASTABLE_ID( cls );                                       \
  1182. void *cls::FindBase( Type_id id ) const                             \
  1183. {                                                                   \
  1184.     return (strcmp( id, CastableIdent ) == 0) ? (void *)this : 0;   \
  1185. }                                                                   \
  1186.  
  1187.                                                                     \
  1188. #define IMPLEMENT_CASTABLE1( cls, base1 )                           \
  1189. IMPLEMENT_CASTABLE_ID( cls );                                       \
  1190. void *cls::FindBase( Type_id id ) const                             \
  1191. {                                                                   \
  1192.     if(strcmp( id, CastableIdent ) == 0)                            \
  1193.         return (void *)this;                                        \
  1194.     else                                                            \
  1195.         return base1::FindBase(id);                                 \
  1196. }                                                                   \
  1197.  
  1198. #define IMPLEMENT_CASTABLE2( cls, base1, base2 )                    \
  1199. IMPLEMENT_CASTABLE_ID( cls );                                       \
  1200. void *cls::FindBase( Type_id id ) const                             \
  1201. {                                                                   \
  1202.     void *res = 0;                                                  \
  1203.     if(strcmp( id, CastableIdent ) == 0)                            \
  1204.         return (void *)this;                                        \
  1205.     else if( (res = base1::FindBase(id)) != 0 )                     \
  1206.         return res;                                                 \
  1207.     else if( (res = base2::FindBase(id)) != 0 )                     \
  1208.         return res;                                                 \
  1209.     else                                                            \
  1210.         return 0;                                                   \
  1211. }                                                                   \
  1212.  
  1213. #define IMPLEMENT_CASTABLE3( cls, base1, base2, base3 )             \
  1214. IMPLEMENT_CASTABLE_ID( cls );                                       \
  1215. void *cls::FindBase( Type_id id ) const                             \
  1216. {                                                                   \
  1217.     void *res = 0;                                                  \
  1218.     if(strcmp( id, CastableIdent ) == 0)                            \
  1219.         return (void *)this;                                        \
  1220.     else if( (res = base1::FindBase(id)) != 0 )                     \
  1221.         return res;                                                 \
  1222.     else if( (res = base2::FindBase(id)) != 0 )                     \
  1223.         return res;                                                 \
  1224.     else if( (res = base3::FindBase(id)) != 0 )                     \
  1225.         return res;                                                 \
  1226.     else                                                            \
  1227.         return 0;                                                   \
  1228. }                                                                   \
  1229.  
  1230. #define IMPLEMENT_CASTABLE4( cls, base1, base2, base3, base4 )      \
  1231. IMPLEMENT_CASTABLE_ID( cls );                                       \
  1232. void *cls::FindBase( Type_id id ) const                             \
  1233. {                                                                   \
  1234.     void *res = 0;                                                  \
  1235.     if(strcmp( id, CastableIdent ) == 0)                            \
  1236.         return (void *)this;                                        \
  1237.     else if( (res = base1::FindBase(id)) != 0 )                     \
  1238.         return res;                                                 \
  1239.     else if( (res = base2::FindBase(id)) != 0 )                     \
  1240.         return res;                                                 \
  1241.     else if( (res = base3::FindBase(id)) != 0 )                     \
  1242.         return res;                                                 \
  1243.     else if( (res = base4::FindBase(id)) != 0 )                     \
  1244.         return res;                                                 \
  1245.     else                                                            \
  1246.         return 0;                                                   \
  1247. }                                                                   \
  1248.  
  1249. #define IMPLEMENT_CASTABLE5( cls, base1, base2, base3, base4, base5 )\
  1250. IMPLEMENT_CASTABLE_ID( cls );                                       \
  1251. void *cls::FindBase( Type_id id ) const                             \
  1252. {                                                                   \
  1253.     void *res = 0;                                                  \
  1254.     if(strcmp( id, CastableIdent ) == 0)                            \
  1255.         return (void *)this;                                        \
  1256.     else if( (res = base1::FindBase(id)) != 0 )                     \
  1257.         return res;                                                 \
  1258.     else if( (res = base2::FindBase(id)) != 0 )                     \
  1259.         return res;                                                 \
  1260.     else if( (res = base3::FindBase(id)) != 0 )                     \
  1261.         return res;                                                 \
  1262.     else if( (res = base4::FindBase(id)) != 0 )                     \
  1263.         return res;                                                 \
  1264.     else if( (res = base5::FindBase(id)) != 0 )                     \
  1265.         return res;                                                 \
  1266.     else                                                            \
  1267.         return 0;                                                   \
  1268. }                                                                   \
  1269.  
  1270. #endif  // BI_NO_RTTI
  1271.  
  1272. #if defined( BI_NO_RTTI )
  1273. #   define IMPLEMENT_STREAMABLE_CLASS( cls )    \
  1274.     TStreamableClass r ## cls( cls::CastableIdent, &cls::Streamer::Build )
  1275. #else
  1276. #   define IMPLEMENT_STREAMABLE_CLASS( cls )    \
  1277.     TStreamableClass r ## cls( typeid(cls).name(), &cls::Streamer::Build )
  1278. #endif
  1279.  
  1280. #define IMPLEMENT_STREAMABLE_POINTER( cls )                         \
  1281. ipstream& cls::readPtr( ipstream& is, cls*& cl )                    \
  1282.     {                                                               \
  1283.     TStreamableBase *temp = 0;                                      \
  1284.     is.readObjectPointer( temp );                                   \
  1285.     cl = TYPESAFE_DOWNCAST(temp,cls);                               \
  1286.     return is;                                                      \
  1287.     }                                                               \
  1288. ipstream& cls::readRef( ipstream& is, cls& cl )                     \
  1289.     {                                                               \
  1290.     TStreamableBase *ptr = &cl;                                     \
  1291.     is.readObject( ptr );                                           \
  1292.     return is;                                                      \
  1293.     }                                                               \
  1294. opstream& cls::writeRef( opstream& os, const cls& cl )              \
  1295.     {                                                               \
  1296.     os.writeObject( &cl );                                          \
  1297.     return os;                                                      \
  1298.     }                                                               \
  1299. opstream& cls::writePtr( opstream& os, const cls* cl )              \
  1300.     {                                                               \
  1301.     os.writeObjectPointer( cl );                                    \
  1302.     return os;                                                      \
  1303.     }
  1304.  
  1305. #define IMPLEMENT_STREAMER( cls )                                             \
  1306. cls::Streamer::Streamer( TStreamableBase *obj ) :                   \
  1307.     TNewStreamer(obj), object(TYPESAFE_DOWNCAST(obj,cls)){}
  1308.                                                                     \
  1309. #define IMPLEMENT_STREAMABLE_CTOR( cls )                            \
  1310. cls::cls ( StreamableInit ) {}
  1311.  
  1312. #define IMPLEMENT_STREAMABLE_CTOR1( cls, base1 )                    \
  1313. cls::cls ( StreamableInit ) : base1( streamableInit ) {}
  1314.  
  1315. #define IMPLEMENT_STREAMABLE_CTOR2( cls, base1, base2 )             \
  1316. cls::cls ( StreamableInit ) :                                       \
  1317.     base1 ( streamableInit ),                                       \
  1318.     base2 ( streamableInit ) {}
  1319.  
  1320. #define IMPLEMENT_STREAMABLE_CTOR3( cls, base1, base2, base3 )      \
  1321. cls::cls ( StreamableInit ) :                                       \
  1322.     base1 ( streamableInit ),                                       \
  1323.     base2 ( streamableInit ),                                       \
  1324.     base3 ( streamableInit ) {}
  1325.  
  1326. #define IMPLEMENT_STREAMABLE_CTOR4( cls, base1, base2, base3, base4 )\
  1327. cls::cls ( StreamableInit ) :                                       \
  1328.     base1 ( streamableInit ),                                       \
  1329.     base2 ( streamableInit ),                                       \
  1330.     base3 ( streamableInit ),                                       \
  1331.     base4 ( streamableInit ) {}
  1332.  
  1333. #define IMPLEMENT_STREAMABLE_CTOR5( cls, base1,base2,base3,base4,base5)\
  1334. cls::cls ( StreamableInit ) :                                       \
  1335.     base1 ( streamableInit ),                                       \
  1336.     base2 ( streamableInit ),                                       \
  1337.     base3 ( streamableInit ),                                       \
  1338.     base4 ( streamableInit ),                                       \
  1339.     base5 ( streamableInit ) {}
  1340.  
  1341. /*  Standard Combinations of Streamable Implementations */
  1342.  
  1343. #define IMPLEMENT_ABSTRACT_STREAMABLE( cls )                        \
  1344. IMPLEMENT_STREAMER( cls );                                          \
  1345. IMPLEMENT_STREAMABLE_CTOR( cls );                                   \
  1346. IMPLEMENT_STREAMABLE_POINTER( cls )
  1347.  
  1348. #define IMPLEMENT_ABSTRACT_STREAMABLE1( cls, base1 )                \
  1349. IMPLEMENT_STREAMER( cls );                                          \
  1350. IMPLEMENT_STREAMABLE_CTOR1( cls, base1 );                           \
  1351. IMPLEMENT_STREAMABLE_POINTER( cls )
  1352.  
  1353. #define IMPLEMENT_ABSTRACT_STREAMABLE2( cls, base1, base2 )         \
  1354. IMPLEMENT_STREAMER( cls );                                          \
  1355. IMPLEMENT_STREAMABLE_CTOR2( cls, base1, base2 );                    \
  1356. IMPLEMENT_STREAMABLE_POINTER( cls )
  1357.  
  1358. #define IMPLEMENT_ABSTRACT_STREAMABLE3( cls, base1, base2, base3 )  \
  1359. IMPLEMENT_STREAMER( cls );                                          \
  1360. IMPLEMENT_STREAMABLE_CTOR3( cls, base1, base2, base3 );             \
  1361. IMPLEMENT_STREAMABLE_POINTER( cls )
  1362.  
  1363. #define IMPLEMENT_ABSTRACT_STREAMABLE4( cls, base1, base2, base3, base4 )\
  1364. IMPLEMENT_STREAMER( cls );                                          \
  1365. IMPLEMENT_STREAMABLE_CTOR4( cls, base1, base2, base3, base4 );      \
  1366. IMPLEMENT_STREAMABLE_POINTER( cls )
  1367.  
  1368. #define IMPLEMENT_ABSTRACT_STREAMABLE5( cls, base1, base2, base3, base4, base5 )\
  1369. IMPLEMENT_STREAMER( cls );                                          \
  1370. IMPLEMENT_STREAMABLE_CTOR5( cls, base1, base2, base3, base4, base5 );\
  1371. IMPLEMENT_STREAMABLE_POINTER( cls )
  1372.  
  1373. #define IMPLEMENT_STREAMABLE( cls )                                 \
  1374. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1375. IMPLEMENT_ABSTRACT_STREAMABLE( cls )
  1376.  
  1377. #define IMPLEMENT_STREAMABLE1( cls, base1 )                         \
  1378. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1379. IMPLEMENT_ABSTRACT_STREAMABLE1( cls, base1 )
  1380.  
  1381. #define IMPLEMENT_STREAMABLE2( cls, base1, base2 )                  \
  1382. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1383. IMPLEMENT_ABSTRACT_STREAMABLE2( cls, base1, base2 )
  1384.  
  1385. #define IMPLEMENT_STREAMABLE3( cls, base1, base2, base3 )           \
  1386. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1387. IMPLEMENT_ABSTRACT_STREAMABLE3( cls, base1, base2, base3 )
  1388.  
  1389. #define IMPLEMENT_STREAMABLE4( cls, base1, base2, base3, base4 )    \
  1390. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1391. IMPLEMENT_ABSTRACT_STREAMABLE4( cls, base1, base2, base3, base4 )
  1392.  
  1393. #define IMPLEMENT_STREAMABLE5( cls, base1, base2, base3, base4, base5 )\
  1394. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1395. IMPLEMENT_ABSTRACT_STREAMABLE5( cls, base1, base2, base3, base4, base5 )
  1396.  
  1397. #define IMPLEMENT_STREAMABLE_FROM_BASE( cls, base1 )                \
  1398. IMPLEMENT_STREAMABLE_CLASS( cls );                                  \
  1399. IMPLEMENT_STREAMABLE_CTOR1( cls, base1 );                           \
  1400. IMPLEMENT_STREAMABLE_POINTER( cls )
  1401.  
  1402. #if defined( BI_CLASSLIB_NO_po )
  1403. #pragma option -po.
  1404. #endif
  1405.  
  1406. #endif  // __CLASSLIB_OBJSTRM_H
  1407.  
  1408.