aboutsummaryrefslogtreecommitdiffstats
path: root/net/tipc
diff options
context:
space:
mode:
authorJon Maloy <jon.maloy@ericsson.com>2018-07-06 14:10:05 -0400
committerDavid S. Miller <davem@davemloft.net>2018-07-07 06:49:01 -0400
commit92018c7ca959ccd346d6235dac03cf7fc1ba51f7 (patch)
tree7d9db104a800f18ab9306c4064311953d32df15b /net/tipc
parente415577f57f4452150642500364cbe5fa6112813 (diff)
tipc: fix correct setting of message type in second discoverer
The duplicate address discovery protocol is not safe against two discoverers running in parallel. The one executing first after the trial period is over will set the node address and change its own message type to DSC_REQ_MSG. The one executing last may find that the node address is already set, and never change message type, with the result that its links may never be established. In this commmit we ensure that the message type always is set correctly after the trial period is over. Fixes: 25b0b9c4e835 ("tipc: handle collisions of 32-bit node address hash values") Signed-off-by: Jon Maloy <jon.maloy@ericsson.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/tipc')
-rw-r--r--net/tipc/discover.c13
1 files changed, 7 insertions, 6 deletions
diff --git a/net/tipc/discover.c b/net/tipc/discover.c
index dcadc10dffd1..2830709957bd 100644
--- a/net/tipc/discover.c
+++ b/net/tipc/discover.c
@@ -287,7 +287,6 @@ static void tipc_disc_timeout(struct timer_list *t)
287{ 287{
288 struct tipc_discoverer *d = from_timer(d, t, timer); 288 struct tipc_discoverer *d = from_timer(d, t, timer);
289 struct tipc_net *tn = tipc_net(d->net); 289 struct tipc_net *tn = tipc_net(d->net);
290 u32 self = tipc_own_addr(d->net);
291 struct tipc_media_addr maddr; 290 struct tipc_media_addr maddr;
292 struct sk_buff *skb = NULL; 291 struct sk_buff *skb = NULL;
293 struct net *net = d->net; 292 struct net *net = d->net;
@@ -301,12 +300,14 @@ static void tipc_disc_timeout(struct timer_list *t)
301 goto exit; 300 goto exit;
302 } 301 }
303 302
304 /* Did we just leave the address trial period ? */ 303 /* Trial period over ? */
305 if (!self && !time_before(jiffies, tn->addr_trial_end)) { 304 if (!time_before(jiffies, tn->addr_trial_end)) {
306 self = tn->trial_addr; 305 /* Did we just leave it ? */
307 tipc_net_finalize(net, self); 306 if (!tipc_own_addr(net))
308 msg_set_prevnode(buf_msg(d->skb), self); 307 tipc_net_finalize(net, tn->trial_addr);
308
309 msg_set_type(buf_msg(d->skb), DSC_REQ_MSG); 309 msg_set_type(buf_msg(d->skb), DSC_REQ_MSG);
310 msg_set_prevnode(buf_msg(d->skb), tipc_own_addr(net));
310 } 311 }
311 312
312 /* Adjust timeout interval according to discovery phase */ 313 /* Adjust timeout interval according to discovery phase */