]> git.proxmox.com Git - mirror_frr.git/blobdiff - zebra/kernel_netlink.c
Merge pull request #1813 from donaldsharp/pbr_setup
[mirror_frr.git] / zebra / kernel_netlink.c
index 7fc2d613328c2f20cf9b507de197f5b2f25ea355..52b26920901bada0982a9d5ce77451c07117f688 100644 (file)
@@ -20,6 +20,8 @@
 
 #include <zebra.h>
 
+#ifdef HAVE_NETLINK
+
 #include "linklist.h"
 #include "if.h"
 #include "log.h"
 #include "zebra/zserv.h"
 #include "zebra/zebra_ns.h"
 #include "zebra/zebra_vrf.h"
+#include "zebra/rt.h"
 #include "zebra/debug.h"
 #include "zebra/kernel_netlink.h"
 #include "zebra/rt_netlink.h"
 #include "zebra/if_netlink.h"
+#include "zebra/rule_netlink.h"
 
 #ifndef SO_RCVBUFFORCE
 #define SO_RCVBUFFORCE  (33)
@@ -82,6 +86,9 @@ static const struct message nlmsg_str[] = {{RTM_NEWROUTE, "RTM_NEWROUTE"},
                                           {RTM_NEWNEIGH, "RTM_NEWNEIGH"},
                                           {RTM_DELNEIGH, "RTM_DELNEIGH"},
                                           {RTM_GETNEIGH, "RTM_GETNEIGH"},
+                                          {RTM_NEWRULE, "RTM_NEWRULE"},
+                                          {RTM_DELRULE, "RTM_DELRULE"},
+                                          {RTM_GETRULE, "RTM_GETRULE"},
                                           {0}};
 
 static const struct message rtproto_str[] = {
@@ -185,7 +192,7 @@ static int netlink_socket(struct nlsock *nl, unsigned long groups,
                return -1;
        }
 
-       sock = socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
+       sock = ns_socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE, ns_id);
        if (sock < 0) {
                zlog_err("Can't open %s socket: %s", nl->name,
                         safe_strerror(errno));
@@ -237,31 +244,28 @@ static int netlink_information_fetch(struct sockaddr_nl *snl,
        switch (h->nlmsg_type) {
        case RTM_NEWROUTE:
                return netlink_route_change(snl, h, ns_id, startup);
-               break;
        case RTM_DELROUTE:
                return netlink_route_change(snl, h, ns_id, startup);
-               break;
        case RTM_NEWLINK:
                return netlink_link_change(snl, h, ns_id, startup);
-               break;
        case RTM_DELLINK:
                return netlink_link_change(snl, h, ns_id, startup);
-               break;
        case RTM_NEWADDR:
                return netlink_interface_addr(snl, h, ns_id, startup);
-               break;
        case RTM_DELADDR:
                return netlink_interface_addr(snl, h, ns_id, startup);
-               break;
        case RTM_NEWNEIGH:
                return netlink_neigh_change(snl, h, ns_id);
-               break;
        case RTM_DELNEIGH:
                return netlink_neigh_change(snl, h, ns_id);
-               break;
+       case RTM_NEWRULE:
+               return netlink_rule_change(snl, h, ns_id, startup);
+       case RTM_DELRULE:
+               return netlink_rule_change(snl, h, ns_id, startup);
        default:
-               zlog_warn("Unknown netlink nlmsg_type %d vrf %u\n",
-                         h->nlmsg_type, ns_id);
+               if (IS_ZEBRA_DEBUG_KERNEL)
+                       zlog_debug("Unknown netlink nlmsg_type %d vrf %u\n",
+                                  h->nlmsg_type, ns_id);
                break;
        }
        return 0;
@@ -673,16 +677,21 @@ int netlink_talk(int (*filter)(struct sockaddr_nl *, struct nlmsghdr *, ns_id_t,
 {
        int status;
        struct sockaddr_nl snl;
-       struct iovec iov = {.iov_base = (void *)n, .iov_len = n->nlmsg_len};
-       struct msghdr msg = {
-               .msg_name = (void *)&snl,
-               .msg_namelen = sizeof snl,
-               .msg_iov = &iov,
-               .msg_iovlen = 1,
-       };
+       struct iovec iov;
+       struct msghdr msg;
        int save_errno;
 
        memset(&snl, 0, sizeof snl);
+       memset(&iov, 0, sizeof iov);
+       memset(&msg, 0, sizeof msg);
+
+       iov.iov_base = n;
+       iov.iov_len = n->nlmsg_len;
+       msg.msg_name = (void *)&snl;
+       msg.msg_namelen = sizeof snl;
+       msg.msg_iov = &iov;
+       msg.msg_iovlen = 1;
+
        snl.nl_family = AF_NETLINK;
 
        n->nlmsg_seq = ++nl->seq;
@@ -779,7 +788,8 @@ void kernel_init(struct zebra_ns *zns)
        /* Initialize netlink sockets */
        groups = RTMGRP_LINK | RTMGRP_IPV4_ROUTE | RTMGRP_IPV4_IFADDR
                 | RTMGRP_IPV6_ROUTE | RTMGRP_IPV6_IFADDR | RTMGRP_IPV4_MROUTE
-                | RTMGRP_NEIGH;
+                | RTMGRP_NEIGH
+                | RTNLGRP_IPV4_RULE | RTNLGRP_IPV6_RULE;
 
        snprintf(zns->netlink.name, sizeof(zns->netlink.name),
                 "netlink-listen (NS %u)", zns->ns_id);
@@ -826,3 +836,5 @@ void kernel_terminate(struct zebra_ns *zns)
                zns->netlink_cmd.sock = -1;
        }
 }
+
+#endif /* HAVE_NETLINK */