#include "node.h"
#include "name_distr.h"
+#define NODE_HTABLE_SIZE 512
+
static void node_lost_contact(struct tipc_node *n_ptr);
static void node_established_contact(struct tipc_node *n_ptr);
static u32 tipc_num_nodes;
static atomic_t tipc_num_links = ATOMIC_INIT(0);
-u32 tipc_own_tag;
-/**
+/*
+ * A trivial power-of-two bitmask technique is used for speed, since this
+ * operation is done for every incoming TIPC packet. The number of hash table
+ * entries has been chosen so that no hash chain exceeds 8 nodes and will
+ * usually be much smaller (typically only a single node).
+ */
+static inline unsigned int tipc_hashfn(u32 addr)
+{
+ return addr & (NODE_HTABLE_SIZE - 1);
+}
+
+/*
* tipc_node_find - locate specified node object, if it exists
*/
}
list_add_tail(&n_ptr->list, &temp_node->list);
n_ptr->block_setup = WAIT_PEER_DOWN;
+ n_ptr->signature = INVALID_NODE_SIG;
tipc_num_nodes++;
* Link becomes active (alone or shared) or standby, depending on its priority.
*/
-void tipc_node_link_up(struct tipc_node *n_ptr, struct link *l_ptr)
+void tipc_node_link_up(struct tipc_node *n_ptr, struct tipc_link *l_ptr)
{
- struct link **active = &n_ptr->active_links[0];
+ struct tipc_link **active = &n_ptr->active_links[0];
n_ptr->working_links++;
static void node_select_active_links(struct tipc_node *n_ptr)
{
- struct link **active = &n_ptr->active_links[0];
+ struct tipc_link **active = &n_ptr->active_links[0];
u32 i;
u32 highest_prio = 0;
active[0] = active[1] = NULL;
for (i = 0; i < MAX_BEARERS; i++) {
- struct link *l_ptr = n_ptr->links[i];
+ struct tipc_link *l_ptr = n_ptr->links[i];
if (!l_ptr || !tipc_link_is_up(l_ptr) ||
(l_ptr->priority < highest_prio))
* tipc_node_link_down - handle loss of link
*/
-void tipc_node_link_down(struct tipc_node *n_ptr, struct link *l_ptr)
+void tipc_node_link_down(struct tipc_node *n_ptr, struct tipc_link *l_ptr)
{
- struct link **active;
+ struct tipc_link **active;
n_ptr->working_links--;
return tipc_node_active_links(n_ptr);
}
-void tipc_node_attach_link(struct tipc_node *n_ptr, struct link *l_ptr)
+void tipc_node_attach_link(struct tipc_node *n_ptr, struct tipc_link *l_ptr)
{
n_ptr->links[l_ptr->b_ptr->identity] = l_ptr;
atomic_inc(&tipc_num_links);
n_ptr->link_cnt++;
}
-void tipc_node_detach_link(struct tipc_node *n_ptr, struct link *l_ptr)
+void tipc_node_detach_link(struct tipc_node *n_ptr, struct tipc_link *l_ptr)
{
n_ptr->links[l_ptr->b_ptr->identity] = NULL;
atomic_dec(&tipc_num_links);
n_ptr->link_cnt--;
}
-/*
- * Routing table management - five cases to handle:
- *
- * 1: A link towards a zone/cluster external node comes up.
- * => Send a multicast message updating routing tables of all
- * system nodes within own cluster that the new destination
- * can be reached via this node.
- * (node.establishedContact()=>cluster.multicastNewRoute())
- *
- * 2: A link towards a slave node comes up.
- * => Send a multicast message updating routing tables of all
- * system nodes within own cluster that the new destination
- * can be reached via this node.
- * (node.establishedContact()=>cluster.multicastNewRoute())
- * => Send a message to the slave node about existence
- * of all system nodes within cluster:
- * (node.establishedContact()=>cluster.sendLocalRoutes())
- *
- * 3: A new cluster local system node becomes available.
- * => Send message(s) to this particular node containing
- * information about all cluster external and slave
- * nodes which can be reached via this node.
- * (node.establishedContact()==>network.sendExternalRoutes())
- * (node.establishedContact()==>network.sendSlaveRoutes())
- * => Send messages to all directly connected slave nodes
- * containing information about the existence of the new node
- * (node.establishedContact()=>cluster.multicastNewRoute())
- *
- * 4: The link towards a zone/cluster external node or slave
- * node goes down.
- * => Send a multcast message updating routing tables of all
- * nodes within cluster that the new destination can not any
- * longer be reached via this node.
- * (node.lostAllLinks()=>cluster.bcastLostRoute())
- *
- * 5: A cluster local system node becomes unavailable.
- * => Remove all references to this node from the local
- * routing tables. Note: This is a completely node
- * local operation.
- * (node.lostAllLinks()=>network.removeAsRouter())
- * => Send messages to all directly connected slave nodes
- * containing information about loss of the node
- * (node.establishedContact()=>cluster.multicastLostRoute())
- *
- */
-
static void node_established_contact(struct tipc_node *n_ptr)
{
tipc_k_signal((Handler)tipc_named_node_up, n_ptr->addr);
- /* Syncronize broadcast acks */
- n_ptr->bclink.acked = tipc_bclink_get_last_sent();
-
- if (n_ptr->bclink.supported) {
- tipc_nmap_add(&tipc_bcast_nmap, n_ptr->addr);
- if (n_ptr->addr < tipc_own_addr)
- tipc_own_tag++;
+ if (n_ptr->bclink.supportable) {
+ n_ptr->bclink.acked = tipc_bclink_get_last_sent();
+ tipc_bclink_add_node(n_ptr->addr);
+ n_ptr->bclink.supported = 1;
}
}
/* Flush broadcast link info associated with lost node */
if (n_ptr->bclink.supported) {
- n_ptr->bclink.gap_after = n_ptr->bclink.gap_to = 0;
while (n_ptr->bclink.deferred_head) {
struct sk_buff *buf = n_ptr->bclink.deferred_head;
n_ptr->bclink.deferred_head = buf->next;
- buf_discard(buf);
+ kfree_skb(buf);
}
+ n_ptr->bclink.deferred_size = 0;
if (n_ptr->bclink.defragm) {
- buf_discard(n_ptr->bclink.defragm);
+ kfree_skb(n_ptr->bclink.defragm);
n_ptr->bclink.defragm = NULL;
}
- tipc_nmap_remove(&tipc_bcast_nmap, n_ptr->addr);
- tipc_bclink_acknowledge(n_ptr,
- mod(n_ptr->bclink.acked + 10000));
- if (n_ptr->addr < tipc_own_addr)
- tipc_own_tag--;
+ tipc_bclink_remove_node(n_ptr->addr);
+ tipc_bclink_acknowledge(n_ptr, INVALID_LINK_SEQ);
n_ptr->bclink.supported = 0;
}
/* Abort link changeover */
for (i = 0; i < MAX_BEARERS; i++) {
- struct link *l_ptr = n_ptr->links[i];
+ struct tipc_link *l_ptr = n_ptr->links[i];
if (!l_ptr)
continue;
l_ptr->reset_checkpoint = l_ptr->next_in_no;
read_lock_bh(&tipc_net_lock);
- /* Get space for all unicast links + multicast link */
+ /* Get space for all unicast links + broadcast link */
payload_size = TLV_SPACE(sizeof(link_info)) *
(atomic_read(&tipc_num_links) + 1);