On Fri, May 24, 2013 at 10:02:27AM +0200, Linus Lüssing wrote:
> If the soft interface of a node is not part of a bridge then a node
> announces a new multicast TVLV: The according flag
> (BATADV_MCAST_LISTENER_ANNOUNCEMENT) signalizes that this node is
> announcing all of its multicast listeners via the translation table
> infrastructure. More precisely, all multicast listeners of scope greater
> than link-local for IPv4 and of scope greater
> or equal to link-local for IPv6.
> 
> Signed-off-by: Linus Lüssing <[email protected]>
> ---
>  main.c           |    4 ++++
>  multicast.c      |   62 
> ++++++++++++++++++++++++++++++++++++++++++++++++++++--
>  multicast.h      |    7 ++++++
>  originator.c     |    3 +++
>  packet.h         |    7 ++++++
>  soft-interface.c |    1 +
>  types.h          |    4 ++++
>  7 files changed, 86 insertions(+), 2 deletions(-)
> 
> diff --git a/main.c b/main.c
> index 1c82c18..6ab5b2d 100644
> --- a/main.c
> +++ b/main.c
> @@ -145,6 +145,10 @@ int batadv_mesh_init(struct net_device *soft_iface)
>       if (ret < 0)
>               goto err;
>  
> +     ret = batadv_mcast_init(bat_priv);
> +     if (ret < 0)
> +             goto err;
> +
>       ret = batadv_gw_init(bat_priv);
>       if (ret < 0)
>               goto err;
> diff --git a/multicast.c b/multicast.c
> index 56a1128..36e4c59 100644
> --- a/multicast.c
> +++ b/multicast.c
> @@ -204,10 +213,59 @@ out:
>  }
>  
>  /**
> + * batadv_mcast_tvlv_ogm_handler_v1 - process incoming multicast tvlv 
> container
> + * @bat_priv: the bat priv with all the soft interface information
> + * @orig: the orig_node of the ogm
> + * @flags: flags indicating the tvlv state (see batadv_tvlv_handler_flags)
> + * @tvlv_value: tvlv buffer containing the multicast data
> + * @tvlv_value_len: tvlv buffer length
> + */
> +static void batadv_mcast_tvlv_ogm_handler_v1(struct batadv_priv *bat_priv,
> +                                          struct batadv_orig_node *orig,
> +                                          uint8_t flags,
> +                                          void *tvlv_value,
> +                                          uint16_t tvlv_value_len)
> +{
> +     uint8_t mcast_flags = BATADV_NO_FLAGS;
> +
> +     /* only fetch the tvlv value if the handler wasn't called via the
> +      * CIFNOTFND flag and if there is data to fetch
> +      */
> +     if (!(flags & BATADV_TVLV_HANDLER_OGM_CIFNOTFND) &&
> +         (tvlv_value) && (tvlv_value_len == sizeof(mcast_flags)))
> +             mcast_flags = *(uint8_t *)tvlv_value;
> +
> +     if (!(mcast_flags & BATADV_MCAST_LISTENER_ANNOUNCEMENT) &&
> +         orig->mcast_flags & BATADV_MCAST_LISTENER_ANNOUNCEMENT) {
> +             atomic_inc(&bat_priv->mcast.num_non_aware);
> +     } else if (mcast_flags & BATADV_MCAST_LISTENER_ANNOUNCEMENT &&
> +                !(orig->mcast_flags & BATADV_MCAST_LISTENER_ANNOUNCEMENT)) {
> +             atomic_dec(&bat_priv->mcast.num_non_aware);
> +     }

What happens if the orig_node is removed/times out? I can't see where 
num_non_aware
is updated in this case.

We do have a work struct touch every orig every second anyway 
(batadv_purge_orig), maybe
put counting multicast aware routers there? Then you don't have to care about
synchronizing stuff ...

> +
> +     orig->mcast_flags = mcast_flags;
> +}
> +
> +/**
> + * batadv_mcast_init - initialize the multicast optimizations structures
> + * @bat_priv: the bat priv with all the soft interface information
> + */
> +int batadv_mcast_init(struct batadv_priv *bat_priv)
> +{
> +     batadv_tvlv_handler_register(bat_priv, batadv_mcast_tvlv_ogm_handler_v1,
> +                                  NULL, BATADV_TVLV_MCAST, 1,
> +                                  BATADV_TVLV_HANDLER_OGM_CIFNOTFND);
> +     return 0;
> +}
> +
> +/**
>   * batadv_mcast_free - free the multicast optimizations structures
>   * @bat_priv: the bat priv with all the soft interface information
>   */
>  void batadv_mcast_free(struct batadv_priv *bat_priv)
>  {
> +     batadv_tvlv_container_unregister(bat_priv, BATADV_TVLV_MCAST, 1);
> +     batadv_tvlv_handler_unregister(bat_priv, BATADV_TVLV_MCAST, 1);
> +
>       batadv_mcast_mla_tt_clean(bat_priv, NULL);
>  }

Attachment: signature.asc
Description: Digital signature

Reply via email to