Re:[boost] Re: Re:Serialization17 - assert in basic_text_oarchive.hpp

Jeff Flinn wrote:
Another data point. I've separated binary/text/xml serialization into three .cpp files so that each of the three compilation units only deals with a single archive type.
No doubt that works around the issue but it doesn't make ME feel much better. The problem of "confused" template parameters was a big one with VC 6.0 . I had hoped all those issues had been resolved with VC 7.1. Now I'm not so sure. I did make a small example which included several archive types but I had no problem with it so I'm kind of stuck.
The following results:
Save Load
---- ----
Bin Pass Pass Txt Pass Pass Xml Pass Fail
Where Fail is an assertion in basic_xml_archive.ipp Line: 29.
Attached is the offending xml archive, if it will offer any insight.
This is most likely a bug of my own in generating/parsing xml archives. Again, I'm going to need a smaller test case. However, your example does illustrate the need to replace the assertions with exceptions in case the XML has been tampered with - I'll add these in. Robert Ramey

I've been corresponding privately with Robert for a while about the serialization library and he's encouraged me to start contributing to this forum. Recently I've been looking at using shared_ptr with the serialization tools as this is core to how I plan to use the library. We found that it was fine to serialize a shared_ptr<A> which held an A*. However, if there were a derived class B which was a public A then it wasn't possible to serialize a shared_ptr<A> which held a B* into an archive. The workaround for this, was to do this... BOOST_CLASS_EXPORT(boost::detail::sp_counted_base_impl< B*, boost::checked_deleter<B> >) That seems to give the library enough information to be able to serialize a shared_ptr<A> that holds a B*. To save typing I now use a macro HACK_SERIALIZATION_EXPORT_SHARED_POINTER(T) which is included in the attached file. Now let me introduce a new problem. I seem to have uncovered another bug. Using the workaround above I can demonstrate expected behaviour with text archives. However, if I try to serialize a shared_ptr<A> containing a B* to a BINARY archive then I get an assertion failure (puzzlingly in basic_text_oarchive.hpp - line 133). I don't have any problems serializing shared_ptr<A>s containing A*s to binary archives, and I don't have any problems at all with text archives. The file I've attached is a heavily modified version of demo_shared_ptr.cpp which performs four tests: 1. Serialize shared_ptr<A>s containing A*s to and from text archives. 2. Serialize shared_ptr<A>s containing B*s to and from text archives. 3. Serialize shared_ptr<A>s containing A*s to and from binary archives. 4. Serialize shared_ptr<A>s containing B*s to and from binary archives. Tests 1-3 all work fine. Test 4 fails as described. I'd appreciate it if others with an interest in the serialization library could take a look. I can quite believe that it's an error on my part but I haven't been able to spot it yet. DT

I know that recently some changes have been made to the serialization library to make it raise exceptions on error rather than fail assertions. In particular, at line #300 of boost/serialization/oserializer.hpp an unregistered_class exception is now thrown when the type information system hasn't heard of the class which is to be serialized. I think we could go further to aid debugging if the archive_exception class had another data member which could be used to store the name of the class which couldn't be written. We'd have something like this instead... boost::throw_exception( boost::archive::archive_exception( boost::archive::archive_exception::unregistered_class, typeid(*(&t)).name() // THIS IS THE NEW BIT ) ); When catching the exception what() would be able to return "unregistered class: my_derived_class" rather than just "unregistered class". When you've got a few dozen different classes to serialize through pointers to base classes it would make it a lot easier to find out which one you haven't registered properly. Of course, this does assume that RTTI is available on all our platforms. Is that an assumption we can make? If not, could we revert to the current behaviour on platforms which don't have it? Do the other users of the serialization library have a strong point of view on this? DT

[The first time I pointed this, I forgot to add the attachment...] I've been corresponding privately with Robert for a while about the serialization library and he's encouraged me to start contributing to this forum. Recently I've been looking at using shared_ptr with the serialization tools as this is core to how I plan to use the library. We found that it was fine to serialize a shared_ptr<A> which held an A*. However, if there were a derived class B which was a public A then it wasn't possible to serialize a shared_ptr<A> which held a B* into an archive. The workaround for this, was to do this... BOOST_CLASS_EXPORT(boost::detail::sp_counted_base_impl< B*, boost::checked_deleter<B> >) That seems to give the library enough information to be able to serialize a shared_ptr<A> that holds a B*. To save typing I now use a macro HACK_SERIALIZATION_EXPORT_SHARED_POINTER(T) which is included in the attached file. Now let me introduce a new problem. I seem to have uncovered another bug. Using the workaround above I can demonstrate expected behaviour with text archives. However, if I try to serialize a shared_ptr<A> containing a B* to a BINARY archive then I get an assertion failure (puzzlingly in basic_text_oarchive.hpp - line 133). I don't have any problems serializing shared_ptr<A>s containing A*s to binary archives, and I don't have any problems at all with text archives. The file I've attached is a heavily modified version of demo_shared_ptr.cpp which performs four tests: 1. Serialize shared_ptr<A>s containing A*s to and from text archives. 2. Serialize shared_ptr<A>s containing B*s to and from text archives. 3. Serialize shared_ptr<A>s containing A*s to and from binary archives. 4. Serialize shared_ptr<A>s containing B*s to and from binary archives. Tests 1-3 all work fine. Test 4 fails as described. I'd appreciate it if others with an interest in the serialization library could take a look. I can quite believe that it's an error on my part but I haven't been able to spot it yet. DT

"David Tonge" <david.tonge@davidtonge.com> wrote
Tests 1-3 all work fine. Test 4 fails as described.
I'd appreciate it if others with an interest in the serialization library could take a look. I can quite believe that it's an error on my part but I haven't been able to spot it yet.
I didn't look deeper into it yet but test 4 fails for me as well (with Intel C++ 7.0 and old Dinkumware). (As coincidence it helped to find and fix Intel C++ 7 ICE.) I was not able to compile it so far on BCB. /Pavel
participants (3)
-
David Tonge
-
Pavel Vozenilek
-
Robert Ramey