diff options
Diffstat (limited to 'net/batman-adv/translation-table.c')
-rw-r--r-- | net/batman-adv/translation-table.c | 27 |
1 files changed, 22 insertions, 5 deletions
diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c index c7aafc7c5ed4..5f09a578d49d 100644 --- a/net/batman-adv/translation-table.c +++ b/net/batman-adv/translation-table.c | |||
@@ -245,9 +245,11 @@ void tt_local_add(struct net_device *soft_iface, const uint8_t *addr, | |||
245 | if (tt_global_entry) { | 245 | if (tt_global_entry) { |
246 | /* This node is probably going to update its tt table */ | 246 | /* This node is probably going to update its tt table */ |
247 | tt_global_entry->orig_node->tt_poss_change = true; | 247 | tt_global_entry->orig_node->tt_poss_change = true; |
248 | /* The global entry has to be marked as PENDING and has to be | 248 | /* The global entry has to be marked as ROAMING and has to be |
249 | * kept for consistency purpose */ | 249 | * kept for consistency purpose */ |
250 | tt_global_entry->flags |= TT_CLIENT_PENDING; | 250 | tt_global_entry->flags |= TT_CLIENT_ROAM; |
251 | tt_global_entry->roam_at = jiffies; | ||
252 | |||
251 | send_roam_adv(bat_priv, tt_global_entry->addr, | 253 | send_roam_adv(bat_priv, tt_global_entry->addr, |
252 | tt_global_entry->orig_node); | 254 | tt_global_entry->orig_node); |
253 | } | 255 | } |
@@ -694,6 +696,7 @@ void tt_global_del(struct bat_priv *bat_priv, | |||
694 | const char *message, bool roaming) | 696 | const char *message, bool roaming) |
695 | { | 697 | { |
696 | struct tt_global_entry *tt_global_entry = NULL; | 698 | struct tt_global_entry *tt_global_entry = NULL; |
699 | struct tt_local_entry *tt_local_entry = NULL; | ||
697 | 700 | ||
698 | tt_global_entry = tt_global_hash_find(bat_priv, addr); | 701 | tt_global_entry = tt_global_hash_find(bat_priv, addr); |
699 | if (!tt_global_entry) | 702 | if (!tt_global_entry) |
@@ -701,15 +704,29 @@ void tt_global_del(struct bat_priv *bat_priv, | |||
701 | 704 | ||
702 | if (tt_global_entry->orig_node == orig_node) { | 705 | if (tt_global_entry->orig_node == orig_node) { |
703 | if (roaming) { | 706 | if (roaming) { |
704 | tt_global_entry->flags |= TT_CLIENT_ROAM; | 707 | /* if we are deleting a global entry due to a roam |
705 | tt_global_entry->roam_at = jiffies; | 708 | * event, there are two possibilities: |
706 | goto out; | 709 | * 1) the client roamed from node A to node B => we mark |
710 | * it with TT_CLIENT_ROAM, we start a timer and we | ||
711 | * wait for node B to claim it. In case of timeout | ||
712 | * the entry is purged. | ||
713 | * 2) the client roamed to us => we can directly delete | ||
714 | * the global entry, since it is useless now. */ | ||
715 | tt_local_entry = tt_local_hash_find(bat_priv, | ||
716 | tt_global_entry->addr); | ||
717 | if (!tt_local_entry) { | ||
718 | tt_global_entry->flags |= TT_CLIENT_ROAM; | ||
719 | tt_global_entry->roam_at = jiffies; | ||
720 | goto out; | ||
721 | } | ||
707 | } | 722 | } |
708 | _tt_global_del(bat_priv, tt_global_entry, message); | 723 | _tt_global_del(bat_priv, tt_global_entry, message); |
709 | } | 724 | } |
710 | out: | 725 | out: |
711 | if (tt_global_entry) | 726 | if (tt_global_entry) |
712 | tt_global_entry_free_ref(tt_global_entry); | 727 | tt_global_entry_free_ref(tt_global_entry); |
728 | if (tt_local_entry) | ||
729 | tt_local_entry_free_ref(tt_local_entry); | ||
713 | } | 730 | } |
714 | 731 | ||
715 | void tt_global_del_orig(struct bat_priv *bat_priv, | 732 | void tt_global_del_orig(struct bat_priv *bat_priv, |