aboutsummaryrefslogtreecommitdiffstats
path: root/net/tipc/node.h
diff options
context:
space:
mode:
authorJon Paul Maloy <jon.maloy@ericsson.com>2015-07-16 16:54:30 -0400
committerDavid S. Miller <davem@davemloft.net>2015-07-20 23:41:16 -0400
commit1a20cc254e60e79929ef7edb5cf784df86b46e42 (patch)
tree20ace0bcaf31803fe6ffbd048df89be9bb26b8d6 /net/tipc/node.h
parent8a1577c96f122308ac9b5f195f9f9a7dd74ac541 (diff)
tipc: introduce node contact FSM
The logics for determining when a node is permitted to establish and maintain contact with its peer node becomes non-trivial in the presence of multiple parallel links that may come and go independently. A known failure scenario is that one endpoint registers both its links to the peer lost, cleans up it binding table, and prepares for a table update once contact is re-establihed, while the other endpoint may see its links reset and re-established one by one, hence seeing no need to re-synchronize the binding table. To avoid this, a node must not allow re-establishing contact until it has confirmation that even the peer has lost both links. Currently, the mechanism for handling this consists of setting and resetting two state flags from different locations in the code. This solution is hard to understand and maintain. A closer analysis even reveals that it is not completely safe. In this commit we do instead introduce an FSM that keeps track of the conditions for when the node can establish and maintain links. It has six states and four events, and is strictly based on explicit knowledge about the own node's and the peer node's contact states. Only events leading to state change are shown as edges in the figure below. +--------------+ | SELF_UP/ | +---------------->| PEER_COMING |-----------------+ SELF_ | +--------------+ |PEER_ ESTBL_ | | |ESTBL_ CONTACT| SELF_LOST_CONTACT | |CONTACT | v | | +--------------+ | | PEER_ | SELF_DOWN/ | SELF_ | | LOST_ +--| PEER_LEAVING |<--+ LOST_ v +-------------+ CONTACT | +--------------+ | CONTACT +-----------+ | SELF_DOWN/ |<----------+ +----------| SELF_UP/ | | PEER_DOWN |<----------+ +----------| PEER_UP | +-------------+ SELF_ | +--------------+ | PEER_ +-----------+ | LOST_ +--| SELF_LEAVING/|<--+ LOST_ A | CONTACT | PEER_DOWN | CONTACT | | +--------------+ | | A | PEER_ | PEER_LOST_CONTACT | |SELF_ ESTBL_ | | |ESTBL_ CONTACT| +--------------+ |CONTACT +---------------->| PEER_UP/ |-----------------+ | SELF_COMING | +--------------+ Reviewed-by: Ying Xue <ying.xue@windriver.com> Signed-off-by: Jon Maloy <jon.maloy@ericsson.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/tipc/node.h')
-rw-r--r--net/tipc/node.h28
1 files changed, 21 insertions, 7 deletions
diff --git a/net/tipc/node.h b/net/tipc/node.h
index 2d56344962e7..270256e09ee5 100644
--- a/net/tipc/node.h
+++ b/net/tipc/node.h
@@ -47,6 +47,24 @@
47 47
48#define INVALID_BEARER_ID -1 48#define INVALID_BEARER_ID -1
49 49
50/* Node FSM states and events:
51 */
52enum {
53 SELF_DOWN_PEER_DOWN = 0xdd,
54 SELF_UP_PEER_UP = 0xaa,
55 SELF_DOWN_PEER_LEAVING = 0xd1,
56 SELF_UP_PEER_COMING = 0xac,
57 SELF_COMING_PEER_UP = 0xca,
58 SELF_LEAVING_PEER_DOWN = 0x1d,
59};
60
61enum {
62 SELF_ESTABL_CONTACT_EVT = 0xec,
63 SELF_LOST_CONTACT_EVT = 0x1c,
64 PEER_ESTABL_CONTACT_EVT = 0xfec,
65 PEER_LOST_CONTACT_EVT = 0xf1c
66};
67
50/* Flags used to take different actions according to flag type 68/* Flags used to take different actions according to flag type
51 * TIPC_WAIT_PEER_LINKS_DOWN: wait to see that peer's links are down 69 * TIPC_WAIT_PEER_LINKS_DOWN: wait to see that peer's links are down
52 * TIPC_WAIT_OWN_LINKS_DOWN: wait until peer node is declared down 70 * TIPC_WAIT_OWN_LINKS_DOWN: wait until peer node is declared down
@@ -56,8 +74,6 @@
56 */ 74 */
57enum { 75enum {
58 TIPC_MSG_EVT = 1, 76 TIPC_MSG_EVT = 1,
59 TIPC_WAIT_PEER_LINKS_DOWN = (1 << 1),
60 TIPC_WAIT_OWN_LINKS_DOWN = (1 << 2),
61 TIPC_NOTIFY_NODE_DOWN = (1 << 3), 77 TIPC_NOTIFY_NODE_DOWN = (1 << 3),
62 TIPC_NOTIFY_NODE_UP = (1 << 4), 78 TIPC_NOTIFY_NODE_UP = (1 << 4),
63 TIPC_WAKEUP_BCAST_USERS = (1 << 5), 79 TIPC_WAKEUP_BCAST_USERS = (1 << 5),
@@ -133,6 +149,7 @@ struct tipc_node {
133 int action_flags; 149 int action_flags;
134 struct tipc_node_bclink bclink; 150 struct tipc_node_bclink bclink;
135 struct list_head list; 151 struct list_head list;
152 int state;
136 int link_cnt; 153 int link_cnt;
137 u16 working_links; 154 u16 working_links;
138 u16 capabilities; 155 u16 capabilities;
@@ -176,11 +193,8 @@ static inline void tipc_node_lock(struct tipc_node *node)
176 spin_lock_bh(&node->lock); 193 spin_lock_bh(&node->lock);
177} 194}
178 195
179static inline bool tipc_node_blocked(struct tipc_node *node) 196void tipc_node_fsm_evt(struct tipc_node *n, int evt);
180{ 197bool tipc_node_filter_skb(struct tipc_node *n, struct tipc_msg *hdr);
181 return (node->action_flags & (TIPC_WAIT_PEER_LINKS_DOWN |
182 TIPC_NOTIFY_NODE_DOWN | TIPC_WAIT_OWN_LINKS_DOWN));
183}
184 198
185static inline struct tipc_link *node_active_link(struct tipc_node *n, int sel) 199static inline struct tipc_link *node_active_link(struct tipc_node *n, int sel)
186{ 200{