#include <errno.h>
#include <time.h>
#include <sys/uio.h>
+#include <linux/if_addrlabel.h>
+#include <linux/if_bridge.h>
#include "libnetlink.h"
return rtnl_open_byproto(rth, subscriptions, NETLINK_ROUTE);
}
+int rtnl_addrdump_req(struct rtnl_handle *rth, int family)
+{
+ struct {
+ struct nlmsghdr nlh;
+ struct ifaddrmsg ifm;
+ } req = {
+ .nlh.nlmsg_len = sizeof(req),
+ .nlh.nlmsg_type = RTM_GETADDR,
+ .nlh.nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST,
+ .nlh.nlmsg_seq = rth->dump = ++rth->seq,
+ .ifm.ifa_family = family,
+ };
+
+ return send(rth->fd, &req, sizeof(req), 0);
+}
+
+int rtnl_addrlbldump_req(struct rtnl_handle *rth, int family)
+{
+ struct {
+ struct nlmsghdr nlh;
+ struct ifaddrlblmsg ifal;
+ } req = {
+ .nlh.nlmsg_len = sizeof(req),
+ .nlh.nlmsg_type = RTM_GETADDRLABEL,
+ .nlh.nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST,
+ .nlh.nlmsg_seq = rth->dump = ++rth->seq,
+ .ifal.ifal_family = family,
+ };
+
+ return send(rth->fd, &req, sizeof(req), 0);
+}
+
+int rtnl_routedump_req(struct rtnl_handle *rth, int family)
+{
+ struct {
+ struct nlmsghdr nlh;
+ struct rtmsg rtm;
+ } req = {
+ .nlh.nlmsg_len = sizeof(req),
+ .nlh.nlmsg_type = RTM_GETROUTE,
+ .nlh.nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST,
+ .nlh.nlmsg_seq = rth->dump = ++rth->seq,
+ .rtm.rtm_family = family,
+ };
+
+ return send(rth->fd, &req, sizeof(req), 0);
+}
+
+int rtnl_mdbdump_req(struct rtnl_handle *rth, int family)
+{
+ struct {
+ struct nlmsghdr nlh;
+ struct br_port_msg bpm;
+ } req = {
+ .nlh.nlmsg_len = sizeof(req),
+ .nlh.nlmsg_type = RTM_GETMDB,
+ .nlh.nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST,
+ .nlh.nlmsg_seq = rth->dump = ++rth->seq,
+ .bpm.family = family,
+ };
+
+ return send(rth->fd, &req, sizeof(req), 0);
+}
+
int rtnl_wilddump_request(struct rtnl_handle *rth, int family, int type)
{
return rtnl_wilddump_req_filter(rth, family, type, RTEXT_FILTER_VF);
msg.msg_iovlen = 1;
i = 0;
while (1) {
-next:
status = rtnl_recvmsg(rtnl->fd, &msg, &buf);
++i;
if (l < sizeof(struct nlmsgerr)) {
fprintf(stderr, "ERROR truncated\n");
- } else if (!err->error) {
+ free(buf);
+ return -1;
+ }
+
+ if (!err->error)
/* check messages from kernel */
nl_dump_ext_ack(h, errfn);
+ else {
+ errno = -err->error;
- if (answer)
- *answer = (struct nlmsghdr *)buf;
- else
- free(buf);
- if (h->nlmsg_seq == seq)
- return 0;
- else if (i < iovlen)
- goto next;
- return 0;
+ if (rtnl->proto != NETLINK_SOCK_DIAG &&
+ show_rtnl_err)
+ rtnl_talk_error(h, err, errfn);
}
- if (rtnl->proto != NETLINK_SOCK_DIAG &&
- show_rtnl_err)
- rtnl_talk_error(h, err, errfn);
+ if (answer)
+ *answer = (struct nlmsghdr *)buf;
+ else
+ free(buf);
- errno = -err->error;
- free(buf);
- return -i;
+ return err->error ? -i : 0;
}
if (answer) {