samedi 2 septembre 2017

Using C++ shared pointer's aliasing constructor with an empty shared pointer

std::shared_ptr has an aliasing constructor that allows newly created shared_ptr to share state with an existing shared pointer while pointing to some other object.

I was thinking about abusing this constructor to put pointer to some global object inside shared_ptr:

int global = 0;

int main() 
{
    // because we point to global object we do not need to track its lifetime
    // so we use empty shared_ptr<void> as a provider of shared state
    std::shared_ptr<int> p(std::shared_ptr<void>(), &global);
    std::shared_ptr<int> pp = p; 
    return *pp;
}

My question is: Is it legal? The code successfully works on major compilers.

Note, that I do not ask if it's a good thing to do. I do understand that there's a canonical way of putting pointers to global objects into shared_ptr using no-op deleter. It is also a bit disturbing if it is legal, because it would be possible to have dereferenceable shared_ptr, weak pointers to which are always expired:

    std::shared_ptr<int> p(std::shared_ptr<void>(), &global);
    std::weak_ptr<int> w = p;
    if (p) // p is alive and well 
    {      // and w is not
        *w.lock(); // and here program crashes
    }

Aucun commentaire:

Enregistrer un commentaire