We recently had a great example of how misuse of virtual functions introduces errors.
There is a shared library that has a message handler:
class CMessageHandler { public: virtual void OnException( std::exception& e );
it is assumed that you can inherit this class and use it for custom error handling:
class YourMessageHandler : public CMessageHandler { public: virtual void OnException( std::exception& e ) {
The error handling mechanism uses the CMessageHandler* pointer, so it does not need the actual type of the object. The function is virtual, so whenever there is an overloaded version, the last one is called.
Cool huh Yes, that was until the developers of the shared library changed the base class:
class CMessageHandler { public: virtual void OnException( const std::exception& e );
... and the overloads just stopped working.
Do you see what happened? After changing the base class, overloads ceased to be overloads from the point of view of C ++ - they became new, other, unrelated functions.
The base class had a default implementation that was not marked as pure virtual, so derived classes were not forced to overload the default implementation. And finally, functon is called only in case of error handling, which is not used every time here and there. Thus, the error was introduced silently and for a long time went unnoticed.
The only way to eliminate it once and for all is to perform a search on the entire code base and edit all the relevant code fragments.
sharptooth Jun 16 2018-10-06T00: 00Z
source share