Undefined vtable reference - virtual member, classes created by gsoap

gsoap with its wsdl2h and soapcpp2 tools provided me with a soapStub.h file containing the following:

class SOAP_CMAC ns2__SOAPKunden { public: std::string *adresszusatz; // ... public: virtual int soap_type() const { return 7; } // ... ns2__SOAPKunden() : adresszusatz(NULL), x(NULL) { } // left out all member init. virtual ~ns2__SOAPKunden() { } }; 

I start with a small application that uses a class to populate objects with data from an informix database.

But for compilation, I have to leave all the virtual things successfully - I found a lot of messages about this error and the use of virtual members in subclasses - otherwise I get

 main.o: In function `ns2__SOAPKunden::ns2__SOAPKunden()': main.cpp:(.text._ZN15ns2__SOAPKundenC1Ev[ns2__SOAPKunden::ns2__SOAPKunden()]+0xf): undefined reference to `vtable for ns2__SOAPKunden' main.o: In function `ns2__SOAPKunden::~ns2__SOAPKunden()': main.cpp:(.text._ZN15ns2__SOAPKundenD1Ev[ns2__SOAPKunden::~ns2__SOAPKunden()]+0x13): undefined reference to `vtable for ns2__SOAPKunden' collect2: ld returned 1 exit status 

I admit that after several years of writing scripts, it is very difficult for me to understand C ++ code ... I want to ask for advice on what to try next. My class is not a derived class, for example, which makes me think.

+6
c ++ virtual vtable gsoap
source share
2 answers

An error means that the virtual table was not compiled / linked correctly in the final binary file (executable file or library). There are two general reasons leading to this error:

  • you do not link the object file containing the virtual table definitions --ie you compiled soapStub.cpp in soapStub.o but did not add this binary to the linker command line.
  • the compiler does not generate a virtual table anywhere, so even if you include all object files that do not include a virtual table.

The second case is the most difficult to identify for inexperienced developers and can be called by a class that is defined in the header and contains virtual functions. If all virtual functions are defined internally, the compiler will generate a virtual table in all translation units that include the header, and mark it as a weak character so that the linker can discard them, but if you add a new virtual method later and you leave it undefined in the header, or if you delete a definition from one of the virtual functions, the compiler will not generate a virtual table in each translation unit, but only in the one that defines these functions.

What you need to check:

  • you link all object files
  • either all virtual functions are defined in the class definition line, or you have a .cpp that defines virtual functions, and you bind this.
+14
source share

This is what David Rodriguez said is simply said easier, I think ...

I had this situation in my interface class:

 class IBase { public: virtual void begin(unsigned long); virtual void end(); virtual int available(void) = 0; virtual int peek(void) = 0; virtual int read(void) = 0; virtual void flush(void) = 0; } 

and changed it to the following:

 class IBase { public: virtual void begin(unsigned long) = 0; virtual void end() = 0; virtual int available(void) = 0; virtual int peek(void) = 0; virtual int read(void) = 0; virtual void flush(void) = 0; } 

who did the trick.

begin () and end () were defined in a derived class in another file, the IBase class (interface) was declared only in the header and included in several places.

The error from OP appeared only when I set the optimization to none (-O0), any other setting did not lead to an error (gcc 4.8).

0
source share

All Articles