Boost logo

Boost Users :

From: RIVASSEAU Jean Noel (JN.RIVASSEAU_at_[hidden])
Date: 2006-02-27 04:12:02


Again I forgot to include the code sorry...

 

  _____

De : boost-users-bounces_at_[hidden] [mailto:boost-users-bounces_at_[hidden]] De la part de Robert Ramey
Envoyé : vendredi 24 février 2006 17:53
À : boost-users_at_[hidden]
Objet : Re: [Boost-users] Serialization : unregistered_cast & otherquestions

 

 

        "RIVASSEAU Jean Noel" <JN.RIVASSEAU_at_[hidden]> wrote in message news:87F60F7FA02FF749AFB02BD9FCAA6B04DA737E_at_naserv31.nanterre.oberthurcs.com...

        Thanks for all your help. I have decided to try to reorganize everything into small parts as you have said, in order to better understand.

         

        I am in the process of doing this, but I have already some remarks about your comments.

         

        I have chosen the organisation principle you have said:

         

        in the class.h, nothing about the serialization is present

         

        in serialization/class_serialization.hh : I have the serialization declaration code + some traits

         

        in serialization/class_serialization.cc : I have the serialization implementation code + BOOST_EXPORT

         

        The only thing where I have not followed your advice is the presence of BOOST_EXPORT on the class_serialization.hh rather than class_serialization.cc.

         

        If I put it on the header, since I have to include the header on test.cc, one instantation of something is done while encountering BOOST_EXPORT. Later while compiling class_serialization.cc, since it encounters BOOST_EXPORT one more time another instantiation occurs and I had problems with linking (gcc 3.4 reported multiple definitions of something).

         

        ****

        OK - BOOST_EXPORT has some non-obvious behavior which I'll explain. Maybe this will help.

         

        BOOST_EXPORT has two functions:

         

        a) To associate a class with an external unique name (GUID)

        b) To instanticiate templated code for archives used.

         

        The second is not as obvious as it might seem. Suppose I have:

         

        class A {

        };

         

        class B : public A {

        }

         

        A * aptr = new B;

         

        text_archive ar;

         

        ar << a;

         

        The problem is that the compiler never sees anything like ar << b so it has no way to know that the

        serialization code for B needs to be instantiated for the archive class text_archive.

         

        So each archive class defines a special macro.

         

        Then BOOST_EXPORT instantiates code for each combination of the class and archive class. If this were

        not done, one would get a link error with undefined symbol for load<text_archive, B> or something lke that.

         

        Of course the above presumes that the archive classes are included BEFORE the serialization/boost/export.hpp

        header.

         

        So if you make the following changes in your code I believe you will get the desired results.

         

        a) Move BOOST_EXPORT to the class header.

         

        b) In test.cc - move the headers boost/archive/... above the headers boost/serialization/..

         

        and let me know that happens.

         

         

        Robert Ramey

         

         

        
  _____

        De : boost-users-bounces_at_[hidden] [mailto:boost-users-bounces_at_[hidden]] De la part de Robert Ramey
        Envoyé : jeudi 23 février 2006 17:44
        À : boost-users_at_[hidden]
        Objet : Re: [Boost-users] Serialization : unregistered_cast & otherquestions

         

        Without actually seeing the code, its hard for me to give intelligent advice. Lucky for

        you (maybe) that's not going to inhibit me from speculating. Here is what I recommend

        for anyone making a very large program:

         

        a) extended_type_info_no_rtti presumes that all classes serialized as pointers

        have been exported. Should this not be the case, you'll get the error message indicated.

        Double check this.

         

        b) Serilaization traits should be in the header files so that they are not "missed" anytime

        something like "ar << x" is invoked. Given you're situation I would recommend a file

        structure like the following:

         

        class.hpp - without seriaiization like you have now.

         

        serialization/class.hpp - includes class.hpp. also includes BOOST_EXPORT and any

        other traits for this "class".

         

        serialization/class.cpp c - includes serialization/class.hpp and includes the

        actual serialization code. Also this should include code instantiation for the archives that

        you use. Look at demo_pimpl to see how this is done.

         

        All the above code should be organized into a library. The reason is that this will generate

        code for all the archives mentioned but your application may not use all the archives so

        putting the above code in a library and linking to it will mean that your application will

        always have what it actuallyuses but nothing it doesn't - avoids "code bloat". Note that

        in compiling code for the library make sure to specify "function level linking".

         

        Take the "least derived class" - that one at the top of the class hierarchy. Make a small

        test program similar to the tests in the serialization library. This should be a very small

        job. This code can be class_test.cpp. Run this test on all archives you use. When

        this test passes, do the same for the other classes until something fails.

         

        This might seem to be more work - believe me its not. It will

         

        a) guarentee that you make progress toward a robust program

        b) give you confidence that your program has minimum of hidden bugs

        c) permit you to re-run the tests automatically when you make future changes.

        d) should a problem arise with the serialization or other library, it will give

        a lot more information in order to be helpful.

         

        Robert Ramey

         

                Now, the problem is where to put the serialization code for these classes. If I just write them on the implementation file (the .cc) for the class, it does not work. At run time I have always errors telling me that either the class is not exported (unregistered_class exception) or an unregistered_cast happens.

                 

                 

                 

                 

                The only solution I have found is to put *ALL* serialization code into the same big .cc file. If I do just that, it works. However this file is becoming enormous and has to be recompiled every time I change only *one* of the class to be serialized. It is already taking a minute to compile on a fast machine, so I must really break it up into other parts.

                 

                But everytime I do that everything stops working.

                 

                Have you any ideas, Robert? I am using extended_type_info_no_rtti, this may be the cause of the problem...

                 

                Jean-Noël

                 

                Ps: I still have the std::string bug, which is also uncomprehensible for me.

                
  _____

                _______________________________________________
                Boost-users mailing list
                Boost-users_at_[hidden]
                http://lists.boost.org/mailman/listinfo.cgi/boost-users

        
  _____

        _______________________________________________
        Boost-users mailing list
        Boost-users_at_[hidden]
        http://lists.boost.org/mailman/listinfo.cgi/boost-users





Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net