If you want the C API to call a member function, you need to pass two pieces of data: the function (static member) and the object for which it must be called.
Typically, C API callbacks have some form of "user data", often void* , through which you can tunnel your object address:
// Beware, brain-compiled code ahead! typedef void (*callback)(int data, void* user_data); void f(callback cb, void* user_data); class cpp_callback { public: virtual ~cpp_callback() {} // sometimes needed void cb(int data) = 0; callback* get_callback() const {return &cb_;} private static void cb_(int data, void* user_data) { cpp_callback* that = reinterpret_cast<my_cpp_callback*>(user_Data); that->cb(data); } }; class my_callback { public: void cb(int data) { // deal with data } }; void g() { my_callback cb; f(cb.get_callback(), &cb); }
That pcapCallback does not look like it has user data, unless it is that param . If this is true, you will need to store the address of the callback object in some global variable before calling the API. Something like that:
// Beware, brain-compiled code ahead! typedef void (*callback)(int data); void f(callback cb); class cpp_callback { public: cpp_callback() : the_old_cb_(this) {std::swap(the_cb_,the_old_cb_);} virtual ~cpp_callback() {std::swap(the_cb_,the_old_cb_);} void cb(int data) = 0; callback* get_callback() const {return &cb_;} private static cpp_callback* the_cb_; cpp_callback* the_old_cb_; static void cb_(int data, void* user_data) { the_cb_->cb(data); } }; class my_callback { public: void cb(int data) { /* deal with data */ } }; void g() { my_callback cb; f(cb.get_callback(), &cb); }
As always with global data, it is dangerous if more than one callback instance is alive. I tried to minimize the harm so that it would work if their life time was invested. However, everything else will hurt.
source share