]> git.proxmox.com Git - mirror_frr.git/blobdiff - pimd/pim_msdp_socket.c
*: Actually allow end users to not build pbrd
[mirror_frr.git] / pimd / pim_msdp_socket.c
index 0ce09710122081e19de6d9224c3b43ec02a9424b..f245a043534af4557dca3210e35dfab4418e6906 100644 (file)
 #include <lib/sockunion.h>
 #include <lib/thread.h>
 #include <lib/vty.h>
+#include <lib/if.h>
+#include <lib/vrf.h>
 
 #include "pimd.h"
+#include "pim_sock.h"
 
 #include "pim_msdp.h"
 #include "pim_msdp_socket.h"
@@ -56,7 +59,7 @@ static void pim_msdp_update_sock_send_buffer_size(int fd)
 static int pim_msdp_sock_accept(struct thread *thread)
 {
        union sockunion su;
-       struct pim_msdp_listener *listener = THREAD_ARG(thread);
+       struct pim_instance *pim = THREAD_ARG(thread);
        int accept_sock;
        int msdp_sock;
        struct pim_msdp_peer *mp;
@@ -70,9 +73,9 @@ static int pim_msdp_sock_accept(struct thread *thread)
                zlog_err("accept_sock is negative value %d", accept_sock);
                return -1;
        }
-       listener->thread = NULL;
-       thread_add_read(master, pim_msdp_sock_accept, listener, accept_sock,
-                       &listener->thread);
+       pim->msdp.listener.thread = NULL;
+       thread_add_read(master, pim_msdp_sock_accept, pim, accept_sock,
+                       &pim->msdp.listener.thread);
 
        /* accept client connection. */
        msdp_sock = sockunion_accept(accept_sock, &su);
@@ -83,9 +86,9 @@ static int pim_msdp_sock_accept(struct thread *thread)
        }
 
        /* see if have peer config for this */
-       mp = pim_msdp_peer_find(su.sin.sin_addr);
+       mp = pim_msdp_peer_find(pim, su.sin.sin_addr);
        if (!mp || !PIM_MSDP_PEER_IS_LISTENER(mp)) {
-               ++msdp->rejected_accepts;
+               ++pim->msdp.rejected_accepts;
                if (PIM_DEBUG_MSDP_EVENTS) {
                        zlog_err("msdp peer connection refused from %s",
                                 sockunion2str(&su, buf, SU_ADDRSTRLEN));
@@ -117,15 +120,15 @@ static int pim_msdp_sock_accept(struct thread *thread)
 }
 
 /* global listener for the MSDP well know TCP port */
-int pim_msdp_sock_listen(void)
+int pim_msdp_sock_listen(struct pim_instance *pim)
 {
        int sock;
        int socklen;
        struct sockaddr_in sin;
        int rc;
-       struct pim_msdp_listener *listener = &msdp->listener;
+       struct pim_msdp_listener *listener = &pim->msdp.listener;
 
-       if (msdp->flags & PIM_MSDPF_LISTENER) {
+       if (pim->msdp.flags & PIM_MSDPF_LISTENER) {
                /* listener already setup */
                return 0;
        }
@@ -147,6 +150,23 @@ int pim_msdp_sock_listen(void)
        sockopt_reuseaddr(sock);
        sockopt_reuseport(sock);
 
+       if (pim->vrf_id != VRF_DEFAULT) {
+               struct interface *ifp =
+                       if_lookup_by_name(pim->vrf->name, pim->vrf_id);
+               if (!ifp) {
+                       zlog_err("%s: Unable to lookup vrf interface: %s",
+                                __PRETTY_FUNCTION__, pim->vrf->name);
+                       close(sock);
+                       return -1;
+               }
+               if (pim_socket_bind(sock, ifp)) {
+                       zlog_err("%s: Unable to bind to socket: %s",
+                                __PRETTY_FUNCTION__, safe_strerror(errno));
+                       close(sock);
+                       return -1;
+               }
+       }
+
        if (pimd_privs.change(ZPRIVS_RAISE)) {
                zlog_err("pim_msdp_socket: could not raise privs, %s",
                         safe_strerror(errno));
@@ -178,10 +198,10 @@ int pim_msdp_sock_listen(void)
        listener->fd = sock;
        memcpy(&listener->su, &sin, socklen);
        listener->thread = NULL;
-       thread_add_read(msdp->master, pim_msdp_sock_accept, listener, sock,
+       thread_add_read(pim->msdp.master, pim_msdp_sock_accept, pim, sock,
                        &listener->thread);
 
-       msdp->flags |= PIM_MSDPF_LISTENER;
+       pim->msdp.flags |= PIM_MSDPF_LISTENER;
        return 0;
 }
 
@@ -214,6 +234,23 @@ int pim_msdp_sock_connect(struct pim_msdp_peer *mp)
                return -1;
        }
 
+       if (mp->pim->vrf_id != VRF_DEFAULT) {
+               struct interface *ifp =
+                       if_lookup_by_name(mp->pim->vrf->name, mp->pim->vrf_id);
+               if (!ifp) {
+                       zlog_err("%s: Unable to lookup vrf interface: %s",
+                                __PRETTY_FUNCTION__, mp->pim->vrf->name);
+                       return -1;
+               }
+               if (pim_socket_bind(mp->fd, ifp)) {
+                       zlog_err("%s: Unable to bind to socket: %s",
+                                __PRETTY_FUNCTION__, safe_strerror(errno));
+                       close(mp->fd);
+                       mp->fd = -1;
+                       return -1;
+               }
+       }
+
        set_nonblocking(mp->fd);
 
        /* Set socket send buffer size */