> In order to prepare for incremental processing of IGMP groups break > out code that will be common into functions. > > Signed-off-by: Jacob Tanenbaum <[email protected]>
Acked-by: Lorenzo Bianconi <[email protected]> > > diff --git a/northd/northd.c b/northd/northd.c > index 3a488ff3d..0dfeee0b9 100644 > --- a/northd/northd.c > +++ b/northd/northd.c > @@ -17799,6 +17799,21 @@ build_mcast_groups(const struct > sbrec_igmp_group_table *sbrec_igmp_group_table, > struct hmap *mcast_groups, > struct hmap *igmp_groups); > > +static void > +build_igmp_group_for_sb(const struct sbrec_igmp_group *sb_igmp, > + struct ovn_datapath *od, > + struct ovsdb_idl_index *sbrec_mcast_group_by_name_dp, > + const struct hmap *ls_ports, > + struct hmap *igmp_groups); > +static void > +build_igmp_router_entries(struct ovn_datapath *od, > + struct ovsdb_idl_index > *sbrec_mcast_group_by_name_dp, > + struct hmap *igmp_groups); > + > +static void > +build_mcast_group_from_igmp_group(struct ovn_igmp_group *igmp_group, > + struct hmap *mcast_groups, > + struct hmap *igmp_groups); > static struct sbrec_multicast_group * > create_sb_multicast_group(struct ovsdb_idl_txn *ovnsb_txn, > const struct sbrec_datapath_binding *dp, > @@ -18632,39 +18647,10 @@ build_mcast_groups(const struct > sbrec_igmp_group_table *sbrec_igmp_group_table, > sbrec_igmp_group_delete(sb_igmp); > continue; > } > + build_igmp_group_for_sb(sb_igmp, od, > + sbrec_mcast_group_by_name_dp, > + ls_ports, igmp_groups); > > - struct in6_addr group_address; > - if (!strcmp(sb_igmp->address, OVN_IGMP_GROUP_MROUTERS)) { > - /* Use all-zeros IP to denote a group corresponding to mrouters. > */ > - memset(&group_address, 0, sizeof group_address); > - } else if (!ip46_parse(sb_igmp->address, &group_address)) { > - static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 1); > - VLOG_WARN_RL(&rl, "invalid IGMP group address: %s", > - sb_igmp->address); > - continue; > - } > - > - /* Extract the IGMP group ports from the SB entry. */ > - size_t n_igmp_ports; > - struct ovn_port **igmp_ports = > - ovn_igmp_group_get_ports(sb_igmp, &n_igmp_ports, ls_ports); > - > - /* It can be that all ports in the IGMP group record already have > - * mcast_flood=true and then we can skip the group completely. > - */ > - if (!igmp_ports) { > - continue; > - } > - > - /* Add the IGMP group entry. Will also try to allocate an ID for it > - * if the multicast group already exists. > - */ > - struct ovn_igmp_group *igmp_group = > - ovn_igmp_group_add(sbrec_mcast_group_by_name_dp, igmp_groups, od, > - &group_address, sb_igmp->address); > - > - /* Add the extracted ports to the IGMP group. */ > - ovn_igmp_group_add_entry(igmp_group, igmp_ports, n_igmp_ports); > } > > /* Build IGMP groups for multicast routers with relay enabled. The router > @@ -18676,53 +18662,9 @@ build_mcast_groups(const struct > sbrec_igmp_group_table *sbrec_igmp_group_table, > if (ovs_list_is_empty(&od->mcast_info.groups)) { > continue; > } > - > - for (size_t i = 0; i < od->n_router_ports; i++) { > - struct ovn_port *router_port = od->router_ports[i]->peer; > - > - /* If the router the port connects to doesn't have multicast > - * relay enabled or if it was already configured to flood > - * multicast traffic then skip it. > - */ > - if (!router_port || !router_port->od || > - !router_port->od->mcast_info.rtr.relay || > - router_port->mcast_info.flood) { > - continue; > - } > - > - struct ovn_igmp_group *igmp_group; > - LIST_FOR_EACH (igmp_group, list_node, &od->mcast_info.groups) { > - struct in6_addr *address = &igmp_group->address; > - > - /* Skip mrouter entries. */ > - if (!strcmp(igmp_group->mcgroup.name, > - OVN_IGMP_GROUP_MROUTERS)) { > - continue; > - } > - > - /* For IPv6 only relay routable multicast groups > - * (RFC 4291 2.7). > - */ > - if (!IN6_IS_ADDR_V4MAPPED(address) && > - !ipv6_addr_is_routable_multicast(address)) { > - continue; > - } > - > - struct ovn_igmp_group *igmp_group_rtr = > - ovn_igmp_group_add(sbrec_mcast_group_by_name_dp, > - igmp_groups, router_port->od, > - address, igmp_group->mcgroup.name); > - struct ovn_port **router_igmp_ports = > - xmalloc(sizeof *router_igmp_ports); > - /* Store the chassis redirect port otherwise traffic will > not > - * be tunneled properly. > - */ > - router_igmp_ports[0] = router_port->cr_port > - ? router_port->cr_port > - : router_port; > - ovn_igmp_group_add_entry(igmp_group_rtr, router_igmp_ports, > 1); > - } > - } > + build_igmp_router_entries(od, > + sbrec_mcast_group_by_name_dp, > + igmp_groups); > } > > /* Walk the aggregated IGMP groups and allocate IDs for new entries. > @@ -18732,26 +18674,9 @@ build_mcast_groups(const struct > sbrec_igmp_group_table *sbrec_igmp_group_table, > */ > struct ovn_igmp_group *igmp_group; > HMAP_FOR_EACH_SAFE (igmp_group, hmap_node, igmp_groups) { > - > - /* If this is a mrouter entry just aggregate the mrouter ports > - * into the MC_MROUTER mcast_group and destroy the igmp_group; > - * no more processing needed. */ > - if (!strcmp(igmp_group->mcgroup.name, OVN_IGMP_GROUP_MROUTERS)) { > - ovn_igmp_mrouter_aggregate_ports(igmp_group, mcast_groups); > - ovn_igmp_group_destroy(igmp_groups, igmp_group); > - continue; > - } > - > - if (!ovn_igmp_group_allocate_id(igmp_group)) { > - /* If we ran out of keys just destroy the entry. */ > - ovn_igmp_group_destroy(igmp_groups, igmp_group); > - continue; > - } > - > - /* Aggregate the ports from all entries corresponding to this > - * group. > - */ > - ovn_igmp_group_aggregate_ports(igmp_group, mcast_groups); > + build_mcast_group_from_igmp_group(igmp_group, > + mcast_groups, > + igmp_groups); > } > } > > @@ -19400,3 +19325,130 @@ northd_get_datapath_for_port(const struct hmap > *ls_ports, > > return op ? op->od : NULL; > } > + > +static void > +build_igmp_group_for_sb(const struct sbrec_igmp_group *sb_igmp, > + struct ovn_datapath *od, > + struct ovsdb_idl_index *sbrec_mcast_group_by_name_dp, > + const struct hmap *ls_ports, > + struct hmap *igmp_groups) > +{ > + > + struct in6_addr group_address; > + if (!strcmp(sb_igmp->address, OVN_IGMP_GROUP_MROUTERS)) { > + /* Use all-zeros IP to denote a group corresponding to mrouters. */ > + memset(&group_address, 0, sizeof group_address); > + } else if (!ip46_parse(sb_igmp->address, &group_address)) { > + static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 1); > + VLOG_WARN_RL(&rl, "invalid IGMP group address: %s", > + sb_igmp->address); > + return; > + } > + > + /* Extract the IGMP group ports from the SB entry. */ > + size_t n_igmp_ports; > + struct ovn_port **igmp_ports = > + ovn_igmp_group_get_ports(sb_igmp, &n_igmp_ports, ls_ports); > + > + /* It can be that all ports in the IGMP group record already have > + * mcast_flood=true and then we can skip the group completely. > + */ > + if (!igmp_ports) { > + return; > + } > + > + /* Add the IGMP group entry. Will also try to allocate an ID for it > + * if the multicast group already exists. > + */ > + struct ovn_igmp_group *igmp_group = > + ovn_igmp_group_add(sbrec_mcast_group_by_name_dp, igmp_groups, od, > + &group_address, sb_igmp->address); > + > + /* Add the extracted ports to the IGMP group. */ > + ovn_igmp_group_add_entry(igmp_group, igmp_ports, n_igmp_ports); > +} > + > +/* Build IGMP groups for multicast routers with relay enabled, adding the > + * entries to the list of igmp_groups. > + */ > +static void > +build_igmp_router_entries(struct ovn_datapath *od, > + struct ovsdb_idl_index > *sbrec_mcast_group_by_name_dp, > + struct hmap *igmp_groups) > +{ > + for (size_t i = 0; i < od->n_router_ports; i++) { > + struct ovn_port *router_port = od->router_ports[i]->peer; > + > + /* If the router the port connects to doesn't have multicast > + * relay enabled or if it was already configured to flood > + * multicast traffic then skip it. > + */ > + if (!router_port || !router_port->od || > + !router_port->od->mcast_info.rtr.relay || > + router_port->mcast_info.flood) { > + continue; > + } > + > + struct ovn_igmp_group *igmp_group; > + LIST_FOR_EACH (igmp_group, list_node, &od->mcast_info.groups) { > + struct in6_addr *address = &igmp_group->address; > + > + /* Skip mrouter entries. */ > + if (!strcmp(igmp_group->mcgroup.name, > + OVN_IGMP_GROUP_MROUTERS)) { > + continue; > + } > + > + /* For IPv6 only relay routable multicast groups > + * (RFC 4291 2.7). > + */ > + if (!IN6_IS_ADDR_V4MAPPED(address) && > + !ipv6_addr_is_routable_multicast(address)) { > + continue; > + } > + > + struct ovn_igmp_group *igmp_group_rtr = > + ovn_igmp_group_add(sbrec_mcast_group_by_name_dp, > + igmp_groups, router_port->od, > + address, igmp_group->mcgroup.name); > + struct ovn_port **router_igmp_ports = > + xmalloc(sizeof *router_igmp_ports); > + /* Store the chassis redirect port otherwise traffic will not > + * be tunneled properly. > + */ > + router_igmp_ports[0] = router_port->cr_port > + ? router_port->cr_port > + : router_port; > + ovn_igmp_group_add_entry(igmp_group_rtr, router_igmp_ports, 1); > + } > + } > +} > + > +/* From the provided igmp_group process its ports into an mcast_group and > add > + * it to the hmap of mcast_groups. > + */ > +static void > +build_mcast_group_from_igmp_group(struct ovn_igmp_group *igmp_group, > + struct hmap *mcast_groups, > + struct hmap *igmp_groups) > +{ > + /* If this is a mrouter entry just aggregate the mrouter ports > + * into the MC_MROUTER mcast_group and destroy the igmp_group; > + * no more processing needed. */ > + if (!strcmp(igmp_group->mcgroup.name, OVN_IGMP_GROUP_MROUTERS)) { > + ovn_igmp_mrouter_aggregate_ports(igmp_group, mcast_groups); > + ovn_igmp_group_destroy(igmp_groups, igmp_group); > + return; > + } > + > + if (!ovn_igmp_group_allocate_id(igmp_group)) { > + /* If we ran out of keys just destroy the entry. */ > + ovn_igmp_group_destroy(igmp_groups, igmp_group); > + return; > + } > + > + /* Aggregate the ports from all entries corresponding to this > + * group. > + */ > + ovn_igmp_group_aggregate_ports(igmp_group, mcast_groups); > +} > -- > 2.47.1 > > _______________________________________________ > dev mailing list > [email protected] > https://mail.openvswitch.org/mailman/listinfo/ovs-dev >
_______________________________________________ dev mailing list [email protected] https://mail.openvswitch.org/mailman/listinfo/ovs-dev
