diff options
author | Samuel Ortiz <sameo@linux.intel.com> | 2013-11-18 01:42:46 +0100 |
---|---|---|
committer | Samuel Ortiz <sameo@linux.intel.com> | 2013-11-18 01:42:46 +0100 |
commit | b7f624308f1b5f3169d23f8607c5821bc38ad673 (patch) | |
tree | 3449e29571812672886518d88f2d99fa916d32ab | |
parent | 6f542a7fff3807252c4cbdb4407d0374215a29e8 (diff) | |
download | neard-b7f624308f1b5f3169d23f8607c5821bc38ad673.tar.gz neard-b7f624308f1b5f3169d23f8607c5821bc38ad673.tar.bz2 neard-b7f624308f1b5f3169d23f8607c5821bc38ad673.zip |
netlink: Expose NL_CB_FINISH handler
In some cases (e.g. multipart messages) it is interesting to know when a
messages is finished. Some multipart messages can carry a NULL payload
and without having a NL_CB_FINISH handler, neard never knows when it's
actually finished.
-rw-r--r-- | src/netlink.c | 32 |
1 files changed, 27 insertions, 5 deletions
diff --git a/src/netlink.c b/src/netlink.c index 38d66d6..936f65a 100644 --- a/src/netlink.c +++ b/src/netlink.c @@ -68,6 +68,12 @@ struct nlnfc_state { static struct nlnfc_state *nfc_state; static GIOChannel *netlink_channel = NULL; +struct send_msg_data { + void *data; + int *done; + int (*finish_handler)(struct nl_msg *, void *); +}; + static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err, void *arg) { @@ -80,13 +86,17 @@ static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err, return NL_STOP; } -static int finish_handler(struct nl_msg *msg, void *arg) +static int __finish_handler(struct nl_msg *msg, void *arg) { - int *ret = arg; + struct send_msg_data *data = arg; + DBG(""); - *ret = 1; + if (data->finish_handler) + data->finish_handler(msg, data->data); + + *(data->done) = 1; return NL_SKIP; } @@ -102,12 +112,14 @@ static int ack_handler(struct nl_msg *msg, void *arg) return NL_STOP; } -static int nl_send_msg(struct nl_sock *sock, struct nl_msg *msg, +static int __nl_send_msg(struct nl_sock *sock, struct nl_msg *msg, int (*rx_handler)(struct nl_msg *, void *), + int (*finish_handler)(struct nl_msg *, void *), void *data) { struct nl_cb *cb; int err, done; + struct send_msg_data send_data; DBG(""); @@ -124,9 +136,12 @@ static int nl_send_msg(struct nl_sock *sock, struct nl_msg *msg, } err = done = 0; + send_data.done = &done; + send_data.data = data; + send_data.finish_handler = finish_handler; + nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, __finish_handler, &send_data); nl_cb_err(cb, NL_CB_CUSTOM, error_handler, &err); - nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, finish_handler, &done); nl_cb_set(cb, NL_CB_ACK, NL_CB_CUSTOM, ack_handler, &done); if (rx_handler) @@ -140,6 +155,13 @@ static int nl_send_msg(struct nl_sock *sock, struct nl_msg *msg, return err; } +static inline int nl_send_msg(struct nl_sock *sock, struct nl_msg *msg, + int (*rx_handler)(struct nl_msg *, void *), + void *data) +{ + return __nl_send_msg(sock, msg, rx_handler, NULL, data); +} + static int get_devices_handler(struct nl_msg *n, void *arg) { struct nlmsghdr *nlh = nlmsg_hdr(n); |