KAME people started putting multicast addresses in the routing table.
But since it hasn't been designed for that they used workarounds.
I believe it's time to embrace and consolidate this choice.
. The first reason is that multicast address are not going away from
the routing table, thanks to IPv6.
. The second reason is that using the routing table for mcast group
lookup would make them MP-safe for free.
. Finally adding joined groups in the routing table would allow user
to see which multicast addresses are accepted by which interface.
Since we are already late in the 6.0 release cycle I don't plan to change
much for now. However Aaron Riekenberg reported [0] a leak due to one
of the existing workaround. The proper way to fix the leak would be to
introduce the RTF_MULTICAST flag and use it instead of RTF_CLONING.
Diff below does that and reuses the 'm' marker for displaying such route
entries in route(8) and netstat(1). Man page bits are for the moment
missing.
Comments? Oks?
[0] http://marc.info/?l=openbsd-misc&m=146676764030238&w=2
Index: sys/net/route.h
===================================================================
RCS file: /cvs/src/sys/net/route.h,v
retrieving revision 1.138
diff -u -p -r1.138 route.h
--- sys/net/route.h 14 Jun 2016 09:48:52 -0000 1.138
+++ sys/net/route.h 5 Jul 2016 14:28:22 -0000
@@ -131,7 +131,7 @@ struct rtentry {
#define RTF_DONE 0x40 /* message confirmed */
#define RTF_MASK 0x80 /* subnet mask present */
#define RTF_CLONING 0x100 /* generate new routes on use */
-/* 0x200 unused */
+#define RTF_MULTICAST 0x200 /* route associated to a mcast addr. */
#define RTF_LLINFO 0x400 /* generated by ARP or ND */
#define RTF_STATIC 0x800 /* manually added */
#define RTF_BLACKHOLE 0x1000 /* just discard pkts (during updates) */
Index: sys/netinet/if_ether.c
===================================================================
RCS file: /cvs/src/sys/netinet/if_ether.c,v
retrieving revision 1.216
diff -u -p -r1.216 if_ether.c
--- sys/netinet/if_ether.c 28 Jun 2016 17:18:24 -0000 1.216
+++ sys/netinet/if_ether.c 5 Jul 2016 14:34:10 -0000
@@ -139,7 +139,7 @@ arp_rtrequest(struct ifnet *ifp, int req
timeout_add_sec(&arptimer_to, 1);
}
- if (rt->rt_flags & (RTF_GATEWAY|RTF_BROADCAST))
+ if (ISSET(rt->rt_flags, RTF_GATEWAY|RTF_BROADCAST|RTF_MULTICAST))
return;
switch (req) {
Index: sys/netinet6/in6.c
===================================================================
RCS file: /cvs/src/sys/netinet6/in6.c,v
retrieving revision 1.188
diff -u -p -r1.188 in6.c
--- sys/netinet6/in6.c 5 Jul 2016 10:17:14 -0000 1.188
+++ sys/netinet6/in6.c 5 Jul 2016 14:19:36 -0000
@@ -757,8 +757,7 @@ in6_update_ifa(struct ifnet *ifp, struct
info.rti_info[RTAX_GATEWAY] = sin6tosa(&ia6->ia_addr);
info.rti_info[RTAX_NETMASK] = sin6tosa(&mltmask);
info.rti_info[RTAX_IFA] = sin6tosa(&ia6->ia_addr);
- /* XXX: we need RTF_CLONING to fake nd6_rtrequest */
- info.rti_flags = RTF_CLONING;
+ info.rti_flags = RTF_MULTICAST;
error = rtrequest(RTM_ADD, &info, RTP_CONNECTED, NULL,
ifp->if_rdomain);
if (error)
@@ -814,7 +813,7 @@ in6_update_ifa(struct ifnet *ifp, struct
info.rti_info[RTAX_GATEWAY] = sin6tosa(&ia6->ia_addr);
info.rti_info[RTAX_NETMASK] = sin6tosa(&mltmask);
info.rti_info[RTAX_IFA] = sin6tosa(&ia6->ia_addr);
- info.rti_flags = RTF_CLONING;
+ info.rti_flags = RTF_MULTICAST;
error = rtrequest(RTM_ADD, &info, RTP_CONNECTED, NULL,
ifp->if_rdomain);
if (error)
Index: sys/netinet6/nd6.c
===================================================================
RCS file: /cvs/src/sys/netinet6/nd6.c,v
retrieving revision 1.186
diff -u -p -r1.186 nd6.c
--- sys/netinet6/nd6.c 15 Jun 2016 11:49:34 -0000 1.186
+++ sys/netinet6/nd6.c 5 Jul 2016 14:34:55 -0000
@@ -882,7 +882,7 @@ nd6_rtrequest(struct ifnet *ifp, int req
dr->installed = 0;
}
- if ((rt->rt_flags & RTF_GATEWAY) != 0)
+ if (ISSET(rt->rt_flags, RTF_GATEWAY|RTF_MULTICAST))
return;
if (nd6_need_cache(ifp) == 0 && (rt->rt_flags & RTF_HOST) == 0) {
Index: sbin/route/show.c
===================================================================
RCS file: /cvs/src/sbin/route/show.c,v
retrieving revision 1.103
diff -u -p -r1.103 show.c
--- sbin/route/show.c 27 Nov 2015 16:26:52 -0000 1.103
+++ sbin/route/show.c 5 Jul 2016 14:18:24 -0000
@@ -78,8 +78,8 @@ static const struct bits bits[] = {
{ RTF_DYNAMIC, 'D' },
{ RTF_MODIFIED, 'M' },
{ RTF_DONE, 'd' }, /* Completed -- for routing messages only */
- { RTF_MASK, 'm' }, /* Mask Present -- for routing messages only */
{ RTF_CLONING, 'C' },
+ { RTF_MULTICAST,'m' },
{ RTF_LLINFO, 'L' },
{ RTF_STATIC, 'S' },
{ RTF_PROTO1, '1' },
Index: usr.bin/netstat/show.c
===================================================================
RCS file: /cvs/src/usr.bin/netstat/show.c,v
retrieving revision 1.49
diff -u -p -r1.49 show.c
--- usr.bin/netstat/show.c 11 Sep 2015 20:10:26 -0000 1.49
+++ usr.bin/netstat/show.c 5 Jul 2016 14:20:05 -0000
@@ -78,8 +78,8 @@ static const struct bits bits[] = {
{ RTF_DYNAMIC, 'D' },
{ RTF_MODIFIED, 'M' },
{ RTF_DONE, 'd' }, /* Completed -- for routing messages only */
- { RTF_MASK, 'm' }, /* Mask Present -- for routing messages only */
{ RTF_CLONING, 'C' },
+ { RTF_MULTICAST,'m' },
{ RTF_LLINFO, 'L' },
{ RTF_STATIC, 'S' },
{ RTF_PROTO1, '1' },
Index: usr.sbin/route6d/route6d.c
===================================================================
RCS file: /cvs/src/usr.sbin/route6d/route6d.c,v
retrieving revision 1.86
diff -u -p -r1.86 route6d.c
--- usr.sbin/route6d/route6d.c 25 Jan 2016 05:15:43 -0000 1.86
+++ usr.sbin/route6d/route6d.c 5 Jul 2016 14:24:03 -0000
@@ -2319,45 +2319,16 @@ do { \
RTFLAG("D", RTF_DYNAMIC);
RTFLAG("M", RTF_MODIFIED);
RTFLAG("d", RTF_DONE);
-#ifdef RTF_MASK
- RTFLAG("m", RTF_MASK);
-#endif
+ RTFLAG("m", RTF_MULTICAST);
RTFLAG("C", RTF_CLONING);
-#ifdef RTF_CLONED
RTFLAG("c", RTF_CLONED);
-#endif
-#ifdef RTF_PRCLONING
- RTFLAG("c", RTF_PRCLONING);
-#endif
-#ifdef RTF_WASCLONED
- RTFLAG("W", RTF_WASCLONED);
-#endif
RTFLAG("L", RTF_LLINFO);
RTFLAG("S", RTF_STATIC);
RTFLAG("B", RTF_BLACKHOLE);
-#ifdef RTF_PROTO3
RTFLAG("3", RTF_PROTO3);
-#endif
RTFLAG("2", RTF_PROTO2);
RTFLAG("1", RTF_PROTO1);
-#ifdef RTF_BROADCAST
RTFLAG("b", RTF_BROADCAST);
-#endif
-#ifdef RTF_DEFAULT
- RTFLAG("d", RTF_DEFAULT);
-#endif
-#ifdef RTF_ISAROUTER
- RTFLAG("r", RTF_ISAROUTER);
-#endif
-#ifdef RTF_TUNNEL
- RTFLAG("T", RTF_TUNNEL);
-#endif
-#ifdef RTF_AUTH
- RTFLAG("A", RTF_AUTH);
-#endif
-#ifdef RTF_CRYPT
- RTFLAG("E", RTF_CRYPT);
-#endif
#undef RTFLAG
return buf;
}
Index: share/man/man4/route.4
===================================================================
RCS file: /cvs/src/share/man/man4/route.4,v
retrieving revision 1.40
diff -u -p -r1.40 route.4
--- share/man/man4/route.4 23 Mar 2016 12:57:53 -0000 1.40
+++ share/man/man4/route.4 5 Jul 2016 14:22:27 -0000
@@ -358,6 +358,7 @@ Flags include the values:
#define RTF_DONE 0x40 /* message confirmed */
#define RTF_MASK 0x80 /* subnet mask present */
#define RTF_CLONING 0x100 /* generate new routes on use */
+#define RTF_MULTICAST 0x200 /* route associated to a mcast addr. */
#define RTF_LLINFO 0x400 /* generated by ARP or NDP */
#define RTF_STATIC 0x800 /* manually added */
#define RTF_BLACKHOLE 0x1000 /* just discard pkts (during updates) */