diff options
Diffstat (limited to 'netlink_callbacks.c')
-rw-r--r-- | netlink_callbacks.c | 66 |
1 files changed, 66 insertions, 0 deletions
diff --git a/netlink_callbacks.c b/netlink_callbacks.c new file mode 100644 index 0000000..5e0f34e --- /dev/null +++ b/netlink_callbacks.c @@ -0,0 +1,66 @@ +/* + * Copyright 2012 Daniel Drown <dan-android@drown.org> + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * netlink_callbacks.c - generic callbacks for netlink responses + */ +#include <netinet/in.h> +#include <net/if.h> + +#include <linux/rtnetlink.h> +#include <netlink/handlers.h> +#include <netlink/msg.h> + +/* function: ack_handler + * generic netlink callback for ack messages + * msg - netlink message + * data - pointer to an int, stores the success code + */ +static int ack_handler(struct nl_msg *msg, void *data) { + int *retval = data; + *retval = 0; + return NL_OK; +} + +/* function: error_handler + * generic netlink callback for error messages + * nla - error source + * err - netlink error message + * arg - pointer to an int, stores the error code + */ +static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err, void *arg) { + int *retval = arg; + if(err->error < 0) { + *retval = err->error; + } else { + *retval = 0; // NLMSG_ERROR used as reply type on no error + } + return NL_OK; +} + +/* function: alloc_ack_callbacks + * allocates a set of netlink callbacks. returns NULL on failure. callbacks will modify retval with <0 meaning failure + * retval - shared state between caller and callback functions + */ +struct nl_cb *alloc_ack_callbacks(int *retval) { + struct nl_cb *callbacks; + + callbacks = nl_cb_alloc(NL_CB_DEFAULT); + if(!callbacks) { + return NULL; + } + nl_cb_set(callbacks, NL_CB_ACK, NL_CB_CUSTOM, ack_handler, retval); + nl_cb_err(callbacks, NL_CB_CUSTOM, error_handler, retval); + return callbacks; +} |