1 /* Copyright (C) 2007-2015 B.A.T.M.A.N. contributors: 2 * 3 * Marek Lindner, Simon Wunderlich, Antonio Quartulli 4 * 5 * This program is free software; you can redistribute it and/or 6 * modify it under the terms of version 2 of the GNU General Public 7 * License as published by the Free Software Foundation. 8 * 9 * This program is distributed in the hope that it will be useful, but 10 * WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, see <http://www.gnu.org/licenses/>. 16 */ 17 18 #include "translation-table.h" 19 #include "main.h" 20 21 #include <linux/atomic.h> 22 #include <linux/bitops.h> 23 #include <linux/bug.h> 24 #include <linux/byteorder/generic.h> 25 #include <linux/compiler.h> 26 #include <linux/crc32c.h> 27 #include <linux/errno.h> 28 #include <linux/etherdevice.h> 29 #include <linux/fs.h> 30 #include <linux/if_ether.h> 31 #include <linux/jhash.h> 32 #include <linux/jiffies.h> 33 #include <linux/kernel.h> 34 #include <linux/list.h> 35 #include <linux/lockdep.h> 36 #include <linux/netdevice.h> 37 #include <linux/rculist.h> 38 #include <linux/rcupdate.h> 39 #include <linux/seq_file.h> 40 #include <linux/slab.h> 41 #include <linux/spinlock.h> 42 #include <linux/stddef.h> 43 #include <linux/string.h> 44 #include <linux/workqueue.h> 45 #include <net/net_namespace.h> 46 47 #include "bridge_loop_avoidance.h" 48 #include "hard-interface.h" 49 #include "hash.h" 50 #include "multicast.h" 51 #include "originator.h" 52 #include "packet.h" 53 #include "soft-interface.h" 54 55 /* hash class keys */ 56 static struct lock_class_key batadv_tt_local_hash_lock_class_key; 57 static struct lock_class_key batadv_tt_global_hash_lock_class_key; 58 59 static void batadv_send_roam_adv(struct batadv_priv *bat_priv, u8 *client, 60 unsigned short vid, 61 struct batadv_orig_node *orig_node); 62 static void batadv_tt_purge(struct work_struct *work); 63 static void 64 batadv_tt_global_del_orig_list(struct batadv_tt_global_entry *tt_global_entry); 65 static void batadv_tt_global_del(struct batadv_priv *bat_priv, 66 struct batadv_orig_node *orig_node, 67 const unsigned char *addr, 68 unsigned short vid, const char *message, 69 bool roaming); 70 71 /* returns 1 if they are the same mac addr */ 72 static int batadv_compare_tt(const struct hlist_node *node, const void *data2) 73 { 74 const void *data1 = container_of(node, struct batadv_tt_common_entry, 75 hash_entry); 76 77 return batadv_compare_eth(data1, data2); 78 } 79 80 /** 81 * batadv_choose_tt - return the index of the tt entry in the hash table 82 * @data: pointer to the tt_common_entry object to map 83 * @size: the size of the hash table 84 * 85 * Returns the hash index where the object represented by 'data' should be 86 * stored at. 87 */ 88 static inline u32 batadv_choose_tt(const void *data, u32 size) 89 { 90 struct batadv_tt_common_entry *tt; 91 u32 hash = 0; 92 93 tt = (struct batadv_tt_common_entry *)data; 94 hash = jhash(&tt->addr, ETH_ALEN, hash); 95 hash = jhash(&tt->vid, sizeof(tt->vid), hash); 96 97 return hash % size; 98 } 99 100 /** 101 * batadv_tt_hash_find - look for a client in the given hash table 102 * @hash: the hash table to search 103 * @addr: the mac address of the client to look for 104 * @vid: VLAN identifier 105 * 106 * Returns a pointer to the tt_common struct belonging to the searched client if 107 * found, NULL otherwise. 108 */ 109 static struct batadv_tt_common_entry * 110 batadv_tt_hash_find(struct batadv_hashtable *hash, const u8 *addr, 111 unsigned short vid) 112 { 113 struct hlist_head *head; 114 struct batadv_tt_common_entry to_search, *tt, *tt_tmp = NULL; 115 u32 index; 116 117 if (!hash) 118 return NULL; 119 120 ether_addr_copy(to_search.addr, addr); 121 to_search.vid = vid; 122 123 index = batadv_choose_tt(&to_search, hash->size); 124 head = &hash->table[index]; 125 126 rcu_read_lock(); 127 hlist_for_each_entry_rcu(tt, head, hash_entry) { 128 if (!batadv_compare_eth(tt, addr)) 129 continue; 130 131 if (tt->vid != vid) 132 continue; 133 134 if (!atomic_inc_not_zero(&tt->refcount)) 135 continue; 136 137 tt_tmp = tt; 138 break; 139 } 140 rcu_read_unlock(); 141 142 return tt_tmp; 143 } 144 145 /** 146 * batadv_tt_local_hash_find - search the local table for a given client 147 * @bat_priv: the bat priv with all the soft interface information 148 * @addr: the mac address of the client to look for 149 * @vid: VLAN identifier 150 * 151 * Returns a pointer to the corresponding tt_local_entry struct if the client is 152 * found, NULL otherwise. 153 */ 154 static struct batadv_tt_local_entry * 155 batadv_tt_local_hash_find(struct batadv_priv *bat_priv, const u8 *addr, 156 unsigned short vid) 157 { 158 struct batadv_tt_common_entry *tt_common_entry; 159 struct batadv_tt_local_entry *tt_local_entry = NULL; 160 161 tt_common_entry = batadv_tt_hash_find(bat_priv->tt.local_hash, addr, 162 vid); 163 if (tt_common_entry) 164 tt_local_entry = container_of(tt_common_entry, 165 struct batadv_tt_local_entry, 166 common); 167 return tt_local_entry; 168 } 169 170 /** 171 * batadv_tt_global_hash_find - search the global table for a given client 172 * @bat_priv: the bat priv with all the soft interface information 173 * @addr: the mac address of the client to look for 174 * @vid: VLAN identifier 175 * 176 * Returns a pointer to the corresponding tt_global_entry struct if the client 177 * is found, NULL otherwise. 178 */ 179 static struct batadv_tt_global_entry * 180 batadv_tt_global_hash_find(struct batadv_priv *bat_priv, const u8 *addr, 181 unsigned short vid) 182 { 183 struct batadv_tt_common_entry *tt_common_entry; 184 struct batadv_tt_global_entry *tt_global_entry = NULL; 185 186 tt_common_entry = batadv_tt_hash_find(bat_priv->tt.global_hash, addr, 187 vid); 188 if (tt_common_entry) 189 tt_global_entry = container_of(tt_common_entry, 190 struct batadv_tt_global_entry, 191 common); 192 return tt_global_entry; 193 } 194 195 static void 196 batadv_tt_local_entry_free_ref(struct batadv_tt_local_entry *tt_local_entry) 197 { 198 if (atomic_dec_and_test(&tt_local_entry->common.refcount)) 199 kfree_rcu(tt_local_entry, common.rcu); 200 } 201 202 /** 203 * batadv_tt_global_entry_free_ref - decrement the refcounter for a 204 * tt_global_entry and possibly free it 205 * @tt_global_entry: the object to free 206 */ 207 static void 208 batadv_tt_global_entry_free_ref(struct batadv_tt_global_entry *tt_global_entry) 209 { 210 if (atomic_dec_and_test(&tt_global_entry->common.refcount)) { 211 batadv_tt_global_del_orig_list(tt_global_entry); 212 kfree_rcu(tt_global_entry, common.rcu); 213 } 214 } 215 216 /** 217 * batadv_tt_global_hash_count - count the number of orig entries 218 * @hash: hash table containing the tt entries 219 * @addr: the mac address of the client to count entries for 220 * @vid: VLAN identifier 221 * 222 * Return the number of originators advertising the given address/data 223 * (excluding ourself). 224 */ 225 int batadv_tt_global_hash_count(struct batadv_priv *bat_priv, 226 const u8 *addr, unsigned short vid) 227 { 228 struct batadv_tt_global_entry *tt_global_entry; 229 int count; 230 231 tt_global_entry = batadv_tt_global_hash_find(bat_priv, addr, vid); 232 if (!tt_global_entry) 233 return 0; 234 235 count = atomic_read(&tt_global_entry->orig_list_count); 236 batadv_tt_global_entry_free_ref(tt_global_entry); 237 238 return count; 239 } 240 241 static void batadv_tt_orig_list_entry_free_rcu(struct rcu_head *rcu) 242 { 243 struct batadv_tt_orig_list_entry *orig_entry; 244 245 orig_entry = container_of(rcu, struct batadv_tt_orig_list_entry, rcu); 246 247 /* We are in an rcu callback here, therefore we cannot use 248 * batadv_orig_node_free_ref() and its call_rcu(): 249 * An rcu_barrier() wouldn't wait for that to finish 250 */ 251 batadv_orig_node_free_ref_now(orig_entry->orig_node); 252 kfree(orig_entry); 253 } 254 255 /** 256 * batadv_tt_local_size_mod - change the size by v of the local table identified 257 * by vid 258 * @bat_priv: the bat priv with all the soft interface information 259 * @vid: the VLAN identifier of the sub-table to change 260 * @v: the amount to sum to the local table size 261 */ 262 static void batadv_tt_local_size_mod(struct batadv_priv *bat_priv, 263 unsigned short vid, int v) 264 { 265 struct batadv_softif_vlan *vlan; 266 267 vlan = batadv_softif_vlan_get(bat_priv, vid); 268 if (!vlan) 269 return; 270 271 atomic_add(v, &vlan->tt.num_entries); 272 273 batadv_softif_vlan_free_ref(vlan); 274 } 275 276 /** 277 * batadv_tt_local_size_inc - increase by one the local table size for the given 278 * vid 279 * @bat_priv: the bat priv with all the soft interface information 280 * @vid: the VLAN identifier 281 */ 282 static void batadv_tt_local_size_inc(struct batadv_priv *bat_priv, 283 unsigned short vid) 284 { 285 batadv_tt_local_size_mod(bat_priv, vid, 1); 286 } 287 288 /** 289 * batadv_tt_local_size_dec - decrease by one the local table size for the given 290 * vid 291 * @bat_priv: the bat priv with all the soft interface information 292 * @vid: the VLAN identifier 293 */ 294 static void batadv_tt_local_size_dec(struct batadv_priv *bat_priv, 295 unsigned short vid) 296 { 297 batadv_tt_local_size_mod(bat_priv, vid, -1); 298 } 299 300 /** 301 * batadv_tt_global_size_mod - change the size by v of the local table 302 * identified by vid 303 * @bat_priv: the bat priv with all the soft interface information 304 * @vid: the VLAN identifier 305 * @v: the amount to sum to the global table size 306 */ 307 static void batadv_tt_global_size_mod(struct batadv_orig_node *orig_node, 308 unsigned short vid, int v) 309 { 310 struct batadv_orig_node_vlan *vlan; 311 312 vlan = batadv_orig_node_vlan_new(orig_node, vid); 313 if (!vlan) 314 return; 315 316 if (atomic_add_return(v, &vlan->tt.num_entries) == 0) { 317 spin_lock_bh(&orig_node->vlan_list_lock); 318 hlist_del_init_rcu(&vlan->list); 319 spin_unlock_bh(&orig_node->vlan_list_lock); 320 batadv_orig_node_vlan_free_ref(vlan); 321 } 322 323 batadv_orig_node_vlan_free_ref(vlan); 324 } 325 326 /** 327 * batadv_tt_global_size_inc - increase by one the global table size for the 328 * given vid 329 * @orig_node: the originator which global table size has to be decreased 330 * @vid: the vlan identifier 331 */ 332 static void batadv_tt_global_size_inc(struct batadv_orig_node *orig_node, 333 unsigned short vid) 334 { 335 batadv_tt_global_size_mod(orig_node, vid, 1); 336 } 337 338 /** 339 * batadv_tt_global_size_dec - decrease by one the global table size for the 340 * given vid 341 * @orig_node: the originator which global table size has to be decreased 342 * @vid: the vlan identifier 343 */ 344 static void batadv_tt_global_size_dec(struct batadv_orig_node *orig_node, 345 unsigned short vid) 346 { 347 batadv_tt_global_size_mod(orig_node, vid, -1); 348 } 349 350 static void 351 batadv_tt_orig_list_entry_free_ref(struct batadv_tt_orig_list_entry *orig_entry) 352 { 353 if (!atomic_dec_and_test(&orig_entry->refcount)) 354 return; 355 356 call_rcu(&orig_entry->rcu, batadv_tt_orig_list_entry_free_rcu); 357 } 358 359 /** 360 * batadv_tt_local_event - store a local TT event (ADD/DEL) 361 * @bat_priv: the bat priv with all the soft interface information 362 * @tt_local_entry: the TT entry involved in the event 363 * @event_flags: flags to store in the event structure 364 */ 365 static void batadv_tt_local_event(struct batadv_priv *bat_priv, 366 struct batadv_tt_local_entry *tt_local_entry, 367 u8 event_flags) 368 { 369 struct batadv_tt_change_node *tt_change_node, *entry, *safe; 370 struct batadv_tt_common_entry *common = &tt_local_entry->common; 371 u8 flags = common->flags | event_flags; 372 bool event_removed = false; 373 bool del_op_requested, del_op_entry; 374 375 tt_change_node = kmalloc(sizeof(*tt_change_node), GFP_ATOMIC); 376 if (!tt_change_node) 377 return; 378 379 tt_change_node->change.flags = flags; 380 memset(tt_change_node->change.reserved, 0, 381 sizeof(tt_change_node->change.reserved)); 382 ether_addr_copy(tt_change_node->change.addr, common->addr); 383 tt_change_node->change.vid = htons(common->vid); 384 385 del_op_requested = flags & BATADV_TT_CLIENT_DEL; 386 387 /* check for ADD+DEL or DEL+ADD events */ 388 spin_lock_bh(&bat_priv->tt.changes_list_lock); 389 list_for_each_entry_safe(entry, safe, &bat_priv->tt.changes_list, 390 list) { 391 if (!batadv_compare_eth(entry->change.addr, common->addr)) 392 continue; 393 394 /* DEL+ADD in the same orig interval have no effect and can be 395 * removed to avoid silly behaviour on the receiver side. The 396 * other way around (ADD+DEL) can happen in case of roaming of 397 * a client still in the NEW state. Roaming of NEW clients is 398 * now possible due to automatically recognition of "temporary" 399 * clients 400 */ 401 del_op_entry = entry->change.flags & BATADV_TT_CLIENT_DEL; 402 if (!del_op_requested && del_op_entry) 403 goto del; 404 if (del_op_requested && !del_op_entry) 405 goto del; 406 407 /* this is a second add in the same originator interval. It 408 * means that flags have been changed: update them! 409 */ 410 if (!del_op_requested && !del_op_entry) 411 entry->change.flags = flags; 412 413 continue; 414 del: 415 list_del(&entry->list); 416 kfree(entry); 417 kfree(tt_change_node); 418 event_removed = true; 419 goto unlock; 420 } 421 422 /* track the change in the OGMinterval list */ 423 list_add_tail(&tt_change_node->list, &bat_priv->tt.changes_list); 424 425 unlock: 426 spin_unlock_bh(&bat_priv->tt.changes_list_lock); 427 428 if (event_removed) 429 atomic_dec(&bat_priv->tt.local_changes); 430 else 431 atomic_inc(&bat_priv->tt.local_changes); 432 } 433 434 /** 435 * batadv_tt_len - compute length in bytes of given number of tt changes 436 * @changes_num: number of tt changes 437 * 438 * Returns computed length in bytes. 439 */ 440 static int batadv_tt_len(int changes_num) 441 { 442 return changes_num * sizeof(struct batadv_tvlv_tt_change); 443 } 444 445 /** 446 * batadv_tt_entries - compute the number of entries fitting in tt_len bytes 447 * @tt_len: available space 448 * 449 * Returns the number of entries. 450 */ 451 static u16 batadv_tt_entries(u16 tt_len) 452 { 453 return tt_len / batadv_tt_len(1); 454 } 455 456 /** 457 * batadv_tt_local_table_transmit_size - calculates the local translation table 458 * size when transmitted over the air 459 * @bat_priv: the bat priv with all the soft interface information 460 * 461 * Returns local translation table size in bytes. 462 */ 463 static int batadv_tt_local_table_transmit_size(struct batadv_priv *bat_priv) 464 { 465 u16 num_vlan = 0; 466 u16 tt_local_entries = 0; 467 struct batadv_softif_vlan *vlan; 468 int hdr_size; 469 470 rcu_read_lock(); 471 hlist_for_each_entry_rcu(vlan, &bat_priv->softif_vlan_list, list) { 472 num_vlan++; 473 tt_local_entries += atomic_read(&vlan->tt.num_entries); 474 } 475 rcu_read_unlock(); 476 477 /* header size of tvlv encapsulated tt response payload */ 478 hdr_size = sizeof(struct batadv_unicast_tvlv_packet); 479 hdr_size += sizeof(struct batadv_tvlv_hdr); 480 hdr_size += sizeof(struct batadv_tvlv_tt_data); 481 hdr_size += num_vlan * sizeof(struct batadv_tvlv_tt_vlan_data); 482 483 return hdr_size + batadv_tt_len(tt_local_entries); 484 } 485 486 static int batadv_tt_local_init(struct batadv_priv *bat_priv) 487 { 488 if (bat_priv->tt.local_hash) 489 return 0; 490 491 bat_priv->tt.local_hash = batadv_hash_new(1024); 492 493 if (!bat_priv->tt.local_hash) 494 return -ENOMEM; 495 496 batadv_hash_set_lock_class(bat_priv->tt.local_hash, 497 &batadv_tt_local_hash_lock_class_key); 498 499 return 0; 500 } 501 502 static void batadv_tt_global_free(struct batadv_priv *bat_priv, 503 struct batadv_tt_global_entry *tt_global, 504 const char *message) 505 { 506 batadv_dbg(BATADV_DBG_TT, bat_priv, 507 "Deleting global tt entry %pM (vid: %d): %s\n", 508 tt_global->common.addr, 509 BATADV_PRINT_VID(tt_global->common.vid), message); 510 511 batadv_hash_remove(bat_priv->tt.global_hash, batadv_compare_tt, 512 batadv_choose_tt, &tt_global->common); 513 batadv_tt_global_entry_free_ref(tt_global); 514 } 515 516 /** 517 * batadv_tt_local_add - add a new client to the local table or update an 518 * existing client 519 * @soft_iface: netdev struct of the mesh interface 520 * @addr: the mac address of the client to add 521 * @vid: VLAN identifier 522 * @ifindex: index of the interface where the client is connected to (useful to 523 * identify wireless clients) 524 * @mark: the value contained in the skb->mark field of the received packet (if 525 * any) 526 * 527 * Returns true if the client was successfully added, false otherwise. 528 */ 529 bool batadv_tt_local_add(struct net_device *soft_iface, const u8 *addr, 530 unsigned short vid, int ifindex, u32 mark) 531 { 532 struct batadv_priv *bat_priv = netdev_priv(soft_iface); 533 struct batadv_tt_local_entry *tt_local; 534 struct batadv_tt_global_entry *tt_global = NULL; 535 struct batadv_softif_vlan *vlan; 536 struct net_device *in_dev = NULL; 537 struct hlist_head *head; 538 struct batadv_tt_orig_list_entry *orig_entry; 539 int hash_added, table_size, packet_size_max; 540 bool ret = false; 541 bool roamed_back = false; 542 u8 remote_flags; 543 u32 match_mark; 544 545 if (ifindex != BATADV_NULL_IFINDEX) 546 in_dev = dev_get_by_index(&init_net, ifindex); 547 548 tt_local = batadv_tt_local_hash_find(bat_priv, addr, vid); 549 550 if (!is_multicast_ether_addr(addr)) 551 tt_global = batadv_tt_global_hash_find(bat_priv, addr, vid); 552 553 if (tt_local) { 554 tt_local->last_seen = jiffies; 555 if (tt_local->common.flags & BATADV_TT_CLIENT_PENDING) { 556 batadv_dbg(BATADV_DBG_TT, bat_priv, 557 "Re-adding pending client %pM (vid: %d)\n", 558 addr, BATADV_PRINT_VID(vid)); 559 /* whatever the reason why the PENDING flag was set, 560 * this is a client which was enqueued to be removed in 561 * this orig_interval. Since it popped up again, the 562 * flag can be reset like it was never enqueued 563 */ 564 tt_local->common.flags &= ~BATADV_TT_CLIENT_PENDING; 565 goto add_event; 566 } 567 568 if (tt_local->common.flags & BATADV_TT_CLIENT_ROAM) { 569 batadv_dbg(BATADV_DBG_TT, bat_priv, 570 "Roaming client %pM (vid: %d) came back to its original location\n", 571 addr, BATADV_PRINT_VID(vid)); 572 /* the ROAM flag is set because this client roamed away 573 * and the node got a roaming_advertisement message. Now 574 * that the client popped up again at its original 575 * location such flag can be unset 576 */ 577 tt_local->common.flags &= ~BATADV_TT_CLIENT_ROAM; 578 roamed_back = true; 579 } 580 goto check_roaming; 581 } 582 583 /* Ignore the client if we cannot send it in a full table response. */ 584 table_size = batadv_tt_local_table_transmit_size(bat_priv); 585 table_size += batadv_tt_len(1); 586 packet_size_max = atomic_read(&bat_priv->packet_size_max); 587 if (table_size > packet_size_max) { 588 net_ratelimited_function(batadv_info, soft_iface, 589 "Local translation table size (%i) exceeds maximum packet size (%i); Ignoring new local tt entry: %pM\n", 590 table_size, packet_size_max, addr); 591 goto out; 592 } 593 594 tt_local = kmalloc(sizeof(*tt_local), GFP_ATOMIC); 595 if (!tt_local) 596 goto out; 597 598 /* increase the refcounter of the related vlan */ 599 vlan = batadv_softif_vlan_get(bat_priv, vid); 600 if (WARN(!vlan, "adding TT local entry %pM to non-existent VLAN %d", 601 addr, BATADV_PRINT_VID(vid))) { 602 kfree(tt_local); 603 tt_local = NULL; 604 goto out; 605 } 606 607 batadv_dbg(BATADV_DBG_TT, bat_priv, 608 "Creating new local tt entry: %pM (vid: %d, ttvn: %d)\n", 609 addr, BATADV_PRINT_VID(vid), 610 (u8)atomic_read(&bat_priv->tt.vn)); 611 612 ether_addr_copy(tt_local->common.addr, addr); 613 /* The local entry has to be marked as NEW to avoid to send it in 614 * a full table response going out before the next ttvn increment 615 * (consistency check) 616 */ 617 tt_local->common.flags = BATADV_TT_CLIENT_NEW; 618 tt_local->common.vid = vid; 619 if (batadv_is_wifi_netdev(in_dev)) 620 tt_local->common.flags |= BATADV_TT_CLIENT_WIFI; 621 atomic_set(&tt_local->common.refcount, 2); 622 tt_local->last_seen = jiffies; 623 tt_local->common.added_at = tt_local->last_seen; 624 625 /* the batman interface mac and multicast addresses should never be 626 * purged 627 */ 628 if (batadv_compare_eth(addr, soft_iface->dev_addr) || 629 is_multicast_ether_addr(addr)) 630 tt_local->common.flags |= BATADV_TT_CLIENT_NOPURGE; 631 632 hash_added = batadv_hash_add(bat_priv->tt.local_hash, batadv_compare_tt, 633 batadv_choose_tt, &tt_local->common, 634 &tt_local->common.hash_entry); 635 636 if (unlikely(hash_added != 0)) { 637 /* remove the reference for the hash */ 638 batadv_tt_local_entry_free_ref(tt_local); 639 batadv_softif_vlan_free_ref(vlan); 640 goto out; 641 } 642 643 add_event: 644 batadv_tt_local_event(bat_priv, tt_local, BATADV_NO_FLAGS); 645 646 check_roaming: 647 /* Check whether it is a roaming, but don't do anything if the roaming 648 * process has already been handled 649 */ 650 if (tt_global && !(tt_global->common.flags & BATADV_TT_CLIENT_ROAM)) { 651 /* These node are probably going to update their tt table */ 652 head = &tt_global->orig_list; 653 rcu_read_lock(); 654 hlist_for_each_entry_rcu(orig_entry, head, list) { 655 batadv_send_roam_adv(bat_priv, tt_global->common.addr, 656 tt_global->common.vid, 657 orig_entry->orig_node); 658 } 659 rcu_read_unlock(); 660 if (roamed_back) { 661 batadv_tt_global_free(bat_priv, tt_global, 662 "Roaming canceled"); 663 tt_global = NULL; 664 } else { 665 /* The global entry has to be marked as ROAMING and 666 * has to be kept for consistency purpose 667 */ 668 tt_global->common.flags |= BATADV_TT_CLIENT_ROAM; 669 tt_global->roam_at = jiffies; 670 } 671 } 672 673 /* store the current remote flags before altering them. This helps 674 * understanding is flags are changing or not 675 */ 676 remote_flags = tt_local->common.flags & BATADV_TT_REMOTE_MASK; 677 678 if (batadv_is_wifi_netdev(in_dev)) 679 tt_local->common.flags |= BATADV_TT_CLIENT_WIFI; 680 else 681 tt_local->common.flags &= ~BATADV_TT_CLIENT_WIFI; 682 683 /* check the mark in the skb: if it's equal to the configured 684 * isolation_mark, it means the packet is coming from an isolated 685 * non-mesh client 686 */ 687 match_mark = (mark & bat_priv->isolation_mark_mask); 688 if (bat_priv->isolation_mark_mask && 689 match_mark == bat_priv->isolation_mark) 690 tt_local->common.flags |= BATADV_TT_CLIENT_ISOLA; 691 else 692 tt_local->common.flags &= ~BATADV_TT_CLIENT_ISOLA; 693 694 /* if any "dynamic" flag has been modified, resend an ADD event for this 695 * entry so that all the nodes can get the new flags 696 */ 697 if (remote_flags ^ (tt_local->common.flags & BATADV_TT_REMOTE_MASK)) 698 batadv_tt_local_event(bat_priv, tt_local, BATADV_NO_FLAGS); 699 700 ret = true; 701 out: 702 if (in_dev) 703 dev_put(in_dev); 704 if (tt_local) 705 batadv_tt_local_entry_free_ref(tt_local); 706 if (tt_global) 707 batadv_tt_global_entry_free_ref(tt_global); 708 return ret; 709 } 710 711 /** 712 * batadv_tt_prepare_tvlv_global_data - prepare the TVLV TT header to send 713 * within a TT Response directed to another node 714 * @orig_node: originator for which the TT data has to be prepared 715 * @tt_data: uninitialised pointer to the address of the TVLV buffer 716 * @tt_change: uninitialised pointer to the address of the area where the TT 717 * changed can be stored 718 * @tt_len: pointer to the length to reserve to the tt_change. if -1 this 719 * function reserves the amount of space needed to send the entire global TT 720 * table. In case of success the value is updated with the real amount of 721 * reserved bytes 722 723 * Allocate the needed amount of memory for the entire TT TVLV and write its 724 * header made up by one tvlv_tt_data object and a series of tvlv_tt_vlan_data 725 * objects, one per active VLAN served by the originator node. 726 * 727 * Return the size of the allocated buffer or 0 in case of failure. 728 */ 729 static u16 730 batadv_tt_prepare_tvlv_global_data(struct batadv_orig_node *orig_node, 731 struct batadv_tvlv_tt_data **tt_data, 732 struct batadv_tvlv_tt_change **tt_change, 733 s32 *tt_len) 734 { 735 u16 num_vlan = 0; 736 u16 num_entries = 0; 737 u16 change_offset; 738 u16 tvlv_len; 739 struct batadv_tvlv_tt_vlan_data *tt_vlan; 740 struct batadv_orig_node_vlan *vlan; 741 u8 *tt_change_ptr; 742 743 rcu_read_lock(); 744 hlist_for_each_entry_rcu(vlan, &orig_node->vlan_list, list) { 745 num_vlan++; 746 num_entries += atomic_read(&vlan->tt.num_entries); 747 } 748 749 change_offset = sizeof(**tt_data); 750 change_offset += num_vlan * sizeof(*tt_vlan); 751 752 /* if tt_len is negative, allocate the space needed by the full table */ 753 if (*tt_len < 0) 754 *tt_len = batadv_tt_len(num_entries); 755 756 tvlv_len = *tt_len; 757 tvlv_len += change_offset; 758 759 *tt_data = kmalloc(tvlv_len, GFP_ATOMIC); 760 if (!*tt_data) { 761 *tt_len = 0; 762 goto out; 763 } 764 765 (*tt_data)->flags = BATADV_NO_FLAGS; 766 (*tt_data)->ttvn = atomic_read(&orig_node->last_ttvn); 767 (*tt_data)->num_vlan = htons(num_vlan); 768 769 tt_vlan = (struct batadv_tvlv_tt_vlan_data *)(*tt_data + 1); 770 hlist_for_each_entry_rcu(vlan, &orig_node->vlan_list, list) { 771 tt_vlan->vid = htons(vlan->vid); 772 tt_vlan->crc = htonl(vlan->tt.crc); 773 774 tt_vlan++; 775 } 776 777 tt_change_ptr = (u8 *)*tt_data + change_offset; 778 *tt_change = (struct batadv_tvlv_tt_change *)tt_change_ptr; 779 780 out: 781 rcu_read_unlock(); 782 return tvlv_len; 783 } 784 785 /** 786 * batadv_tt_prepare_tvlv_local_data - allocate and prepare the TT TVLV for this 787 * node 788 * @bat_priv: the bat priv with all the soft interface information 789 * @tt_data: uninitialised pointer to the address of the TVLV buffer 790 * @tt_change: uninitialised pointer to the address of the area where the TT 791 * changes can be stored 792 * @tt_len: pointer to the length to reserve to the tt_change. if -1 this 793 * function reserves the amount of space needed to send the entire local TT 794 * table. In case of success the value is updated with the real amount of 795 * reserved bytes 796 * 797 * Allocate the needed amount of memory for the entire TT TVLV and write its 798 * header made up by one tvlv_tt_data object and a series of tvlv_tt_vlan_data 799 * objects, one per active VLAN. 800 * 801 * Return the size of the allocated buffer or 0 in case of failure. 802 */ 803 static u16 804 batadv_tt_prepare_tvlv_local_data(struct batadv_priv *bat_priv, 805 struct batadv_tvlv_tt_data **tt_data, 806 struct batadv_tvlv_tt_change **tt_change, 807 s32 *tt_len) 808 { 809 struct batadv_tvlv_tt_vlan_data *tt_vlan; 810 struct batadv_softif_vlan *vlan; 811 u16 num_vlan = 0; 812 u16 num_entries = 0; 813 u16 tvlv_len; 814 u8 *tt_change_ptr; 815 int change_offset; 816 817 rcu_read_lock(); 818 hlist_for_each_entry_rcu(vlan, &bat_priv->softif_vlan_list, list) { 819 num_vlan++; 820 num_entries += atomic_read(&vlan->tt.num_entries); 821 } 822 823 change_offset = sizeof(**tt_data); 824 change_offset += num_vlan * sizeof(*tt_vlan); 825 826 /* if tt_len is negative, allocate the space needed by the full table */ 827 if (*tt_len < 0) 828 *tt_len = batadv_tt_len(num_entries); 829 830 tvlv_len = *tt_len; 831 tvlv_len += change_offset; 832 833 *tt_data = kmalloc(tvlv_len, GFP_ATOMIC); 834 if (!*tt_data) { 835 tvlv_len = 0; 836 goto out; 837 } 838 839 (*tt_data)->flags = BATADV_NO_FLAGS; 840 (*tt_data)->ttvn = atomic_read(&bat_priv->tt.vn); 841 (*tt_data)->num_vlan = htons(num_vlan); 842 843 tt_vlan = (struct batadv_tvlv_tt_vlan_data *)(*tt_data + 1); 844 hlist_for_each_entry_rcu(vlan, &bat_priv->softif_vlan_list, list) { 845 tt_vlan->vid = htons(vlan->vid); 846 tt_vlan->crc = htonl(vlan->tt.crc); 847 848 tt_vlan++; 849 } 850 851 tt_change_ptr = (u8 *)*tt_data + change_offset; 852 *tt_change = (struct batadv_tvlv_tt_change *)tt_change_ptr; 853 854 out: 855 rcu_read_unlock(); 856 return tvlv_len; 857 } 858 859 /** 860 * batadv_tt_tvlv_container_update - update the translation table tvlv container 861 * after local tt changes have been committed 862 * @bat_priv: the bat priv with all the soft interface information 863 */ 864 static void batadv_tt_tvlv_container_update(struct batadv_priv *bat_priv) 865 { 866 struct batadv_tt_change_node *entry, *safe; 867 struct batadv_tvlv_tt_data *tt_data; 868 struct batadv_tvlv_tt_change *tt_change; 869 int tt_diff_len, tt_change_len = 0; 870 int tt_diff_entries_num = 0; 871 int tt_diff_entries_count = 0; 872 u16 tvlv_len; 873 874 tt_diff_entries_num = atomic_read(&bat_priv->tt.local_changes); 875 tt_diff_len = batadv_tt_len(tt_diff_entries_num); 876 877 /* if we have too many changes for one packet don't send any 878 * and wait for the tt table request which will be fragmented 879 */ 880 if (tt_diff_len > bat_priv->soft_iface->mtu) 881 tt_diff_len = 0; 882 883 tvlv_len = batadv_tt_prepare_tvlv_local_data(bat_priv, &tt_data, 884 &tt_change, &tt_diff_len); 885 if (!tvlv_len) 886 return; 887 888 tt_data->flags = BATADV_TT_OGM_DIFF; 889 890 if (tt_diff_len == 0) 891 goto container_register; 892 893 spin_lock_bh(&bat_priv->tt.changes_list_lock); 894 atomic_set(&bat_priv->tt.local_changes, 0); 895 896 list_for_each_entry_safe(entry, safe, &bat_priv->tt.changes_list, 897 list) { 898 if (tt_diff_entries_count < tt_diff_entries_num) { 899 memcpy(tt_change + tt_diff_entries_count, 900 &entry->change, 901 sizeof(struct batadv_tvlv_tt_change)); 902 tt_diff_entries_count++; 903 } 904 list_del(&entry->list); 905 kfree(entry); 906 } 907 spin_unlock_bh(&bat_priv->tt.changes_list_lock); 908 909 /* Keep the buffer for possible tt_request */ 910 spin_lock_bh(&bat_priv->tt.last_changeset_lock); 911 kfree(bat_priv->tt.last_changeset); 912 bat_priv->tt.last_changeset_len = 0; 913 bat_priv->tt.last_changeset = NULL; 914 tt_change_len = batadv_tt_len(tt_diff_entries_count); 915 /* check whether this new OGM has no changes due to size problems */ 916 if (tt_diff_entries_count > 0) { 917 /* if kmalloc() fails we will reply with the full table 918 * instead of providing the diff 919 */ 920 bat_priv->tt.last_changeset = kzalloc(tt_diff_len, GFP_ATOMIC); 921 if (bat_priv->tt.last_changeset) { 922 memcpy(bat_priv->tt.last_changeset, 923 tt_change, tt_change_len); 924 bat_priv->tt.last_changeset_len = tt_diff_len; 925 } 926 } 927 spin_unlock_bh(&bat_priv->tt.last_changeset_lock); 928 929 container_register: 930 batadv_tvlv_container_register(bat_priv, BATADV_TVLV_TT, 1, tt_data, 931 tvlv_len); 932 kfree(tt_data); 933 } 934 935 int batadv_tt_local_seq_print_text(struct seq_file *seq, void *offset) 936 { 937 struct net_device *net_dev = (struct net_device *)seq->private; 938 struct batadv_priv *bat_priv = netdev_priv(net_dev); 939 struct batadv_hashtable *hash = bat_priv->tt.local_hash; 940 struct batadv_tt_common_entry *tt_common_entry; 941 struct batadv_tt_local_entry *tt_local; 942 struct batadv_hard_iface *primary_if; 943 struct batadv_softif_vlan *vlan; 944 struct hlist_head *head; 945 unsigned short vid; 946 u32 i; 947 int last_seen_secs; 948 int last_seen_msecs; 949 unsigned long last_seen_jiffies; 950 bool no_purge; 951 u16 np_flag = BATADV_TT_CLIENT_NOPURGE; 952 953 primary_if = batadv_seq_print_text_primary_if_get(seq); 954 if (!primary_if) 955 goto out; 956 957 seq_printf(seq, 958 "Locally retrieved addresses (from %s) announced via TT (TTVN: %u):\n", 959 net_dev->name, (u8)atomic_read(&bat_priv->tt.vn)); 960 seq_printf(seq, " %-13s %s %-8s %-9s (%-10s)\n", "Client", "VID", 961 "Flags", "Last seen", "CRC"); 962 963 for (i = 0; i < hash->size; i++) { 964 head = &hash->table[i]; 965 966 rcu_read_lock(); 967 hlist_for_each_entry_rcu(tt_common_entry, 968 head, hash_entry) { 969 tt_local = container_of(tt_common_entry, 970 struct batadv_tt_local_entry, 971 common); 972 vid = tt_common_entry->vid; 973 last_seen_jiffies = jiffies - tt_local->last_seen; 974 last_seen_msecs = jiffies_to_msecs(last_seen_jiffies); 975 last_seen_secs = last_seen_msecs / 1000; 976 last_seen_msecs = last_seen_msecs % 1000; 977 978 no_purge = tt_common_entry->flags & np_flag; 979 980 vlan = batadv_softif_vlan_get(bat_priv, vid); 981 if (!vlan) { 982 seq_printf(seq, "Cannot retrieve VLAN %d\n", 983 BATADV_PRINT_VID(vid)); 984 continue; 985 } 986 987 seq_printf(seq, 988 " * %pM %4i [%c%c%c%c%c%c] %3u.%03u (%#.8x)\n", 989 tt_common_entry->addr, 990 BATADV_PRINT_VID(tt_common_entry->vid), 991 ((tt_common_entry->flags & 992 BATADV_TT_CLIENT_ROAM) ? 'R' : '.'), 993 no_purge ? 'P' : '.', 994 ((tt_common_entry->flags & 995 BATADV_TT_CLIENT_NEW) ? 'N' : '.'), 996 ((tt_common_entry->flags & 997 BATADV_TT_CLIENT_PENDING) ? 'X' : '.'), 998 ((tt_common_entry->flags & 999 BATADV_TT_CLIENT_WIFI) ? 'W' : '.'), 1000 ((tt_common_entry->flags & 1001 BATADV_TT_CLIENT_ISOLA) ? 'I' : '.'), 1002 no_purge ? 0 : last_seen_secs, 1003 no_purge ? 0 : last_seen_msecs, 1004 vlan->tt.crc); 1005 1006 batadv_softif_vlan_free_ref(vlan); 1007 } 1008 rcu_read_unlock(); 1009 } 1010 out: 1011 if (primary_if) 1012 batadv_hardif_free_ref(primary_if); 1013 return 0; 1014 } 1015 1016 static void 1017 batadv_tt_local_set_pending(struct batadv_priv *bat_priv, 1018 struct batadv_tt_local_entry *tt_local_entry, 1019 u16 flags, const char *message) 1020 { 1021 batadv_tt_local_event(bat_priv, tt_local_entry, flags); 1022 1023 /* The local client has to be marked as "pending to be removed" but has 1024 * to be kept in the table in order to send it in a full table 1025 * response issued before the net ttvn increment (consistency check) 1026 */ 1027 tt_local_entry->common.flags |= BATADV_TT_CLIENT_PENDING; 1028 1029 batadv_dbg(BATADV_DBG_TT, bat_priv, 1030 "Local tt entry (%pM, vid: %d) pending to be removed: %s\n", 1031 tt_local_entry->common.addr, 1032 BATADV_PRINT_VID(tt_local_entry->common.vid), message); 1033 } 1034 1035 /** 1036 * batadv_tt_local_remove - logically remove an entry from the local table 1037 * @bat_priv: the bat priv with all the soft interface information 1038 * @addr: the MAC address of the client to remove 1039 * @vid: VLAN identifier 1040 * @message: message to append to the log on deletion 1041 * @roaming: true if the deletion is due to a roaming event 1042 * 1043 * Returns the flags assigned to the local entry before being deleted 1044 */ 1045 u16 batadv_tt_local_remove(struct batadv_priv *bat_priv, const u8 *addr, 1046 unsigned short vid, const char *message, 1047 bool roaming) 1048 { 1049 struct batadv_tt_local_entry *tt_local_entry; 1050 u16 flags, curr_flags = BATADV_NO_FLAGS; 1051 struct batadv_softif_vlan *vlan; 1052 void *tt_entry_exists; 1053 1054 tt_local_entry = batadv_tt_local_hash_find(bat_priv, addr, vid); 1055 if (!tt_local_entry) 1056 goto out; 1057 1058 curr_flags = tt_local_entry->common.flags; 1059 1060 flags = BATADV_TT_CLIENT_DEL; 1061 /* if this global entry addition is due to a roaming, the node has to 1062 * mark the local entry as "roamed" in order to correctly reroute 1063 * packets later 1064 */ 1065 if (roaming) { 1066 flags |= BATADV_TT_CLIENT_ROAM; 1067 /* mark the local client as ROAMed */ 1068 tt_local_entry->common.flags |= BATADV_TT_CLIENT_ROAM; 1069 } 1070 1071 if (!(tt_local_entry->common.flags & BATADV_TT_CLIENT_NEW)) { 1072 batadv_tt_local_set_pending(bat_priv, tt_local_entry, flags, 1073 message); 1074 goto out; 1075 } 1076 /* if this client has been added right now, it is possible to 1077 * immediately purge it 1078 */ 1079 batadv_tt_local_event(bat_priv, tt_local_entry, BATADV_TT_CLIENT_DEL); 1080 1081 tt_entry_exists = batadv_hash_remove(bat_priv->tt.local_hash, 1082 batadv_compare_tt, 1083 batadv_choose_tt, 1084 &tt_local_entry->common); 1085 if (!tt_entry_exists) 1086 goto out; 1087 1088 /* extra call to free the local tt entry */ 1089 batadv_tt_local_entry_free_ref(tt_local_entry); 1090 1091 /* decrease the reference held for this vlan */ 1092 vlan = batadv_softif_vlan_get(bat_priv, vid); 1093 if (!vlan) 1094 goto out; 1095 1096 batadv_softif_vlan_free_ref(vlan); 1097 batadv_softif_vlan_free_ref(vlan); 1098 1099 out: 1100 if (tt_local_entry) 1101 batadv_tt_local_entry_free_ref(tt_local_entry); 1102 1103 return curr_flags; 1104 } 1105 1106 /** 1107 * batadv_tt_local_purge_list - purge inactive tt local entries 1108 * @bat_priv: the bat priv with all the soft interface information 1109 * @head: pointer to the list containing the local tt entries 1110 * @timeout: parameter deciding whether a given tt local entry is considered 1111 * inactive or not 1112 */ 1113 static void batadv_tt_local_purge_list(struct batadv_priv *bat_priv, 1114 struct hlist_head *head, 1115 int timeout) 1116 { 1117 struct batadv_tt_local_entry *tt_local_entry; 1118 struct batadv_tt_common_entry *tt_common_entry; 1119 struct hlist_node *node_tmp; 1120 1121 hlist_for_each_entry_safe(tt_common_entry, node_tmp, head, 1122 hash_entry) { 1123 tt_local_entry = container_of(tt_common_entry, 1124 struct batadv_tt_local_entry, 1125 common); 1126 if (tt_local_entry->common.flags & BATADV_TT_CLIENT_NOPURGE) 1127 continue; 1128 1129 /* entry already marked for deletion */ 1130 if (tt_local_entry->common.flags & BATADV_TT_CLIENT_PENDING) 1131 continue; 1132 1133 if (!batadv_has_timed_out(tt_local_entry->last_seen, timeout)) 1134 continue; 1135 1136 batadv_tt_local_set_pending(bat_priv, tt_local_entry, 1137 BATADV_TT_CLIENT_DEL, "timed out"); 1138 } 1139 } 1140 1141 /** 1142 * batadv_tt_local_purge - purge inactive tt local entries 1143 * @bat_priv: the bat priv with all the soft interface information 1144 * @timeout: parameter deciding whether a given tt local entry is considered 1145 * inactive or not 1146 */ 1147 static void batadv_tt_local_purge(struct batadv_priv *bat_priv, 1148 int timeout) 1149 { 1150 struct batadv_hashtable *hash = bat_priv->tt.local_hash; 1151 struct hlist_head *head; 1152 spinlock_t *list_lock; /* protects write access to the hash lists */ 1153 u32 i; 1154 1155 for (i = 0; i < hash->size; i++) { 1156 head = &hash->table[i]; 1157 list_lock = &hash->list_locks[i]; 1158 1159 spin_lock_bh(list_lock); 1160 batadv_tt_local_purge_list(bat_priv, head, timeout); 1161 spin_unlock_bh(list_lock); 1162 } 1163 } 1164 1165 static void batadv_tt_local_table_free(struct batadv_priv *bat_priv) 1166 { 1167 struct batadv_hashtable *hash; 1168 spinlock_t *list_lock; /* protects write access to the hash lists */ 1169 struct batadv_tt_common_entry *tt_common_entry; 1170 struct batadv_tt_local_entry *tt_local; 1171 struct batadv_softif_vlan *vlan; 1172 struct hlist_node *node_tmp; 1173 struct hlist_head *head; 1174 u32 i; 1175 1176 if (!bat_priv->tt.local_hash) 1177 return; 1178 1179 hash = bat_priv->tt.local_hash; 1180 1181 for (i = 0; i < hash->size; i++) { 1182 head = &hash->table[i]; 1183 list_lock = &hash->list_locks[i]; 1184 1185 spin_lock_bh(list_lock); 1186 hlist_for_each_entry_safe(tt_common_entry, node_tmp, 1187 head, hash_entry) { 1188 hlist_del_rcu(&tt_common_entry->hash_entry); 1189 tt_local = container_of(tt_common_entry, 1190 struct batadv_tt_local_entry, 1191 common); 1192 1193 /* decrease the reference held for this vlan */ 1194 vlan = batadv_softif_vlan_get(bat_priv, 1195 tt_common_entry->vid); 1196 if (vlan) { 1197 batadv_softif_vlan_free_ref(vlan); 1198 batadv_softif_vlan_free_ref(vlan); 1199 } 1200 1201 batadv_tt_local_entry_free_ref(tt_local); 1202 } 1203 spin_unlock_bh(list_lock); 1204 } 1205 1206 batadv_hash_destroy(hash); 1207 1208 bat_priv->tt.local_hash = NULL; 1209 } 1210 1211 static int batadv_tt_global_init(struct batadv_priv *bat_priv) 1212 { 1213 if (bat_priv->tt.global_hash) 1214 return 0; 1215 1216 bat_priv->tt.global_hash = batadv_hash_new(1024); 1217 1218 if (!bat_priv->tt.global_hash) 1219 return -ENOMEM; 1220 1221 batadv_hash_set_lock_class(bat_priv->tt.global_hash, 1222 &batadv_tt_global_hash_lock_class_key); 1223 1224 return 0; 1225 } 1226 1227 static void batadv_tt_changes_list_free(struct batadv_priv *bat_priv) 1228 { 1229 struct batadv_tt_change_node *entry, *safe; 1230 1231 spin_lock_bh(&bat_priv->tt.changes_list_lock); 1232 1233 list_for_each_entry_safe(entry, safe, &bat_priv->tt.changes_list, 1234 list) { 1235 list_del(&entry->list); 1236 kfree(entry); 1237 } 1238 1239 atomic_set(&bat_priv->tt.local_changes, 0); 1240 spin_unlock_bh(&bat_priv->tt.changes_list_lock); 1241 } 1242 1243 /* retrieves the orig_tt_list_entry belonging to orig_node from the 1244 * batadv_tt_global_entry list 1245 * 1246 * returns it with an increased refcounter, NULL if not found 1247 */ 1248 static struct batadv_tt_orig_list_entry * 1249 batadv_tt_global_orig_entry_find(const struct batadv_tt_global_entry *entry, 1250 const struct batadv_orig_node *orig_node) 1251 { 1252 struct batadv_tt_orig_list_entry *tmp_orig_entry, *orig_entry = NULL; 1253 const struct hlist_head *head; 1254 1255 rcu_read_lock(); 1256 head = &entry->orig_list; 1257 hlist_for_each_entry_rcu(tmp_orig_entry, head, list) { 1258 if (tmp_orig_entry->orig_node != orig_node) 1259 continue; 1260 if (!atomic_inc_not_zero(&tmp_orig_entry->refcount)) 1261 continue; 1262 1263 orig_entry = tmp_orig_entry; 1264 break; 1265 } 1266 rcu_read_unlock(); 1267 1268 return orig_entry; 1269 } 1270 1271 /* find out if an orig_node is already in the list of a tt_global_entry. 1272 * returns true if found, false otherwise 1273 */ 1274 static bool 1275 batadv_tt_global_entry_has_orig(const struct batadv_tt_global_entry *entry, 1276 const struct batadv_orig_node *orig_node) 1277 { 1278 struct batadv_tt_orig_list_entry *orig_entry; 1279 bool found = false; 1280 1281 orig_entry = batadv_tt_global_orig_entry_find(entry, orig_node); 1282 if (orig_entry) { 1283 found = true; 1284 batadv_tt_orig_list_entry_free_ref(orig_entry); 1285 } 1286 1287 return found; 1288 } 1289 1290 static void 1291 batadv_tt_global_orig_entry_add(struct batadv_tt_global_entry *tt_global, 1292 struct batadv_orig_node *orig_node, int ttvn) 1293 { 1294 struct batadv_tt_orig_list_entry *orig_entry; 1295 1296 orig_entry = batadv_tt_global_orig_entry_find(tt_global, orig_node); 1297 if (orig_entry) { 1298 /* refresh the ttvn: the current value could be a bogus one that 1299 * was added during a "temporary client detection" 1300 */ 1301 orig_entry->ttvn = ttvn; 1302 goto out; 1303 } 1304 1305 orig_entry = kzalloc(sizeof(*orig_entry), GFP_ATOMIC); 1306 if (!orig_entry) 1307 goto out; 1308 1309 INIT_HLIST_NODE(&orig_entry->list); 1310 atomic_inc(&orig_node->refcount); 1311 batadv_tt_global_size_inc(orig_node, tt_global->common.vid); 1312 orig_entry->orig_node = orig_node; 1313 orig_entry->ttvn = ttvn; 1314 atomic_set(&orig_entry->refcount, 2); 1315 1316 spin_lock_bh(&tt_global->list_lock); 1317 hlist_add_head_rcu(&orig_entry->list, 1318 &tt_global->orig_list); 1319 spin_unlock_bh(&tt_global->list_lock); 1320 atomic_inc(&tt_global->orig_list_count); 1321 1322 out: 1323 if (orig_entry) 1324 batadv_tt_orig_list_entry_free_ref(orig_entry); 1325 } 1326 1327 /** 1328 * batadv_tt_global_add - add a new TT global entry or update an existing one 1329 * @bat_priv: the bat priv with all the soft interface information 1330 * @orig_node: the originator announcing the client 1331 * @tt_addr: the mac address of the non-mesh client 1332 * @vid: VLAN identifier 1333 * @flags: TT flags that have to be set for this non-mesh client 1334 * @ttvn: the tt version number ever announcing this non-mesh client 1335 * 1336 * Add a new TT global entry for the given originator. If the entry already 1337 * exists add a new reference to the given originator (a global entry can have 1338 * references to multiple originators) and adjust the flags attribute to reflect 1339 * the function argument. 1340 * If a TT local entry exists for this non-mesh client remove it. 1341 * 1342 * The caller must hold orig_node refcount. 1343 * 1344 * Return true if the new entry has been added, false otherwise 1345 */ 1346 static bool batadv_tt_global_add(struct batadv_priv *bat_priv, 1347 struct batadv_orig_node *orig_node, 1348 const unsigned char *tt_addr, 1349 unsigned short vid, u16 flags, u8 ttvn) 1350 { 1351 struct batadv_tt_global_entry *tt_global_entry; 1352 struct batadv_tt_local_entry *tt_local_entry; 1353 bool ret = false; 1354 int hash_added; 1355 struct batadv_tt_common_entry *common; 1356 u16 local_flags; 1357 1358 /* ignore global entries from backbone nodes */ 1359 if (batadv_bla_is_backbone_gw_orig(bat_priv, orig_node->orig, vid)) 1360 return true; 1361 1362 tt_global_entry = batadv_tt_global_hash_find(bat_priv, tt_addr, vid); 1363 tt_local_entry = batadv_tt_local_hash_find(bat_priv, tt_addr, vid); 1364 1365 /* if the node already has a local client for this entry, it has to wait 1366 * for a roaming advertisement instead of manually messing up the global 1367 * table 1368 */ 1369 if ((flags & BATADV_TT_CLIENT_TEMP) && tt_local_entry && 1370 !(tt_local_entry->common.flags & BATADV_TT_CLIENT_NEW)) 1371 goto out; 1372 1373 if (!tt_global_entry) { 1374 tt_global_entry = kzalloc(sizeof(*tt_global_entry), GFP_ATOMIC); 1375 if (!tt_global_entry) 1376 goto out; 1377 1378 common = &tt_global_entry->common; 1379 ether_addr_copy(common->addr, tt_addr); 1380 common->vid = vid; 1381 1382 common->flags = flags; 1383 tt_global_entry->roam_at = 0; 1384 /* node must store current time in case of roaming. This is 1385 * needed to purge this entry out on timeout (if nobody claims 1386 * it) 1387 */ 1388 if (flags & BATADV_TT_CLIENT_ROAM) 1389 tt_global_entry->roam_at = jiffies; 1390 atomic_set(&common->refcount, 2); 1391 common->added_at = jiffies; 1392 1393 INIT_HLIST_HEAD(&tt_global_entry->orig_list); 1394 atomic_set(&tt_global_entry->orig_list_count, 0); 1395 spin_lock_init(&tt_global_entry->list_lock); 1396 1397 hash_added = batadv_hash_add(bat_priv->tt.global_hash, 1398 batadv_compare_tt, 1399 batadv_choose_tt, common, 1400 &common->hash_entry); 1401 1402 if (unlikely(hash_added != 0)) { 1403 /* remove the reference for the hash */ 1404 batadv_tt_global_entry_free_ref(tt_global_entry); 1405 goto out_remove; 1406 } 1407 } else { 1408 common = &tt_global_entry->common; 1409 /* If there is already a global entry, we can use this one for 1410 * our processing. 1411 * But if we are trying to add a temporary client then here are 1412 * two options at this point: 1413 * 1) the global client is not a temporary client: the global 1414 * client has to be left as it is, temporary information 1415 * should never override any already known client state 1416 * 2) the global client is a temporary client: purge the 1417 * originator list and add the new one orig_entry 1418 */ 1419 if (flags & BATADV_TT_CLIENT_TEMP) { 1420 if (!(common->flags & BATADV_TT_CLIENT_TEMP)) 1421 goto out; 1422 if (batadv_tt_global_entry_has_orig(tt_global_entry, 1423 orig_node)) 1424 goto out_remove; 1425 batadv_tt_global_del_orig_list(tt_global_entry); 1426 goto add_orig_entry; 1427 } 1428 1429 /* if the client was temporary added before receiving the first 1430 * OGM announcing it, we have to clear the TEMP flag 1431 */ 1432 common->flags &= ~BATADV_TT_CLIENT_TEMP; 1433 1434 /* the change can carry possible "attribute" flags like the 1435 * TT_CLIENT_WIFI, therefore they have to be copied in the 1436 * client entry 1437 */ 1438 tt_global_entry->common.flags |= flags; 1439 1440 /* If there is the BATADV_TT_CLIENT_ROAM flag set, there is only 1441 * one originator left in the list and we previously received a 1442 * delete + roaming change for this originator. 1443 * 1444 * We should first delete the old originator before adding the 1445 * new one. 1446 */ 1447 if (common->flags & BATADV_TT_CLIENT_ROAM) { 1448 batadv_tt_global_del_orig_list(tt_global_entry); 1449 common->flags &= ~BATADV_TT_CLIENT_ROAM; 1450 tt_global_entry->roam_at = 0; 1451 } 1452 } 1453 add_orig_entry: 1454 /* add the new orig_entry (if needed) or update it */ 1455 batadv_tt_global_orig_entry_add(tt_global_entry, orig_node, ttvn); 1456 1457 batadv_dbg(BATADV_DBG_TT, bat_priv, 1458 "Creating new global tt entry: %pM (vid: %d, via %pM)\n", 1459 common->addr, BATADV_PRINT_VID(common->vid), 1460 orig_node->orig); 1461 ret = true; 1462 1463 out_remove: 1464 /* Do not remove multicast addresses from the local hash on 1465 * global additions 1466 */ 1467 if (is_multicast_ether_addr(tt_addr)) 1468 goto out; 1469 1470 /* remove address from local hash if present */ 1471 local_flags = batadv_tt_local_remove(bat_priv, tt_addr, vid, 1472 "global tt received", 1473 flags & BATADV_TT_CLIENT_ROAM); 1474 tt_global_entry->common.flags |= local_flags & BATADV_TT_CLIENT_WIFI; 1475 1476 if (!(flags & BATADV_TT_CLIENT_ROAM)) 1477 /* this is a normal global add. Therefore the client is not in a 1478 * roaming state anymore. 1479 */ 1480 tt_global_entry->common.flags &= ~BATADV_TT_CLIENT_ROAM; 1481 1482 out: 1483 if (tt_global_entry) 1484 batadv_tt_global_entry_free_ref(tt_global_entry); 1485 if (tt_local_entry) 1486 batadv_tt_local_entry_free_ref(tt_local_entry); 1487 return ret; 1488 } 1489 1490 /** 1491 * batadv_transtable_best_orig - Get best originator list entry from tt entry 1492 * @bat_priv: the bat priv with all the soft interface information 1493 * @tt_global_entry: global translation table entry to be analyzed 1494 * 1495 * This functon assumes the caller holds rcu_read_lock(). 1496 * Returns best originator list entry or NULL on errors. 1497 */ 1498 static struct batadv_tt_orig_list_entry * 1499 batadv_transtable_best_orig(struct batadv_priv *bat_priv, 1500 struct batadv_tt_global_entry *tt_global_entry) 1501 { 1502 struct batadv_neigh_node *router, *best_router = NULL; 1503 struct batadv_algo_ops *bao = bat_priv->bat_algo_ops; 1504 struct hlist_head *head; 1505 struct batadv_tt_orig_list_entry *orig_entry, *best_entry = NULL; 1506 1507 head = &tt_global_entry->orig_list; 1508 hlist_for_each_entry_rcu(orig_entry, head, list) { 1509 router = batadv_orig_router_get(orig_entry->orig_node, 1510 BATADV_IF_DEFAULT); 1511 if (!router) 1512 continue; 1513 1514 if (best_router && 1515 bao->bat_neigh_cmp(router, BATADV_IF_DEFAULT, 1516 best_router, BATADV_IF_DEFAULT) <= 0) { 1517 batadv_neigh_node_free_ref(router); 1518 continue; 1519 } 1520 1521 /* release the refcount for the "old" best */ 1522 if (best_router) 1523 batadv_neigh_node_free_ref(best_router); 1524 1525 best_entry = orig_entry; 1526 best_router = router; 1527 } 1528 1529 if (best_router) 1530 batadv_neigh_node_free_ref(best_router); 1531 1532 return best_entry; 1533 } 1534 1535 /** 1536 * batadv_tt_global_print_entry - print all orig nodes who announce the address 1537 * for this global entry 1538 * @bat_priv: the bat priv with all the soft interface information 1539 * @tt_global_entry: global translation table entry to be printed 1540 * @seq: debugfs table seq_file struct 1541 * 1542 * This functon assumes the caller holds rcu_read_lock(). 1543 */ 1544 static void 1545 batadv_tt_global_print_entry(struct batadv_priv *bat_priv, 1546 struct batadv_tt_global_entry *tt_global_entry, 1547 struct seq_file *seq) 1548 { 1549 struct batadv_tt_orig_list_entry *orig_entry, *best_entry; 1550 struct batadv_tt_common_entry *tt_common_entry; 1551 struct batadv_orig_node_vlan *vlan; 1552 struct hlist_head *head; 1553 u8 last_ttvn; 1554 u16 flags; 1555 1556 tt_common_entry = &tt_global_entry->common; 1557 flags = tt_common_entry->flags; 1558 1559 best_entry = batadv_transtable_best_orig(bat_priv, tt_global_entry); 1560 if (best_entry) { 1561 vlan = batadv_orig_node_vlan_get(best_entry->orig_node, 1562 tt_common_entry->vid); 1563 if (!vlan) { 1564 seq_printf(seq, 1565 " * Cannot retrieve VLAN %d for originator %pM\n", 1566 BATADV_PRINT_VID(tt_common_entry->vid), 1567 best_entry->orig_node->orig); 1568 goto print_list; 1569 } 1570 1571 last_ttvn = atomic_read(&best_entry->orig_node->last_ttvn); 1572 seq_printf(seq, 1573 " %c %pM %4i (%3u) via %pM (%3u) (%#.8x) [%c%c%c%c]\n", 1574 '*', tt_global_entry->common.addr, 1575 BATADV_PRINT_VID(tt_global_entry->common.vid), 1576 best_entry->ttvn, best_entry->orig_node->orig, 1577 last_ttvn, vlan->tt.crc, 1578 ((flags & BATADV_TT_CLIENT_ROAM) ? 'R' : '.'), 1579 ((flags & BATADV_TT_CLIENT_WIFI) ? 'W' : '.'), 1580 ((flags & BATADV_TT_CLIENT_ISOLA) ? 'I' : '.'), 1581 ((flags & BATADV_TT_CLIENT_TEMP) ? 'T' : '.')); 1582 1583 batadv_orig_node_vlan_free_ref(vlan); 1584 } 1585 1586 print_list: 1587 head = &tt_global_entry->orig_list; 1588 1589 hlist_for_each_entry_rcu(orig_entry, head, list) { 1590 if (best_entry == orig_entry) 1591 continue; 1592 1593 vlan = batadv_orig_node_vlan_get(orig_entry->orig_node, 1594 tt_common_entry->vid); 1595 if (!vlan) { 1596 seq_printf(seq, 1597 " + Cannot retrieve VLAN %d for originator %pM\n", 1598 BATADV_PRINT_VID(tt_common_entry->vid), 1599 orig_entry->orig_node->orig); 1600 continue; 1601 } 1602 1603 last_ttvn = atomic_read(&orig_entry->orig_node->last_ttvn); 1604 seq_printf(seq, 1605 " %c %pM %4d (%3u) via %pM (%3u) (%#.8x) [%c%c%c%c]\n", 1606 '+', tt_global_entry->common.addr, 1607 BATADV_PRINT_VID(tt_global_entry->common.vid), 1608 orig_entry->ttvn, orig_entry->orig_node->orig, 1609 last_ttvn, vlan->tt.crc, 1610 ((flags & BATADV_TT_CLIENT_ROAM) ? 'R' : '.'), 1611 ((flags & BATADV_TT_CLIENT_WIFI) ? 'W' : '.'), 1612 ((flags & BATADV_TT_CLIENT_ISOLA) ? 'I' : '.'), 1613 ((flags & BATADV_TT_CLIENT_TEMP) ? 'T' : '.')); 1614 1615 batadv_orig_node_vlan_free_ref(vlan); 1616 } 1617 } 1618 1619 int batadv_tt_global_seq_print_text(struct seq_file *seq, void *offset) 1620 { 1621 struct net_device *net_dev = (struct net_device *)seq->private; 1622 struct batadv_priv *bat_priv = netdev_priv(net_dev); 1623 struct batadv_hashtable *hash = bat_priv->tt.global_hash; 1624 struct batadv_tt_common_entry *tt_common_entry; 1625 struct batadv_tt_global_entry *tt_global; 1626 struct batadv_hard_iface *primary_if; 1627 struct hlist_head *head; 1628 u32 i; 1629 1630 primary_if = batadv_seq_print_text_primary_if_get(seq); 1631 if (!primary_if) 1632 goto out; 1633 1634 seq_printf(seq, 1635 "Globally announced TT entries received via the mesh %s\n", 1636 net_dev->name); 1637 seq_printf(seq, " %-13s %s %s %-15s %s (%-10s) %s\n", 1638 "Client", "VID", "(TTVN)", "Originator", "(Curr TTVN)", 1639 "CRC", "Flags"); 1640 1641 for (i = 0; i < hash->size; i++) { 1642 head = &hash->table[i]; 1643 1644 rcu_read_lock(); 1645 hlist_for_each_entry_rcu(tt_common_entry, 1646 head, hash_entry) { 1647 tt_global = container_of(tt_common_entry, 1648 struct batadv_tt_global_entry, 1649 common); 1650 batadv_tt_global_print_entry(bat_priv, tt_global, seq); 1651 } 1652 rcu_read_unlock(); 1653 } 1654 out: 1655 if (primary_if) 1656 batadv_hardif_free_ref(primary_if); 1657 return 0; 1658 } 1659 1660 /** 1661 * _batadv_tt_global_del_orig_entry - remove and free an orig_entry 1662 * @tt_global_entry: the global entry to remove the orig_entry from 1663 * @orig_entry: the orig entry to remove and free 1664 * 1665 * Remove an orig_entry from its list in the given tt_global_entry and 1666 * free this orig_entry afterwards. 1667 * 1668 * Caller must hold tt_global_entry->list_lock and ensure orig_entry->list is 1669 * part of a list. 1670 */ 1671 static void 1672 _batadv_tt_global_del_orig_entry(struct batadv_tt_global_entry *tt_global_entry, 1673 struct batadv_tt_orig_list_entry *orig_entry) 1674 { 1675 lockdep_assert_held(&tt_global_entry->list_lock); 1676 1677 batadv_tt_global_size_dec(orig_entry->orig_node, 1678 tt_global_entry->common.vid); 1679 atomic_dec(&tt_global_entry->orig_list_count); 1680 /* requires holding tt_global_entry->list_lock and orig_entry->list 1681 * being part of a list 1682 */ 1683 hlist_del_rcu(&orig_entry->list); 1684 batadv_tt_orig_list_entry_free_ref(orig_entry); 1685 } 1686 1687 /* deletes the orig list of a tt_global_entry */ 1688 static void 1689 batadv_tt_global_del_orig_list(struct batadv_tt_global_entry *tt_global_entry) 1690 { 1691 struct hlist_head *head; 1692 struct hlist_node *safe; 1693 struct batadv_tt_orig_list_entry *orig_entry; 1694 1695 spin_lock_bh(&tt_global_entry->list_lock); 1696 head = &tt_global_entry->orig_list; 1697 hlist_for_each_entry_safe(orig_entry, safe, head, list) 1698 _batadv_tt_global_del_orig_entry(tt_global_entry, orig_entry); 1699 spin_unlock_bh(&tt_global_entry->list_lock); 1700 } 1701 1702 /** 1703 * batadv_tt_global_del_orig_node - remove orig_node from a global tt entry 1704 * @bat_priv: the bat priv with all the soft interface information 1705 * @tt_global_entry: the global entry to remove the orig_node from 1706 * @orig_node: the originator announcing the client 1707 * @message: message to append to the log on deletion 1708 * 1709 * Remove the given orig_node and its according orig_entry from the given 1710 * global tt entry. 1711 */ 1712 static void 1713 batadv_tt_global_del_orig_node(struct batadv_priv *bat_priv, 1714 struct batadv_tt_global_entry *tt_global_entry, 1715 struct batadv_orig_node *orig_node, 1716 const char *message) 1717 { 1718 struct hlist_head *head; 1719 struct hlist_node *safe; 1720 struct batadv_tt_orig_list_entry *orig_entry; 1721 unsigned short vid; 1722 1723 spin_lock_bh(&tt_global_entry->list_lock); 1724 head = &tt_global_entry->orig_list; 1725 hlist_for_each_entry_safe(orig_entry, safe, head, list) { 1726 if (orig_entry->orig_node == orig_node) { 1727 vid = tt_global_entry->common.vid; 1728 batadv_dbg(BATADV_DBG_TT, bat_priv, 1729 "Deleting %pM from global tt entry %pM (vid: %d): %s\n", 1730 orig_node->orig, 1731 tt_global_entry->common.addr, 1732 BATADV_PRINT_VID(vid), message); 1733 _batadv_tt_global_del_orig_entry(tt_global_entry, 1734 orig_entry); 1735 } 1736 } 1737 spin_unlock_bh(&tt_global_entry->list_lock); 1738 } 1739 1740 /* If the client is to be deleted, we check if it is the last origantor entry 1741 * within tt_global entry. If yes, we set the BATADV_TT_CLIENT_ROAM flag and the 1742 * timer, otherwise we simply remove the originator scheduled for deletion. 1743 */ 1744 static void 1745 batadv_tt_global_del_roaming(struct batadv_priv *bat_priv, 1746 struct batadv_tt_global_entry *tt_global_entry, 1747 struct batadv_orig_node *orig_node, 1748 const char *message) 1749 { 1750 bool last_entry = true; 1751 struct hlist_head *head; 1752 struct batadv_tt_orig_list_entry *orig_entry; 1753 1754 /* no local entry exists, case 1: 1755 * Check if this is the last one or if other entries exist. 1756 */ 1757 1758 rcu_read_lock(); 1759 head = &tt_global_entry->orig_list; 1760 hlist_for_each_entry_rcu(orig_entry, head, list) { 1761 if (orig_entry->orig_node != orig_node) { 1762 last_entry = false; 1763 break; 1764 } 1765 } 1766 rcu_read_unlock(); 1767 1768 if (last_entry) { 1769 /* its the last one, mark for roaming. */ 1770 tt_global_entry->common.flags |= BATADV_TT_CLIENT_ROAM; 1771 tt_global_entry->roam_at = jiffies; 1772 } else 1773 /* there is another entry, we can simply delete this 1774 * one and can still use the other one. 1775 */ 1776 batadv_tt_global_del_orig_node(bat_priv, tt_global_entry, 1777 orig_node, message); 1778 } 1779 1780 /** 1781 * batadv_tt_global_del - remove a client from the global table 1782 * @bat_priv: the bat priv with all the soft interface information 1783 * @orig_node: an originator serving this client 1784 * @addr: the mac address of the client 1785 * @vid: VLAN identifier 1786 * @message: a message explaining the reason for deleting the client to print 1787 * for debugging purpose 1788 * @roaming: true if the deletion has been triggered by a roaming event 1789 */ 1790 static void batadv_tt_global_del(struct batadv_priv *bat_priv, 1791 struct batadv_orig_node *orig_node, 1792 const unsigned char *addr, unsigned short vid, 1793 const char *message, bool roaming) 1794 { 1795 struct batadv_tt_global_entry *tt_global_entry; 1796 struct batadv_tt_local_entry *local_entry = NULL; 1797 1798 tt_global_entry = batadv_tt_global_hash_find(bat_priv, addr, vid); 1799 if (!tt_global_entry) 1800 goto out; 1801 1802 if (!roaming) { 1803 batadv_tt_global_del_orig_node(bat_priv, tt_global_entry, 1804 orig_node, message); 1805 1806 if (hlist_empty(&tt_global_entry->orig_list)) 1807 batadv_tt_global_free(bat_priv, tt_global_entry, 1808 message); 1809 1810 goto out; 1811 } 1812 1813 /* if we are deleting a global entry due to a roam 1814 * event, there are two possibilities: 1815 * 1) the client roamed from node A to node B => if there 1816 * is only one originator left for this client, we mark 1817 * it with BATADV_TT_CLIENT_ROAM, we start a timer and we 1818 * wait for node B to claim it. In case of timeout 1819 * the entry is purged. 1820 * 1821 * If there are other originators left, we directly delete 1822 * the originator. 1823 * 2) the client roamed to us => we can directly delete 1824 * the global entry, since it is useless now. 1825 */ 1826 local_entry = batadv_tt_local_hash_find(bat_priv, 1827 tt_global_entry->common.addr, 1828 vid); 1829 if (local_entry) { 1830 /* local entry exists, case 2: client roamed to us. */ 1831 batadv_tt_global_del_orig_list(tt_global_entry); 1832 batadv_tt_global_free(bat_priv, tt_global_entry, message); 1833 } else 1834 /* no local entry exists, case 1: check for roaming */ 1835 batadv_tt_global_del_roaming(bat_priv, tt_global_entry, 1836 orig_node, message); 1837 1838 out: 1839 if (tt_global_entry) 1840 batadv_tt_global_entry_free_ref(tt_global_entry); 1841 if (local_entry) 1842 batadv_tt_local_entry_free_ref(local_entry); 1843 } 1844 1845 /** 1846 * batadv_tt_global_del_orig - remove all the TT global entries belonging to the 1847 * given originator matching the provided vid 1848 * @bat_priv: the bat priv with all the soft interface information 1849 * @orig_node: the originator owning the entries to remove 1850 * @match_vid: the VLAN identifier to match. If negative all the entries will be 1851 * removed 1852 * @message: debug message to print as "reason" 1853 */ 1854 void batadv_tt_global_del_orig(struct batadv_priv *bat_priv, 1855 struct batadv_orig_node *orig_node, 1856 s32 match_vid, 1857 const char *message) 1858 { 1859 struct batadv_tt_global_entry *tt_global; 1860 struct batadv_tt_common_entry *tt_common_entry; 1861 u32 i; 1862 struct batadv_hashtable *hash = bat_priv->tt.global_hash; 1863 struct hlist_node *safe; 1864 struct hlist_head *head; 1865 spinlock_t *list_lock; /* protects write access to the hash lists */ 1866 unsigned short vid; 1867 1868 if (!hash) 1869 return; 1870 1871 for (i = 0; i < hash->size; i++) { 1872 head = &hash->table[i]; 1873 list_lock = &hash->list_locks[i]; 1874 1875 spin_lock_bh(list_lock); 1876 hlist_for_each_entry_safe(tt_common_entry, safe, 1877 head, hash_entry) { 1878 /* remove only matching entries */ 1879 if (match_vid >= 0 && tt_common_entry->vid != match_vid) 1880 continue; 1881 1882 tt_global = container_of(tt_common_entry, 1883 struct batadv_tt_global_entry, 1884 common); 1885 1886 batadv_tt_global_del_orig_node(bat_priv, tt_global, 1887 orig_node, message); 1888 1889 if (hlist_empty(&tt_global->orig_list)) { 1890 vid = tt_global->common.vid; 1891 batadv_dbg(BATADV_DBG_TT, bat_priv, 1892 "Deleting global tt entry %pM (vid: %d): %s\n", 1893 tt_global->common.addr, 1894 BATADV_PRINT_VID(vid), message); 1895 hlist_del_rcu(&tt_common_entry->hash_entry); 1896 batadv_tt_global_entry_free_ref(tt_global); 1897 } 1898 } 1899 spin_unlock_bh(list_lock); 1900 } 1901 clear_bit(BATADV_ORIG_CAPA_HAS_TT, &orig_node->capa_initialized); 1902 } 1903 1904 static bool batadv_tt_global_to_purge(struct batadv_tt_global_entry *tt_global, 1905 char **msg) 1906 { 1907 bool purge = false; 1908 unsigned long roam_timeout = BATADV_TT_CLIENT_ROAM_TIMEOUT; 1909 unsigned long temp_timeout = BATADV_TT_CLIENT_TEMP_TIMEOUT; 1910 1911 if ((tt_global->common.flags & BATADV_TT_CLIENT_ROAM) && 1912 batadv_has_timed_out(tt_global->roam_at, roam_timeout)) { 1913 purge = true; 1914 *msg = "Roaming timeout\n"; 1915 } 1916 1917 if ((tt_global->common.flags & BATADV_TT_CLIENT_TEMP) && 1918 batadv_has_timed_out(tt_global->common.added_at, temp_timeout)) { 1919 purge = true; 1920 *msg = "Temporary client timeout\n"; 1921 } 1922 1923 return purge; 1924 } 1925 1926 static void batadv_tt_global_purge(struct batadv_priv *bat_priv) 1927 { 1928 struct batadv_hashtable *hash = bat_priv->tt.global_hash; 1929 struct hlist_head *head; 1930 struct hlist_node *node_tmp; 1931 spinlock_t *list_lock; /* protects write access to the hash lists */ 1932 u32 i; 1933 char *msg = NULL; 1934 struct batadv_tt_common_entry *tt_common; 1935 struct batadv_tt_global_entry *tt_global; 1936 1937 for (i = 0; i < hash->size; i++) { 1938 head = &hash->table[i]; 1939 list_lock = &hash->list_locks[i]; 1940 1941 spin_lock_bh(list_lock); 1942 hlist_for_each_entry_safe(tt_common, node_tmp, head, 1943 hash_entry) { 1944 tt_global = container_of(tt_common, 1945 struct batadv_tt_global_entry, 1946 common); 1947 1948 if (!batadv_tt_global_to_purge(tt_global, &msg)) 1949 continue; 1950 1951 batadv_dbg(BATADV_DBG_TT, bat_priv, 1952 "Deleting global tt entry %pM (vid: %d): %s\n", 1953 tt_global->common.addr, 1954 BATADV_PRINT_VID(tt_global->common.vid), 1955 msg); 1956 1957 hlist_del_rcu(&tt_common->hash_entry); 1958 1959 batadv_tt_global_entry_free_ref(tt_global); 1960 } 1961 spin_unlock_bh(list_lock); 1962 } 1963 } 1964 1965 static void batadv_tt_global_table_free(struct batadv_priv *bat_priv) 1966 { 1967 struct batadv_hashtable *hash; 1968 spinlock_t *list_lock; /* protects write access to the hash lists */ 1969 struct batadv_tt_common_entry *tt_common_entry; 1970 struct batadv_tt_global_entry *tt_global; 1971 struct hlist_node *node_tmp; 1972 struct hlist_head *head; 1973 u32 i; 1974 1975 if (!bat_priv->tt.global_hash) 1976 return; 1977 1978 hash = bat_priv->tt.global_hash; 1979 1980 for (i = 0; i < hash->size; i++) { 1981 head = &hash->table[i]; 1982 list_lock = &hash->list_locks[i]; 1983 1984 spin_lock_bh(list_lock); 1985 hlist_for_each_entry_safe(tt_common_entry, node_tmp, 1986 head, hash_entry) { 1987 hlist_del_rcu(&tt_common_entry->hash_entry); 1988 tt_global = container_of(tt_common_entry, 1989 struct batadv_tt_global_entry, 1990 common); 1991 batadv_tt_global_entry_free_ref(tt_global); 1992 } 1993 spin_unlock_bh(list_lock); 1994 } 1995 1996 batadv_hash_destroy(hash); 1997 1998 bat_priv->tt.global_hash = NULL; 1999 } 2000 2001 static bool 2002 _batadv_is_ap_isolated(struct batadv_tt_local_entry *tt_local_entry, 2003 struct batadv_tt_global_entry *tt_global_entry) 2004 { 2005 bool ret = false; 2006 2007 if (tt_local_entry->common.flags & BATADV_TT_CLIENT_WIFI && 2008 tt_global_entry->common.flags & BATADV_TT_CLIENT_WIFI) 2009 ret = true; 2010 2011 /* check if the two clients are marked as isolated */ 2012 if (tt_local_entry->common.flags & BATADV_TT_CLIENT_ISOLA && 2013 tt_global_entry->common.flags & BATADV_TT_CLIENT_ISOLA) 2014 ret = true; 2015 2016 return ret; 2017 } 2018 2019 /** 2020 * batadv_transtable_search - get the mesh destination for a given client 2021 * @bat_priv: the bat priv with all the soft interface information 2022 * @src: mac address of the source client 2023 * @addr: mac address of the destination client 2024 * @vid: VLAN identifier 2025 * 2026 * Returns a pointer to the originator that was selected as destination in the 2027 * mesh for contacting the client 'addr', NULL otherwise. 2028 * In case of multiple originators serving the same client, the function returns 2029 * the best one (best in terms of metric towards the destination node). 2030 * 2031 * If the two clients are AP isolated the function returns NULL. 2032 */ 2033 struct batadv_orig_node *batadv_transtable_search(struct batadv_priv *bat_priv, 2034 const u8 *src, 2035 const u8 *addr, 2036 unsigned short vid) 2037 { 2038 struct batadv_tt_local_entry *tt_local_entry = NULL; 2039 struct batadv_tt_global_entry *tt_global_entry = NULL; 2040 struct batadv_orig_node *orig_node = NULL; 2041 struct batadv_tt_orig_list_entry *best_entry; 2042 2043 if (src && batadv_vlan_ap_isola_get(bat_priv, vid)) { 2044 tt_local_entry = batadv_tt_local_hash_find(bat_priv, src, vid); 2045 if (!tt_local_entry || 2046 (tt_local_entry->common.flags & BATADV_TT_CLIENT_PENDING)) 2047 goto out; 2048 } 2049 2050 tt_global_entry = batadv_tt_global_hash_find(bat_priv, addr, vid); 2051 if (!tt_global_entry) 2052 goto out; 2053 2054 /* check whether the clients should not communicate due to AP 2055 * isolation 2056 */ 2057 if (tt_local_entry && 2058 _batadv_is_ap_isolated(tt_local_entry, tt_global_entry)) 2059 goto out; 2060 2061 rcu_read_lock(); 2062 best_entry = batadv_transtable_best_orig(bat_priv, tt_global_entry); 2063 /* found anything? */ 2064 if (best_entry) 2065 orig_node = best_entry->orig_node; 2066 if (orig_node && !atomic_inc_not_zero(&orig_node->refcount)) 2067 orig_node = NULL; 2068 rcu_read_unlock(); 2069 2070 out: 2071 if (tt_global_entry) 2072 batadv_tt_global_entry_free_ref(tt_global_entry); 2073 if (tt_local_entry) 2074 batadv_tt_local_entry_free_ref(tt_local_entry); 2075 2076 return orig_node; 2077 } 2078 2079 /** 2080 * batadv_tt_global_crc - calculates the checksum of the local table belonging 2081 * to the given orig_node 2082 * @bat_priv: the bat priv with all the soft interface information 2083 * @orig_node: originator for which the CRC should be computed 2084 * @vid: VLAN identifier for which the CRC32 has to be computed 2085 * 2086 * This function computes the checksum for the global table corresponding to a 2087 * specific originator. In particular, the checksum is computed as follows: For 2088 * each client connected to the originator the CRC32C of the MAC address and the 2089 * VID is computed and then all the CRC32Cs of the various clients are xor'ed 2090 * together. 2091 * 2092 * The idea behind is that CRC32C should be used as much as possible in order to 2093 * produce a unique hash of the table, but since the order which is used to feed 2094 * the CRC32C function affects the result and since every node in the network 2095 * probably sorts the clients differently, the hash function cannot be directly 2096 * computed over the entire table. Hence the CRC32C is used only on 2097 * the single client entry, while all the results are then xor'ed together 2098 * because the XOR operation can combine them all while trying to reduce the 2099 * noise as much as possible. 2100 * 2101 * Returns the checksum of the global table of a given originator. 2102 */ 2103 static u32 batadv_tt_global_crc(struct batadv_priv *bat_priv, 2104 struct batadv_orig_node *orig_node, 2105 unsigned short vid) 2106 { 2107 struct batadv_hashtable *hash = bat_priv->tt.global_hash; 2108 struct batadv_tt_common_entry *tt_common; 2109 struct batadv_tt_global_entry *tt_global; 2110 struct hlist_head *head; 2111 u32 i, crc_tmp, crc = 0; 2112 u8 flags; 2113 __be16 tmp_vid; 2114 2115 for (i = 0; i < hash->size; i++) { 2116 head = &hash->table[i]; 2117 2118 rcu_read_lock(); 2119 hlist_for_each_entry_rcu(tt_common, head, hash_entry) { 2120 tt_global = container_of(tt_common, 2121 struct batadv_tt_global_entry, 2122 common); 2123 /* compute the CRC only for entries belonging to the 2124 * VLAN identified by the vid passed as parameter 2125 */ 2126 if (tt_common->vid != vid) 2127 continue; 2128 2129 /* Roaming clients are in the global table for 2130 * consistency only. They don't have to be 2131 * taken into account while computing the 2132 * global crc 2133 */ 2134 if (tt_common->flags & BATADV_TT_CLIENT_ROAM) 2135 continue; 2136 /* Temporary clients have not been announced yet, so 2137 * they have to be skipped while computing the global 2138 * crc 2139 */ 2140 if (tt_common->flags & BATADV_TT_CLIENT_TEMP) 2141 continue; 2142 2143 /* find out if this global entry is announced by this 2144 * originator 2145 */ 2146 if (!batadv_tt_global_entry_has_orig(tt_global, 2147 orig_node)) 2148 continue; 2149 2150 /* use network order to read the VID: this ensures that 2151 * every node reads the bytes in the same order. 2152 */ 2153 tmp_vid = htons(tt_common->vid); 2154 crc_tmp = crc32c(0, &tmp_vid, sizeof(tmp_vid)); 2155 2156 /* compute the CRC on flags that have to be kept in sync 2157 * among nodes 2158 */ 2159 flags = tt_common->flags & BATADV_TT_SYNC_MASK; 2160 crc_tmp = crc32c(crc_tmp, &flags, sizeof(flags)); 2161 2162 crc ^= crc32c(crc_tmp, tt_common->addr, ETH_ALEN); 2163 } 2164 rcu_read_unlock(); 2165 } 2166 2167 return crc; 2168 } 2169 2170 /** 2171 * batadv_tt_local_crc - calculates the checksum of the local table 2172 * @bat_priv: the bat priv with all the soft interface information 2173 * @vid: VLAN identifier for which the CRC32 has to be computed 2174 * 2175 * For details about the computation, please refer to the documentation for 2176 * batadv_tt_global_crc(). 2177 * 2178 * Returns the checksum of the local table 2179 */ 2180 static u32 batadv_tt_local_crc(struct batadv_priv *bat_priv, 2181 unsigned short vid) 2182 { 2183 struct batadv_hashtable *hash = bat_priv->tt.local_hash; 2184 struct batadv_tt_common_entry *tt_common; 2185 struct hlist_head *head; 2186 u32 i, crc_tmp, crc = 0; 2187 u8 flags; 2188 __be16 tmp_vid; 2189 2190 for (i = 0; i < hash->size; i++) { 2191 head = &hash->table[i]; 2192 2193 rcu_read_lock(); 2194 hlist_for_each_entry_rcu(tt_common, head, hash_entry) { 2195 /* compute the CRC only for entries belonging to the 2196 * VLAN identified by vid 2197 */ 2198 if (tt_common->vid != vid) 2199 continue; 2200 2201 /* not yet committed clients have not to be taken into 2202 * account while computing the CRC 2203 */ 2204 if (tt_common->flags & BATADV_TT_CLIENT_NEW) 2205 continue; 2206 2207 /* use network order to read the VID: this ensures that 2208 * every node reads the bytes in the same order. 2209 */ 2210 tmp_vid = htons(tt_common->vid); 2211 crc_tmp = crc32c(0, &tmp_vid, sizeof(tmp_vid)); 2212 2213 /* compute the CRC on flags that have to be kept in sync 2214 * among nodes 2215 */ 2216 flags = tt_common->flags & BATADV_TT_SYNC_MASK; 2217 crc_tmp = crc32c(crc_tmp, &flags, sizeof(flags)); 2218 2219 crc ^= crc32c(crc_tmp, tt_common->addr, ETH_ALEN); 2220 } 2221 rcu_read_unlock(); 2222 } 2223 2224 return crc; 2225 } 2226 2227 static void batadv_tt_req_list_free(struct batadv_priv *bat_priv) 2228 { 2229 struct batadv_tt_req_node *node; 2230 struct hlist_node *safe; 2231 2232 spin_lock_bh(&bat_priv->tt.req_list_lock); 2233 2234 hlist_for_each_entry_safe(node, safe, &bat_priv->tt.req_list, list) { 2235 hlist_del_init(&node->list); 2236 kfree(node); 2237 } 2238 2239 spin_unlock_bh(&bat_priv->tt.req_list_lock); 2240 } 2241 2242 static void batadv_tt_save_orig_buffer(struct batadv_priv *bat_priv, 2243 struct batadv_orig_node *orig_node, 2244 const void *tt_buff, 2245 u16 tt_buff_len) 2246 { 2247 /* Replace the old buffer only if I received something in the 2248 * last OGM (the OGM could carry no changes) 2249 */ 2250 spin_lock_bh(&orig_node->tt_buff_lock); 2251 if (tt_buff_len > 0) { 2252 kfree(orig_node->tt_buff); 2253 orig_node->tt_buff_len = 0; 2254 orig_node->tt_buff = kmalloc(tt_buff_len, GFP_ATOMIC); 2255 if (orig_node->tt_buff) { 2256 memcpy(orig_node->tt_buff, tt_buff, tt_buff_len); 2257 orig_node->tt_buff_len = tt_buff_len; 2258 } 2259 } 2260 spin_unlock_bh(&orig_node->tt_buff_lock); 2261 } 2262 2263 static void batadv_tt_req_purge(struct batadv_priv *bat_priv) 2264 { 2265 struct batadv_tt_req_node *node; 2266 struct hlist_node *safe; 2267 2268 spin_lock_bh(&bat_priv->tt.req_list_lock); 2269 hlist_for_each_entry_safe(node, safe, &bat_priv->tt.req_list, list) { 2270 if (batadv_has_timed_out(node->issued_at, 2271 BATADV_TT_REQUEST_TIMEOUT)) { 2272 hlist_del_init(&node->list); 2273 kfree(node); 2274 } 2275 } 2276 spin_unlock_bh(&bat_priv->tt.req_list_lock); 2277 } 2278 2279 /** 2280 * batadv_tt_req_node_new - search and possibly create a tt_req_node object 2281 * @bat_priv: the bat priv with all the soft interface information 2282 * @orig_node: orig node this request is being issued for 2283 * 2284 * Returns the pointer to the new tt_req_node struct if no request 2285 * has already been issued for this orig_node, NULL otherwise. 2286 */ 2287 static struct batadv_tt_req_node * 2288 batadv_tt_req_node_new(struct batadv_priv *bat_priv, 2289 struct batadv_orig_node *orig_node) 2290 { 2291 struct batadv_tt_req_node *tt_req_node_tmp, *tt_req_node = NULL; 2292 2293 spin_lock_bh(&bat_priv->tt.req_list_lock); 2294 hlist_for_each_entry(tt_req_node_tmp, &bat_priv->tt.req_list, list) { 2295 if (batadv_compare_eth(tt_req_node_tmp, orig_node) && 2296 !batadv_has_timed_out(tt_req_node_tmp->issued_at, 2297 BATADV_TT_REQUEST_TIMEOUT)) 2298 goto unlock; 2299 } 2300 2301 tt_req_node = kmalloc(sizeof(*tt_req_node), GFP_ATOMIC); 2302 if (!tt_req_node) 2303 goto unlock; 2304 2305 ether_addr_copy(tt_req_node->addr, orig_node->orig); 2306 tt_req_node->issued_at = jiffies; 2307 2308 hlist_add_head(&tt_req_node->list, &bat_priv->tt.req_list); 2309 unlock: 2310 spin_unlock_bh(&bat_priv->tt.req_list_lock); 2311 return tt_req_node; 2312 } 2313 2314 /** 2315 * batadv_tt_local_valid - verify that given tt entry is a valid one 2316 * @entry_ptr: to be checked local tt entry 2317 * @data_ptr: not used but definition required to satisfy the callback prototype 2318 * 2319 * Returns 1 if the entry is a valid, 0 otherwise. 2320 */ 2321 static int batadv_tt_local_valid(const void *entry_ptr, const void *data_ptr) 2322 { 2323 const struct batadv_tt_common_entry *tt_common_entry = entry_ptr; 2324 2325 if (tt_common_entry->flags & BATADV_TT_CLIENT_NEW) 2326 return 0; 2327 return 1; 2328 } 2329 2330 static int batadv_tt_global_valid(const void *entry_ptr, 2331 const void *data_ptr) 2332 { 2333 const struct batadv_tt_common_entry *tt_common_entry = entry_ptr; 2334 const struct batadv_tt_global_entry *tt_global_entry; 2335 const struct batadv_orig_node *orig_node = data_ptr; 2336 2337 if (tt_common_entry->flags & BATADV_TT_CLIENT_ROAM || 2338 tt_common_entry->flags & BATADV_TT_CLIENT_TEMP) 2339 return 0; 2340 2341 tt_global_entry = container_of(tt_common_entry, 2342 struct batadv_tt_global_entry, 2343 common); 2344 2345 return batadv_tt_global_entry_has_orig(tt_global_entry, orig_node); 2346 } 2347 2348 /** 2349 * batadv_tt_tvlv_generate - fill the tvlv buff with the tt entries from the 2350 * specified tt hash 2351 * @bat_priv: the bat priv with all the soft interface information 2352 * @hash: hash table containing the tt entries 2353 * @tt_len: expected tvlv tt data buffer length in number of bytes 2354 * @tvlv_buff: pointer to the buffer to fill with the TT data 2355 * @valid_cb: function to filter tt change entries 2356 * @cb_data: data passed to the filter function as argument 2357 */ 2358 static void batadv_tt_tvlv_generate(struct batadv_priv *bat_priv, 2359 struct batadv_hashtable *hash, 2360 void *tvlv_buff, u16 tt_len, 2361 int (*valid_cb)(const void *, const void *), 2362 void *cb_data) 2363 { 2364 struct batadv_tt_common_entry *tt_common_entry; 2365 struct batadv_tvlv_tt_change *tt_change; 2366 struct hlist_head *head; 2367 u16 tt_tot, tt_num_entries = 0; 2368 u32 i; 2369 2370 tt_tot = batadv_tt_entries(tt_len); 2371 tt_change = (struct batadv_tvlv_tt_change *)tvlv_buff; 2372 2373 rcu_read_lock(); 2374 for (i = 0; i < hash->size; i++) { 2375 head = &hash->table[i]; 2376 2377 hlist_for_each_entry_rcu(tt_common_entry, 2378 head, hash_entry) { 2379 if (tt_tot == tt_num_entries) 2380 break; 2381 2382 if ((valid_cb) && (!valid_cb(tt_common_entry, cb_data))) 2383 continue; 2384 2385 ether_addr_copy(tt_change->addr, tt_common_entry->addr); 2386 tt_change->flags = tt_common_entry->flags; 2387 tt_change->vid = htons(tt_common_entry->vid); 2388 memset(tt_change->reserved, 0, 2389 sizeof(tt_change->reserved)); 2390 2391 tt_num_entries++; 2392 tt_change++; 2393 } 2394 } 2395 rcu_read_unlock(); 2396 } 2397 2398 /** 2399 * batadv_tt_global_check_crc - check if all the CRCs are correct 2400 * @orig_node: originator for which the CRCs have to be checked 2401 * @tt_vlan: pointer to the first tvlv VLAN entry 2402 * @num_vlan: number of tvlv VLAN entries 2403 * @create: if true, create VLAN objects if not found 2404 * 2405 * Return true if all the received CRCs match the locally stored ones, false 2406 * otherwise 2407 */ 2408 static bool batadv_tt_global_check_crc(struct batadv_orig_node *orig_node, 2409 struct batadv_tvlv_tt_vlan_data *tt_vlan, 2410 u16 num_vlan) 2411 { 2412 struct batadv_tvlv_tt_vlan_data *tt_vlan_tmp; 2413 struct batadv_orig_node_vlan *vlan; 2414 u32 crc; 2415 int i; 2416 2417 /* check if each received CRC matches the locally stored one */ 2418 for (i = 0; i < num_vlan; i++) { 2419 tt_vlan_tmp = tt_vlan + i; 2420 2421 /* if orig_node is a backbone node for this VLAN, don't check 2422 * the CRC as we ignore all the global entries over it 2423 */ 2424 if (batadv_bla_is_backbone_gw_orig(orig_node->bat_priv, 2425 orig_node->orig, 2426 ntohs(tt_vlan_tmp->vid))) 2427 continue; 2428 2429 vlan = batadv_orig_node_vlan_get(orig_node, 2430 ntohs(tt_vlan_tmp->vid)); 2431 if (!vlan) 2432 return false; 2433 2434 crc = vlan->tt.crc; 2435 batadv_orig_node_vlan_free_ref(vlan); 2436 2437 if (crc != ntohl(tt_vlan_tmp->crc)) 2438 return false; 2439 } 2440 2441 return true; 2442 } 2443 2444 /** 2445 * batadv_tt_local_update_crc - update all the local CRCs 2446 * @bat_priv: the bat priv with all the soft interface information 2447 */ 2448 static void batadv_tt_local_update_crc(struct batadv_priv *bat_priv) 2449 { 2450 struct batadv_softif_vlan *vlan; 2451 2452 /* recompute the global CRC for each VLAN */ 2453 rcu_read_lock(); 2454 hlist_for_each_entry_rcu(vlan, &bat_priv->softif_vlan_list, list) { 2455 vlan->tt.crc = batadv_tt_local_crc(bat_priv, vlan->vid); 2456 } 2457 rcu_read_unlock(); 2458 } 2459 2460 /** 2461 * batadv_tt_global_update_crc - update all the global CRCs for this orig_node 2462 * @bat_priv: the bat priv with all the soft interface information 2463 * @orig_node: the orig_node for which the CRCs have to be updated 2464 */ 2465 static void batadv_tt_global_update_crc(struct batadv_priv *bat_priv, 2466 struct batadv_orig_node *orig_node) 2467 { 2468 struct batadv_orig_node_vlan *vlan; 2469 u32 crc; 2470 2471 /* recompute the global CRC for each VLAN */ 2472 rcu_read_lock(); 2473 hlist_for_each_entry_rcu(vlan, &orig_node->vlan_list, list) { 2474 /* if orig_node is a backbone node for this VLAN, don't compute 2475 * the CRC as we ignore all the global entries over it 2476 */ 2477 if (batadv_bla_is_backbone_gw_orig(bat_priv, orig_node->orig, 2478 vlan->vid)) 2479 continue; 2480 2481 crc = batadv_tt_global_crc(bat_priv, orig_node, vlan->vid); 2482 vlan->tt.crc = crc; 2483 } 2484 rcu_read_unlock(); 2485 } 2486 2487 /** 2488 * batadv_send_tt_request - send a TT Request message to a given node 2489 * @bat_priv: the bat priv with all the soft interface information 2490 * @dst_orig_node: the destination of the message 2491 * @ttvn: the version number that the source of the message is looking for 2492 * @tt_vlan: pointer to the first tvlv VLAN object to request 2493 * @num_vlan: number of tvlv VLAN entries 2494 * @full_table: ask for the entire translation table if true, while only for the 2495 * last TT diff otherwise 2496 */ 2497 static int batadv_send_tt_request(struct batadv_priv *bat_priv, 2498 struct batadv_orig_node *dst_orig_node, 2499 u8 ttvn, 2500 struct batadv_tvlv_tt_vlan_data *tt_vlan, 2501 u16 num_vlan, bool full_table) 2502 { 2503 struct batadv_tvlv_tt_data *tvlv_tt_data = NULL; 2504 struct batadv_tt_req_node *tt_req_node = NULL; 2505 struct batadv_tvlv_tt_vlan_data *tt_vlan_req; 2506 struct batadv_hard_iface *primary_if; 2507 bool ret = false; 2508 int i, size; 2509 2510 primary_if = batadv_primary_if_get_selected(bat_priv); 2511 if (!primary_if) 2512 goto out; 2513 2514 /* The new tt_req will be issued only if I'm not waiting for a 2515 * reply from the same orig_node yet 2516 */ 2517 tt_req_node = batadv_tt_req_node_new(bat_priv, dst_orig_node); 2518 if (!tt_req_node) 2519 goto out; 2520 2521 size = sizeof(*tvlv_tt_data) + sizeof(*tt_vlan_req) * num_vlan; 2522 tvlv_tt_data = kzalloc(size, GFP_ATOMIC); 2523 if (!tvlv_tt_data) 2524 goto out; 2525 2526 tvlv_tt_data->flags = BATADV_TT_REQUEST; 2527 tvlv_tt_data->ttvn = ttvn; 2528 tvlv_tt_data->num_vlan = htons(num_vlan); 2529 2530 /* send all the CRCs within the request. This is needed by intermediate 2531 * nodes to ensure they have the correct table before replying 2532 */ 2533 tt_vlan_req = (struct batadv_tvlv_tt_vlan_data *)(tvlv_tt_data + 1); 2534 for (i = 0; i < num_vlan; i++) { 2535 tt_vlan_req->vid = tt_vlan->vid; 2536 tt_vlan_req->crc = tt_vlan->crc; 2537 2538 tt_vlan_req++; 2539 tt_vlan++; 2540 } 2541 2542 if (full_table) 2543 tvlv_tt_data->flags |= BATADV_TT_FULL_TABLE; 2544 2545 batadv_dbg(BATADV_DBG_TT, bat_priv, "Sending TT_REQUEST to %pM [%c]\n", 2546 dst_orig_node->orig, full_table ? 'F' : '.'); 2547 2548 batadv_inc_counter(bat_priv, BATADV_CNT_TT_REQUEST_TX); 2549 batadv_tvlv_unicast_send(bat_priv, primary_if->net_dev->dev_addr, 2550 dst_orig_node->orig, BATADV_TVLV_TT, 1, 2551 tvlv_tt_data, size); 2552 ret = true; 2553 2554 out: 2555 if (primary_if) 2556 batadv_hardif_free_ref(primary_if); 2557 if (ret && tt_req_node) { 2558 spin_lock_bh(&bat_priv->tt.req_list_lock); 2559 /* hlist_del_init() verifies tt_req_node still is in the list */ 2560 hlist_del_init(&tt_req_node->list); 2561 spin_unlock_bh(&bat_priv->tt.req_list_lock); 2562 kfree(tt_req_node); 2563 } 2564 kfree(tvlv_tt_data); 2565 return ret; 2566 } 2567 2568 /** 2569 * batadv_send_other_tt_response - send reply to tt request concerning another 2570 * node's translation table 2571 * @bat_priv: the bat priv with all the soft interface information 2572 * @tt_data: tt data containing the tt request information 2573 * @req_src: mac address of tt request sender 2574 * @req_dst: mac address of tt request recipient 2575 * 2576 * Returns true if tt request reply was sent, false otherwise. 2577 */ 2578 static bool batadv_send_other_tt_response(struct batadv_priv *bat_priv, 2579 struct batadv_tvlv_tt_data *tt_data, 2580 u8 *req_src, u8 *req_dst) 2581 { 2582 struct batadv_orig_node *req_dst_orig_node; 2583 struct batadv_orig_node *res_dst_orig_node = NULL; 2584 struct batadv_tvlv_tt_change *tt_change; 2585 struct batadv_tvlv_tt_data *tvlv_tt_data = NULL; 2586 struct batadv_tvlv_tt_vlan_data *tt_vlan; 2587 bool ret = false, full_table; 2588 u8 orig_ttvn, req_ttvn; 2589 u16 tvlv_len; 2590 s32 tt_len; 2591 2592 batadv_dbg(BATADV_DBG_TT, bat_priv, 2593 "Received TT_REQUEST from %pM for ttvn: %u (%pM) [%c]\n", 2594 req_src, tt_data->ttvn, req_dst, 2595 ((tt_data->flags & BATADV_TT_FULL_TABLE) ? 'F' : '.')); 2596 2597 /* Let's get the orig node of the REAL destination */ 2598 req_dst_orig_node = batadv_orig_hash_find(bat_priv, req_dst); 2599 if (!req_dst_orig_node) 2600 goto out; 2601 2602 res_dst_orig_node = batadv_orig_hash_find(bat_priv, req_src); 2603 if (!res_dst_orig_node) 2604 goto out; 2605 2606 orig_ttvn = (u8)atomic_read(&req_dst_orig_node->last_ttvn); 2607 req_ttvn = tt_data->ttvn; 2608 2609 tt_vlan = (struct batadv_tvlv_tt_vlan_data *)(tt_data + 1); 2610 /* this node doesn't have the requested data */ 2611 if (orig_ttvn != req_ttvn || 2612 !batadv_tt_global_check_crc(req_dst_orig_node, tt_vlan, 2613 ntohs(tt_data->num_vlan))) 2614 goto out; 2615 2616 /* If the full table has been explicitly requested */ 2617 if (tt_data->flags & BATADV_TT_FULL_TABLE || 2618 !req_dst_orig_node->tt_buff) 2619 full_table = true; 2620 else 2621 full_table = false; 2622 2623 /* TT fragmentation hasn't been implemented yet, so send as many 2624 * TT entries fit a single packet as possible only 2625 */ 2626 if (!full_table) { 2627 spin_lock_bh(&req_dst_orig_node->tt_buff_lock); 2628 tt_len = req_dst_orig_node->tt_buff_len; 2629 2630 tvlv_len = batadv_tt_prepare_tvlv_global_data(req_dst_orig_node, 2631 &tvlv_tt_data, 2632 &tt_change, 2633 &tt_len); 2634 if (!tt_len) 2635 goto unlock; 2636 2637 /* Copy the last orig_node's OGM buffer */ 2638 memcpy(tt_change, req_dst_orig_node->tt_buff, 2639 req_dst_orig_node->tt_buff_len); 2640 spin_unlock_bh(&req_dst_orig_node->tt_buff_lock); 2641 } else { 2642 /* allocate the tvlv, put the tt_data and all the tt_vlan_data 2643 * in the initial part 2644 */ 2645 tt_len = -1; 2646 tvlv_len = batadv_tt_prepare_tvlv_global_data(req_dst_orig_node, 2647 &tvlv_tt_data, 2648 &tt_change, 2649 &tt_len); 2650 if (!tt_len) 2651 goto out; 2652 2653 /* fill the rest of the tvlv with the real TT entries */ 2654 batadv_tt_tvlv_generate(bat_priv, bat_priv->tt.global_hash, 2655 tt_change, tt_len, 2656 batadv_tt_global_valid, 2657 req_dst_orig_node); 2658 } 2659 2660 /* Don't send the response, if larger than fragmented packet. */ 2661 tt_len = sizeof(struct batadv_unicast_tvlv_packet) + tvlv_len; 2662 if (tt_len > atomic_read(&bat_priv->packet_size_max)) { 2663 net_ratelimited_function(batadv_info, bat_priv->soft_iface, 2664 "Ignoring TT_REQUEST from %pM; Response size exceeds max packet size.\n", 2665 res_dst_orig_node->orig); 2666 goto out; 2667 } 2668 2669 tvlv_tt_data->flags = BATADV_TT_RESPONSE; 2670 tvlv_tt_data->ttvn = req_ttvn; 2671 2672 if (full_table) 2673 tvlv_tt_data->flags |= BATADV_TT_FULL_TABLE; 2674 2675 batadv_dbg(BATADV_DBG_TT, bat_priv, 2676 "Sending TT_RESPONSE %pM for %pM [%c] (ttvn: %u)\n", 2677 res_dst_orig_node->orig, req_dst_orig_node->orig, 2678 full_table ? 'F' : '.', req_ttvn); 2679 2680 batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_TX); 2681 2682 batadv_tvlv_unicast_send(bat_priv, req_dst_orig_node->orig, 2683 req_src, BATADV_TVLV_TT, 1, tvlv_tt_data, 2684 tvlv_len); 2685 2686 ret = true; 2687 goto out; 2688 2689 unlock: 2690 spin_unlock_bh(&req_dst_orig_node->tt_buff_lock); 2691 2692 out: 2693 if (res_dst_orig_node) 2694 batadv_orig_node_free_ref(res_dst_orig_node); 2695 if (req_dst_orig_node) 2696 batadv_orig_node_free_ref(req_dst_orig_node); 2697 kfree(tvlv_tt_data); 2698 return ret; 2699 } 2700 2701 /** 2702 * batadv_send_my_tt_response - send reply to tt request concerning this node's 2703 * translation table 2704 * @bat_priv: the bat priv with all the soft interface information 2705 * @tt_data: tt data containing the tt request information 2706 * @req_src: mac address of tt request sender 2707 * 2708 * Returns true if tt request reply was sent, false otherwise. 2709 */ 2710 static bool batadv_send_my_tt_response(struct batadv_priv *bat_priv, 2711 struct batadv_tvlv_tt_data *tt_data, 2712 u8 *req_src) 2713 { 2714 struct batadv_tvlv_tt_data *tvlv_tt_data = NULL; 2715 struct batadv_hard_iface *primary_if = NULL; 2716 struct batadv_tvlv_tt_change *tt_change; 2717 struct batadv_orig_node *orig_node; 2718 u8 my_ttvn, req_ttvn; 2719 u16 tvlv_len; 2720 bool full_table; 2721 s32 tt_len; 2722 2723 batadv_dbg(BATADV_DBG_TT, bat_priv, 2724 "Received TT_REQUEST from %pM for ttvn: %u (me) [%c]\n", 2725 req_src, tt_data->ttvn, 2726 ((tt_data->flags & BATADV_TT_FULL_TABLE) ? 'F' : '.')); 2727 2728 spin_lock_bh(&bat_priv->tt.commit_lock); 2729 2730 my_ttvn = (u8)atomic_read(&bat_priv->tt.vn); 2731 req_ttvn = tt_data->ttvn; 2732 2733 orig_node = batadv_orig_hash_find(bat_priv, req_src); 2734 if (!orig_node) 2735 goto out; 2736 2737 primary_if = batadv_primary_if_get_selected(bat_priv); 2738 if (!primary_if) 2739 goto out; 2740 2741 /* If the full table has been explicitly requested or the gap 2742 * is too big send the whole local translation table 2743 */ 2744 if (tt_data->flags & BATADV_TT_FULL_TABLE || my_ttvn != req_ttvn || 2745 !bat_priv->tt.last_changeset) 2746 full_table = true; 2747 else 2748 full_table = false; 2749 2750 /* TT fragmentation hasn't been implemented yet, so send as many 2751 * TT entries fit a single packet as possible only 2752 */ 2753 if (!full_table) { 2754 spin_lock_bh(&bat_priv->tt.last_changeset_lock); 2755 2756 tt_len = bat_priv->tt.last_changeset_len; 2757 tvlv_len = batadv_tt_prepare_tvlv_local_data(bat_priv, 2758 &tvlv_tt_data, 2759 &tt_change, 2760 &tt_len); 2761 if (!tt_len) 2762 goto unlock; 2763 2764 /* Copy the last orig_node's OGM buffer */ 2765 memcpy(tt_change, bat_priv->tt.last_changeset, 2766 bat_priv->tt.last_changeset_len); 2767 spin_unlock_bh(&bat_priv->tt.last_changeset_lock); 2768 } else { 2769 req_ttvn = (u8)atomic_read(&bat_priv->tt.vn); 2770 2771 /* allocate the tvlv, put the tt_data and all the tt_vlan_data 2772 * in the initial part 2773 */ 2774 tt_len = -1; 2775 tvlv_len = batadv_tt_prepare_tvlv_local_data(bat_priv, 2776 &tvlv_tt_data, 2777 &tt_change, 2778 &tt_len); 2779 if (!tt_len) 2780 goto out; 2781 2782 /* fill the rest of the tvlv with the real TT entries */ 2783 batadv_tt_tvlv_generate(bat_priv, bat_priv->tt.local_hash, 2784 tt_change, tt_len, 2785 batadv_tt_local_valid, NULL); 2786 } 2787 2788 tvlv_tt_data->flags = BATADV_TT_RESPONSE; 2789 tvlv_tt_data->ttvn = req_ttvn; 2790 2791 if (full_table) 2792 tvlv_tt_data->flags |= BATADV_TT_FULL_TABLE; 2793 2794 batadv_dbg(BATADV_DBG_TT, bat_priv, 2795 "Sending TT_RESPONSE to %pM [%c] (ttvn: %u)\n", 2796 orig_node->orig, full_table ? 'F' : '.', req_ttvn); 2797 2798 batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_TX); 2799 2800 batadv_tvlv_unicast_send(bat_priv, primary_if->net_dev->dev_addr, 2801 req_src, BATADV_TVLV_TT, 1, tvlv_tt_data, 2802 tvlv_len); 2803 2804 goto out; 2805 2806 unlock: 2807 spin_unlock_bh(&bat_priv->tt.last_changeset_lock); 2808 out: 2809 spin_unlock_bh(&bat_priv->tt.commit_lock); 2810 if (orig_node) 2811 batadv_orig_node_free_ref(orig_node); 2812 if (primary_if) 2813 batadv_hardif_free_ref(primary_if); 2814 kfree(tvlv_tt_data); 2815 /* The packet was for this host, so it doesn't need to be re-routed */ 2816 return true; 2817 } 2818 2819 /** 2820 * batadv_send_tt_response - send reply to tt request 2821 * @bat_priv: the bat priv with all the soft interface information 2822 * @tt_data: tt data containing the tt request information 2823 * @req_src: mac address of tt request sender 2824 * @req_dst: mac address of tt request recipient 2825 * 2826 * Returns true if tt request reply was sent, false otherwise. 2827 */ 2828 static bool batadv_send_tt_response(struct batadv_priv *bat_priv, 2829 struct batadv_tvlv_tt_data *tt_data, 2830 u8 *req_src, u8 *req_dst) 2831 { 2832 if (batadv_is_my_mac(bat_priv, req_dst)) 2833 return batadv_send_my_tt_response(bat_priv, tt_data, req_src); 2834 return batadv_send_other_tt_response(bat_priv, tt_data, req_src, 2835 req_dst); 2836 } 2837 2838 static void _batadv_tt_update_changes(struct batadv_priv *bat_priv, 2839 struct batadv_orig_node *orig_node, 2840 struct batadv_tvlv_tt_change *tt_change, 2841 u16 tt_num_changes, u8 ttvn) 2842 { 2843 int i; 2844 int roams; 2845 2846 for (i = 0; i < tt_num_changes; i++) { 2847 if ((tt_change + i)->flags & BATADV_TT_CLIENT_DEL) { 2848 roams = (tt_change + i)->flags & BATADV_TT_CLIENT_ROAM; 2849 batadv_tt_global_del(bat_priv, orig_node, 2850 (tt_change + i)->addr, 2851 ntohs((tt_change + i)->vid), 2852 "tt removed by changes", 2853 roams); 2854 } else { 2855 if (!batadv_tt_global_add(bat_priv, orig_node, 2856 (tt_change + i)->addr, 2857 ntohs((tt_change + i)->vid), 2858 (tt_change + i)->flags, ttvn)) 2859 /* In case of problem while storing a 2860 * global_entry, we stop the updating 2861 * procedure without committing the 2862 * ttvn change. This will avoid to send 2863 * corrupted data on tt_request 2864 */ 2865 return; 2866 } 2867 } 2868 set_bit(BATADV_ORIG_CAPA_HAS_TT, &orig_node->capa_initialized); 2869 } 2870 2871 static void batadv_tt_fill_gtable(struct batadv_priv *bat_priv, 2872 struct batadv_tvlv_tt_change *tt_change, 2873 u8 ttvn, u8 *resp_src, 2874 u16 num_entries) 2875 { 2876 struct batadv_orig_node *orig_node; 2877 2878 orig_node = batadv_orig_hash_find(bat_priv, resp_src); 2879 if (!orig_node) 2880 goto out; 2881 2882 /* Purge the old table first.. */ 2883 batadv_tt_global_del_orig(bat_priv, orig_node, -1, 2884 "Received full table"); 2885 2886 _batadv_tt_update_changes(bat_priv, orig_node, tt_change, num_entries, 2887 ttvn); 2888 2889 spin_lock_bh(&orig_node->tt_buff_lock); 2890 kfree(orig_node->tt_buff); 2891 orig_node->tt_buff_len = 0; 2892 orig_node->tt_buff = NULL; 2893 spin_unlock_bh(&orig_node->tt_buff_lock); 2894 2895 atomic_set(&orig_node->last_ttvn, ttvn); 2896 2897 out: 2898 if (orig_node) 2899 batadv_orig_node_free_ref(orig_node); 2900 } 2901 2902 static void batadv_tt_update_changes(struct batadv_priv *bat_priv, 2903 struct batadv_orig_node *orig_node, 2904 u16 tt_num_changes, u8 ttvn, 2905 struct batadv_tvlv_tt_change *tt_change) 2906 { 2907 _batadv_tt_update_changes(bat_priv, orig_node, tt_change, 2908 tt_num_changes, ttvn); 2909 2910 batadv_tt_save_orig_buffer(bat_priv, orig_node, tt_change, 2911 batadv_tt_len(tt_num_changes)); 2912 atomic_set(&orig_node->last_ttvn, ttvn); 2913 } 2914 2915 /** 2916 * batadv_is_my_client - check if a client is served by the local node 2917 * @bat_priv: the bat priv with all the soft interface information 2918 * @addr: the mac address of the client to check 2919 * @vid: VLAN identifier 2920 * 2921 * Returns true if the client is served by this node, false otherwise. 2922 */ 2923 bool batadv_is_my_client(struct batadv_priv *bat_priv, const u8 *addr, 2924 unsigned short vid) 2925 { 2926 struct batadv_tt_local_entry *tt_local_entry; 2927 bool ret = false; 2928 2929 tt_local_entry = batadv_tt_local_hash_find(bat_priv, addr, vid); 2930 if (!tt_local_entry) 2931 goto out; 2932 /* Check if the client has been logically deleted (but is kept for 2933 * consistency purpose) 2934 */ 2935 if ((tt_local_entry->common.flags & BATADV_TT_CLIENT_PENDING) || 2936 (tt_local_entry->common.flags & BATADV_TT_CLIENT_ROAM)) 2937 goto out; 2938 ret = true; 2939 out: 2940 if (tt_local_entry) 2941 batadv_tt_local_entry_free_ref(tt_local_entry); 2942 return ret; 2943 } 2944 2945 /** 2946 * batadv_handle_tt_response - process incoming tt reply 2947 * @bat_priv: the bat priv with all the soft interface information 2948 * @tt_data: tt data containing the tt request information 2949 * @resp_src: mac address of tt reply sender 2950 * @num_entries: number of tt change entries appended to the tt data 2951 */ 2952 static void batadv_handle_tt_response(struct batadv_priv *bat_priv, 2953 struct batadv_tvlv_tt_data *tt_data, 2954 u8 *resp_src, u16 num_entries) 2955 { 2956 struct batadv_tt_req_node *node; 2957 struct hlist_node *safe; 2958 struct batadv_orig_node *orig_node = NULL; 2959 struct batadv_tvlv_tt_change *tt_change; 2960 u8 *tvlv_ptr = (u8 *)tt_data; 2961 u16 change_offset; 2962 2963 batadv_dbg(BATADV_DBG_TT, bat_priv, 2964 "Received TT_RESPONSE from %pM for ttvn %d t_size: %d [%c]\n", 2965 resp_src, tt_data->ttvn, num_entries, 2966 ((tt_data->flags & BATADV_TT_FULL_TABLE) ? 'F' : '.')); 2967 2968 orig_node = batadv_orig_hash_find(bat_priv, resp_src); 2969 if (!orig_node) 2970 goto out; 2971 2972 spin_lock_bh(&orig_node->tt_lock); 2973 2974 change_offset = sizeof(struct batadv_tvlv_tt_vlan_data); 2975 change_offset *= ntohs(tt_data->num_vlan); 2976 change_offset += sizeof(*tt_data); 2977 tvlv_ptr += change_offset; 2978 2979 tt_change = (struct batadv_tvlv_tt_change *)tvlv_ptr; 2980 if (tt_data->flags & BATADV_TT_FULL_TABLE) { 2981 batadv_tt_fill_gtable(bat_priv, tt_change, tt_data->ttvn, 2982 resp_src, num_entries); 2983 } else { 2984 batadv_tt_update_changes(bat_priv, orig_node, num_entries, 2985 tt_data->ttvn, tt_change); 2986 } 2987 2988 /* Recalculate the CRC for this orig_node and store it */ 2989 batadv_tt_global_update_crc(bat_priv, orig_node); 2990 2991 spin_unlock_bh(&orig_node->tt_lock); 2992 2993 /* Delete the tt_req_node from pending tt_requests list */ 2994 spin_lock_bh(&bat_priv->tt.req_list_lock); 2995 hlist_for_each_entry_safe(node, safe, &bat_priv->tt.req_list, list) { 2996 if (!batadv_compare_eth(node->addr, resp_src)) 2997 continue; 2998 hlist_del_init(&node->list); 2999 kfree(node); 3000 } 3001 3002 spin_unlock_bh(&bat_priv->tt.req_list_lock); 3003 out: 3004 if (orig_node) 3005 batadv_orig_node_free_ref(orig_node); 3006 } 3007 3008 static void batadv_tt_roam_list_free(struct batadv_priv *bat_priv) 3009 { 3010 struct batadv_tt_roam_node *node, *safe; 3011 3012 spin_lock_bh(&bat_priv->tt.roam_list_lock); 3013 3014 list_for_each_entry_safe(node, safe, &bat_priv->tt.roam_list, list) { 3015 list_del(&node->list); 3016 kfree(node); 3017 } 3018 3019 spin_unlock_bh(&bat_priv->tt.roam_list_lock); 3020 } 3021 3022 static void batadv_tt_roam_purge(struct batadv_priv *bat_priv) 3023 { 3024 struct batadv_tt_roam_node *node, *safe; 3025 3026 spin_lock_bh(&bat_priv->tt.roam_list_lock); 3027 list_for_each_entry_safe(node, safe, &bat_priv->tt.roam_list, list) { 3028 if (!batadv_has_timed_out(node->first_time, 3029 BATADV_ROAMING_MAX_TIME)) 3030 continue; 3031 3032 list_del(&node->list); 3033 kfree(node); 3034 } 3035 spin_unlock_bh(&bat_priv->tt.roam_list_lock); 3036 } 3037 3038 /* This function checks whether the client already reached the 3039 * maximum number of possible roaming phases. In this case the ROAMING_ADV 3040 * will not be sent. 3041 * 3042 * returns true if the ROAMING_ADV can be sent, false otherwise 3043 */ 3044 static bool batadv_tt_check_roam_count(struct batadv_priv *bat_priv, u8 *client) 3045 { 3046 struct batadv_tt_roam_node *tt_roam_node; 3047 bool ret = false; 3048 3049 spin_lock_bh(&bat_priv->tt.roam_list_lock); 3050 /* The new tt_req will be issued only if I'm not waiting for a 3051 * reply from the same orig_node yet 3052 */ 3053 list_for_each_entry(tt_roam_node, &bat_priv->tt.roam_list, list) { 3054 if (!batadv_compare_eth(tt_roam_node->addr, client)) 3055 continue; 3056 3057 if (batadv_has_timed_out(tt_roam_node->first_time, 3058 BATADV_ROAMING_MAX_TIME)) 3059 continue; 3060 3061 if (!batadv_atomic_dec_not_zero(&tt_roam_node->counter)) 3062 /* Sorry, you roamed too many times! */ 3063 goto unlock; 3064 ret = true; 3065 break; 3066 } 3067 3068 if (!ret) { 3069 tt_roam_node = kmalloc(sizeof(*tt_roam_node), GFP_ATOMIC); 3070 if (!tt_roam_node) 3071 goto unlock; 3072 3073 tt_roam_node->first_time = jiffies; 3074 atomic_set(&tt_roam_node->counter, 3075 BATADV_ROAMING_MAX_COUNT - 1); 3076 ether_addr_copy(tt_roam_node->addr, client); 3077 3078 list_add(&tt_roam_node->list, &bat_priv->tt.roam_list); 3079 ret = true; 3080 } 3081 3082 unlock: 3083 spin_unlock_bh(&bat_priv->tt.roam_list_lock); 3084 return ret; 3085 } 3086 3087 /** 3088 * batadv_send_roam_adv - send a roaming advertisement message 3089 * @bat_priv: the bat priv with all the soft interface information 3090 * @client: mac address of the roaming client 3091 * @vid: VLAN identifier 3092 * @orig_node: message destination 3093 * 3094 * Send a ROAMING_ADV message to the node which was previously serving this 3095 * client. This is done to inform the node that from now on all traffic destined 3096 * for this particular roamed client has to be forwarded to the sender of the 3097 * roaming message. 3098 */ 3099 static void batadv_send_roam_adv(struct batadv_priv *bat_priv, u8 *client, 3100 unsigned short vid, 3101 struct batadv_orig_node *orig_node) 3102 { 3103 struct batadv_hard_iface *primary_if; 3104 struct batadv_tvlv_roam_adv tvlv_roam; 3105 3106 primary_if = batadv_primary_if_get_selected(bat_priv); 3107 if (!primary_if) 3108 goto out; 3109 3110 /* before going on we have to check whether the client has 3111 * already roamed to us too many times 3112 */ 3113 if (!batadv_tt_check_roam_count(bat_priv, client)) 3114 goto out; 3115 3116 batadv_dbg(BATADV_DBG_TT, bat_priv, 3117 "Sending ROAMING_ADV to %pM (client %pM, vid: %d)\n", 3118 orig_node->orig, client, BATADV_PRINT_VID(vid)); 3119 3120 batadv_inc_counter(bat_priv, BATADV_CNT_TT_ROAM_ADV_TX); 3121 3122 memcpy(tvlv_roam.client, client, sizeof(tvlv_roam.client)); 3123 tvlv_roam.vid = htons(vid); 3124 3125 batadv_tvlv_unicast_send(bat_priv, primary_if->net_dev->dev_addr, 3126 orig_node->orig, BATADV_TVLV_ROAM, 1, 3127 &tvlv_roam, sizeof(tvlv_roam)); 3128 3129 out: 3130 if (primary_if) 3131 batadv_hardif_free_ref(primary_if); 3132 } 3133 3134 static void batadv_tt_purge(struct work_struct *work) 3135 { 3136 struct delayed_work *delayed_work; 3137 struct batadv_priv_tt *priv_tt; 3138 struct batadv_priv *bat_priv; 3139 3140 delayed_work = container_of(work, struct delayed_work, work); 3141 priv_tt = container_of(delayed_work, struct batadv_priv_tt, work); 3142 bat_priv = container_of(priv_tt, struct batadv_priv, tt); 3143 3144 batadv_tt_local_purge(bat_priv, BATADV_TT_LOCAL_TIMEOUT); 3145 batadv_tt_global_purge(bat_priv); 3146 batadv_tt_req_purge(bat_priv); 3147 batadv_tt_roam_purge(bat_priv); 3148 3149 queue_delayed_work(batadv_event_workqueue, &bat_priv->tt.work, 3150 msecs_to_jiffies(BATADV_TT_WORK_PERIOD)); 3151 } 3152 3153 void batadv_tt_free(struct batadv_priv *bat_priv) 3154 { 3155 batadv_tvlv_container_unregister(bat_priv, BATADV_TVLV_TT, 1); 3156 batadv_tvlv_handler_unregister(bat_priv, BATADV_TVLV_TT, 1); 3157 3158 cancel_delayed_work_sync(&bat_priv->tt.work); 3159 3160 batadv_tt_local_table_free(bat_priv); 3161 batadv_tt_global_table_free(bat_priv); 3162 batadv_tt_req_list_free(bat_priv); 3163 batadv_tt_changes_list_free(bat_priv); 3164 batadv_tt_roam_list_free(bat_priv); 3165 3166 kfree(bat_priv->tt.last_changeset); 3167 } 3168 3169 /** 3170 * batadv_tt_local_set_flags - set or unset the specified flags on the local 3171 * table and possibly count them in the TT size 3172 * @bat_priv: the bat priv with all the soft interface information 3173 * @flags: the flag to switch 3174 * @enable: whether to set or unset the flag 3175 * @count: whether to increase the TT size by the number of changed entries 3176 */ 3177 static void batadv_tt_local_set_flags(struct batadv_priv *bat_priv, u16 flags, 3178 bool enable, bool count) 3179 { 3180 struct batadv_hashtable *hash = bat_priv->tt.local_hash; 3181 struct batadv_tt_common_entry *tt_common_entry; 3182 u16 changed_num = 0; 3183 struct hlist_head *head; 3184 u32 i; 3185 3186 if (!hash) 3187 return; 3188 3189 for (i = 0; i < hash->size; i++) { 3190 head = &hash->table[i]; 3191 3192 rcu_read_lock(); 3193 hlist_for_each_entry_rcu(tt_common_entry, 3194 head, hash_entry) { 3195 if (enable) { 3196 if ((tt_common_entry->flags & flags) == flags) 3197 continue; 3198 tt_common_entry->flags |= flags; 3199 } else { 3200 if (!(tt_common_entry->flags & flags)) 3201 continue; 3202 tt_common_entry->flags &= ~flags; 3203 } 3204 changed_num++; 3205 3206 if (!count) 3207 continue; 3208 3209 batadv_tt_local_size_inc(bat_priv, 3210 tt_common_entry->vid); 3211 } 3212 rcu_read_unlock(); 3213 } 3214 } 3215 3216 /* Purge out all the tt local entries marked with BATADV_TT_CLIENT_PENDING */ 3217 static void batadv_tt_local_purge_pending_clients(struct batadv_priv *bat_priv) 3218 { 3219 struct batadv_hashtable *hash = bat_priv->tt.local_hash; 3220 struct batadv_tt_common_entry *tt_common; 3221 struct batadv_tt_local_entry *tt_local; 3222 struct batadv_softif_vlan *vlan; 3223 struct hlist_node *node_tmp; 3224 struct hlist_head *head; 3225 spinlock_t *list_lock; /* protects write access to the hash lists */ 3226 u32 i; 3227 3228 if (!hash) 3229 return; 3230 3231 for (i = 0; i < hash->size; i++) { 3232 head = &hash->table[i]; 3233 list_lock = &hash->list_locks[i]; 3234 3235 spin_lock_bh(list_lock); 3236 hlist_for_each_entry_safe(tt_common, node_tmp, head, 3237 hash_entry) { 3238 if (!(tt_common->flags & BATADV_TT_CLIENT_PENDING)) 3239 continue; 3240 3241 batadv_dbg(BATADV_DBG_TT, bat_priv, 3242 "Deleting local tt entry (%pM, vid: %d): pending\n", 3243 tt_common->addr, 3244 BATADV_PRINT_VID(tt_common->vid)); 3245 3246 batadv_tt_local_size_dec(bat_priv, tt_common->vid); 3247 hlist_del_rcu(&tt_common->hash_entry); 3248 tt_local = container_of(tt_common, 3249 struct batadv_tt_local_entry, 3250 common); 3251 3252 /* decrease the reference held for this vlan */ 3253 vlan = batadv_softif_vlan_get(bat_priv, tt_common->vid); 3254 if (vlan) { 3255 batadv_softif_vlan_free_ref(vlan); 3256 batadv_softif_vlan_free_ref(vlan); 3257 } 3258 3259 batadv_tt_local_entry_free_ref(tt_local); 3260 } 3261 spin_unlock_bh(list_lock); 3262 } 3263 } 3264 3265 /** 3266 * batadv_tt_local_commit_changes_nolock - commit all pending local tt changes 3267 * which have been queued in the time since the last commit 3268 * @bat_priv: the bat priv with all the soft interface information 3269 * 3270 * Caller must hold tt->commit_lock. 3271 */ 3272 static void batadv_tt_local_commit_changes_nolock(struct batadv_priv *bat_priv) 3273 { 3274 lockdep_assert_held(&bat_priv->tt.commit_lock); 3275 3276 /* Update multicast addresses in local translation table */ 3277 batadv_mcast_mla_update(bat_priv); 3278 3279 if (atomic_read(&bat_priv->tt.local_changes) < 1) { 3280 if (!batadv_atomic_dec_not_zero(&bat_priv->tt.ogm_append_cnt)) 3281 batadv_tt_tvlv_container_update(bat_priv); 3282 return; 3283 } 3284 3285 batadv_tt_local_set_flags(bat_priv, BATADV_TT_CLIENT_NEW, false, true); 3286 3287 batadv_tt_local_purge_pending_clients(bat_priv); 3288 batadv_tt_local_update_crc(bat_priv); 3289 3290 /* Increment the TTVN only once per OGM interval */ 3291 atomic_inc(&bat_priv->tt.vn); 3292 batadv_dbg(BATADV_DBG_TT, bat_priv, 3293 "Local changes committed, updating to ttvn %u\n", 3294 (u8)atomic_read(&bat_priv->tt.vn)); 3295 3296 /* reset the sending counter */ 3297 atomic_set(&bat_priv->tt.ogm_append_cnt, BATADV_TT_OGM_APPEND_MAX); 3298 batadv_tt_tvlv_container_update(bat_priv); 3299 } 3300 3301 /** 3302 * batadv_tt_local_commit_changes - commit all pending local tt changes which 3303 * have been queued in the time since the last commit 3304 * @bat_priv: the bat priv with all the soft interface information 3305 */ 3306 void batadv_tt_local_commit_changes(struct batadv_priv *bat_priv) 3307 { 3308 spin_lock_bh(&bat_priv->tt.commit_lock); 3309 batadv_tt_local_commit_changes_nolock(bat_priv); 3310 spin_unlock_bh(&bat_priv->tt.commit_lock); 3311 } 3312 3313 bool batadv_is_ap_isolated(struct batadv_priv *bat_priv, u8 *src, u8 *dst, 3314 unsigned short vid) 3315 { 3316 struct batadv_tt_local_entry *tt_local_entry = NULL; 3317 struct batadv_tt_global_entry *tt_global_entry = NULL; 3318 struct batadv_softif_vlan *vlan; 3319 bool ret = false; 3320 3321 vlan = batadv_softif_vlan_get(bat_priv, vid); 3322 if (!vlan || !atomic_read(&vlan->ap_isolation)) 3323 goto out; 3324 3325 tt_local_entry = batadv_tt_local_hash_find(bat_priv, dst, vid); 3326 if (!tt_local_entry) 3327 goto out; 3328 3329 tt_global_entry = batadv_tt_global_hash_find(bat_priv, src, vid); 3330 if (!tt_global_entry) 3331 goto out; 3332 3333 if (!_batadv_is_ap_isolated(tt_local_entry, tt_global_entry)) 3334 goto out; 3335 3336 ret = true; 3337 3338 out: 3339 if (vlan) 3340 batadv_softif_vlan_free_ref(vlan); 3341 if (tt_global_entry) 3342 batadv_tt_global_entry_free_ref(tt_global_entry); 3343 if (tt_local_entry) 3344 batadv_tt_local_entry_free_ref(tt_local_entry); 3345 return ret; 3346 } 3347 3348 /** 3349 * batadv_tt_update_orig - update global translation table with new tt 3350 * information received via ogms 3351 * @bat_priv: the bat priv with all the soft interface information 3352 * @orig: the orig_node of the ogm 3353 * @tt_vlan: pointer to the first tvlv VLAN entry 3354 * @tt_num_vlan: number of tvlv VLAN entries 3355 * @tt_change: pointer to the first entry in the TT buffer 3356 * @tt_num_changes: number of tt changes inside the tt buffer 3357 * @ttvn: translation table version number of this changeset 3358 * @tt_crc: crc32 checksum of orig node's translation table 3359 */ 3360 static void batadv_tt_update_orig(struct batadv_priv *bat_priv, 3361 struct batadv_orig_node *orig_node, 3362 const void *tt_buff, u16 tt_num_vlan, 3363 struct batadv_tvlv_tt_change *tt_change, 3364 u16 tt_num_changes, u8 ttvn) 3365 { 3366 u8 orig_ttvn = (u8)atomic_read(&orig_node->last_ttvn); 3367 struct batadv_tvlv_tt_vlan_data *tt_vlan; 3368 bool full_table = true; 3369 bool has_tt_init; 3370 3371 tt_vlan = (struct batadv_tvlv_tt_vlan_data *)tt_buff; 3372 has_tt_init = test_bit(BATADV_ORIG_CAPA_HAS_TT, 3373 &orig_node->capa_initialized); 3374 3375 /* orig table not initialised AND first diff is in the OGM OR the ttvn 3376 * increased by one -> we can apply the attached changes 3377 */ 3378 if ((!has_tt_init && ttvn == 1) || ttvn - orig_ttvn == 1) { 3379 /* the OGM could not contain the changes due to their size or 3380 * because they have already been sent BATADV_TT_OGM_APPEND_MAX 3381 * times. 3382 * In this case send a tt request 3383 */ 3384 if (!tt_num_changes) { 3385 full_table = false; 3386 goto request_table; 3387 } 3388 3389 spin_lock_bh(&orig_node->tt_lock); 3390 3391 batadv_tt_update_changes(bat_priv, orig_node, tt_num_changes, 3392 ttvn, tt_change); 3393 3394 /* Even if we received the precomputed crc with the OGM, we 3395 * prefer to recompute it to spot any possible inconsistency 3396 * in the global table 3397 */ 3398 batadv_tt_global_update_crc(bat_priv, orig_node); 3399 3400 spin_unlock_bh(&orig_node->tt_lock); 3401 3402 /* The ttvn alone is not enough to guarantee consistency 3403 * because a single value could represent different states 3404 * (due to the wrap around). Thus a node has to check whether 3405 * the resulting table (after applying the changes) is still 3406 * consistent or not. E.g. a node could disconnect while its 3407 * ttvn is X and reconnect on ttvn = X + TTVN_MAX: in this case 3408 * checking the CRC value is mandatory to detect the 3409 * inconsistency 3410 */ 3411 if (!batadv_tt_global_check_crc(orig_node, tt_vlan, 3412 tt_num_vlan)) 3413 goto request_table; 3414 } else { 3415 /* if we missed more than one change or our tables are not 3416 * in sync anymore -> request fresh tt data 3417 */ 3418 if (!has_tt_init || ttvn != orig_ttvn || 3419 !batadv_tt_global_check_crc(orig_node, tt_vlan, 3420 tt_num_vlan)) { 3421 request_table: 3422 batadv_dbg(BATADV_DBG_TT, bat_priv, 3423 "TT inconsistency for %pM. Need to retrieve the correct information (ttvn: %u last_ttvn: %u num_changes: %u)\n", 3424 orig_node->orig, ttvn, orig_ttvn, 3425 tt_num_changes); 3426 batadv_send_tt_request(bat_priv, orig_node, ttvn, 3427 tt_vlan, tt_num_vlan, 3428 full_table); 3429 return; 3430 } 3431 } 3432 } 3433 3434 /** 3435 * batadv_tt_global_client_is_roaming - check if a client is marked as roaming 3436 * @bat_priv: the bat priv with all the soft interface information 3437 * @addr: the mac address of the client to check 3438 * @vid: VLAN identifier 3439 * 3440 * Returns true if we know that the client has moved from its old originator 3441 * to another one. This entry is still kept for consistency purposes and will be 3442 * deleted later by a DEL or because of timeout 3443 */ 3444 bool batadv_tt_global_client_is_roaming(struct batadv_priv *bat_priv, 3445 u8 *addr, unsigned short vid) 3446 { 3447 struct batadv_tt_global_entry *tt_global_entry; 3448 bool ret = false; 3449 3450 tt_global_entry = batadv_tt_global_hash_find(bat_priv, addr, vid); 3451 if (!tt_global_entry) 3452 goto out; 3453 3454 ret = tt_global_entry->common.flags & BATADV_TT_CLIENT_ROAM; 3455 batadv_tt_global_entry_free_ref(tt_global_entry); 3456 out: 3457 return ret; 3458 } 3459 3460 /** 3461 * batadv_tt_local_client_is_roaming - tells whether the client is roaming 3462 * @bat_priv: the bat priv with all the soft interface information 3463 * @addr: the mac address of the local client to query 3464 * @vid: VLAN identifier 3465 * 3466 * Returns true if the local client is known to be roaming (it is not served by 3467 * this node anymore) or not. If yes, the client is still present in the table 3468 * to keep the latter consistent with the node TTVN 3469 */ 3470 bool batadv_tt_local_client_is_roaming(struct batadv_priv *bat_priv, 3471 u8 *addr, unsigned short vid) 3472 { 3473 struct batadv_tt_local_entry *tt_local_entry; 3474 bool ret = false; 3475 3476 tt_local_entry = batadv_tt_local_hash_find(bat_priv, addr, vid); 3477 if (!tt_local_entry) 3478 goto out; 3479 3480 ret = tt_local_entry->common.flags & BATADV_TT_CLIENT_ROAM; 3481 batadv_tt_local_entry_free_ref(tt_local_entry); 3482 out: 3483 return ret; 3484 } 3485 3486 bool batadv_tt_add_temporary_global_entry(struct batadv_priv *bat_priv, 3487 struct batadv_orig_node *orig_node, 3488 const unsigned char *addr, 3489 unsigned short vid) 3490 { 3491 bool ret = false; 3492 3493 if (!batadv_tt_global_add(bat_priv, orig_node, addr, vid, 3494 BATADV_TT_CLIENT_TEMP, 3495 atomic_read(&orig_node->last_ttvn))) 3496 goto out; 3497 3498 batadv_dbg(BATADV_DBG_TT, bat_priv, 3499 "Added temporary global client (addr: %pM, vid: %d, orig: %pM)\n", 3500 addr, BATADV_PRINT_VID(vid), orig_node->orig); 3501 ret = true; 3502 out: 3503 return ret; 3504 } 3505 3506 /** 3507 * batadv_tt_local_resize_to_mtu - resize the local translation table fit the 3508 * maximum packet size that can be transported through the mesh 3509 * @soft_iface: netdev struct of the mesh interface 3510 * 3511 * Remove entries older than 'timeout' and half timeout if more entries need 3512 * to be removed. 3513 */ 3514 void batadv_tt_local_resize_to_mtu(struct net_device *soft_iface) 3515 { 3516 struct batadv_priv *bat_priv = netdev_priv(soft_iface); 3517 int packet_size_max = atomic_read(&bat_priv->packet_size_max); 3518 int table_size, timeout = BATADV_TT_LOCAL_TIMEOUT / 2; 3519 bool reduced = false; 3520 3521 spin_lock_bh(&bat_priv->tt.commit_lock); 3522 3523 while (true) { 3524 table_size = batadv_tt_local_table_transmit_size(bat_priv); 3525 if (packet_size_max >= table_size) 3526 break; 3527 3528 batadv_tt_local_purge(bat_priv, timeout); 3529 batadv_tt_local_purge_pending_clients(bat_priv); 3530 3531 timeout /= 2; 3532 reduced = true; 3533 net_ratelimited_function(batadv_info, soft_iface, 3534 "Forced to purge local tt entries to fit new maximum fragment MTU (%i)\n", 3535 packet_size_max); 3536 } 3537 3538 /* commit these changes immediately, to avoid synchronization problem 3539 * with the TTVN 3540 */ 3541 if (reduced) 3542 batadv_tt_local_commit_changes_nolock(bat_priv); 3543 3544 spin_unlock_bh(&bat_priv->tt.commit_lock); 3545 } 3546 3547 /** 3548 * batadv_tt_tvlv_ogm_handler_v1 - process incoming tt tvlv container 3549 * @bat_priv: the bat priv with all the soft interface information 3550 * @orig: the orig_node of the ogm 3551 * @flags: flags indicating the tvlv state (see batadv_tvlv_handler_flags) 3552 * @tvlv_value: tvlv buffer containing the gateway data 3553 * @tvlv_value_len: tvlv buffer length 3554 */ 3555 static void batadv_tt_tvlv_ogm_handler_v1(struct batadv_priv *bat_priv, 3556 struct batadv_orig_node *orig, 3557 u8 flags, void *tvlv_value, 3558 u16 tvlv_value_len) 3559 { 3560 struct batadv_tvlv_tt_vlan_data *tt_vlan; 3561 struct batadv_tvlv_tt_change *tt_change; 3562 struct batadv_tvlv_tt_data *tt_data; 3563 u16 num_entries, num_vlan; 3564 3565 if (tvlv_value_len < sizeof(*tt_data)) 3566 return; 3567 3568 tt_data = (struct batadv_tvlv_tt_data *)tvlv_value; 3569 tvlv_value_len -= sizeof(*tt_data); 3570 3571 num_vlan = ntohs(tt_data->num_vlan); 3572 3573 if (tvlv_value_len < sizeof(*tt_vlan) * num_vlan) 3574 return; 3575 3576 tt_vlan = (struct batadv_tvlv_tt_vlan_data *)(tt_data + 1); 3577 tt_change = (struct batadv_tvlv_tt_change *)(tt_vlan + num_vlan); 3578 tvlv_value_len -= sizeof(*tt_vlan) * num_vlan; 3579 3580 num_entries = batadv_tt_entries(tvlv_value_len); 3581 3582 batadv_tt_update_orig(bat_priv, orig, tt_vlan, num_vlan, tt_change, 3583 num_entries, tt_data->ttvn); 3584 } 3585 3586 /** 3587 * batadv_tt_tvlv_unicast_handler_v1 - process incoming (unicast) tt tvlv 3588 * container 3589 * @bat_priv: the bat priv with all the soft interface information 3590 * @src: mac address of tt tvlv sender 3591 * @dst: mac address of tt tvlv recipient 3592 * @tvlv_value: tvlv buffer containing the tt data 3593 * @tvlv_value_len: tvlv buffer length 3594 * 3595 * Returns NET_RX_DROP if the tt tvlv is to be re-routed, NET_RX_SUCCESS 3596 * otherwise. 3597 */ 3598 static int batadv_tt_tvlv_unicast_handler_v1(struct batadv_priv *bat_priv, 3599 u8 *src, u8 *dst, 3600 void *tvlv_value, 3601 u16 tvlv_value_len) 3602 { 3603 struct batadv_tvlv_tt_data *tt_data; 3604 u16 tt_vlan_len, tt_num_entries; 3605 char tt_flag; 3606 bool ret; 3607 3608 if (tvlv_value_len < sizeof(*tt_data)) 3609 return NET_RX_SUCCESS; 3610 3611 tt_data = (struct batadv_tvlv_tt_data *)tvlv_value; 3612 tvlv_value_len -= sizeof(*tt_data); 3613 3614 tt_vlan_len = sizeof(struct batadv_tvlv_tt_vlan_data); 3615 tt_vlan_len *= ntohs(tt_data->num_vlan); 3616 3617 if (tvlv_value_len < tt_vlan_len) 3618 return NET_RX_SUCCESS; 3619 3620 tvlv_value_len -= tt_vlan_len; 3621 tt_num_entries = batadv_tt_entries(tvlv_value_len); 3622 3623 switch (tt_data->flags & BATADV_TT_DATA_TYPE_MASK) { 3624 case BATADV_TT_REQUEST: 3625 batadv_inc_counter(bat_priv, BATADV_CNT_TT_REQUEST_RX); 3626 3627 /* If this node cannot provide a TT response the tt_request is 3628 * forwarded 3629 */ 3630 ret = batadv_send_tt_response(bat_priv, tt_data, src, dst); 3631 if (!ret) { 3632 if (tt_data->flags & BATADV_TT_FULL_TABLE) 3633 tt_flag = 'F'; 3634 else 3635 tt_flag = '.'; 3636 3637 batadv_dbg(BATADV_DBG_TT, bat_priv, 3638 "Routing TT_REQUEST to %pM [%c]\n", 3639 dst, tt_flag); 3640 /* tvlv API will re-route the packet */ 3641 return NET_RX_DROP; 3642 } 3643 break; 3644 case BATADV_TT_RESPONSE: 3645 batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_RX); 3646 3647 if (batadv_is_my_mac(bat_priv, dst)) { 3648 batadv_handle_tt_response(bat_priv, tt_data, 3649 src, tt_num_entries); 3650 return NET_RX_SUCCESS; 3651 } 3652 3653 if (tt_data->flags & BATADV_TT_FULL_TABLE) 3654 tt_flag = 'F'; 3655 else 3656 tt_flag = '.'; 3657 3658 batadv_dbg(BATADV_DBG_TT, bat_priv, 3659 "Routing TT_RESPONSE to %pM [%c]\n", dst, tt_flag); 3660 3661 /* tvlv API will re-route the packet */ 3662 return NET_RX_DROP; 3663 } 3664 3665 return NET_RX_SUCCESS; 3666 } 3667 3668 /** 3669 * batadv_roam_tvlv_unicast_handler_v1 - process incoming tt roam tvlv container 3670 * @bat_priv: the bat priv with all the soft interface information 3671 * @src: mac address of tt tvlv sender 3672 * @dst: mac address of tt tvlv recipient 3673 * @tvlv_value: tvlv buffer containing the tt data 3674 * @tvlv_value_len: tvlv buffer length 3675 * 3676 * Returns NET_RX_DROP if the tt roam tvlv is to be re-routed, NET_RX_SUCCESS 3677 * otherwise. 3678 */ 3679 static int batadv_roam_tvlv_unicast_handler_v1(struct batadv_priv *bat_priv, 3680 u8 *src, u8 *dst, 3681 void *tvlv_value, 3682 u16 tvlv_value_len) 3683 { 3684 struct batadv_tvlv_roam_adv *roaming_adv; 3685 struct batadv_orig_node *orig_node = NULL; 3686 3687 /* If this node is not the intended recipient of the 3688 * roaming advertisement the packet is forwarded 3689 * (the tvlv API will re-route the packet). 3690 */ 3691 if (!batadv_is_my_mac(bat_priv, dst)) 3692 return NET_RX_DROP; 3693 3694 if (tvlv_value_len < sizeof(*roaming_adv)) 3695 goto out; 3696 3697 orig_node = batadv_orig_hash_find(bat_priv, src); 3698 if (!orig_node) 3699 goto out; 3700 3701 batadv_inc_counter(bat_priv, BATADV_CNT_TT_ROAM_ADV_RX); 3702 roaming_adv = (struct batadv_tvlv_roam_adv *)tvlv_value; 3703 3704 batadv_dbg(BATADV_DBG_TT, bat_priv, 3705 "Received ROAMING_ADV from %pM (client %pM)\n", 3706 src, roaming_adv->client); 3707 3708 batadv_tt_global_add(bat_priv, orig_node, roaming_adv->client, 3709 ntohs(roaming_adv->vid), BATADV_TT_CLIENT_ROAM, 3710 atomic_read(&orig_node->last_ttvn) + 1); 3711 3712 out: 3713 if (orig_node) 3714 batadv_orig_node_free_ref(orig_node); 3715 return NET_RX_SUCCESS; 3716 } 3717 3718 /** 3719 * batadv_tt_init - initialise the translation table internals 3720 * @bat_priv: the bat priv with all the soft interface information 3721 * 3722 * Return 0 on success or negative error number in case of failure. 3723 */ 3724 int batadv_tt_init(struct batadv_priv *bat_priv) 3725 { 3726 int ret; 3727 3728 /* synchronized flags must be remote */ 3729 BUILD_BUG_ON(!(BATADV_TT_SYNC_MASK & BATADV_TT_REMOTE_MASK)); 3730 3731 ret = batadv_tt_local_init(bat_priv); 3732 if (ret < 0) 3733 return ret; 3734 3735 ret = batadv_tt_global_init(bat_priv); 3736 if (ret < 0) 3737 return ret; 3738 3739 batadv_tvlv_handler_register(bat_priv, batadv_tt_tvlv_ogm_handler_v1, 3740 batadv_tt_tvlv_unicast_handler_v1, 3741 BATADV_TVLV_TT, 1, BATADV_NO_FLAGS); 3742 3743 batadv_tvlv_handler_register(bat_priv, NULL, 3744 batadv_roam_tvlv_unicast_handler_v1, 3745 BATADV_TVLV_ROAM, 1, BATADV_NO_FLAGS); 3746 3747 INIT_DELAYED_WORK(&bat_priv->tt.work, batadv_tt_purge); 3748 queue_delayed_work(batadv_event_workqueue, &bat_priv->tt.work, 3749 msecs_to_jiffies(BATADV_TT_WORK_PERIOD)); 3750 3751 return 1; 3752 } 3753 3754 /** 3755 * batadv_tt_global_is_isolated - check if a client is marked as isolated 3756 * @bat_priv: the bat priv with all the soft interface information 3757 * @addr: the mac address of the client 3758 * @vid: the identifier of the VLAN where this client is connected 3759 * 3760 * Returns true if the client is marked with the TT_CLIENT_ISOLA flag, false 3761 * otherwise 3762 */ 3763 bool batadv_tt_global_is_isolated(struct batadv_priv *bat_priv, 3764 const u8 *addr, unsigned short vid) 3765 { 3766 struct batadv_tt_global_entry *tt; 3767 bool ret; 3768 3769 tt = batadv_tt_global_hash_find(bat_priv, addr, vid); 3770 if (!tt) 3771 return false; 3772 3773 ret = tt->common.flags & BATADV_TT_CLIENT_ISOLA; 3774 3775 batadv_tt_global_entry_free_ref(tt); 3776 3777 return ret; 3778 } 3779