Boost logo

Boost Users :

From: Robbie Morrison (robbie_at_[hidden])
Date: 2007-09-07 14:09:53


Hi all

In order to assist my troubleshooting, I wrote a free
function called 'extraArchiveWhat' which adds to the
sometimes obscure (to me anyway) comments thrown by
Boost.Serialization.

John Pye-4 wrote:

> Vaguely related comment on your problem. I was also recently seeing this
> "unregistered void cast" runtime error. As far as I could tell it was a
> problem relating to my ordering and placement of "#include
> <boost/archive/text_oarchive.hpp> (or ditto iarchive), and "#include
> <boost/serialization/export.hpp> as well as calls to BOOST_CLASS_EXPORT.
>
> It was nothing to do with my use of void_cast_register, which in fact I
> don't use anywhere in any of my code.
>
> So FWIW I think that this error message is not particularly helpful or
> well-worded.

Here is my client code first (the typedef enables me to
switch between text, XML, and platform-specific binary):

8<--------------------------------------

  typedef boost::archive::xml_oarchive output_archive_type;
  const char* cfilename = filename.c_str(); // convert to C-style string
  ...
  try
    {
      std::ifstream ifs(cfilename, std::ios::binary);
      if ( !ifs ) // see note below
        {
          std::cout << "** ofstream open failed: " << cfilename
                    << std::endl;
        }
      input_archive_type ar(ifs); // see above typedef
      ar & boost::serialization::make_nvp("container", container);
    }
  catch (const boost::archive::archive_exception& ae)
    {
      std::cout << "** boost::archive load exception"
                << ": " << __FILE__ << ":" << __LINE__ << ":" << __func__
                << ": " << ae.what() << "\n"
                << " " << extraArchiveWhat(ae.what())
                << std::endl;
    }

-------------------------------------->8

Note that C++ stream io operations do not throw
exceptions. Each stream keeps its own mask of error
bits known as its "io state", accessible via rdstate().
In addition, each stream object can also be treated as
a Boolean value representing good (true) or faulty
(false).

Note too that __FILE__, __LINE__, and __func__ are
built-in macros which give the current source file
name, line number, and invoked call, respectively.

Now the helper function itself:

8<--------------------------------------

  std::string // an interpretation based on my experiences
  extraArchiveWhat
  (const std::string what) // that is, the string returned by what()
  {
    std::string ret = "no local interpretation";
    if ( what == "coding error" )
      ret = "Boost.Serialization library problem";
    else if ( what == "unrecognized XML syntax" )
      ret = "name-value-pair name contains illegal chars including whitespace?";
    else if ( what == "unregistered class" )
      ret = "missing BOOST_CLASS_EXPORT(SubClass) macro?";
    else if ( what == "unregistered void cast" )
      ret = "missing ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(BaseClass) statement?";
    else if ( what == "stream error" )
      ret = "asymmetric serialization, including attempt to load empty archive?";
    ret = "(" + ret + ")"; // add parentheses
    return ret;
  }

-------------------------------------->8

Hence a typical message might read:

  ** boost::archive load exception: main.cpp:101:main: unregistered void cast
     (missing ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(BaseClass) statement?)

Finally, here is a list of possible exceptions copied
(with minor tweaks) from the relevant Boost.Serialization
headers:

// From <boost/archive archive_exception.hpp>
//
// "programming error" [in Boost.Serialization, that is]
//
// "unregistered class" : attempt to serialize a pointer
// of an an unregistered class
//
// "invalid signature" : first line of archive does not
// contain expected string
//
// "unsupported version" : archive created with library
// version subsequent to this one
//
// "pointer conflict" : an attempt has been made to
// directly serialize an object after having
// already serialized the same object through a
// pointer -- were this permitted, it the archive
// load would result in the creation of extraneous
// object
//
// "incompatible native format" : attempt to read native
// binary format on incompatible platform
//
// "array size too short" : array being loaded doesn't
// fit in array allocated
//
// "stream error": i/o error on stream
//
// "class name too long" : class name greater than the
// maximum permitted -- most likely a corrupted archive
// or an attempt to insert a virus via buffer overrun method
//
// "unregistered void cast" : base - derived relationship not
// registered with void_cast_register
//
// From <boost/archive/basic_xml_archive.hpp>
//
// "unrecognized XML syntax" : archive doesn't contain
// expected data
//
// "XML start/end tag mismatch" : start/end tag in archive
// doesn't match program
//
// "Invalid XML tag name" : tag name contains
// invalid characters

cheers, Robbie

---
Robbie Morrison
PhD student -- policy-oriented energy system simulation
Institute for Energy Engineering (IET)
Technical University of Berlin (TU-Berlin), Germany
[from IMAP client]

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