Included changes:
- first set of patches that add the batadv_ prefix to all the exported symbols - restyling of comments -----BEGIN PGP SIGNATURE----- Version: GnuPG v2.0.19 (GNU/Linux) iEYEABECAAYFAk/jT/QACgkQpGgxIkP9cweBQgCcCOFZ0RSCB+m2K60o7kH9xfcz hq4AnA3j+kVzViwew0IRavA60CcixdxN =L16j -----END PGP SIGNATURE----- Merge tag 'batman-adv-for-davem' of git://git.open-mesh.org/linux-merge Included changes: - first set of patches that add the batadv_ prefix to all the exported symbols - restyling of comments
This commit is contained in:
commit
3e428fe038
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,12 +15,11 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_BAT_ALGO_H_
|
#ifndef _NET_BATMAN_ADV_BAT_ALGO_H_
|
||||||
#define _NET_BATMAN_ADV_BAT_ALGO_H_
|
#define _NET_BATMAN_ADV_BAT_ALGO_H_
|
||||||
|
|
||||||
int bat_iv_init(void);
|
int batadv_iv_init(void);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_BAT_ALGO_H_ */
|
#endif /* _NET_BATMAN_ADV_BAT_ALGO_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -76,7 +74,7 @@ static int fdebug_log(struct debug_log *debug_log, const char *fmt, ...)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int debug_log(struct bat_priv *bat_priv, const char *fmt, ...)
|
int batadv_debug_log(struct bat_priv *bat_priv, const char *fmt, ...)
|
||||||
{
|
{
|
||||||
va_list args;
|
va_list args;
|
||||||
char tmp_log_buf[256];
|
char tmp_log_buf[256];
|
||||||
|
@ -94,13 +92,13 @@ static int log_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
nonseekable_open(inode, file);
|
nonseekable_open(inode, file);
|
||||||
file->private_data = inode->i_private;
|
file->private_data = inode->i_private;
|
||||||
inc_module_count();
|
batadv_inc_module_count();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int log_release(struct inode *inode, struct file *file)
|
static int log_release(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
dec_module_count();
|
batadv_dec_module_count();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -224,45 +222,46 @@ static void debug_log_cleanup(struct bat_priv *bat_priv)
|
||||||
|
|
||||||
static int bat_algorithms_open(struct inode *inode, struct file *file)
|
static int bat_algorithms_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
return single_open(file, bat_algo_seq_print_text, NULL);
|
return single_open(file, batadv_algo_seq_print_text, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int originators_open(struct inode *inode, struct file *file)
|
static int originators_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
||||||
return single_open(file, orig_seq_print_text, net_dev);
|
return single_open(file, batadv_orig_seq_print_text, net_dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int gateways_open(struct inode *inode, struct file *file)
|
static int gateways_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
||||||
return single_open(file, gw_client_seq_print_text, net_dev);
|
return single_open(file, batadv_gw_client_seq_print_text, net_dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int transtable_global_open(struct inode *inode, struct file *file)
|
static int transtable_global_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
||||||
return single_open(file, tt_global_seq_print_text, net_dev);
|
return single_open(file, batadv_tt_global_seq_print_text, net_dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef CONFIG_BATMAN_ADV_BLA
|
#ifdef CONFIG_BATMAN_ADV_BLA
|
||||||
static int bla_claim_table_open(struct inode *inode, struct file *file)
|
static int bla_claim_table_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
||||||
return single_open(file, bla_claim_table_seq_print_text, net_dev);
|
return single_open(file, batadv_bla_claim_table_seq_print_text,
|
||||||
|
net_dev);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static int transtable_local_open(struct inode *inode, struct file *file)
|
static int transtable_local_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
||||||
return single_open(file, tt_local_seq_print_text, net_dev);
|
return single_open(file, batadv_tt_local_seq_print_text, net_dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int vis_data_open(struct inode *inode, struct file *file)
|
static int vis_data_open(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
struct net_device *net_dev = (struct net_device *)inode->i_private;
|
||||||
return single_open(file, vis_seq_print_text, net_dev);
|
return single_open(file, batadv_vis_seq_print_text, net_dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
struct bat_debuginfo {
|
struct bat_debuginfo {
|
||||||
|
@ -304,7 +303,7 @@ static struct bat_debuginfo *mesh_debuginfos[] = {
|
||||||
NULL,
|
NULL,
|
||||||
};
|
};
|
||||||
|
|
||||||
void debugfs_init(void)
|
void batadv_debugfs_init(void)
|
||||||
{
|
{
|
||||||
struct bat_debuginfo *bat_debug;
|
struct bat_debuginfo *bat_debug;
|
||||||
struct dentry *file;
|
struct dentry *file;
|
||||||
|
@ -327,7 +326,7 @@ out:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
void debugfs_destroy(void)
|
void batadv_debugfs_destroy(void)
|
||||||
{
|
{
|
||||||
if (bat_debugfs) {
|
if (bat_debugfs) {
|
||||||
debugfs_remove_recursive(bat_debugfs);
|
debugfs_remove_recursive(bat_debugfs);
|
||||||
|
@ -335,7 +334,7 @@ void debugfs_destroy(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int debugfs_add_meshif(struct net_device *dev)
|
int batadv_debugfs_add_meshif(struct net_device *dev)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(dev);
|
struct bat_priv *bat_priv = netdev_priv(dev);
|
||||||
struct bat_debuginfo **bat_debug;
|
struct bat_debuginfo **bat_debug;
|
||||||
|
@ -348,7 +347,7 @@ int debugfs_add_meshif(struct net_device *dev)
|
||||||
if (!bat_priv->debug_dir)
|
if (!bat_priv->debug_dir)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
if (bat_socket_setup(bat_priv) < 0)
|
if (batadv_socket_setup(bat_priv) < 0)
|
||||||
goto rem_attr;
|
goto rem_attr;
|
||||||
|
|
||||||
if (debug_log_setup(bat_priv) < 0)
|
if (debug_log_setup(bat_priv) < 0)
|
||||||
|
@ -378,7 +377,7 @@ out:
|
||||||
#endif /* CONFIG_DEBUG_FS */
|
#endif /* CONFIG_DEBUG_FS */
|
||||||
}
|
}
|
||||||
|
|
||||||
void debugfs_del_meshif(struct net_device *dev)
|
void batadv_debugfs_del_meshif(struct net_device *dev)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(dev);
|
struct bat_priv *bat_priv = netdev_priv(dev);
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,18 +15,16 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_DEBUGFS_H_
|
#ifndef _NET_BATMAN_ADV_DEBUGFS_H_
|
||||||
#define _NET_BATMAN_ADV_DEBUGFS_H_
|
#define _NET_BATMAN_ADV_DEBUGFS_H_
|
||||||
|
|
||||||
#define DEBUGFS_BAT_SUBDIR "batman_adv"
|
#define DEBUGFS_BAT_SUBDIR "batman_adv"
|
||||||
|
|
||||||
void debugfs_init(void);
|
void batadv_debugfs_init(void);
|
||||||
void debugfs_destroy(void);
|
void batadv_debugfs_destroy(void);
|
||||||
int debugfs_add_meshif(struct net_device *dev);
|
int batadv_debugfs_add_meshif(struct net_device *dev);
|
||||||
void debugfs_del_meshif(struct net_device *dev);
|
void batadv_debugfs_del_meshif(struct net_device *dev);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_DEBUGFS_H_ */
|
#endif /* _NET_BATMAN_ADV_DEBUGFS_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -138,7 +136,10 @@ static uint8_t hop_penalty(uint8_t tq, const struct bat_priv *bat_priv)
|
||||||
static int bat_iv_ogm_aggr_packet(int buff_pos, int packet_len,
|
static int bat_iv_ogm_aggr_packet(int buff_pos, int packet_len,
|
||||||
int tt_num_changes)
|
int tt_num_changes)
|
||||||
{
|
{
|
||||||
int next_buff_pos = buff_pos + BATMAN_OGM_HLEN + tt_len(tt_num_changes);
|
int next_buff_pos = 0;
|
||||||
|
|
||||||
|
next_buff_pos += buff_pos + BATMAN_OGM_HLEN;
|
||||||
|
next_buff_pos += batadv_tt_len(tt_num_changes);
|
||||||
|
|
||||||
return (next_buff_pos <= packet_len) &&
|
return (next_buff_pos <= packet_len) &&
|
||||||
(next_buff_pos <= MAX_AGGREGATION_BYTES);
|
(next_buff_pos <= MAX_AGGREGATION_BYTES);
|
||||||
|
@ -167,7 +168,8 @@ static void bat_iv_ogm_send_to_if(struct forw_packet *forw_packet,
|
||||||
batman_ogm_packet->tt_num_changes)) {
|
batman_ogm_packet->tt_num_changes)) {
|
||||||
|
|
||||||
/* we might have aggregated direct link packets with an
|
/* we might have aggregated direct link packets with an
|
||||||
* ordinary base packet */
|
* ordinary base packet
|
||||||
|
*/
|
||||||
if ((forw_packet->direct_link_flags & (1 << packet_num)) &&
|
if ((forw_packet->direct_link_flags & (1 << packet_num)) &&
|
||||||
(forw_packet->if_incoming == hard_iface))
|
(forw_packet->if_incoming == hard_iface))
|
||||||
batman_ogm_packet->flags |= DIRECTLINK;
|
batman_ogm_packet->flags |= DIRECTLINK;
|
||||||
|
@ -188,8 +190,8 @@ static void bat_iv_ogm_send_to_if(struct forw_packet *forw_packet,
|
||||||
batman_ogm_packet->ttvn, hard_iface->net_dev->name,
|
batman_ogm_packet->ttvn, hard_iface->net_dev->name,
|
||||||
hard_iface->net_dev->dev_addr);
|
hard_iface->net_dev->dev_addr);
|
||||||
|
|
||||||
buff_pos += BATMAN_OGM_HLEN +
|
buff_pos += BATMAN_OGM_HLEN;
|
||||||
tt_len(batman_ogm_packet->tt_num_changes);
|
buff_pos += batadv_tt_len(batman_ogm_packet->tt_num_changes);
|
||||||
packet_num++;
|
packet_num++;
|
||||||
batman_ogm_packet = (struct batman_ogm_packet *)
|
batman_ogm_packet = (struct batman_ogm_packet *)
|
||||||
(forw_packet->skb->data + buff_pos);
|
(forw_packet->skb->data + buff_pos);
|
||||||
|
@ -201,7 +203,7 @@ static void bat_iv_ogm_send_to_if(struct forw_packet *forw_packet,
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_MGMT_TX);
|
batadv_inc_counter(bat_priv, BAT_CNT_MGMT_TX);
|
||||||
batadv_add_counter(bat_priv, BAT_CNT_MGMT_TX_BYTES,
|
batadv_add_counter(bat_priv, BAT_CNT_MGMT_TX_BYTES,
|
||||||
skb->len + ETH_HLEN);
|
skb->len + ETH_HLEN);
|
||||||
send_skb_packet(skb, hard_iface, broadcast_addr);
|
batadv_send_skb_packet(skb, hard_iface, batadv_broadcast_addr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -234,8 +236,9 @@ static void bat_iv_ogm_emit(struct forw_packet *forw_packet)
|
||||||
if (!primary_if)
|
if (!primary_if)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* multihomed peer assumed */
|
/* multihomed peer assumed
|
||||||
/* non-primary OGMs are only broadcasted on their interface */
|
* non-primary OGMs are only broadcasted on their interface
|
||||||
|
*/
|
||||||
if ((directlink && (batman_ogm_packet->header.ttl == 1)) ||
|
if ((directlink && (batman_ogm_packet->header.ttl == 1)) ||
|
||||||
(forw_packet->own && (forw_packet->if_incoming != primary_if))) {
|
(forw_packet->own && (forw_packet->if_incoming != primary_if))) {
|
||||||
|
|
||||||
|
@ -250,8 +253,9 @@ static void bat_iv_ogm_emit(struct forw_packet *forw_packet)
|
||||||
forw_packet->if_incoming->net_dev->dev_addr);
|
forw_packet->if_incoming->net_dev->dev_addr);
|
||||||
|
|
||||||
/* skb is only used once and than forw_packet is free'd */
|
/* skb is only used once and than forw_packet is free'd */
|
||||||
send_skb_packet(forw_packet->skb, forw_packet->if_incoming,
|
batadv_send_skb_packet(forw_packet->skb,
|
||||||
broadcast_addr);
|
forw_packet->if_incoming,
|
||||||
|
batadv_broadcast_addr);
|
||||||
forw_packet->skb = NULL;
|
forw_packet->skb = NULL;
|
||||||
|
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -259,7 +263,7 @@ static void bat_iv_ogm_emit(struct forw_packet *forw_packet)
|
||||||
|
|
||||||
/* broadcast on every interface */
|
/* broadcast on every interface */
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if (hard_iface->soft_iface != soft_iface)
|
if (hard_iface->soft_iface != soft_iface)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -288,41 +292,39 @@ static bool bat_iv_ogm_can_aggregate(const struct batman_ogm_packet
|
||||||
|
|
||||||
batman_ogm_packet = (struct batman_ogm_packet *)forw_packet->skb->data;
|
batman_ogm_packet = (struct batman_ogm_packet *)forw_packet->skb->data;
|
||||||
|
|
||||||
/**
|
/* we can aggregate the current packet to this aggregated packet
|
||||||
* we can aggregate the current packet to this aggregated packet
|
|
||||||
* if:
|
* if:
|
||||||
*
|
*
|
||||||
* - the send time is within our MAX_AGGREGATION_MS time
|
* - the send time is within our MAX_AGGREGATION_MS time
|
||||||
* - the resulting packet wont be bigger than
|
* - the resulting packet wont be bigger than
|
||||||
* MAX_AGGREGATION_BYTES
|
* MAX_AGGREGATION_BYTES
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if (time_before(send_time, forw_packet->send_time) &&
|
if (time_before(send_time, forw_packet->send_time) &&
|
||||||
time_after_eq(send_time + msecs_to_jiffies(MAX_AGGREGATION_MS),
|
time_after_eq(send_time + msecs_to_jiffies(MAX_AGGREGATION_MS),
|
||||||
forw_packet->send_time) &&
|
forw_packet->send_time) &&
|
||||||
(aggregated_bytes <= MAX_AGGREGATION_BYTES)) {
|
(aggregated_bytes <= MAX_AGGREGATION_BYTES)) {
|
||||||
|
|
||||||
/**
|
/* check aggregation compatibility
|
||||||
* check aggregation compatibility
|
|
||||||
* -> direct link packets are broadcasted on
|
* -> direct link packets are broadcasted on
|
||||||
* their interface only
|
* their interface only
|
||||||
* -> aggregate packet if the current packet is
|
* -> aggregate packet if the current packet is
|
||||||
* a "global" packet as well as the base
|
* a "global" packet as well as the base
|
||||||
* packet
|
* packet
|
||||||
*/
|
*/
|
||||||
|
|
||||||
primary_if = primary_if_get_selected(bat_priv);
|
primary_if = primary_if_get_selected(bat_priv);
|
||||||
if (!primary_if)
|
if (!primary_if)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* packets without direct link flag and high TTL
|
/* packets without direct link flag and high TTL
|
||||||
* are flooded through the net */
|
* are flooded through the net
|
||||||
|
*/
|
||||||
if ((!directlink) &&
|
if ((!directlink) &&
|
||||||
(!(batman_ogm_packet->flags & DIRECTLINK)) &&
|
(!(batman_ogm_packet->flags & DIRECTLINK)) &&
|
||||||
(batman_ogm_packet->header.ttl != 1) &&
|
(batman_ogm_packet->header.ttl != 1) &&
|
||||||
|
|
||||||
/* own packets originating non-primary
|
/* own packets originating non-primary
|
||||||
* interfaces leave only that interface */
|
* interfaces leave only that interface
|
||||||
|
*/
|
||||||
((!forw_packet->own) ||
|
((!forw_packet->own) ||
|
||||||
(forw_packet->if_incoming == primary_if))) {
|
(forw_packet->if_incoming == primary_if))) {
|
||||||
res = true;
|
res = true;
|
||||||
|
@ -330,14 +332,16 @@ static bool bat_iv_ogm_can_aggregate(const struct batman_ogm_packet
|
||||||
}
|
}
|
||||||
|
|
||||||
/* if the incoming packet is sent via this one
|
/* if the incoming packet is sent via this one
|
||||||
* interface only - we still can aggregate */
|
* interface only - we still can aggregate
|
||||||
|
*/
|
||||||
if ((directlink) &&
|
if ((directlink) &&
|
||||||
(new_batman_ogm_packet->header.ttl == 1) &&
|
(new_batman_ogm_packet->header.ttl == 1) &&
|
||||||
(forw_packet->if_incoming == if_incoming) &&
|
(forw_packet->if_incoming == if_incoming) &&
|
||||||
|
|
||||||
/* packets from direct neighbors or
|
/* packets from direct neighbors or
|
||||||
* own secondary interface packets
|
* own secondary interface packets
|
||||||
* (= secondary interface packets in general) */
|
* (= secondary interface packets in general)
|
||||||
|
*/
|
||||||
(batman_ogm_packet->flags & DIRECTLINK ||
|
(batman_ogm_packet->flags & DIRECTLINK ||
|
||||||
(forw_packet->own &&
|
(forw_packet->own &&
|
||||||
forw_packet->if_incoming != primary_if))) {
|
forw_packet->if_incoming != primary_if))) {
|
||||||
|
@ -420,8 +424,8 @@ static void bat_iv_ogm_aggregate_new(const unsigned char *packet_buff,
|
||||||
|
|
||||||
/* start timer for this packet */
|
/* start timer for this packet */
|
||||||
INIT_DELAYED_WORK(&forw_packet_aggr->delayed_work,
|
INIT_DELAYED_WORK(&forw_packet_aggr->delayed_work,
|
||||||
send_outstanding_bat_ogm_packet);
|
batadv_send_outstanding_bat_ogm_packet);
|
||||||
queue_delayed_work(bat_event_workqueue,
|
queue_delayed_work(batadv_event_workqueue,
|
||||||
&forw_packet_aggr->delayed_work,
|
&forw_packet_aggr->delayed_work,
|
||||||
send_time - jiffies);
|
send_time - jiffies);
|
||||||
|
|
||||||
|
@ -453,8 +457,7 @@ static void bat_iv_ogm_queue_add(struct bat_priv *bat_priv,
|
||||||
int packet_len, struct hard_iface *if_incoming,
|
int packet_len, struct hard_iface *if_incoming,
|
||||||
int own_packet, unsigned long send_time)
|
int own_packet, unsigned long send_time)
|
||||||
{
|
{
|
||||||
/**
|
/* _aggr -> pointer to the packet we want to aggregate with
|
||||||
* _aggr -> pointer to the packet we want to aggregate with
|
|
||||||
* _pos -> pointer to the position in the queue
|
* _pos -> pointer to the position in the queue
|
||||||
*/
|
*/
|
||||||
struct forw_packet *forw_packet_aggr = NULL, *forw_packet_pos = NULL;
|
struct forw_packet *forw_packet_aggr = NULL, *forw_packet_pos = NULL;
|
||||||
|
@ -483,13 +486,13 @@ static void bat_iv_ogm_queue_add(struct bat_priv *bat_priv,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* nothing to aggregate with - either aggregation disabled or no
|
/* nothing to aggregate with - either aggregation disabled or no
|
||||||
* suitable aggregation packet found */
|
* suitable aggregation packet found
|
||||||
|
*/
|
||||||
if (!forw_packet_aggr) {
|
if (!forw_packet_aggr) {
|
||||||
/* the following section can run without the lock */
|
/* the following section can run without the lock */
|
||||||
spin_unlock_bh(&bat_priv->forw_bat_list_lock);
|
spin_unlock_bh(&bat_priv->forw_bat_list_lock);
|
||||||
|
|
||||||
/**
|
/* if we could not aggregate this packet with one of the others
|
||||||
* if we could not aggregate this packet with one of the others
|
|
||||||
* we hold it back for a while, so that it might be aggregated
|
* we hold it back for a while, so that it might be aggregated
|
||||||
* later on
|
* later on
|
||||||
*/
|
*/
|
||||||
|
@ -555,7 +558,7 @@ static void bat_iv_ogm_forward(struct orig_node *orig_node,
|
||||||
batman_ogm_packet->flags &= ~DIRECTLINK;
|
batman_ogm_packet->flags &= ~DIRECTLINK;
|
||||||
|
|
||||||
bat_iv_ogm_queue_add(bat_priv, (unsigned char *)batman_ogm_packet,
|
bat_iv_ogm_queue_add(bat_priv, (unsigned char *)batman_ogm_packet,
|
||||||
BATMAN_OGM_HLEN + tt_len(tt_num_changes),
|
BATMAN_OGM_HLEN + batadv_tt_len(tt_num_changes),
|
||||||
if_incoming, 0, bat_iv_ogm_fwd_send_time());
|
if_incoming, 0, bat_iv_ogm_fwd_send_time());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -599,7 +602,7 @@ static void bat_iv_ogm_schedule(struct hard_iface *hard_iface)
|
||||||
else
|
else
|
||||||
batman_ogm_packet->gw_flags = NO_FLAGS;
|
batman_ogm_packet->gw_flags = NO_FLAGS;
|
||||||
|
|
||||||
slide_own_bcast_window(hard_iface);
|
batadv_slide_own_bcast_window(hard_iface);
|
||||||
bat_iv_ogm_queue_add(bat_priv, hard_iface->packet_buff,
|
bat_iv_ogm_queue_add(bat_priv, hard_iface->packet_buff,
|
||||||
hard_iface->packet_len, hard_iface, 1,
|
hard_iface->packet_len, hard_iface, 1,
|
||||||
bat_iv_ogm_emit_send_time(bat_priv));
|
bat_iv_ogm_emit_send_time(bat_priv));
|
||||||
|
@ -633,7 +636,7 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
(tmp_neigh_node->if_incoming == if_incoming) &&
|
(tmp_neigh_node->if_incoming == if_incoming) &&
|
||||||
atomic_inc_not_zero(&tmp_neigh_node->refcount)) {
|
atomic_inc_not_zero(&tmp_neigh_node->refcount)) {
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
neigh_node = tmp_neigh_node;
|
neigh_node = tmp_neigh_node;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -642,17 +645,17 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
spin_lock_bh(&tmp_neigh_node->lq_update_lock);
|
spin_lock_bh(&tmp_neigh_node->lq_update_lock);
|
||||||
ring_buffer_set(tmp_neigh_node->tq_recv,
|
batadv_ring_buffer_set(tmp_neigh_node->tq_recv,
|
||||||
&tmp_neigh_node->tq_index, 0);
|
&tmp_neigh_node->tq_index, 0);
|
||||||
tmp_neigh_node->tq_avg =
|
tmp_neigh_node->tq_avg =
|
||||||
ring_buffer_avg(tmp_neigh_node->tq_recv);
|
batadv_ring_buffer_avg(tmp_neigh_node->tq_recv);
|
||||||
spin_unlock_bh(&tmp_neigh_node->lq_update_lock);
|
spin_unlock_bh(&tmp_neigh_node->lq_update_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!neigh_node) {
|
if (!neigh_node) {
|
||||||
struct orig_node *orig_tmp;
|
struct orig_node *orig_tmp;
|
||||||
|
|
||||||
orig_tmp = get_orig_node(bat_priv, ethhdr->h_source);
|
orig_tmp = batadv_get_orig_node(bat_priv, ethhdr->h_source);
|
||||||
if (!orig_tmp)
|
if (!orig_tmp)
|
||||||
goto unlock;
|
goto unlock;
|
||||||
|
|
||||||
|
@ -660,7 +663,7 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
orig_node, orig_tmp,
|
orig_node, orig_tmp,
|
||||||
batman_ogm_packet->seqno);
|
batman_ogm_packet->seqno);
|
||||||
|
|
||||||
orig_node_free_ref(orig_tmp);
|
batadv_orig_node_free_ref(orig_tmp);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto unlock;
|
goto unlock;
|
||||||
} else
|
} else
|
||||||
|
@ -673,10 +676,10 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
neigh_node->last_seen = jiffies;
|
neigh_node->last_seen = jiffies;
|
||||||
|
|
||||||
spin_lock_bh(&neigh_node->lq_update_lock);
|
spin_lock_bh(&neigh_node->lq_update_lock);
|
||||||
ring_buffer_set(neigh_node->tq_recv,
|
batadv_ring_buffer_set(neigh_node->tq_recv,
|
||||||
&neigh_node->tq_index,
|
&neigh_node->tq_index,
|
||||||
batman_ogm_packet->tq);
|
batman_ogm_packet->tq);
|
||||||
neigh_node->tq_avg = ring_buffer_avg(neigh_node->tq_recv);
|
neigh_node->tq_avg = batadv_ring_buffer_avg(neigh_node->tq_recv);
|
||||||
spin_unlock_bh(&neigh_node->lq_update_lock);
|
spin_unlock_bh(&neigh_node->lq_update_lock);
|
||||||
|
|
||||||
if (!is_duplicate) {
|
if (!is_duplicate) {
|
||||||
|
@ -684,11 +687,12 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
neigh_node->last_ttl = batman_ogm_packet->header.ttl;
|
neigh_node->last_ttl = batman_ogm_packet->header.ttl;
|
||||||
}
|
}
|
||||||
|
|
||||||
bonding_candidate_add(orig_node, neigh_node);
|
batadv_bonding_candidate_add(orig_node, neigh_node);
|
||||||
|
|
||||||
/* if this neighbor already is our next hop there is nothing
|
/* if this neighbor already is our next hop there is nothing
|
||||||
* to change */
|
* to change
|
||||||
router = orig_node_get_router(orig_node);
|
*/
|
||||||
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (router == neigh_node)
|
if (router == neigh_node)
|
||||||
goto update_tt;
|
goto update_tt;
|
||||||
|
|
||||||
|
@ -697,7 +701,8 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
goto update_tt;
|
goto update_tt;
|
||||||
|
|
||||||
/* if the TQ is the same and the link not more symmetric we
|
/* if the TQ is the same and the link not more symmetric we
|
||||||
* won't consider it either */
|
* won't consider it either
|
||||||
|
*/
|
||||||
if (router && (neigh_node->tq_avg == router->tq_avg)) {
|
if (router && (neigh_node->tq_avg == router->tq_avg)) {
|
||||||
orig_node_tmp = router->orig_node;
|
orig_node_tmp = router->orig_node;
|
||||||
spin_lock_bh(&orig_node_tmp->ogm_cnt_lock);
|
spin_lock_bh(&orig_node_tmp->ogm_cnt_lock);
|
||||||
|
@ -715,22 +720,23 @@ static void bat_iv_ogm_orig_update(struct bat_priv *bat_priv,
|
||||||
goto update_tt;
|
goto update_tt;
|
||||||
}
|
}
|
||||||
|
|
||||||
update_route(bat_priv, orig_node, neigh_node);
|
batadv_update_route(bat_priv, orig_node, neigh_node);
|
||||||
|
|
||||||
update_tt:
|
update_tt:
|
||||||
/* I have to check for transtable changes only if the OGM has been
|
/* I have to check for transtable changes only if the OGM has been
|
||||||
* sent through a primary interface */
|
* sent through a primary interface
|
||||||
|
*/
|
||||||
if (((batman_ogm_packet->orig != ethhdr->h_source) &&
|
if (((batman_ogm_packet->orig != ethhdr->h_source) &&
|
||||||
(batman_ogm_packet->header.ttl > 2)) ||
|
(batman_ogm_packet->header.ttl > 2)) ||
|
||||||
(batman_ogm_packet->flags & PRIMARIES_FIRST_HOP))
|
(batman_ogm_packet->flags & PRIMARIES_FIRST_HOP))
|
||||||
tt_update_orig(bat_priv, orig_node, tt_buff,
|
batadv_tt_update_orig(bat_priv, orig_node, tt_buff,
|
||||||
batman_ogm_packet->tt_num_changes,
|
batman_ogm_packet->tt_num_changes,
|
||||||
batman_ogm_packet->ttvn,
|
batman_ogm_packet->ttvn,
|
||||||
ntohs(batman_ogm_packet->tt_crc));
|
ntohs(batman_ogm_packet->tt_crc));
|
||||||
|
|
||||||
if (orig_node->gw_flags != batman_ogm_packet->gw_flags)
|
if (orig_node->gw_flags != batman_ogm_packet->gw_flags)
|
||||||
gw_node_update(bat_priv, orig_node,
|
batadv_gw_node_update(bat_priv, orig_node,
|
||||||
batman_ogm_packet->gw_flags);
|
batman_ogm_packet->gw_flags);
|
||||||
|
|
||||||
orig_node->gw_flags = batman_ogm_packet->gw_flags;
|
orig_node->gw_flags = batman_ogm_packet->gw_flags;
|
||||||
|
|
||||||
|
@ -738,7 +744,7 @@ update_tt:
|
||||||
if ((orig_node->gw_flags) &&
|
if ((orig_node->gw_flags) &&
|
||||||
(atomic_read(&bat_priv->gw_mode) == GW_MODE_CLIENT) &&
|
(atomic_read(&bat_priv->gw_mode) == GW_MODE_CLIENT) &&
|
||||||
(atomic_read(&bat_priv->gw_sel_class) > 2))
|
(atomic_read(&bat_priv->gw_sel_class) > 2))
|
||||||
gw_check_election(bat_priv, orig_node);
|
batadv_gw_check_election(bat_priv, orig_node);
|
||||||
|
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -746,9 +752,9 @@ unlock:
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
out:
|
out:
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int bat_iv_ogm_calc_tq(struct orig_node *orig_node,
|
static int bat_iv_ogm_calc_tq(struct orig_node *orig_node,
|
||||||
|
@ -808,15 +814,17 @@ static int bat_iv_ogm_calc_tq(struct orig_node *orig_node,
|
||||||
total_count = (orig_eq_count > neigh_rq_count ?
|
total_count = (orig_eq_count > neigh_rq_count ?
|
||||||
neigh_rq_count : orig_eq_count);
|
neigh_rq_count : orig_eq_count);
|
||||||
|
|
||||||
/* if we have too few packets (too less data) we set tq_own to zero */
|
/* if we have too few packets (too less data) we set tq_own to zero
|
||||||
/* if we receive too few packets it is not considered bidirectional */
|
* if we receive too few packets it is not considered bidirectional
|
||||||
|
*/
|
||||||
if ((total_count < TQ_LOCAL_BIDRECT_SEND_MINIMUM) ||
|
if ((total_count < TQ_LOCAL_BIDRECT_SEND_MINIMUM) ||
|
||||||
(neigh_rq_count < TQ_LOCAL_BIDRECT_RECV_MINIMUM))
|
(neigh_rq_count < TQ_LOCAL_BIDRECT_RECV_MINIMUM))
|
||||||
tq_own = 0;
|
tq_own = 0;
|
||||||
else
|
else
|
||||||
/* neigh_node->real_packet_count is never zero as we
|
/* neigh_node->real_packet_count is never zero as we
|
||||||
* only purge old information when getting new
|
* only purge old information when getting new
|
||||||
* information */
|
* information
|
||||||
|
*/
|
||||||
tq_own = (TQ_MAX_VALUE * total_count) / neigh_rq_count;
|
tq_own = (TQ_MAX_VALUE * total_count) / neigh_rq_count;
|
||||||
|
|
||||||
/* 1 - ((1-x) ** 3), normalized to TQ_MAX_VALUE this does
|
/* 1 - ((1-x) ** 3), normalized to TQ_MAX_VALUE this does
|
||||||
|
@ -842,13 +850,14 @@ static int bat_iv_ogm_calc_tq(struct orig_node *orig_node,
|
||||||
neigh_rq_count, tq_own, tq_asym_penalty, batman_ogm_packet->tq);
|
neigh_rq_count, tq_own, tq_asym_penalty, batman_ogm_packet->tq);
|
||||||
|
|
||||||
/* if link has the minimum required transmission quality
|
/* if link has the minimum required transmission quality
|
||||||
* consider it bidirectional */
|
* consider it bidirectional
|
||||||
|
*/
|
||||||
if (batman_ogm_packet->tq >= TQ_TOTAL_BIDRECT_LIMIT)
|
if (batman_ogm_packet->tq >= TQ_TOTAL_BIDRECT_LIMIT)
|
||||||
ret = 1;
|
ret = 1;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -875,7 +884,7 @@ static int bat_iv_ogm_update_seqnos(const struct ethhdr *ethhdr,
|
||||||
int set_mark, ret = -1;
|
int set_mark, ret = -1;
|
||||||
uint32_t seqno = ntohl(batman_ogm_packet->seqno);
|
uint32_t seqno = ntohl(batman_ogm_packet->seqno);
|
||||||
|
|
||||||
orig_node = get_orig_node(bat_priv, batman_ogm_packet->orig);
|
orig_node = batadv_get_orig_node(bat_priv, batman_ogm_packet->orig);
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
@ -884,8 +893,8 @@ static int bat_iv_ogm_update_seqnos(const struct ethhdr *ethhdr,
|
||||||
|
|
||||||
/* signalize caller that the packet is to be dropped. */
|
/* signalize caller that the packet is to be dropped. */
|
||||||
if (!hlist_empty(&orig_node->neigh_list) &&
|
if (!hlist_empty(&orig_node->neigh_list) &&
|
||||||
window_protected(bat_priv, seq_diff,
|
batadv_window_protected(bat_priv, seq_diff,
|
||||||
&orig_node->batman_seqno_reset))
|
&orig_node->batman_seqno_reset))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
|
@ -903,9 +912,9 @@ static int bat_iv_ogm_update_seqnos(const struct ethhdr *ethhdr,
|
||||||
set_mark = 0;
|
set_mark = 0;
|
||||||
|
|
||||||
/* if the window moved, set the update flag. */
|
/* if the window moved, set the update flag. */
|
||||||
need_update |= bit_get_packet(bat_priv,
|
need_update |= batadv_bit_get_packet(bat_priv,
|
||||||
tmp_neigh_node->real_bits,
|
tmp_neigh_node->real_bits,
|
||||||
seq_diff, set_mark);
|
seq_diff, set_mark);
|
||||||
|
|
||||||
tmp_neigh_node->real_packet_count =
|
tmp_neigh_node->real_packet_count =
|
||||||
bitmap_weight(tmp_neigh_node->real_bits,
|
bitmap_weight(tmp_neigh_node->real_bits,
|
||||||
|
@ -924,7 +933,7 @@ static int bat_iv_ogm_update_seqnos(const struct ethhdr *ethhdr,
|
||||||
|
|
||||||
out:
|
out:
|
||||||
spin_unlock_bh(&orig_node->ogm_cnt_lock);
|
spin_unlock_bh(&orig_node->ogm_cnt_lock);
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -980,7 +989,7 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
batman_ogm_packet->header.version, has_directlink_flag);
|
batman_ogm_packet->header.version, has_directlink_flag);
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if (hard_iface->if_status != IF_ACTIVE)
|
if (hard_iface->if_status != IF_ACTIVE)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -1029,13 +1038,15 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
unsigned long *word;
|
unsigned long *word;
|
||||||
int offset;
|
int offset;
|
||||||
|
|
||||||
orig_neigh_node = get_orig_node(bat_priv, ethhdr->h_source);
|
orig_neigh_node = batadv_get_orig_node(bat_priv,
|
||||||
|
ethhdr->h_source);
|
||||||
if (!orig_neigh_node)
|
if (!orig_neigh_node)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
/* neighbor has to indicate direct link and it has to
|
/* neighbor has to indicate direct link and it has to
|
||||||
* come via the corresponding interface */
|
* come via the corresponding interface
|
||||||
/* save packet seqno for bidirectional check */
|
* save packet seqno for bidirectional check
|
||||||
|
*/
|
||||||
if (has_directlink_flag &&
|
if (has_directlink_flag &&
|
||||||
compare_eth(if_incoming->net_dev->dev_addr,
|
compare_eth(if_incoming->net_dev->dev_addr,
|
||||||
batman_ogm_packet->orig)) {
|
batman_ogm_packet->orig)) {
|
||||||
|
@ -1053,7 +1064,7 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
|
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
"Drop packet: originator packet from myself (via neighbor)\n");
|
"Drop packet: originator packet from myself (via neighbor)\n");
|
||||||
orig_node_free_ref(orig_neigh_node);
|
batadv_orig_node_free_ref(orig_neigh_node);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1071,7 +1082,7 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
orig_node = get_orig_node(bat_priv, batman_ogm_packet->orig);
|
orig_node = batadv_get_orig_node(bat_priv, batman_ogm_packet->orig);
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
@ -1091,9 +1102,9 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (router)
|
if (router)
|
||||||
router_router = orig_node_get_router(router->orig_node);
|
router_router = batadv_orig_node_get_router(router->orig_node);
|
||||||
|
|
||||||
if ((router && router->tq_avg != 0) &&
|
if ((router && router->tq_avg != 0) &&
|
||||||
(compare_eth(router->addr, ethhdr->h_source)))
|
(compare_eth(router->addr, ethhdr->h_source)))
|
||||||
|
@ -1112,17 +1123,19 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* if sender is a direct neighbor the sender mac equals
|
/* if sender is a direct neighbor the sender mac equals
|
||||||
* originator mac */
|
* originator mac
|
||||||
|
*/
|
||||||
orig_neigh_node = (is_single_hop_neigh ?
|
orig_neigh_node = (is_single_hop_neigh ?
|
||||||
orig_node :
|
orig_node :
|
||||||
get_orig_node(bat_priv, ethhdr->h_source));
|
batadv_get_orig_node(bat_priv, ethhdr->h_source));
|
||||||
if (!orig_neigh_node)
|
if (!orig_neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
orig_neigh_router = orig_node_get_router(orig_neigh_node);
|
orig_neigh_router = batadv_orig_node_get_router(orig_neigh_node);
|
||||||
|
|
||||||
/* drop packet if sender is not a direct neighbor and if we
|
/* drop packet if sender is not a direct neighbor and if we
|
||||||
* don't route towards it */
|
* don't route towards it
|
||||||
|
*/
|
||||||
if (!is_single_hop_neigh && (!orig_neigh_router)) {
|
if (!is_single_hop_neigh && (!orig_neigh_router)) {
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
"Drop packet: OGM via unknown neighbor!\n");
|
"Drop packet: OGM via unknown neighbor!\n");
|
||||||
|
@ -1132,10 +1145,12 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
is_bidirectional = bat_iv_ogm_calc_tq(orig_node, orig_neigh_node,
|
is_bidirectional = bat_iv_ogm_calc_tq(orig_node, orig_neigh_node,
|
||||||
batman_ogm_packet, if_incoming);
|
batman_ogm_packet, if_incoming);
|
||||||
|
|
||||||
bonding_save_primary(orig_node, orig_neigh_node, batman_ogm_packet);
|
batadv_bonding_save_primary(orig_node, orig_neigh_node,
|
||||||
|
batman_ogm_packet);
|
||||||
|
|
||||||
/* update ranking if it is not a duplicate or has the same
|
/* update ranking if it is not a duplicate or has the same
|
||||||
* seqno and similar ttl as the non-duplicate */
|
* seqno and similar ttl as the non-duplicate
|
||||||
|
*/
|
||||||
if (is_bidirectional &&
|
if (is_bidirectional &&
|
||||||
(!is_duplicate ||
|
(!is_duplicate ||
|
||||||
((orig_node->last_real_seqno == ntohl(batman_ogm_packet->seqno)) &&
|
((orig_node->last_real_seqno == ntohl(batman_ogm_packet->seqno)) &&
|
||||||
|
@ -1178,16 +1193,16 @@ static void bat_iv_ogm_process(const struct ethhdr *ethhdr,
|
||||||
|
|
||||||
out_neigh:
|
out_neigh:
|
||||||
if ((orig_neigh_node) && (!is_single_hop_neigh))
|
if ((orig_neigh_node) && (!is_single_hop_neigh))
|
||||||
orig_node_free_ref(orig_neigh_node);
|
batadv_orig_node_free_ref(orig_neigh_node);
|
||||||
out:
|
out:
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
if (router_router)
|
if (router_router)
|
||||||
neigh_node_free_ref(router_router);
|
batadv_neigh_node_free_ref(router_router);
|
||||||
if (orig_neigh_router)
|
if (orig_neigh_router)
|
||||||
neigh_node_free_ref(orig_neigh_router);
|
batadv_neigh_node_free_ref(orig_neigh_router);
|
||||||
|
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int bat_iv_ogm_receive(struct sk_buff *skb,
|
static int bat_iv_ogm_receive(struct sk_buff *skb,
|
||||||
|
@ -1200,7 +1215,7 @@ static int bat_iv_ogm_receive(struct sk_buff *skb,
|
||||||
unsigned char *tt_buff, *packet_buff;
|
unsigned char *tt_buff, *packet_buff;
|
||||||
bool ret;
|
bool ret;
|
||||||
|
|
||||||
ret = check_management_packet(skb, if_incoming, BATMAN_OGM_HLEN);
|
ret = batadv_check_management_packet(skb, if_incoming, BATMAN_OGM_HLEN);
|
||||||
if (!ret)
|
if (!ret)
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
|
|
||||||
|
@ -1226,8 +1241,8 @@ static int bat_iv_ogm_receive(struct sk_buff *skb,
|
||||||
bat_iv_ogm_process(ethhdr, batman_ogm_packet,
|
bat_iv_ogm_process(ethhdr, batman_ogm_packet,
|
||||||
tt_buff, if_incoming);
|
tt_buff, if_incoming);
|
||||||
|
|
||||||
buff_pos += BATMAN_OGM_HLEN +
|
buff_pos += BATMAN_OGM_HLEN;
|
||||||
tt_len(batman_ogm_packet->tt_num_changes);
|
buff_pos += batadv_tt_len(batman_ogm_packet->tt_num_changes);
|
||||||
|
|
||||||
batman_ogm_packet = (struct batman_ogm_packet *)
|
batman_ogm_packet = (struct batman_ogm_packet *)
|
||||||
(packet_buff + buff_pos);
|
(packet_buff + buff_pos);
|
||||||
|
@ -1248,23 +1263,23 @@ static struct bat_algo_ops batman_iv __read_mostly = {
|
||||||
.bat_ogm_emit = bat_iv_ogm_emit,
|
.bat_ogm_emit = bat_iv_ogm_emit,
|
||||||
};
|
};
|
||||||
|
|
||||||
int __init bat_iv_init(void)
|
int __init batadv_iv_init(void)
|
||||||
{
|
{
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
/* batman originator packet */
|
/* batman originator packet */
|
||||||
ret = recv_handler_register(BAT_IV_OGM, bat_iv_ogm_receive);
|
ret = batadv_recv_handler_register(BAT_IV_OGM, bat_iv_ogm_receive);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
ret = bat_algo_register(&batman_iv);
|
ret = batadv_algo_register(&batman_iv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto handler_unregister;
|
goto handler_unregister;
|
||||||
|
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
handler_unregister:
|
handler_unregister:
|
||||||
recv_handler_unregister(BAT_IV_OGM);
|
batadv_recv_handler_unregister(BAT_IV_OGM);
|
||||||
out:
|
out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -84,7 +82,8 @@ ssize_t show_##_name(struct kobject *kobj, \
|
||||||
} \
|
} \
|
||||||
|
|
||||||
/* Use this, if you are going to turn a [name] in the soft-interface
|
/* Use this, if you are going to turn a [name] in the soft-interface
|
||||||
* (bat_priv) on or off */
|
* (bat_priv) on or off
|
||||||
|
*/
|
||||||
#define BAT_ATTR_SIF_BOOL(_name, _mode, _post_func) \
|
#define BAT_ATTR_SIF_BOOL(_name, _mode, _post_func) \
|
||||||
static BAT_ATTR_SIF_STORE_BOOL(_name, _post_func) \
|
static BAT_ATTR_SIF_STORE_BOOL(_name, _post_func) \
|
||||||
static BAT_ATTR_SIF_SHOW_BOOL(_name) \
|
static BAT_ATTR_SIF_SHOW_BOOL(_name) \
|
||||||
|
@ -110,7 +109,8 @@ ssize_t show_##_name(struct kobject *kobj, \
|
||||||
} \
|
} \
|
||||||
|
|
||||||
/* Use this, if you are going to set [name] in the soft-interface
|
/* Use this, if you are going to set [name] in the soft-interface
|
||||||
* (bat_priv) to an unsigned integer value */
|
* (bat_priv) to an unsigned integer value
|
||||||
|
*/
|
||||||
#define BAT_ATTR_SIF_UINT(_name, _mode, _min, _max, _post_func) \
|
#define BAT_ATTR_SIF_UINT(_name, _mode, _min, _max, _post_func) \
|
||||||
static BAT_ATTR_SIF_STORE_UINT(_name, _min, _max, _post_func) \
|
static BAT_ATTR_SIF_STORE_UINT(_name, _min, _max, _post_func) \
|
||||||
static BAT_ATTR_SIF_SHOW_UINT(_name) \
|
static BAT_ATTR_SIF_SHOW_UINT(_name) \
|
||||||
|
@ -122,9 +122,10 @@ ssize_t store_##_name(struct kobject *kobj, struct attribute *attr, \
|
||||||
char *buff, size_t count) \
|
char *buff, size_t count) \
|
||||||
{ \
|
{ \
|
||||||
struct net_device *net_dev = kobj_to_netdev(kobj); \
|
struct net_device *net_dev = kobj_to_netdev(kobj); \
|
||||||
struct hard_iface *hard_iface = hardif_get_by_netdev(net_dev); \
|
struct hard_iface *hard_iface; \
|
||||||
ssize_t length; \
|
ssize_t length; \
|
||||||
\
|
\
|
||||||
|
hard_iface = batadv_hardif_get_by_netdev(net_dev); \
|
||||||
if (!hard_iface) \
|
if (!hard_iface) \
|
||||||
return 0; \
|
return 0; \
|
||||||
\
|
\
|
||||||
|
@ -140,9 +141,10 @@ ssize_t show_##_name(struct kobject *kobj, \
|
||||||
struct attribute *attr, char *buff) \
|
struct attribute *attr, char *buff) \
|
||||||
{ \
|
{ \
|
||||||
struct net_device *net_dev = kobj_to_netdev(kobj); \
|
struct net_device *net_dev = kobj_to_netdev(kobj); \
|
||||||
struct hard_iface *hard_iface = hardif_get_by_netdev(net_dev); \
|
struct hard_iface *hard_iface; \
|
||||||
ssize_t length; \
|
ssize_t length; \
|
||||||
\
|
\
|
||||||
|
hard_iface = batadv_hardif_get_by_netdev(net_dev); \
|
||||||
if (!hard_iface) \
|
if (!hard_iface) \
|
||||||
return 0; \
|
return 0; \
|
||||||
\
|
\
|
||||||
|
@ -153,7 +155,8 @@ ssize_t show_##_name(struct kobject *kobj, \
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Use this, if you are going to set [name] in hard_iface to an
|
/* Use this, if you are going to set [name] in hard_iface to an
|
||||||
* unsigned integer value*/
|
* unsigned integer value
|
||||||
|
*/
|
||||||
#define BAT_ATTR_HIF_UINT(_name, _mode, _min, _max, _post_func) \
|
#define BAT_ATTR_HIF_UINT(_name, _mode, _min, _max, _post_func) \
|
||||||
static BAT_ATTR_HIF_STORE_UINT(_name, _min, _max, _post_func) \
|
static BAT_ATTR_HIF_STORE_UINT(_name, _min, _max, _post_func) \
|
||||||
static BAT_ATTR_HIF_SHOW_UINT(_name) \
|
static BAT_ATTR_HIF_SHOW_UINT(_name) \
|
||||||
|
@ -326,7 +329,7 @@ static ssize_t show_bat_algo(struct kobject *kobj, struct attribute *attr,
|
||||||
static void post_gw_deselect(struct net_device *net_dev)
|
static void post_gw_deselect(struct net_device *net_dev)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
}
|
}
|
||||||
|
|
||||||
static ssize_t show_gw_mode(struct kobject *kobj, struct attribute *attr,
|
static ssize_t show_gw_mode(struct kobject *kobj, struct attribute *attr,
|
||||||
|
@ -397,7 +400,7 @@ static ssize_t store_gw_mode(struct kobject *kobj, struct attribute *attr,
|
||||||
bat_info(net_dev, "Changing gw mode from: %s to: %s\n",
|
bat_info(net_dev, "Changing gw mode from: %s to: %s\n",
|
||||||
curr_gw_mode_str, buff);
|
curr_gw_mode_str, buff);
|
||||||
|
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
atomic_set(&bat_priv->gw_mode, (unsigned int)gw_mode_tmp);
|
atomic_set(&bat_priv->gw_mode, (unsigned int)gw_mode_tmp);
|
||||||
return count;
|
return count;
|
||||||
}
|
}
|
||||||
|
@ -409,7 +412,7 @@ static ssize_t show_gw_bwidth(struct kobject *kobj, struct attribute *attr,
|
||||||
int down, up;
|
int down, up;
|
||||||
int gw_bandwidth = atomic_read(&bat_priv->gw_bandwidth);
|
int gw_bandwidth = atomic_read(&bat_priv->gw_bandwidth);
|
||||||
|
|
||||||
gw_bandwidth_to_kbit(gw_bandwidth, &down, &up);
|
batadv_gw_bandwidth_to_kbit(gw_bandwidth, &down, &up);
|
||||||
return sprintf(buff, "%i%s/%i%s\n",
|
return sprintf(buff, "%i%s/%i%s\n",
|
||||||
(down > 2048 ? down / 1024 : down),
|
(down > 2048 ? down / 1024 : down),
|
||||||
(down > 2048 ? "MBit" : "KBit"),
|
(down > 2048 ? "MBit" : "KBit"),
|
||||||
|
@ -425,7 +428,7 @@ static ssize_t store_gw_bwidth(struct kobject *kobj, struct attribute *attr,
|
||||||
if (buff[count - 1] == '\n')
|
if (buff[count - 1] == '\n')
|
||||||
buff[count - 1] = '\0';
|
buff[count - 1] = '\0';
|
||||||
|
|
||||||
return gw_bandwidth_set(net_dev, buff, count);
|
return batadv_gw_bandwidth_set(net_dev, buff, count);
|
||||||
}
|
}
|
||||||
|
|
||||||
BAT_ATTR_SIF_BOOL(aggregated_ogms, S_IRUGO | S_IWUSR, NULL);
|
BAT_ATTR_SIF_BOOL(aggregated_ogms, S_IRUGO | S_IWUSR, NULL);
|
||||||
|
@ -433,7 +436,7 @@ BAT_ATTR_SIF_BOOL(bonding, S_IRUGO | S_IWUSR, NULL);
|
||||||
#ifdef CONFIG_BATMAN_ADV_BLA
|
#ifdef CONFIG_BATMAN_ADV_BLA
|
||||||
BAT_ATTR_SIF_BOOL(bridge_loop_avoidance, S_IRUGO | S_IWUSR, NULL);
|
BAT_ATTR_SIF_BOOL(bridge_loop_avoidance, S_IRUGO | S_IWUSR, NULL);
|
||||||
#endif
|
#endif
|
||||||
BAT_ATTR_SIF_BOOL(fragmentation, S_IRUGO | S_IWUSR, update_min_mtu);
|
BAT_ATTR_SIF_BOOL(fragmentation, S_IRUGO | S_IWUSR, batadv_update_min_mtu);
|
||||||
BAT_ATTR_SIF_BOOL(ap_isolation, S_IRUGO | S_IWUSR, NULL);
|
BAT_ATTR_SIF_BOOL(ap_isolation, S_IRUGO | S_IWUSR, NULL);
|
||||||
static BAT_ATTR(vis_mode, S_IRUGO | S_IWUSR, show_vis_mode, store_vis_mode);
|
static BAT_ATTR(vis_mode, S_IRUGO | S_IWUSR, show_vis_mode, store_vis_mode);
|
||||||
static BAT_ATTR(routing_algo, S_IRUGO, show_bat_algo, NULL);
|
static BAT_ATTR(routing_algo, S_IRUGO, show_bat_algo, NULL);
|
||||||
|
@ -469,7 +472,7 @@ static struct bat_attribute *mesh_attrs[] = {
|
||||||
NULL,
|
NULL,
|
||||||
};
|
};
|
||||||
|
|
||||||
int sysfs_add_meshif(struct net_device *dev)
|
int batadv_sysfs_add_meshif(struct net_device *dev)
|
||||||
{
|
{
|
||||||
struct kobject *batif_kobject = &dev->dev.kobj;
|
struct kobject *batif_kobject = &dev->dev.kobj;
|
||||||
struct bat_priv *bat_priv = netdev_priv(dev);
|
struct bat_priv *bat_priv = netdev_priv(dev);
|
||||||
|
@ -507,7 +510,7 @@ out:
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
}
|
}
|
||||||
|
|
||||||
void sysfs_del_meshif(struct net_device *dev)
|
void batadv_sysfs_del_meshif(struct net_device *dev)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(dev);
|
struct bat_priv *bat_priv = netdev_priv(dev);
|
||||||
struct bat_attribute **bat_attr;
|
struct bat_attribute **bat_attr;
|
||||||
|
@ -523,7 +526,7 @@ static ssize_t show_mesh_iface(struct kobject *kobj, struct attribute *attr,
|
||||||
char *buff)
|
char *buff)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = kobj_to_netdev(kobj);
|
struct net_device *net_dev = kobj_to_netdev(kobj);
|
||||||
struct hard_iface *hard_iface = hardif_get_by_netdev(net_dev);
|
struct hard_iface *hard_iface = batadv_hardif_get_by_netdev(net_dev);
|
||||||
ssize_t length;
|
ssize_t length;
|
||||||
|
|
||||||
if (!hard_iface)
|
if (!hard_iface)
|
||||||
|
@ -541,7 +544,7 @@ static ssize_t store_mesh_iface(struct kobject *kobj, struct attribute *attr,
|
||||||
char *buff, size_t count)
|
char *buff, size_t count)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = kobj_to_netdev(kobj);
|
struct net_device *net_dev = kobj_to_netdev(kobj);
|
||||||
struct hard_iface *hard_iface = hardif_get_by_netdev(net_dev);
|
struct hard_iface *hard_iface = batadv_hardif_get_by_netdev(net_dev);
|
||||||
int status_tmp = -1;
|
int status_tmp = -1;
|
||||||
int ret = count;
|
int ret = count;
|
||||||
|
|
||||||
|
@ -576,15 +579,15 @@ static ssize_t store_mesh_iface(struct kobject *kobj, struct attribute *attr,
|
||||||
}
|
}
|
||||||
|
|
||||||
if (status_tmp == IF_NOT_IN_USE) {
|
if (status_tmp == IF_NOT_IN_USE) {
|
||||||
hardif_disable_interface(hard_iface);
|
batadv_hardif_disable_interface(hard_iface);
|
||||||
goto unlock;
|
goto unlock;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* if the interface already is in use */
|
/* if the interface already is in use */
|
||||||
if (hard_iface->if_status != IF_NOT_IN_USE)
|
if (hard_iface->if_status != IF_NOT_IN_USE)
|
||||||
hardif_disable_interface(hard_iface);
|
batadv_hardif_disable_interface(hard_iface);
|
||||||
|
|
||||||
ret = hardif_enable_interface(hard_iface, buff);
|
ret = batadv_hardif_enable_interface(hard_iface, buff);
|
||||||
|
|
||||||
unlock:
|
unlock:
|
||||||
rtnl_unlock();
|
rtnl_unlock();
|
||||||
|
@ -597,7 +600,7 @@ static ssize_t show_iface_status(struct kobject *kobj, struct attribute *attr,
|
||||||
char *buff)
|
char *buff)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = kobj_to_netdev(kobj);
|
struct net_device *net_dev = kobj_to_netdev(kobj);
|
||||||
struct hard_iface *hard_iface = hardif_get_by_netdev(net_dev);
|
struct hard_iface *hard_iface = batadv_hardif_get_by_netdev(net_dev);
|
||||||
ssize_t length;
|
ssize_t length;
|
||||||
|
|
||||||
if (!hard_iface)
|
if (!hard_iface)
|
||||||
|
@ -637,7 +640,7 @@ static struct bat_attribute *batman_attrs[] = {
|
||||||
NULL,
|
NULL,
|
||||||
};
|
};
|
||||||
|
|
||||||
int sysfs_add_hardif(struct kobject **hardif_obj, struct net_device *dev)
|
int batadv_sysfs_add_hardif(struct kobject **hardif_obj, struct net_device *dev)
|
||||||
{
|
{
|
||||||
struct kobject *hardif_kobject = &dev->dev.kobj;
|
struct kobject *hardif_kobject = &dev->dev.kobj;
|
||||||
struct bat_attribute **bat_attr;
|
struct bat_attribute **bat_attr;
|
||||||
|
@ -671,14 +674,14 @@ out:
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
}
|
}
|
||||||
|
|
||||||
void sysfs_del_hardif(struct kobject **hardif_obj)
|
void batadv_sysfs_del_hardif(struct kobject **hardif_obj)
|
||||||
{
|
{
|
||||||
kobject_put(*hardif_obj);
|
kobject_put(*hardif_obj);
|
||||||
*hardif_obj = NULL;
|
*hardif_obj = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int throw_uevent(struct bat_priv *bat_priv, enum uev_type type,
|
int batadv_throw_uevent(struct bat_priv *bat_priv, enum uev_type type,
|
||||||
enum uev_action action, const char *data)
|
enum uev_action action, const char *data)
|
||||||
{
|
{
|
||||||
int ret = -ENOMEM;
|
int ret = -ENOMEM;
|
||||||
struct hard_iface *primary_if = NULL;
|
struct hard_iface *primary_if = NULL;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,10 +15,8 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_SYSFS_H_
|
#ifndef _NET_BATMAN_ADV_SYSFS_H_
|
||||||
#define _NET_BATMAN_ADV_SYSFS_H_
|
#define _NET_BATMAN_ADV_SYSFS_H_
|
||||||
|
|
||||||
|
@ -34,11 +31,12 @@ struct bat_attribute {
|
||||||
char *buf, size_t count);
|
char *buf, size_t count);
|
||||||
};
|
};
|
||||||
|
|
||||||
int sysfs_add_meshif(struct net_device *dev);
|
int batadv_sysfs_add_meshif(struct net_device *dev);
|
||||||
void sysfs_del_meshif(struct net_device *dev);
|
void batadv_sysfs_del_meshif(struct net_device *dev);
|
||||||
int sysfs_add_hardif(struct kobject **hardif_obj, struct net_device *dev);
|
int batadv_sysfs_add_hardif(struct kobject **hardif_obj,
|
||||||
void sysfs_del_hardif(struct kobject **hardif_obj);
|
struct net_device *dev);
|
||||||
int throw_uevent(struct bat_priv *bat_priv, enum uev_type type,
|
void batadv_sysfs_del_hardif(struct kobject **hardif_obj);
|
||||||
enum uev_action action, const char *data);
|
int batadv_throw_uevent(struct bat_priv *bat_priv, enum uev_type type,
|
||||||
|
enum uev_action action, const char *data);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_SYSFS_H_ */
|
#endif /* _NET_BATMAN_ADV_SYSFS_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich, Marek Lindner
|
* Simon Wunderlich, Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -25,7 +23,7 @@
|
||||||
#include <linux/bitops.h>
|
#include <linux/bitops.h>
|
||||||
|
|
||||||
/* shift the packet array by n places. */
|
/* shift the packet array by n places. */
|
||||||
static void bat_bitmap_shift_left(unsigned long *seq_bits, int32_t n)
|
static void batadv_bitmap_shift_left(unsigned long *seq_bits, int32_t n)
|
||||||
{
|
{
|
||||||
if (n <= 0 || n >= TQ_LOCAL_WINDOW_SIZE)
|
if (n <= 0 || n >= TQ_LOCAL_WINDOW_SIZE)
|
||||||
return;
|
return;
|
||||||
|
@ -40,14 +38,14 @@ static void bat_bitmap_shift_left(unsigned long *seq_bits, int32_t n)
|
||||||
* 1 if the window was moved (either new or very old)
|
* 1 if the window was moved (either new or very old)
|
||||||
* 0 if the window was not moved/shifted.
|
* 0 if the window was not moved/shifted.
|
||||||
*/
|
*/
|
||||||
int bit_get_packet(void *priv, unsigned long *seq_bits,
|
int batadv_bit_get_packet(void *priv, unsigned long *seq_bits,
|
||||||
int32_t seq_num_diff, int set_mark)
|
int32_t seq_num_diff, int set_mark)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = priv;
|
struct bat_priv *bat_priv = priv;
|
||||||
|
|
||||||
/* sequence number is slightly older. We already got a sequence number
|
/* sequence number is slightly older. We already got a sequence number
|
||||||
* higher than this one, so we just mark it. */
|
* higher than this one, so we just mark it.
|
||||||
|
*/
|
||||||
if ((seq_num_diff <= 0) && (seq_num_diff > -TQ_LOCAL_WINDOW_SIZE)) {
|
if ((seq_num_diff <= 0) && (seq_num_diff > -TQ_LOCAL_WINDOW_SIZE)) {
|
||||||
if (set_mark)
|
if (set_mark)
|
||||||
bat_set_bit(seq_bits, -seq_num_diff);
|
bat_set_bit(seq_bits, -seq_num_diff);
|
||||||
|
@ -55,10 +53,10 @@ int bit_get_packet(void *priv, unsigned long *seq_bits,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* sequence number is slightly newer, so we shift the window and
|
/* sequence number is slightly newer, so we shift the window and
|
||||||
* set the mark if required */
|
* set the mark if required
|
||||||
|
*/
|
||||||
if ((seq_num_diff > 0) && (seq_num_diff < TQ_LOCAL_WINDOW_SIZE)) {
|
if ((seq_num_diff > 0) && (seq_num_diff < TQ_LOCAL_WINDOW_SIZE)) {
|
||||||
bat_bitmap_shift_left(seq_bits, seq_num_diff);
|
batadv_bitmap_shift_left(seq_bits, seq_num_diff);
|
||||||
|
|
||||||
if (set_mark)
|
if (set_mark)
|
||||||
bat_set_bit(seq_bits, 0);
|
bat_set_bit(seq_bits, 0);
|
||||||
|
@ -66,7 +64,6 @@ int bit_get_packet(void *priv, unsigned long *seq_bits,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* sequence number is much newer, probably missed a lot of packets */
|
/* sequence number is much newer, probably missed a lot of packets */
|
||||||
|
|
||||||
if ((seq_num_diff >= TQ_LOCAL_WINDOW_SIZE) &&
|
if ((seq_num_diff >= TQ_LOCAL_WINDOW_SIZE) &&
|
||||||
(seq_num_diff < EXPECTED_SEQNO_RANGE)) {
|
(seq_num_diff < EXPECTED_SEQNO_RANGE)) {
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
|
@ -81,8 +78,8 @@ int bit_get_packet(void *priv, unsigned long *seq_bits,
|
||||||
/* received a much older packet. The other host either restarted
|
/* received a much older packet. The other host either restarted
|
||||||
* or the old packet got delayed somewhere in the network. The
|
* or the old packet got delayed somewhere in the network. The
|
||||||
* packet should be dropped without calling this function if the
|
* packet should be dropped without calling this function if the
|
||||||
* seqno window is protected. */
|
* seqno window is protected.
|
||||||
|
*/
|
||||||
if ((seq_num_diff <= -TQ_LOCAL_WINDOW_SIZE) ||
|
if ((seq_num_diff <= -TQ_LOCAL_WINDOW_SIZE) ||
|
||||||
(seq_num_diff >= EXPECTED_SEQNO_RANGE)) {
|
(seq_num_diff >= EXPECTED_SEQNO_RANGE)) {
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich, Marek Lindner
|
* Simon Wunderlich, Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,14 +15,14 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_BITARRAY_H_
|
#ifndef _NET_BATMAN_ADV_BITARRAY_H_
|
||||||
#define _NET_BATMAN_ADV_BITARRAY_H_
|
#define _NET_BATMAN_ADV_BITARRAY_H_
|
||||||
|
|
||||||
/* returns true if the corresponding bit in the given seq_bits indicates true
|
/* returns true if the corresponding bit in the given seq_bits indicates true
|
||||||
* and curr_seqno is within range of last_seqno */
|
* and curr_seqno is within range of last_seqno
|
||||||
|
*/
|
||||||
static inline int bat_test_bit(const unsigned long *seq_bits,
|
static inline int bat_test_bit(const unsigned long *seq_bits,
|
||||||
uint32_t last_seqno, uint32_t curr_seqno)
|
uint32_t last_seqno, uint32_t curr_seqno)
|
||||||
{
|
{
|
||||||
|
@ -47,8 +46,9 @@ static inline void bat_set_bit(unsigned long *seq_bits, int32_t n)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* receive and process one packet, returns 1 if received seq_num is considered
|
/* receive and process one packet, returns 1 if received seq_num is considered
|
||||||
* new, 0 if old */
|
* new, 0 if old
|
||||||
int bit_get_packet(void *priv, unsigned long *seq_bits,
|
*/
|
||||||
int32_t seq_num_diff, int set_mark);
|
int batadv_bit_get_packet(void *priv, unsigned long *seq_bits,
|
||||||
|
int32_t seq_num_diff, int set_mark);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_BITARRAY_H_ */
|
#endif /* _NET_BATMAN_ADV_BITARRAY_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich
|
* Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -123,8 +121,7 @@ static void claim_free_ref(struct claim *claim)
|
||||||
call_rcu(&claim->rcu, claim_free_rcu);
|
call_rcu(&claim->rcu, claim_free_rcu);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @data: search data (may be local/static data)
|
* @data: search data (may be local/static data)
|
||||||
*
|
*
|
||||||
* looks for a claim in the hash, and returns it if found
|
* looks for a claim in the hash, and returns it if found
|
||||||
|
@ -162,8 +159,7 @@ static struct claim *claim_hash_find(struct bat_priv *bat_priv,
|
||||||
return claim_tmp;
|
return claim_tmp;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @addr: the address of the originator
|
* @addr: the address of the originator
|
||||||
* @vid: the VLAN ID
|
* @vid: the VLAN ID
|
||||||
*
|
*
|
||||||
|
@ -241,8 +237,7 @@ static void bla_del_backbone_claims(struct backbone_gw *backbone_gw)
|
||||||
backbone_gw->crc = BLA_CRC_INIT;
|
backbone_gw->crc = BLA_CRC_INIT;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @orig: the mac address to be announced within the claim
|
* @orig: the mac address to be announced within the claim
|
||||||
* @vid: the VLAN ID
|
* @vid: the VLAN ID
|
||||||
* @claimtype: the type of the claim (CLAIM, UNCLAIM, ANNOUNCE, ...)
|
* @claimtype: the type of the claim (CLAIM, UNCLAIM, ANNOUNCE, ...)
|
||||||
|
@ -347,8 +342,7 @@ out:
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @orig: the mac address of the originator
|
* @orig: the mac address of the originator
|
||||||
* @vid: the VLAN ID
|
* @vid: the VLAN ID
|
||||||
*
|
*
|
||||||
|
@ -397,9 +391,9 @@ static struct backbone_gw *bla_get_backbone_gw(struct bat_priv *bat_priv,
|
||||||
/* this is a gateway now, remove any tt entries */
|
/* this is a gateway now, remove any tt entries */
|
||||||
orig_node = orig_hash_find(bat_priv, orig);
|
orig_node = orig_hash_find(bat_priv, orig);
|
||||||
if (orig_node) {
|
if (orig_node) {
|
||||||
tt_global_del_orig(bat_priv, orig_node,
|
batadv_tt_global_del_orig(bat_priv, orig_node,
|
||||||
"became a backbone gateway");
|
"became a backbone gateway");
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
return entry;
|
return entry;
|
||||||
}
|
}
|
||||||
|
@ -422,8 +416,7 @@ static void bla_update_own_backbone_gw(struct bat_priv *bat_priv,
|
||||||
backbone_gw_free_ref(backbone_gw);
|
backbone_gw_free_ref(backbone_gw);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @vid: the vid where the request came on
|
* @vid: the vid where the request came on
|
||||||
*
|
*
|
||||||
* Repeat all of our own claims, and finally send an ANNOUNCE frame
|
* Repeat all of our own claims, and finally send an ANNOUNCE frame
|
||||||
|
@ -468,8 +461,7 @@ static void bla_answer_request(struct bat_priv *bat_priv,
|
||||||
backbone_gw_free_ref(backbone_gw);
|
backbone_gw_free_ref(backbone_gw);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @backbone_gw: the backbone gateway from whom we are out of sync
|
||||||
* @backbone_gw: the backbone gateway from whom we are out of sync
|
|
||||||
*
|
*
|
||||||
* When the crc is wrong, ask the backbone gateway for a full table update.
|
* When the crc is wrong, ask the backbone gateway for a full table update.
|
||||||
* After the request, it will repeat all of his own claims and finally
|
* After the request, it will repeat all of his own claims and finally
|
||||||
|
@ -495,8 +487,7 @@ static void bla_send_request(struct backbone_gw *backbone_gw)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @backbone_gw: our backbone gateway which should be announced
|
* @backbone_gw: our backbone gateway which should be announced
|
||||||
*
|
*
|
||||||
* This function sends an announcement. It is called from multiple
|
* This function sends an announcement. It is called from multiple
|
||||||
|
@ -516,8 +507,7 @@ static void bla_send_announce(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @mac: the mac address of the claim
|
* @mac: the mac address of the claim
|
||||||
* @vid: the VLAN ID of the frame
|
* @vid: the VLAN ID of the frame
|
||||||
* @backbone_gw: the backbone gateway which claims it
|
* @backbone_gw: the backbone gateway which claims it
|
||||||
|
@ -731,8 +721,7 @@ static int handle_claim(struct bat_priv *bat_priv,
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @hw_src: the Hardware source in the ARP Header
|
* @hw_src: the Hardware source in the ARP Header
|
||||||
* @hw_dst: the Hardware destination in the ARP Header
|
* @hw_dst: the Hardware destination in the ARP Header
|
||||||
* @ethhdr: pointer to the Ethernet header of the claim frame
|
* @ethhdr: pointer to the Ethernet header of the claim frame
|
||||||
|
@ -804,14 +793,13 @@ static int check_claim_group(struct bat_priv *bat_priv,
|
||||||
bla_dst_own->group = bla_dst->group;
|
bla_dst_own->group = bla_dst->group;
|
||||||
}
|
}
|
||||||
|
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
|
|
||||||
return 2;
|
return 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @skb: the frame to be checked
|
* @skb: the frame to be checked
|
||||||
*
|
*
|
||||||
* Check if this is a claim frame, and process it accordingly.
|
* Check if this is a claim frame, and process it accordingly.
|
||||||
|
@ -860,7 +848,6 @@ static int bla_process_claim(struct bat_priv *bat_priv,
|
||||||
/* Check whether the ARP frame carries a valid
|
/* Check whether the ARP frame carries a valid
|
||||||
* IP information
|
* IP information
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if (arphdr->ar_hrd != htons(ARPHRD_ETHER))
|
if (arphdr->ar_hrd != htons(ARPHRD_ETHER))
|
||||||
return 0;
|
return 0;
|
||||||
if (arphdr->ar_pro != htons(ETH_P_IP))
|
if (arphdr->ar_pro != htons(ETH_P_IP))
|
||||||
|
@ -963,8 +950,7 @@ purge_now:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @primary_if: the selected primary interface, may be NULL if now is set
|
* @primary_if: the selected primary interface, may be NULL if now is set
|
||||||
* @now: whether the whole hash shall be wiped now
|
* @now: whether the whole hash shall be wiped now
|
||||||
*
|
*
|
||||||
|
@ -1011,17 +997,15 @@ purge_now:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @primary_if: the new selected primary_if
|
* @primary_if: the new selected primary_if
|
||||||
* @oldif: the old primary interface, may be NULL
|
* @oldif: the old primary interface, may be NULL
|
||||||
*
|
*
|
||||||
* Update the backbone gateways when the own orig address changes.
|
* Update the backbone gateways when the own orig address changes.
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
void bla_update_orig_address(struct bat_priv *bat_priv,
|
void batadv_bla_update_orig_address(struct bat_priv *bat_priv,
|
||||||
struct hard_iface *primary_if,
|
struct hard_iface *primary_if,
|
||||||
struct hard_iface *oldif)
|
struct hard_iface *oldif)
|
||||||
{
|
{
|
||||||
struct backbone_gw *backbone_gw;
|
struct backbone_gw *backbone_gw;
|
||||||
struct hlist_node *node;
|
struct hlist_node *node;
|
||||||
|
@ -1070,7 +1054,7 @@ void bla_update_orig_address(struct bat_priv *bat_priv,
|
||||||
static void bla_start_timer(struct bat_priv *bat_priv)
|
static void bla_start_timer(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
INIT_DELAYED_WORK(&bat_priv->bla_work, bla_periodic_work);
|
INIT_DELAYED_WORK(&bat_priv->bla_work, bla_periodic_work);
|
||||||
queue_delayed_work(bat_event_workqueue, &bat_priv->bla_work,
|
queue_delayed_work(batadv_event_workqueue, &bat_priv->bla_work,
|
||||||
msecs_to_jiffies(BLA_PERIOD_LENGTH));
|
msecs_to_jiffies(BLA_PERIOD_LENGTH));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1136,7 +1120,7 @@ static struct lock_class_key claim_hash_lock_class_key;
|
||||||
static struct lock_class_key backbone_hash_lock_class_key;
|
static struct lock_class_key backbone_hash_lock_class_key;
|
||||||
|
|
||||||
/* initialize all bla structures */
|
/* initialize all bla structures */
|
||||||
int bla_init(struct bat_priv *bat_priv)
|
int batadv_bla_init(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
uint8_t claim_dest[ETH_ALEN] = {0xff, 0x43, 0x05, 0x00, 0x00, 0x00};
|
uint8_t claim_dest[ETH_ALEN] = {0xff, 0x43, 0x05, 0x00, 0x00, 0x00};
|
||||||
|
@ -1166,8 +1150,8 @@ int bla_init(struct bat_priv *bat_priv)
|
||||||
if (bat_priv->claim_hash)
|
if (bat_priv->claim_hash)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
bat_priv->claim_hash = hash_new(128);
|
bat_priv->claim_hash = batadv_hash_new(128);
|
||||||
bat_priv->backbone_hash = hash_new(32);
|
bat_priv->backbone_hash = batadv_hash_new(32);
|
||||||
|
|
||||||
if (!bat_priv->claim_hash || !bat_priv->backbone_hash)
|
if (!bat_priv->claim_hash || !bat_priv->backbone_hash)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
@ -1183,8 +1167,7 @@ int bla_init(struct bat_priv *bat_priv)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @bcast_packet: originator mac address
|
* @bcast_packet: originator mac address
|
||||||
* @hdr_size: maximum length of the frame
|
* @hdr_size: maximum length of the frame
|
||||||
*
|
*
|
||||||
|
@ -1196,12 +1179,10 @@ int bla_init(struct bat_priv *bat_priv)
|
||||||
* with a good chance that it is the same packet. If it is furthermore
|
* with a good chance that it is the same packet. If it is furthermore
|
||||||
* sent by another host, drop it. We allow equal packets from
|
* sent by another host, drop it. We allow equal packets from
|
||||||
* the same host however as this might be intended.
|
* the same host however as this might be intended.
|
||||||
*
|
*/
|
||||||
**/
|
int batadv_bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
||||||
|
struct bcast_packet *bcast_packet,
|
||||||
int bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
int hdr_size)
|
||||||
struct bcast_packet *bcast_packet,
|
|
||||||
int hdr_size)
|
|
||||||
{
|
{
|
||||||
int i, length, curr;
|
int i, length, curr;
|
||||||
uint8_t *content;
|
uint8_t *content;
|
||||||
|
@ -1250,17 +1231,14 @@ int bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @orig: originator mac address
|
* @orig: originator mac address
|
||||||
*
|
*
|
||||||
* check if the originator is a gateway for any VLAN ID.
|
* check if the originator is a gateway for any VLAN ID.
|
||||||
*
|
*
|
||||||
* returns 1 if it is found, 0 otherwise
|
* returns 1 if it is found, 0 otherwise
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
int batadv_bla_is_backbone_gw_orig(struct bat_priv *bat_priv, uint8_t *orig)
|
||||||
int bla_is_backbone_gw_orig(struct bat_priv *bat_priv, uint8_t *orig)
|
|
||||||
{
|
{
|
||||||
struct hashtable_t *hash = bat_priv->backbone_hash;
|
struct hashtable_t *hash = bat_priv->backbone_hash;
|
||||||
struct hlist_head *head;
|
struct hlist_head *head;
|
||||||
|
@ -1291,18 +1269,16 @@ int bla_is_backbone_gw_orig(struct bat_priv *bat_priv, uint8_t *orig)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/* @skb: the frame to be checked
|
||||||
* @skb: the frame to be checked
|
|
||||||
* @orig_node: the orig_node of the frame
|
* @orig_node: the orig_node of the frame
|
||||||
* @hdr_size: maximum length of the frame
|
* @hdr_size: maximum length of the frame
|
||||||
*
|
*
|
||||||
* bla_is_backbone_gw inspects the skb for the VLAN ID and returns 1
|
* bla_is_backbone_gw inspects the skb for the VLAN ID and returns 1
|
||||||
* if the orig_node is also a gateway on the soft interface, otherwise it
|
* if the orig_node is also a gateway on the soft interface, otherwise it
|
||||||
* returns 0.
|
* returns 0.
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
int bla_is_backbone_gw(struct sk_buff *skb,
|
int batadv_bla_is_backbone_gw(struct sk_buff *skb,
|
||||||
struct orig_node *orig_node, int hdr_size)
|
struct orig_node *orig_node, int hdr_size)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
struct vlan_ethhdr *vhdr;
|
struct vlan_ethhdr *vhdr;
|
||||||
|
@ -1328,7 +1304,6 @@ int bla_is_backbone_gw(struct sk_buff *skb,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* see if this originator is a backbone gw for this VLAN */
|
/* see if this originator is a backbone gw for this VLAN */
|
||||||
|
|
||||||
backbone_gw = backbone_hash_find(orig_node->bat_priv,
|
backbone_gw = backbone_hash_find(orig_node->bat_priv,
|
||||||
orig_node->orig, vid);
|
orig_node->orig, vid);
|
||||||
if (!backbone_gw)
|
if (!backbone_gw)
|
||||||
|
@ -1339,7 +1314,7 @@ int bla_is_backbone_gw(struct sk_buff *skb,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* free all bla structures (for softinterface free or module unload) */
|
/* free all bla structures (for softinterface free or module unload) */
|
||||||
void bla_free(struct bat_priv *bat_priv)
|
void batadv_bla_free(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct hard_iface *primary_if;
|
struct hard_iface *primary_if;
|
||||||
|
|
||||||
|
@ -1348,20 +1323,19 @@ void bla_free(struct bat_priv *bat_priv)
|
||||||
|
|
||||||
if (bat_priv->claim_hash) {
|
if (bat_priv->claim_hash) {
|
||||||
bla_purge_claims(bat_priv, primary_if, 1);
|
bla_purge_claims(bat_priv, primary_if, 1);
|
||||||
hash_destroy(bat_priv->claim_hash);
|
batadv_hash_destroy(bat_priv->claim_hash);
|
||||||
bat_priv->claim_hash = NULL;
|
bat_priv->claim_hash = NULL;
|
||||||
}
|
}
|
||||||
if (bat_priv->backbone_hash) {
|
if (bat_priv->backbone_hash) {
|
||||||
bla_purge_backbone_gw(bat_priv, 1);
|
bla_purge_backbone_gw(bat_priv, 1);
|
||||||
hash_destroy(bat_priv->backbone_hash);
|
batadv_hash_destroy(bat_priv->backbone_hash);
|
||||||
bat_priv->backbone_hash = NULL;
|
bat_priv->backbone_hash = NULL;
|
||||||
}
|
}
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @skb: the frame to be checked
|
* @skb: the frame to be checked
|
||||||
* @vid: the VLAN ID of the frame
|
* @vid: the VLAN ID of the frame
|
||||||
*
|
*
|
||||||
|
@ -1372,9 +1346,8 @@ void bla_free(struct bat_priv *bat_priv)
|
||||||
* in these cases, the skb is further handled by this function and
|
* in these cases, the skb is further handled by this function and
|
||||||
* returns 1, otherwise it returns 0 and the caller shall further
|
* returns 1, otherwise it returns 0 and the caller shall further
|
||||||
* process the skb.
|
* process the skb.
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
int bla_rx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid)
|
int batadv_bla_rx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
struct claim search_claim, *claim = NULL;
|
struct claim search_claim, *claim = NULL;
|
||||||
|
@ -1449,8 +1422,7 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* @bat_priv: the bat priv with all the soft interface information
|
||||||
* @bat_priv: the bat priv with all the soft interface information
|
|
||||||
* @skb: the frame to be checked
|
* @skb: the frame to be checked
|
||||||
* @vid: the VLAN ID of the frame
|
* @vid: the VLAN ID of the frame
|
||||||
*
|
*
|
||||||
|
@ -1461,9 +1433,8 @@ out:
|
||||||
* in these cases, the skb is further handled by this function and
|
* in these cases, the skb is further handled by this function and
|
||||||
* returns 1, otherwise it returns 0 and the caller shall further
|
* returns 1, otherwise it returns 0 and the caller shall further
|
||||||
* process the skb.
|
* process the skb.
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
int bla_tx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid)
|
int batadv_bla_tx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
struct claim search_claim, *claim = NULL;
|
struct claim search_claim, *claim = NULL;
|
||||||
|
@ -1537,7 +1508,7 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int bla_claim_table_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_bla_claim_table_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)seq->private;
|
struct net_device *net_dev = (struct net_device *)seq->private;
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich
|
* Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,80 +15,82 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_BLA_H_
|
#ifndef _NET_BATMAN_ADV_BLA_H_
|
||||||
#define _NET_BATMAN_ADV_BLA_H_
|
#define _NET_BATMAN_ADV_BLA_H_
|
||||||
|
|
||||||
#ifdef CONFIG_BATMAN_ADV_BLA
|
#ifdef CONFIG_BATMAN_ADV_BLA
|
||||||
int bla_rx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid);
|
int batadv_bla_rx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid);
|
||||||
int bla_tx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid);
|
int batadv_bla_tx(struct bat_priv *bat_priv, struct sk_buff *skb, short vid);
|
||||||
int bla_is_backbone_gw(struct sk_buff *skb,
|
int batadv_bla_is_backbone_gw(struct sk_buff *skb,
|
||||||
struct orig_node *orig_node, int hdr_size);
|
struct orig_node *orig_node, int hdr_size);
|
||||||
int bla_claim_table_seq_print_text(struct seq_file *seq, void *offset);
|
int batadv_bla_claim_table_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
int bla_is_backbone_gw_orig(struct bat_priv *bat_priv, uint8_t *orig);
|
int batadv_bla_is_backbone_gw_orig(struct bat_priv *bat_priv, uint8_t *orig);
|
||||||
int bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
int batadv_bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
||||||
struct bcast_packet *bcast_packet, int hdr_size);
|
struct bcast_packet *bcast_packet,
|
||||||
void bla_update_orig_address(struct bat_priv *bat_priv,
|
int hdr_size);
|
||||||
struct hard_iface *primary_if,
|
void batadv_bla_update_orig_address(struct bat_priv *bat_priv,
|
||||||
struct hard_iface *oldif);
|
struct hard_iface *primary_if,
|
||||||
int bla_init(struct bat_priv *bat_priv);
|
struct hard_iface *oldif);
|
||||||
void bla_free(struct bat_priv *bat_priv);
|
int batadv_bla_init(struct bat_priv *bat_priv);
|
||||||
|
void batadv_bla_free(struct bat_priv *bat_priv);
|
||||||
|
|
||||||
#define BLA_CRC_INIT 0
|
#define BLA_CRC_INIT 0
|
||||||
#else /* ifdef CONFIG_BATMAN_ADV_BLA */
|
#else /* ifdef CONFIG_BATMAN_ADV_BLA */
|
||||||
|
|
||||||
static inline int bla_rx(struct bat_priv *bat_priv, struct sk_buff *skb,
|
static inline int batadv_bla_rx(struct bat_priv *bat_priv, struct sk_buff *skb,
|
||||||
short vid)
|
short vid)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline int bla_tx(struct bat_priv *bat_priv, struct sk_buff *skb,
|
static inline int batadv_bla_tx(struct bat_priv *bat_priv, struct sk_buff *skb,
|
||||||
short vid)
|
short vid)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline int bla_is_backbone_gw(struct sk_buff *skb,
|
static inline int batadv_bla_is_backbone_gw(struct sk_buff *skb,
|
||||||
struct orig_node *orig_node,
|
struct orig_node *orig_node,
|
||||||
int hdr_size)
|
int hdr_size)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline int bla_claim_table_seq_print_text(struct seq_file *seq,
|
static inline int batadv_bla_claim_table_seq_print_text(struct seq_file *seq,
|
||||||
void *offset)
|
void *offset)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline int bla_is_backbone_gw_orig(struct bat_priv *bat_priv,
|
static inline int batadv_bla_is_backbone_gw_orig(struct bat_priv *bat_priv,
|
||||||
uint8_t *orig)
|
uint8_t *orig)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline int bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
static inline int
|
||||||
struct bcast_packet *bcast_packet,
|
batadv_bla_check_bcast_duplist(struct bat_priv *bat_priv,
|
||||||
int hdr_size)
|
struct bcast_packet *bcast_packet,
|
||||||
|
int hdr_size)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void bla_update_orig_address(struct bat_priv *bat_priv,
|
static inline void
|
||||||
struct hard_iface *primary_if,
|
batadv_bla_update_orig_address(struct bat_priv *bat_priv,
|
||||||
struct hard_iface *oldif)
|
struct hard_iface *primary_if,
|
||||||
|
struct hard_iface *oldif)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline int bla_init(struct bat_priv *bat_priv)
|
static inline int batadv_bla_init(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void bla_free(struct bat_priv *bat_priv)
|
static inline void batadv_bla_free(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -33,7 +31,8 @@
|
||||||
#include <linux/if_vlan.h>
|
#include <linux/if_vlan.h>
|
||||||
|
|
||||||
/* This is the offset of the options field in a dhcp packet starting at
|
/* This is the offset of the options field in a dhcp packet starting at
|
||||||
* the beginning of the dhcp header */
|
* the beginning of the dhcp header
|
||||||
|
*/
|
||||||
#define DHCP_OPTIONS_OFFSET 240
|
#define DHCP_OPTIONS_OFFSET 240
|
||||||
#define DHCP_REQUEST 3
|
#define DHCP_REQUEST 3
|
||||||
|
|
||||||
|
@ -60,7 +59,7 @@ out:
|
||||||
return gw_node;
|
return gw_node;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct orig_node *gw_get_selected_orig(struct bat_priv *bat_priv)
|
struct orig_node *batadv_gw_get_selected_orig(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct gw_node *gw_node;
|
struct gw_node *gw_node;
|
||||||
struct orig_node *orig_node = NULL;
|
struct orig_node *orig_node = NULL;
|
||||||
|
@ -103,7 +102,7 @@ static void gw_select(struct bat_priv *bat_priv, struct gw_node *new_gw_node)
|
||||||
spin_unlock_bh(&bat_priv->gw_list_lock);
|
spin_unlock_bh(&bat_priv->gw_list_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gw_deselect(struct bat_priv *bat_priv)
|
void batadv_gw_deselect(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
atomic_set(&bat_priv->gw_reselect, 1);
|
atomic_set(&bat_priv->gw_reselect, 1);
|
||||||
}
|
}
|
||||||
|
@ -116,13 +115,15 @@ static struct gw_node *gw_get_best_gw_node(struct bat_priv *bat_priv)
|
||||||
uint32_t max_gw_factor = 0, tmp_gw_factor = 0;
|
uint32_t max_gw_factor = 0, tmp_gw_factor = 0;
|
||||||
uint8_t max_tq = 0;
|
uint8_t max_tq = 0;
|
||||||
int down, up;
|
int down, up;
|
||||||
|
struct orig_node *orig_node;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
hlist_for_each_entry_rcu(gw_node, node, &bat_priv->gw_list, list) {
|
hlist_for_each_entry_rcu(gw_node, node, &bat_priv->gw_list, list) {
|
||||||
if (gw_node->deleted)
|
if (gw_node->deleted)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
router = orig_node_get_router(gw_node->orig_node);
|
orig_node = gw_node->orig_node;
|
||||||
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -131,8 +132,8 @@ static struct gw_node *gw_get_best_gw_node(struct bat_priv *bat_priv)
|
||||||
|
|
||||||
switch (atomic_read(&bat_priv->gw_sel_class)) {
|
switch (atomic_read(&bat_priv->gw_sel_class)) {
|
||||||
case 1: /* fast connection */
|
case 1: /* fast connection */
|
||||||
gw_bandwidth_to_kbit(gw_node->orig_node->gw_flags,
|
batadv_gw_bandwidth_to_kbit(orig_node->gw_flags,
|
||||||
&down, &up);
|
&down, &up);
|
||||||
|
|
||||||
tmp_gw_factor = (router->tq_avg * router->tq_avg *
|
tmp_gw_factor = (router->tq_avg * router->tq_avg *
|
||||||
down * 100 * 100) /
|
down * 100 * 100) /
|
||||||
|
@ -149,14 +150,13 @@ static struct gw_node *gw_get_best_gw_node(struct bat_priv *bat_priv)
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default: /**
|
default: /* 2: stable connection (use best statistic)
|
||||||
* 2: stable connection (use best statistic)
|
|
||||||
* 3: fast-switch (use best statistic but change as
|
* 3: fast-switch (use best statistic but change as
|
||||||
* soon as a better gateway appears)
|
* soon as a better gateway appears)
|
||||||
* XX: late-switch (use best statistic but change as
|
* XX: late-switch (use best statistic but change as
|
||||||
* soon as a better gateway appears which has
|
* soon as a better gateway appears which has
|
||||||
* $routing_class more tq points)
|
* $routing_class more tq points)
|
||||||
**/
|
*/
|
||||||
if (router->tq_avg > max_tq) {
|
if (router->tq_avg > max_tq) {
|
||||||
if (curr_gw)
|
if (curr_gw)
|
||||||
gw_node_free_ref(curr_gw);
|
gw_node_free_ref(curr_gw);
|
||||||
|
@ -175,25 +175,24 @@ static struct gw_node *gw_get_best_gw_node(struct bat_priv *bat_priv)
|
||||||
gw_node_free_ref(gw_node);
|
gw_node_free_ref(gw_node);
|
||||||
|
|
||||||
next:
|
next:
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
|
|
||||||
return curr_gw;
|
return curr_gw;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gw_election(struct bat_priv *bat_priv)
|
void batadv_gw_election(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct gw_node *curr_gw = NULL, *next_gw = NULL;
|
struct gw_node *curr_gw = NULL, *next_gw = NULL;
|
||||||
struct neigh_node *router = NULL;
|
struct neigh_node *router = NULL;
|
||||||
char gw_addr[18] = { '\0' };
|
char gw_addr[18] = { '\0' };
|
||||||
|
|
||||||
/**
|
/* The batman daemon checks here if we already passed a full originator
|
||||||
* The batman daemon checks here if we already passed a full originator
|
|
||||||
* cycle in order to make sure we don't choose the first gateway we
|
* cycle in order to make sure we don't choose the first gateway we
|
||||||
* hear about. This check is based on the daemon's uptime which we
|
* hear about. This check is based on the daemon's uptime which we
|
||||||
* don't have.
|
* don't have.
|
||||||
**/
|
*/
|
||||||
if (atomic_read(&bat_priv->gw_mode) != GW_MODE_CLIENT)
|
if (atomic_read(&bat_priv->gw_mode) != GW_MODE_CLIENT)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -210,9 +209,9 @@ void gw_election(struct bat_priv *bat_priv)
|
||||||
if (next_gw) {
|
if (next_gw) {
|
||||||
sprintf(gw_addr, "%pM", next_gw->orig_node->orig);
|
sprintf(gw_addr, "%pM", next_gw->orig_node->orig);
|
||||||
|
|
||||||
router = orig_node_get_router(next_gw->orig_node);
|
router = batadv_orig_node_get_router(next_gw->orig_node);
|
||||||
if (!router) {
|
if (!router) {
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -220,19 +219,19 @@ void gw_election(struct bat_priv *bat_priv)
|
||||||
if ((curr_gw) && (!next_gw)) {
|
if ((curr_gw) && (!next_gw)) {
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
"Removing selected gateway - no gateway in range\n");
|
"Removing selected gateway - no gateway in range\n");
|
||||||
throw_uevent(bat_priv, UEV_GW, UEV_DEL, NULL);
|
batadv_throw_uevent(bat_priv, UEV_GW, UEV_DEL, NULL);
|
||||||
} else if ((!curr_gw) && (next_gw)) {
|
} else if ((!curr_gw) && (next_gw)) {
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
"Adding route to gateway %pM (gw_flags: %i, tq: %i)\n",
|
"Adding route to gateway %pM (gw_flags: %i, tq: %i)\n",
|
||||||
next_gw->orig_node->orig, next_gw->orig_node->gw_flags,
|
next_gw->orig_node->orig, next_gw->orig_node->gw_flags,
|
||||||
router->tq_avg);
|
router->tq_avg);
|
||||||
throw_uevent(bat_priv, UEV_GW, UEV_ADD, gw_addr);
|
batadv_throw_uevent(bat_priv, UEV_GW, UEV_ADD, gw_addr);
|
||||||
} else {
|
} else {
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
"Changing route to gateway %pM (gw_flags: %i, tq: %i)\n",
|
"Changing route to gateway %pM (gw_flags: %i, tq: %i)\n",
|
||||||
next_gw->orig_node->orig, next_gw->orig_node->gw_flags,
|
next_gw->orig_node->orig, next_gw->orig_node->gw_flags,
|
||||||
router->tq_avg);
|
router->tq_avg);
|
||||||
throw_uevent(bat_priv, UEV_GW, UEV_CHANGE, gw_addr);
|
batadv_throw_uevent(bat_priv, UEV_GW, UEV_CHANGE, gw_addr);
|
||||||
}
|
}
|
||||||
|
|
||||||
gw_select(bat_priv, next_gw);
|
gw_select(bat_priv, next_gw);
|
||||||
|
@ -243,20 +242,21 @@ out:
|
||||||
if (next_gw)
|
if (next_gw)
|
||||||
gw_node_free_ref(next_gw);
|
gw_node_free_ref(next_gw);
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gw_check_election(struct bat_priv *bat_priv, struct orig_node *orig_node)
|
void batadv_gw_check_election(struct bat_priv *bat_priv,
|
||||||
|
struct orig_node *orig_node)
|
||||||
{
|
{
|
||||||
struct orig_node *curr_gw_orig;
|
struct orig_node *curr_gw_orig;
|
||||||
struct neigh_node *router_gw = NULL, *router_orig = NULL;
|
struct neigh_node *router_gw = NULL, *router_orig = NULL;
|
||||||
uint8_t gw_tq_avg, orig_tq_avg;
|
uint8_t gw_tq_avg, orig_tq_avg;
|
||||||
|
|
||||||
curr_gw_orig = gw_get_selected_orig(bat_priv);
|
curr_gw_orig = batadv_gw_get_selected_orig(bat_priv);
|
||||||
if (!curr_gw_orig)
|
if (!curr_gw_orig)
|
||||||
goto deselect;
|
goto deselect;
|
||||||
|
|
||||||
router_gw = orig_node_get_router(curr_gw_orig);
|
router_gw = batadv_orig_node_get_router(curr_gw_orig);
|
||||||
if (!router_gw)
|
if (!router_gw)
|
||||||
goto deselect;
|
goto deselect;
|
||||||
|
|
||||||
|
@ -264,7 +264,7 @@ void gw_check_election(struct bat_priv *bat_priv, struct orig_node *orig_node)
|
||||||
if (curr_gw_orig == orig_node)
|
if (curr_gw_orig == orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
router_orig = orig_node_get_router(orig_node);
|
router_orig = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router_orig)
|
if (!router_orig)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -275,10 +275,9 @@ void gw_check_election(struct bat_priv *bat_priv, struct orig_node *orig_node)
|
||||||
if (orig_tq_avg < gw_tq_avg)
|
if (orig_tq_avg < gw_tq_avg)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/**
|
/* if the routing class is greater than 3 the value tells us how much
|
||||||
* if the routing class is greater than 3 the value tells us how much
|
|
||||||
* greater the TQ value of the new gateway must be
|
* greater the TQ value of the new gateway must be
|
||||||
**/
|
*/
|
||||||
if ((atomic_read(&bat_priv->gw_sel_class) > 3) &&
|
if ((atomic_read(&bat_priv->gw_sel_class) > 3) &&
|
||||||
(orig_tq_avg - gw_tq_avg < atomic_read(&bat_priv->gw_sel_class)))
|
(orig_tq_avg - gw_tq_avg < atomic_read(&bat_priv->gw_sel_class)))
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -288,14 +287,14 @@ void gw_check_election(struct bat_priv *bat_priv, struct orig_node *orig_node)
|
||||||
gw_tq_avg, orig_tq_avg);
|
gw_tq_avg, orig_tq_avg);
|
||||||
|
|
||||||
deselect:
|
deselect:
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
out:
|
out:
|
||||||
if (curr_gw_orig)
|
if (curr_gw_orig)
|
||||||
orig_node_free_ref(curr_gw_orig);
|
batadv_orig_node_free_ref(curr_gw_orig);
|
||||||
if (router_gw)
|
if (router_gw)
|
||||||
neigh_node_free_ref(router_gw);
|
batadv_neigh_node_free_ref(router_gw);
|
||||||
if (router_orig)
|
if (router_orig)
|
||||||
neigh_node_free_ref(router_orig);
|
batadv_neigh_node_free_ref(router_orig);
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -318,7 +317,7 @@ static void gw_node_add(struct bat_priv *bat_priv,
|
||||||
hlist_add_head_rcu(&gw_node->list, &bat_priv->gw_list);
|
hlist_add_head_rcu(&gw_node->list, &bat_priv->gw_list);
|
||||||
spin_unlock_bh(&bat_priv->gw_list_lock);
|
spin_unlock_bh(&bat_priv->gw_list_lock);
|
||||||
|
|
||||||
gw_bandwidth_to_kbit(new_gwflags, &down, &up);
|
batadv_gw_bandwidth_to_kbit(new_gwflags, &down, &up);
|
||||||
bat_dbg(DBG_BATMAN, bat_priv,
|
bat_dbg(DBG_BATMAN, bat_priv,
|
||||||
"Found new gateway %pM -> gw_class: %i - %i%s/%i%s\n",
|
"Found new gateway %pM -> gw_class: %i - %i%s/%i%s\n",
|
||||||
orig_node->orig, new_gwflags,
|
orig_node->orig, new_gwflags,
|
||||||
|
@ -328,14 +327,13 @@ static void gw_node_add(struct bat_priv *bat_priv,
|
||||||
(up > 2048 ? "MBit" : "KBit"));
|
(up > 2048 ? "MBit" : "KBit"));
|
||||||
}
|
}
|
||||||
|
|
||||||
void gw_node_update(struct bat_priv *bat_priv,
|
void batadv_gw_node_update(struct bat_priv *bat_priv,
|
||||||
struct orig_node *orig_node, uint8_t new_gwflags)
|
struct orig_node *orig_node, uint8_t new_gwflags)
|
||||||
{
|
{
|
||||||
struct hlist_node *node;
|
struct hlist_node *node;
|
||||||
struct gw_node *gw_node, *curr_gw;
|
struct gw_node *gw_node, *curr_gw;
|
||||||
|
|
||||||
/**
|
/* Note: We don't need a NULL check here, since curr_gw never gets
|
||||||
* Note: We don't need a NULL check here, since curr_gw never gets
|
|
||||||
* dereferenced. If curr_gw is NULL we also should not exit as we may
|
* dereferenced. If curr_gw is NULL we also should not exit as we may
|
||||||
* have this gateway in our list (duplication check!) even though we
|
* have this gateway in our list (duplication check!) even though we
|
||||||
* have no currently selected gateway.
|
* have no currently selected gateway.
|
||||||
|
@ -374,7 +372,7 @@ void gw_node_update(struct bat_priv *bat_priv,
|
||||||
goto unlock;
|
goto unlock;
|
||||||
|
|
||||||
deselect:
|
deselect:
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
unlock:
|
unlock:
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
|
|
||||||
|
@ -382,12 +380,13 @@ unlock:
|
||||||
gw_node_free_ref(curr_gw);
|
gw_node_free_ref(curr_gw);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gw_node_delete(struct bat_priv *bat_priv, struct orig_node *orig_node)
|
void batadv_gw_node_delete(struct bat_priv *bat_priv,
|
||||||
|
struct orig_node *orig_node)
|
||||||
{
|
{
|
||||||
gw_node_update(bat_priv, orig_node, 0);
|
batadv_gw_node_update(bat_priv, orig_node, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gw_node_purge(struct bat_priv *bat_priv)
|
void batadv_gw_node_purge(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct gw_node *gw_node, *curr_gw;
|
struct gw_node *gw_node, *curr_gw;
|
||||||
struct hlist_node *node, *node_tmp;
|
struct hlist_node *node, *node_tmp;
|
||||||
|
@ -416,15 +415,13 @@ void gw_node_purge(struct bat_priv *bat_priv)
|
||||||
|
|
||||||
/* gw_deselect() needs to acquire the gw_list_lock */
|
/* gw_deselect() needs to acquire the gw_list_lock */
|
||||||
if (do_deselect)
|
if (do_deselect)
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
|
|
||||||
if (curr_gw)
|
if (curr_gw)
|
||||||
gw_node_free_ref(curr_gw);
|
gw_node_free_ref(curr_gw);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* fails if orig_node has no router */
|
||||||
* fails if orig_node has no router
|
|
||||||
*/
|
|
||||||
static int _write_buffer_text(struct bat_priv *bat_priv, struct seq_file *seq,
|
static int _write_buffer_text(struct bat_priv *bat_priv, struct seq_file *seq,
|
||||||
const struct gw_node *gw_node)
|
const struct gw_node *gw_node)
|
||||||
{
|
{
|
||||||
|
@ -432,9 +429,9 @@ static int _write_buffer_text(struct bat_priv *bat_priv, struct seq_file *seq,
|
||||||
struct neigh_node *router;
|
struct neigh_node *router;
|
||||||
int down, up, ret = -1;
|
int down, up, ret = -1;
|
||||||
|
|
||||||
gw_bandwidth_to_kbit(gw_node->orig_node->gw_flags, &down, &up);
|
batadv_gw_bandwidth_to_kbit(gw_node->orig_node->gw_flags, &down, &up);
|
||||||
|
|
||||||
router = orig_node_get_router(gw_node->orig_node);
|
router = batadv_orig_node_get_router(gw_node->orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -451,14 +448,14 @@ static int _write_buffer_text(struct bat_priv *bat_priv, struct seq_file *seq,
|
||||||
(up > 2048 ? up / 1024 : up),
|
(up > 2048 ? up / 1024 : up),
|
||||||
(up > 2048 ? "MBit" : "KBit"));
|
(up > 2048 ? "MBit" : "KBit"));
|
||||||
|
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
if (curr_gw)
|
if (curr_gw)
|
||||||
gw_node_free_ref(curr_gw);
|
gw_node_free_ref(curr_gw);
|
||||||
out:
|
out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int gw_client_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_gw_client_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)seq->private;
|
struct net_device *net_dev = (struct net_device *)seq->private;
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
|
@ -530,12 +527,14 @@ static bool is_type_dhcprequest(struct sk_buff *skb, int header_len)
|
||||||
/* Access the dhcp option lists. Each entry is made up by:
|
/* Access the dhcp option lists. Each entry is made up by:
|
||||||
* - octet 1: option type
|
* - octet 1: option type
|
||||||
* - octet 2: option data len (only if type != 255 and 0)
|
* - octet 2: option data len (only if type != 255 and 0)
|
||||||
* - octet 3: option data */
|
* - octet 3: option data
|
||||||
|
*/
|
||||||
while (*p != 255 && !ret) {
|
while (*p != 255 && !ret) {
|
||||||
/* p now points to the first octet: option type */
|
/* p now points to the first octet: option type */
|
||||||
if (*p == 53) {
|
if (*p == 53) {
|
||||||
/* type 53 is the message type option.
|
/* type 53 is the message type option.
|
||||||
* Jump the len octet and go to the data octet */
|
* Jump the len octet and go to the data octet
|
||||||
|
*/
|
||||||
if (pkt_len < 2)
|
if (pkt_len < 2)
|
||||||
goto out;
|
goto out;
|
||||||
p += 2;
|
p += 2;
|
||||||
|
@ -568,7 +567,7 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool gw_is_dhcp_target(struct sk_buff *skb, unsigned int *header_len)
|
bool batadv_gw_is_dhcp_target(struct sk_buff *skb, unsigned int *header_len)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
struct iphdr *iphdr;
|
struct iphdr *iphdr;
|
||||||
|
@ -634,8 +633,8 @@ bool gw_is_dhcp_target(struct sk_buff *skb, unsigned int *header_len)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool gw_out_of_range(struct bat_priv *bat_priv,
|
bool batadv_gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
struct sk_buff *skb, struct ethhdr *ethhdr)
|
struct sk_buff *skb, struct ethhdr *ethhdr)
|
||||||
{
|
{
|
||||||
struct neigh_node *neigh_curr = NULL, *neigh_old = NULL;
|
struct neigh_node *neigh_curr = NULL, *neigh_old = NULL;
|
||||||
struct orig_node *orig_dst_node = NULL;
|
struct orig_node *orig_dst_node = NULL;
|
||||||
|
@ -644,12 +643,12 @@ bool gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
unsigned int header_len = 0;
|
unsigned int header_len = 0;
|
||||||
uint8_t curr_tq_avg;
|
uint8_t curr_tq_avg;
|
||||||
|
|
||||||
ret = gw_is_dhcp_target(skb, &header_len);
|
ret = batadv_gw_is_dhcp_target(skb, &header_len);
|
||||||
if (!ret)
|
if (!ret)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
orig_dst_node = transtable_search(bat_priv, ethhdr->h_source,
|
orig_dst_node = batadv_transtable_search(bat_priv, ethhdr->h_source,
|
||||||
ethhdr->h_dest);
|
ethhdr->h_dest);
|
||||||
if (!orig_dst_node)
|
if (!orig_dst_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -663,7 +662,8 @@ bool gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
switch (atomic_read(&bat_priv->gw_mode)) {
|
switch (atomic_read(&bat_priv->gw_mode)) {
|
||||||
case GW_MODE_SERVER:
|
case GW_MODE_SERVER:
|
||||||
/* If we are a GW then we are our best GW. We can artificially
|
/* If we are a GW then we are our best GW. We can artificially
|
||||||
* set the tq towards ourself as the maximum value */
|
* set the tq towards ourself as the maximum value
|
||||||
|
*/
|
||||||
curr_tq_avg = TQ_MAX_VALUE;
|
curr_tq_avg = TQ_MAX_VALUE;
|
||||||
break;
|
break;
|
||||||
case GW_MODE_CLIENT:
|
case GW_MODE_CLIENT:
|
||||||
|
@ -677,8 +677,10 @@ bool gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* If the dhcp packet has been sent to a different gw,
|
/* If the dhcp packet has been sent to a different gw,
|
||||||
* we have to evaluate whether the old gw is still
|
* we have to evaluate whether the old gw is still
|
||||||
* reliable enough */
|
* reliable enough
|
||||||
neigh_curr = find_router(bat_priv, curr_gw->orig_node, NULL);
|
*/
|
||||||
|
neigh_curr = batadv_find_router(bat_priv, curr_gw->orig_node,
|
||||||
|
NULL);
|
||||||
if (!neigh_curr)
|
if (!neigh_curr)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -689,7 +691,7 @@ bool gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
neigh_old = find_router(bat_priv, orig_dst_node, NULL);
|
neigh_old = batadv_find_router(bat_priv, orig_dst_node, NULL);
|
||||||
if (!neigh_old)
|
if (!neigh_old)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -698,12 +700,12 @@ bool gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (orig_dst_node)
|
if (orig_dst_node)
|
||||||
orig_node_free_ref(orig_dst_node);
|
batadv_orig_node_free_ref(orig_dst_node);
|
||||||
if (curr_gw)
|
if (curr_gw)
|
||||||
gw_node_free_ref(curr_gw);
|
gw_node_free_ref(curr_gw);
|
||||||
if (neigh_old)
|
if (neigh_old)
|
||||||
neigh_node_free_ref(neigh_old);
|
batadv_neigh_node_free_ref(neigh_old);
|
||||||
if (neigh_curr)
|
if (neigh_curr)
|
||||||
neigh_node_free_ref(neigh_curr);
|
batadv_neigh_node_free_ref(neigh_curr);
|
||||||
return out_of_range;
|
return out_of_range;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,23 +15,24 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_GATEWAY_CLIENT_H_
|
#ifndef _NET_BATMAN_ADV_GATEWAY_CLIENT_H_
|
||||||
#define _NET_BATMAN_ADV_GATEWAY_CLIENT_H_
|
#define _NET_BATMAN_ADV_GATEWAY_CLIENT_H_
|
||||||
|
|
||||||
void gw_deselect(struct bat_priv *bat_priv);
|
void batadv_gw_deselect(struct bat_priv *bat_priv);
|
||||||
void gw_election(struct bat_priv *bat_priv);
|
void batadv_gw_election(struct bat_priv *bat_priv);
|
||||||
struct orig_node *gw_get_selected_orig(struct bat_priv *bat_priv);
|
struct orig_node *batadv_gw_get_selected_orig(struct bat_priv *bat_priv);
|
||||||
void gw_check_election(struct bat_priv *bat_priv, struct orig_node *orig_node);
|
void batadv_gw_check_election(struct bat_priv *bat_priv,
|
||||||
void gw_node_update(struct bat_priv *bat_priv,
|
struct orig_node *orig_node);
|
||||||
struct orig_node *orig_node, uint8_t new_gwflags);
|
void batadv_gw_node_update(struct bat_priv *bat_priv,
|
||||||
void gw_node_delete(struct bat_priv *bat_priv, struct orig_node *orig_node);
|
struct orig_node *orig_node, uint8_t new_gwflags);
|
||||||
void gw_node_purge(struct bat_priv *bat_priv);
|
void batadv_gw_node_delete(struct bat_priv *bat_priv,
|
||||||
int gw_client_seq_print_text(struct seq_file *seq, void *offset);
|
struct orig_node *orig_node);
|
||||||
bool gw_is_dhcp_target(struct sk_buff *skb, unsigned int *header_len);
|
void batadv_gw_node_purge(struct bat_priv *bat_priv);
|
||||||
bool gw_out_of_range(struct bat_priv *bat_priv,
|
int batadv_gw_client_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
struct sk_buff *skb, struct ethhdr *ethhdr);
|
bool batadv_gw_is_dhcp_target(struct sk_buff *skb, unsigned int *header_len);
|
||||||
|
bool batadv_gw_out_of_range(struct bat_priv *bat_priv,
|
||||||
|
struct sk_buff *skb, struct ethhdr *ethhdr);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_GATEWAY_CLIENT_H_ */
|
#endif /* _NET_BATMAN_ADV_GATEWAY_CLIENT_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -59,7 +57,7 @@ static void kbit_to_gw_bandwidth(int down, int up, long *gw_srv_class)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* returns the up and downspeeds in kbit, calculated from the class */
|
/* returns the up and downspeeds in kbit, calculated from the class */
|
||||||
void gw_bandwidth_to_kbit(uint8_t gw_srv_class, int *down, int *up)
|
void batadv_gw_bandwidth_to_kbit(uint8_t gw_srv_class, int *down, int *up)
|
||||||
{
|
{
|
||||||
int sbit = (gw_srv_class & 0x80) >> 7;
|
int sbit = (gw_srv_class & 0x80) >> 7;
|
||||||
int dpart = (gw_srv_class & 0x78) >> 3;
|
int dpart = (gw_srv_class & 0x78) >> 3;
|
||||||
|
@ -136,7 +134,8 @@ static bool parse_gw_bandwidth(struct net_device *net_dev, char *buff,
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t gw_bandwidth_set(struct net_device *net_dev, char *buff, size_t count)
|
ssize_t batadv_gw_bandwidth_set(struct net_device *net_dev, char *buff,
|
||||||
|
size_t count)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
long gw_bandwidth_tmp = 0;
|
long gw_bandwidth_tmp = 0;
|
||||||
|
@ -155,17 +154,16 @@ ssize_t gw_bandwidth_set(struct net_device *net_dev, char *buff, size_t count)
|
||||||
|
|
||||||
kbit_to_gw_bandwidth(down, up, &gw_bandwidth_tmp);
|
kbit_to_gw_bandwidth(down, up, &gw_bandwidth_tmp);
|
||||||
|
|
||||||
/**
|
/* the gw bandwidth we guessed above might not match the given
|
||||||
* the gw bandwidth we guessed above might not match the given
|
|
||||||
* speeds, hence we need to calculate it back to show the number
|
* speeds, hence we need to calculate it back to show the number
|
||||||
* that is going to be propagated
|
* that is going to be propagated
|
||||||
**/
|
*/
|
||||||
gw_bandwidth_to_kbit((uint8_t)gw_bandwidth_tmp, &down, &up);
|
batadv_gw_bandwidth_to_kbit((uint8_t)gw_bandwidth_tmp, &down, &up);
|
||||||
|
|
||||||
if (atomic_read(&bat_priv->gw_bandwidth) == gw_bandwidth_tmp)
|
if (atomic_read(&bat_priv->gw_bandwidth) == gw_bandwidth_tmp)
|
||||||
return count;
|
return count;
|
||||||
|
|
||||||
gw_deselect(bat_priv);
|
batadv_gw_deselect(bat_priv);
|
||||||
bat_info(net_dev,
|
bat_info(net_dev,
|
||||||
"Changing gateway bandwidth from: '%i' to: '%ld' (propagating: %d%s/%d%s)\n",
|
"Changing gateway bandwidth from: '%i' to: '%ld' (propagating: %d%s/%d%s)\n",
|
||||||
atomic_read(&bat_priv->gw_bandwidth), gw_bandwidth_tmp,
|
atomic_read(&bat_priv->gw_bandwidth), gw_bandwidth_tmp,
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_GATEWAY_COMMON_H_
|
#ifndef _NET_BATMAN_ADV_GATEWAY_COMMON_H_
|
||||||
|
@ -32,7 +30,8 @@ enum gw_modes {
|
||||||
#define GW_MODE_CLIENT_NAME "client"
|
#define GW_MODE_CLIENT_NAME "client"
|
||||||
#define GW_MODE_SERVER_NAME "server"
|
#define GW_MODE_SERVER_NAME "server"
|
||||||
|
|
||||||
void gw_bandwidth_to_kbit(uint8_t gw_class, int *down, int *up);
|
void batadv_gw_bandwidth_to_kbit(uint8_t gw_class, int *down, int *up);
|
||||||
ssize_t gw_bandwidth_set(struct net_device *net_dev, char *buff, size_t count);
|
ssize_t batadv_gw_bandwidth_set(struct net_device *net_dev, char *buff,
|
||||||
|
size_t count);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_GATEWAY_COMMON_H_ */
|
#endif /* _NET_BATMAN_ADV_GATEWAY_COMMON_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -32,7 +30,7 @@
|
||||||
|
|
||||||
#include <linux/if_arp.h>
|
#include <linux/if_arp.h>
|
||||||
|
|
||||||
void hardif_free_rcu(struct rcu_head *rcu)
|
void batadv_hardif_free_rcu(struct rcu_head *rcu)
|
||||||
{
|
{
|
||||||
struct hard_iface *hard_iface;
|
struct hard_iface *hard_iface;
|
||||||
|
|
||||||
|
@ -41,12 +39,12 @@ void hardif_free_rcu(struct rcu_head *rcu)
|
||||||
kfree(hard_iface);
|
kfree(hard_iface);
|
||||||
}
|
}
|
||||||
|
|
||||||
struct hard_iface *hardif_get_by_netdev(const struct net_device *net_dev)
|
struct hard_iface *batadv_hardif_get_by_netdev(const struct net_device *net_dev)
|
||||||
{
|
{
|
||||||
struct hard_iface *hard_iface;
|
struct hard_iface *hard_iface;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if (hard_iface->net_dev == net_dev &&
|
if (hard_iface->net_dev == net_dev &&
|
||||||
atomic_inc_not_zero(&hard_iface->refcount))
|
atomic_inc_not_zero(&hard_iface->refcount))
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -71,13 +69,9 @@ static int is_valid_iface(const struct net_device *net_dev)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
/* no batman over batman */
|
/* no batman over batman */
|
||||||
if (softif_is_valid(net_dev))
|
if (batadv_softif_is_valid(net_dev))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
/* Device is being bridged */
|
|
||||||
/* if (net_dev->priv_flags & IFF_BRIDGE_PORT)
|
|
||||||
return 0; */
|
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -86,7 +80,7 @@ static struct hard_iface *hardif_get_active(const struct net_device *soft_iface)
|
||||||
struct hard_iface *hard_iface;
|
struct hard_iface *hard_iface;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if (hard_iface->soft_iface != soft_iface)
|
if (hard_iface->soft_iface != soft_iface)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -118,7 +112,7 @@ static void primary_if_update_addr(struct bat_priv *bat_priv,
|
||||||
memcpy(vis_packet->sender_orig,
|
memcpy(vis_packet->sender_orig,
|
||||||
primary_if->net_dev->dev_addr, ETH_ALEN);
|
primary_if->net_dev->dev_addr, ETH_ALEN);
|
||||||
|
|
||||||
bla_update_orig_address(bat_priv, primary_if, oldif);
|
batadv_bla_update_orig_address(bat_priv, primary_if, oldif);
|
||||||
out:
|
out:
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
|
@ -161,7 +155,7 @@ static void check_known_mac_addr(const struct net_device *net_dev)
|
||||||
const struct hard_iface *hard_iface;
|
const struct hard_iface *hard_iface;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if ((hard_iface->if_status != IF_ACTIVE) &&
|
if ((hard_iface->if_status != IF_ACTIVE) &&
|
||||||
(hard_iface->if_status != IF_TO_BE_ACTIVATED))
|
(hard_iface->if_status != IF_TO_BE_ACTIVATED))
|
||||||
continue;
|
continue;
|
||||||
|
@ -180,19 +174,20 @@ static void check_known_mac_addr(const struct net_device *net_dev)
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
int hardif_min_mtu(struct net_device *soft_iface)
|
int batadv_hardif_min_mtu(struct net_device *soft_iface)
|
||||||
{
|
{
|
||||||
const struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
const struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
||||||
const struct hard_iface *hard_iface;
|
const struct hard_iface *hard_iface;
|
||||||
/* allow big frames if all devices are capable to do so
|
/* allow big frames if all devices are capable to do so
|
||||||
* (have MTU > 1500 + BAT_HEADER_LEN) */
|
* (have MTU > 1500 + BAT_HEADER_LEN)
|
||||||
|
*/
|
||||||
int min_mtu = ETH_DATA_LEN;
|
int min_mtu = ETH_DATA_LEN;
|
||||||
|
|
||||||
if (atomic_read(&bat_priv->fragmentation))
|
if (atomic_read(&bat_priv->fragmentation))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if ((hard_iface->if_status != IF_ACTIVE) &&
|
if ((hard_iface->if_status != IF_ACTIVE) &&
|
||||||
(hard_iface->if_status != IF_TO_BE_ACTIVATED))
|
(hard_iface->if_status != IF_TO_BE_ACTIVATED))
|
||||||
continue;
|
continue;
|
||||||
|
@ -209,11 +204,11 @@ out:
|
||||||
}
|
}
|
||||||
|
|
||||||
/* adjusts the MTU if a new interface with a smaller MTU appeared. */
|
/* adjusts the MTU if a new interface with a smaller MTU appeared. */
|
||||||
void update_min_mtu(struct net_device *soft_iface)
|
void batadv_update_min_mtu(struct net_device *soft_iface)
|
||||||
{
|
{
|
||||||
int min_mtu;
|
int min_mtu;
|
||||||
|
|
||||||
min_mtu = hardif_min_mtu(soft_iface);
|
min_mtu = batadv_hardif_min_mtu(soft_iface);
|
||||||
if (soft_iface->mtu != min_mtu)
|
if (soft_iface->mtu != min_mtu)
|
||||||
soft_iface->mtu = min_mtu;
|
soft_iface->mtu = min_mtu;
|
||||||
}
|
}
|
||||||
|
@ -231,8 +226,7 @@ static void hardif_activate_interface(struct hard_iface *hard_iface)
|
||||||
bat_priv->bat_algo_ops->bat_iface_update_mac(hard_iface);
|
bat_priv->bat_algo_ops->bat_iface_update_mac(hard_iface);
|
||||||
hard_iface->if_status = IF_TO_BE_ACTIVATED;
|
hard_iface->if_status = IF_TO_BE_ACTIVATED;
|
||||||
|
|
||||||
/**
|
/* the first active interface becomes our primary interface or
|
||||||
* the first active interface becomes our primary interface or
|
|
||||||
* the next active interface after the old primary interface was removed
|
* the next active interface after the old primary interface was removed
|
||||||
*/
|
*/
|
||||||
primary_if = primary_if_get_selected(bat_priv);
|
primary_if = primary_if_get_selected(bat_priv);
|
||||||
|
@ -242,7 +236,7 @@ static void hardif_activate_interface(struct hard_iface *hard_iface)
|
||||||
bat_info(hard_iface->soft_iface, "Interface activated: %s\n",
|
bat_info(hard_iface->soft_iface, "Interface activated: %s\n",
|
||||||
hard_iface->net_dev->name);
|
hard_iface->net_dev->name);
|
||||||
|
|
||||||
update_min_mtu(hard_iface->soft_iface);
|
batadv_update_min_mtu(hard_iface->soft_iface);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
|
@ -260,11 +254,11 @@ static void hardif_deactivate_interface(struct hard_iface *hard_iface)
|
||||||
bat_info(hard_iface->soft_iface, "Interface deactivated: %s\n",
|
bat_info(hard_iface->soft_iface, "Interface deactivated: %s\n",
|
||||||
hard_iface->net_dev->name);
|
hard_iface->net_dev->name);
|
||||||
|
|
||||||
update_min_mtu(hard_iface->soft_iface);
|
batadv_update_min_mtu(hard_iface->soft_iface);
|
||||||
}
|
}
|
||||||
|
|
||||||
int hardif_enable_interface(struct hard_iface *hard_iface,
|
int batadv_hardif_enable_interface(struct hard_iface *hard_iface,
|
||||||
const char *iface_name)
|
const char *iface_name)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv;
|
struct bat_priv *bat_priv;
|
||||||
struct net_device *soft_iface;
|
struct net_device *soft_iface;
|
||||||
|
@ -284,7 +278,7 @@ int hardif_enable_interface(struct hard_iface *hard_iface,
|
||||||
soft_iface = dev_get_by_name(&init_net, iface_name);
|
soft_iface = dev_get_by_name(&init_net, iface_name);
|
||||||
|
|
||||||
if (!soft_iface) {
|
if (!soft_iface) {
|
||||||
soft_iface = softif_create(iface_name);
|
soft_iface = batadv_softif_create(iface_name);
|
||||||
|
|
||||||
if (!soft_iface) {
|
if (!soft_iface) {
|
||||||
ret = -ENOMEM;
|
ret = -ENOMEM;
|
||||||
|
@ -295,7 +289,7 @@ int hardif_enable_interface(struct hard_iface *hard_iface,
|
||||||
dev_hold(soft_iface);
|
dev_hold(soft_iface);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!softif_is_valid(soft_iface)) {
|
if (!batadv_softif_is_valid(soft_iface)) {
|
||||||
pr_err("Can't create batman mesh interface %s: already exists as regular interface\n",
|
pr_err("Can't create batman mesh interface %s: already exists as regular interface\n",
|
||||||
soft_iface->name);
|
soft_iface->name);
|
||||||
ret = -EINVAL;
|
ret = -EINVAL;
|
||||||
|
@ -312,10 +306,10 @@ int hardif_enable_interface(struct hard_iface *hard_iface,
|
||||||
hard_iface->if_num = bat_priv->num_ifaces;
|
hard_iface->if_num = bat_priv->num_ifaces;
|
||||||
bat_priv->num_ifaces++;
|
bat_priv->num_ifaces++;
|
||||||
hard_iface->if_status = IF_INACTIVE;
|
hard_iface->if_status = IF_INACTIVE;
|
||||||
orig_hash_add_if(hard_iface, bat_priv->num_ifaces);
|
batadv_orig_hash_add_if(hard_iface, bat_priv->num_ifaces);
|
||||||
|
|
||||||
hard_iface->batman_adv_ptype.type = __constant_htons(ETH_P_BATMAN);
|
hard_iface->batman_adv_ptype.type = __constant_htons(ETH_P_BATMAN);
|
||||||
hard_iface->batman_adv_ptype.func = batman_skb_recv;
|
hard_iface->batman_adv_ptype.func = batadv_batman_skb_recv;
|
||||||
hard_iface->batman_adv_ptype.dev = hard_iface->net_dev;
|
hard_iface->batman_adv_ptype.dev = hard_iface->net_dev;
|
||||||
dev_add_pack(&hard_iface->batman_adv_ptype);
|
dev_add_pack(&hard_iface->batman_adv_ptype);
|
||||||
|
|
||||||
|
@ -345,7 +339,7 @@ int hardif_enable_interface(struct hard_iface *hard_iface,
|
||||||
hard_iface->net_dev->name);
|
hard_iface->net_dev->name);
|
||||||
|
|
||||||
/* begin scheduling originator messages on that interface */
|
/* begin scheduling originator messages on that interface */
|
||||||
schedule_bat_ogm(hard_iface);
|
batadv_schedule_bat_ogm(hard_iface);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -357,7 +351,7 @@ err:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void hardif_disable_interface(struct hard_iface *hard_iface)
|
void batadv_hardif_disable_interface(struct hard_iface *hard_iface)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
||||||
struct hard_iface *primary_if = NULL;
|
struct hard_iface *primary_if = NULL;
|
||||||
|
@ -373,7 +367,7 @@ void hardif_disable_interface(struct hard_iface *hard_iface)
|
||||||
dev_remove_pack(&hard_iface->batman_adv_ptype);
|
dev_remove_pack(&hard_iface->batman_adv_ptype);
|
||||||
|
|
||||||
bat_priv->num_ifaces--;
|
bat_priv->num_ifaces--;
|
||||||
orig_hash_del_if(hard_iface, bat_priv->num_ifaces);
|
batadv_orig_hash_del_if(hard_iface, bat_priv->num_ifaces);
|
||||||
|
|
||||||
primary_if = primary_if_get_selected(bat_priv);
|
primary_if = primary_if_get_selected(bat_priv);
|
||||||
if (hard_iface == primary_if) {
|
if (hard_iface == primary_if) {
|
||||||
|
@ -390,13 +384,13 @@ void hardif_disable_interface(struct hard_iface *hard_iface)
|
||||||
hard_iface->if_status = IF_NOT_IN_USE;
|
hard_iface->if_status = IF_NOT_IN_USE;
|
||||||
|
|
||||||
/* delete all references to this hard_iface */
|
/* delete all references to this hard_iface */
|
||||||
purge_orig_ref(bat_priv);
|
batadv_purge_orig_ref(bat_priv);
|
||||||
purge_outstanding_packets(bat_priv, hard_iface);
|
batadv_purge_outstanding_packets(bat_priv, hard_iface);
|
||||||
dev_put(hard_iface->soft_iface);
|
dev_put(hard_iface->soft_iface);
|
||||||
|
|
||||||
/* nobody uses this interface anymore */
|
/* nobody uses this interface anymore */
|
||||||
if (!bat_priv->num_ifaces)
|
if (!bat_priv->num_ifaces)
|
||||||
softif_destroy(hard_iface->soft_iface);
|
batadv_softif_destroy(hard_iface->soft_iface);
|
||||||
|
|
||||||
hard_iface->soft_iface = NULL;
|
hard_iface->soft_iface = NULL;
|
||||||
hardif_free_ref(hard_iface);
|
hardif_free_ref(hard_iface);
|
||||||
|
@ -423,7 +417,7 @@ static struct hard_iface *hardif_add_interface(struct net_device *net_dev)
|
||||||
if (!hard_iface)
|
if (!hard_iface)
|
||||||
goto release_dev;
|
goto release_dev;
|
||||||
|
|
||||||
ret = sysfs_add_hardif(&hard_iface->hardif_obj, net_dev);
|
ret = batadv_sysfs_add_hardif(&hard_iface->hardif_obj, net_dev);
|
||||||
if (ret)
|
if (ret)
|
||||||
goto free_if;
|
goto free_if;
|
||||||
|
|
||||||
|
@ -436,10 +430,9 @@ static struct hard_iface *hardif_add_interface(struct net_device *net_dev)
|
||||||
atomic_set(&hard_iface->refcount, 2);
|
atomic_set(&hard_iface->refcount, 2);
|
||||||
|
|
||||||
check_known_mac_addr(hard_iface->net_dev);
|
check_known_mac_addr(hard_iface->net_dev);
|
||||||
list_add_tail_rcu(&hard_iface->list, &hardif_list);
|
list_add_tail_rcu(&hard_iface->list, &batadv_hardif_list);
|
||||||
|
|
||||||
/**
|
/* This can't be called via a bat_priv callback because
|
||||||
* This can't be called via a bat_priv callback because
|
|
||||||
* we have no bat_priv yet.
|
* we have no bat_priv yet.
|
||||||
*/
|
*/
|
||||||
atomic_set(&hard_iface->seqno, 1);
|
atomic_set(&hard_iface->seqno, 1);
|
||||||
|
@ -461,23 +454,23 @@ static void hardif_remove_interface(struct hard_iface *hard_iface)
|
||||||
|
|
||||||
/* first deactivate interface */
|
/* first deactivate interface */
|
||||||
if (hard_iface->if_status != IF_NOT_IN_USE)
|
if (hard_iface->if_status != IF_NOT_IN_USE)
|
||||||
hardif_disable_interface(hard_iface);
|
batadv_hardif_disable_interface(hard_iface);
|
||||||
|
|
||||||
if (hard_iface->if_status != IF_NOT_IN_USE)
|
if (hard_iface->if_status != IF_NOT_IN_USE)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
hard_iface->if_status = IF_TO_BE_REMOVED;
|
hard_iface->if_status = IF_TO_BE_REMOVED;
|
||||||
sysfs_del_hardif(&hard_iface->hardif_obj);
|
batadv_sysfs_del_hardif(&hard_iface->hardif_obj);
|
||||||
hardif_free_ref(hard_iface);
|
hardif_free_ref(hard_iface);
|
||||||
}
|
}
|
||||||
|
|
||||||
void hardif_remove_interfaces(void)
|
void batadv_hardif_remove_interfaces(void)
|
||||||
{
|
{
|
||||||
struct hard_iface *hard_iface, *hard_iface_tmp;
|
struct hard_iface *hard_iface, *hard_iface_tmp;
|
||||||
|
|
||||||
rtnl_lock();
|
rtnl_lock();
|
||||||
list_for_each_entry_safe(hard_iface, hard_iface_tmp,
|
list_for_each_entry_safe(hard_iface, hard_iface_tmp,
|
||||||
&hardif_list, list) {
|
&batadv_hardif_list, list) {
|
||||||
list_del_rcu(&hard_iface->list);
|
list_del_rcu(&hard_iface->list);
|
||||||
hardif_remove_interface(hard_iface);
|
hardif_remove_interface(hard_iface);
|
||||||
}
|
}
|
||||||
|
@ -488,7 +481,7 @@ static int hard_if_event(struct notifier_block *this,
|
||||||
unsigned long event, void *ptr)
|
unsigned long event, void *ptr)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = ptr;
|
struct net_device *net_dev = ptr;
|
||||||
struct hard_iface *hard_iface = hardif_get_by_netdev(net_dev);
|
struct hard_iface *hard_iface = batadv_hardif_get_by_netdev(net_dev);
|
||||||
struct hard_iface *primary_if = NULL;
|
struct hard_iface *primary_if = NULL;
|
||||||
struct bat_priv *bat_priv;
|
struct bat_priv *bat_priv;
|
||||||
|
|
||||||
|
@ -513,7 +506,7 @@ static int hard_if_event(struct notifier_block *this,
|
||||||
break;
|
break;
|
||||||
case NETDEV_CHANGEMTU:
|
case NETDEV_CHANGEMTU:
|
||||||
if (hard_iface->soft_iface)
|
if (hard_iface->soft_iface)
|
||||||
update_min_mtu(hard_iface->soft_iface);
|
batadv_update_min_mtu(hard_iface->soft_iface);
|
||||||
break;
|
break;
|
||||||
case NETDEV_CHANGEADDR:
|
case NETDEV_CHANGEADDR:
|
||||||
if (hard_iface->if_status == IF_NOT_IN_USE)
|
if (hard_iface->if_status == IF_NOT_IN_USE)
|
||||||
|
@ -544,8 +537,9 @@ out:
|
||||||
}
|
}
|
||||||
|
|
||||||
/* This function returns true if the interface represented by ifindex is a
|
/* This function returns true if the interface represented by ifindex is a
|
||||||
* 802.11 wireless device */
|
* 802.11 wireless device
|
||||||
bool is_wifi_iface(int ifindex)
|
*/
|
||||||
|
bool batadv_is_wifi_iface(int ifindex)
|
||||||
{
|
{
|
||||||
struct net_device *net_device = NULL;
|
struct net_device *net_device = NULL;
|
||||||
bool ret = false;
|
bool ret = false;
|
||||||
|
@ -559,7 +553,8 @@ bool is_wifi_iface(int ifindex)
|
||||||
|
|
||||||
#ifdef CONFIG_WIRELESS_EXT
|
#ifdef CONFIG_WIRELESS_EXT
|
||||||
/* pre-cfg80211 drivers have to implement WEXT, so it is possible to
|
/* pre-cfg80211 drivers have to implement WEXT, so it is possible to
|
||||||
* check for wireless_handlers != NULL */
|
* check for wireless_handlers != NULL
|
||||||
|
*/
|
||||||
if (net_device->wireless_handlers)
|
if (net_device->wireless_handlers)
|
||||||
ret = true;
|
ret = true;
|
||||||
else
|
else
|
||||||
|
@ -573,6 +568,6 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct notifier_block hard_if_notifier = {
|
struct notifier_block batadv_hard_if_notifier = {
|
||||||
.notifier_call = hard_if_event,
|
.notifier_call = hard_if_event,
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_HARD_INTERFACE_H_
|
#ifndef _NET_BATMAN_ADV_HARD_INTERFACE_H_
|
||||||
|
@ -31,23 +29,23 @@ enum hard_if_state {
|
||||||
IF_I_WANT_YOU
|
IF_I_WANT_YOU
|
||||||
};
|
};
|
||||||
|
|
||||||
extern struct notifier_block hard_if_notifier;
|
extern struct notifier_block batadv_hard_if_notifier;
|
||||||
|
|
||||||
struct hard_iface*
|
struct hard_iface*
|
||||||
hardif_get_by_netdev(const struct net_device *net_dev);
|
batadv_hardif_get_by_netdev(const struct net_device *net_dev);
|
||||||
int hardif_enable_interface(struct hard_iface *hard_iface,
|
int batadv_hardif_enable_interface(struct hard_iface *hard_iface,
|
||||||
const char *iface_name);
|
const char *iface_name);
|
||||||
void hardif_disable_interface(struct hard_iface *hard_iface);
|
void batadv_hardif_disable_interface(struct hard_iface *hard_iface);
|
||||||
void hardif_remove_interfaces(void);
|
void batadv_hardif_remove_interfaces(void);
|
||||||
int hardif_min_mtu(struct net_device *soft_iface);
|
int batadv_hardif_min_mtu(struct net_device *soft_iface);
|
||||||
void update_min_mtu(struct net_device *soft_iface);
|
void batadv_update_min_mtu(struct net_device *soft_iface);
|
||||||
void hardif_free_rcu(struct rcu_head *rcu);
|
void batadv_hardif_free_rcu(struct rcu_head *rcu);
|
||||||
bool is_wifi_iface(int ifindex);
|
bool batadv_is_wifi_iface(int ifindex);
|
||||||
|
|
||||||
static inline void hardif_free_ref(struct hard_iface *hard_iface)
|
static inline void hardif_free_ref(struct hard_iface *hard_iface)
|
||||||
{
|
{
|
||||||
if (atomic_dec_and_test(&hard_iface->refcount))
|
if (atomic_dec_and_test(&hard_iface->refcount))
|
||||||
call_rcu(&hard_iface->rcu, hardif_free_rcu);
|
call_rcu(&hard_iface->rcu, batadv_hardif_free_rcu);
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline struct hard_iface *primary_if_get_selected(
|
static inline struct hard_iface *primary_if_get_selected(
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich, Marek Lindner
|
* Simon Wunderlich, Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -34,7 +32,7 @@ static void hash_init(struct hashtable_t *hash)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* free only the hashtable and the hash itself. */
|
/* free only the hashtable and the hash itself. */
|
||||||
void hash_destroy(struct hashtable_t *hash)
|
void batadv_hash_destroy(struct hashtable_t *hash)
|
||||||
{
|
{
|
||||||
kfree(hash->list_locks);
|
kfree(hash->list_locks);
|
||||||
kfree(hash->table);
|
kfree(hash->table);
|
||||||
|
@ -42,7 +40,7 @@ void hash_destroy(struct hashtable_t *hash)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* allocates and clears the hash */
|
/* allocates and clears the hash */
|
||||||
struct hashtable_t *hash_new(uint32_t size)
|
struct hashtable_t *batadv_hash_new(uint32_t size)
|
||||||
{
|
{
|
||||||
struct hashtable_t *hash;
|
struct hashtable_t *hash;
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich, Marek Lindner
|
* Simon Wunderlich, Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_HASH_H_
|
#ifndef _NET_BATMAN_ADV_HASH_H_
|
||||||
|
@ -24,15 +22,15 @@
|
||||||
|
|
||||||
#include <linux/list.h>
|
#include <linux/list.h>
|
||||||
|
|
||||||
/* callback to a compare function. should
|
/* callback to a compare function. should compare 2 element datas for their
|
||||||
* compare 2 element datas for their keys,
|
* keys, return 0 if same and not 0 if not same
|
||||||
* return 0 if same and not 0 if not
|
*/
|
||||||
* same */
|
|
||||||
typedef int (*hashdata_compare_cb)(const struct hlist_node *, const void *);
|
typedef int (*hashdata_compare_cb)(const struct hlist_node *, const void *);
|
||||||
|
|
||||||
/* the hashfunction, should return an index
|
/* the hashfunction, should return an index
|
||||||
* based on the key in the data of the first
|
* based on the key in the data of the first
|
||||||
* argument and the size the second */
|
* argument and the size the second
|
||||||
|
*/
|
||||||
typedef uint32_t (*hashdata_choose_cb)(const void *, uint32_t);
|
typedef uint32_t (*hashdata_choose_cb)(const void *, uint32_t);
|
||||||
typedef void (*hashdata_free_cb)(struct hlist_node *, void *);
|
typedef void (*hashdata_free_cb)(struct hlist_node *, void *);
|
||||||
|
|
||||||
|
@ -43,18 +41,19 @@ struct hashtable_t {
|
||||||
};
|
};
|
||||||
|
|
||||||
/* allocates and clears the hash */
|
/* allocates and clears the hash */
|
||||||
struct hashtable_t *hash_new(uint32_t size);
|
struct hashtable_t *batadv_hash_new(uint32_t size);
|
||||||
|
|
||||||
/* set class key for all locks */
|
/* set class key for all locks */
|
||||||
void batadv_hash_set_lock_class(struct hashtable_t *hash,
|
void batadv_hash_set_lock_class(struct hashtable_t *hash,
|
||||||
struct lock_class_key *key);
|
struct lock_class_key *key);
|
||||||
|
|
||||||
/* free only the hashtable and the hash itself. */
|
/* free only the hashtable and the hash itself. */
|
||||||
void hash_destroy(struct hashtable_t *hash);
|
void batadv_hash_destroy(struct hashtable_t *hash);
|
||||||
|
|
||||||
/* remove the hash structure. if hashdata_free_cb != NULL, this function will be
|
/* remove the hash structure. if hashdata_free_cb != NULL, this function will be
|
||||||
* called to remove the elements inside of the hash. if you don't remove the
|
* called to remove the elements inside of the hash. if you don't remove the
|
||||||
* elements, memory might be leaked. */
|
* elements, memory might be leaked.
|
||||||
|
*/
|
||||||
static inline void hash_delete(struct hashtable_t *hash,
|
static inline void hash_delete(struct hashtable_t *hash,
|
||||||
hashdata_free_cb free_cb, void *arg)
|
hashdata_free_cb free_cb, void *arg)
|
||||||
{
|
{
|
||||||
|
@ -77,11 +76,10 @@ static inline void hash_delete(struct hashtable_t *hash,
|
||||||
spin_unlock_bh(list_lock);
|
spin_unlock_bh(list_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
hash_destroy(hash);
|
batadv_hash_destroy(hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* hash_add - adds data to the hashtable
|
||||||
* hash_add - adds data to the hashtable
|
|
||||||
* @hash: storage hash table
|
* @hash: storage hash table
|
||||||
* @compare: callback to determine if 2 hash elements are identical
|
* @compare: callback to determine if 2 hash elements are identical
|
||||||
* @choose: callback calculating the hash index
|
* @choose: callback calculating the hash index
|
||||||
|
@ -91,7 +89,6 @@ static inline void hash_delete(struct hashtable_t *hash,
|
||||||
* Returns 0 on success, 1 if the element already is in the hash
|
* Returns 0 on success, 1 if the element already is in the hash
|
||||||
* and -1 on error.
|
* and -1 on error.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static inline int hash_add(struct hashtable_t *hash,
|
static inline int hash_add(struct hashtable_t *hash,
|
||||||
hashdata_compare_cb compare,
|
hashdata_compare_cb compare,
|
||||||
hashdata_choose_cb choose,
|
hashdata_choose_cb choose,
|
||||||
|
@ -134,7 +131,8 @@ out:
|
||||||
/* removes data from hash, if found. returns pointer do data on success, so you
|
/* removes data from hash, if found. returns pointer do data on success, so you
|
||||||
* can remove the used structure yourself, or NULL on error . data could be the
|
* can remove the used structure yourself, or NULL on error . data could be the
|
||||||
* structure you use with just the key filled, we just need the key for
|
* structure you use with just the key filled, we just need the key for
|
||||||
* comparing. */
|
* comparing.
|
||||||
|
*/
|
||||||
static inline void *hash_remove(struct hashtable_t *hash,
|
static inline void *hash_remove(struct hashtable_t *hash,
|
||||||
hashdata_compare_cb compare,
|
hashdata_compare_cb compare,
|
||||||
hashdata_choose_cb choose, void *data)
|
hashdata_choose_cb choose, void *data)
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -34,7 +32,7 @@ static void bat_socket_add_packet(struct socket_client *socket_client,
|
||||||
struct icmp_packet_rr *icmp_packet,
|
struct icmp_packet_rr *icmp_packet,
|
||||||
size_t icmp_len);
|
size_t icmp_len);
|
||||||
|
|
||||||
void bat_socket_init(void)
|
void batadv_socket_init(void)
|
||||||
{
|
{
|
||||||
memset(socket_client_hash, 0, sizeof(socket_client_hash));
|
memset(socket_client_hash, 0, sizeof(socket_client_hash));
|
||||||
}
|
}
|
||||||
|
@ -73,7 +71,7 @@ static int bat_socket_open(struct inode *inode, struct file *file)
|
||||||
|
|
||||||
file->private_data = socket_client;
|
file->private_data = socket_client;
|
||||||
|
|
||||||
inc_module_count();
|
batadv_inc_module_count();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -98,7 +96,7 @@ static int bat_socket_release(struct inode *inode, struct file *file)
|
||||||
spin_unlock_bh(&socket_client->lock);
|
spin_unlock_bh(&socket_client->lock);
|
||||||
|
|
||||||
kfree(socket_client);
|
kfree(socket_client);
|
||||||
dec_module_count();
|
batadv_dec_module_count();
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -219,7 +217,7 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto dst_unreach;
|
goto dst_unreach;
|
||||||
|
|
||||||
neigh_node = orig_node_get_router(orig_node);
|
neigh_node = batadv_orig_node_get_router(orig_node);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto dst_unreach;
|
goto dst_unreach;
|
||||||
|
|
||||||
|
@ -236,7 +234,7 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
|
||||||
memcpy(icmp_packet->rr,
|
memcpy(icmp_packet->rr,
|
||||||
neigh_node->if_incoming->net_dev->dev_addr, ETH_ALEN);
|
neigh_node->if_incoming->net_dev->dev_addr, ETH_ALEN);
|
||||||
|
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
dst_unreach:
|
dst_unreach:
|
||||||
|
@ -248,9 +246,9 @@ out:
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -276,7 +274,7 @@ static const struct file_operations fops = {
|
||||||
.llseek = no_llseek,
|
.llseek = no_llseek,
|
||||||
};
|
};
|
||||||
|
|
||||||
int bat_socket_setup(struct bat_priv *bat_priv)
|
int batadv_socket_setup(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct dentry *d;
|
struct dentry *d;
|
||||||
|
|
||||||
|
@ -312,7 +310,8 @@ static void bat_socket_add_packet(struct socket_client *socket_client,
|
||||||
spin_lock_bh(&socket_client->lock);
|
spin_lock_bh(&socket_client->lock);
|
||||||
|
|
||||||
/* while waiting for the lock the socket_client could have been
|
/* while waiting for the lock the socket_client could have been
|
||||||
* deleted */
|
* deleted
|
||||||
|
*/
|
||||||
if (!socket_client_hash[icmp_packet->uid]) {
|
if (!socket_client_hash[icmp_packet->uid]) {
|
||||||
spin_unlock_bh(&socket_client->lock);
|
spin_unlock_bh(&socket_client->lock);
|
||||||
kfree(socket_packet);
|
kfree(socket_packet);
|
||||||
|
@ -336,8 +335,8 @@ static void bat_socket_add_packet(struct socket_client *socket_client,
|
||||||
wake_up(&socket_client->queue_wait);
|
wake_up(&socket_client->queue_wait);
|
||||||
}
|
}
|
||||||
|
|
||||||
void bat_socket_receive_packet(struct icmp_packet_rr *icmp_packet,
|
void batadv_socket_receive_packet(struct icmp_packet_rr *icmp_packet,
|
||||||
size_t icmp_len)
|
size_t icmp_len)
|
||||||
{
|
{
|
||||||
struct socket_client *hash = socket_client_hash[icmp_packet->uid];
|
struct socket_client *hash = socket_client_hash[icmp_packet->uid];
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_ICMP_SOCKET_H_
|
#ifndef _NET_BATMAN_ADV_ICMP_SOCKET_H_
|
||||||
|
@ -24,9 +22,9 @@
|
||||||
|
|
||||||
#define ICMP_SOCKET "socket"
|
#define ICMP_SOCKET "socket"
|
||||||
|
|
||||||
void bat_socket_init(void);
|
void batadv_socket_init(void);
|
||||||
int bat_socket_setup(struct bat_priv *bat_priv);
|
int batadv_socket_setup(struct bat_priv *bat_priv);
|
||||||
void bat_socket_receive_packet(struct icmp_packet_rr *icmp_packet,
|
void batadv_socket_receive_packet(struct icmp_packet_rr *icmp_packet,
|
||||||
size_t icmp_len);
|
size_t icmp_len);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_ICMP_SOCKET_H_ */
|
#endif /* _NET_BATMAN_ADV_ICMP_SOCKET_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -37,38 +35,40 @@
|
||||||
|
|
||||||
|
|
||||||
/* List manipulations on hardif_list have to be rtnl_lock()'ed,
|
/* List manipulations on hardif_list have to be rtnl_lock()'ed,
|
||||||
* list traversals just rcu-locked */
|
* list traversals just rcu-locked
|
||||||
struct list_head hardif_list;
|
*/
|
||||||
|
struct list_head batadv_hardif_list;
|
||||||
static int (*recv_packet_handler[256])(struct sk_buff *, struct hard_iface *);
|
static int (*recv_packet_handler[256])(struct sk_buff *, struct hard_iface *);
|
||||||
char bat_routing_algo[20] = "BATMAN_IV";
|
char batadv_routing_algo[20] = "BATMAN_IV";
|
||||||
static struct hlist_head bat_algo_list;
|
static struct hlist_head bat_algo_list;
|
||||||
|
|
||||||
unsigned char broadcast_addr[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
|
unsigned char batadv_broadcast_addr[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
|
||||||
|
|
||||||
struct workqueue_struct *bat_event_workqueue;
|
struct workqueue_struct *batadv_event_workqueue;
|
||||||
|
|
||||||
static void recv_handler_init(void);
|
static void recv_handler_init(void);
|
||||||
|
|
||||||
static int __init batman_init(void)
|
static int __init batman_init(void)
|
||||||
{
|
{
|
||||||
INIT_LIST_HEAD(&hardif_list);
|
INIT_LIST_HEAD(&batadv_hardif_list);
|
||||||
INIT_HLIST_HEAD(&bat_algo_list);
|
INIT_HLIST_HEAD(&bat_algo_list);
|
||||||
|
|
||||||
recv_handler_init();
|
recv_handler_init();
|
||||||
|
|
||||||
bat_iv_init();
|
batadv_iv_init();
|
||||||
|
|
||||||
/* the name should not be longer than 10 chars - see
|
/* the name should not be longer than 10 chars - see
|
||||||
* http://lwn.net/Articles/23634/ */
|
* http://lwn.net/Articles/23634/
|
||||||
bat_event_workqueue = create_singlethread_workqueue("bat_events");
|
*/
|
||||||
|
batadv_event_workqueue = create_singlethread_workqueue("bat_events");
|
||||||
|
|
||||||
if (!bat_event_workqueue)
|
if (!batadv_event_workqueue)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
|
||||||
bat_socket_init();
|
batadv_socket_init();
|
||||||
debugfs_init();
|
batadv_debugfs_init();
|
||||||
|
|
||||||
register_netdevice_notifier(&hard_if_notifier);
|
register_netdevice_notifier(&batadv_hard_if_notifier);
|
||||||
|
|
||||||
pr_info("B.A.T.M.A.N. advanced %s (compatibility version %i) loaded\n",
|
pr_info("B.A.T.M.A.N. advanced %s (compatibility version %i) loaded\n",
|
||||||
SOURCE_VERSION, COMPAT_VERSION);
|
SOURCE_VERSION, COMPAT_VERSION);
|
||||||
|
@ -78,18 +78,18 @@ static int __init batman_init(void)
|
||||||
|
|
||||||
static void __exit batman_exit(void)
|
static void __exit batman_exit(void)
|
||||||
{
|
{
|
||||||
debugfs_destroy();
|
batadv_debugfs_destroy();
|
||||||
unregister_netdevice_notifier(&hard_if_notifier);
|
unregister_netdevice_notifier(&batadv_hard_if_notifier);
|
||||||
hardif_remove_interfaces();
|
batadv_hardif_remove_interfaces();
|
||||||
|
|
||||||
flush_workqueue(bat_event_workqueue);
|
flush_workqueue(batadv_event_workqueue);
|
||||||
destroy_workqueue(bat_event_workqueue);
|
destroy_workqueue(batadv_event_workqueue);
|
||||||
bat_event_workqueue = NULL;
|
batadv_event_workqueue = NULL;
|
||||||
|
|
||||||
rcu_barrier();
|
rcu_barrier();
|
||||||
}
|
}
|
||||||
|
|
||||||
int mesh_init(struct net_device *soft_iface)
|
int batadv_mesh_init(struct net_device *soft_iface)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
||||||
int ret;
|
int ret;
|
||||||
|
@ -111,21 +111,21 @@ int mesh_init(struct net_device *soft_iface)
|
||||||
INIT_LIST_HEAD(&bat_priv->tt_req_list);
|
INIT_LIST_HEAD(&bat_priv->tt_req_list);
|
||||||
INIT_LIST_HEAD(&bat_priv->tt_roam_list);
|
INIT_LIST_HEAD(&bat_priv->tt_roam_list);
|
||||||
|
|
||||||
ret = originator_init(bat_priv);
|
ret = batadv_originator_init(bat_priv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
ret = tt_init(bat_priv);
|
ret = batadv_tt_init(bat_priv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
tt_local_add(soft_iface, soft_iface->dev_addr, NULL_IFINDEX);
|
batadv_tt_local_add(soft_iface, soft_iface->dev_addr, NULL_IFINDEX);
|
||||||
|
|
||||||
ret = vis_init(bat_priv);
|
ret = batadv_vis_init(bat_priv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
ret = bla_init(bat_priv);
|
ret = batadv_bla_init(bat_priv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
|
@ -135,48 +135,48 @@ int mesh_init(struct net_device *soft_iface)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
err:
|
err:
|
||||||
mesh_free(soft_iface);
|
batadv_mesh_free(soft_iface);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void mesh_free(struct net_device *soft_iface)
|
void batadv_mesh_free(struct net_device *soft_iface)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
||||||
|
|
||||||
atomic_set(&bat_priv->mesh_state, MESH_DEACTIVATING);
|
atomic_set(&bat_priv->mesh_state, MESH_DEACTIVATING);
|
||||||
|
|
||||||
purge_outstanding_packets(bat_priv, NULL);
|
batadv_purge_outstanding_packets(bat_priv, NULL);
|
||||||
|
|
||||||
vis_quit(bat_priv);
|
batadv_vis_quit(bat_priv);
|
||||||
|
|
||||||
gw_node_purge(bat_priv);
|
batadv_gw_node_purge(bat_priv);
|
||||||
originator_free(bat_priv);
|
batadv_originator_free(bat_priv);
|
||||||
|
|
||||||
tt_free(bat_priv);
|
batadv_tt_free(bat_priv);
|
||||||
|
|
||||||
bla_free(bat_priv);
|
batadv_bla_free(bat_priv);
|
||||||
|
|
||||||
free_percpu(bat_priv->bat_counters);
|
free_percpu(bat_priv->bat_counters);
|
||||||
|
|
||||||
atomic_set(&bat_priv->mesh_state, MESH_INACTIVE);
|
atomic_set(&bat_priv->mesh_state, MESH_INACTIVE);
|
||||||
}
|
}
|
||||||
|
|
||||||
void inc_module_count(void)
|
void batadv_inc_module_count(void)
|
||||||
{
|
{
|
||||||
try_module_get(THIS_MODULE);
|
try_module_get(THIS_MODULE);
|
||||||
}
|
}
|
||||||
|
|
||||||
void dec_module_count(void)
|
void batadv_dec_module_count(void)
|
||||||
{
|
{
|
||||||
module_put(THIS_MODULE);
|
module_put(THIS_MODULE);
|
||||||
}
|
}
|
||||||
|
|
||||||
int is_my_mac(const uint8_t *addr)
|
int batadv_is_my_mac(const uint8_t *addr)
|
||||||
{
|
{
|
||||||
const struct hard_iface *hard_iface;
|
const struct hard_iface *hard_iface;
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if (hard_iface->if_status != IF_ACTIVE)
|
if (hard_iface->if_status != IF_ACTIVE)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -198,8 +198,9 @@ static int recv_unhandled_packet(struct sk_buff *skb,
|
||||||
/* incoming packets with the batman ethertype received on any active hard
|
/* incoming packets with the batman ethertype received on any active hard
|
||||||
* interface
|
* interface
|
||||||
*/
|
*/
|
||||||
int batman_skb_recv(struct sk_buff *skb, struct net_device *dev,
|
int batadv_batman_skb_recv(struct sk_buff *skb, struct net_device *dev,
|
||||||
struct packet_type *ptype, struct net_device *orig_dev)
|
struct packet_type *ptype,
|
||||||
|
struct net_device *orig_dev)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv;
|
struct bat_priv *bat_priv;
|
||||||
struct batman_ogm_packet *batman_ogm_packet;
|
struct batman_ogm_packet *batman_ogm_packet;
|
||||||
|
@ -272,24 +273,24 @@ static void recv_handler_init(void)
|
||||||
recv_packet_handler[i] = recv_unhandled_packet;
|
recv_packet_handler[i] = recv_unhandled_packet;
|
||||||
|
|
||||||
/* batman icmp packet */
|
/* batman icmp packet */
|
||||||
recv_packet_handler[BAT_ICMP] = recv_icmp_packet;
|
recv_packet_handler[BAT_ICMP] = batadv_recv_icmp_packet;
|
||||||
/* unicast packet */
|
/* unicast packet */
|
||||||
recv_packet_handler[BAT_UNICAST] = recv_unicast_packet;
|
recv_packet_handler[BAT_UNICAST] = batadv_recv_unicast_packet;
|
||||||
/* fragmented unicast packet */
|
/* fragmented unicast packet */
|
||||||
recv_packet_handler[BAT_UNICAST_FRAG] = recv_ucast_frag_packet;
|
recv_packet_handler[BAT_UNICAST_FRAG] = batadv_recv_ucast_frag_packet;
|
||||||
/* broadcast packet */
|
/* broadcast packet */
|
||||||
recv_packet_handler[BAT_BCAST] = recv_bcast_packet;
|
recv_packet_handler[BAT_BCAST] = batadv_recv_bcast_packet;
|
||||||
/* vis packet */
|
/* vis packet */
|
||||||
recv_packet_handler[BAT_VIS] = recv_vis_packet;
|
recv_packet_handler[BAT_VIS] = batadv_recv_vis_packet;
|
||||||
/* Translation table query (request or response) */
|
/* Translation table query (request or response) */
|
||||||
recv_packet_handler[BAT_TT_QUERY] = recv_tt_query;
|
recv_packet_handler[BAT_TT_QUERY] = batadv_recv_tt_query;
|
||||||
/* Roaming advertisement */
|
/* Roaming advertisement */
|
||||||
recv_packet_handler[BAT_ROAM_ADV] = recv_roam_adv;
|
recv_packet_handler[BAT_ROAM_ADV] = batadv_recv_roam_adv;
|
||||||
}
|
}
|
||||||
|
|
||||||
int recv_handler_register(uint8_t packet_type,
|
int batadv_recv_handler_register(uint8_t packet_type,
|
||||||
int (*recv_handler)(struct sk_buff *,
|
int (*recv_handler)(struct sk_buff *,
|
||||||
struct hard_iface *))
|
struct hard_iface *))
|
||||||
{
|
{
|
||||||
if (recv_packet_handler[packet_type] != &recv_unhandled_packet)
|
if (recv_packet_handler[packet_type] != &recv_unhandled_packet)
|
||||||
return -EBUSY;
|
return -EBUSY;
|
||||||
|
@ -298,7 +299,7 @@ int recv_handler_register(uint8_t packet_type,
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void recv_handler_unregister(uint8_t packet_type)
|
void batadv_recv_handler_unregister(uint8_t packet_type)
|
||||||
{
|
{
|
||||||
recv_packet_handler[packet_type] = recv_unhandled_packet;
|
recv_packet_handler[packet_type] = recv_unhandled_packet;
|
||||||
}
|
}
|
||||||
|
@ -319,7 +320,7 @@ static struct bat_algo_ops *bat_algo_get(char *name)
|
||||||
return bat_algo_ops;
|
return bat_algo_ops;
|
||||||
}
|
}
|
||||||
|
|
||||||
int bat_algo_register(struct bat_algo_ops *bat_algo_ops)
|
int batadv_algo_register(struct bat_algo_ops *bat_algo_ops)
|
||||||
{
|
{
|
||||||
struct bat_algo_ops *bat_algo_ops_tmp;
|
struct bat_algo_ops *bat_algo_ops_tmp;
|
||||||
int ret;
|
int ret;
|
||||||
|
@ -353,7 +354,7 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int bat_algo_select(struct bat_priv *bat_priv, char *name)
|
int batadv_algo_select(struct bat_priv *bat_priv, char *name)
|
||||||
{
|
{
|
||||||
struct bat_algo_ops *bat_algo_ops;
|
struct bat_algo_ops *bat_algo_ops;
|
||||||
int ret = -EINVAL;
|
int ret = -EINVAL;
|
||||||
|
@ -369,7 +370,7 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int bat_algo_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_algo_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct bat_algo_ops *bat_algo_ops;
|
struct bat_algo_ops *bat_algo_ops;
|
||||||
struct hlist_node *node;
|
struct hlist_node *node;
|
||||||
|
@ -407,8 +408,8 @@ static const struct kernel_param_ops param_ops_ra = {
|
||||||
};
|
};
|
||||||
|
|
||||||
static struct kparam_string __param_string_ra = {
|
static struct kparam_string __param_string_ra = {
|
||||||
.maxlen = sizeof(bat_routing_algo),
|
.maxlen = sizeof(batadv_routing_algo),
|
||||||
.string = bat_routing_algo,
|
.string = batadv_routing_algo,
|
||||||
};
|
};
|
||||||
|
|
||||||
module_param_cb(routing_algo, ¶m_ops_ra, &__param_string_ra, 0644);
|
module_param_cb(routing_algo, ¶m_ops_ra, &__param_string_ra, 0644);
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_MAIN_H_
|
#ifndef _NET_BATMAN_ADV_MAIN_H_
|
||||||
|
@ -36,19 +34,21 @@
|
||||||
#define TQ_MAX_VALUE 255
|
#define TQ_MAX_VALUE 255
|
||||||
#define JITTER 20
|
#define JITTER 20
|
||||||
|
|
||||||
/* Time To Live of broadcast messages */
|
/* Time To Live of broadcast messages */
|
||||||
#define TTL 50
|
#define TTL 50
|
||||||
|
|
||||||
/* purge originators after time in seconds if no valid packet comes in
|
/* purge originators after time in seconds if no valid packet comes in
|
||||||
* -> TODO: check influence on TQ_LOCAL_WINDOW_SIZE */
|
* -> TODO: check influence on TQ_LOCAL_WINDOW_SIZE
|
||||||
|
*/
|
||||||
#define PURGE_TIMEOUT 200000 /* 200 seconds */
|
#define PURGE_TIMEOUT 200000 /* 200 seconds */
|
||||||
#define TT_LOCAL_TIMEOUT 3600000 /* in miliseconds */
|
#define TT_LOCAL_TIMEOUT 3600000 /* in miliseconds */
|
||||||
#define TT_CLIENT_ROAM_TIMEOUT 600000 /* in miliseconds */
|
#define TT_CLIENT_ROAM_TIMEOUT 600000 /* in miliseconds */
|
||||||
/* sliding packet range of received originator messages in sequence numbers
|
/* sliding packet range of received originator messages in sequence numbers
|
||||||
* (should be a multiple of our word size) */
|
* (should be a multiple of our word size)
|
||||||
|
*/
|
||||||
#define TQ_LOCAL_WINDOW_SIZE 64
|
#define TQ_LOCAL_WINDOW_SIZE 64
|
||||||
#define TT_REQUEST_TIMEOUT 3000 /* miliseconds we have to keep
|
/* miliseconds we have to keep pending tt_req */
|
||||||
* pending tt_req */
|
#define TT_REQUEST_TIMEOUT 3000
|
||||||
|
|
||||||
#define TQ_GLOBAL_WINDOW_SIZE 5
|
#define TQ_GLOBAL_WINDOW_SIZE 5
|
||||||
#define TQ_LOCAL_BIDRECT_SEND_MINIMUM 1
|
#define TQ_LOCAL_BIDRECT_SEND_MINIMUM 1
|
||||||
|
@ -57,8 +57,10 @@
|
||||||
|
|
||||||
#define TT_OGM_APPEND_MAX 3 /* number of OGMs sent with the last tt diff */
|
#define TT_OGM_APPEND_MAX 3 /* number of OGMs sent with the last tt diff */
|
||||||
|
|
||||||
#define ROAMING_MAX_TIME 20000 /* Time in which a client can roam at most
|
/* Time in which a client can roam at most ROAMING_MAX_COUNT times in
|
||||||
* ROAMING_MAX_COUNT times in miliseconds*/
|
* miliseconds
|
||||||
|
*/
|
||||||
|
#define ROAMING_MAX_TIME 20000
|
||||||
#define ROAMING_MAX_COUNT 5
|
#define ROAMING_MAX_COUNT 5
|
||||||
|
|
||||||
#define NO_FLAGS 0
|
#define NO_FLAGS 0
|
||||||
|
@ -72,11 +74,13 @@
|
||||||
#define VIS_INTERVAL 5000 /* 5 seconds */
|
#define VIS_INTERVAL 5000 /* 5 seconds */
|
||||||
|
|
||||||
/* how much worse secondary interfaces may be to be considered as bonding
|
/* how much worse secondary interfaces may be to be considered as bonding
|
||||||
* candidates */
|
* candidates
|
||||||
|
*/
|
||||||
#define BONDING_TQ_THRESHOLD 50
|
#define BONDING_TQ_THRESHOLD 50
|
||||||
|
|
||||||
/* should not be bigger than 512 bytes or change the size of
|
/* should not be bigger than 512 bytes or change the size of
|
||||||
* forw_packet->direct_link_flags */
|
* forw_packet->direct_link_flags
|
||||||
|
*/
|
||||||
#define MAX_AGGREGATION_BYTES 512
|
#define MAX_AGGREGATION_BYTES 512
|
||||||
#define MAX_AGGREGATION_MS 100
|
#define MAX_AGGREGATION_MS 100
|
||||||
|
|
||||||
|
@ -145,34 +149,36 @@ enum dbg_level {
|
||||||
#include <linux/seq_file.h>
|
#include <linux/seq_file.h>
|
||||||
#include "types.h"
|
#include "types.h"
|
||||||
|
|
||||||
extern char bat_routing_algo[];
|
extern char batadv_routing_algo[];
|
||||||
extern struct list_head hardif_list;
|
extern struct list_head batadv_hardif_list;
|
||||||
|
|
||||||
extern unsigned char broadcast_addr[];
|
extern unsigned char batadv_broadcast_addr[];
|
||||||
extern struct workqueue_struct *bat_event_workqueue;
|
extern struct workqueue_struct *batadv_event_workqueue;
|
||||||
|
|
||||||
int mesh_init(struct net_device *soft_iface);
|
int batadv_mesh_init(struct net_device *soft_iface);
|
||||||
void mesh_free(struct net_device *soft_iface);
|
void batadv_mesh_free(struct net_device *soft_iface);
|
||||||
void inc_module_count(void);
|
void batadv_inc_module_count(void);
|
||||||
void dec_module_count(void);
|
void batadv_dec_module_count(void);
|
||||||
int is_my_mac(const uint8_t *addr);
|
int batadv_is_my_mac(const uint8_t *addr);
|
||||||
int batman_skb_recv(struct sk_buff *skb, struct net_device *dev,
|
int batadv_batman_skb_recv(struct sk_buff *skb, struct net_device *dev,
|
||||||
struct packet_type *ptype, struct net_device *orig_dev);
|
struct packet_type *ptype,
|
||||||
int recv_handler_register(uint8_t packet_type,
|
struct net_device *orig_dev);
|
||||||
int (*recv_handler)(struct sk_buff *,
|
int batadv_recv_handler_register(uint8_t packet_type,
|
||||||
struct hard_iface *));
|
int (*recv_handler)(struct sk_buff *,
|
||||||
void recv_handler_unregister(uint8_t packet_type);
|
struct hard_iface *));
|
||||||
int bat_algo_register(struct bat_algo_ops *bat_algo_ops);
|
void batadv_recv_handler_unregister(uint8_t packet_type);
|
||||||
int bat_algo_select(struct bat_priv *bat_priv, char *name);
|
int batadv_algo_register(struct bat_algo_ops *bat_algo_ops);
|
||||||
int bat_algo_seq_print_text(struct seq_file *seq, void *offset);
|
int batadv_algo_select(struct bat_priv *bat_priv, char *name);
|
||||||
|
int batadv_algo_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
|
|
||||||
#ifdef CONFIG_BATMAN_ADV_DEBUG
|
#ifdef CONFIG_BATMAN_ADV_DEBUG
|
||||||
int debug_log(struct bat_priv *bat_priv, const char *fmt, ...) __printf(2, 3);
|
int batadv_debug_log(struct bat_priv *bat_priv, const char *fmt, ...)
|
||||||
|
__printf(2, 3);
|
||||||
|
|
||||||
#define bat_dbg(type, bat_priv, fmt, arg...) \
|
#define bat_dbg(type, bat_priv, fmt, arg...) \
|
||||||
do { \
|
do { \
|
||||||
if (atomic_read(&bat_priv->log_level) & type) \
|
if (atomic_read(&bat_priv->log_level) & type) \
|
||||||
debug_log(bat_priv, fmt, ## arg); \
|
batadv_debug_log(bat_priv, fmt, ## arg);\
|
||||||
} \
|
} \
|
||||||
while (0)
|
while (0)
|
||||||
#else /* !CONFIG_BATMAN_ADV_DEBUG */
|
#else /* !CONFIG_BATMAN_ADV_DEBUG */
|
||||||
|
@ -199,19 +205,16 @@ static inline void bat_dbg(int type __always_unused,
|
||||||
pr_err("%s: " fmt, _netdev->name, ## arg); \
|
pr_err("%s: " fmt, _netdev->name, ## arg); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
/**
|
/* returns 1 if they are the same ethernet addr
|
||||||
* returns 1 if they are the same ethernet addr
|
|
||||||
*
|
*
|
||||||
* note: can't use compare_ether_addr() as it requires aligned memory
|
* note: can't use compare_ether_addr() as it requires aligned memory
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static inline int compare_eth(const void *data1, const void *data2)
|
static inline int compare_eth(const void *data1, const void *data2)
|
||||||
{
|
{
|
||||||
return (memcmp(data1, data2, ETH_ALEN) == 0 ? 1 : 0);
|
return (memcmp(data1, data2, ETH_ALEN) == 0 ? 1 : 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/* has_timed_out - compares current time (jiffies) and timestamp + timeout
|
||||||
* has_timed_out - compares current time (jiffies) and timestamp + timeout
|
|
||||||
* @timestamp: base value to compare with (in jiffies)
|
* @timestamp: base value to compare with (in jiffies)
|
||||||
* @timeout: added to base value before comparing (in milliseconds)
|
* @timeout: added to base value before comparing (in milliseconds)
|
||||||
*
|
*
|
||||||
|
@ -235,7 +238,8 @@ static inline bool has_timed_out(unsigned long timestamp, unsigned int timeout)
|
||||||
* - when adding nothing - it is neither a predecessor nor a successor
|
* - when adding nothing - it is neither a predecessor nor a successor
|
||||||
* - before adding more than 127 to the starting value - it is a predecessor,
|
* - before adding more than 127 to the starting value - it is a predecessor,
|
||||||
* - when adding 128 - it is neither a predecessor nor a successor,
|
* - when adding 128 - it is neither a predecessor nor a successor,
|
||||||
* - after adding more than 127 to the starting value - it is a successor */
|
* - after adding more than 127 to the starting value - it is a successor
|
||||||
|
*/
|
||||||
#define seq_before(x, y) ({typeof(x) _d1 = (x); \
|
#define seq_before(x, y) ({typeof(x) _d1 = (x); \
|
||||||
typeof(y) _d2 = (y); \
|
typeof(y) _d2 = (y); \
|
||||||
typeof(x) _dummy = (_d1 - _d2); \
|
typeof(x) _dummy = (_d1 - _d2); \
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -35,7 +33,7 @@ static void purge_orig(struct work_struct *work);
|
||||||
static void start_purge_timer(struct bat_priv *bat_priv)
|
static void start_purge_timer(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
INIT_DELAYED_WORK(&bat_priv->orig_work, purge_orig);
|
INIT_DELAYED_WORK(&bat_priv->orig_work, purge_orig);
|
||||||
queue_delayed_work(bat_event_workqueue,
|
queue_delayed_work(batadv_event_workqueue,
|
||||||
&bat_priv->orig_work, msecs_to_jiffies(1000));
|
&bat_priv->orig_work, msecs_to_jiffies(1000));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -47,12 +45,12 @@ static int compare_orig(const struct hlist_node *node, const void *data2)
|
||||||
return (memcmp(data1, data2, ETH_ALEN) == 0 ? 1 : 0);
|
return (memcmp(data1, data2, ETH_ALEN) == 0 ? 1 : 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
int originator_init(struct bat_priv *bat_priv)
|
int batadv_originator_init(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
if (bat_priv->orig_hash)
|
if (bat_priv->orig_hash)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
bat_priv->orig_hash = hash_new(1024);
|
bat_priv->orig_hash = batadv_hash_new(1024);
|
||||||
|
|
||||||
if (!bat_priv->orig_hash)
|
if (!bat_priv->orig_hash)
|
||||||
goto err;
|
goto err;
|
||||||
|
@ -64,14 +62,14 @@ err:
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
}
|
}
|
||||||
|
|
||||||
void neigh_node_free_ref(struct neigh_node *neigh_node)
|
void batadv_neigh_node_free_ref(struct neigh_node *neigh_node)
|
||||||
{
|
{
|
||||||
if (atomic_dec_and_test(&neigh_node->refcount))
|
if (atomic_dec_and_test(&neigh_node->refcount))
|
||||||
kfree_rcu(neigh_node, rcu);
|
kfree_rcu(neigh_node, rcu);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* increases the refcounter of a found router */
|
/* increases the refcounter of a found router */
|
||||||
struct neigh_node *orig_node_get_router(struct orig_node *orig_node)
|
struct neigh_node *batadv_orig_node_get_router(struct orig_node *orig_node)
|
||||||
{
|
{
|
||||||
struct neigh_node *router;
|
struct neigh_node *router;
|
||||||
|
|
||||||
|
@ -126,21 +124,21 @@ static void orig_node_free_rcu(struct rcu_head *rcu)
|
||||||
list_for_each_entry_safe(neigh_node, tmp_neigh_node,
|
list_for_each_entry_safe(neigh_node, tmp_neigh_node,
|
||||||
&orig_node->bond_list, bonding_list) {
|
&orig_node->bond_list, bonding_list) {
|
||||||
list_del_rcu(&neigh_node->bonding_list);
|
list_del_rcu(&neigh_node->bonding_list);
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* for all neighbors towards this originator ... */
|
/* for all neighbors towards this originator ... */
|
||||||
hlist_for_each_entry_safe(neigh_node, node, node_tmp,
|
hlist_for_each_entry_safe(neigh_node, node, node_tmp,
|
||||||
&orig_node->neigh_list, list) {
|
&orig_node->neigh_list, list) {
|
||||||
hlist_del_rcu(&neigh_node->list);
|
hlist_del_rcu(&neigh_node->list);
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
spin_unlock_bh(&orig_node->neigh_list_lock);
|
spin_unlock_bh(&orig_node->neigh_list_lock);
|
||||||
|
|
||||||
frag_list_free(&orig_node->frag_list);
|
batadv_frag_list_free(&orig_node->frag_list);
|
||||||
tt_global_del_orig(orig_node->bat_priv, orig_node,
|
batadv_tt_global_del_orig(orig_node->bat_priv, orig_node,
|
||||||
"originator timed out");
|
"originator timed out");
|
||||||
|
|
||||||
kfree(orig_node->tt_buff);
|
kfree(orig_node->tt_buff);
|
||||||
kfree(orig_node->bcast_own);
|
kfree(orig_node->bcast_own);
|
||||||
|
@ -148,13 +146,13 @@ static void orig_node_free_rcu(struct rcu_head *rcu)
|
||||||
kfree(orig_node);
|
kfree(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
void orig_node_free_ref(struct orig_node *orig_node)
|
void batadv_orig_node_free_ref(struct orig_node *orig_node)
|
||||||
{
|
{
|
||||||
if (atomic_dec_and_test(&orig_node->refcount))
|
if (atomic_dec_and_test(&orig_node->refcount))
|
||||||
call_rcu(&orig_node->rcu, orig_node_free_rcu);
|
call_rcu(&orig_node->rcu, orig_node_free_rcu);
|
||||||
}
|
}
|
||||||
|
|
||||||
void originator_free(struct bat_priv *bat_priv)
|
void batadv_originator_free(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct hashtable_t *hash = bat_priv->orig_hash;
|
struct hashtable_t *hash = bat_priv->orig_hash;
|
||||||
struct hlist_node *node, *node_tmp;
|
struct hlist_node *node, *node_tmp;
|
||||||
|
@ -179,17 +177,19 @@ void originator_free(struct bat_priv *bat_priv)
|
||||||
head, hash_entry) {
|
head, hash_entry) {
|
||||||
|
|
||||||
hlist_del_rcu(node);
|
hlist_del_rcu(node);
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
spin_unlock_bh(list_lock);
|
spin_unlock_bh(list_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
hash_destroy(hash);
|
batadv_hash_destroy(hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* this function finds or creates an originator entry for the given
|
/* this function finds or creates an originator entry for the given
|
||||||
* address if it does not exits */
|
* address if it does not exits
|
||||||
struct orig_node *get_orig_node(struct bat_priv *bat_priv, const uint8_t *addr)
|
*/
|
||||||
|
struct orig_node *batadv_get_orig_node(struct bat_priv *bat_priv,
|
||||||
|
const uint8_t *addr)
|
||||||
{
|
{
|
||||||
struct orig_node *orig_node;
|
struct orig_node *orig_node;
|
||||||
int size;
|
int size;
|
||||||
|
@ -306,8 +306,8 @@ static bool purge_orig_neighbors(struct bat_priv *bat_priv,
|
||||||
neigh_purged = true;
|
neigh_purged = true;
|
||||||
|
|
||||||
hlist_del_rcu(&neigh_node->list);
|
hlist_del_rcu(&neigh_node->list);
|
||||||
bonding_candidate_del(orig_node, neigh_node);
|
batadv_bonding_candidate_del(orig_node, neigh_node);
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
} else {
|
} else {
|
||||||
if ((!*best_neigh_node) ||
|
if ((!*best_neigh_node) ||
|
||||||
(neigh_node->tq_avg > (*best_neigh_node)->tq_avg))
|
(neigh_node->tq_avg > (*best_neigh_node)->tq_avg))
|
||||||
|
@ -333,7 +333,8 @@ static bool purge_orig_node(struct bat_priv *bat_priv,
|
||||||
} else {
|
} else {
|
||||||
if (purge_orig_neighbors(bat_priv, orig_node,
|
if (purge_orig_neighbors(bat_priv, orig_node,
|
||||||
&best_neigh_node))
|
&best_neigh_node))
|
||||||
update_route(bat_priv, orig_node, best_neigh_node);
|
batadv_update_route(bat_priv, orig_node,
|
||||||
|
best_neigh_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
|
@ -361,21 +362,22 @@ static void _purge_orig(struct bat_priv *bat_priv)
|
||||||
head, hash_entry) {
|
head, hash_entry) {
|
||||||
if (purge_orig_node(bat_priv, orig_node)) {
|
if (purge_orig_node(bat_priv, orig_node)) {
|
||||||
if (orig_node->gw_flags)
|
if (orig_node->gw_flags)
|
||||||
gw_node_delete(bat_priv, orig_node);
|
batadv_gw_node_delete(bat_priv,
|
||||||
|
orig_node);
|
||||||
hlist_del_rcu(node);
|
hlist_del_rcu(node);
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (has_timed_out(orig_node->last_frag_packet,
|
if (has_timed_out(orig_node->last_frag_packet,
|
||||||
FRAG_TIMEOUT))
|
FRAG_TIMEOUT))
|
||||||
frag_list_free(&orig_node->frag_list);
|
batadv_frag_list_free(&orig_node->frag_list);
|
||||||
}
|
}
|
||||||
spin_unlock_bh(list_lock);
|
spin_unlock_bh(list_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
gw_node_purge(bat_priv);
|
batadv_gw_node_purge(bat_priv);
|
||||||
gw_election(bat_priv);
|
batadv_gw_election(bat_priv);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void purge_orig(struct work_struct *work)
|
static void purge_orig(struct work_struct *work)
|
||||||
|
@ -389,12 +391,12 @@ static void purge_orig(struct work_struct *work)
|
||||||
start_purge_timer(bat_priv);
|
start_purge_timer(bat_priv);
|
||||||
}
|
}
|
||||||
|
|
||||||
void purge_orig_ref(struct bat_priv *bat_priv)
|
void batadv_purge_orig_ref(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
_purge_orig(bat_priv);
|
_purge_orig(bat_priv);
|
||||||
}
|
}
|
||||||
|
|
||||||
int orig_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_orig_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)seq->private;
|
struct net_device *net_dev = (struct net_device *)seq->private;
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
|
@ -438,7 +440,7 @@ int orig_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
hlist_for_each_entry_rcu(orig_node, node, head, hash_entry) {
|
hlist_for_each_entry_rcu(orig_node, node, head, hash_entry) {
|
||||||
neigh_node = orig_node_get_router(orig_node);
|
neigh_node = batadv_orig_node_get_router(orig_node);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -467,7 +469,7 @@ int orig_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
batman_count++;
|
batman_count++;
|
||||||
|
|
||||||
next:
|
next:
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
}
|
}
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
}
|
}
|
||||||
|
@ -507,7 +509,7 @@ static int orig_node_add_if(struct orig_node *orig_node, int max_if_num)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int orig_hash_add_if(struct hard_iface *hard_iface, int max_if_num)
|
int batadv_orig_hash_add_if(struct hard_iface *hard_iface, int max_if_num)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
||||||
struct hashtable_t *hash = bat_priv->orig_hash;
|
struct hashtable_t *hash = bat_priv->orig_hash;
|
||||||
|
@ -518,7 +520,8 @@ int orig_hash_add_if(struct hard_iface *hard_iface, int max_if_num)
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
/* resize all orig nodes because orig_node->bcast_own(_sum) depend on
|
/* resize all orig nodes because orig_node->bcast_own(_sum) depend on
|
||||||
* if_num */
|
* if_num
|
||||||
|
*/
|
||||||
for (i = 0; i < hash->size; i++) {
|
for (i = 0; i < hash->size; i++) {
|
||||||
head = &hash->table[i];
|
head = &hash->table[i];
|
||||||
|
|
||||||
|
@ -589,7 +592,7 @@ free_own_sum:
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int orig_hash_del_if(struct hard_iface *hard_iface, int max_if_num)
|
int batadv_orig_hash_del_if(struct hard_iface *hard_iface, int max_if_num)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
||||||
struct hashtable_t *hash = bat_priv->orig_hash;
|
struct hashtable_t *hash = bat_priv->orig_hash;
|
||||||
|
@ -601,7 +604,8 @@ int orig_hash_del_if(struct hard_iface *hard_iface, int max_if_num)
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
/* resize all orig nodes because orig_node->bcast_own(_sum) depend on
|
/* resize all orig nodes because orig_node->bcast_own(_sum) depend on
|
||||||
* if_num */
|
* if_num
|
||||||
|
*/
|
||||||
for (i = 0; i < hash->size; i++) {
|
for (i = 0; i < hash->size; i++) {
|
||||||
head = &hash->table[i];
|
head = &hash->table[i];
|
||||||
|
|
||||||
|
@ -620,7 +624,7 @@ int orig_hash_del_if(struct hard_iface *hard_iface, int max_if_num)
|
||||||
|
|
||||||
/* renumber remaining batman interfaces _inside_ of orig_hash_lock */
|
/* renumber remaining batman interfaces _inside_ of orig_hash_lock */
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface_tmp, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface_tmp, &batadv_hardif_list, list) {
|
||||||
if (hard_iface_tmp->if_status == IF_NOT_IN_USE)
|
if (hard_iface_tmp->if_status == IF_NOT_IN_USE)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_ORIGINATOR_H_
|
#ifndef _NET_BATMAN_ADV_ORIGINATOR_H_
|
||||||
|
@ -24,23 +22,25 @@
|
||||||
|
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
|
|
||||||
int originator_init(struct bat_priv *bat_priv);
|
int batadv_originator_init(struct bat_priv *bat_priv);
|
||||||
void originator_free(struct bat_priv *bat_priv);
|
void batadv_originator_free(struct bat_priv *bat_priv);
|
||||||
void purge_orig_ref(struct bat_priv *bat_priv);
|
void batadv_purge_orig_ref(struct bat_priv *bat_priv);
|
||||||
void orig_node_free_ref(struct orig_node *orig_node);
|
void batadv_orig_node_free_ref(struct orig_node *orig_node);
|
||||||
struct orig_node *get_orig_node(struct bat_priv *bat_priv, const uint8_t *addr);
|
struct orig_node *batadv_get_orig_node(struct bat_priv *bat_priv,
|
||||||
|
const uint8_t *addr);
|
||||||
struct neigh_node *batadv_neigh_node_new(struct hard_iface *hard_iface,
|
struct neigh_node *batadv_neigh_node_new(struct hard_iface *hard_iface,
|
||||||
const uint8_t *neigh_addr,
|
const uint8_t *neigh_addr,
|
||||||
uint32_t seqno);
|
uint32_t seqno);
|
||||||
void neigh_node_free_ref(struct neigh_node *neigh_node);
|
void batadv_neigh_node_free_ref(struct neigh_node *neigh_node);
|
||||||
struct neigh_node *orig_node_get_router(struct orig_node *orig_node);
|
struct neigh_node *batadv_orig_node_get_router(struct orig_node *orig_node);
|
||||||
int orig_seq_print_text(struct seq_file *seq, void *offset);
|
int batadv_orig_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
int orig_hash_add_if(struct hard_iface *hard_iface, int max_if_num);
|
int batadv_orig_hash_add_if(struct hard_iface *hard_iface, int max_if_num);
|
||||||
int orig_hash_del_if(struct hard_iface *hard_iface, int max_if_num);
|
int batadv_orig_hash_del_if(struct hard_iface *hard_iface, int max_if_num);
|
||||||
|
|
||||||
|
|
||||||
/* hashfunction to choose an entry in a hash table of given size */
|
/* hashfunction to choose an entry in a hash table of given size
|
||||||
/* hash algorithm from http://en.wikipedia.org/wiki/Hash_table */
|
* hash algorithm from http://en.wikipedia.org/wiki/Hash_table
|
||||||
|
*/
|
||||||
static inline uint32_t choose_orig(const void *data, uint32_t size)
|
static inline uint32_t choose_orig(const void *data, uint32_t size)
|
||||||
{
|
{
|
||||||
const unsigned char *key = data;
|
const unsigned char *key = data;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_PACKET_H_
|
#ifndef _NET_BATMAN_ADV_PACKET_H_
|
||||||
|
@ -81,7 +79,8 @@ enum tt_query_flags {
|
||||||
|
|
||||||
/* TT_CLIENT flags.
|
/* TT_CLIENT flags.
|
||||||
* Flags from 1 to 1 << 7 are sent on the wire, while flags from 1 << 8 to
|
* Flags from 1 to 1 << 7 are sent on the wire, while flags from 1 << 8 to
|
||||||
* 1 << 15 are used for local computation only */
|
* 1 << 15 are used for local computation only
|
||||||
|
*/
|
||||||
enum tt_client_flags {
|
enum tt_client_flags {
|
||||||
TT_CLIENT_DEL = 1 << 0,
|
TT_CLIENT_DEL = 1 << 0,
|
||||||
TT_CLIENT_ROAM = 1 << 1,
|
TT_CLIENT_ROAM = 1 << 1,
|
||||||
|
@ -142,7 +141,8 @@ struct icmp_packet {
|
||||||
#define BAT_RR_LEN 16
|
#define BAT_RR_LEN 16
|
||||||
|
|
||||||
/* icmp_packet_rr must start with all fields from imcp_packet
|
/* icmp_packet_rr must start with all fields from imcp_packet
|
||||||
* as this is assumed by code that handles ICMP packets */
|
* as this is assumed by code that handles ICMP packets
|
||||||
|
*/
|
||||||
struct icmp_packet_rr {
|
struct icmp_packet_rr {
|
||||||
struct batman_header header;
|
struct batman_header header;
|
||||||
uint8_t msg_type; /* see ICMP message types above */
|
uint8_t msg_type; /* see ICMP message types above */
|
||||||
|
@ -192,7 +192,8 @@ struct tt_query_packet {
|
||||||
struct batman_header header;
|
struct batman_header header;
|
||||||
/* the flag field is a combination of:
|
/* the flag field is a combination of:
|
||||||
* - TT_REQUEST or TT_RESPONSE
|
* - TT_REQUEST or TT_RESPONSE
|
||||||
* - TT_FULL_TABLE */
|
* - TT_FULL_TABLE
|
||||||
|
*/
|
||||||
uint8_t flags;
|
uint8_t flags;
|
||||||
uint8_t dst[ETH_ALEN];
|
uint8_t dst[ETH_ALEN];
|
||||||
uint8_t src[ETH_ALEN];
|
uint8_t src[ETH_ALEN];
|
||||||
|
@ -200,13 +201,15 @@ struct tt_query_packet {
|
||||||
* if TT_REQUEST: ttvn that triggered the
|
* if TT_REQUEST: ttvn that triggered the
|
||||||
* request
|
* request
|
||||||
* if TT_RESPONSE: new ttvn for the src
|
* if TT_RESPONSE: new ttvn for the src
|
||||||
* orig_node */
|
* orig_node
|
||||||
|
*/
|
||||||
uint8_t ttvn;
|
uint8_t ttvn;
|
||||||
/* tt_data field is:
|
/* tt_data field is:
|
||||||
* if TT_REQUEST: crc associated with the
|
* if TT_REQUEST: crc associated with the
|
||||||
* ttvn
|
* ttvn
|
||||||
* if TT_RESPONSE: table_size */
|
* if TT_RESPONSE: table_size
|
||||||
__be16 tt_data;
|
*/
|
||||||
|
__be16 tt_data;
|
||||||
} __packed;
|
} __packed;
|
||||||
|
|
||||||
struct roam_adv_packet {
|
struct roam_adv_packet {
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,19 +15,19 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
#include "ring_buffer.h"
|
#include "ring_buffer.h"
|
||||||
|
|
||||||
void ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index, uint8_t value)
|
void batadv_ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index,
|
||||||
|
uint8_t value)
|
||||||
{
|
{
|
||||||
lq_recv[*lq_index] = value;
|
lq_recv[*lq_index] = value;
|
||||||
*lq_index = (*lq_index + 1) % TQ_GLOBAL_WINDOW_SIZE;
|
*lq_index = (*lq_index + 1) % TQ_GLOBAL_WINDOW_SIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t ring_buffer_avg(const uint8_t lq_recv[])
|
uint8_t batadv_ring_buffer_avg(const uint8_t lq_recv[])
|
||||||
{
|
{
|
||||||
const uint8_t *ptr;
|
const uint8_t *ptr;
|
||||||
uint16_t count = 0, i = 0, sum = 0;
|
uint16_t count = 0, i = 0, sum = 0;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,13 +15,13 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_RING_BUFFER_H_
|
#ifndef _NET_BATMAN_ADV_RING_BUFFER_H_
|
||||||
#define _NET_BATMAN_ADV_RING_BUFFER_H_
|
#define _NET_BATMAN_ADV_RING_BUFFER_H_
|
||||||
|
|
||||||
void ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index, uint8_t value);
|
void batadv_ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index,
|
||||||
uint8_t ring_buffer_avg(const uint8_t lq_recv[]);
|
uint8_t value);
|
||||||
|
uint8_t batadv_ring_buffer_avg(const uint8_t lq_recv[]);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_RING_BUFFER_H_ */
|
#endif /* _NET_BATMAN_ADV_RING_BUFFER_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -34,7 +32,7 @@
|
||||||
static int route_unicast_packet(struct sk_buff *skb,
|
static int route_unicast_packet(struct sk_buff *skb,
|
||||||
struct hard_iface *recv_if);
|
struct hard_iface *recv_if);
|
||||||
|
|
||||||
void slide_own_bcast_window(struct hard_iface *hard_iface)
|
void batadv_slide_own_bcast_window(struct hard_iface *hard_iface)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
||||||
struct hashtable_t *hash = bat_priv->orig_hash;
|
struct hashtable_t *hash = bat_priv->orig_hash;
|
||||||
|
@ -54,7 +52,7 @@ void slide_own_bcast_window(struct hard_iface *hard_iface)
|
||||||
word_index = hard_iface->if_num * NUM_WORDS;
|
word_index = hard_iface->if_num * NUM_WORDS;
|
||||||
word = &(orig_node->bcast_own[word_index]);
|
word = &(orig_node->bcast_own[word_index]);
|
||||||
|
|
||||||
bit_get_packet(bat_priv, word, 1, 0);
|
batadv_bit_get_packet(bat_priv, word, 1, 0);
|
||||||
orig_node->bcast_own_sum[hard_iface->if_num] =
|
orig_node->bcast_own_sum[hard_iface->if_num] =
|
||||||
bitmap_weight(word, TQ_LOCAL_WINDOW_SIZE);
|
bitmap_weight(word, TQ_LOCAL_WINDOW_SIZE);
|
||||||
spin_unlock_bh(&orig_node->ogm_cnt_lock);
|
spin_unlock_bh(&orig_node->ogm_cnt_lock);
|
||||||
|
@ -69,14 +67,14 @@ static void _update_route(struct bat_priv *bat_priv,
|
||||||
{
|
{
|
||||||
struct neigh_node *curr_router;
|
struct neigh_node *curr_router;
|
||||||
|
|
||||||
curr_router = orig_node_get_router(orig_node);
|
curr_router = batadv_orig_node_get_router(orig_node);
|
||||||
|
|
||||||
/* route deleted */
|
/* route deleted */
|
||||||
if ((curr_router) && (!neigh_node)) {
|
if ((curr_router) && (!neigh_node)) {
|
||||||
bat_dbg(DBG_ROUTES, bat_priv, "Deleting route towards: %pM\n",
|
bat_dbg(DBG_ROUTES, bat_priv, "Deleting route towards: %pM\n",
|
||||||
orig_node->orig);
|
orig_node->orig);
|
||||||
tt_global_del_orig(bat_priv, orig_node,
|
batadv_tt_global_del_orig(bat_priv, orig_node,
|
||||||
"Deleted route towards originator");
|
"Deleted route towards originator");
|
||||||
|
|
||||||
/* route added */
|
/* route added */
|
||||||
} else if ((!curr_router) && (neigh_node)) {
|
} else if ((!curr_router) && (neigh_node)) {
|
||||||
|
@ -93,7 +91,7 @@ static void _update_route(struct bat_priv *bat_priv,
|
||||||
}
|
}
|
||||||
|
|
||||||
if (curr_router)
|
if (curr_router)
|
||||||
neigh_node_free_ref(curr_router);
|
batadv_neigh_node_free_ref(curr_router);
|
||||||
|
|
||||||
/* increase refcount of new best neighbor */
|
/* increase refcount of new best neighbor */
|
||||||
if (neigh_node && !atomic_inc_not_zero(&neigh_node->refcount))
|
if (neigh_node && !atomic_inc_not_zero(&neigh_node->refcount))
|
||||||
|
@ -105,30 +103,30 @@ static void _update_route(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* decrease refcount of previous best neighbor */
|
/* decrease refcount of previous best neighbor */
|
||||||
if (curr_router)
|
if (curr_router)
|
||||||
neigh_node_free_ref(curr_router);
|
batadv_neigh_node_free_ref(curr_router);
|
||||||
}
|
}
|
||||||
|
|
||||||
void update_route(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
void batadv_update_route(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
struct neigh_node *neigh_node)
|
struct neigh_node *neigh_node)
|
||||||
{
|
{
|
||||||
struct neigh_node *router = NULL;
|
struct neigh_node *router = NULL;
|
||||||
|
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
|
|
||||||
if (router != neigh_node)
|
if (router != neigh_node)
|
||||||
_update_route(bat_priv, orig_node, neigh_node);
|
_update_route(bat_priv, orig_node, neigh_node);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* caller must hold the neigh_list_lock */
|
/* caller must hold the neigh_list_lock */
|
||||||
void bonding_candidate_del(struct orig_node *orig_node,
|
void batadv_bonding_candidate_del(struct orig_node *orig_node,
|
||||||
struct neigh_node *neigh_node)
|
struct neigh_node *neigh_node)
|
||||||
{
|
{
|
||||||
/* this neighbor is not part of our candidate list */
|
/* this neighbor is not part of our candidate list */
|
||||||
if (list_empty(&neigh_node->bonding_list))
|
if (list_empty(&neigh_node->bonding_list))
|
||||||
|
@ -136,15 +134,15 @@ void bonding_candidate_del(struct orig_node *orig_node,
|
||||||
|
|
||||||
list_del_rcu(&neigh_node->bonding_list);
|
list_del_rcu(&neigh_node->bonding_list);
|
||||||
INIT_LIST_HEAD(&neigh_node->bonding_list);
|
INIT_LIST_HEAD(&neigh_node->bonding_list);
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
atomic_dec(&orig_node->bond_candidates);
|
atomic_dec(&orig_node->bond_candidates);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
void bonding_candidate_add(struct orig_node *orig_node,
|
void batadv_bonding_candidate_add(struct orig_node *orig_node,
|
||||||
struct neigh_node *neigh_node)
|
struct neigh_node *neigh_node)
|
||||||
{
|
{
|
||||||
struct hlist_node *node;
|
struct hlist_node *node;
|
||||||
struct neigh_node *tmp_neigh_node, *router = NULL;
|
struct neigh_node *tmp_neigh_node, *router = NULL;
|
||||||
|
@ -157,7 +155,7 @@ void bonding_candidate_add(struct orig_node *orig_node,
|
||||||
neigh_node->orig_node->primary_addr))
|
neigh_node->orig_node->primary_addr))
|
||||||
goto candidate_del;
|
goto candidate_del;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto candidate_del;
|
goto candidate_del;
|
||||||
|
|
||||||
|
@ -165,8 +163,7 @@ void bonding_candidate_add(struct orig_node *orig_node,
|
||||||
if (neigh_node->tq_avg < router->tq_avg - BONDING_TQ_THRESHOLD)
|
if (neigh_node->tq_avg < router->tq_avg - BONDING_TQ_THRESHOLD)
|
||||||
goto candidate_del;
|
goto candidate_del;
|
||||||
|
|
||||||
/**
|
/* check if we have another candidate with the same mac address or
|
||||||
* check if we have another candidate with the same mac address or
|
|
||||||
* interface. If we do, we won't select this candidate because of
|
* interface. If we do, we won't select this candidate because of
|
||||||
* possible interference.
|
* possible interference.
|
||||||
*/
|
*/
|
||||||
|
@ -177,7 +174,8 @@ void bonding_candidate_add(struct orig_node *orig_node,
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/* we only care if the other candidate is even
|
/* we only care if the other candidate is even
|
||||||
* considered as candidate. */
|
* considered as candidate.
|
||||||
|
*/
|
||||||
if (list_empty(&tmp_neigh_node->bonding_list))
|
if (list_empty(&tmp_neigh_node->bonding_list))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -204,19 +202,20 @@ void bonding_candidate_add(struct orig_node *orig_node,
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
candidate_del:
|
candidate_del:
|
||||||
bonding_candidate_del(orig_node, neigh_node);
|
batadv_bonding_candidate_del(orig_node, neigh_node);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
spin_unlock_bh(&orig_node->neigh_list_lock);
|
spin_unlock_bh(&orig_node->neigh_list_lock);
|
||||||
|
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* copy primary address for bonding */
|
/* copy primary address for bonding */
|
||||||
void bonding_save_primary(const struct orig_node *orig_node,
|
void
|
||||||
struct orig_node *orig_neigh_node,
|
batadv_bonding_save_primary(const struct orig_node *orig_node,
|
||||||
const struct batman_ogm_packet *batman_ogm_packet)
|
struct orig_node *orig_neigh_node,
|
||||||
|
const struct batman_ogm_packet *batman_ogm_packet)
|
||||||
{
|
{
|
||||||
if (!(batman_ogm_packet->flags & PRIMARIES_FIRST_HOP))
|
if (!(batman_ogm_packet->flags & PRIMARIES_FIRST_HOP))
|
||||||
return;
|
return;
|
||||||
|
@ -229,8 +228,8 @@ void bonding_save_primary(const struct orig_node *orig_node,
|
||||||
* 0 if the packet is to be accepted
|
* 0 if the packet is to be accepted
|
||||||
* 1 if the packet is to be ignored.
|
* 1 if the packet is to be ignored.
|
||||||
*/
|
*/
|
||||||
int window_protected(struct bat_priv *bat_priv, int32_t seq_num_diff,
|
int batadv_window_protected(struct bat_priv *bat_priv, int32_t seq_num_diff,
|
||||||
unsigned long *last_reset)
|
unsigned long *last_reset)
|
||||||
{
|
{
|
||||||
if ((seq_num_diff <= -TQ_LOCAL_WINDOW_SIZE) ||
|
if ((seq_num_diff <= -TQ_LOCAL_WINDOW_SIZE) ||
|
||||||
(seq_num_diff >= EXPECTED_SEQNO_RANGE)) {
|
(seq_num_diff >= EXPECTED_SEQNO_RANGE)) {
|
||||||
|
@ -245,9 +244,9 @@ int window_protected(struct bat_priv *bat_priv, int32_t seq_num_diff,
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool check_management_packet(struct sk_buff *skb,
|
bool batadv_check_management_packet(struct sk_buff *skb,
|
||||||
struct hard_iface *hard_iface,
|
struct hard_iface *hard_iface,
|
||||||
int header_len)
|
int header_len)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
|
|
||||||
|
@ -289,7 +288,7 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* add data to device queue */
|
/* add data to device queue */
|
||||||
if (icmp_packet->msg_type != ECHO_REQUEST) {
|
if (icmp_packet->msg_type != ECHO_REQUEST) {
|
||||||
bat_socket_receive_packet(icmp_packet, icmp_len);
|
batadv_socket_receive_packet(icmp_packet, icmp_len);
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -303,7 +302,7 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -318,16 +317,16 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
|
||||||
icmp_packet->msg_type = ECHO_REPLY;
|
icmp_packet->msg_type = ECHO_REPLY;
|
||||||
icmp_packet->header.ttl = TTL;
|
icmp_packet->header.ttl = TTL;
|
||||||
|
|
||||||
send_skb_packet(skb, router->if_incoming, router->addr);
|
batadv_send_skb_packet(skb, router->if_incoming, router->addr);
|
||||||
ret = NET_RX_SUCCESS;
|
ret = NET_RX_SUCCESS;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -358,7 +357,7 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -373,21 +372,21 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
|
||||||
icmp_packet->msg_type = TTL_EXCEEDED;
|
icmp_packet->msg_type = TTL_EXCEEDED;
|
||||||
icmp_packet->header.ttl = TTL;
|
icmp_packet->header.ttl = TTL;
|
||||||
|
|
||||||
send_skb_packet(skb, router->if_incoming, router->addr);
|
batadv_send_skb_packet(skb, router->if_incoming, router->addr);
|
||||||
ret = NET_RX_SUCCESS;
|
ret = NET_RX_SUCCESS;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
||||||
struct icmp_packet_rr *icmp_packet;
|
struct icmp_packet_rr *icmp_packet;
|
||||||
|
@ -397,9 +396,7 @@ int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
int hdr_size = sizeof(struct icmp_packet);
|
int hdr_size = sizeof(struct icmp_packet);
|
||||||
int ret = NET_RX_DROP;
|
int ret = NET_RX_DROP;
|
||||||
|
|
||||||
/**
|
/* we truncate all incoming icmp packets if they don't match our size */
|
||||||
* we truncate all incoming icmp packets if they don't match our size
|
|
||||||
*/
|
|
||||||
if (skb->len >= sizeof(struct icmp_packet_rr))
|
if (skb->len >= sizeof(struct icmp_packet_rr))
|
||||||
hdr_size = sizeof(struct icmp_packet_rr);
|
hdr_size = sizeof(struct icmp_packet_rr);
|
||||||
|
|
||||||
|
@ -418,7 +415,7 @@ int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* not for me */
|
/* not for me */
|
||||||
if (!is_my_mac(ethhdr->h_dest))
|
if (!batadv_is_my_mac(ethhdr->h_dest))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
icmp_packet = (struct icmp_packet_rr *)skb->data;
|
icmp_packet = (struct icmp_packet_rr *)skb->data;
|
||||||
|
@ -432,7 +429,7 @@ int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* packet for me */
|
/* packet for me */
|
||||||
if (is_my_mac(icmp_packet->dst))
|
if (batadv_is_my_mac(icmp_packet->dst))
|
||||||
return recv_my_icmp_packet(bat_priv, skb, hdr_size);
|
return recv_my_icmp_packet(bat_priv, skb, hdr_size);
|
||||||
|
|
||||||
/* TTL exceeded */
|
/* TTL exceeded */
|
||||||
|
@ -444,7 +441,7 @@ int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -458,14 +455,14 @@ int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
icmp_packet->header.ttl--;
|
icmp_packet->header.ttl--;
|
||||||
|
|
||||||
/* route it */
|
/* route it */
|
||||||
send_skb_packet(skb, router->if_incoming, router->addr);
|
batadv_send_skb_packet(skb, router->if_incoming, router->addr);
|
||||||
ret = NET_RX_SUCCESS;
|
ret = NET_RX_SUCCESS;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -473,7 +470,8 @@ out:
|
||||||
* robin fashion over the remaining interfaces.
|
* robin fashion over the remaining interfaces.
|
||||||
*
|
*
|
||||||
* This method rotates the bonding list and increases the
|
* This method rotates the bonding list and increases the
|
||||||
* returned router's refcount. */
|
* returned router's refcount.
|
||||||
|
*/
|
||||||
static struct neigh_node *find_bond_router(struct orig_node *primary_orig,
|
static struct neigh_node *find_bond_router(struct orig_node *primary_orig,
|
||||||
const struct hard_iface *recv_if)
|
const struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
|
@ -506,10 +504,12 @@ static struct neigh_node *find_bond_router(struct orig_node *primary_orig,
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* selected should point to the next element
|
/* selected should point to the next element
|
||||||
* after the current router */
|
* after the current router
|
||||||
|
*/
|
||||||
spin_lock_bh(&primary_orig->neigh_list_lock);
|
spin_lock_bh(&primary_orig->neigh_list_lock);
|
||||||
/* this is a list_move(), which unfortunately
|
/* this is a list_move(), which unfortunately
|
||||||
* does not exist as rcu version */
|
* does not exist as rcu version
|
||||||
|
*/
|
||||||
list_del_rcu(&primary_orig->bond_list);
|
list_del_rcu(&primary_orig->bond_list);
|
||||||
list_add_rcu(&primary_orig->bond_list,
|
list_add_rcu(&primary_orig->bond_list,
|
||||||
&router->bonding_list);
|
&router->bonding_list);
|
||||||
|
@ -524,7 +524,8 @@ out:
|
||||||
* remaining candidates which are not using
|
* remaining candidates which are not using
|
||||||
* this interface.
|
* this interface.
|
||||||
*
|
*
|
||||||
* Increases the returned router's refcount */
|
* Increases the returned router's refcount
|
||||||
|
*/
|
||||||
static struct neigh_node *find_ifalter_router(struct orig_node *primary_orig,
|
static struct neigh_node *find_ifalter_router(struct orig_node *primary_orig,
|
||||||
const struct hard_iface *recv_if)
|
const struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
|
@ -545,19 +546,21 @@ static struct neigh_node *find_ifalter_router(struct orig_node *primary_orig,
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/* if we don't have a router yet
|
/* if we don't have a router yet
|
||||||
* or this one is better, choose it. */
|
* or this one is better, choose it.
|
||||||
|
*/
|
||||||
if ((!router) ||
|
if ((!router) ||
|
||||||
(tmp_neigh_node->tq_avg > router->tq_avg)) {
|
(tmp_neigh_node->tq_avg > router->tq_avg)) {
|
||||||
/* decrement refcount of
|
/* decrement refcount of
|
||||||
* previously selected router */
|
* previously selected router
|
||||||
|
*/
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
|
|
||||||
router = tmp_neigh_node;
|
router = tmp_neigh_node;
|
||||||
atomic_inc_not_zero(&router->refcount);
|
atomic_inc_not_zero(&router->refcount);
|
||||||
}
|
}
|
||||||
|
|
||||||
neigh_node_free_ref(tmp_neigh_node);
|
batadv_neigh_node_free_ref(tmp_neigh_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* use the first candidate if nothing was found. */
|
/* use the first candidate if nothing was found. */
|
||||||
|
@ -569,7 +572,7 @@ static struct neigh_node *find_ifalter_router(struct orig_node *primary_orig,
|
||||||
return router;
|
return router;
|
||||||
}
|
}
|
||||||
|
|
||||||
int recv_tt_query(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_tt_query(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
||||||
struct tt_query_packet *tt_query;
|
struct tt_query_packet *tt_query;
|
||||||
|
@ -601,8 +604,9 @@ int recv_tt_query(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_TT_REQUEST_RX);
|
batadv_inc_counter(bat_priv, BAT_CNT_TT_REQUEST_RX);
|
||||||
|
|
||||||
/* If we cannot provide an answer the tt_request is
|
/* If we cannot provide an answer the tt_request is
|
||||||
* forwarded */
|
* forwarded
|
||||||
if (!send_tt_response(bat_priv, tt_query)) {
|
*/
|
||||||
|
if (!batadv_send_tt_response(bat_priv, tt_query)) {
|
||||||
bat_dbg(DBG_TT, bat_priv,
|
bat_dbg(DBG_TT, bat_priv,
|
||||||
"Routing TT_REQUEST to %pM [%c]\n",
|
"Routing TT_REQUEST to %pM [%c]\n",
|
||||||
tt_query->dst,
|
tt_query->dst,
|
||||||
|
@ -613,22 +617,23 @@ int recv_tt_query(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
case TT_RESPONSE:
|
case TT_RESPONSE:
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_TT_RESPONSE_RX);
|
batadv_inc_counter(bat_priv, BAT_CNT_TT_RESPONSE_RX);
|
||||||
|
|
||||||
if (is_my_mac(tt_query->dst)) {
|
if (batadv_is_my_mac(tt_query->dst)) {
|
||||||
/* packet needs to be linearized to access the TT
|
/* packet needs to be linearized to access the TT
|
||||||
* changes */
|
* changes
|
||||||
|
*/
|
||||||
if (skb_linearize(skb) < 0)
|
if (skb_linearize(skb) < 0)
|
||||||
goto out;
|
goto out;
|
||||||
/* skb_linearize() possibly changed skb->data */
|
/* skb_linearize() possibly changed skb->data */
|
||||||
tt_query = (struct tt_query_packet *)skb->data;
|
tt_query = (struct tt_query_packet *)skb->data;
|
||||||
|
|
||||||
tt_size = tt_len(ntohs(tt_query->tt_data));
|
tt_size = batadv_tt_len(ntohs(tt_query->tt_data));
|
||||||
|
|
||||||
/* Ensure we have all the claimed data */
|
/* Ensure we have all the claimed data */
|
||||||
if (unlikely(skb_headlen(skb) <
|
if (unlikely(skb_headlen(skb) <
|
||||||
sizeof(struct tt_query_packet) + tt_size))
|
sizeof(struct tt_query_packet) + tt_size))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
handle_tt_response(bat_priv, tt_query);
|
batadv_handle_tt_response(bat_priv, tt_query);
|
||||||
} else {
|
} else {
|
||||||
bat_dbg(DBG_TT, bat_priv,
|
bat_dbg(DBG_TT, bat_priv,
|
||||||
"Routing TT_RESPONSE to %pM [%c]\n",
|
"Routing TT_RESPONSE to %pM [%c]\n",
|
||||||
|
@ -644,7 +649,7 @@ out:
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
}
|
}
|
||||||
|
|
||||||
int recv_roam_adv(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_roam_adv(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
||||||
struct roam_adv_packet *roam_adv_packet;
|
struct roam_adv_packet *roam_adv_packet;
|
||||||
|
@ -669,14 +674,14 @@ int recv_roam_adv(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
|
|
||||||
roam_adv_packet = (struct roam_adv_packet *)skb->data;
|
roam_adv_packet = (struct roam_adv_packet *)skb->data;
|
||||||
|
|
||||||
if (!is_my_mac(roam_adv_packet->dst))
|
if (!batadv_is_my_mac(roam_adv_packet->dst))
|
||||||
return route_unicast_packet(skb, recv_if);
|
return route_unicast_packet(skb, recv_if);
|
||||||
|
|
||||||
/* check if it is a backbone gateway. we don't accept
|
/* check if it is a backbone gateway. we don't accept
|
||||||
* roaming advertisement from it, as it has the same
|
* roaming advertisement from it, as it has the same
|
||||||
* entries as we have.
|
* entries as we have.
|
||||||
*/
|
*/
|
||||||
if (bla_is_backbone_gw_orig(bat_priv, roam_adv_packet->src))
|
if (batadv_bla_is_backbone_gw_orig(bat_priv, roam_adv_packet->src))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
orig_node = orig_hash_find(bat_priv, roam_adv_packet->src);
|
orig_node = orig_hash_find(bat_priv, roam_adv_packet->src);
|
||||||
|
@ -687,15 +692,17 @@ int recv_roam_adv(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
"Received ROAMING_ADV from %pM (client %pM)\n",
|
"Received ROAMING_ADV from %pM (client %pM)\n",
|
||||||
roam_adv_packet->src, roam_adv_packet->client);
|
roam_adv_packet->src, roam_adv_packet->client);
|
||||||
|
|
||||||
tt_global_add(bat_priv, orig_node, roam_adv_packet->client,
|
batadv_tt_global_add(bat_priv, orig_node, roam_adv_packet->client,
|
||||||
atomic_read(&orig_node->last_ttvn) + 1, true, false);
|
atomic_read(&orig_node->last_ttvn) + 1, true,
|
||||||
|
false);
|
||||||
|
|
||||||
/* Roaming phase starts: I have new information but the ttvn has not
|
/* Roaming phase starts: I have new information but the ttvn has not
|
||||||
* been incremented yet. This flag will make me check all the incoming
|
* been incremented yet. This flag will make me check all the incoming
|
||||||
* packets for the correct destination. */
|
* packets for the correct destination.
|
||||||
|
*/
|
||||||
bat_priv->tt_poss_change = true;
|
bat_priv->tt_poss_change = true;
|
||||||
|
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
out:
|
out:
|
||||||
/* returning NET_RX_DROP will make the caller function kfree the skb */
|
/* returning NET_RX_DROP will make the caller function kfree the skb */
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
|
@ -703,10 +710,11 @@ out:
|
||||||
|
|
||||||
/* find a suitable router for this originator, and use
|
/* find a suitable router for this originator, and use
|
||||||
* bonding if possible. increases the found neighbors
|
* bonding if possible. increases the found neighbors
|
||||||
* refcount.*/
|
* refcount.
|
||||||
struct neigh_node *find_router(struct bat_priv *bat_priv,
|
*/
|
||||||
struct orig_node *orig_node,
|
struct neigh_node *batadv_find_router(struct bat_priv *bat_priv,
|
||||||
const struct hard_iface *recv_if)
|
struct orig_node *orig_node,
|
||||||
|
const struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct orig_node *primary_orig_node;
|
struct orig_node *primary_orig_node;
|
||||||
struct orig_node *router_orig;
|
struct orig_node *router_orig;
|
||||||
|
@ -717,12 +725,13 @@ struct neigh_node *find_router(struct bat_priv *bat_priv,
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
/* without bonding, the first node should
|
/* without bonding, the first node should
|
||||||
* always choose the default router. */
|
* always choose the default router.
|
||||||
|
*/
|
||||||
bonding_enabled = atomic_read(&bat_priv->bonding);
|
bonding_enabled = atomic_read(&bat_priv->bonding);
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
|
@ -735,13 +744,14 @@ struct neigh_node *find_router(struct bat_priv *bat_priv,
|
||||||
goto return_router;
|
goto return_router;
|
||||||
|
|
||||||
/* if we have something in the primary_addr, we can search
|
/* if we have something in the primary_addr, we can search
|
||||||
* for a potential bonding candidate. */
|
* for a potential bonding candidate.
|
||||||
|
*/
|
||||||
if (compare_eth(router_orig->primary_addr, zero_mac))
|
if (compare_eth(router_orig->primary_addr, zero_mac))
|
||||||
goto return_router;
|
goto return_router;
|
||||||
|
|
||||||
/* find the orig_node which has the primary interface. might
|
/* find the orig_node which has the primary interface. might
|
||||||
* even be the same as our router_orig in many cases */
|
* even be the same as our router_orig in many cases
|
||||||
|
*/
|
||||||
if (compare_eth(router_orig->primary_addr, router_orig->orig)) {
|
if (compare_eth(router_orig->primary_addr, router_orig->orig)) {
|
||||||
primary_orig_node = router_orig;
|
primary_orig_node = router_orig;
|
||||||
} else {
|
} else {
|
||||||
|
@ -750,19 +760,20 @@ struct neigh_node *find_router(struct bat_priv *bat_priv,
|
||||||
if (!primary_orig_node)
|
if (!primary_orig_node)
|
||||||
goto return_router;
|
goto return_router;
|
||||||
|
|
||||||
orig_node_free_ref(primary_orig_node);
|
batadv_orig_node_free_ref(primary_orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* with less than 2 candidates, we can't do any
|
/* with less than 2 candidates, we can't do any
|
||||||
* bonding and prefer the original router. */
|
* bonding and prefer the original router.
|
||||||
|
*/
|
||||||
if (atomic_read(&primary_orig_node->bond_candidates) < 2)
|
if (atomic_read(&primary_orig_node->bond_candidates) < 2)
|
||||||
goto return_router;
|
goto return_router;
|
||||||
|
|
||||||
/* all nodes between should choose a candidate which
|
/* all nodes between should choose a candidate which
|
||||||
* is is not on the interface where the packet came
|
* is is not on the interface where the packet came
|
||||||
* in. */
|
* in.
|
||||||
|
*/
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
|
|
||||||
if (bonding_enabled)
|
if (bonding_enabled)
|
||||||
router = find_bond_router(primary_orig_node, recv_if);
|
router = find_bond_router(primary_orig_node, recv_if);
|
||||||
|
@ -779,7 +790,7 @@ err_unlock:
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
err:
|
err:
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -802,7 +813,7 @@ static int check_unicast_packet(struct sk_buff *skb, int hdr_size)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
/* not for me */
|
/* not for me */
|
||||||
if (!is_my_mac(ethhdr->h_dest))
|
if (!batadv_is_my_mac(ethhdr->h_dest))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -834,7 +845,7 @@ static int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* find_router() increases neigh_nodes refcount if found. */
|
/* find_router() increases neigh_nodes refcount if found. */
|
||||||
neigh_node = find_router(bat_priv, orig_node, recv_if);
|
neigh_node = batadv_find_router(bat_priv, orig_node, recv_if);
|
||||||
|
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -848,15 +859,16 @@ static int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
if (unicast_packet->header.packet_type == BAT_UNICAST &&
|
if (unicast_packet->header.packet_type == BAT_UNICAST &&
|
||||||
atomic_read(&bat_priv->fragmentation) &&
|
atomic_read(&bat_priv->fragmentation) &&
|
||||||
skb->len > neigh_node->if_incoming->net_dev->mtu) {
|
skb->len > neigh_node->if_incoming->net_dev->mtu) {
|
||||||
ret = frag_send_skb(skb, bat_priv,
|
ret = batadv_frag_send_skb(skb, bat_priv,
|
||||||
neigh_node->if_incoming, neigh_node->addr);
|
neigh_node->if_incoming,
|
||||||
|
neigh_node->addr);
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (unicast_packet->header.packet_type == BAT_UNICAST_FRAG &&
|
if (unicast_packet->header.packet_type == BAT_UNICAST_FRAG &&
|
||||||
frag_can_reassemble(skb, neigh_node->if_incoming->net_dev->mtu)) {
|
frag_can_reassemble(skb, neigh_node->if_incoming->net_dev->mtu)) {
|
||||||
|
|
||||||
ret = frag_reassemble_skb(skb, bat_priv, &new_skb);
|
ret = batadv_frag_reassemble_skb(skb, bat_priv, &new_skb);
|
||||||
|
|
||||||
if (ret == NET_RX_DROP)
|
if (ret == NET_RX_DROP)
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -880,14 +892,14 @@ static int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
skb->len + ETH_HLEN);
|
skb->len + ETH_HLEN);
|
||||||
|
|
||||||
/* route it */
|
/* route it */
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
ret = NET_RX_SUCCESS;
|
ret = NET_RX_SUCCESS;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -906,7 +918,7 @@ static int check_unicast_ttvn(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
unicast_packet = (struct unicast_packet *)skb->data;
|
unicast_packet = (struct unicast_packet *)skb->data;
|
||||||
|
|
||||||
if (is_my_mac(unicast_packet->dest)) {
|
if (batadv_is_my_mac(unicast_packet->dest)) {
|
||||||
tt_poss_change = bat_priv->tt_poss_change;
|
tt_poss_change = bat_priv->tt_poss_change;
|
||||||
curr_ttvn = (uint8_t)atomic_read(&bat_priv->ttvn);
|
curr_ttvn = (uint8_t)atomic_read(&bat_priv->ttvn);
|
||||||
} else {
|
} else {
|
||||||
|
@ -917,7 +929,7 @@ static int check_unicast_ttvn(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
curr_ttvn = (uint8_t)atomic_read(&orig_node->last_ttvn);
|
curr_ttvn = (uint8_t)atomic_read(&orig_node->last_ttvn);
|
||||||
tt_poss_change = orig_node->tt_poss_change;
|
tt_poss_change = orig_node->tt_poss_change;
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Check whether I have to reroute the packet */
|
/* Check whether I have to reroute the packet */
|
||||||
|
@ -933,13 +945,15 @@ static int check_unicast_ttvn(struct bat_priv *bat_priv,
|
||||||
/* we don't have an updated route for this client, so we should
|
/* we don't have an updated route for this client, so we should
|
||||||
* not try to reroute the packet!!
|
* not try to reroute the packet!!
|
||||||
*/
|
*/
|
||||||
if (tt_global_client_is_roaming(bat_priv, ethhdr->h_dest))
|
if (batadv_tt_global_client_is_roaming(bat_priv,
|
||||||
|
ethhdr->h_dest))
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
orig_node = transtable_search(bat_priv, NULL, ethhdr->h_dest);
|
orig_node = batadv_transtable_search(bat_priv, NULL,
|
||||||
|
ethhdr->h_dest);
|
||||||
|
|
||||||
if (!orig_node) {
|
if (!orig_node) {
|
||||||
if (!is_my_client(bat_priv, ethhdr->h_dest))
|
if (!batadv_is_my_client(bat_priv, ethhdr->h_dest))
|
||||||
return 0;
|
return 0;
|
||||||
primary_if = primary_if_get_selected(bat_priv);
|
primary_if = primary_if_get_selected(bat_priv);
|
||||||
if (!primary_if)
|
if (!primary_if)
|
||||||
|
@ -952,7 +966,7 @@ static int check_unicast_ttvn(struct bat_priv *bat_priv,
|
||||||
ETH_ALEN);
|
ETH_ALEN);
|
||||||
curr_ttvn = (uint8_t)
|
curr_ttvn = (uint8_t)
|
||||||
atomic_read(&orig_node->last_ttvn);
|
atomic_read(&orig_node->last_ttvn);
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
bat_dbg(DBG_ROUTES, bat_priv,
|
bat_dbg(DBG_ROUTES, bat_priv,
|
||||||
|
@ -965,7 +979,7 @@ static int check_unicast_ttvn(struct bat_priv *bat_priv,
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int recv_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
||||||
struct unicast_packet *unicast_packet;
|
struct unicast_packet *unicast_packet;
|
||||||
|
@ -980,15 +994,17 @@ int recv_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
unicast_packet = (struct unicast_packet *)skb->data;
|
unicast_packet = (struct unicast_packet *)skb->data;
|
||||||
|
|
||||||
/* packet for me */
|
/* packet for me */
|
||||||
if (is_my_mac(unicast_packet->dest)) {
|
if (batadv_is_my_mac(unicast_packet->dest)) {
|
||||||
interface_rx(recv_if->soft_iface, skb, recv_if, hdr_size);
|
batadv_interface_rx(recv_if->soft_iface, skb, recv_if,
|
||||||
|
hdr_size);
|
||||||
return NET_RX_SUCCESS;
|
return NET_RX_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
return route_unicast_packet(skb, recv_if);
|
return route_unicast_packet(skb, recv_if);
|
||||||
}
|
}
|
||||||
|
|
||||||
int recv_ucast_frag_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_ucast_frag_packet(struct sk_buff *skb,
|
||||||
|
struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
||||||
struct unicast_frag_packet *unicast_packet;
|
struct unicast_frag_packet *unicast_packet;
|
||||||
|
@ -1005,9 +1021,9 @@ int recv_ucast_frag_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
unicast_packet = (struct unicast_frag_packet *)skb->data;
|
unicast_packet = (struct unicast_frag_packet *)skb->data;
|
||||||
|
|
||||||
/* packet for me */
|
/* packet for me */
|
||||||
if (is_my_mac(unicast_packet->dest)) {
|
if (batadv_is_my_mac(unicast_packet->dest)) {
|
||||||
|
|
||||||
ret = frag_reassemble_skb(skb, bat_priv, &new_skb);
|
ret = batadv_frag_reassemble_skb(skb, bat_priv, &new_skb);
|
||||||
|
|
||||||
if (ret == NET_RX_DROP)
|
if (ret == NET_RX_DROP)
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
|
@ -1016,8 +1032,8 @@ int recv_ucast_frag_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
if (!new_skb)
|
if (!new_skb)
|
||||||
return NET_RX_SUCCESS;
|
return NET_RX_SUCCESS;
|
||||||
|
|
||||||
interface_rx(recv_if->soft_iface, new_skb, recv_if,
|
batadv_interface_rx(recv_if->soft_iface, new_skb, recv_if,
|
||||||
sizeof(struct unicast_packet));
|
sizeof(struct unicast_packet));
|
||||||
return NET_RX_SUCCESS;
|
return NET_RX_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1025,7 +1041,7 @@ int recv_ucast_frag_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(recv_if->soft_iface);
|
||||||
struct orig_node *orig_node = NULL;
|
struct orig_node *orig_node = NULL;
|
||||||
|
@ -1050,13 +1066,13 @@ int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* ignore broadcasts sent by myself */
|
/* ignore broadcasts sent by myself */
|
||||||
if (is_my_mac(ethhdr->h_source))
|
if (batadv_is_my_mac(ethhdr->h_source))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
bcast_packet = (struct bcast_packet *)skb->data;
|
bcast_packet = (struct bcast_packet *)skb->data;
|
||||||
|
|
||||||
/* ignore broadcasts originated by myself */
|
/* ignore broadcasts originated by myself */
|
||||||
if (is_my_mac(bcast_packet->orig))
|
if (batadv_is_my_mac(bcast_packet->orig))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
if (bcast_packet->header.ttl < 2)
|
if (bcast_packet->header.ttl < 2)
|
||||||
|
@ -1077,32 +1093,33 @@ int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
seq_diff = ntohl(bcast_packet->seqno) - orig_node->last_bcast_seqno;
|
seq_diff = ntohl(bcast_packet->seqno) - orig_node->last_bcast_seqno;
|
||||||
|
|
||||||
/* check whether the packet is old and the host just restarted. */
|
/* check whether the packet is old and the host just restarted. */
|
||||||
if (window_protected(bat_priv, seq_diff,
|
if (batadv_window_protected(bat_priv, seq_diff,
|
||||||
&orig_node->bcast_seqno_reset))
|
&orig_node->bcast_seqno_reset))
|
||||||
goto spin_unlock;
|
goto spin_unlock;
|
||||||
|
|
||||||
/* mark broadcast in flood history, update window position
|
/* mark broadcast in flood history, update window position
|
||||||
* if required. */
|
* if required.
|
||||||
if (bit_get_packet(bat_priv, orig_node->bcast_bits, seq_diff, 1))
|
*/
|
||||||
|
if (batadv_bit_get_packet(bat_priv, orig_node->bcast_bits, seq_diff, 1))
|
||||||
orig_node->last_bcast_seqno = ntohl(bcast_packet->seqno);
|
orig_node->last_bcast_seqno = ntohl(bcast_packet->seqno);
|
||||||
|
|
||||||
spin_unlock_bh(&orig_node->bcast_seqno_lock);
|
spin_unlock_bh(&orig_node->bcast_seqno_lock);
|
||||||
|
|
||||||
/* check whether this has been sent by another originator before */
|
/* check whether this has been sent by another originator before */
|
||||||
if (bla_check_bcast_duplist(bat_priv, bcast_packet, hdr_size))
|
if (batadv_bla_check_bcast_duplist(bat_priv, bcast_packet, hdr_size))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* rebroadcast packet */
|
/* rebroadcast packet */
|
||||||
add_bcast_packet_to_list(bat_priv, skb, 1);
|
batadv_add_bcast_packet_to_list(bat_priv, skb, 1);
|
||||||
|
|
||||||
/* don't hand the broadcast up if it is from an originator
|
/* don't hand the broadcast up if it is from an originator
|
||||||
* from the same backbone.
|
* from the same backbone.
|
||||||
*/
|
*/
|
||||||
if (bla_is_backbone_gw(skb, orig_node, hdr_size))
|
if (batadv_bla_is_backbone_gw(skb, orig_node, hdr_size))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* broadcast for me */
|
/* broadcast for me */
|
||||||
interface_rx(recv_if->soft_iface, skb, recv_if, hdr_size);
|
batadv_interface_rx(recv_if->soft_iface, skb, recv_if, hdr_size);
|
||||||
ret = NET_RX_SUCCESS;
|
ret = NET_RX_SUCCESS;
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1110,11 +1127,11 @@ spin_unlock:
|
||||||
spin_unlock_bh(&orig_node->bcast_seqno_lock);
|
spin_unlock_bh(&orig_node->bcast_seqno_lock);
|
||||||
out:
|
out:
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int recv_vis_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
int batadv_recv_vis_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
{
|
{
|
||||||
struct vis_packet *vis_packet;
|
struct vis_packet *vis_packet;
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
|
@ -1132,25 +1149,25 @@ int recv_vis_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
ethhdr = (struct ethhdr *)skb_mac_header(skb);
|
ethhdr = (struct ethhdr *)skb_mac_header(skb);
|
||||||
|
|
||||||
/* not for me */
|
/* not for me */
|
||||||
if (!is_my_mac(ethhdr->h_dest))
|
if (!batadv_is_my_mac(ethhdr->h_dest))
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
|
|
||||||
/* ignore own packets */
|
/* ignore own packets */
|
||||||
if (is_my_mac(vis_packet->vis_orig))
|
if (batadv_is_my_mac(vis_packet->vis_orig))
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
|
|
||||||
if (is_my_mac(vis_packet->sender_orig))
|
if (batadv_is_my_mac(vis_packet->sender_orig))
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
|
|
||||||
switch (vis_packet->vis_type) {
|
switch (vis_packet->vis_type) {
|
||||||
case VIS_TYPE_SERVER_SYNC:
|
case VIS_TYPE_SERVER_SYNC:
|
||||||
receive_server_sync_packet(bat_priv, vis_packet,
|
batadv_receive_server_sync_packet(bat_priv, vis_packet,
|
||||||
skb_headlen(skb));
|
skb_headlen(skb));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case VIS_TYPE_CLIENT_UPDATE:
|
case VIS_TYPE_CLIENT_UPDATE:
|
||||||
receive_client_update_packet(bat_priv, vis_packet,
|
batadv_receive_client_update_packet(bat_priv, vis_packet,
|
||||||
skb_headlen(skb));
|
skb_headlen(skb));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default: /* ignore unknown packet */
|
default: /* ignore unknown packet */
|
||||||
|
@ -1158,6 +1175,7 @@ int recv_vis_packet(struct sk_buff *skb, struct hard_iface *recv_if)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* We take a copy of the data in the packet, so we should
|
/* We take a copy of the data in the packet, so we should
|
||||||
always free the skbuf. */
|
* always free the skbuf.
|
||||||
|
*/
|
||||||
return NET_RX_DROP;
|
return NET_RX_DROP;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,36 +15,37 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_ROUTING_H_
|
#ifndef _NET_BATMAN_ADV_ROUTING_H_
|
||||||
#define _NET_BATMAN_ADV_ROUTING_H_
|
#define _NET_BATMAN_ADV_ROUTING_H_
|
||||||
|
|
||||||
void slide_own_bcast_window(struct hard_iface *hard_iface);
|
void batadv_slide_own_bcast_window(struct hard_iface *hard_iface);
|
||||||
bool check_management_packet(struct sk_buff *skb,
|
bool batadv_check_management_packet(struct sk_buff *skb,
|
||||||
struct hard_iface *hard_iface,
|
struct hard_iface *hard_iface,
|
||||||
int header_len);
|
int header_len);
|
||||||
void update_route(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
void batadv_update_route(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
struct neigh_node *neigh_node);
|
struct neigh_node *neigh_node);
|
||||||
int recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
int batadv_recv_icmp_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
||||||
int recv_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
int batadv_recv_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
||||||
int recv_ucast_frag_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
int batadv_recv_ucast_frag_packet(struct sk_buff *skb,
|
||||||
int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
struct hard_iface *recv_if);
|
||||||
int recv_vis_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
int batadv_recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
||||||
int recv_tt_query(struct sk_buff *skb, struct hard_iface *recv_if);
|
int batadv_recv_vis_packet(struct sk_buff *skb, struct hard_iface *recv_if);
|
||||||
int recv_roam_adv(struct sk_buff *skb, struct hard_iface *recv_if);
|
int batadv_recv_tt_query(struct sk_buff *skb, struct hard_iface *recv_if);
|
||||||
struct neigh_node *find_router(struct bat_priv *bat_priv,
|
int batadv_recv_roam_adv(struct sk_buff *skb, struct hard_iface *recv_if);
|
||||||
struct orig_node *orig_node,
|
struct neigh_node *batadv_find_router(struct bat_priv *bat_priv,
|
||||||
const struct hard_iface *recv_if);
|
struct orig_node *orig_node,
|
||||||
void bonding_candidate_del(struct orig_node *orig_node,
|
const struct hard_iface *recv_if);
|
||||||
struct neigh_node *neigh_node);
|
void batadv_bonding_candidate_del(struct orig_node *orig_node,
|
||||||
void bonding_candidate_add(struct orig_node *orig_node,
|
struct neigh_node *neigh_node);
|
||||||
struct neigh_node *neigh_node);
|
void batadv_bonding_candidate_add(struct orig_node *orig_node,
|
||||||
void bonding_save_primary(const struct orig_node *orig_node,
|
struct neigh_node *neigh_node);
|
||||||
struct orig_node *orig_neigh_node,
|
void batadv_bonding_save_primary(const struct orig_node *orig_node,
|
||||||
const struct batman_ogm_packet *batman_ogm_packet);
|
struct orig_node *orig_neigh_node,
|
||||||
int window_protected(struct bat_priv *bat_priv, int32_t seq_num_diff,
|
const struct batman_ogm_packet
|
||||||
unsigned long *last_reset);
|
*batman_ogm_packet);
|
||||||
|
int batadv_window_protected(struct bat_priv *bat_priv, int32_t seq_num_diff,
|
||||||
|
unsigned long *last_reset);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_ROUTING_H_ */
|
#endif /* _NET_BATMAN_ADV_ROUTING_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -32,9 +30,10 @@
|
||||||
static void send_outstanding_bcast_packet(struct work_struct *work);
|
static void send_outstanding_bcast_packet(struct work_struct *work);
|
||||||
|
|
||||||
/* send out an already prepared packet to the given address via the
|
/* send out an already prepared packet to the given address via the
|
||||||
* specified batman interface */
|
* specified batman interface
|
||||||
int send_skb_packet(struct sk_buff *skb, struct hard_iface *hard_iface,
|
*/
|
||||||
const uint8_t *dst_addr)
|
int batadv_send_skb_packet(struct sk_buff *skb, struct hard_iface *hard_iface,
|
||||||
|
const uint8_t *dst_addr)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
|
|
||||||
|
@ -51,7 +50,7 @@ int send_skb_packet(struct sk_buff *skb, struct hard_iface *hard_iface,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* push to the ethernet header. */
|
/* push to the ethernet header. */
|
||||||
if (my_skb_head_push(skb, ETH_HLEN) < 0)
|
if (batadv_skb_head_push(skb, ETH_HLEN) < 0)
|
||||||
goto send_skb_err;
|
goto send_skb_err;
|
||||||
|
|
||||||
skb_reset_mac_header(skb);
|
skb_reset_mac_header(skb);
|
||||||
|
@ -69,15 +68,15 @@ int send_skb_packet(struct sk_buff *skb, struct hard_iface *hard_iface,
|
||||||
|
|
||||||
/* dev_queue_xmit() returns a negative result on error. However on
|
/* dev_queue_xmit() returns a negative result on error. However on
|
||||||
* congestion and traffic shaping, it drops and returns NET_XMIT_DROP
|
* congestion and traffic shaping, it drops and returns NET_XMIT_DROP
|
||||||
* (which is > 0). This will not be treated as an error. */
|
* (which is > 0). This will not be treated as an error.
|
||||||
|
*/
|
||||||
return dev_queue_xmit(skb);
|
return dev_queue_xmit(skb);
|
||||||
send_skb_err:
|
send_skb_err:
|
||||||
kfree_skb(skb);
|
kfree_skb(skb);
|
||||||
return NET_XMIT_DROP;
|
return NET_XMIT_DROP;
|
||||||
}
|
}
|
||||||
|
|
||||||
void schedule_bat_ogm(struct hard_iface *hard_iface)
|
void batadv_schedule_bat_ogm(struct hard_iface *hard_iface)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
|
||||||
|
|
||||||
|
@ -85,8 +84,7 @@ void schedule_bat_ogm(struct hard_iface *hard_iface)
|
||||||
(hard_iface->if_status == IF_TO_BE_REMOVED))
|
(hard_iface->if_status == IF_TO_BE_REMOVED))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
/**
|
/* the interface gets activated here to avoid race conditions between
|
||||||
* the interface gets activated here to avoid race conditions between
|
|
||||||
* the moment of activating the interface in
|
* the moment of activating the interface in
|
||||||
* hardif_activate_interface() where the originator mac is set and
|
* hardif_activate_interface() where the originator mac is set and
|
||||||
* outdated packets (especially uninitialized mac addresses) in the
|
* outdated packets (especially uninitialized mac addresses) in the
|
||||||
|
@ -121,7 +119,7 @@ static void _add_bcast_packet_to_list(struct bat_priv *bat_priv,
|
||||||
/* start timer for this packet */
|
/* start timer for this packet */
|
||||||
INIT_DELAYED_WORK(&forw_packet->delayed_work,
|
INIT_DELAYED_WORK(&forw_packet->delayed_work,
|
||||||
send_outstanding_bcast_packet);
|
send_outstanding_bcast_packet);
|
||||||
queue_delayed_work(bat_event_workqueue, &forw_packet->delayed_work,
|
queue_delayed_work(batadv_event_workqueue, &forw_packet->delayed_work,
|
||||||
send_time);
|
send_time);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -132,9 +130,11 @@ static void _add_bcast_packet_to_list(struct bat_priv *bat_priv,
|
||||||
* errors.
|
* errors.
|
||||||
*
|
*
|
||||||
* The skb is not consumed, so the caller should make sure that the
|
* The skb is not consumed, so the caller should make sure that the
|
||||||
* skb is freed. */
|
* skb is freed.
|
||||||
int add_bcast_packet_to_list(struct bat_priv *bat_priv,
|
*/
|
||||||
const struct sk_buff *skb, unsigned long delay)
|
int batadv_add_bcast_packet_to_list(struct bat_priv *bat_priv,
|
||||||
|
const struct sk_buff *skb,
|
||||||
|
unsigned long delay)
|
||||||
{
|
{
|
||||||
struct hard_iface *primary_if = NULL;
|
struct hard_iface *primary_if = NULL;
|
||||||
struct forw_packet *forw_packet;
|
struct forw_packet *forw_packet;
|
||||||
|
@ -204,14 +204,15 @@ static void send_outstanding_bcast_packet(struct work_struct *work)
|
||||||
|
|
||||||
/* rebroadcast packet */
|
/* rebroadcast packet */
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
list_for_each_entry_rcu(hard_iface, &hardif_list, list) {
|
list_for_each_entry_rcu(hard_iface, &batadv_hardif_list, list) {
|
||||||
if (hard_iface->soft_iface != soft_iface)
|
if (hard_iface->soft_iface != soft_iface)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/* send a copy of the saved skb */
|
/* send a copy of the saved skb */
|
||||||
skb1 = skb_clone(forw_packet->skb, GFP_ATOMIC);
|
skb1 = skb_clone(forw_packet->skb, GFP_ATOMIC);
|
||||||
if (skb1)
|
if (skb1)
|
||||||
send_skb_packet(skb1, hard_iface, broadcast_addr);
|
batadv_send_skb_packet(skb1, hard_iface,
|
||||||
|
batadv_broadcast_addr);
|
||||||
}
|
}
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
|
|
||||||
|
@ -229,7 +230,7 @@ out:
|
||||||
atomic_inc(&bat_priv->bcast_queue_left);
|
atomic_inc(&bat_priv->bcast_queue_left);
|
||||||
}
|
}
|
||||||
|
|
||||||
void send_outstanding_bat_ogm_packet(struct work_struct *work)
|
void batadv_send_outstanding_bat_ogm_packet(struct work_struct *work)
|
||||||
{
|
{
|
||||||
struct delayed_work *delayed_work =
|
struct delayed_work *delayed_work =
|
||||||
container_of(work, struct delayed_work, work);
|
container_of(work, struct delayed_work, work);
|
||||||
|
@ -247,13 +248,12 @@ void send_outstanding_bat_ogm_packet(struct work_struct *work)
|
||||||
|
|
||||||
bat_priv->bat_algo_ops->bat_ogm_emit(forw_packet);
|
bat_priv->bat_algo_ops->bat_ogm_emit(forw_packet);
|
||||||
|
|
||||||
/**
|
/* we have to have at least one packet in the queue
|
||||||
* we have to have at least one packet in the queue
|
|
||||||
* to determine the queues wake up time unless we are
|
* to determine the queues wake up time unless we are
|
||||||
* shutting down
|
* shutting down
|
||||||
*/
|
*/
|
||||||
if (forw_packet->own)
|
if (forw_packet->own)
|
||||||
schedule_bat_ogm(forw_packet->if_incoming);
|
batadv_schedule_bat_ogm(forw_packet->if_incoming);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
/* don't count own packet */
|
/* don't count own packet */
|
||||||
|
@ -263,8 +263,8 @@ out:
|
||||||
forw_packet_free(forw_packet);
|
forw_packet_free(forw_packet);
|
||||||
}
|
}
|
||||||
|
|
||||||
void purge_outstanding_packets(struct bat_priv *bat_priv,
|
void batadv_purge_outstanding_packets(struct bat_priv *bat_priv,
|
||||||
const struct hard_iface *hard_iface)
|
const struct hard_iface *hard_iface)
|
||||||
{
|
{
|
||||||
struct forw_packet *forw_packet;
|
struct forw_packet *forw_packet;
|
||||||
struct hlist_node *tmp_node, *safe_tmp_node;
|
struct hlist_node *tmp_node, *safe_tmp_node;
|
||||||
|
@ -283,8 +283,7 @@ void purge_outstanding_packets(struct bat_priv *bat_priv,
|
||||||
hlist_for_each_entry_safe(forw_packet, tmp_node, safe_tmp_node,
|
hlist_for_each_entry_safe(forw_packet, tmp_node, safe_tmp_node,
|
||||||
&bat_priv->forw_bcast_list, list) {
|
&bat_priv->forw_bcast_list, list) {
|
||||||
|
|
||||||
/**
|
/* if purge_outstanding_packets() was called with an argument
|
||||||
* if purge_outstanding_packets() was called with an argument
|
|
||||||
* we delete only packets belonging to the given interface
|
* we delete only packets belonging to the given interface
|
||||||
*/
|
*/
|
||||||
if ((hard_iface) &&
|
if ((hard_iface) &&
|
||||||
|
@ -293,8 +292,7 @@ void purge_outstanding_packets(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
spin_unlock_bh(&bat_priv->forw_bcast_list_lock);
|
spin_unlock_bh(&bat_priv->forw_bcast_list_lock);
|
||||||
|
|
||||||
/**
|
/* send_outstanding_bcast_packet() will lock the list to
|
||||||
* send_outstanding_bcast_packet() will lock the list to
|
|
||||||
* delete the item from the list
|
* delete the item from the list
|
||||||
*/
|
*/
|
||||||
pending = cancel_delayed_work_sync(&forw_packet->delayed_work);
|
pending = cancel_delayed_work_sync(&forw_packet->delayed_work);
|
||||||
|
@ -312,8 +310,7 @@ void purge_outstanding_packets(struct bat_priv *bat_priv,
|
||||||
hlist_for_each_entry_safe(forw_packet, tmp_node, safe_tmp_node,
|
hlist_for_each_entry_safe(forw_packet, tmp_node, safe_tmp_node,
|
||||||
&bat_priv->forw_bat_list, list) {
|
&bat_priv->forw_bat_list, list) {
|
||||||
|
|
||||||
/**
|
/* if purge_outstanding_packets() was called with an argument
|
||||||
* if purge_outstanding_packets() was called with an argument
|
|
||||||
* we delete only packets belonging to the given interface
|
* we delete only packets belonging to the given interface
|
||||||
*/
|
*/
|
||||||
if ((hard_iface) &&
|
if ((hard_iface) &&
|
||||||
|
@ -322,8 +319,7 @@ void purge_outstanding_packets(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
spin_unlock_bh(&bat_priv->forw_bat_list_lock);
|
spin_unlock_bh(&bat_priv->forw_bat_list_lock);
|
||||||
|
|
||||||
/**
|
/* send_outstanding_bat_packet() will lock the list to
|
||||||
* send_outstanding_bat_packet() will lock the list to
|
|
||||||
* delete the item from the list
|
* delete the item from the list
|
||||||
*/
|
*/
|
||||||
pending = cancel_delayed_work_sync(&forw_packet->delayed_work);
|
pending = cancel_delayed_work_sync(&forw_packet->delayed_work);
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,19 +15,19 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_SEND_H_
|
#ifndef _NET_BATMAN_ADV_SEND_H_
|
||||||
#define _NET_BATMAN_ADV_SEND_H_
|
#define _NET_BATMAN_ADV_SEND_H_
|
||||||
|
|
||||||
int send_skb_packet(struct sk_buff *skb, struct hard_iface *hard_iface,
|
int batadv_send_skb_packet(struct sk_buff *skb, struct hard_iface *hard_iface,
|
||||||
const uint8_t *dst_addr);
|
const uint8_t *dst_addr);
|
||||||
void schedule_bat_ogm(struct hard_iface *hard_iface);
|
void batadv_schedule_bat_ogm(struct hard_iface *hard_iface);
|
||||||
int add_bcast_packet_to_list(struct bat_priv *bat_priv,
|
int batadv_add_bcast_packet_to_list(struct bat_priv *bat_priv,
|
||||||
const struct sk_buff *skb, unsigned long delay);
|
const struct sk_buff *skb,
|
||||||
void send_outstanding_bat_ogm_packet(struct work_struct *work);
|
unsigned long delay);
|
||||||
void purge_outstanding_packets(struct bat_priv *bat_priv,
|
void batadv_send_outstanding_bat_ogm_packet(struct work_struct *work);
|
||||||
const struct hard_iface *hard_iface);
|
void batadv_purge_outstanding_packets(struct bat_priv *bat_priv,
|
||||||
|
const struct hard_iface *hard_iface);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_SEND_H_ */
|
#endif /* _NET_BATMAN_ADV_SEND_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -61,12 +59,11 @@ static const struct ethtool_ops bat_ethtool_ops = {
|
||||||
.get_sset_count = batadv_get_sset_count,
|
.get_sset_count = batadv_get_sset_count,
|
||||||
};
|
};
|
||||||
|
|
||||||
int my_skb_head_push(struct sk_buff *skb, unsigned int len)
|
int batadv_skb_head_push(struct sk_buff *skb, unsigned int len)
|
||||||
{
|
{
|
||||||
int result;
|
int result;
|
||||||
|
|
||||||
/**
|
/* TODO: We must check if we can release all references to non-payload
|
||||||
* TODO: We must check if we can release all references to non-payload
|
|
||||||
* data using skb_header_release in our skbs to allow skb_cow_header to
|
* data using skb_header_release in our skbs to allow skb_cow_header to
|
||||||
* work optimally. This means that those skbs are not allowed to read
|
* work optimally. This means that those skbs are not allowed to read
|
||||||
* or write any data which is before the current position of skb->data
|
* or write any data which is before the current position of skb->data
|
||||||
|
@ -109,9 +106,9 @@ static int interface_set_mac_addr(struct net_device *dev, void *p)
|
||||||
|
|
||||||
/* only modify transtable if it has been initialized before */
|
/* only modify transtable if it has been initialized before */
|
||||||
if (atomic_read(&bat_priv->mesh_state) == MESH_ACTIVE) {
|
if (atomic_read(&bat_priv->mesh_state) == MESH_ACTIVE) {
|
||||||
tt_local_remove(bat_priv, dev->dev_addr,
|
batadv_tt_local_remove(bat_priv, dev->dev_addr,
|
||||||
"mac address changed", false);
|
"mac address changed", false);
|
||||||
tt_local_add(dev, addr->sa_data, NULL_IFINDEX);
|
batadv_tt_local_add(dev, addr->sa_data, NULL_IFINDEX);
|
||||||
}
|
}
|
||||||
|
|
||||||
memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
|
memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
|
||||||
|
@ -122,7 +119,7 @@ static int interface_set_mac_addr(struct net_device *dev, void *p)
|
||||||
static int interface_change_mtu(struct net_device *dev, int new_mtu)
|
static int interface_change_mtu(struct net_device *dev, int new_mtu)
|
||||||
{
|
{
|
||||||
/* check ranges */
|
/* check ranges */
|
||||||
if ((new_mtu < 68) || (new_mtu > hardif_min_mtu(dev)))
|
if ((new_mtu < 68) || (new_mtu > batadv_hardif_min_mtu(dev)))
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
dev->mtu = new_mtu;
|
dev->mtu = new_mtu;
|
||||||
|
@ -162,11 +159,11 @@ static int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
|
||||||
goto dropped;
|
goto dropped;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (bla_tx(bat_priv, skb, vid))
|
if (batadv_bla_tx(bat_priv, skb, vid))
|
||||||
goto dropped;
|
goto dropped;
|
||||||
|
|
||||||
/* Register the client MAC in the transtable */
|
/* Register the client MAC in the transtable */
|
||||||
tt_local_add(soft_iface, ethhdr->h_source, skb->skb_iif);
|
batadv_tt_local_add(soft_iface, ethhdr->h_source, skb->skb_iif);
|
||||||
|
|
||||||
/* don't accept stp packets. STP does not help in meshes.
|
/* don't accept stp packets. STP does not help in meshes.
|
||||||
* better use the bridge loop avoidance ...
|
* better use the bridge loop avoidance ...
|
||||||
|
@ -180,15 +177,17 @@ static int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
|
||||||
switch (atomic_read(&bat_priv->gw_mode)) {
|
switch (atomic_read(&bat_priv->gw_mode)) {
|
||||||
case GW_MODE_SERVER:
|
case GW_MODE_SERVER:
|
||||||
/* gateway servers should not send dhcp
|
/* gateway servers should not send dhcp
|
||||||
* requests into the mesh */
|
* requests into the mesh
|
||||||
ret = gw_is_dhcp_target(skb, &header_len);
|
*/
|
||||||
|
ret = batadv_gw_is_dhcp_target(skb, &header_len);
|
||||||
if (ret)
|
if (ret)
|
||||||
goto dropped;
|
goto dropped;
|
||||||
break;
|
break;
|
||||||
case GW_MODE_CLIENT:
|
case GW_MODE_CLIENT:
|
||||||
/* gateway clients should send dhcp requests
|
/* gateway clients should send dhcp requests
|
||||||
* via unicast to their gateway */
|
* via unicast to their gateway
|
||||||
ret = gw_is_dhcp_target(skb, &header_len);
|
*/
|
||||||
|
ret = batadv_gw_is_dhcp_target(skb, &header_len);
|
||||||
if (ret)
|
if (ret)
|
||||||
do_bcast = false;
|
do_bcast = false;
|
||||||
break;
|
break;
|
||||||
|
@ -204,7 +203,7 @@ static int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
|
||||||
if (!primary_if)
|
if (!primary_if)
|
||||||
goto dropped;
|
goto dropped;
|
||||||
|
|
||||||
if (my_skb_head_push(skb, sizeof(*bcast_packet)) < 0)
|
if (batadv_skb_head_push(skb, sizeof(*bcast_packet)) < 0)
|
||||||
goto dropped;
|
goto dropped;
|
||||||
|
|
||||||
bcast_packet = (struct bcast_packet *)skb->data;
|
bcast_packet = (struct bcast_packet *)skb->data;
|
||||||
|
@ -215,7 +214,8 @@ static int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
|
||||||
bcast_packet->header.packet_type = BAT_BCAST;
|
bcast_packet->header.packet_type = BAT_BCAST;
|
||||||
|
|
||||||
/* hw address of first interface is the orig mac because only
|
/* hw address of first interface is the orig mac because only
|
||||||
* this mac is known throughout the mesh */
|
* this mac is known throughout the mesh
|
||||||
|
*/
|
||||||
memcpy(bcast_packet->orig,
|
memcpy(bcast_packet->orig,
|
||||||
primary_if->net_dev->dev_addr, ETH_ALEN);
|
primary_if->net_dev->dev_addr, ETH_ALEN);
|
||||||
|
|
||||||
|
@ -223,21 +223,22 @@ static int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
|
||||||
bcast_packet->seqno =
|
bcast_packet->seqno =
|
||||||
htonl(atomic_inc_return(&bat_priv->bcast_seqno));
|
htonl(atomic_inc_return(&bat_priv->bcast_seqno));
|
||||||
|
|
||||||
add_bcast_packet_to_list(bat_priv, skb, 1);
|
batadv_add_bcast_packet_to_list(bat_priv, skb, 1);
|
||||||
|
|
||||||
/* a copy is stored in the bcast list, therefore removing
|
/* a copy is stored in the bcast list, therefore removing
|
||||||
* the original skb. */
|
* the original skb.
|
||||||
|
*/
|
||||||
kfree_skb(skb);
|
kfree_skb(skb);
|
||||||
|
|
||||||
/* unicast packet */
|
/* unicast packet */
|
||||||
} else {
|
} else {
|
||||||
if (atomic_read(&bat_priv->gw_mode) != GW_MODE_OFF) {
|
if (atomic_read(&bat_priv->gw_mode) != GW_MODE_OFF) {
|
||||||
ret = gw_out_of_range(bat_priv, skb, ethhdr);
|
ret = batadv_gw_out_of_range(bat_priv, skb, ethhdr);
|
||||||
if (ret)
|
if (ret)
|
||||||
goto dropped;
|
goto dropped;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = unicast_send_skb(skb, bat_priv);
|
ret = batadv_unicast_send_skb(skb, bat_priv);
|
||||||
if (ret != 0)
|
if (ret != 0)
|
||||||
goto dropped_freed;
|
goto dropped_freed;
|
||||||
}
|
}
|
||||||
|
@ -256,9 +257,9 @@ end:
|
||||||
return NETDEV_TX_OK;
|
return NETDEV_TX_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
void interface_rx(struct net_device *soft_iface,
|
void batadv_interface_rx(struct net_device *soft_iface,
|
||||||
struct sk_buff *skb, struct hard_iface *recv_if,
|
struct sk_buff *skb, struct hard_iface *recv_if,
|
||||||
int hdr_size)
|
int hdr_size)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
||||||
struct ethhdr *ethhdr;
|
struct ethhdr *ethhdr;
|
||||||
|
@ -294,22 +295,23 @@ void interface_rx(struct net_device *soft_iface,
|
||||||
|
|
||||||
/* should not be necessary anymore as we use skb_pull_rcsum()
|
/* should not be necessary anymore as we use skb_pull_rcsum()
|
||||||
* TODO: please verify this and remove this TODO
|
* TODO: please verify this and remove this TODO
|
||||||
* -- Dec 21st 2009, Simon Wunderlich */
|
* -- Dec 21st 2009, Simon Wunderlich
|
||||||
|
*/
|
||||||
|
|
||||||
/* skb->ip_summed = CHECKSUM_UNNECESSARY;*/
|
/* skb->ip_summed = CHECKSUM_UNNECESSARY; */
|
||||||
|
|
||||||
bat_priv->stats.rx_packets++;
|
bat_priv->stats.rx_packets++;
|
||||||
bat_priv->stats.rx_bytes += skb->len + ETH_HLEN;
|
bat_priv->stats.rx_bytes += skb->len + ETH_HLEN;
|
||||||
|
|
||||||
soft_iface->last_rx = jiffies;
|
soft_iface->last_rx = jiffies;
|
||||||
|
|
||||||
if (is_ap_isolated(bat_priv, ethhdr->h_source, ethhdr->h_dest))
|
if (batadv_is_ap_isolated(bat_priv, ethhdr->h_source, ethhdr->h_dest))
|
||||||
goto dropped;
|
goto dropped;
|
||||||
|
|
||||||
/* Let the bridge loop avoidance check the packet. If will
|
/* Let the bridge loop avoidance check the packet. If will
|
||||||
* not handle it, we can safely push it up.
|
* not handle it, we can safely push it up.
|
||||||
*/
|
*/
|
||||||
if (bla_rx(bat_priv, skb, vid))
|
if (batadv_bla_rx(bat_priv, skb, vid))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
netif_rx(skb);
|
netif_rx(skb);
|
||||||
|
@ -341,8 +343,7 @@ static void interface_setup(struct net_device *dev)
|
||||||
dev->destructor = free_netdev;
|
dev->destructor = free_netdev;
|
||||||
dev->tx_queue_len = 0;
|
dev->tx_queue_len = 0;
|
||||||
|
|
||||||
/**
|
/* can't call min_mtu, because the needed variables
|
||||||
* can't call min_mtu, because the needed variables
|
|
||||||
* have not been initialized yet
|
* have not been initialized yet
|
||||||
*/
|
*/
|
||||||
dev->mtu = ETH_DATA_LEN;
|
dev->mtu = ETH_DATA_LEN;
|
||||||
|
@ -357,7 +358,7 @@ static void interface_setup(struct net_device *dev)
|
||||||
memset(priv, 0, sizeof(*priv));
|
memset(priv, 0, sizeof(*priv));
|
||||||
}
|
}
|
||||||
|
|
||||||
struct net_device *softif_create(const char *name)
|
struct net_device *batadv_softif_create(const char *name)
|
||||||
{
|
{
|
||||||
struct net_device *soft_iface;
|
struct net_device *soft_iface;
|
||||||
struct bat_priv *bat_priv;
|
struct bat_priv *bat_priv;
|
||||||
|
@ -411,28 +412,28 @@ struct net_device *softif_create(const char *name)
|
||||||
if (!bat_priv->bat_counters)
|
if (!bat_priv->bat_counters)
|
||||||
goto unreg_soft_iface;
|
goto unreg_soft_iface;
|
||||||
|
|
||||||
ret = bat_algo_select(bat_priv, bat_routing_algo);
|
ret = batadv_algo_select(bat_priv, batadv_routing_algo);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto free_bat_counters;
|
goto free_bat_counters;
|
||||||
|
|
||||||
ret = sysfs_add_meshif(soft_iface);
|
ret = batadv_sysfs_add_meshif(soft_iface);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto free_bat_counters;
|
goto free_bat_counters;
|
||||||
|
|
||||||
ret = debugfs_add_meshif(soft_iface);
|
ret = batadv_debugfs_add_meshif(soft_iface);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto unreg_sysfs;
|
goto unreg_sysfs;
|
||||||
|
|
||||||
ret = mesh_init(soft_iface);
|
ret = batadv_mesh_init(soft_iface);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
goto unreg_debugfs;
|
goto unreg_debugfs;
|
||||||
|
|
||||||
return soft_iface;
|
return soft_iface;
|
||||||
|
|
||||||
unreg_debugfs:
|
unreg_debugfs:
|
||||||
debugfs_del_meshif(soft_iface);
|
batadv_debugfs_del_meshif(soft_iface);
|
||||||
unreg_sysfs:
|
unreg_sysfs:
|
||||||
sysfs_del_meshif(soft_iface);
|
batadv_sysfs_del_meshif(soft_iface);
|
||||||
free_bat_counters:
|
free_bat_counters:
|
||||||
free_percpu(bat_priv->bat_counters);
|
free_percpu(bat_priv->bat_counters);
|
||||||
unreg_soft_iface:
|
unreg_soft_iface:
|
||||||
|
@ -445,15 +446,15 @@ out:
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void softif_destroy(struct net_device *soft_iface)
|
void batadv_softif_destroy(struct net_device *soft_iface)
|
||||||
{
|
{
|
||||||
debugfs_del_meshif(soft_iface);
|
batadv_debugfs_del_meshif(soft_iface);
|
||||||
sysfs_del_meshif(soft_iface);
|
batadv_sysfs_del_meshif(soft_iface);
|
||||||
mesh_free(soft_iface);
|
batadv_mesh_free(soft_iface);
|
||||||
unregister_netdevice(soft_iface);
|
unregister_netdevice(soft_iface);
|
||||||
}
|
}
|
||||||
|
|
||||||
int softif_is_valid(const struct net_device *net_dev)
|
int batadv_softif_is_valid(const struct net_device *net_dev)
|
||||||
{
|
{
|
||||||
if (net_dev->netdev_ops->ndo_start_xmit == interface_tx)
|
if (net_dev->netdev_ops->ndo_start_xmit == interface_tx)
|
||||||
return 1;
|
return 1;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner
|
* Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,18 +15,16 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_SOFT_INTERFACE_H_
|
#ifndef _NET_BATMAN_ADV_SOFT_INTERFACE_H_
|
||||||
#define _NET_BATMAN_ADV_SOFT_INTERFACE_H_
|
#define _NET_BATMAN_ADV_SOFT_INTERFACE_H_
|
||||||
|
|
||||||
int my_skb_head_push(struct sk_buff *skb, unsigned int len);
|
int batadv_skb_head_push(struct sk_buff *skb, unsigned int len);
|
||||||
void interface_rx(struct net_device *soft_iface,
|
void batadv_interface_rx(struct net_device *soft_iface, struct sk_buff *skb,
|
||||||
struct sk_buff *skb, struct hard_iface *recv_if,
|
struct hard_iface *recv_if, int hdr_size);
|
||||||
int hdr_size);
|
struct net_device *batadv_softif_create(const char *name);
|
||||||
struct net_device *softif_create(const char *name);
|
void batadv_softif_destroy(struct net_device *soft_iface);
|
||||||
void softif_destroy(struct net_device *soft_iface);
|
int batadv_softif_is_valid(const struct net_device *net_dev);
|
||||||
int softif_is_valid(const struct net_device *net_dev);
|
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_SOFT_INTERFACE_H_ */
|
#endif /* _NET_BATMAN_ADV_SOFT_INTERFACE_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich, Antonio Quartulli
|
* Marek Lindner, Simon Wunderlich, Antonio Quartulli
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -48,7 +46,7 @@ static int compare_tt(const struct hlist_node *node, const void *data2)
|
||||||
static void tt_start_timer(struct bat_priv *bat_priv)
|
static void tt_start_timer(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
INIT_DELAYED_WORK(&bat_priv->tt_work, tt_purge);
|
INIT_DELAYED_WORK(&bat_priv->tt_work, tt_purge);
|
||||||
queue_delayed_work(bat_event_workqueue, &bat_priv->tt_work,
|
queue_delayed_work(batadv_event_workqueue, &bat_priv->tt_work,
|
||||||
msecs_to_jiffies(5000));
|
msecs_to_jiffies(5000));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -142,7 +140,7 @@ static void tt_orig_list_entry_free_rcu(struct rcu_head *rcu)
|
||||||
|
|
||||||
orig_entry = container_of(rcu, struct tt_orig_list_entry, rcu);
|
orig_entry = container_of(rcu, struct tt_orig_list_entry, rcu);
|
||||||
atomic_dec(&orig_entry->orig_node->tt_size);
|
atomic_dec(&orig_entry->orig_node->tt_size);
|
||||||
orig_node_free_ref(orig_entry->orig_node);
|
batadv_orig_node_free_ref(orig_entry->orig_node);
|
||||||
kfree(orig_entry);
|
kfree(orig_entry);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -173,7 +171,7 @@ static void tt_local_event(struct bat_priv *bat_priv, const uint8_t *addr,
|
||||||
atomic_set(&bat_priv->tt_ogm_append_cnt, 0);
|
atomic_set(&bat_priv->tt_ogm_append_cnt, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
int tt_len(int changes_num)
|
int batadv_tt_len(int changes_num)
|
||||||
{
|
{
|
||||||
return changes_num * sizeof(struct tt_change);
|
return changes_num * sizeof(struct tt_change);
|
||||||
}
|
}
|
||||||
|
@ -183,7 +181,7 @@ static int tt_local_init(struct bat_priv *bat_priv)
|
||||||
if (bat_priv->tt_local_hash)
|
if (bat_priv->tt_local_hash)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
bat_priv->tt_local_hash = hash_new(1024);
|
bat_priv->tt_local_hash = batadv_hash_new(1024);
|
||||||
|
|
||||||
if (!bat_priv->tt_local_hash)
|
if (!bat_priv->tt_local_hash)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
@ -191,8 +189,8 @@ static int tt_local_init(struct bat_priv *bat_priv)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
|
void batadv_tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
|
||||||
int ifindex)
|
int ifindex)
|
||||||
{
|
{
|
||||||
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
struct bat_priv *bat_priv = netdev_priv(soft_iface);
|
||||||
struct tt_local_entry *tt_local_entry = NULL;
|
struct tt_local_entry *tt_local_entry = NULL;
|
||||||
|
@ -221,7 +219,7 @@ void tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
|
||||||
|
|
||||||
memcpy(tt_local_entry->common.addr, addr, ETH_ALEN);
|
memcpy(tt_local_entry->common.addr, addr, ETH_ALEN);
|
||||||
tt_local_entry->common.flags = NO_FLAGS;
|
tt_local_entry->common.flags = NO_FLAGS;
|
||||||
if (is_wifi_iface(ifindex))
|
if (batadv_is_wifi_iface(ifindex))
|
||||||
tt_local_entry->common.flags |= TT_CLIENT_WIFI;
|
tt_local_entry->common.flags |= TT_CLIENT_WIFI;
|
||||||
atomic_set(&tt_local_entry->common.refcount, 2);
|
atomic_set(&tt_local_entry->common.refcount, 2);
|
||||||
tt_local_entry->last_seen = jiffies;
|
tt_local_entry->last_seen = jiffies;
|
||||||
|
@ -232,7 +230,8 @@ void tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
|
||||||
|
|
||||||
/* The local entry has to be marked as NEW to avoid to send it in
|
/* The local entry has to be marked as NEW to avoid to send it in
|
||||||
* a full table response going out before the next ttvn increment
|
* a full table response going out before the next ttvn increment
|
||||||
* (consistency check) */
|
* (consistency check)
|
||||||
|
*/
|
||||||
tt_local_entry->common.flags |= TT_CLIENT_NEW;
|
tt_local_entry->common.flags |= TT_CLIENT_NEW;
|
||||||
|
|
||||||
hash_added = hash_add(bat_priv->tt_local_hash, compare_tt, choose_orig,
|
hash_added = hash_add(bat_priv->tt_local_hash, compare_tt, choose_orig,
|
||||||
|
@ -302,7 +301,7 @@ static void tt_prepare_packet_buff(struct bat_priv *bat_priv,
|
||||||
primary_if = primary_if_get_selected(bat_priv);
|
primary_if = primary_if_get_selected(bat_priv);
|
||||||
|
|
||||||
req_len = min_packet_len;
|
req_len = min_packet_len;
|
||||||
req_len += tt_len(atomic_read(&bat_priv->tt_local_changes));
|
req_len += batadv_tt_len(atomic_read(&bat_priv->tt_local_changes));
|
||||||
|
|
||||||
/* if we have too many changes for one packet don't send any
|
/* if we have too many changes for one packet don't send any
|
||||||
* and wait for the tt table request which will be fragmented
|
* and wait for the tt table request which will be fragmented
|
||||||
|
@ -332,7 +331,7 @@ static int tt_changes_fill_buff(struct bat_priv *bat_priv,
|
||||||
tt_buff = *packet_buff + min_packet_len;
|
tt_buff = *packet_buff + min_packet_len;
|
||||||
|
|
||||||
if (new_len > 0)
|
if (new_len > 0)
|
||||||
tot_changes = new_len / tt_len(1);
|
tot_changes = new_len / batadv_tt_len(1);
|
||||||
|
|
||||||
spin_lock_bh(&bat_priv->tt_changes_list_lock);
|
spin_lock_bh(&bat_priv->tt_changes_list_lock);
|
||||||
atomic_set(&bat_priv->tt_local_changes, 0);
|
atomic_set(&bat_priv->tt_local_changes, 0);
|
||||||
|
@ -340,7 +339,7 @@ static int tt_changes_fill_buff(struct bat_priv *bat_priv,
|
||||||
list_for_each_entry_safe(entry, safe, &bat_priv->tt_changes_list,
|
list_for_each_entry_safe(entry, safe, &bat_priv->tt_changes_list,
|
||||||
list) {
|
list) {
|
||||||
if (count < tot_changes) {
|
if (count < tot_changes) {
|
||||||
memcpy(tt_buff + tt_len(count),
|
memcpy(tt_buff + batadv_tt_len(count),
|
||||||
&entry->change, sizeof(struct tt_change));
|
&entry->change, sizeof(struct tt_change));
|
||||||
count++;
|
count++;
|
||||||
}
|
}
|
||||||
|
@ -370,7 +369,7 @@ static int tt_changes_fill_buff(struct bat_priv *bat_priv,
|
||||||
return count;
|
return count;
|
||||||
}
|
}
|
||||||
|
|
||||||
int tt_local_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_tt_local_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)seq->private;
|
struct net_device *net_dev = (struct net_device *)seq->private;
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
|
@ -437,7 +436,8 @@ static void tt_local_set_pending(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* The local client has to be marked as "pending to be removed" but has
|
/* The local client has to be marked as "pending to be removed" but has
|
||||||
* to be kept in the table in order to send it in a full table
|
* to be kept in the table in order to send it in a full table
|
||||||
* response issued before the net ttvn increment (consistency check) */
|
* response issued before the net ttvn increment (consistency check)
|
||||||
|
*/
|
||||||
tt_local_entry->common.flags |= TT_CLIENT_PENDING;
|
tt_local_entry->common.flags |= TT_CLIENT_PENDING;
|
||||||
|
|
||||||
bat_dbg(DBG_TT, bat_priv,
|
bat_dbg(DBG_TT, bat_priv,
|
||||||
|
@ -445,8 +445,8 @@ static void tt_local_set_pending(struct bat_priv *bat_priv,
|
||||||
tt_local_entry->common.addr, message);
|
tt_local_entry->common.addr, message);
|
||||||
}
|
}
|
||||||
|
|
||||||
void tt_local_remove(struct bat_priv *bat_priv, const uint8_t *addr,
|
void batadv_tt_local_remove(struct bat_priv *bat_priv, const uint8_t *addr,
|
||||||
const char *message, bool roaming)
|
const char *message, bool roaming)
|
||||||
{
|
{
|
||||||
struct tt_local_entry *tt_local_entry = NULL;
|
struct tt_local_entry *tt_local_entry = NULL;
|
||||||
|
|
||||||
|
@ -531,7 +531,7 @@ static void tt_local_table_free(struct bat_priv *bat_priv)
|
||||||
spin_unlock_bh(list_lock);
|
spin_unlock_bh(list_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
hash_destroy(hash);
|
batadv_hash_destroy(hash);
|
||||||
|
|
||||||
bat_priv->tt_local_hash = NULL;
|
bat_priv->tt_local_hash = NULL;
|
||||||
}
|
}
|
||||||
|
@ -541,7 +541,7 @@ static int tt_global_init(struct bat_priv *bat_priv)
|
||||||
if (bat_priv->tt_global_hash)
|
if (bat_priv->tt_global_hash)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
bat_priv->tt_global_hash = hash_new(1024);
|
bat_priv->tt_global_hash = batadv_hash_new(1024);
|
||||||
|
|
||||||
if (!bat_priv->tt_global_hash)
|
if (!bat_priv->tt_global_hash)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
@ -611,9 +611,9 @@ static void tt_global_add_orig_entry(struct tt_global_entry *tt_global_entry,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* caller must hold orig_node refcount */
|
/* caller must hold orig_node refcount */
|
||||||
int tt_global_add(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
int batadv_tt_global_add(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
const unsigned char *tt_addr, uint8_t ttvn, bool roaming,
|
const unsigned char *tt_addr, uint8_t ttvn,
|
||||||
bool wifi)
|
bool roaming, bool wifi)
|
||||||
{
|
{
|
||||||
struct tt_global_entry *tt_global_entry = NULL;
|
struct tt_global_entry *tt_global_entry = NULL;
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
|
@ -677,8 +677,8 @@ int tt_global_add(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
|
|
||||||
out_remove:
|
out_remove:
|
||||||
/* remove address from local hash if present */
|
/* remove address from local hash if present */
|
||||||
tt_local_remove(bat_priv, tt_global_entry->common.addr,
|
batadv_tt_local_remove(bat_priv, tt_global_entry->common.addr,
|
||||||
"global tt received", roaming);
|
"global tt received", roaming);
|
||||||
ret = 1;
|
ret = 1;
|
||||||
out:
|
out:
|
||||||
if (tt_global_entry)
|
if (tt_global_entry)
|
||||||
|
@ -714,7 +714,7 @@ static void tt_global_print_entry(struct tt_global_entry *tt_global_entry,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int tt_global_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_tt_global_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct net_device *net_dev = (struct net_device *)seq->private;
|
struct net_device *net_dev = (struct net_device *)seq->private;
|
||||||
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
struct bat_priv *bat_priv = netdev_priv(net_dev);
|
||||||
|
@ -898,8 +898,8 @@ static void tt_global_del(struct bat_priv *bat_priv,
|
||||||
* If there are other originators left, we directly delete
|
* If there are other originators left, we directly delete
|
||||||
* the originator.
|
* the originator.
|
||||||
* 2) the client roamed to us => we can directly delete
|
* 2) the client roamed to us => we can directly delete
|
||||||
* the global entry, since it is useless now. */
|
* the global entry, since it is useless now.
|
||||||
|
*/
|
||||||
tt_local_entry = tt_local_hash_find(bat_priv,
|
tt_local_entry = tt_local_hash_find(bat_priv,
|
||||||
tt_global_entry->common.addr);
|
tt_global_entry->common.addr);
|
||||||
if (tt_local_entry) {
|
if (tt_local_entry) {
|
||||||
|
@ -919,8 +919,8 @@ out:
|
||||||
tt_local_entry_free_ref(tt_local_entry);
|
tt_local_entry_free_ref(tt_local_entry);
|
||||||
}
|
}
|
||||||
|
|
||||||
void tt_global_del_orig(struct bat_priv *bat_priv,
|
void batadv_tt_global_del_orig(struct bat_priv *bat_priv,
|
||||||
struct orig_node *orig_node, const char *message)
|
struct orig_node *orig_node, const char *message)
|
||||||
{
|
{
|
||||||
struct tt_global_entry *tt_global_entry;
|
struct tt_global_entry *tt_global_entry;
|
||||||
struct tt_common_entry *tt_common_entry;
|
struct tt_common_entry *tt_common_entry;
|
||||||
|
@ -1031,7 +1031,7 @@ static void tt_global_table_free(struct bat_priv *bat_priv)
|
||||||
spin_unlock_bh(list_lock);
|
spin_unlock_bh(list_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
hash_destroy(hash);
|
batadv_hash_destroy(hash);
|
||||||
|
|
||||||
bat_priv->tt_global_hash = NULL;
|
bat_priv->tt_global_hash = NULL;
|
||||||
}
|
}
|
||||||
|
@ -1048,8 +1048,9 @@ static bool _is_ap_isolated(struct tt_local_entry *tt_local_entry,
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct orig_node *transtable_search(struct bat_priv *bat_priv,
|
struct orig_node *batadv_transtable_search(struct bat_priv *bat_priv,
|
||||||
const uint8_t *src, const uint8_t *addr)
|
const uint8_t *src,
|
||||||
|
const uint8_t *addr)
|
||||||
{
|
{
|
||||||
struct tt_local_entry *tt_local_entry = NULL;
|
struct tt_local_entry *tt_local_entry = NULL;
|
||||||
struct tt_global_entry *tt_global_entry = NULL;
|
struct tt_global_entry *tt_global_entry = NULL;
|
||||||
|
@ -1071,7 +1072,8 @@ struct orig_node *transtable_search(struct bat_priv *bat_priv,
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* check whether the clients should not communicate due to AP
|
/* check whether the clients should not communicate due to AP
|
||||||
* isolation */
|
* isolation
|
||||||
|
*/
|
||||||
if (tt_local_entry && _is_ap_isolated(tt_local_entry, tt_global_entry))
|
if (tt_local_entry && _is_ap_isolated(tt_local_entry, tt_global_entry))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1080,7 +1082,7 @@ struct orig_node *transtable_search(struct bat_priv *bat_priv,
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
head = &tt_global_entry->orig_list;
|
head = &tt_global_entry->orig_list;
|
||||||
hlist_for_each_entry_rcu(orig_entry, node, head, list) {
|
hlist_for_each_entry_rcu(orig_entry, node, head, list) {
|
||||||
router = orig_node_get_router(orig_entry->orig_node);
|
router = batadv_orig_node_get_router(orig_entry->orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -1088,7 +1090,7 @@ struct orig_node *transtable_search(struct bat_priv *bat_priv,
|
||||||
orig_node = orig_entry->orig_node;
|
orig_node = orig_entry->orig_node;
|
||||||
best_tq = router->tq_avg;
|
best_tq = router->tq_avg;
|
||||||
}
|
}
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
/* found anything? */
|
/* found anything? */
|
||||||
if (orig_node && !atomic_inc_not_zero(&orig_node->refcount))
|
if (orig_node && !atomic_inc_not_zero(&orig_node->refcount))
|
||||||
|
@ -1170,7 +1172,8 @@ static uint16_t batadv_tt_local_crc(struct bat_priv *bat_priv)
|
||||||
hlist_for_each_entry_rcu(tt_common_entry, node,
|
hlist_for_each_entry_rcu(tt_common_entry, node,
|
||||||
head, hash_entry) {
|
head, hash_entry) {
|
||||||
/* not yet committed clients have not to be taken into
|
/* not yet committed clients have not to be taken into
|
||||||
* account while computing the CRC */
|
* account while computing the CRC
|
||||||
|
*/
|
||||||
if (tt_common_entry->flags & TT_CLIENT_NEW)
|
if (tt_common_entry->flags & TT_CLIENT_NEW)
|
||||||
continue;
|
continue;
|
||||||
total_one = 0;
|
total_one = 0;
|
||||||
|
@ -1204,10 +1207,11 @@ static void tt_save_orig_buffer(struct bat_priv *bat_priv,
|
||||||
const unsigned char *tt_buff,
|
const unsigned char *tt_buff,
|
||||||
uint8_t tt_num_changes)
|
uint8_t tt_num_changes)
|
||||||
{
|
{
|
||||||
uint16_t tt_buff_len = tt_len(tt_num_changes);
|
uint16_t tt_buff_len = batadv_tt_len(tt_num_changes);
|
||||||
|
|
||||||
/* Replace the old buffer only if I received something in the
|
/* Replace the old buffer only if I received something in the
|
||||||
* last OGM (the OGM could carry no changes) */
|
* last OGM (the OGM could carry no changes)
|
||||||
|
*/
|
||||||
spin_lock_bh(&orig_node->tt_buff_lock);
|
spin_lock_bh(&orig_node->tt_buff_lock);
|
||||||
if (tt_buff_len > 0) {
|
if (tt_buff_len > 0) {
|
||||||
kfree(orig_node->tt_buff);
|
kfree(orig_node->tt_buff);
|
||||||
|
@ -1236,7 +1240,8 @@ static void tt_req_purge(struct bat_priv *bat_priv)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* returns the pointer to the new tt_req_node struct if no request
|
/* returns the pointer to the new tt_req_node struct if no request
|
||||||
* has already been issued for this orig_node, NULL otherwise */
|
* has already been issued for this orig_node, NULL otherwise
|
||||||
|
*/
|
||||||
static struct tt_req_node *new_tt_req_node(struct bat_priv *bat_priv,
|
static struct tt_req_node *new_tt_req_node(struct bat_priv *bat_priv,
|
||||||
struct orig_node *orig_node)
|
struct orig_node *orig_node)
|
||||||
{
|
{
|
||||||
|
@ -1346,7 +1351,8 @@ static struct sk_buff *tt_response_fill_table(uint16_t tt_len, uint8_t ttvn,
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
|
|
||||||
/* store in the message the number of entries we have successfully
|
/* store in the message the number of entries we have successfully
|
||||||
* copied */
|
* copied
|
||||||
|
*/
|
||||||
tt_response->tt_data = htons(tt_count);
|
tt_response->tt_data = htons(tt_count);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
|
@ -1369,7 +1375,8 @@ static int send_tt_request(struct bat_priv *bat_priv,
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* The new tt_req will be issued only if I'm not waiting for a
|
/* The new tt_req will be issued only if I'm not waiting for a
|
||||||
* reply from the same orig_node yet */
|
* reply from the same orig_node yet
|
||||||
|
*/
|
||||||
tt_req_node = new_tt_req_node(bat_priv, dst_orig_node);
|
tt_req_node = new_tt_req_node(bat_priv, dst_orig_node);
|
||||||
if (!tt_req_node)
|
if (!tt_req_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
@ -1395,7 +1402,7 @@ static int send_tt_request(struct bat_priv *bat_priv,
|
||||||
if (full_table)
|
if (full_table)
|
||||||
tt_request->flags |= TT_FULL_TABLE;
|
tt_request->flags |= TT_FULL_TABLE;
|
||||||
|
|
||||||
neigh_node = orig_node_get_router(dst_orig_node);
|
neigh_node = batadv_orig_node_get_router(dst_orig_node);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1406,12 +1413,12 @@ static int send_tt_request(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_TT_REQUEST_TX);
|
batadv_inc_counter(bat_priv, BAT_CNT_TT_REQUEST_TX);
|
||||||
|
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
ret = 0;
|
ret = 0;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
if (ret)
|
if (ret)
|
||||||
|
@ -1453,7 +1460,7 @@ static bool send_other_tt_response(struct bat_priv *bat_priv,
|
||||||
if (!res_dst_orig_node)
|
if (!res_dst_orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
neigh_node = orig_node_get_router(res_dst_orig_node);
|
neigh_node = batadv_orig_node_get_router(res_dst_orig_node);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1477,7 +1484,8 @@ static bool send_other_tt_response(struct bat_priv *bat_priv,
|
||||||
full_table = false;
|
full_table = false;
|
||||||
|
|
||||||
/* In this version, fragmentation is not implemented, then
|
/* In this version, fragmentation is not implemented, then
|
||||||
* I'll send only one packet with as much TT entries as I can */
|
* I'll send only one packet with as much TT entries as I can
|
||||||
|
*/
|
||||||
if (!full_table) {
|
if (!full_table) {
|
||||||
spin_lock_bh(&req_dst_orig_node->tt_buff_lock);
|
spin_lock_bh(&req_dst_orig_node->tt_buff_lock);
|
||||||
tt_len = req_dst_orig_node->tt_buff_len;
|
tt_len = req_dst_orig_node->tt_buff_len;
|
||||||
|
@ -1532,7 +1540,7 @@ static bool send_other_tt_response(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_TT_RESPONSE_TX);
|
batadv_inc_counter(bat_priv, BAT_CNT_TT_RESPONSE_TX);
|
||||||
|
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
ret = true;
|
ret = true;
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1541,11 +1549,11 @@ unlock:
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (res_dst_orig_node)
|
if (res_dst_orig_node)
|
||||||
orig_node_free_ref(res_dst_orig_node);
|
batadv_orig_node_free_ref(res_dst_orig_node);
|
||||||
if (req_dst_orig_node)
|
if (req_dst_orig_node)
|
||||||
orig_node_free_ref(req_dst_orig_node);
|
batadv_orig_node_free_ref(req_dst_orig_node);
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
if (!ret)
|
if (!ret)
|
||||||
|
@ -1580,7 +1588,7 @@ static bool send_my_tt_response(struct bat_priv *bat_priv,
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
neigh_node = orig_node_get_router(orig_node);
|
neigh_node = batadv_orig_node_get_router(orig_node);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1589,7 +1597,8 @@ static bool send_my_tt_response(struct bat_priv *bat_priv,
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* If the full table has been explicitly requested or the gap
|
/* If the full table has been explicitly requested or the gap
|
||||||
* is too big send the whole local translation table */
|
* is too big send the whole local translation table
|
||||||
|
*/
|
||||||
if (tt_request->flags & TT_FULL_TABLE || my_ttvn != req_ttvn ||
|
if (tt_request->flags & TT_FULL_TABLE || my_ttvn != req_ttvn ||
|
||||||
!bat_priv->tt_buff)
|
!bat_priv->tt_buff)
|
||||||
full_table = true;
|
full_table = true;
|
||||||
|
@ -1597,7 +1606,8 @@ static bool send_my_tt_response(struct bat_priv *bat_priv,
|
||||||
full_table = false;
|
full_table = false;
|
||||||
|
|
||||||
/* In this version, fragmentation is not implemented, then
|
/* In this version, fragmentation is not implemented, then
|
||||||
* I'll send only one packet with as much TT entries as I can */
|
* I'll send only one packet with as much TT entries as I can
|
||||||
|
*/
|
||||||
if (!full_table) {
|
if (!full_table) {
|
||||||
spin_lock_bh(&bat_priv->tt_buff_lock);
|
spin_lock_bh(&bat_priv->tt_buff_lock);
|
||||||
tt_len = bat_priv->tt_buff_len;
|
tt_len = bat_priv->tt_buff_len;
|
||||||
|
@ -1650,7 +1660,7 @@ static bool send_my_tt_response(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_TT_RESPONSE_TX);
|
batadv_inc_counter(bat_priv, BAT_CNT_TT_RESPONSE_TX);
|
||||||
|
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
ret = true;
|
ret = true;
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1658,9 +1668,9 @@ unlock:
|
||||||
spin_unlock_bh(&bat_priv->tt_buff_lock);
|
spin_unlock_bh(&bat_priv->tt_buff_lock);
|
||||||
out:
|
out:
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (primary_if)
|
if (primary_if)
|
||||||
hardif_free_ref(primary_if);
|
hardif_free_ref(primary_if);
|
||||||
if (!ret)
|
if (!ret)
|
||||||
|
@ -1669,12 +1679,12 @@ out:
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool send_tt_response(struct bat_priv *bat_priv,
|
bool batadv_send_tt_response(struct bat_priv *bat_priv,
|
||||||
struct tt_query_packet *tt_request)
|
struct tt_query_packet *tt_request)
|
||||||
{
|
{
|
||||||
if (is_my_mac(tt_request->dst)) {
|
if (batadv_is_my_mac(tt_request->dst)) {
|
||||||
/* don't answer backbone gws! */
|
/* don't answer backbone gws! */
|
||||||
if (bla_is_backbone_gw_orig(bat_priv, tt_request->src))
|
if (batadv_bla_is_backbone_gw_orig(bat_priv, tt_request->src))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
return send_my_tt_response(bat_priv, tt_request);
|
return send_my_tt_response(bat_priv, tt_request);
|
||||||
|
@ -1689,18 +1699,19 @@ static void _tt_update_changes(struct bat_priv *bat_priv,
|
||||||
uint16_t tt_num_changes, uint8_t ttvn)
|
uint16_t tt_num_changes, uint8_t ttvn)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
int is_wifi;
|
||||||
|
|
||||||
for (i = 0; i < tt_num_changes; i++) {
|
for (i = 0; i < tt_num_changes; i++) {
|
||||||
if ((tt_change + i)->flags & TT_CLIENT_DEL)
|
if ((tt_change + i)->flags & TT_CLIENT_DEL) {
|
||||||
tt_global_del(bat_priv, orig_node,
|
tt_global_del(bat_priv, orig_node,
|
||||||
(tt_change + i)->addr,
|
(tt_change + i)->addr,
|
||||||
"tt removed by changes",
|
"tt removed by changes",
|
||||||
(tt_change + i)->flags & TT_CLIENT_ROAM);
|
(tt_change + i)->flags & TT_CLIENT_ROAM);
|
||||||
else
|
} else {
|
||||||
if (!tt_global_add(bat_priv, orig_node,
|
is_wifi = (tt_change + i)->flags & TT_CLIENT_WIFI;
|
||||||
(tt_change + i)->addr, ttvn, false,
|
if (!batadv_tt_global_add(bat_priv, orig_node,
|
||||||
(tt_change + i)->flags &
|
(tt_change + i)->addr, ttvn,
|
||||||
TT_CLIENT_WIFI))
|
false, is_wifi))
|
||||||
/* In case of problem while storing a
|
/* In case of problem while storing a
|
||||||
* global_entry, we stop the updating
|
* global_entry, we stop the updating
|
||||||
* procedure without committing the
|
* procedure without committing the
|
||||||
|
@ -1708,6 +1719,7 @@ static void _tt_update_changes(struct bat_priv *bat_priv,
|
||||||
* corrupted data on tt_request
|
* corrupted data on tt_request
|
||||||
*/
|
*/
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
orig_node->tt_initialised = true;
|
orig_node->tt_initialised = true;
|
||||||
}
|
}
|
||||||
|
@ -1722,7 +1734,7 @@ static void tt_fill_gtable(struct bat_priv *bat_priv,
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* Purge the old table first.. */
|
/* Purge the old table first.. */
|
||||||
tt_global_del_orig(bat_priv, orig_node, "Received full table");
|
batadv_tt_global_del_orig(bat_priv, orig_node, "Received full table");
|
||||||
|
|
||||||
_tt_update_changes(bat_priv, orig_node,
|
_tt_update_changes(bat_priv, orig_node,
|
||||||
(struct tt_change *)(tt_response + 1),
|
(struct tt_change *)(tt_response + 1),
|
||||||
|
@ -1738,7 +1750,7 @@ static void tt_fill_gtable(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void tt_update_changes(struct bat_priv *bat_priv,
|
static void tt_update_changes(struct bat_priv *bat_priv,
|
||||||
|
@ -1754,7 +1766,7 @@ static void tt_update_changes(struct bat_priv *bat_priv,
|
||||||
atomic_set(&orig_node->last_ttvn, ttvn);
|
atomic_set(&orig_node->last_ttvn, ttvn);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool is_my_client(struct bat_priv *bat_priv, const uint8_t *addr)
|
bool batadv_is_my_client(struct bat_priv *bat_priv, const uint8_t *addr)
|
||||||
{
|
{
|
||||||
struct tt_local_entry *tt_local_entry = NULL;
|
struct tt_local_entry *tt_local_entry = NULL;
|
||||||
bool ret = false;
|
bool ret = false;
|
||||||
|
@ -1763,7 +1775,8 @@ bool is_my_client(struct bat_priv *bat_priv, const uint8_t *addr)
|
||||||
if (!tt_local_entry)
|
if (!tt_local_entry)
|
||||||
goto out;
|
goto out;
|
||||||
/* Check if the client has been logically deleted (but is kept for
|
/* Check if the client has been logically deleted (but is kept for
|
||||||
* consistency purpose) */
|
* consistency purpose)
|
||||||
|
*/
|
||||||
if (tt_local_entry->common.flags & TT_CLIENT_PENDING)
|
if (tt_local_entry->common.flags & TT_CLIENT_PENDING)
|
||||||
goto out;
|
goto out;
|
||||||
ret = true;
|
ret = true;
|
||||||
|
@ -1773,8 +1786,8 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void handle_tt_response(struct bat_priv *bat_priv,
|
void batadv_handle_tt_response(struct bat_priv *bat_priv,
|
||||||
struct tt_query_packet *tt_response)
|
struct tt_query_packet *tt_response)
|
||||||
{
|
{
|
||||||
struct tt_req_node *node, *safe;
|
struct tt_req_node *node, *safe;
|
||||||
struct orig_node *orig_node = NULL;
|
struct orig_node *orig_node = NULL;
|
||||||
|
@ -1786,7 +1799,7 @@ void handle_tt_response(struct bat_priv *bat_priv,
|
||||||
(tt_response->flags & TT_FULL_TABLE ? 'F' : '.'));
|
(tt_response->flags & TT_FULL_TABLE ? 'F' : '.'));
|
||||||
|
|
||||||
/* we should have never asked a backbone gw */
|
/* we should have never asked a backbone gw */
|
||||||
if (bla_is_backbone_gw_orig(bat_priv, tt_response->src))
|
if (batadv_bla_is_backbone_gw_orig(bat_priv, tt_response->src))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
orig_node = orig_hash_find(bat_priv, tt_response->src);
|
orig_node = orig_hash_find(bat_priv, tt_response->src);
|
||||||
|
@ -1814,14 +1827,15 @@ void handle_tt_response(struct bat_priv *bat_priv,
|
||||||
/* Recalculate the CRC for this orig_node and store it */
|
/* Recalculate the CRC for this orig_node and store it */
|
||||||
orig_node->tt_crc = tt_global_crc(bat_priv, orig_node);
|
orig_node->tt_crc = tt_global_crc(bat_priv, orig_node);
|
||||||
/* Roaming phase is over: tables are in sync again. I can
|
/* Roaming phase is over: tables are in sync again. I can
|
||||||
* unset the flag */
|
* unset the flag
|
||||||
|
*/
|
||||||
orig_node->tt_poss_change = false;
|
orig_node->tt_poss_change = false;
|
||||||
out:
|
out:
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
int tt_init(struct bat_priv *bat_priv)
|
int batadv_tt_init(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
|
@ -1871,7 +1885,8 @@ static void tt_roam_purge(struct bat_priv *bat_priv)
|
||||||
* maximum number of possible roaming phases. In this case the ROAMING_ADV
|
* maximum number of possible roaming phases. In this case the ROAMING_ADV
|
||||||
* will not be sent.
|
* will not be sent.
|
||||||
*
|
*
|
||||||
* returns true if the ROAMING_ADV can be sent, false otherwise */
|
* returns true if the ROAMING_ADV can be sent, false otherwise
|
||||||
|
*/
|
||||||
static bool tt_check_roam_count(struct bat_priv *bat_priv,
|
static bool tt_check_roam_count(struct bat_priv *bat_priv,
|
||||||
uint8_t *client)
|
uint8_t *client)
|
||||||
{
|
{
|
||||||
|
@ -1880,7 +1895,8 @@ static bool tt_check_roam_count(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
spin_lock_bh(&bat_priv->tt_roam_list_lock);
|
spin_lock_bh(&bat_priv->tt_roam_list_lock);
|
||||||
/* The new tt_req will be issued only if I'm not waiting for a
|
/* The new tt_req will be issued only if I'm not waiting for a
|
||||||
* reply from the same orig_node yet */
|
* reply from the same orig_node yet
|
||||||
|
*/
|
||||||
list_for_each_entry(tt_roam_node, &bat_priv->tt_roam_list, list) {
|
list_for_each_entry(tt_roam_node, &bat_priv->tt_roam_list, list) {
|
||||||
if (!compare_eth(tt_roam_node->addr, client))
|
if (!compare_eth(tt_roam_node->addr, client))
|
||||||
continue;
|
continue;
|
||||||
|
@ -1923,7 +1939,8 @@ static void send_roam_adv(struct bat_priv *bat_priv, uint8_t *client,
|
||||||
struct hard_iface *primary_if;
|
struct hard_iface *primary_if;
|
||||||
|
|
||||||
/* before going on we have to check whether the client has
|
/* before going on we have to check whether the client has
|
||||||
* already roamed to us too many times */
|
* already roamed to us too many times
|
||||||
|
*/
|
||||||
if (!tt_check_roam_count(bat_priv, client))
|
if (!tt_check_roam_count(bat_priv, client))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1947,7 +1964,7 @@ static void send_roam_adv(struct bat_priv *bat_priv, uint8_t *client,
|
||||||
memcpy(roam_adv_packet->dst, orig_node->orig, ETH_ALEN);
|
memcpy(roam_adv_packet->dst, orig_node->orig, ETH_ALEN);
|
||||||
memcpy(roam_adv_packet->client, client, ETH_ALEN);
|
memcpy(roam_adv_packet->client, client, ETH_ALEN);
|
||||||
|
|
||||||
neigh_node = orig_node_get_router(orig_node);
|
neigh_node = batadv_orig_node_get_router(orig_node);
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -1957,12 +1974,12 @@ static void send_roam_adv(struct bat_priv *bat_priv, uint8_t *client,
|
||||||
|
|
||||||
batadv_inc_counter(bat_priv, BAT_CNT_TT_ROAM_ADV_TX);
|
batadv_inc_counter(bat_priv, BAT_CNT_TT_ROAM_ADV_TX);
|
||||||
|
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
ret = 0;
|
ret = 0;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (ret)
|
if (ret)
|
||||||
kfree_skb(skb);
|
kfree_skb(skb);
|
||||||
return;
|
return;
|
||||||
|
@ -1983,7 +2000,7 @@ static void tt_purge(struct work_struct *work)
|
||||||
tt_start_timer(bat_priv);
|
tt_start_timer(bat_priv);
|
||||||
}
|
}
|
||||||
|
|
||||||
void tt_free(struct bat_priv *bat_priv)
|
void batadv_tt_free(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
cancel_delayed_work_sync(&bat_priv->tt_work);
|
cancel_delayed_work_sync(&bat_priv->tt_work);
|
||||||
|
|
||||||
|
@ -1997,7 +2014,8 @@ void tt_free(struct bat_priv *bat_priv)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* This function will enable or disable the specified flags for all the entries
|
/* This function will enable or disable the specified flags for all the entries
|
||||||
* in the given hash table and returns the number of modified entries */
|
* in the given hash table and returns the number of modified entries
|
||||||
|
*/
|
||||||
static uint16_t tt_set_flags(struct hashtable_t *hash, uint16_t flags,
|
static uint16_t tt_set_flags(struct hashtable_t *hash, uint16_t flags,
|
||||||
bool enable)
|
bool enable)
|
||||||
{
|
{
|
||||||
|
@ -2125,7 +2143,8 @@ int batadv_tt_append_diff(struct bat_priv *bat_priv,
|
||||||
return tt_num_changes;
|
return tt_num_changes;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool is_ap_isolated(struct bat_priv *bat_priv, uint8_t *src, uint8_t *dst)
|
bool batadv_is_ap_isolated(struct bat_priv *bat_priv, uint8_t *src,
|
||||||
|
uint8_t *dst)
|
||||||
{
|
{
|
||||||
struct tt_local_entry *tt_local_entry = NULL;
|
struct tt_local_entry *tt_local_entry = NULL;
|
||||||
struct tt_global_entry *tt_global_entry = NULL;
|
struct tt_global_entry *tt_global_entry = NULL;
|
||||||
|
@ -2155,24 +2174,27 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void tt_update_orig(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
void batadv_tt_update_orig(struct bat_priv *bat_priv,
|
||||||
const unsigned char *tt_buff, uint8_t tt_num_changes,
|
struct orig_node *orig_node,
|
||||||
uint8_t ttvn, uint16_t tt_crc)
|
const unsigned char *tt_buff, uint8_t tt_num_changes,
|
||||||
|
uint8_t ttvn, uint16_t tt_crc)
|
||||||
{
|
{
|
||||||
uint8_t orig_ttvn = (uint8_t)atomic_read(&orig_node->last_ttvn);
|
uint8_t orig_ttvn = (uint8_t)atomic_read(&orig_node->last_ttvn);
|
||||||
bool full_table = true;
|
bool full_table = true;
|
||||||
|
|
||||||
/* don't care about a backbone gateways updates. */
|
/* don't care about a backbone gateways updates. */
|
||||||
if (bla_is_backbone_gw_orig(bat_priv, orig_node->orig))
|
if (batadv_bla_is_backbone_gw_orig(bat_priv, orig_node->orig))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
/* orig table not initialised AND first diff is in the OGM OR the ttvn
|
/* orig table not initialised AND first diff is in the OGM OR the ttvn
|
||||||
* increased by one -> we can apply the attached changes */
|
* increased by one -> we can apply the attached changes
|
||||||
|
*/
|
||||||
if ((!orig_node->tt_initialised && ttvn == 1) ||
|
if ((!orig_node->tt_initialised && ttvn == 1) ||
|
||||||
ttvn - orig_ttvn == 1) {
|
ttvn - orig_ttvn == 1) {
|
||||||
/* the OGM could not contain the changes due to their size or
|
/* the OGM could not contain the changes due to their size or
|
||||||
* because they have already been sent TT_OGM_APPEND_MAX times.
|
* because they have already been sent TT_OGM_APPEND_MAX times.
|
||||||
* In this case send a tt request */
|
* In this case send a tt request
|
||||||
|
*/
|
||||||
if (!tt_num_changes) {
|
if (!tt_num_changes) {
|
||||||
full_table = false;
|
full_table = false;
|
||||||
goto request_table;
|
goto request_table;
|
||||||
|
@ -2183,7 +2205,8 @@ void tt_update_orig(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
|
|
||||||
/* Even if we received the precomputed crc with the OGM, we
|
/* Even if we received the precomputed crc with the OGM, we
|
||||||
* prefer to recompute it to spot any possible inconsistency
|
* prefer to recompute it to spot any possible inconsistency
|
||||||
* in the global table */
|
* in the global table
|
||||||
|
*/
|
||||||
orig_node->tt_crc = tt_global_crc(bat_priv, orig_node);
|
orig_node->tt_crc = tt_global_crc(bat_priv, orig_node);
|
||||||
|
|
||||||
/* The ttvn alone is not enough to guarantee consistency
|
/* The ttvn alone is not enough to guarantee consistency
|
||||||
|
@ -2193,17 +2216,19 @@ void tt_update_orig(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
* consistent or not. E.g. a node could disconnect while its
|
* consistent or not. E.g. a node could disconnect while its
|
||||||
* ttvn is X and reconnect on ttvn = X + TTVN_MAX: in this case
|
* ttvn is X and reconnect on ttvn = X + TTVN_MAX: in this case
|
||||||
* checking the CRC value is mandatory to detect the
|
* checking the CRC value is mandatory to detect the
|
||||||
* inconsistency */
|
* inconsistency
|
||||||
|
*/
|
||||||
if (orig_node->tt_crc != tt_crc)
|
if (orig_node->tt_crc != tt_crc)
|
||||||
goto request_table;
|
goto request_table;
|
||||||
|
|
||||||
/* Roaming phase is over: tables are in sync again. I can
|
/* Roaming phase is over: tables are in sync again. I can
|
||||||
* unset the flag */
|
* unset the flag
|
||||||
|
*/
|
||||||
orig_node->tt_poss_change = false;
|
orig_node->tt_poss_change = false;
|
||||||
} else {
|
} else {
|
||||||
/* if we missed more than one change or our tables are not
|
/* if we missed more than one change or our tables are not
|
||||||
* in sync anymore -> request fresh tt data */
|
* in sync anymore -> request fresh tt data
|
||||||
|
*/
|
||||||
if (!orig_node->tt_initialised || ttvn != orig_ttvn ||
|
if (!orig_node->tt_initialised || ttvn != orig_ttvn ||
|
||||||
orig_node->tt_crc != tt_crc) {
|
orig_node->tt_crc != tt_crc) {
|
||||||
request_table:
|
request_table:
|
||||||
|
@ -2222,7 +2247,8 @@ request_table:
|
||||||
* originator to another one. This entry is kept is still kept for consistency
|
* originator to another one. This entry is kept is still kept for consistency
|
||||||
* purposes
|
* purposes
|
||||||
*/
|
*/
|
||||||
bool tt_global_client_is_roaming(struct bat_priv *bat_priv, uint8_t *addr)
|
bool batadv_tt_global_client_is_roaming(struct bat_priv *bat_priv,
|
||||||
|
uint8_t *addr)
|
||||||
{
|
{
|
||||||
struct tt_global_entry *tt_global_entry;
|
struct tt_global_entry *tt_global_entry;
|
||||||
bool ret = false;
|
bool ret = false;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich, Antonio Quartulli
|
* Marek Lindner, Simon Wunderlich, Antonio Quartulli
|
||||||
*
|
*
|
||||||
|
@ -16,43 +15,49 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_TRANSLATION_TABLE_H_
|
#ifndef _NET_BATMAN_ADV_TRANSLATION_TABLE_H_
|
||||||
#define _NET_BATMAN_ADV_TRANSLATION_TABLE_H_
|
#define _NET_BATMAN_ADV_TRANSLATION_TABLE_H_
|
||||||
|
|
||||||
int tt_len(int changes_num);
|
int batadv_tt_len(int changes_num);
|
||||||
int tt_init(struct bat_priv *bat_priv);
|
int batadv_tt_init(struct bat_priv *bat_priv);
|
||||||
void tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
|
void batadv_tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
|
||||||
int ifindex);
|
int ifindex);
|
||||||
void tt_local_remove(struct bat_priv *bat_priv,
|
void batadv_tt_local_remove(struct bat_priv *bat_priv,
|
||||||
const uint8_t *addr, const char *message, bool roaming);
|
const uint8_t *addr, const char *message,
|
||||||
int tt_local_seq_print_text(struct seq_file *seq, void *offset);
|
bool roaming);
|
||||||
void tt_global_add_orig(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
int batadv_tt_local_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
const unsigned char *tt_buff, int tt_buff_len);
|
void batadv_tt_global_add_orig(struct bat_priv *bat_priv,
|
||||||
int tt_global_add(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
struct orig_node *orig_node,
|
||||||
const unsigned char *addr, uint8_t ttvn, bool roaming,
|
const unsigned char *tt_buff, int tt_buff_len);
|
||||||
bool wifi);
|
int batadv_tt_global_add(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
||||||
int tt_global_seq_print_text(struct seq_file *seq, void *offset);
|
const unsigned char *addr, uint8_t ttvn, bool roaming,
|
||||||
void tt_global_del_orig(struct bat_priv *bat_priv,
|
bool wifi);
|
||||||
struct orig_node *orig_node, const char *message);
|
int batadv_tt_global_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
struct orig_node *transtable_search(struct bat_priv *bat_priv,
|
void batadv_tt_global_del_orig(struct bat_priv *bat_priv,
|
||||||
const uint8_t *src, const uint8_t *addr);
|
struct orig_node *orig_node,
|
||||||
void tt_free(struct bat_priv *bat_priv);
|
const char *message);
|
||||||
bool send_tt_response(struct bat_priv *bat_priv,
|
struct orig_node *batadv_transtable_search(struct bat_priv *bat_priv,
|
||||||
struct tt_query_packet *tt_request);
|
const uint8_t *src,
|
||||||
bool is_my_client(struct bat_priv *bat_priv, const uint8_t *addr);
|
const uint8_t *addr);
|
||||||
void handle_tt_response(struct bat_priv *bat_priv,
|
void batadv_tt_free(struct bat_priv *bat_priv);
|
||||||
struct tt_query_packet *tt_response);
|
bool batadv_send_tt_response(struct bat_priv *bat_priv,
|
||||||
bool is_ap_isolated(struct bat_priv *bat_priv, uint8_t *src, uint8_t *dst);
|
struct tt_query_packet *tt_request);
|
||||||
void tt_update_orig(struct bat_priv *bat_priv, struct orig_node *orig_node,
|
bool batadv_is_my_client(struct bat_priv *bat_priv, const uint8_t *addr);
|
||||||
const unsigned char *tt_buff, uint8_t tt_num_changes,
|
void batadv_handle_tt_response(struct bat_priv *bat_priv,
|
||||||
uint8_t ttvn, uint16_t tt_crc);
|
struct tt_query_packet *tt_response);
|
||||||
|
bool batadv_is_ap_isolated(struct bat_priv *bat_priv, uint8_t *src,
|
||||||
|
uint8_t *dst);
|
||||||
|
void batadv_tt_update_orig(struct bat_priv *bat_priv,
|
||||||
|
struct orig_node *orig_node,
|
||||||
|
const unsigned char *tt_buff, uint8_t tt_num_changes,
|
||||||
|
uint8_t ttvn, uint16_t tt_crc);
|
||||||
int batadv_tt_append_diff(struct bat_priv *bat_priv,
|
int batadv_tt_append_diff(struct bat_priv *bat_priv,
|
||||||
unsigned char **packet_buff, int *packet_buff_len,
|
unsigned char **packet_buff, int *packet_buff_len,
|
||||||
int packet_min_len);
|
int packet_min_len);
|
||||||
bool tt_global_client_is_roaming(struct bat_priv *bat_priv, uint8_t *addr);
|
bool batadv_tt_global_client_is_roaming(struct bat_priv *bat_priv,
|
||||||
|
uint8_t *addr);
|
||||||
|
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_TRANSLATION_TABLE_H_ */
|
#endif /* _NET_BATMAN_ADV_TRANSLATION_TABLE_H_ */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Marek Lindner, Simon Wunderlich
|
* Marek Lindner, Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,11 +15,8 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_TYPES_H_
|
#ifndef _NET_BATMAN_ADV_TYPES_H_
|
||||||
#define _NET_BATMAN_ADV_TYPES_H_
|
#define _NET_BATMAN_ADV_TYPES_H_
|
||||||
|
|
||||||
|
@ -49,8 +45,7 @@ struct hard_iface {
|
||||||
struct rcu_head rcu;
|
struct rcu_head rcu;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/* orig_node - structure for orig_list maintaining nodes of mesh
|
||||||
* orig_node - structure for orig_list maintaining nodes of mesh
|
|
||||||
* @primary_addr: hosts primary interface address
|
* @primary_addr: hosts primary interface address
|
||||||
* @last_seen: when last packet from this node was received
|
* @last_seen: when last packet from this node was received
|
||||||
* @bcast_seqno_reset: time when the broadcast seqno window was reset
|
* @bcast_seqno_reset: time when the broadcast seqno window was reset
|
||||||
|
@ -86,7 +81,8 @@ struct orig_node {
|
||||||
* If true, then I sent a Roaming_adv to this orig_node and I have to
|
* If true, then I sent a Roaming_adv to this orig_node and I have to
|
||||||
* inspect every packet directed to it to check whether it is still
|
* inspect every packet directed to it to check whether it is still
|
||||||
* the true destination or not. This flag will be reset to false as
|
* the true destination or not. This flag will be reset to false as
|
||||||
* soon as I receive a new TTVN from this orig_node */
|
* soon as I receive a new TTVN from this orig_node
|
||||||
|
*/
|
||||||
bool tt_poss_change;
|
bool tt_poss_change;
|
||||||
uint32_t last_real_seqno;
|
uint32_t last_real_seqno;
|
||||||
uint8_t last_ttl;
|
uint8_t last_ttl;
|
||||||
|
@ -101,7 +97,8 @@ struct orig_node {
|
||||||
struct bat_priv *bat_priv;
|
struct bat_priv *bat_priv;
|
||||||
unsigned long last_frag_packet;
|
unsigned long last_frag_packet;
|
||||||
/* ogm_cnt_lock protects: bcast_own, bcast_own_sum,
|
/* ogm_cnt_lock protects: bcast_own, bcast_own_sum,
|
||||||
* neigh_node->real_bits, neigh_node->real_packet_count */
|
* neigh_node->real_bits, neigh_node->real_packet_count
|
||||||
|
*/
|
||||||
spinlock_t ogm_cnt_lock;
|
spinlock_t ogm_cnt_lock;
|
||||||
/* bcast_seqno_lock protects bcast_bits, last_bcast_seqno */
|
/* bcast_seqno_lock protects bcast_bits, last_bcast_seqno */
|
||||||
spinlock_t bcast_seqno_lock;
|
spinlock_t bcast_seqno_lock;
|
||||||
|
@ -118,8 +115,7 @@ struct gw_node {
|
||||||
struct rcu_head rcu;
|
struct rcu_head rcu;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/* neigh_node
|
||||||
* neigh_node
|
|
||||||
* @last_seen: when last packet via this neighbor was received
|
* @last_seen: when last packet via this neighbor was received
|
||||||
*/
|
*/
|
||||||
struct neigh_node {
|
struct neigh_node {
|
||||||
|
@ -191,7 +187,8 @@ struct bat_priv {
|
||||||
* If true, then I received a Roaming_adv and I have to inspect every
|
* If true, then I received a Roaming_adv and I have to inspect every
|
||||||
* packet directed to me to check whether I am still the true
|
* packet directed to me to check whether I am still the true
|
||||||
* destination or not. This flag will be reset to false as soon as I
|
* destination or not. This flag will be reset to false as soon as I
|
||||||
* increase my TTVN */
|
* increase my TTVN
|
||||||
|
*/
|
||||||
bool tt_poss_change;
|
bool tt_poss_change;
|
||||||
char num_ifaces;
|
char num_ifaces;
|
||||||
struct debug_log *debug_log;
|
struct debug_log *debug_log;
|
||||||
|
@ -326,8 +323,7 @@ struct tt_roam_node {
|
||||||
struct list_head list;
|
struct list_head list;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/* forw_packet - structure for forw_list maintaining packets to be
|
||||||
* forw_packet - structure for forw_list maintaining packets to be
|
|
||||||
* send/forwarded
|
* send/forwarded
|
||||||
*/
|
*/
|
||||||
struct forw_packet {
|
struct forw_packet {
|
||||||
|
@ -369,7 +365,8 @@ struct frag_packet_list_entry {
|
||||||
struct vis_info {
|
struct vis_info {
|
||||||
unsigned long first_seen;
|
unsigned long first_seen;
|
||||||
/* list of server-neighbors we received a vis-packet
|
/* list of server-neighbors we received a vis-packet
|
||||||
* from. we should not reply to them. */
|
* from. we should not reply to them.
|
||||||
|
*/
|
||||||
struct list_head recv_list;
|
struct list_head recv_list;
|
||||||
struct list_head send_list;
|
struct list_head send_list;
|
||||||
struct kref refcount;
|
struct kref refcount;
|
||||||
|
@ -377,7 +374,7 @@ struct vis_info {
|
||||||
struct bat_priv *bat_priv;
|
struct bat_priv *bat_priv;
|
||||||
/* this packet might be part of the vis send queue. */
|
/* this packet might be part of the vis send queue. */
|
||||||
struct sk_buff *skb_packet;
|
struct sk_buff *skb_packet;
|
||||||
/* vis_info may follow here*/
|
/* vis_info may follow here */
|
||||||
} __packed;
|
} __packed;
|
||||||
|
|
||||||
struct vis_info_entry {
|
struct vis_info_entry {
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Andreas Langer
|
* Andreas Langer
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -101,7 +99,7 @@ static int frag_create_buffer(struct list_head *head)
|
||||||
for (i = 0; i < FRAG_BUFFER_SIZE; i++) {
|
for (i = 0; i < FRAG_BUFFER_SIZE; i++) {
|
||||||
tfp = kmalloc(sizeof(*tfp), GFP_ATOMIC);
|
tfp = kmalloc(sizeof(*tfp), GFP_ATOMIC);
|
||||||
if (!tfp) {
|
if (!tfp) {
|
||||||
frag_list_free(head);
|
batadv_frag_list_free(head);
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
}
|
}
|
||||||
tfp->skb = NULL;
|
tfp->skb = NULL;
|
||||||
|
@ -151,7 +149,7 @@ mov_tail:
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void frag_list_free(struct list_head *head)
|
void batadv_frag_list_free(struct list_head *head)
|
||||||
{
|
{
|
||||||
struct frag_packet_list_entry *pf, *tmp_pf;
|
struct frag_packet_list_entry *pf, *tmp_pf;
|
||||||
|
|
||||||
|
@ -172,8 +170,8 @@ void frag_list_free(struct list_head *head)
|
||||||
* or the skb could be reassembled (skb_new will point to the new packet and
|
* or the skb could be reassembled (skb_new will point to the new packet and
|
||||||
* skb was freed)
|
* skb was freed)
|
||||||
*/
|
*/
|
||||||
int frag_reassemble_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
int batadv_frag_reassemble_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
struct sk_buff **new_skb)
|
struct sk_buff **new_skb)
|
||||||
{
|
{
|
||||||
struct orig_node *orig_node;
|
struct orig_node *orig_node;
|
||||||
struct frag_packet_list_entry *tmp_frag_entry;
|
struct frag_packet_list_entry *tmp_frag_entry;
|
||||||
|
@ -212,12 +210,12 @@ int frag_reassemble_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
int batadv_frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
struct hard_iface *hard_iface, const uint8_t dstaddr[])
|
struct hard_iface *hard_iface, const uint8_t dstaddr[])
|
||||||
{
|
{
|
||||||
struct unicast_packet tmp_uc, *unicast_packet;
|
struct unicast_packet tmp_uc, *unicast_packet;
|
||||||
struct hard_iface *primary_if;
|
struct hard_iface *primary_if;
|
||||||
|
@ -242,8 +240,8 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
memcpy(&tmp_uc, unicast_packet, uc_hdr_len);
|
memcpy(&tmp_uc, unicast_packet, uc_hdr_len);
|
||||||
skb_split(skb, frag_skb, data_len / 2 + uc_hdr_len);
|
skb_split(skb, frag_skb, data_len / 2 + uc_hdr_len);
|
||||||
|
|
||||||
if (my_skb_head_push(skb, ucf_hdr_len - uc_hdr_len) < 0 ||
|
if (batadv_skb_head_push(skb, ucf_hdr_len - uc_hdr_len) < 0 ||
|
||||||
my_skb_head_push(frag_skb, ucf_hdr_len) < 0)
|
batadv_skb_head_push(frag_skb, ucf_hdr_len) < 0)
|
||||||
goto drop_frag;
|
goto drop_frag;
|
||||||
|
|
||||||
frag1 = (struct unicast_frag_packet *)skb->data;
|
frag1 = (struct unicast_frag_packet *)skb->data;
|
||||||
|
@ -268,8 +266,8 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
frag1->seqno = htons(seqno - 1);
|
frag1->seqno = htons(seqno - 1);
|
||||||
frag2->seqno = htons(seqno);
|
frag2->seqno = htons(seqno);
|
||||||
|
|
||||||
send_skb_packet(skb, hard_iface, dstaddr);
|
batadv_send_skb_packet(skb, hard_iface, dstaddr);
|
||||||
send_skb_packet(frag_skb, hard_iface, dstaddr);
|
batadv_send_skb_packet(frag_skb, hard_iface, dstaddr);
|
||||||
ret = NET_RX_SUCCESS;
|
ret = NET_RX_SUCCESS;
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
@ -283,7 +281,7 @@ out:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int unicast_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv)
|
int batadv_unicast_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct ethhdr *ethhdr = (struct ethhdr *)skb->data;
|
struct ethhdr *ethhdr = (struct ethhdr *)skb->data;
|
||||||
struct unicast_packet *unicast_packet;
|
struct unicast_packet *unicast_packet;
|
||||||
|
@ -294,28 +292,26 @@ int unicast_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv)
|
||||||
|
|
||||||
/* get routing information */
|
/* get routing information */
|
||||||
if (is_multicast_ether_addr(ethhdr->h_dest)) {
|
if (is_multicast_ether_addr(ethhdr->h_dest)) {
|
||||||
orig_node = gw_get_selected_orig(bat_priv);
|
orig_node = batadv_gw_get_selected_orig(bat_priv);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
goto find_router;
|
goto find_router;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* check for tt host - increases orig_node refcount.
|
/* check for tt host - increases orig_node refcount.
|
||||||
* returns NULL in case of AP isolation */
|
* returns NULL in case of AP isolation
|
||||||
orig_node = transtable_search(bat_priv, ethhdr->h_source,
|
*/
|
||||||
ethhdr->h_dest);
|
orig_node = batadv_transtable_search(bat_priv, ethhdr->h_source,
|
||||||
|
ethhdr->h_dest);
|
||||||
find_router:
|
find_router:
|
||||||
/**
|
/* find_router():
|
||||||
* find_router():
|
|
||||||
* - if orig_node is NULL it returns NULL
|
* - if orig_node is NULL it returns NULL
|
||||||
* - increases neigh_nodes refcount if found.
|
* - increases neigh_nodes refcount if found.
|
||||||
*/
|
*/
|
||||||
neigh_node = find_router(bat_priv, orig_node, NULL);
|
neigh_node = batadv_find_router(bat_priv, orig_node, NULL);
|
||||||
|
|
||||||
if (!neigh_node)
|
if (!neigh_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
if (my_skb_head_push(skb, sizeof(*unicast_packet)) < 0)
|
if (batadv_skb_head_push(skb, sizeof(*unicast_packet)) < 0)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
unicast_packet = (struct unicast_packet *)skb->data;
|
unicast_packet = (struct unicast_packet *)skb->data;
|
||||||
|
@ -336,7 +332,7 @@ find_router:
|
||||||
* try to reroute it because the ttvn contained in the header is less
|
* try to reroute it because the ttvn contained in the header is less
|
||||||
* than the current one
|
* than the current one
|
||||||
*/
|
*/
|
||||||
if (tt_global_client_is_roaming(bat_priv, ethhdr->h_dest))
|
if (batadv_tt_global_client_is_roaming(bat_priv, ethhdr->h_dest))
|
||||||
unicast_packet->ttvn = unicast_packet->ttvn - 1;
|
unicast_packet->ttvn = unicast_packet->ttvn - 1;
|
||||||
|
|
||||||
if (atomic_read(&bat_priv->fragmentation) &&
|
if (atomic_read(&bat_priv->fragmentation) &&
|
||||||
|
@ -344,20 +340,21 @@ find_router:
|
||||||
neigh_node->if_incoming->net_dev->mtu) {
|
neigh_node->if_incoming->net_dev->mtu) {
|
||||||
/* send frag skb decreases ttl */
|
/* send frag skb decreases ttl */
|
||||||
unicast_packet->header.ttl++;
|
unicast_packet->header.ttl++;
|
||||||
ret = frag_send_skb(skb, bat_priv,
|
ret = batadv_frag_send_skb(skb, bat_priv,
|
||||||
neigh_node->if_incoming, neigh_node->addr);
|
neigh_node->if_incoming,
|
||||||
|
neigh_node->addr);
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr);
|
||||||
ret = 0;
|
ret = 0;
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (neigh_node)
|
if (neigh_node)
|
||||||
neigh_node_free_ref(neigh_node);
|
batadv_neigh_node_free_ref(neigh_node);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
if (ret == 1)
|
if (ret == 1)
|
||||||
kfree_skb(skb);
|
kfree_skb(skb);
|
||||||
return ret;
|
return ret;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Andreas Langer
|
* Andreas Langer
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_UNICAST_H_
|
#ifndef _NET_BATMAN_ADV_UNICAST_H_
|
||||||
|
@ -27,12 +25,13 @@
|
||||||
#define FRAG_TIMEOUT 10000 /* purge frag list entries after time in ms */
|
#define FRAG_TIMEOUT 10000 /* purge frag list entries after time in ms */
|
||||||
#define FRAG_BUFFER_SIZE 6 /* number of list elements in buffer */
|
#define FRAG_BUFFER_SIZE 6 /* number of list elements in buffer */
|
||||||
|
|
||||||
int frag_reassemble_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
int batadv_frag_reassemble_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
struct sk_buff **new_skb);
|
struct sk_buff **new_skb);
|
||||||
void frag_list_free(struct list_head *head);
|
void batadv_frag_list_free(struct list_head *head);
|
||||||
int unicast_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv);
|
int batadv_unicast_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv);
|
||||||
int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
int batadv_frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
|
||||||
struct hard_iface *hard_iface, const uint8_t dstaddr[]);
|
struct hard_iface *hard_iface,
|
||||||
|
const uint8_t dstaddr[]);
|
||||||
|
|
||||||
static inline int frag_can_reassemble(const struct sk_buff *skb, int mtu)
|
static inline int frag_can_reassemble(const struct sk_buff *skb, int mtu)
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2008-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2008-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich
|
* Simon Wunderlich
|
||||||
*
|
*
|
||||||
|
@ -16,7 +15,6 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
@ -64,8 +62,9 @@ static int vis_info_cmp(const struct hlist_node *node, const void *data2)
|
||||||
return compare_eth(p1->vis_orig, p2->vis_orig);
|
return compare_eth(p1->vis_orig, p2->vis_orig);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* hash function to choose an entry in a hash table of given size */
|
/* hash function to choose an entry in a hash table of given size
|
||||||
/* hash algorithm from http://en.wikipedia.org/wiki/Hash_table */
|
* hash algorithm from http://en.wikipedia.org/wiki/Hash_table
|
||||||
|
*/
|
||||||
static uint32_t vis_info_choose(const void *data, uint32_t size)
|
static uint32_t vis_info_choose(const void *data, uint32_t size)
|
||||||
{
|
{
|
||||||
const struct vis_info *vis_info = data;
|
const struct vis_info *vis_info = data;
|
||||||
|
@ -118,7 +117,8 @@ static struct vis_info *vis_hash_find(struct bat_priv *bat_priv,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* insert interface to the list of interfaces of one originator, if it
|
/* insert interface to the list of interfaces of one originator, if it
|
||||||
* does not already exist in the list */
|
* does not already exist in the list
|
||||||
|
*/
|
||||||
static void vis_data_insert_interface(const uint8_t *interface,
|
static void vis_data_insert_interface(const uint8_t *interface,
|
||||||
struct hlist_head *if_list,
|
struct hlist_head *if_list,
|
||||||
bool primary)
|
bool primary)
|
||||||
|
@ -188,7 +188,7 @@ static ssize_t vis_data_read_entry(char *buff,
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int vis_seq_print_text(struct seq_file *seq, void *offset)
|
int batadv_vis_seq_print_text(struct seq_file *seq, void *offset)
|
||||||
{
|
{
|
||||||
struct hard_iface *primary_if;
|
struct hard_iface *primary_if;
|
||||||
struct hlist_node *node;
|
struct hlist_node *node;
|
||||||
|
@ -334,7 +334,8 @@ out:
|
||||||
}
|
}
|
||||||
|
|
||||||
/* add the info packet to the send list, if it was not
|
/* add the info packet to the send list, if it was not
|
||||||
* already linked in. */
|
* already linked in.
|
||||||
|
*/
|
||||||
static void send_list_add(struct bat_priv *bat_priv, struct vis_info *info)
|
static void send_list_add(struct bat_priv *bat_priv, struct vis_info *info)
|
||||||
{
|
{
|
||||||
if (list_empty(&info->send_list)) {
|
if (list_empty(&info->send_list)) {
|
||||||
|
@ -344,7 +345,8 @@ static void send_list_add(struct bat_priv *bat_priv, struct vis_info *info)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* delete the info packet from the send list, if it was
|
/* delete the info packet from the send list, if it was
|
||||||
* linked in. */
|
* linked in.
|
||||||
|
*/
|
||||||
static void send_list_del(struct vis_info *info)
|
static void send_list_del(struct vis_info *info)
|
||||||
{
|
{
|
||||||
if (!list_empty(&info->send_list)) {
|
if (!list_empty(&info->send_list)) {
|
||||||
|
@ -388,7 +390,8 @@ static int recv_list_is_in(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* try to add the packet to the vis_hash. return NULL if invalid (e.g. too old,
|
/* try to add the packet to the vis_hash. return NULL if invalid (e.g. too old,
|
||||||
* broken.. ). vis hash must be locked outside. is_new is set when the packet
|
* broken.. ). vis hash must be locked outside. is_new is set when the packet
|
||||||
* is newer than old entries in the hash. */
|
* is newer than old entries in the hash.
|
||||||
|
*/
|
||||||
static struct vis_info *add_packet(struct bat_priv *bat_priv,
|
static struct vis_info *add_packet(struct bat_priv *bat_priv,
|
||||||
struct vis_packet *vis_packet,
|
struct vis_packet *vis_packet,
|
||||||
int vis_info_len, int *is_new,
|
int vis_info_len, int *is_new,
|
||||||
|
@ -462,7 +465,7 @@ static struct vis_info *add_packet(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* Make it a broadcast packet, if required */
|
/* Make it a broadcast packet, if required */
|
||||||
if (make_broadcast)
|
if (make_broadcast)
|
||||||
memcpy(packet->target_orig, broadcast_addr, ETH_ALEN);
|
memcpy(packet->target_orig, batadv_broadcast_addr, ETH_ALEN);
|
||||||
|
|
||||||
/* repair if entries is longer than packet. */
|
/* repair if entries is longer than packet. */
|
||||||
if (packet->entries * sizeof(struct vis_info_entry) > vis_info_len)
|
if (packet->entries * sizeof(struct vis_info_entry) > vis_info_len)
|
||||||
|
@ -483,9 +486,9 @@ static struct vis_info *add_packet(struct bat_priv *bat_priv,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* handle the server sync packet, forward if needed. */
|
/* handle the server sync packet, forward if needed. */
|
||||||
void receive_server_sync_packet(struct bat_priv *bat_priv,
|
void batadv_receive_server_sync_packet(struct bat_priv *bat_priv,
|
||||||
struct vis_packet *vis_packet,
|
struct vis_packet *vis_packet,
|
||||||
int vis_info_len)
|
int vis_info_len)
|
||||||
{
|
{
|
||||||
struct vis_info *info;
|
struct vis_info *info;
|
||||||
int is_new, make_broadcast;
|
int is_new, make_broadcast;
|
||||||
|
@ -500,7 +503,8 @@ void receive_server_sync_packet(struct bat_priv *bat_priv,
|
||||||
goto end;
|
goto end;
|
||||||
|
|
||||||
/* only if we are server ourselves and packet is newer than the one in
|
/* only if we are server ourselves and packet is newer than the one in
|
||||||
* hash.*/
|
* hash.
|
||||||
|
*/
|
||||||
if (vis_server == VIS_TYPE_SERVER_SYNC && is_new)
|
if (vis_server == VIS_TYPE_SERVER_SYNC && is_new)
|
||||||
send_list_add(bat_priv, info);
|
send_list_add(bat_priv, info);
|
||||||
end:
|
end:
|
||||||
|
@ -508,9 +512,9 @@ end:
|
||||||
}
|
}
|
||||||
|
|
||||||
/* handle an incoming client update packet and schedule forward if needed. */
|
/* handle an incoming client update packet and schedule forward if needed. */
|
||||||
void receive_client_update_packet(struct bat_priv *bat_priv,
|
void batadv_receive_client_update_packet(struct bat_priv *bat_priv,
|
||||||
struct vis_packet *vis_packet,
|
struct vis_packet *vis_packet,
|
||||||
int vis_info_len)
|
int vis_info_len)
|
||||||
{
|
{
|
||||||
struct vis_info *info;
|
struct vis_info *info;
|
||||||
struct vis_packet *packet;
|
struct vis_packet *packet;
|
||||||
|
@ -524,7 +528,7 @@ void receive_client_update_packet(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
/* Are we the target for this VIS packet? */
|
/* Are we the target for this VIS packet? */
|
||||||
if (vis_server == VIS_TYPE_SERVER_SYNC &&
|
if (vis_server == VIS_TYPE_SERVER_SYNC &&
|
||||||
is_my_mac(vis_packet->target_orig))
|
batadv_is_my_mac(vis_packet->target_orig))
|
||||||
are_target = 1;
|
are_target = 1;
|
||||||
|
|
||||||
spin_lock_bh(&bat_priv->vis_hash_lock);
|
spin_lock_bh(&bat_priv->vis_hash_lock);
|
||||||
|
@ -543,7 +547,7 @@ void receive_client_update_packet(struct bat_priv *bat_priv,
|
||||||
send_list_add(bat_priv, info);
|
send_list_add(bat_priv, info);
|
||||||
|
|
||||||
/* ... we're not the recipient (and thus need to forward). */
|
/* ... we're not the recipient (and thus need to forward). */
|
||||||
} else if (!is_my_mac(packet->target_orig)) {
|
} else if (!batadv_is_my_mac(packet->target_orig)) {
|
||||||
send_list_add(bat_priv, info);
|
send_list_add(bat_priv, info);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -554,7 +558,8 @@ end:
|
||||||
/* Walk the originators and find the VIS server with the best tq. Set the packet
|
/* Walk the originators and find the VIS server with the best tq. Set the packet
|
||||||
* address to its address and return the best_tq.
|
* address to its address and return the best_tq.
|
||||||
*
|
*
|
||||||
* Must be called with the originator hash locked */
|
* Must be called with the originator hash locked
|
||||||
|
*/
|
||||||
static int find_best_vis_server(struct bat_priv *bat_priv,
|
static int find_best_vis_server(struct bat_priv *bat_priv,
|
||||||
struct vis_info *info)
|
struct vis_info *info)
|
||||||
{
|
{
|
||||||
|
@ -574,7 +579,7 @@ static int find_best_vis_server(struct bat_priv *bat_priv,
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
hlist_for_each_entry_rcu(orig_node, node, head, hash_entry) {
|
hlist_for_each_entry_rcu(orig_node, node, head, hash_entry) {
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -584,7 +589,7 @@ static int find_best_vis_server(struct bat_priv *bat_priv,
|
||||||
memcpy(packet->target_orig, orig_node->orig,
|
memcpy(packet->target_orig, orig_node->orig,
|
||||||
ETH_ALEN);
|
ETH_ALEN);
|
||||||
}
|
}
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
}
|
}
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
}
|
}
|
||||||
|
@ -605,7 +610,8 @@ static bool vis_packet_full(const struct vis_info *info)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* generates a packet of own vis data,
|
/* generates a packet of own vis data,
|
||||||
* returns 0 on success, -1 if no packet could be generated */
|
* returns 0 on success, -1 if no packet could be generated
|
||||||
|
*/
|
||||||
static int generate_vis_packet(struct bat_priv *bat_priv)
|
static int generate_vis_packet(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct hashtable_t *hash = bat_priv->orig_hash;
|
struct hashtable_t *hash = bat_priv->orig_hash;
|
||||||
|
@ -623,7 +629,7 @@ static int generate_vis_packet(struct bat_priv *bat_priv)
|
||||||
info->first_seen = jiffies;
|
info->first_seen = jiffies;
|
||||||
packet->vis_type = atomic_read(&bat_priv->vis_mode);
|
packet->vis_type = atomic_read(&bat_priv->vis_mode);
|
||||||
|
|
||||||
memcpy(packet->target_orig, broadcast_addr, ETH_ALEN);
|
memcpy(packet->target_orig, batadv_broadcast_addr, ETH_ALEN);
|
||||||
packet->header.ttl = TTL;
|
packet->header.ttl = TTL;
|
||||||
packet->seqno = htonl(ntohl(packet->seqno) + 1);
|
packet->seqno = htonl(ntohl(packet->seqno) + 1);
|
||||||
packet->entries = 0;
|
packet->entries = 0;
|
||||||
|
@ -641,7 +647,7 @@ static int generate_vis_packet(struct bat_priv *bat_priv)
|
||||||
|
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
hlist_for_each_entry_rcu(orig_node, node, head, hash_entry) {
|
hlist_for_each_entry_rcu(orig_node, node, head, hash_entry) {
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -665,7 +671,7 @@ static int generate_vis_packet(struct bat_priv *bat_priv)
|
||||||
packet->entries++;
|
packet->entries++;
|
||||||
|
|
||||||
next:
|
next:
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
|
|
||||||
if (vis_packet_full(info))
|
if (vis_packet_full(info))
|
||||||
goto unlock;
|
goto unlock;
|
||||||
|
@ -703,7 +709,8 @@ unlock:
|
||||||
}
|
}
|
||||||
|
|
||||||
/* free old vis packets. Must be called with this vis_hash_lock
|
/* free old vis packets. Must be called with this vis_hash_lock
|
||||||
* held */
|
* held
|
||||||
|
*/
|
||||||
static void purge_vis_packets(struct bat_priv *bat_priv)
|
static void purge_vis_packets(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
|
@ -757,15 +764,16 @@ static void broadcast_vis_packet(struct bat_priv *bat_priv,
|
||||||
if (!(orig_node->flags & VIS_SERVER))
|
if (!(orig_node->flags & VIS_SERVER))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/* don't send it if we already received the packet from
|
/* don't send it if we already received the packet from
|
||||||
* this node. */
|
* this node.
|
||||||
|
*/
|
||||||
if (recv_list_is_in(bat_priv, &info->recv_list,
|
if (recv_list_is_in(bat_priv, &info->recv_list,
|
||||||
orig_node->orig)) {
|
orig_node->orig)) {
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -773,11 +781,12 @@ static void broadcast_vis_packet(struct bat_priv *bat_priv,
|
||||||
hard_iface = router->if_incoming;
|
hard_iface = router->if_incoming;
|
||||||
memcpy(dstaddr, router->addr, ETH_ALEN);
|
memcpy(dstaddr, router->addr, ETH_ALEN);
|
||||||
|
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
|
|
||||||
skb = skb_clone(info->skb_packet, GFP_ATOMIC);
|
skb = skb_clone(info->skb_packet, GFP_ATOMIC);
|
||||||
if (skb)
|
if (skb)
|
||||||
send_skb_packet(skb, hard_iface, dstaddr);
|
batadv_send_skb_packet(skb, hard_iface,
|
||||||
|
dstaddr);
|
||||||
|
|
||||||
}
|
}
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
|
@ -798,19 +807,19 @@ static void unicast_vis_packet(struct bat_priv *bat_priv,
|
||||||
if (!orig_node)
|
if (!orig_node)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
router = orig_node_get_router(orig_node);
|
router = batadv_orig_node_get_router(orig_node);
|
||||||
if (!router)
|
if (!router)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
skb = skb_clone(info->skb_packet, GFP_ATOMIC);
|
skb = skb_clone(info->skb_packet, GFP_ATOMIC);
|
||||||
if (skb)
|
if (skb)
|
||||||
send_skb_packet(skb, router->if_incoming, router->addr);
|
batadv_send_skb_packet(skb, router->if_incoming, router->addr);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
if (router)
|
if (router)
|
||||||
neigh_node_free_ref(router);
|
batadv_neigh_node_free_ref(router);
|
||||||
if (orig_node)
|
if (orig_node)
|
||||||
orig_node_free_ref(orig_node);
|
batadv_orig_node_free_ref(orig_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* only send one vis packet. called from send_vis_packets() */
|
/* only send one vis packet. called from send_vis_packets() */
|
||||||
|
@ -878,8 +887,9 @@ static void send_vis_packets(struct work_struct *work)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* init the vis server. this may only be called when if_list is already
|
/* init the vis server. this may only be called when if_list is already
|
||||||
* initialized (e.g. bat0 is initialized, interfaces have been added) */
|
* initialized (e.g. bat0 is initialized, interfaces have been added)
|
||||||
int vis_init(struct bat_priv *bat_priv)
|
*/
|
||||||
|
int batadv_vis_init(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
struct vis_packet *packet;
|
struct vis_packet *packet;
|
||||||
int hash_added;
|
int hash_added;
|
||||||
|
@ -889,7 +899,7 @@ int vis_init(struct bat_priv *bat_priv)
|
||||||
|
|
||||||
spin_lock_bh(&bat_priv->vis_hash_lock);
|
spin_lock_bh(&bat_priv->vis_hash_lock);
|
||||||
|
|
||||||
bat_priv->vis_hash = hash_new(256);
|
bat_priv->vis_hash = batadv_hash_new(256);
|
||||||
if (!bat_priv->vis_hash) {
|
if (!bat_priv->vis_hash) {
|
||||||
pr_err("Can't initialize vis_hash\n");
|
pr_err("Can't initialize vis_hash\n");
|
||||||
goto err;
|
goto err;
|
||||||
|
@ -943,7 +953,7 @@ free_info:
|
||||||
bat_priv->my_vis_info = NULL;
|
bat_priv->my_vis_info = NULL;
|
||||||
err:
|
err:
|
||||||
spin_unlock_bh(&bat_priv->vis_hash_lock);
|
spin_unlock_bh(&bat_priv->vis_hash_lock);
|
||||||
vis_quit(bat_priv);
|
batadv_vis_quit(bat_priv);
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -958,7 +968,7 @@ static void free_info_ref(struct hlist_node *node, void *arg)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* shutdown vis-server */
|
/* shutdown vis-server */
|
||||||
void vis_quit(struct bat_priv *bat_priv)
|
void batadv_vis_quit(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
if (!bat_priv->vis_hash)
|
if (!bat_priv->vis_hash)
|
||||||
return;
|
return;
|
||||||
|
@ -977,6 +987,6 @@ void vis_quit(struct bat_priv *bat_priv)
|
||||||
static void start_vis_timer(struct bat_priv *bat_priv)
|
static void start_vis_timer(struct bat_priv *bat_priv)
|
||||||
{
|
{
|
||||||
INIT_DELAYED_WORK(&bat_priv->vis_work, send_vis_packets);
|
INIT_DELAYED_WORK(&bat_priv->vis_work, send_vis_packets);
|
||||||
queue_delayed_work(bat_event_workqueue, &bat_priv->vis_work,
|
queue_delayed_work(batadv_event_workqueue, &bat_priv->vis_work,
|
||||||
msecs_to_jiffies(VIS_INTERVAL));
|
msecs_to_jiffies(VIS_INTERVAL));
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/*
|
/* Copyright (C) 2008-2012 B.A.T.M.A.N. contributors:
|
||||||
* Copyright (C) 2008-2012 B.A.T.M.A.N. contributors:
|
|
||||||
*
|
*
|
||||||
* Simon Wunderlich, Marek Lindner
|
* Simon Wunderlich, Marek Lindner
|
||||||
*
|
*
|
||||||
|
@ -16,23 +15,22 @@
|
||||||
* along with this program; if not, write to the Free Software
|
* along with this program; if not, write to the Free Software
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||||
* 02110-1301, USA
|
* 02110-1301, USA
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_BATMAN_ADV_VIS_H_
|
#ifndef _NET_BATMAN_ADV_VIS_H_
|
||||||
#define _NET_BATMAN_ADV_VIS_H_
|
#define _NET_BATMAN_ADV_VIS_H_
|
||||||
|
|
||||||
#define VIS_TIMEOUT 200000 /* timeout of vis packets
|
/* timeout of vis packets in miliseconds */
|
||||||
* in miliseconds */
|
#define VIS_TIMEOUT 200000
|
||||||
|
|
||||||
int vis_seq_print_text(struct seq_file *seq, void *offset);
|
int batadv_vis_seq_print_text(struct seq_file *seq, void *offset);
|
||||||
void receive_server_sync_packet(struct bat_priv *bat_priv,
|
void batadv_receive_server_sync_packet(struct bat_priv *bat_priv,
|
||||||
struct vis_packet *vis_packet,
|
struct vis_packet *vis_packet,
|
||||||
int vis_info_len);
|
int vis_info_len);
|
||||||
void receive_client_update_packet(struct bat_priv *bat_priv,
|
void batadv_receive_client_update_packet(struct bat_priv *bat_priv,
|
||||||
struct vis_packet *vis_packet,
|
struct vis_packet *vis_packet,
|
||||||
int vis_info_len);
|
int vis_info_len);
|
||||||
int vis_init(struct bat_priv *bat_priv);
|
int batadv_vis_init(struct bat_priv *bat_priv);
|
||||||
void vis_quit(struct bat_priv *bat_priv);
|
void batadv_vis_quit(struct bat_priv *bat_priv);
|
||||||
|
|
||||||
#endif /* _NET_BATMAN_ADV_VIS_H_ */
|
#endif /* _NET_BATMAN_ADV_VIS_H_ */
|
||||||
|
|
Loading…
Reference in New Issue