--- zzzz-none-000/linux-2.6.28.10/net/ipv4/igmp.c 2009-05-02 18:54:43.000000000 +0000 +++ puma5-6360-529/linux-2.6.28.10/net/ipv4/igmp.c 2009-10-23 13:23:35.000000000 +0000 @@ -113,7 +113,7 @@ #define IGMP_V1_Router_Present_Timeout (400*HZ) #define IGMP_V2_Router_Present_Timeout (400*HZ) -#define IGMP_Unsolicited_Report_Interval (10*HZ) +#define IGMP_Unsolicited_Report_Interval (1*HZ) #define IGMP_Query_Response_Interval (10*HZ) #define IGMP_Unsolicited_Report_Count 2 @@ -1176,6 +1176,7 @@ } /* else, v3 */ + if (im->sfmode == MCAST_EXCLUDE) im->crcount = in_dev->mr_qrv ? in_dev->mr_qrv : IGMP_Unsolicited_Report_Count; igmp_ifc_event(in_dev); @@ -1192,7 +1193,7 @@ * A socket has joined a multicast group on device dev. */ -void ip_mc_inc_group(struct in_device *in_dev, __be32 addr) +void ip_mc_inc_group_for_mode(struct in_device *in_dev, __be32 addr, int omode) { struct ip_mc_list *im; @@ -1201,7 +1202,7 @@ for (im=in_dev->mc_list; im; im=im->next) { if (im->multiaddr == addr) { im->users++; - ip_mc_add_src(in_dev, &addr, MCAST_EXCLUDE, 0, NULL, 0); + ip_mc_add_src(in_dev, &addr, omode, 0, NULL, 0); goto out; } } @@ -1215,9 +1216,15 @@ in_dev_hold(in_dev); im->multiaddr=addr; /* initial mode is (EX, empty) */ + if (omode == MCAST_EXCLUDE) { im->sfmode = MCAST_EXCLUDE; im->sfcount[MCAST_INCLUDE] = 0; im->sfcount[MCAST_EXCLUDE] = 1; + } else { + im->sfmode = MCAST_INCLUDE; + im->sfcount[MCAST_INCLUDE] = 1; + im->sfcount[MCAST_EXCLUDE] = 0; + } im->sources = NULL; im->tomb = NULL; im->crcount = 0; @@ -1268,6 +1275,11 @@ #endif } +void ip_mc_inc_group(struct in_device *in_dev, u32 addr) +{ + ip_mc_inc_group_for_mode(in_dev, addr, MCAST_EXCLUDE); +} + /* * A socket has left a multicast group on device dev */ @@ -1734,7 +1746,7 @@ /* * Join a multicast group */ -int ip_mc_join_group(struct sock *sk , struct ip_mreqn *imr) +int ip_mc_join_group_for_mode(struct sock *sk , struct ip_mreqn *imr, int omode) { int err; __be32 addr = imr->imr_multiaddr.s_addr; @@ -1776,15 +1788,20 @@ memcpy(&iml->multi, imr, sizeof(*imr)); iml->next = inet->mc_list; iml->sflist = NULL; - iml->sfmode = MCAST_EXCLUDE; + iml->sfmode = omode; inet->mc_list = iml; - ip_mc_inc_group(in_dev, addr); + ip_mc_inc_group_for_mode(in_dev, addr, omode); err = 0; done: rtnl_unlock(); return err; } +int ip_mc_join_group(struct sock *sk , struct ip_mreqn *imr) +{ + return ip_mc_join_group_for_mode(sk, imr, MCAST_EXCLUDE); +} + static int ip_mc_leave_src(struct sock *sk, struct ip_mc_socklist *iml, struct in_device *in_dev) { @@ -2591,3 +2608,4 @@ EXPORT_SYMBOL(ip_mc_inc_group); EXPORT_SYMBOL(ip_mc_join_group); EXPORT_SYMBOL(ip_mc_rejoin_group); +EXPORT_SYMBOL(ip_mc_join_group_for_mode);