Date: Mon, 17 May 2004 00:36:29 +0800 From: Eugene Grosbein <eugen@grosbein.pp.ru> To: bug-followup@freebsd.org Cc: net@freebsd.org Subject: Re: bin/51927: routed(8) fails to use multicast with IFF_POINTOPOINT interfaces Message-ID: <20040516163629.GA2271@grosbein.pp.ru>
next in thread | raw e-mail | index | archive | help
Reply-To: Hi! ip(4) man page says that IP_MULTICAST_IF, IP_ADD_MEMBERSHIP etc. must use local IP address of desired interface. There are (at least) two undersirable consequents: 1) It is hard (if not impossible) to distinguish between "unnumbered" IFF_POINTOPOINT interfaces, those share the same local IP address with an ethernet interface (think of pppd and proxyarp). 2) routed, zebra and quagga cannot currently use outgoing RIPv2 multicasts with IFF_POINTOPOINT interfaces (ppp, gif etc.) at least in 4-STABLE. There was an attempt to fix this by modifying INADDR_TO_IFP: http://www.freebsd.org/cgi/cvsweb.cgi/src/sys/netinet/in_var.h#rev1.7 It was unsuccessful and Ruslan undid it: http://www.freebsd.org/cgi/cvsweb.cgi/src/sys/netinet/in_var.h#rev1.39 However, we still need working RIPv2: http://www.freebsd.org/cgi/query-pr.cgi?pr=bin/51927 Presently there are only two consumers of INADDR_TO_IFP in a 4.x kernel: ipfw[2] and ip_multicast_if() in src/sys/netinet/ip_output.h, the latter is exactly what prevents routed and ripd to enable multicasts on IFF_POINTOPOINT. Another attempt to fix that is presented. The next patch introduces another macro INADDR_TO_IFP_P2P that is used by ip_multicast_if() when INADDR_TO_IFP does not find ifp. --- in_var.h.orig Sat Dec 15 03:09:34 2001 +++ in_var.h Sun May 16 23:51:14 2004 @@ -117,6 +117,20 @@ (ifp) = (ia == NULL) ? NULL : ia->ia_ifp; \ } +#define INADDR_TO_IFP_P2P(addr, ifp) \ + /* struct in_addr addr; */ \ + /* struct ifnet *ifp; */ \ +{ \ + struct in_ifaddr *ia; \ +\ + TAILQ_FOREACH(ia, &in_ifaddrhead, ia_link) \ + if ((ia->ia_ifp->if_flags & IFF_POINTOPOINT) && \ + IA_DSTSIN(ia)->sin_addr.s_addr == (addr).s_addr) { \ + break; \ + } \ + (ifp) = (ia == NULL) ? NULL : ia->ia_ifp; \ +} + /* * Macro for finding the internet address structure (in_ifaddr) corresponding * to a given interface (ifnet structure). --- sys/netinet/ip_output.c.orig Fri May 14 18:51:35 2004 +++ sys/netinet/ip_output.c Fri May 14 20:40:49 2004 @@ -1785,6 +1785,9 @@ *ifindexp = ifindex; } else { INADDR_TO_IFP(*a, ifp); + if (ifp == NULL) { + INADDR_TO_IFP_P2P(*a, ifp); + } } return ifp; } I think this can be improved by introducing another hash for remote IPs of IFF_POINTOPOINT intefaces (similar to in_ifaddrhashtbl) to avoid linear search but leave that for later stage. Eugene Grosbein
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20040516163629.GA2271>