How can I return info from a callback?

Avery Rozar avery.rozar at insecure-it.com
Mon Jul 25 09:47:24 PDT 2016


That you very much for your reply.

On Mon, Jul 25, 2016 at 12:15 PM, Dan Williams <dcbw at redhat.com> wrote:
> On Fri, 2016-07-22 at 17:27 -0400, Avery Rozar wrote:
>> I wrote a class to get all the available bands for a given wireless
>> interface. I add a callback function to the socket and send it.
>> Inside my callback function I parse for the available bands and print
>> them to the console.
>>
>> How would I return a vector or something else to be used in the class
>> that is calling the class to get the bands? Am I looking at this
>> wrong? I can't get this info in nl_recvmsgs_default can I?
>>
>>
>> Channel Selection Class:
>>
>> int fs_channelSelection::selectChannels(unsigned int
>> *networkDeviceId) {
>>     fs_nl80211 *nl80211 = new fs_nl80211;
>>     vector<uint32_t> band_list;
>>     band_list = nl80211->getBands(networkDeviceId);
>> }
>>
>>
>> fs_nls80211 Class:
>>
>> vector<uint32_t> fs_nl80211::getBands(unsigned int *networkDeviceId)
>> {
>>     // omit code for brevity
>>
>>     // add callback info to the netlink socket
>>     nl_socket_modify_cb((nl_sock *) netlink_sk, NL_CB_VALID,
>> NL_CB_CUSTOM, getBandsCallback, NULL);
>
> The NULL here is the key; it's a void* that's passed directly to
> getBandsCallback().  So you'd create some structure to pass information
> back and forth at the top of getBands(), and then pass a pointer to
> that structure as the last argument to nl_socket_modify_cb().
>
> Then in getBandsCallback() you'll get that pointer as the "void*"
> argument, and you populate that structure with whatever you want to
> pass back.  Then when control returns to getBands() the structure will
> be populated and you'll have the info you want.
>
> Obviously, keep an eye on memory/object ownership and be sure to
> release the memory from the structure (and its members) when
> appropriate.
>
> Dan
>
>>     // construct the message to nlcore
>>     genlmsg_put((nl_msg *) netlink_msg, 0, NL_AUTO_SEQ, nl80211_id,
>> 0,
>> 0, NL80211_CMD_GET_WIPHY, 0);
>>     NLA_PUT_U32((nl_msg *) netlink_msg, NL80211_ATTR_IFINDEX,
>> *networkDeviceId);
>>
>>     // send the message to netlink socket
>>     nl_send_auto((nl_sock *) netlink_sk, (nl_msg *) netlink_msg);
>>
>>     // receive the message
>>     nl_recvmsgs_default((nl_sock *) netlink_sk);
>>     nl_wait_for_ack((nl_sock *) netlink_sk);
>> }
>>
>>
>> getBandsCallback function:
>>
>> static int getBandsCallback(struct nl_msg *msg, void *args) {
>>     // omit code for brevity
>>
>>     struct nlattr *tb_band[NL80211_BAND_ATTR_MAX + 1];
>>     vector<uint32_t> band_list;
>>
>>     // omit code for brevity
>>     // omit code for brevity
>>
>>                     if (!tb_freq[NL80211_FREQUENCY_ATTR_FREQ])
>>                         continue;
>>                     freq =
>> nla_get_u32(tb_freq[NL80211_FREQUENCY_ATTR_FREQ]);
>>                     band_list.push_back(freq);
>>
>>     // omit code for brevity
>>
>>     // I'd like to be able to do this in the Channel Selection Class:
>>     for(auto const& value: band_list) {
>>         cout << value << endl;
>>
>>     }
>> }
>>
>>
>> Thank you,
>> Avery Rozar
>>
>> _______________________________________________
>> libnl mailing list
>> libnl at lists.infradead.org
>> http://lists.infradead.org/mailman/listinfo/libnl



More information about the libnl mailing list