diff options
author | Donald Sharp <sharpd@cumulusnetworks.com> | 2015-10-29 14:35:12 +0100 |
---|---|---|
committer | Donald Sharp <sharpd@cumulusnetwroks.com> | 2016-05-26 02:38:35 +0200 |
commit | c992c9a0c0840b7f5b94f221c3a34aaf6bc4f500 (patch) | |
tree | 6a54c43fdfac5afff7e946791462db6a71d68f31 /pimd/pim_iface.c | |
parent | pimd: Fix some file inclusion issues. (diff) | |
download | frr-c992c9a0c0840b7f5b94f221c3a34aaf6bc4f500.tar.xz frr-c992c9a0c0840b7f5b94f221c3a34aaf6bc4f500.zip |
pimd: Create special pimreg interface
The linux kernel wants a pimreg vif device. The pimd
code wants a 'struct interface *' for anything it works
with. Since the pimreg vif device is not a real linux
device that zebra knows about. Cheat by creating
a pimreg interface pointer and setup the code to
properly be able to handle the registration of the vif
device.
Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
Diffstat (limited to 'pimd/pim_iface.c')
-rw-r--r-- | pimd/pim_iface.c | 28 |
1 files changed, 23 insertions, 5 deletions
diff --git a/pimd/pim_iface.c b/pimd/pim_iface.c index e9e1b491d..985a7588a 100644 --- a/pimd/pim_iface.c +++ b/pimd/pim_iface.c @@ -41,6 +41,8 @@ #include "pim_time.h" #include "pim_ssmpingd.h" +struct interface *pim_regiface = NULL; + static void pim_if_igmp_join_del_all(struct interface *ifp); void pim_if_init() @@ -145,8 +147,6 @@ struct pim_interface *pim_if_new(struct interface *ifp, int igmp, int pim) pim_sock_reset(ifp); - zassert(PIM_IF_TEST_PIM(pim_ifp->options) || PIM_IF_TEST_IGMP(pim_ifp->options)); - if (PIM_MROUTE_IS_ENABLED) { pim_if_add_vif(ifp); } @@ -615,6 +615,7 @@ int pim_if_add_vif(struct interface *ifp) { struct pim_interface *pim_ifp = ifp->info; struct in_addr ifaddr; + unsigned char flags; zassert(pim_ifp); @@ -640,14 +641,15 @@ int pim_if_add_vif(struct interface *ifp) } ifaddr = pim_ifp->primary_address; - if (PIM_INADDR_IS_ANY(ifaddr)) { + if (ifp->ifindex != PIM_OIF_PIM_REGISTER_VIF && PIM_INADDR_IS_ANY(ifaddr)) { zlog_warn("%s: could not get address for interface %s ifindex=%d", __PRETTY_FUNCTION__, ifp->name, ifp->ifindex); return -4; } - if (pim_mroute_add_vif(ifp->ifindex, ifaddr, 0)) { + flags = (ifp->ifindex == PIM_OIF_PIM_REGISTER_VIF) ? VIFF_REGISTER : 0; + if (pim_mroute_add_vif(ifp->ifindex, ifaddr, flags)) { /* pim_mroute_add_vif reported error */ return -5; } @@ -657,7 +659,8 @@ int pim_if_add_vif(struct interface *ifp) /* Update highest vif_index */ - if (pim_ifp->mroute_vif_index > qpim_mroute_oif_highest_vif_index) { + if (pim_ifp->mroute_vif_index != PIM_OIF_PIM_REGISTER_VIF && + pim_ifp->mroute_vif_index > qpim_mroute_oif_highest_vif_index) { qpim_mroute_oif_highest_vif_index = pim_ifp->mroute_vif_index; } @@ -1197,3 +1200,18 @@ void pim_if_update_assert_tracking_desired(struct interface *ifp) pim_ifchannel_update_assert_tracking_desired(ch); } } + +/* + * PIM wants to have an interface pointer for everything it does. + * The pimreg is a special interface that we have that is not + * quite an inteface but a VIF is created for it. + */ +void pim_if_create_pimreg (void) +{ + if (!pim_regiface) { + pim_regiface = if_create("pimreg", strlen("pimreg")); + pim_regiface->ifindex = PIM_OIF_PIM_REGISTER_VIF; + + pim_if_new(pim_regiface, 0, 0); + } +} |