nitroshare / qmdnsengine

Multicast DNS library for Qt applications
MIT License
81 stars 40 forks source link

ProviderPrivate desctructor is unsafe #11

Open vekkuli opened 5 years ago

vekkuli commented 5 years ago

The Provider/ProviderPrivate class destructor causes a crash in certain cases. See the destructor below:

ProviderPrivate::~ProviderPrivate()
{
    if (confirmed) {
        farewell();
    }
}

The farewell() function then proceeds to use the server member variable. This causes a crash if the objects are not deleted in correct order. The example/doc code

QMdnsEngine::Server server;
QMdnsEngine::Hostname hostname(&server);
QMdnsEngine::Provider provider(&server, &hostname);

is safe because the destructors of local objects are called in the reverse order of their constructors (~Provider() --> ~Hostname() --> ~Server()). The following, perhaps as surprise to many however, is not:

QMdnsEngine::Server* mServer = new QMdnsEngine::Server(this);
QMdnsEngine::Hostname* mHostname = new QMdnsEngine::Hostname(mServer, this);
QMdnsEngine::Provider* mProvider = new QMdnsEngine::Provider(mServer, mHostname, this);

because the QObject children are deleted in a different order (~Server() --> ~Hostname() --> ~Provider()).

The problem is trivial to go around by forcing the deletion order but I think proper Qt integration and QObject conformance would require supporting the natural QObject child object deletion order as well.

KonstantinRitt commented 3 years ago

https://github.com/nitroshare/qmdnsengine/issues/21 seems to be related