bat_v_ogm.c 33 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087
  1. // SPDX-License-Identifier: GPL-2.0
  2. /* Copyright (C) B.A.T.M.A.N. contributors:
  3. *
  4. * Antonio Quartulli
  5. */
  6. #include "bat_v_ogm.h"
  7. #include "main.h"
  8. #include <linux/atomic.h>
  9. #include <linux/byteorder/generic.h>
  10. #include <linux/container_of.h>
  11. #include <linux/errno.h>
  12. #include <linux/etherdevice.h>
  13. #include <linux/gfp.h>
  14. #include <linux/if_ether.h>
  15. #include <linux/jiffies.h>
  16. #include <linux/kref.h>
  17. #include <linux/list.h>
  18. #include <linux/lockdep.h>
  19. #include <linux/minmax.h>
  20. #include <linux/mutex.h>
  21. #include <linux/netdevice.h>
  22. #include <linux/random.h>
  23. #include <linux/rculist.h>
  24. #include <linux/rcupdate.h>
  25. #include <linux/skbuff.h>
  26. #include <linux/slab.h>
  27. #include <linux/spinlock.h>
  28. #include <linux/stddef.h>
  29. #include <linux/string.h>
  30. #include <linux/types.h>
  31. #include <linux/workqueue.h>
  32. #include <uapi/linux/batadv_packet.h>
  33. #include "bat_algo.h"
  34. #include "hard-interface.h"
  35. #include "hash.h"
  36. #include "log.h"
  37. #include "originator.h"
  38. #include "routing.h"
  39. #include "send.h"
  40. #include "translation-table.h"
  41. #include "tvlv.h"
  42. /**
  43. * batadv_v_ogm_orig_get() - retrieve and possibly create an originator node
  44. * @bat_priv: the bat priv with all the soft interface information
  45. * @addr: the address of the originator
  46. *
  47. * Return: the orig_node corresponding to the specified address. If such an
  48. * object does not exist, it is allocated here. In case of allocation failure
  49. * returns NULL.
  50. */
  51. struct batadv_orig_node *batadv_v_ogm_orig_get(struct batadv_priv *bat_priv,
  52. const u8 *addr)
  53. {
  54. struct batadv_orig_node *orig_node;
  55. int hash_added;
  56. orig_node = batadv_orig_hash_find(bat_priv, addr);
  57. if (orig_node)
  58. return orig_node;
  59. orig_node = batadv_orig_node_new(bat_priv, addr);
  60. if (!orig_node)
  61. return NULL;
  62. kref_get(&orig_node->refcount);
  63. hash_added = batadv_hash_add(bat_priv->orig_hash, batadv_compare_orig,
  64. batadv_choose_orig, orig_node,
  65. &orig_node->hash_entry);
  66. if (hash_added != 0) {
  67. /* remove refcnt for newly created orig_node and hash entry */
  68. batadv_orig_node_put(orig_node);
  69. batadv_orig_node_put(orig_node);
  70. orig_node = NULL;
  71. }
  72. return orig_node;
  73. }
  74. /**
  75. * batadv_v_ogm_start_queue_timer() - restart the OGM aggregation timer
  76. * @hard_iface: the interface to use to send the OGM
  77. */
  78. static void batadv_v_ogm_start_queue_timer(struct batadv_hard_iface *hard_iface)
  79. {
  80. unsigned int msecs = BATADV_MAX_AGGREGATION_MS * 1000;
  81. /* msecs * [0.9, 1.1] */
  82. msecs += get_random_u32_below(msecs / 5) - (msecs / 10);
  83. queue_delayed_work(batadv_event_workqueue, &hard_iface->bat_v.aggr_wq,
  84. msecs_to_jiffies(msecs / 1000));
  85. }
  86. /**
  87. * batadv_v_ogm_start_timer() - restart the OGM sending timer
  88. * @bat_priv: the bat priv with all the soft interface information
  89. */
  90. static void batadv_v_ogm_start_timer(struct batadv_priv *bat_priv)
  91. {
  92. unsigned long msecs;
  93. /* this function may be invoked in different contexts (ogm rescheduling
  94. * or hard_iface activation), but the work timer should not be reset
  95. */
  96. if (delayed_work_pending(&bat_priv->bat_v.ogm_wq))
  97. return;
  98. msecs = atomic_read(&bat_priv->orig_interval) - BATADV_JITTER;
  99. msecs += get_random_u32_below(2 * BATADV_JITTER);
  100. queue_delayed_work(batadv_event_workqueue, &bat_priv->bat_v.ogm_wq,
  101. msecs_to_jiffies(msecs));
  102. }
  103. /**
  104. * batadv_v_ogm_send_to_if() - send a batman ogm using a given interface
  105. * @skb: the OGM to send
  106. * @hard_iface: the interface to use to send the OGM
  107. */
  108. static void batadv_v_ogm_send_to_if(struct sk_buff *skb,
  109. struct batadv_hard_iface *hard_iface)
  110. {
  111. struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
  112. if (hard_iface->if_status != BATADV_IF_ACTIVE) {
  113. kfree_skb(skb);
  114. return;
  115. }
  116. batadv_inc_counter(bat_priv, BATADV_CNT_MGMT_TX);
  117. batadv_add_counter(bat_priv, BATADV_CNT_MGMT_TX_BYTES,
  118. skb->len + ETH_HLEN);
  119. batadv_send_broadcast_skb(skb, hard_iface);
  120. }
  121. /**
  122. * batadv_v_ogm_len() - OGMv2 packet length
  123. * @skb: the OGM to check
  124. *
  125. * Return: Length of the given OGMv2 packet, including tvlv length, excluding
  126. * ethernet header length.
  127. */
  128. static unsigned int batadv_v_ogm_len(struct sk_buff *skb)
  129. {
  130. struct batadv_ogm2_packet *ogm_packet;
  131. ogm_packet = (struct batadv_ogm2_packet *)skb->data;
  132. return BATADV_OGM2_HLEN + ntohs(ogm_packet->tvlv_len);
  133. }
  134. /**
  135. * batadv_v_ogm_queue_left() - check if given OGM still fits aggregation queue
  136. * @skb: the OGM to check
  137. * @hard_iface: the interface to use to send the OGM
  138. *
  139. * Caller needs to hold the hard_iface->bat_v.aggr_list.lock.
  140. *
  141. * Return: True, if the given OGMv2 packet still fits, false otherwise.
  142. */
  143. static bool batadv_v_ogm_queue_left(struct sk_buff *skb,
  144. struct batadv_hard_iface *hard_iface)
  145. {
  146. unsigned int max = min_t(unsigned int, hard_iface->net_dev->mtu,
  147. BATADV_MAX_AGGREGATION_BYTES);
  148. unsigned int ogm_len = batadv_v_ogm_len(skb);
  149. lockdep_assert_held(&hard_iface->bat_v.aggr_list.lock);
  150. return hard_iface->bat_v.aggr_len + ogm_len <= max;
  151. }
  152. /**
  153. * batadv_v_ogm_aggr_list_free - free all elements in an aggregation queue
  154. * @hard_iface: the interface holding the aggregation queue
  155. *
  156. * Empties the OGMv2 aggregation queue and frees all the skbs it contains.
  157. *
  158. * Caller needs to hold the hard_iface->bat_v.aggr_list.lock.
  159. */
  160. static void batadv_v_ogm_aggr_list_free(struct batadv_hard_iface *hard_iface)
  161. {
  162. lockdep_assert_held(&hard_iface->bat_v.aggr_list.lock);
  163. __skb_queue_purge(&hard_iface->bat_v.aggr_list);
  164. hard_iface->bat_v.aggr_len = 0;
  165. }
  166. /**
  167. * batadv_v_ogm_aggr_send() - flush & send aggregation queue
  168. * @hard_iface: the interface with the aggregation queue to flush
  169. *
  170. * Aggregates all OGMv2 packets currently in the aggregation queue into a
  171. * single OGMv2 packet and transmits this aggregate.
  172. *
  173. * The aggregation queue is empty after this call.
  174. *
  175. * Caller needs to hold the hard_iface->bat_v.aggr_list.lock.
  176. */
  177. static void batadv_v_ogm_aggr_send(struct batadv_hard_iface *hard_iface)
  178. {
  179. unsigned int aggr_len = hard_iface->bat_v.aggr_len;
  180. struct sk_buff *skb_aggr;
  181. unsigned int ogm_len;
  182. struct sk_buff *skb;
  183. lockdep_assert_held(&hard_iface->bat_v.aggr_list.lock);
  184. if (!aggr_len)
  185. return;
  186. skb_aggr = dev_alloc_skb(aggr_len + ETH_HLEN + NET_IP_ALIGN);
  187. if (!skb_aggr) {
  188. batadv_v_ogm_aggr_list_free(hard_iface);
  189. return;
  190. }
  191. skb_reserve(skb_aggr, ETH_HLEN + NET_IP_ALIGN);
  192. skb_reset_network_header(skb_aggr);
  193. while ((skb = __skb_dequeue(&hard_iface->bat_v.aggr_list))) {
  194. hard_iface->bat_v.aggr_len -= batadv_v_ogm_len(skb);
  195. ogm_len = batadv_v_ogm_len(skb);
  196. skb_put_data(skb_aggr, skb->data, ogm_len);
  197. consume_skb(skb);
  198. }
  199. batadv_v_ogm_send_to_if(skb_aggr, hard_iface);
  200. }
  201. /**
  202. * batadv_v_ogm_queue_on_if() - queue a batman ogm on a given interface
  203. * @skb: the OGM to queue
  204. * @hard_iface: the interface to queue the OGM on
  205. */
  206. static void batadv_v_ogm_queue_on_if(struct sk_buff *skb,
  207. struct batadv_hard_iface *hard_iface)
  208. {
  209. struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
  210. if (!atomic_read(&bat_priv->aggregated_ogms)) {
  211. batadv_v_ogm_send_to_if(skb, hard_iface);
  212. return;
  213. }
  214. spin_lock_bh(&hard_iface->bat_v.aggr_list.lock);
  215. if (!batadv_v_ogm_queue_left(skb, hard_iface))
  216. batadv_v_ogm_aggr_send(hard_iface);
  217. hard_iface->bat_v.aggr_len += batadv_v_ogm_len(skb);
  218. __skb_queue_tail(&hard_iface->bat_v.aggr_list, skb);
  219. spin_unlock_bh(&hard_iface->bat_v.aggr_list.lock);
  220. }
  221. /**
  222. * batadv_v_ogm_send_softif() - periodic worker broadcasting the own OGM
  223. * @bat_priv: the bat priv with all the soft interface information
  224. */
  225. static void batadv_v_ogm_send_softif(struct batadv_priv *bat_priv)
  226. {
  227. struct batadv_hard_iface *hard_iface;
  228. struct batadv_ogm2_packet *ogm_packet;
  229. struct sk_buff *skb, *skb_tmp;
  230. unsigned char *ogm_buff;
  231. int ogm_buff_len;
  232. u16 tvlv_len = 0;
  233. int ret;
  234. lockdep_assert_held(&bat_priv->bat_v.ogm_buff_mutex);
  235. if (atomic_read(&bat_priv->mesh_state) == BATADV_MESH_DEACTIVATING)
  236. goto out;
  237. ogm_buff = bat_priv->bat_v.ogm_buff;
  238. ogm_buff_len = bat_priv->bat_v.ogm_buff_len;
  239. /* tt changes have to be committed before the tvlv data is
  240. * appended as it may alter the tt tvlv container
  241. */
  242. batadv_tt_local_commit_changes(bat_priv);
  243. tvlv_len = batadv_tvlv_container_ogm_append(bat_priv, &ogm_buff,
  244. &ogm_buff_len,
  245. BATADV_OGM2_HLEN);
  246. bat_priv->bat_v.ogm_buff = ogm_buff;
  247. bat_priv->bat_v.ogm_buff_len = ogm_buff_len;
  248. skb = netdev_alloc_skb_ip_align(NULL, ETH_HLEN + ogm_buff_len);
  249. if (!skb)
  250. goto reschedule;
  251. skb_reserve(skb, ETH_HLEN);
  252. skb_put_data(skb, ogm_buff, ogm_buff_len);
  253. ogm_packet = (struct batadv_ogm2_packet *)skb->data;
  254. ogm_packet->seqno = htonl(atomic_read(&bat_priv->bat_v.ogm_seqno));
  255. atomic_inc(&bat_priv->bat_v.ogm_seqno);
  256. ogm_packet->tvlv_len = htons(tvlv_len);
  257. /* broadcast on every interface */
  258. rcu_read_lock();
  259. list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
  260. if (hard_iface->soft_iface != bat_priv->soft_iface)
  261. continue;
  262. if (!kref_get_unless_zero(&hard_iface->refcount))
  263. continue;
  264. ret = batadv_hardif_no_broadcast(hard_iface, NULL, NULL);
  265. if (ret) {
  266. char *type;
  267. switch (ret) {
  268. case BATADV_HARDIF_BCAST_NORECIPIENT:
  269. type = "no neighbor";
  270. break;
  271. case BATADV_HARDIF_BCAST_DUPFWD:
  272. type = "single neighbor is source";
  273. break;
  274. case BATADV_HARDIF_BCAST_DUPORIG:
  275. type = "single neighbor is originator";
  276. break;
  277. default:
  278. type = "unknown";
  279. }
  280. batadv_dbg(BATADV_DBG_BATMAN, bat_priv, "OGM2 from ourselves on %s suppressed: %s\n",
  281. hard_iface->net_dev->name, type);
  282. batadv_hardif_put(hard_iface);
  283. continue;
  284. }
  285. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  286. "Sending own OGM2 packet (originator %pM, seqno %u, throughput %u, TTL %d) on interface %s [%pM]\n",
  287. ogm_packet->orig, ntohl(ogm_packet->seqno),
  288. ntohl(ogm_packet->throughput), ogm_packet->ttl,
  289. hard_iface->net_dev->name,
  290. hard_iface->net_dev->dev_addr);
  291. /* this skb gets consumed by batadv_v_ogm_send_to_if() */
  292. skb_tmp = skb_clone(skb, GFP_ATOMIC);
  293. if (!skb_tmp) {
  294. batadv_hardif_put(hard_iface);
  295. break;
  296. }
  297. batadv_v_ogm_queue_on_if(skb_tmp, hard_iface);
  298. batadv_hardif_put(hard_iface);
  299. }
  300. rcu_read_unlock();
  301. consume_skb(skb);
  302. reschedule:
  303. batadv_v_ogm_start_timer(bat_priv);
  304. out:
  305. return;
  306. }
  307. /**
  308. * batadv_v_ogm_send() - periodic worker broadcasting the own OGM
  309. * @work: work queue item
  310. */
  311. static void batadv_v_ogm_send(struct work_struct *work)
  312. {
  313. struct batadv_priv_bat_v *bat_v;
  314. struct batadv_priv *bat_priv;
  315. bat_v = container_of(work, struct batadv_priv_bat_v, ogm_wq.work);
  316. bat_priv = container_of(bat_v, struct batadv_priv, bat_v);
  317. mutex_lock(&bat_priv->bat_v.ogm_buff_mutex);
  318. batadv_v_ogm_send_softif(bat_priv);
  319. mutex_unlock(&bat_priv->bat_v.ogm_buff_mutex);
  320. }
  321. /**
  322. * batadv_v_ogm_aggr_work() - OGM queue periodic task per interface
  323. * @work: work queue item
  324. *
  325. * Emits aggregated OGM messages in regular intervals.
  326. */
  327. void batadv_v_ogm_aggr_work(struct work_struct *work)
  328. {
  329. struct batadv_hard_iface_bat_v *batv;
  330. struct batadv_hard_iface *hard_iface;
  331. batv = container_of(work, struct batadv_hard_iface_bat_v, aggr_wq.work);
  332. hard_iface = container_of(batv, struct batadv_hard_iface, bat_v);
  333. spin_lock_bh(&hard_iface->bat_v.aggr_list.lock);
  334. batadv_v_ogm_aggr_send(hard_iface);
  335. spin_unlock_bh(&hard_iface->bat_v.aggr_list.lock);
  336. batadv_v_ogm_start_queue_timer(hard_iface);
  337. }
  338. /**
  339. * batadv_v_ogm_iface_enable() - prepare an interface for B.A.T.M.A.N. V
  340. * @hard_iface: the interface to prepare
  341. *
  342. * Takes care of scheduling its own OGM sending routine for this interface.
  343. *
  344. * Return: 0 on success or a negative error code otherwise
  345. */
  346. int batadv_v_ogm_iface_enable(struct batadv_hard_iface *hard_iface)
  347. {
  348. struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
  349. batadv_v_ogm_start_queue_timer(hard_iface);
  350. batadv_v_ogm_start_timer(bat_priv);
  351. return 0;
  352. }
  353. /**
  354. * batadv_v_ogm_iface_disable() - release OGM interface private resources
  355. * @hard_iface: interface for which the resources have to be released
  356. */
  357. void batadv_v_ogm_iface_disable(struct batadv_hard_iface *hard_iface)
  358. {
  359. cancel_delayed_work_sync(&hard_iface->bat_v.aggr_wq);
  360. spin_lock_bh(&hard_iface->bat_v.aggr_list.lock);
  361. batadv_v_ogm_aggr_list_free(hard_iface);
  362. spin_unlock_bh(&hard_iface->bat_v.aggr_list.lock);
  363. }
  364. /**
  365. * batadv_v_ogm_primary_iface_set() - set a new primary interface
  366. * @primary_iface: the new primary interface
  367. */
  368. void batadv_v_ogm_primary_iface_set(struct batadv_hard_iface *primary_iface)
  369. {
  370. struct batadv_priv *bat_priv = netdev_priv(primary_iface->soft_iface);
  371. struct batadv_ogm2_packet *ogm_packet;
  372. mutex_lock(&bat_priv->bat_v.ogm_buff_mutex);
  373. if (!bat_priv->bat_v.ogm_buff)
  374. goto unlock;
  375. ogm_packet = (struct batadv_ogm2_packet *)bat_priv->bat_v.ogm_buff;
  376. ether_addr_copy(ogm_packet->orig, primary_iface->net_dev->dev_addr);
  377. unlock:
  378. mutex_unlock(&bat_priv->bat_v.ogm_buff_mutex);
  379. }
  380. /**
  381. * batadv_v_forward_penalty() - apply a penalty to the throughput metric
  382. * forwarded with B.A.T.M.A.N. V OGMs
  383. * @bat_priv: the bat priv with all the soft interface information
  384. * @if_incoming: the interface where the OGM has been received
  385. * @if_outgoing: the interface where the OGM has to be forwarded to
  386. * @throughput: the current throughput
  387. *
  388. * Apply a penalty on the current throughput metric value based on the
  389. * characteristic of the interface where the OGM has been received.
  390. *
  391. * Initially the per hardif hop penalty is applied to the throughput. After
  392. * that the return value is then computed as follows:
  393. * - throughput * 50% if the incoming and outgoing interface are the
  394. * same WiFi interface and the throughput is above
  395. * 1MBit/s
  396. * - throughput if the outgoing interface is the default
  397. * interface (i.e. this OGM is processed for the
  398. * internal table and not forwarded)
  399. * - throughput * node hop penalty otherwise
  400. *
  401. * Return: the penalised throughput metric.
  402. */
  403. static u32 batadv_v_forward_penalty(struct batadv_priv *bat_priv,
  404. struct batadv_hard_iface *if_incoming,
  405. struct batadv_hard_iface *if_outgoing,
  406. u32 throughput)
  407. {
  408. int if_hop_penalty = atomic_read(&if_incoming->hop_penalty);
  409. int hop_penalty = atomic_read(&bat_priv->hop_penalty);
  410. int hop_penalty_max = BATADV_TQ_MAX_VALUE;
  411. /* Apply per hardif hop penalty */
  412. throughput = throughput * (hop_penalty_max - if_hop_penalty) /
  413. hop_penalty_max;
  414. /* Don't apply hop penalty in default originator table. */
  415. if (if_outgoing == BATADV_IF_DEFAULT)
  416. return throughput;
  417. /* Forwarding on the same WiFi interface cuts the throughput in half
  418. * due to the store & forward characteristics of WIFI.
  419. * Very low throughput values are the exception.
  420. */
  421. if (throughput > 10 &&
  422. if_incoming == if_outgoing &&
  423. !(if_incoming->bat_v.flags & BATADV_FULL_DUPLEX))
  424. return throughput / 2;
  425. /* hop penalty of 255 equals 100% */
  426. return throughput * (hop_penalty_max - hop_penalty) / hop_penalty_max;
  427. }
  428. /**
  429. * batadv_v_ogm_forward() - check conditions and forward an OGM to the given
  430. * outgoing interface
  431. * @bat_priv: the bat priv with all the soft interface information
  432. * @ogm_received: previously received OGM to be forwarded
  433. * @orig_node: the originator which has been updated
  434. * @neigh_node: the neigh_node through with the OGM has been received
  435. * @if_incoming: the interface on which this OGM was received on
  436. * @if_outgoing: the interface to which the OGM has to be forwarded to
  437. *
  438. * Forward an OGM to an interface after having altered the throughput metric and
  439. * the TTL value contained in it. The original OGM isn't modified.
  440. */
  441. static void batadv_v_ogm_forward(struct batadv_priv *bat_priv,
  442. const struct batadv_ogm2_packet *ogm_received,
  443. struct batadv_orig_node *orig_node,
  444. struct batadv_neigh_node *neigh_node,
  445. struct batadv_hard_iface *if_incoming,
  446. struct batadv_hard_iface *if_outgoing)
  447. {
  448. struct batadv_neigh_ifinfo *neigh_ifinfo = NULL;
  449. struct batadv_orig_ifinfo *orig_ifinfo = NULL;
  450. struct batadv_neigh_node *router = NULL;
  451. struct batadv_ogm2_packet *ogm_forward;
  452. unsigned char *skb_buff;
  453. struct sk_buff *skb;
  454. size_t packet_len;
  455. u16 tvlv_len;
  456. /* only forward for specific interfaces, not for the default one. */
  457. if (if_outgoing == BATADV_IF_DEFAULT)
  458. goto out;
  459. orig_ifinfo = batadv_orig_ifinfo_new(orig_node, if_outgoing);
  460. if (!orig_ifinfo)
  461. goto out;
  462. /* acquire possibly updated router */
  463. router = batadv_orig_router_get(orig_node, if_outgoing);
  464. /* strict rule: forward packets coming from the best next hop only */
  465. if (neigh_node != router)
  466. goto out;
  467. /* don't forward the same seqno twice on one interface */
  468. if (orig_ifinfo->last_seqno_forwarded == ntohl(ogm_received->seqno))
  469. goto out;
  470. orig_ifinfo->last_seqno_forwarded = ntohl(ogm_received->seqno);
  471. if (ogm_received->ttl <= 1) {
  472. batadv_dbg(BATADV_DBG_BATMAN, bat_priv, "ttl exceeded\n");
  473. goto out;
  474. }
  475. neigh_ifinfo = batadv_neigh_ifinfo_get(neigh_node, if_outgoing);
  476. if (!neigh_ifinfo)
  477. goto out;
  478. tvlv_len = ntohs(ogm_received->tvlv_len);
  479. packet_len = BATADV_OGM2_HLEN + tvlv_len;
  480. skb = netdev_alloc_skb_ip_align(if_outgoing->net_dev,
  481. ETH_HLEN + packet_len);
  482. if (!skb)
  483. goto out;
  484. skb_reserve(skb, ETH_HLEN);
  485. skb_buff = skb_put_data(skb, ogm_received, packet_len);
  486. /* apply forward penalty */
  487. ogm_forward = (struct batadv_ogm2_packet *)skb_buff;
  488. ogm_forward->throughput = htonl(neigh_ifinfo->bat_v.throughput);
  489. ogm_forward->ttl--;
  490. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  491. "Forwarding OGM2 packet on %s: throughput %u, ttl %u, received via %s\n",
  492. if_outgoing->net_dev->name, ntohl(ogm_forward->throughput),
  493. ogm_forward->ttl, if_incoming->net_dev->name);
  494. batadv_v_ogm_queue_on_if(skb, if_outgoing);
  495. out:
  496. batadv_orig_ifinfo_put(orig_ifinfo);
  497. batadv_neigh_node_put(router);
  498. batadv_neigh_ifinfo_put(neigh_ifinfo);
  499. }
  500. /**
  501. * batadv_v_ogm_metric_update() - update route metric based on OGM
  502. * @bat_priv: the bat priv with all the soft interface information
  503. * @ogm2: OGM2 structure
  504. * @orig_node: Originator structure for which the OGM has been received
  505. * @neigh_node: the neigh_node through with the OGM has been received
  506. * @if_incoming: the interface where this packet was received
  507. * @if_outgoing: the interface for which the packet should be considered
  508. *
  509. * Return:
  510. * 1 if the OGM is new,
  511. * 0 if it is not new but valid,
  512. * <0 on error (e.g. old OGM)
  513. */
  514. static int batadv_v_ogm_metric_update(struct batadv_priv *bat_priv,
  515. const struct batadv_ogm2_packet *ogm2,
  516. struct batadv_orig_node *orig_node,
  517. struct batadv_neigh_node *neigh_node,
  518. struct batadv_hard_iface *if_incoming,
  519. struct batadv_hard_iface *if_outgoing)
  520. {
  521. struct batadv_orig_ifinfo *orig_ifinfo;
  522. struct batadv_neigh_ifinfo *neigh_ifinfo = NULL;
  523. bool protection_started = false;
  524. int ret = -EINVAL;
  525. u32 path_throughput;
  526. s32 seq_diff;
  527. orig_ifinfo = batadv_orig_ifinfo_new(orig_node, if_outgoing);
  528. if (!orig_ifinfo)
  529. goto out;
  530. seq_diff = ntohl(ogm2->seqno) - orig_ifinfo->last_real_seqno;
  531. if (!hlist_empty(&orig_node->neigh_list) &&
  532. batadv_window_protected(bat_priv, seq_diff,
  533. BATADV_OGM_MAX_AGE,
  534. &orig_ifinfo->batman_seqno_reset,
  535. &protection_started)) {
  536. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  537. "Drop packet: packet within window protection time from %pM\n",
  538. ogm2->orig);
  539. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  540. "Last reset: %ld, %ld\n",
  541. orig_ifinfo->batman_seqno_reset, jiffies);
  542. goto out;
  543. }
  544. /* drop packets with old seqnos, however accept the first packet after
  545. * a host has been rebooted.
  546. */
  547. if (seq_diff < 0 && !protection_started)
  548. goto out;
  549. neigh_node->last_seen = jiffies;
  550. orig_node->last_seen = jiffies;
  551. orig_ifinfo->last_real_seqno = ntohl(ogm2->seqno);
  552. orig_ifinfo->last_ttl = ogm2->ttl;
  553. neigh_ifinfo = batadv_neigh_ifinfo_new(neigh_node, if_outgoing);
  554. if (!neigh_ifinfo)
  555. goto out;
  556. path_throughput = batadv_v_forward_penalty(bat_priv, if_incoming,
  557. if_outgoing,
  558. ntohl(ogm2->throughput));
  559. neigh_ifinfo->bat_v.throughput = path_throughput;
  560. neigh_ifinfo->bat_v.last_seqno = ntohl(ogm2->seqno);
  561. neigh_ifinfo->last_ttl = ogm2->ttl;
  562. if (seq_diff > 0 || protection_started)
  563. ret = 1;
  564. else
  565. ret = 0;
  566. out:
  567. batadv_orig_ifinfo_put(orig_ifinfo);
  568. batadv_neigh_ifinfo_put(neigh_ifinfo);
  569. return ret;
  570. }
  571. /**
  572. * batadv_v_ogm_route_update() - update routes based on OGM
  573. * @bat_priv: the bat priv with all the soft interface information
  574. * @ethhdr: the Ethernet header of the OGM2
  575. * @ogm2: OGM2 structure
  576. * @orig_node: Originator structure for which the OGM has been received
  577. * @neigh_node: the neigh_node through with the OGM has been received
  578. * @if_incoming: the interface where this packet was received
  579. * @if_outgoing: the interface for which the packet should be considered
  580. *
  581. * Return: true if the packet should be forwarded, false otherwise
  582. */
  583. static bool batadv_v_ogm_route_update(struct batadv_priv *bat_priv,
  584. const struct ethhdr *ethhdr,
  585. const struct batadv_ogm2_packet *ogm2,
  586. struct batadv_orig_node *orig_node,
  587. struct batadv_neigh_node *neigh_node,
  588. struct batadv_hard_iface *if_incoming,
  589. struct batadv_hard_iface *if_outgoing)
  590. {
  591. struct batadv_neigh_node *router = NULL;
  592. struct batadv_orig_node *orig_neigh_node;
  593. struct batadv_neigh_node *orig_neigh_router = NULL;
  594. struct batadv_neigh_ifinfo *router_ifinfo = NULL, *neigh_ifinfo = NULL;
  595. u32 router_throughput, neigh_throughput;
  596. u32 router_last_seqno;
  597. u32 neigh_last_seqno;
  598. s32 neigh_seq_diff;
  599. bool forward = false;
  600. orig_neigh_node = batadv_v_ogm_orig_get(bat_priv, ethhdr->h_source);
  601. if (!orig_neigh_node)
  602. goto out;
  603. orig_neigh_router = batadv_orig_router_get(orig_neigh_node,
  604. if_outgoing);
  605. /* drop packet if sender is not a direct neighbor and if we
  606. * don't route towards it
  607. */
  608. router = batadv_orig_router_get(orig_node, if_outgoing);
  609. if (router && router->orig_node != orig_node && !orig_neigh_router) {
  610. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  611. "Drop packet: OGM via unknown neighbor!\n");
  612. goto out;
  613. }
  614. /* Mark the OGM to be considered for forwarding, and update routes
  615. * if needed.
  616. */
  617. forward = true;
  618. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  619. "Searching and updating originator entry of received packet\n");
  620. /* if this neighbor already is our next hop there is nothing
  621. * to change
  622. */
  623. if (router == neigh_node)
  624. goto out;
  625. /* don't consider neighbours with worse throughput.
  626. * also switch route if this seqno is BATADV_V_MAX_ORIGDIFF newer than
  627. * the last received seqno from our best next hop.
  628. */
  629. if (router) {
  630. router_ifinfo = batadv_neigh_ifinfo_get(router, if_outgoing);
  631. neigh_ifinfo = batadv_neigh_ifinfo_get(neigh_node, if_outgoing);
  632. /* if these are not allocated, something is wrong. */
  633. if (!router_ifinfo || !neigh_ifinfo)
  634. goto out;
  635. neigh_last_seqno = neigh_ifinfo->bat_v.last_seqno;
  636. router_last_seqno = router_ifinfo->bat_v.last_seqno;
  637. neigh_seq_diff = neigh_last_seqno - router_last_seqno;
  638. router_throughput = router_ifinfo->bat_v.throughput;
  639. neigh_throughput = neigh_ifinfo->bat_v.throughput;
  640. if (neigh_seq_diff < BATADV_OGM_MAX_ORIGDIFF &&
  641. router_throughput >= neigh_throughput)
  642. goto out;
  643. }
  644. batadv_update_route(bat_priv, orig_node, if_outgoing, neigh_node);
  645. out:
  646. batadv_neigh_node_put(router);
  647. batadv_neigh_node_put(orig_neigh_router);
  648. batadv_orig_node_put(orig_neigh_node);
  649. batadv_neigh_ifinfo_put(router_ifinfo);
  650. batadv_neigh_ifinfo_put(neigh_ifinfo);
  651. return forward;
  652. }
  653. /**
  654. * batadv_v_ogm_process_per_outif() - process a batman v OGM for an outgoing if
  655. * @bat_priv: the bat priv with all the soft interface information
  656. * @ethhdr: the Ethernet header of the OGM2
  657. * @ogm2: OGM2 structure
  658. * @orig_node: Originator structure for which the OGM has been received
  659. * @neigh_node: the neigh_node through with the OGM has been received
  660. * @if_incoming: the interface where this packet was received
  661. * @if_outgoing: the interface for which the packet should be considered
  662. */
  663. static void
  664. batadv_v_ogm_process_per_outif(struct batadv_priv *bat_priv,
  665. const struct ethhdr *ethhdr,
  666. const struct batadv_ogm2_packet *ogm2,
  667. struct batadv_orig_node *orig_node,
  668. struct batadv_neigh_node *neigh_node,
  669. struct batadv_hard_iface *if_incoming,
  670. struct batadv_hard_iface *if_outgoing)
  671. {
  672. int seqno_age;
  673. bool forward;
  674. /* first, update the metric with according sanity checks */
  675. seqno_age = batadv_v_ogm_metric_update(bat_priv, ogm2, orig_node,
  676. neigh_node, if_incoming,
  677. if_outgoing);
  678. /* outdated sequence numbers are to be discarded */
  679. if (seqno_age < 0)
  680. return;
  681. /* only unknown & newer OGMs contain TVLVs we are interested in */
  682. if (seqno_age > 0 && if_outgoing == BATADV_IF_DEFAULT)
  683. batadv_tvlv_containers_process(bat_priv, BATADV_OGM2, orig_node,
  684. NULL,
  685. (unsigned char *)(ogm2 + 1),
  686. ntohs(ogm2->tvlv_len));
  687. /* if the metric update went through, update routes if needed */
  688. forward = batadv_v_ogm_route_update(bat_priv, ethhdr, ogm2, orig_node,
  689. neigh_node, if_incoming,
  690. if_outgoing);
  691. /* if the routes have been processed correctly, check and forward */
  692. if (forward)
  693. batadv_v_ogm_forward(bat_priv, ogm2, orig_node, neigh_node,
  694. if_incoming, if_outgoing);
  695. }
  696. /**
  697. * batadv_v_ogm_aggr_packet() - checks if there is another OGM aggregated
  698. * @buff_pos: current position in the skb
  699. * @packet_len: total length of the skb
  700. * @ogm2_packet: potential OGM2 in buffer
  701. *
  702. * Return: true if there is enough space for another OGM, false otherwise.
  703. */
  704. static bool
  705. batadv_v_ogm_aggr_packet(int buff_pos, int packet_len,
  706. const struct batadv_ogm2_packet *ogm2_packet)
  707. {
  708. int next_buff_pos = 0;
  709. /* check if there is enough space for the header */
  710. next_buff_pos += buff_pos + sizeof(*ogm2_packet);
  711. if (next_buff_pos > packet_len)
  712. return false;
  713. /* check if there is enough space for the optional TVLV */
  714. next_buff_pos += ntohs(ogm2_packet->tvlv_len);
  715. return (next_buff_pos <= packet_len) &&
  716. (next_buff_pos <= BATADV_MAX_AGGREGATION_BYTES);
  717. }
  718. /**
  719. * batadv_v_ogm_process() - process an incoming batman v OGM
  720. * @skb: the skb containing the OGM
  721. * @ogm_offset: offset to the OGM which should be processed (for aggregates)
  722. * @if_incoming: the interface where this packet was received
  723. */
  724. static void batadv_v_ogm_process(const struct sk_buff *skb, int ogm_offset,
  725. struct batadv_hard_iface *if_incoming)
  726. {
  727. struct batadv_priv *bat_priv = netdev_priv(if_incoming->soft_iface);
  728. struct ethhdr *ethhdr;
  729. struct batadv_orig_node *orig_node = NULL;
  730. struct batadv_hardif_neigh_node *hardif_neigh = NULL;
  731. struct batadv_neigh_node *neigh_node = NULL;
  732. struct batadv_hard_iface *hard_iface;
  733. struct batadv_ogm2_packet *ogm_packet;
  734. u32 ogm_throughput, link_throughput, path_throughput;
  735. int ret;
  736. ethhdr = eth_hdr(skb);
  737. ogm_packet = (struct batadv_ogm2_packet *)(skb->data + ogm_offset);
  738. ogm_throughput = ntohl(ogm_packet->throughput);
  739. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  740. "Received OGM2 packet via NB: %pM, IF: %s [%pM] (from OG: %pM, seqno %u, throughput %u, TTL %u, V %u, tvlv_len %u)\n",
  741. ethhdr->h_source, if_incoming->net_dev->name,
  742. if_incoming->net_dev->dev_addr, ogm_packet->orig,
  743. ntohl(ogm_packet->seqno), ogm_throughput, ogm_packet->ttl,
  744. ogm_packet->version, ntohs(ogm_packet->tvlv_len));
  745. if (batadv_is_my_mac(bat_priv, ogm_packet->orig)) {
  746. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  747. "Drop packet: originator packet from ourself\n");
  748. return;
  749. }
  750. /* If the throughput metric is 0, immediately drop the packet. No need
  751. * to create orig_node / neigh_node for an unusable route.
  752. */
  753. if (ogm_throughput == 0) {
  754. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  755. "Drop packet: originator packet with throughput metric of 0\n");
  756. return;
  757. }
  758. /* require ELP packets be to received from this neighbor first */
  759. hardif_neigh = batadv_hardif_neigh_get(if_incoming, ethhdr->h_source);
  760. if (!hardif_neigh) {
  761. batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
  762. "Drop packet: OGM via unknown neighbor!\n");
  763. goto out;
  764. }
  765. orig_node = batadv_v_ogm_orig_get(bat_priv, ogm_packet->orig);
  766. if (!orig_node)
  767. goto out;
  768. neigh_node = batadv_neigh_node_get_or_create(orig_node, if_incoming,
  769. ethhdr->h_source);
  770. if (!neigh_node)
  771. goto out;
  772. /* Update the received throughput metric to match the link
  773. * characteristic:
  774. * - If this OGM traveled one hop so far (emitted by single hop
  775. * neighbor) the path throughput metric equals the link throughput.
  776. * - For OGMs traversing more than hop the path throughput metric is
  777. * the smaller of the path throughput and the link throughput.
  778. */
  779. link_throughput = ewma_throughput_read(&hardif_neigh->bat_v.throughput);
  780. path_throughput = min_t(u32, link_throughput, ogm_throughput);
  781. ogm_packet->throughput = htonl(path_throughput);
  782. batadv_v_ogm_process_per_outif(bat_priv, ethhdr, ogm_packet, orig_node,
  783. neigh_node, if_incoming,
  784. BATADV_IF_DEFAULT);
  785. rcu_read_lock();
  786. list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
  787. if (hard_iface->if_status != BATADV_IF_ACTIVE)
  788. continue;
  789. if (hard_iface->soft_iface != bat_priv->soft_iface)
  790. continue;
  791. if (!kref_get_unless_zero(&hard_iface->refcount))
  792. continue;
  793. ret = batadv_hardif_no_broadcast(hard_iface,
  794. ogm_packet->orig,
  795. hardif_neigh->orig);
  796. if (ret) {
  797. char *type;
  798. switch (ret) {
  799. case BATADV_HARDIF_BCAST_NORECIPIENT:
  800. type = "no neighbor";
  801. break;
  802. case BATADV_HARDIF_BCAST_DUPFWD:
  803. type = "single neighbor is source";
  804. break;
  805. case BATADV_HARDIF_BCAST_DUPORIG:
  806. type = "single neighbor is originator";
  807. break;
  808. default:
  809. type = "unknown";
  810. }
  811. batadv_dbg(BATADV_DBG_BATMAN, bat_priv, "OGM2 packet from %pM on %s suppressed: %s\n",
  812. ogm_packet->orig, hard_iface->net_dev->name,
  813. type);
  814. batadv_hardif_put(hard_iface);
  815. continue;
  816. }
  817. batadv_v_ogm_process_per_outif(bat_priv, ethhdr, ogm_packet,
  818. orig_node, neigh_node,
  819. if_incoming, hard_iface);
  820. batadv_hardif_put(hard_iface);
  821. }
  822. rcu_read_unlock();
  823. out:
  824. batadv_orig_node_put(orig_node);
  825. batadv_neigh_node_put(neigh_node);
  826. batadv_hardif_neigh_put(hardif_neigh);
  827. }
  828. /**
  829. * batadv_v_ogm_packet_recv() - OGM2 receiving handler
  830. * @skb: the received OGM
  831. * @if_incoming: the interface where this OGM has been received
  832. *
  833. * Return: NET_RX_SUCCESS and consume the skb on success or returns NET_RX_DROP
  834. * (without freeing the skb) on failure
  835. */
  836. int batadv_v_ogm_packet_recv(struct sk_buff *skb,
  837. struct batadv_hard_iface *if_incoming)
  838. {
  839. struct batadv_priv *bat_priv = netdev_priv(if_incoming->soft_iface);
  840. struct batadv_ogm2_packet *ogm_packet;
  841. struct ethhdr *ethhdr;
  842. int ogm_offset;
  843. u8 *packet_pos;
  844. int ret = NET_RX_DROP;
  845. /* did we receive a OGM2 packet on an interface that does not have
  846. * B.A.T.M.A.N. V enabled ?
  847. */
  848. if (strcmp(bat_priv->algo_ops->name, "BATMAN_V") != 0)
  849. goto free_skb;
  850. if (!batadv_check_management_packet(skb, if_incoming, BATADV_OGM2_HLEN))
  851. goto free_skb;
  852. ethhdr = eth_hdr(skb);
  853. if (batadv_is_my_mac(bat_priv, ethhdr->h_source))
  854. goto free_skb;
  855. batadv_inc_counter(bat_priv, BATADV_CNT_MGMT_RX);
  856. batadv_add_counter(bat_priv, BATADV_CNT_MGMT_RX_BYTES,
  857. skb->len + ETH_HLEN);
  858. ogm_offset = 0;
  859. ogm_packet = (struct batadv_ogm2_packet *)skb->data;
  860. while (batadv_v_ogm_aggr_packet(ogm_offset, skb_headlen(skb),
  861. ogm_packet)) {
  862. batadv_v_ogm_process(skb, ogm_offset, if_incoming);
  863. ogm_offset += BATADV_OGM2_HLEN;
  864. ogm_offset += ntohs(ogm_packet->tvlv_len);
  865. packet_pos = skb->data + ogm_offset;
  866. ogm_packet = (struct batadv_ogm2_packet *)packet_pos;
  867. }
  868. ret = NET_RX_SUCCESS;
  869. free_skb:
  870. if (ret == NET_RX_SUCCESS)
  871. consume_skb(skb);
  872. else
  873. kfree_skb(skb);
  874. return ret;
  875. }
  876. /**
  877. * batadv_v_ogm_init() - initialise the OGM2 engine
  878. * @bat_priv: the bat priv with all the soft interface information
  879. *
  880. * Return: 0 on success or a negative error code in case of failure
  881. */
  882. int batadv_v_ogm_init(struct batadv_priv *bat_priv)
  883. {
  884. struct batadv_ogm2_packet *ogm_packet;
  885. unsigned char *ogm_buff;
  886. u32 random_seqno;
  887. bat_priv->bat_v.ogm_buff_len = BATADV_OGM2_HLEN;
  888. ogm_buff = kzalloc(bat_priv->bat_v.ogm_buff_len, GFP_ATOMIC);
  889. if (!ogm_buff)
  890. return -ENOMEM;
  891. bat_priv->bat_v.ogm_buff = ogm_buff;
  892. ogm_packet = (struct batadv_ogm2_packet *)ogm_buff;
  893. ogm_packet->packet_type = BATADV_OGM2;
  894. ogm_packet->version = BATADV_COMPAT_VERSION;
  895. ogm_packet->ttl = BATADV_TTL;
  896. ogm_packet->flags = BATADV_NO_FLAGS;
  897. ogm_packet->throughput = htonl(BATADV_THROUGHPUT_MAX_VALUE);
  898. /* randomize initial seqno to avoid collision */
  899. get_random_bytes(&random_seqno, sizeof(random_seqno));
  900. atomic_set(&bat_priv->bat_v.ogm_seqno, random_seqno);
  901. INIT_DELAYED_WORK(&bat_priv->bat_v.ogm_wq, batadv_v_ogm_send);
  902. mutex_init(&bat_priv->bat_v.ogm_buff_mutex);
  903. return 0;
  904. }
  905. /**
  906. * batadv_v_ogm_free() - free OGM private resources
  907. * @bat_priv: the bat priv with all the soft interface information
  908. */
  909. void batadv_v_ogm_free(struct batadv_priv *bat_priv)
  910. {
  911. cancel_delayed_work_sync(&bat_priv->bat_v.ogm_wq);
  912. mutex_lock(&bat_priv->bat_v.ogm_buff_mutex);
  913. kfree(bat_priv->bat_v.ogm_buff);
  914. bat_priv->bat_v.ogm_buff = NULL;
  915. bat_priv->bat_v.ogm_buff_len = 0;
  916. mutex_unlock(&bat_priv->bat_v.ogm_buff_mutex);
  917. }