summaryrefslogtreecommitdiff
path: root/zebra/if_netlink.c
diff options
context:
space:
mode:
Diffstat (limited to 'zebra/if_netlink.c')
-rw-r--r--zebra/if_netlink.c31
1 files changed, 31 insertions, 0 deletions
diff --git a/zebra/if_netlink.c b/zebra/if_netlink.c
index acec2db526..a46657dd2e 100644
--- a/zebra/if_netlink.c
+++ b/zebra/if_netlink.c
@@ -21,6 +21,8 @@
#include <zebra.h>
+#ifdef GNU_LINUX
+
/* The following definition is to workaround an issue in the Linux kernel
* header files with redefinition of 'struct in6_addr' in both
* netinet/in.h and linux/in6.h.
@@ -768,6 +770,33 @@ int interface_lookup_netlink(struct zebra_ns *zns)
return 0;
}
+int kernel_interface_set_master(struct interface *master,
+ struct interface *slave)
+{
+ struct zebra_ns *zns = zebra_ns_lookup(NS_DEFAULT);
+
+ struct {
+ struct nlmsghdr n;
+ struct ifinfomsg ifa;
+ char buf[NL_PKT_BUF_SIZE];
+ } req;
+
+ memset(&req, 0, sizeof req);
+
+ req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg));
+ req.n.nlmsg_flags = NLM_F_REQUEST;
+ req.n.nlmsg_type = RTM_SETLINK;
+ req.n.nlmsg_pid = zns->netlink_cmd.snl.nl_pid;
+
+ req.ifa.ifi_index = slave->ifindex;
+
+ addattr_l(&req.n, sizeof req, IFLA_MASTER, &master->ifindex, 4);
+ addattr_l(&req.n, sizeof req, IFLA_LINK, &slave->ifindex, 4);
+
+ return netlink_talk(netlink_talk_filter, &req.n, &zns->netlink_cmd, zns,
+ 0);
+}
+
/* Interface address modification. */
static int netlink_address(int cmd, int family, struct interface *ifp,
struct connected *ifc)
@@ -1218,3 +1247,5 @@ void interface_list(struct zebra_ns *zns)
{
interface_lookup_netlink(zns);
}
+
+#endif /* GNU_LINUX */