I have these two classes (let's call them A
and B
) that both include boost/archive and boost/serialization files. These includes are in my hpp files (with header guards) for each of the two classes. Class A
(and other parts of the code base) include class B
and as such repeats the exact same includes.
From my understanding the header guards in the boost library should be preventing the library files from being included a second time here; but that appears not to be the case. I have even gone as far as putting another header guard around the include bloc just to make sure it wouldn't be included multiple times; and yet at linkage I get a multiple definition's error.
Includes in class A
:
#ifndef _A_H
#define _A_H
// Other none boost includes for class A
#ifndef _BOOST_INCLUDES_
#define _BOOST_INCLUDES_
#include <boost/archive/binary_iarchive.hpp>
#include <boost/archive/binary_oarchive.hpp>
#include <boost/serialization/access.hpp>
#include <boost/serialization/export.hpp>
#include <boost/serialization/binary_object.hpp>
#include <boost/serialization/base_object.hpp>
#include <boost/serialization/vector.hpp>
#include <boost/serialization/string.hpp>
#endif
class A{/*...*/};
And class B
has the same include block (and _BOOST_INCLUDES_
guard) in its header file. Other parts of the code also include class A
or class B
at some point, but the problem stems from something in the includes here.
Why is this happening (and how could I fix it)? Why aren't the boost header guards stopping this second inclusion? Could this have nothing to do with the code itself but rather be a build problem?
Makefile extract:
BOOST_ROOT := myPathToBoost/boost_1_75_0/
BOOST_LIBS := -L$(BOOST_ROOT)stage/lib/ -lboost_serialization
BOOST := -I $(BOOST_ROOT) $(BOOST_LIBS)
$(CM_OBJS): $(CM_SOURCES)
$(CC) $(FLAGS) -MMD $(BOOST) -c $(INCLUDES) -o $@ $< $(LIBS)
The linker error is:
/usr/bin/ld: /projectPath/build/clientMain.o:(.bss+0x0): multiple definition of `boost::archive::detail::extra_detail::init_guid<EndGame>::g'; /projectPath/build/Register.o:(.bss+0x0): first defined here
And this message repeats for every include; with the file names varying, and the contents of ::init_guid<X>
varying as well.
Indeed putting BOOST_CLASS_EXPORT
in a header file leads to multiply defined symbols as soon as you have included the header file into more than one translation unit (think .cpp file).
In absence of your code, I have many full examples on this site. I'd search like "user:85371 boost_class_export_key":
Most of them have multi-file live demos online and included in the answer text.