tambre
tambre

Reputation: 4853

Get a pointer pointer for a smart pointer

I have a smart pointer for an object, that I need to pass to a method, that only accepts a pointer pointer.

Here's an example, where the original smart pointer loses the ownership.

int main(int argc, char* argv[])
{
    std::unique_pointer<pcap_if_t> object;

    auto object_pointer = object.get();
    pcap_findalldevs(&object_pointer, ...); // The unique_ptr loses ownership after being passed to the function
}

How would I accomplish this, without the original smart pointer losing the pointer ownership?

EDIT:
The function I'm calling is pcap_findalldevs in libpcap. I'm afraid that the function might be the cause of losing ownership.
I have updated my code example to reflect the what I actually do.

Upvotes: 5

Views: 2319

Answers (3)

n. m. could be an AI
n. m. could be an AI

Reputation: 119867

You don't need any of this. This is the correct calling sequence:

 pcap_if_t ip = nullptr;
 res = pcap_findalldevs(&ip, errbuf);
 // now ip (hopefully) points to something

There's no place for a smart pointer to anything before the call. Now after the call you can assign ip to some kind of smart pointer. Don't forget a custom deleter, you will need it.

Note that ip actually points to a linked list implemented with plain raw dumb honest pointers, which you cannot change. Utility of a smart pointer to the head of the list is questionable at best. It would probably make sense to copy the information to a suitable C++ container and dispose of the linked list right after the call.

Upvotes: 2

Revolver_Ocelot
Revolver_Ocelot

Reputation: 8785

Function which takes pointer to pointer usually does so because it might change it, and pcap_findalldevs is indeed does that. And that pointer should be released with call to pcap_freealldevs.

So your best bet is unique_ptr with custom deleter aquiring ownership from raw pointer:

struct pcap_deleter
{
    void operator()(pcap_if_t* ptr) 
    {
        pcap_freealldevs(ptr);
    }
};

//...
using pcap_ptr = std::unique_ptr<pcap_if_t, pcap_deleter> 
pcap_ptr get_devs() {
    pcap_if_t* object_pointer;
    pcap_findalldevs(&object_pointer, ...); 
    return pcap_ptr(object_pointer);
}

//...

auto object = get_devs();

Upvotes: 6

Richard Hodges
Richard Hodges

Reputation: 69864

Here's an example, where the original smart pointer loses the ownership.

Nope. The unique_ptr retains ownership after a call to get()

unique_ptr will lose ownership after a call to release()

reference: http://en.cppreference.com/w/cpp/memory/unique_ptr

Upvotes: 3

Related Questions