As a further preparation for the upcoming 'replicast' functionality,
we add some necessary structs and functions for looking up and returning
a list of all nodes that host destinations for a given multicast message.

Signed-off-by: Jon Maloy <jon.ma...@ericsson.com>
---
 net/tipc/bcast.c      | 81 +++++++++++++++++++++++++++++++++++++++++++++++++--
 net/tipc/bcast.h      | 24 ++++++++++++++-
 net/tipc/name_table.c | 33 +++++++++++++++++++++
 net/tipc/name_table.h |  4 +++
 4 files changed, 139 insertions(+), 3 deletions(-)

diff --git a/net/tipc/bcast.c b/net/tipc/bcast.c
index 886df68..2a73a03 100644
--- a/net/tipc/bcast.c
+++ b/net/tipc/bcast.c
@@ -39,9 +39,7 @@
 #include "socket.h"
 #include "msg.h"
 #include "bcast.h"
-#include "name_distr.h"
 #include "link.h"
-#include "node.h"
 
 #define        BCLINK_WIN_DEFAULT      50      /* bcast link window size 
(default) */
 #define        BCLINK_WIN_MIN          32      /* bcast minimum link window 
size */
@@ -428,3 +426,82 @@ void tipc_bcast_stop(struct net *net)
        kfree(tn->bcbase);
        kfree(tn->bcl);
 }
+
+void tipc_nlist_init(struct tipc_nlist *nl, u32 self)
+{
+       memset(nl, 0, sizeof(*nl));
+       INIT_LIST_HEAD(&nl->sent);
+       INIT_LIST_HEAD(&nl->unsent);
+       skb_queue_head_init(&nl->localq);
+       nl->self = self;
+}
+
+static struct tipc_nitem *tipc_nlist_find(struct tipc_nlist *nl, u32 node)
+{
+       struct tipc_nitem *n;
+
+       list_for_each_entry(n, &nl->unsent, list) {
+               if (n->node == node)
+                       return n;
+       }
+       list_for_each_entry(n, &nl->sent, list) {
+               if (n->node == node)
+                       return n;
+       }
+       return NULL;
+}
+
+void tipc_nlist_add(struct tipc_nlist *nl, u32 node)
+{
+       struct tipc_nitem *n;
+
+       if (node == nl->self) {
+               nl->local = true;
+               return;
+       }
+       n = tipc_nlist_find(nl, node);
+       if (n)
+               return;
+       n = kzalloc(sizeof(*n), GFP_KERNEL);
+       if (!n)
+               return;
+       INIT_LIST_HEAD(&n->list);
+       n->node = node;
+       nl->remote++;
+       list_add(&n->list, &nl->unsent);
+}
+
+void tipc_nlist_sent(struct tipc_nlist *nl, struct tipc_nitem *n)
+{
+       list_del(&n->list);
+       list_add(&n->list, &nl->sent);
+}
+
+void tipc_nlist_del(struct tipc_nlist *nl, u32 node)
+{
+       struct tipc_nitem *n = tipc_nlist_find(nl, node);
+
+       if (!n)
+               return;
+       list_del(&n->list);
+       kfree(n);
+       nl->remote--;
+}
+
+void tipc_nlist_restore(struct tipc_nlist *nl)
+{
+       list_splice_tail_init(&nl->sent, &nl->unsent);
+}
+
+void tipc_nlist_purge(struct tipc_nlist *nl)
+{
+       struct tipc_nitem *n, *tmp;
+
+       list_splice_tail_init(&nl->sent, &nl->unsent);
+       list_for_each_entry_safe(n, tmp, &nl->unsent, list) {
+               list_del(&n->list);
+               kfree(n);
+       }
+       nl->remote = 0;
+       nl->local = 0;
+}
diff --git a/net/tipc/bcast.h b/net/tipc/bcast.h
index 5ffe344..8f9a210 100644
--- a/net/tipc/bcast.h
+++ b/net/tipc/bcast.h
@@ -42,9 +42,31 @@
 struct tipc_node;
 struct tipc_msg;
 struct tipc_nl_msg;
-struct tipc_node_map;
+struct tipc_nlist;
+struct tipc_nitem;
 extern const char tipc_bclink_name[];
 
+struct tipc_nitem {
+       struct list_head list;
+       u32 node;
+};
+
+struct tipc_nlist {
+       struct list_head unsent;
+       struct list_head sent;
+       struct sk_buff_head localq;
+       u32 self;
+       int remote;
+       bool local;
+};
+
+void tipc_nlist_init(struct tipc_nlist *nl, u32 self);
+void tipc_nlist_restore(struct tipc_nlist *nl);
+void tipc_nlist_purge(struct tipc_nlist *nl);
+void tipc_nlist_add(struct tipc_nlist *nl, u32 node);
+void tipc_nlist_sent(struct tipc_nlist *nl, struct tipc_nitem *n);
+void tipc_nlist_del(struct tipc_nlist *nl, u32 node);
+
 int tipc_bcast_init(struct net *net);
 void tipc_bcast_stop(struct net *net);
 void tipc_bcast_add_peer(struct net *net, struct tipc_link *l,
diff --git a/net/tipc/name_table.c b/net/tipc/name_table.c
index e190460..de58a0d 100644
--- a/net/tipc/name_table.c
+++ b/net/tipc/name_table.c
@@ -645,6 +645,39 @@ int tipc_nametbl_mc_translate(struct net *net, u32 type, 
u32 lower, u32 upper,
        return res;
 }
 
+/* tipc_nametbl_lookup_dst_nodes - find broadcast destination nodes
+ * - Creates list of nodes that overlap the given multicast address
+ * - Determines if any node local ports overlap
+ */
+void tipc_nametbl_lookup_dst_nodes(struct net *net, u32 type, u32 lower,
+                                  u32 upper, u32 domain,
+                                  struct tipc_nlist *nodes)
+{
+       struct sub_seq *sseq, *stop;
+       struct publication *publ;
+       struct name_info *info;
+       struct name_seq *seq;
+
+       rcu_read_lock();
+       seq = nametbl_find_seq(net, type);
+       if (!seq)
+               goto exit;
+
+       spin_lock_bh(&seq->lock);
+       sseq = seq->sseqs + nameseq_locate_subseq(seq, lower);
+       stop = seq->sseqs + seq->first_free;
+       for (; sseq->lower <= upper && sseq != stop; sseq++) {
+               info = sseq->info;
+               list_for_each_entry(publ, &info->zone_list, zone_list) {
+                       if (tipc_in_scope(domain, publ->node))
+                               tipc_nlist_add(nodes, publ->node);
+               }
+       }
+       spin_unlock_bh(&seq->lock);
+exit:
+       rcu_read_unlock();
+}
+
 /*
  * tipc_nametbl_publish - add name publication to network name tables
  */
diff --git a/net/tipc/name_table.h b/net/tipc/name_table.h
index 1524a73..5f65a8f 100644
--- a/net/tipc/name_table.h
+++ b/net/tipc/name_table.h
@@ -39,6 +39,7 @@
 
 struct tipc_subscription;
 struct tipc_plist;
+struct tipc_nlist;
 
 /*
  * TIPC name types reserved for internal TIPC use (both current and planned)
@@ -100,6 +101,9 @@ int tipc_nl_name_table_dump(struct sk_buff *skb, struct 
netlink_callback *cb);
 u32 tipc_nametbl_translate(struct net *net, u32 type, u32 instance, u32 *node);
 int tipc_nametbl_mc_translate(struct net *net, u32 type, u32 lower, u32 upper,
                              u32 limit, struct tipc_plist *dports);
+void tipc_nametbl_lookup_dst_nodes(struct net *net, u32 type, u32 lower,
+                                  u32 upper, u32 domain,
+                                  struct tipc_nlist *nodes);
 struct publication *tipc_nametbl_publish(struct net *net, u32 type, u32 lower,
                                         u32 upper, u32 scope, u32 port_ref,
                                         u32 key);
-- 
2.7.4


------------------------------------------------------------------------------
The Command Line: Reinvented for Modern Developers
Did the resurgence of CLI tooling catch you by surprise?
Reconnect with the command line and become more productive. 
Learn the new .NET and ASP.NET CLI. Get your free copy!
http://sdm.link/telerik
_______________________________________________
tipc-discussion mailing list
tipc-discussion@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/tipc-discussion

Reply via email to