提交 a230e033 编写于 作者: D David S. Miller

Merge tag 'batman-adv-for-davem' of git://git.open-mesh.org/linux-merge

Included changes:
- reduce broadcast overhead on non-lossy wired links
- fix typos in kernel doc
- use eth_hdr() when possible
- use netdev_allock_skb_ip_align() and don't deal with NET_IP_ALIGN
- change VID semantic in the BLA component
- other minor cleanups and code refactoring
Signed-off-by: NDavid S. Miller <davem@davemloft.net>
...@@ -32,7 +32,6 @@ batman-adv-y += icmp_socket.o ...@@ -32,7 +32,6 @@ batman-adv-y += icmp_socket.o
batman-adv-y += main.o batman-adv-y += main.o
batman-adv-$(CONFIG_BATMAN_ADV_NC) += network-coding.o batman-adv-$(CONFIG_BATMAN_ADV_NC) += network-coding.o
batman-adv-y += originator.o batman-adv-y += originator.o
batman-adv-y += ring_buffer.o
batman-adv-y += routing.o batman-adv-y += routing.o
batman-adv-y += send.o batman-adv-y += send.o
batman-adv-y += soft-interface.o batman-adv-y += soft-interface.o
......
...@@ -19,7 +19,6 @@ ...@@ -19,7 +19,6 @@
#include "main.h" #include "main.h"
#include "translation-table.h" #include "translation-table.h"
#include "ring_buffer.h"
#include "originator.h" #include "originator.h"
#include "routing.h" #include "routing.h"
#include "gateway_common.h" #include "gateway_common.h"
...@@ -29,16 +28,57 @@ ...@@ -29,16 +28,57 @@
#include "bat_algo.h" #include "bat_algo.h"
#include "network-coding.h" #include "network-coding.h"
/**
* batadv_ring_buffer_set - update the ring buffer with the given value
* @lq_recv: pointer to the ring buffer
* @lq_index: index to store the value at
* @value: value to store in the ring buffer
*/
static void batadv_ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index,
uint8_t value)
{
lq_recv[*lq_index] = value;
*lq_index = (*lq_index + 1) % BATADV_TQ_GLOBAL_WINDOW_SIZE;
}
/**
* batadv_ring_buffer_set - compute the average of all non-zero values stored
* in the given ring buffer
* @lq_recv: pointer to the ring buffer
*
* Returns computed average value.
*/
static uint8_t batadv_ring_buffer_avg(const uint8_t lq_recv[])
{
const uint8_t *ptr;
uint16_t count = 0, i = 0, sum = 0;
ptr = lq_recv;
while (i < BATADV_TQ_GLOBAL_WINDOW_SIZE) {
if (*ptr != 0) {
count++;
sum += *ptr;
}
i++;
ptr++;
}
if (count == 0)
return 0;
return (uint8_t)(sum / count);
}
static struct batadv_neigh_node * static struct batadv_neigh_node *
batadv_iv_ogm_neigh_new(struct batadv_hard_iface *hard_iface, batadv_iv_ogm_neigh_new(struct batadv_hard_iface *hard_iface,
const uint8_t *neigh_addr, const uint8_t *neigh_addr,
struct batadv_orig_node *orig_node, struct batadv_orig_node *orig_node,
struct batadv_orig_node *orig_neigh, __be32 seqno) struct batadv_orig_node *orig_neigh)
{ {
struct batadv_neigh_node *neigh_node; struct batadv_neigh_node *neigh_node;
neigh_node = batadv_neigh_node_new(hard_iface, neigh_addr, neigh_node = batadv_neigh_node_new(hard_iface, neigh_addr);
ntohl(seqno));
if (!neigh_node) if (!neigh_node)
goto out; goto out;
...@@ -413,18 +453,16 @@ static void batadv_iv_ogm_aggregate_new(const unsigned char *packet_buff, ...@@ -413,18 +453,16 @@ static void batadv_iv_ogm_aggregate_new(const unsigned char *packet_buff,
else else
skb_size = packet_len; skb_size = packet_len;
skb_size += ETH_HLEN + NET_IP_ALIGN; skb_size += ETH_HLEN;
forw_packet_aggr->skb = dev_alloc_skb(skb_size); forw_packet_aggr->skb = netdev_alloc_skb_ip_align(NULL, skb_size);
if (!forw_packet_aggr->skb) { if (!forw_packet_aggr->skb) {
if (!own_packet) if (!own_packet)
atomic_inc(&bat_priv->batman_queue_left); atomic_inc(&bat_priv->batman_queue_left);
kfree(forw_packet_aggr); kfree(forw_packet_aggr);
goto out; goto out;
} }
skb_reserve(forw_packet_aggr->skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(forw_packet_aggr->skb, ETH_HLEN);
INIT_HLIST_NODE(&forw_packet_aggr->list);
skb_buff = skb_put(forw_packet_aggr->skb, packet_len); skb_buff = skb_put(forw_packet_aggr->skb, packet_len);
forw_packet_aggr->packet_len = packet_len; forw_packet_aggr->packet_len = packet_len;
...@@ -590,6 +628,41 @@ static void batadv_iv_ogm_forward(struct batadv_orig_node *orig_node, ...@@ -590,6 +628,41 @@ static void batadv_iv_ogm_forward(struct batadv_orig_node *orig_node,
if_incoming, 0, batadv_iv_ogm_fwd_send_time()); if_incoming, 0, batadv_iv_ogm_fwd_send_time());
} }
/**
* batadv_iv_ogm_slide_own_bcast_window - bitshift own OGM broadcast windows for
* the given interface
* @hard_iface: the interface for which the windows have to be shifted
*/
static void
batadv_iv_ogm_slide_own_bcast_window(struct batadv_hard_iface *hard_iface)
{
struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
struct batadv_hashtable *hash = bat_priv->orig_hash;
struct hlist_head *head;
struct batadv_orig_node *orig_node;
unsigned long *word;
uint32_t i;
size_t word_index;
uint8_t *w;
for (i = 0; i < hash->size; i++) {
head = &hash->table[i];
rcu_read_lock();
hlist_for_each_entry_rcu(orig_node, head, hash_entry) {
spin_lock_bh(&orig_node->ogm_cnt_lock);
word_index = hard_iface->if_num * BATADV_NUM_WORDS;
word = &(orig_node->bcast_own[word_index]);
batadv_bit_get_packet(bat_priv, word, 1, 0);
w = &orig_node->bcast_own_sum[hard_iface->if_num];
*w = bitmap_weight(word, BATADV_TQ_LOCAL_WINDOW_SIZE);
spin_unlock_bh(&orig_node->ogm_cnt_lock);
}
rcu_read_unlock();
}
}
static void batadv_iv_ogm_schedule(struct batadv_hard_iface *hard_iface) static void batadv_iv_ogm_schedule(struct batadv_hard_iface *hard_iface)
{ {
struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface); struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
...@@ -634,7 +707,7 @@ static void batadv_iv_ogm_schedule(struct batadv_hard_iface *hard_iface) ...@@ -634,7 +707,7 @@ static void batadv_iv_ogm_schedule(struct batadv_hard_iface *hard_iface)
batadv_ogm_packet->gw_flags = BATADV_NO_FLAGS; batadv_ogm_packet->gw_flags = BATADV_NO_FLAGS;
} }
batadv_slide_own_bcast_window(hard_iface); batadv_iv_ogm_slide_own_bcast_window(hard_iface);
batadv_iv_ogm_queue_add(bat_priv, hard_iface->bat_iv.ogm_buff, batadv_iv_ogm_queue_add(bat_priv, hard_iface->bat_iv.ogm_buff,
hard_iface->bat_iv.ogm_buff_len, hard_iface, 1, hard_iface->bat_iv.ogm_buff_len, hard_iface, 1,
batadv_iv_ogm_emit_send_time(bat_priv)); batadv_iv_ogm_emit_send_time(bat_priv));
...@@ -670,7 +743,7 @@ batadv_iv_ogm_orig_update(struct batadv_priv *bat_priv, ...@@ -670,7 +743,7 @@ batadv_iv_ogm_orig_update(struct batadv_priv *bat_priv,
if (batadv_compare_eth(neigh_addr, ethhdr->h_source) && if (batadv_compare_eth(neigh_addr, ethhdr->h_source) &&
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 (WARN(neigh_node, "too many matching neigh_nodes"))
batadv_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;
...@@ -696,8 +769,7 @@ batadv_iv_ogm_orig_update(struct batadv_priv *bat_priv, ...@@ -696,8 +769,7 @@ batadv_iv_ogm_orig_update(struct batadv_priv *bat_priv,
neigh_node = batadv_iv_ogm_neigh_new(if_incoming, neigh_node = batadv_iv_ogm_neigh_new(if_incoming,
ethhdr->h_source, ethhdr->h_source,
orig_node, orig_tmp, orig_node, orig_tmp);
batadv_ogm_packet->seqno);
batadv_orig_node_free_ref(orig_tmp); batadv_orig_node_free_ref(orig_tmp);
if (!neigh_node) if (!neigh_node)
...@@ -829,8 +901,7 @@ static int batadv_iv_ogm_calc_tq(struct batadv_orig_node *orig_node, ...@@ -829,8 +901,7 @@ static int batadv_iv_ogm_calc_tq(struct batadv_orig_node *orig_node,
neigh_node = batadv_iv_ogm_neigh_new(if_incoming, neigh_node = batadv_iv_ogm_neigh_new(if_incoming,
orig_neigh_node->orig, orig_neigh_node->orig,
orig_neigh_node, orig_neigh_node,
orig_neigh_node, orig_neigh_node);
batadv_ogm_packet->seqno);
if (!neigh_node) if (!neigh_node)
goto out; goto out;
...@@ -991,7 +1062,7 @@ static void batadv_iv_ogm_process(const struct ethhdr *ethhdr, ...@@ -991,7 +1062,7 @@ static void batadv_iv_ogm_process(const struct ethhdr *ethhdr,
struct batadv_neigh_node *orig_neigh_router = NULL; struct batadv_neigh_node *orig_neigh_router = NULL;
int has_directlink_flag; int has_directlink_flag;
int is_my_addr = 0, is_my_orig = 0, is_my_oldorig = 0; int is_my_addr = 0, is_my_orig = 0, is_my_oldorig = 0;
int is_broadcast = 0, is_bidirect; int is_bidirect;
bool is_single_hop_neigh = false; bool is_single_hop_neigh = false;
bool is_from_best_next_hop = false; bool is_from_best_next_hop = false;
int is_duplicate, sameseq, simlar_ttl; int is_duplicate, sameseq, simlar_ttl;
...@@ -1054,19 +1125,9 @@ static void batadv_iv_ogm_process(const struct ethhdr *ethhdr, ...@@ -1054,19 +1125,9 @@ static void batadv_iv_ogm_process(const struct ethhdr *ethhdr,
if (batadv_compare_eth(batadv_ogm_packet->prev_sender, if (batadv_compare_eth(batadv_ogm_packet->prev_sender,
hard_iface->net_dev->dev_addr)) hard_iface->net_dev->dev_addr))
is_my_oldorig = 1; is_my_oldorig = 1;
if (is_broadcast_ether_addr(ethhdr->h_source))
is_broadcast = 1;
} }
rcu_read_unlock(); rcu_read_unlock();
if (batadv_ogm_packet->header.version != BATADV_COMPAT_VERSION) {
batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
"Drop packet: incompatible batman version (%i)\n",
batadv_ogm_packet->header.version);
return;
}
if (is_my_addr) { if (is_my_addr) {
batadv_dbg(BATADV_DBG_BATMAN, bat_priv, batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
"Drop packet: received my own broadcast (sender: %pM)\n", "Drop packet: received my own broadcast (sender: %pM)\n",
...@@ -1074,13 +1135,6 @@ static void batadv_iv_ogm_process(const struct ethhdr *ethhdr, ...@@ -1074,13 +1135,6 @@ static void batadv_iv_ogm_process(const struct ethhdr *ethhdr,
return; return;
} }
if (is_broadcast) {
batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
"Drop packet: ignoring all packets with broadcast source addr (sender: %pM)\n",
ethhdr->h_source);
return;
}
if (is_my_orig) { if (is_my_orig) {
unsigned long *word; unsigned long *word;
int offset; int offset;
...@@ -1288,7 +1342,7 @@ static int batadv_iv_ogm_receive(struct sk_buff *skb, ...@@ -1288,7 +1342,7 @@ static int batadv_iv_ogm_receive(struct sk_buff *skb,
skb->len + ETH_HLEN); skb->len + ETH_HLEN);
packet_len = skb_headlen(skb); packet_len = skb_headlen(skb);
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
packet_buff = skb->data; packet_buff = skb->data;
batadv_ogm_packet = (struct batadv_ogm_packet *)packet_buff; batadv_ogm_packet = (struct batadv_ogm_packet *)packet_buff;
......
...@@ -180,7 +180,7 @@ static struct batadv_bla_claim ...@@ -180,7 +180,7 @@ static struct batadv_bla_claim
*/ */
static struct batadv_bla_backbone_gw * static struct batadv_bla_backbone_gw *
batadv_backbone_hash_find(struct batadv_priv *bat_priv, batadv_backbone_hash_find(struct batadv_priv *bat_priv,
uint8_t *addr, short vid) uint8_t *addr, unsigned short vid)
{ {
struct batadv_hashtable *hash = bat_priv->bla.backbone_hash; struct batadv_hashtable *hash = bat_priv->bla.backbone_hash;
struct hlist_head *head; struct hlist_head *head;
...@@ -257,7 +257,7 @@ batadv_bla_del_backbone_claims(struct batadv_bla_backbone_gw *backbone_gw) ...@@ -257,7 +257,7 @@ batadv_bla_del_backbone_claims(struct batadv_bla_backbone_gw *backbone_gw)
* @claimtype: the type of the claim (CLAIM, UNCLAIM, ANNOUNCE, ...) * @claimtype: the type of the claim (CLAIM, UNCLAIM, ANNOUNCE, ...)
*/ */
static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac, static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac,
short vid, int claimtype) unsigned short vid, int claimtype)
{ {
struct sk_buff *skb; struct sk_buff *skb;
struct ethhdr *ethhdr; struct ethhdr *ethhdr;
...@@ -307,7 +307,8 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac, ...@@ -307,7 +307,8 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac,
*/ */
memcpy(ethhdr->h_source, mac, ETH_ALEN); memcpy(ethhdr->h_source, mac, ETH_ALEN);
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_send_claim(): CLAIM %pM on vid %d\n", mac, vid); "bla_send_claim(): CLAIM %pM on vid %d\n", mac,
BATADV_PRINT_VID(vid));
break; break;
case BATADV_CLAIM_TYPE_UNCLAIM: case BATADV_CLAIM_TYPE_UNCLAIM:
/* unclaim frame /* unclaim frame
...@@ -316,7 +317,7 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac, ...@@ -316,7 +317,7 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac,
memcpy(hw_src, mac, ETH_ALEN); memcpy(hw_src, mac, ETH_ALEN);
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_send_claim(): UNCLAIM %pM on vid %d\n", mac, "bla_send_claim(): UNCLAIM %pM on vid %d\n", mac,
vid); BATADV_PRINT_VID(vid));
break; break;
case BATADV_CLAIM_TYPE_ANNOUNCE: case BATADV_CLAIM_TYPE_ANNOUNCE:
/* announcement frame /* announcement frame
...@@ -325,7 +326,7 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac, ...@@ -325,7 +326,7 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac,
memcpy(hw_src, mac, ETH_ALEN); memcpy(hw_src, mac, ETH_ALEN);
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_send_claim(): ANNOUNCE of %pM on vid %d\n", "bla_send_claim(): ANNOUNCE of %pM on vid %d\n",
ethhdr->h_source, vid); ethhdr->h_source, BATADV_PRINT_VID(vid));
break; break;
case BATADV_CLAIM_TYPE_REQUEST: case BATADV_CLAIM_TYPE_REQUEST:
/* request frame /* request frame
...@@ -335,13 +336,15 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac, ...@@ -335,13 +336,15 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac,
memcpy(hw_src, mac, ETH_ALEN); memcpy(hw_src, mac, ETH_ALEN);
memcpy(ethhdr->h_dest, mac, ETH_ALEN); memcpy(ethhdr->h_dest, mac, ETH_ALEN);
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_send_claim(): REQUEST of %pM to %pMon vid %d\n", "bla_send_claim(): REQUEST of %pM to %pM on vid %d\n",
ethhdr->h_source, ethhdr->h_dest, vid); ethhdr->h_source, ethhdr->h_dest,
BATADV_PRINT_VID(vid));
break; break;
} }
if (vid != -1) if (vid & BATADV_VLAN_HAS_TAG)
skb = vlan_insert_tag(skb, htons(ETH_P_8021Q), vid); skb = vlan_insert_tag(skb, htons(ETH_P_8021Q),
vid & VLAN_VID_MASK);
skb_reset_mac_header(skb); skb_reset_mac_header(skb);
skb->protocol = eth_type_trans(skb, soft_iface); skb->protocol = eth_type_trans(skb, soft_iface);
...@@ -367,7 +370,7 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac, ...@@ -367,7 +370,7 @@ static void batadv_bla_send_claim(struct batadv_priv *bat_priv, uint8_t *mac,
*/ */
static struct batadv_bla_backbone_gw * static struct batadv_bla_backbone_gw *
batadv_bla_get_backbone_gw(struct batadv_priv *bat_priv, uint8_t *orig, batadv_bla_get_backbone_gw(struct batadv_priv *bat_priv, uint8_t *orig,
short vid, bool own_backbone) unsigned short vid, bool own_backbone)
{ {
struct batadv_bla_backbone_gw *entry; struct batadv_bla_backbone_gw *entry;
struct batadv_orig_node *orig_node; struct batadv_orig_node *orig_node;
...@@ -380,7 +383,7 @@ batadv_bla_get_backbone_gw(struct batadv_priv *bat_priv, uint8_t *orig, ...@@ -380,7 +383,7 @@ batadv_bla_get_backbone_gw(struct batadv_priv *bat_priv, uint8_t *orig,
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_get_backbone_gw(): not found (%pM, %d), creating new entry\n", "bla_get_backbone_gw(): not found (%pM, %d), creating new entry\n",
orig, vid); orig, BATADV_PRINT_VID(vid));
entry = kzalloc(sizeof(*entry), GFP_ATOMIC); entry = kzalloc(sizeof(*entry), GFP_ATOMIC);
if (!entry) if (!entry)
...@@ -434,7 +437,7 @@ batadv_bla_get_backbone_gw(struct batadv_priv *bat_priv, uint8_t *orig, ...@@ -434,7 +437,7 @@ batadv_bla_get_backbone_gw(struct batadv_priv *bat_priv, uint8_t *orig,
static void static void
batadv_bla_update_own_backbone_gw(struct batadv_priv *bat_priv, batadv_bla_update_own_backbone_gw(struct batadv_priv *bat_priv,
struct batadv_hard_iface *primary_if, struct batadv_hard_iface *primary_if,
short vid) unsigned short vid)
{ {
struct batadv_bla_backbone_gw *backbone_gw; struct batadv_bla_backbone_gw *backbone_gw;
...@@ -456,7 +459,7 @@ batadv_bla_update_own_backbone_gw(struct batadv_priv *bat_priv, ...@@ -456,7 +459,7 @@ batadv_bla_update_own_backbone_gw(struct batadv_priv *bat_priv,
*/ */
static void batadv_bla_answer_request(struct batadv_priv *bat_priv, static void batadv_bla_answer_request(struct batadv_priv *bat_priv,
struct batadv_hard_iface *primary_if, struct batadv_hard_iface *primary_if,
short vid) unsigned short vid)
{ {
struct hlist_head *head; struct hlist_head *head;
struct batadv_hashtable *hash; struct batadv_hashtable *hash;
...@@ -547,7 +550,7 @@ static void batadv_bla_send_announce(struct batadv_priv *bat_priv, ...@@ -547,7 +550,7 @@ static void batadv_bla_send_announce(struct batadv_priv *bat_priv,
* @backbone_gw: the backbone gateway which claims it * @backbone_gw: the backbone gateway which claims it
*/ */
static void batadv_bla_add_claim(struct batadv_priv *bat_priv, static void batadv_bla_add_claim(struct batadv_priv *bat_priv,
const uint8_t *mac, const short vid, const uint8_t *mac, const unsigned short vid,
struct batadv_bla_backbone_gw *backbone_gw) struct batadv_bla_backbone_gw *backbone_gw)
{ {
struct batadv_bla_claim *claim; struct batadv_bla_claim *claim;
...@@ -572,7 +575,7 @@ static void batadv_bla_add_claim(struct batadv_priv *bat_priv, ...@@ -572,7 +575,7 @@ static void batadv_bla_add_claim(struct batadv_priv *bat_priv,
atomic_set(&claim->refcount, 2); atomic_set(&claim->refcount, 2);
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_add_claim(): adding new entry %pM, vid %d to hash ...\n", "bla_add_claim(): adding new entry %pM, vid %d to hash ...\n",
mac, vid); mac, BATADV_PRINT_VID(vid));
hash_added = batadv_hash_add(bat_priv->bla.claim_hash, hash_added = batadv_hash_add(bat_priv->bla.claim_hash,
batadv_compare_claim, batadv_compare_claim,
batadv_choose_claim, claim, batadv_choose_claim, claim,
...@@ -591,7 +594,7 @@ static void batadv_bla_add_claim(struct batadv_priv *bat_priv, ...@@ -591,7 +594,7 @@ static void batadv_bla_add_claim(struct batadv_priv *bat_priv,
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_add_claim(): changing ownership for %pM, vid %d\n", "bla_add_claim(): changing ownership for %pM, vid %d\n",
mac, vid); mac, BATADV_PRINT_VID(vid));
claim->backbone_gw->crc ^= crc16(0, claim->addr, ETH_ALEN); claim->backbone_gw->crc ^= crc16(0, claim->addr, ETH_ALEN);
batadv_backbone_gw_free_ref(claim->backbone_gw); batadv_backbone_gw_free_ref(claim->backbone_gw);
...@@ -611,7 +614,7 @@ static void batadv_bla_add_claim(struct batadv_priv *bat_priv, ...@@ -611,7 +614,7 @@ static void batadv_bla_add_claim(struct batadv_priv *bat_priv,
* given mac address and vid. * given mac address and vid.
*/ */
static void batadv_bla_del_claim(struct batadv_priv *bat_priv, static void batadv_bla_del_claim(struct batadv_priv *bat_priv,
const uint8_t *mac, const short vid) const uint8_t *mac, const unsigned short vid)
{ {
struct batadv_bla_claim search_claim, *claim; struct batadv_bla_claim search_claim, *claim;
...@@ -622,7 +625,7 @@ static void batadv_bla_del_claim(struct batadv_priv *bat_priv, ...@@ -622,7 +625,7 @@ static void batadv_bla_del_claim(struct batadv_priv *bat_priv,
return; return;
batadv_dbg(BATADV_DBG_BLA, bat_priv, "bla_del_claim(): %pM, vid %d\n", batadv_dbg(BATADV_DBG_BLA, bat_priv, "bla_del_claim(): %pM, vid %d\n",
mac, vid); mac, BATADV_PRINT_VID(vid));
batadv_hash_remove(bat_priv->bla.claim_hash, batadv_compare_claim, batadv_hash_remove(bat_priv->bla.claim_hash, batadv_compare_claim,
batadv_choose_claim, claim); batadv_choose_claim, claim);
...@@ -637,7 +640,7 @@ static void batadv_bla_del_claim(struct batadv_priv *bat_priv, ...@@ -637,7 +640,7 @@ static void batadv_bla_del_claim(struct batadv_priv *bat_priv,
/* check for ANNOUNCE frame, return 1 if handled */ /* check for ANNOUNCE frame, return 1 if handled */
static int batadv_handle_announce(struct batadv_priv *bat_priv, static int batadv_handle_announce(struct batadv_priv *bat_priv,
uint8_t *an_addr, uint8_t *backbone_addr, uint8_t *an_addr, uint8_t *backbone_addr,
short vid) unsigned short vid)
{ {
struct batadv_bla_backbone_gw *backbone_gw; struct batadv_bla_backbone_gw *backbone_gw;
uint16_t crc; uint16_t crc;
...@@ -658,12 +661,13 @@ static int batadv_handle_announce(struct batadv_priv *bat_priv, ...@@ -658,12 +661,13 @@ static int batadv_handle_announce(struct batadv_priv *bat_priv,
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"handle_announce(): ANNOUNCE vid %d (sent by %pM)... CRC = %#.4x\n", "handle_announce(): ANNOUNCE vid %d (sent by %pM)... CRC = %#.4x\n",
vid, backbone_gw->orig, crc); BATADV_PRINT_VID(vid), backbone_gw->orig, crc);
if (backbone_gw->crc != crc) { if (backbone_gw->crc != crc) {
batadv_dbg(BATADV_DBG_BLA, backbone_gw->bat_priv, batadv_dbg(BATADV_DBG_BLA, backbone_gw->bat_priv,
"handle_announce(): CRC FAILED for %pM/%d (my = %#.4x, sent = %#.4x)\n", "handle_announce(): CRC FAILED for %pM/%d (my = %#.4x, sent = %#.4x)\n",
backbone_gw->orig, backbone_gw->vid, backbone_gw->orig,
BATADV_PRINT_VID(backbone_gw->vid),
backbone_gw->crc, crc); backbone_gw->crc, crc);
batadv_bla_send_request(backbone_gw); batadv_bla_send_request(backbone_gw);
...@@ -685,7 +689,7 @@ static int batadv_handle_announce(struct batadv_priv *bat_priv, ...@@ -685,7 +689,7 @@ static int batadv_handle_announce(struct batadv_priv *bat_priv,
static int batadv_handle_request(struct batadv_priv *bat_priv, static int batadv_handle_request(struct batadv_priv *bat_priv,
struct batadv_hard_iface *primary_if, struct batadv_hard_iface *primary_if,
uint8_t *backbone_addr, uint8_t *backbone_addr,
struct ethhdr *ethhdr, short vid) struct ethhdr *ethhdr, unsigned short vid)
{ {
/* check for REQUEST frame */ /* check for REQUEST frame */
if (!batadv_compare_eth(backbone_addr, ethhdr->h_dest)) if (!batadv_compare_eth(backbone_addr, ethhdr->h_dest))
...@@ -699,7 +703,7 @@ static int batadv_handle_request(struct batadv_priv *bat_priv, ...@@ -699,7 +703,7 @@ static int batadv_handle_request(struct batadv_priv *bat_priv,
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"handle_request(): REQUEST vid %d (sent by %pM)...\n", "handle_request(): REQUEST vid %d (sent by %pM)...\n",
vid, ethhdr->h_source); BATADV_PRINT_VID(vid), ethhdr->h_source);
batadv_bla_answer_request(bat_priv, primary_if, vid); batadv_bla_answer_request(bat_priv, primary_if, vid);
return 1; return 1;
...@@ -709,7 +713,7 @@ static int batadv_handle_request(struct batadv_priv *bat_priv, ...@@ -709,7 +713,7 @@ static int batadv_handle_request(struct batadv_priv *bat_priv,
static int batadv_handle_unclaim(struct batadv_priv *bat_priv, static int batadv_handle_unclaim(struct batadv_priv *bat_priv,
struct batadv_hard_iface *primary_if, struct batadv_hard_iface *primary_if,
uint8_t *backbone_addr, uint8_t *backbone_addr,
uint8_t *claim_addr, short vid) uint8_t *claim_addr, unsigned short vid)
{ {
struct batadv_bla_backbone_gw *backbone_gw; struct batadv_bla_backbone_gw *backbone_gw;
...@@ -727,7 +731,7 @@ static int batadv_handle_unclaim(struct batadv_priv *bat_priv, ...@@ -727,7 +731,7 @@ static int batadv_handle_unclaim(struct batadv_priv *bat_priv,
/* this must be an UNCLAIM frame */ /* this must be an UNCLAIM frame */
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"handle_unclaim(): UNCLAIM %pM on vid %d (sent by %pM)...\n", "handle_unclaim(): UNCLAIM %pM on vid %d (sent by %pM)...\n",
claim_addr, vid, backbone_gw->orig); claim_addr, BATADV_PRINT_VID(vid), backbone_gw->orig);
batadv_bla_del_claim(bat_priv, claim_addr, vid); batadv_bla_del_claim(bat_priv, claim_addr, vid);
batadv_backbone_gw_free_ref(backbone_gw); batadv_backbone_gw_free_ref(backbone_gw);
...@@ -738,7 +742,7 @@ static int batadv_handle_unclaim(struct batadv_priv *bat_priv, ...@@ -738,7 +742,7 @@ static int batadv_handle_unclaim(struct batadv_priv *bat_priv,
static int batadv_handle_claim(struct batadv_priv *bat_priv, static int batadv_handle_claim(struct batadv_priv *bat_priv,
struct batadv_hard_iface *primary_if, struct batadv_hard_iface *primary_if,
uint8_t *backbone_addr, uint8_t *claim_addr, uint8_t *backbone_addr, uint8_t *claim_addr,
short vid) unsigned short vid)
{ {
struct batadv_bla_backbone_gw *backbone_gw; struct batadv_bla_backbone_gw *backbone_gw;
...@@ -861,14 +865,15 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv, ...@@ -861,14 +865,15 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv,
struct batadv_bla_claim_dst *bla_dst; struct batadv_bla_claim_dst *bla_dst;
uint16_t proto; uint16_t proto;
int headlen; int headlen;
short vid = -1; unsigned short vid = BATADV_NO_FLAGS;
int ret; int ret;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
if (ntohs(ethhdr->h_proto) == ETH_P_8021Q) { if (ntohs(ethhdr->h_proto) == ETH_P_8021Q) {
vhdr = (struct vlan_ethhdr *)ethhdr; vhdr = (struct vlan_ethhdr *)ethhdr;
vid = ntohs(vhdr->h_vlan_TCI) & VLAN_VID_MASK; vid = ntohs(vhdr->h_vlan_TCI) & VLAN_VID_MASK;
vid |= BATADV_VLAN_HAS_TAG;
proto = ntohs(vhdr->h_vlan_encapsulated_proto); proto = ntohs(vhdr->h_vlan_encapsulated_proto);
headlen = sizeof(*vhdr); headlen = sizeof(*vhdr);
} else { } else {
...@@ -885,7 +890,7 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv, ...@@ -885,7 +890,7 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv,
return 0; return 0;
/* pskb_may_pull() may have modified the pointers, get ethhdr again */ /* pskb_may_pull() may have modified the pointers, get ethhdr again */
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
arphdr = (struct arphdr *)((uint8_t *)ethhdr + headlen); arphdr = (struct arphdr *)((uint8_t *)ethhdr + headlen);
/* Check whether the ARP frame carries a valid /* Check whether the ARP frame carries a valid
...@@ -910,7 +915,8 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv, ...@@ -910,7 +915,8 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv,
if (ret == 1) if (ret == 1)
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_process_claim(): received a claim frame from another group. From: %pM on vid %d ...(hw_src %pM, hw_dst %pM)\n", "bla_process_claim(): received a claim frame from another group. From: %pM on vid %d ...(hw_src %pM, hw_dst %pM)\n",
ethhdr->h_source, vid, hw_src, hw_dst); ethhdr->h_source, BATADV_PRINT_VID(vid), hw_src,
hw_dst);
if (ret < 2) if (ret < 2)
return ret; return ret;
...@@ -945,7 +951,7 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv, ...@@ -945,7 +951,7 @@ static int batadv_bla_process_claim(struct batadv_priv *bat_priv,
batadv_dbg(BATADV_DBG_BLA, bat_priv, batadv_dbg(BATADV_DBG_BLA, bat_priv,
"bla_process_claim(): ERROR - this looks like a claim frame, but is useless. eth src %pM on vid %d ...(hw_src %pM, hw_dst %pM)\n", "bla_process_claim(): ERROR - this looks like a claim frame, but is useless. eth src %pM on vid %d ...(hw_src %pM, hw_dst %pM)\n",
ethhdr->h_source, vid, hw_src, hw_dst); ethhdr->h_source, BATADV_PRINT_VID(vid), hw_src, hw_dst);
return 1; return 1;
} }
...@@ -1358,7 +1364,7 @@ int batadv_bla_is_backbone_gw(struct sk_buff *skb, ...@@ -1358,7 +1364,7 @@ int batadv_bla_is_backbone_gw(struct sk_buff *skb,
struct ethhdr *ethhdr; struct ethhdr *ethhdr;
struct vlan_ethhdr *vhdr; struct vlan_ethhdr *vhdr;
struct batadv_bla_backbone_gw *backbone_gw; struct batadv_bla_backbone_gw *backbone_gw;
short vid = -1; unsigned short vid = BATADV_NO_FLAGS;
if (!atomic_read(&orig_node->bat_priv->bridge_loop_avoidance)) if (!atomic_read(&orig_node->bat_priv->bridge_loop_avoidance))
return 0; return 0;
...@@ -1375,6 +1381,7 @@ int batadv_bla_is_backbone_gw(struct sk_buff *skb, ...@@ -1375,6 +1381,7 @@ int batadv_bla_is_backbone_gw(struct sk_buff *skb,
vhdr = (struct vlan_ethhdr *)(skb->data + hdr_size); vhdr = (struct vlan_ethhdr *)(skb->data + hdr_size);
vid = ntohs(vhdr->h_vlan_TCI) & VLAN_VID_MASK; vid = ntohs(vhdr->h_vlan_TCI) & VLAN_VID_MASK;
vid |= BATADV_VLAN_HAS_TAG;
} }
/* see if this originator is a backbone gw for this VLAN */ /* see if this originator is a backbone gw for this VLAN */
...@@ -1424,15 +1431,15 @@ void batadv_bla_free(struct batadv_priv *bat_priv) ...@@ -1424,15 +1431,15 @@ void batadv_bla_free(struct batadv_priv *bat_priv)
* 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 batadv_bla_rx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid, int batadv_bla_rx(struct batadv_priv *bat_priv, struct sk_buff *skb,
bool is_bcast) unsigned short vid, bool is_bcast)
{ {
struct ethhdr *ethhdr; struct ethhdr *ethhdr;
struct batadv_bla_claim search_claim, *claim = NULL; struct batadv_bla_claim search_claim, *claim = NULL;
struct batadv_hard_iface *primary_if; struct batadv_hard_iface *primary_if;
int ret; int ret;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
primary_if = batadv_primary_if_get_selected(bat_priv); primary_if = batadv_primary_if_get_selected(bat_priv);
if (!primary_if) if (!primary_if)
...@@ -1519,7 +1526,8 @@ int batadv_bla_rx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid, ...@@ -1519,7 +1526,8 @@ int batadv_bla_rx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid,
* 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 batadv_bla_tx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid) int batadv_bla_tx(struct batadv_priv *bat_priv, struct sk_buff *skb,
unsigned short vid)
{ {
struct ethhdr *ethhdr; struct ethhdr *ethhdr;
struct batadv_bla_claim search_claim, *claim = NULL; struct batadv_bla_claim search_claim, *claim = NULL;
...@@ -1539,7 +1547,7 @@ int batadv_bla_tx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid) ...@@ -1539,7 +1547,7 @@ int batadv_bla_tx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid)
if (batadv_bla_process_claim(bat_priv, primary_if, skb)) if (batadv_bla_process_claim(bat_priv, primary_if, skb))
goto handled; goto handled;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
if (unlikely(atomic_read(&bat_priv->bla.num_requests))) if (unlikely(atomic_read(&bat_priv->bla.num_requests)))
/* don't allow broadcasts while requests are in flight */ /* don't allow broadcasts while requests are in flight */
...@@ -1623,8 +1631,8 @@ int batadv_bla_claim_table_seq_print_text(struct seq_file *seq, void *offset) ...@@ -1623,8 +1631,8 @@ int batadv_bla_claim_table_seq_print_text(struct seq_file *seq, void *offset)
hlist_for_each_entry_rcu(claim, head, hash_entry) { hlist_for_each_entry_rcu(claim, head, hash_entry) {
is_own = batadv_compare_eth(claim->backbone_gw->orig, is_own = batadv_compare_eth(claim->backbone_gw->orig,
primary_addr); primary_addr);
seq_printf(seq, " * %pM on % 5d by %pM [%c] (%#.4x)\n", seq_printf(seq, " * %pM on %5d by %pM [%c] (%#.4x)\n",
claim->addr, claim->vid, claim->addr, BATADV_PRINT_VID(claim->vid),
claim->backbone_gw->orig, claim->backbone_gw->orig,
(is_own ? 'x' : ' '), (is_own ? 'x' : ' '),
claim->backbone_gw->crc); claim->backbone_gw->crc);
...@@ -1676,10 +1684,10 @@ int batadv_bla_backbone_table_seq_print_text(struct seq_file *seq, void *offset) ...@@ -1676,10 +1684,10 @@ int batadv_bla_backbone_table_seq_print_text(struct seq_file *seq, void *offset)
if (is_own) if (is_own)
continue; continue;
seq_printf(seq, seq_printf(seq, " * %pM on %5d %4i.%03is (%#.4x)\n",
" * %pM on % 5d % 4i.%03is (%#.4x)\n", backbone_gw->orig,
backbone_gw->orig, backbone_gw->vid, BATADV_PRINT_VID(backbone_gw->vid), secs,
secs, msecs, backbone_gw->crc); msecs, backbone_gw->crc);
} }
rcu_read_unlock(); rcu_read_unlock();
} }
......
...@@ -21,9 +21,10 @@ ...@@ -21,9 +21,10 @@
#define _NET_BATMAN_ADV_BLA_H_ #define _NET_BATMAN_ADV_BLA_H_
#ifdef CONFIG_BATMAN_ADV_BLA #ifdef CONFIG_BATMAN_ADV_BLA
int batadv_bla_rx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid, int batadv_bla_rx(struct batadv_priv *bat_priv, struct sk_buff *skb,
bool is_bcast); unsigned short vid, bool is_bcast);
int batadv_bla_tx(struct batadv_priv *bat_priv, struct sk_buff *skb, short vid); int batadv_bla_tx(struct batadv_priv *bat_priv, struct sk_buff *skb,
unsigned short vid);
int batadv_bla_is_backbone_gw(struct sk_buff *skb, int batadv_bla_is_backbone_gw(struct sk_buff *skb,
struct batadv_orig_node *orig_node, int hdr_size); struct batadv_orig_node *orig_node, int hdr_size);
int batadv_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);
...@@ -42,13 +43,14 @@ void batadv_bla_free(struct batadv_priv *bat_priv); ...@@ -42,13 +43,14 @@ void batadv_bla_free(struct batadv_priv *bat_priv);
#else /* ifdef CONFIG_BATMAN_ADV_BLA */ #else /* ifdef CONFIG_BATMAN_ADV_BLA */
static inline int batadv_bla_rx(struct batadv_priv *bat_priv, static inline int batadv_bla_rx(struct batadv_priv *bat_priv,
struct sk_buff *skb, short vid, bool is_bcast) struct sk_buff *skb, unsigned short vid,
bool is_bcast)
{ {
return 0; return 0;
} }
static inline int batadv_bla_tx(struct batadv_priv *bat_priv, static inline int batadv_bla_tx(struct batadv_priv *bat_priv,
struct sk_buff *skb, short vid) struct sk_buff *skb, unsigned short vid)
{ {
return 0; return 0;
} }
......
...@@ -45,9 +45,9 @@ static void batadv_dat_start_timer(struct batadv_priv *bat_priv) ...@@ -45,9 +45,9 @@ static void batadv_dat_start_timer(struct batadv_priv *bat_priv)
} }
/** /**
* batadv_dat_entry_free_ref - decrements the dat_entry refcounter and possibly * batadv_dat_entry_free_ref - decrement the dat_entry refcounter and possibly
* free it * free it
* @dat_entry: the oentry to free * @dat_entry: the entry to free
*/ */
static void batadv_dat_entry_free_ref(struct batadv_dat_entry *dat_entry) static void batadv_dat_entry_free_ref(struct batadv_dat_entry *dat_entry)
{ {
...@@ -56,10 +56,10 @@ static void batadv_dat_entry_free_ref(struct batadv_dat_entry *dat_entry) ...@@ -56,10 +56,10 @@ static void batadv_dat_entry_free_ref(struct batadv_dat_entry *dat_entry)
} }
/** /**
* batadv_dat_to_purge - checks whether a dat_entry has to be purged or not * batadv_dat_to_purge - check whether a dat_entry has to be purged or not
* @dat_entry: the entry to check * @dat_entry: the entry to check
* *
* Returns true if the entry has to be purged now, false otherwise * Returns true if the entry has to be purged now, false otherwise.
*/ */
static bool batadv_dat_to_purge(struct batadv_dat_entry *dat_entry) static bool batadv_dat_to_purge(struct batadv_dat_entry *dat_entry)
{ {
...@@ -75,8 +75,8 @@ static bool batadv_dat_to_purge(struct batadv_dat_entry *dat_entry) ...@@ -75,8 +75,8 @@ static bool batadv_dat_to_purge(struct batadv_dat_entry *dat_entry)
* returns a boolean value: true is the entry has to be deleted, * returns a boolean value: true is the entry has to be deleted,
* false otherwise * false otherwise
* *
* Loops over each entry in the DAT local storage and delete it if and only if * Loops over each entry in the DAT local storage and deletes it if and only if
* the to_purge function passed as argument returns true * the to_purge function passed as argument returns true.
*/ */
static void __batadv_dat_purge(struct batadv_priv *bat_priv, static void __batadv_dat_purge(struct batadv_priv *bat_priv,
bool (*to_purge)(struct batadv_dat_entry *)) bool (*to_purge)(struct batadv_dat_entry *))
...@@ -97,7 +97,7 @@ static void __batadv_dat_purge(struct batadv_priv *bat_priv, ...@@ -97,7 +97,7 @@ static void __batadv_dat_purge(struct batadv_priv *bat_priv,
spin_lock_bh(list_lock); spin_lock_bh(list_lock);
hlist_for_each_entry_safe(dat_entry, node_tmp, head, hlist_for_each_entry_safe(dat_entry, node_tmp, head,
hash_entry) { hash_entry) {
/* if an helper function has been passed as parameter, /* if a helper function has been passed as parameter,
* ask it if the entry has to be purged or not * ask it if the entry has to be purged or not
*/ */
if (to_purge && !to_purge(dat_entry)) if (to_purge && !to_purge(dat_entry))
...@@ -134,7 +134,7 @@ static void batadv_dat_purge(struct work_struct *work) ...@@ -134,7 +134,7 @@ static void batadv_dat_purge(struct work_struct *work)
* @node: node in the local table * @node: node in the local table
* @data2: second object to compare the node to * @data2: second object to compare the node to
* *
* Returns 1 if the two entry are the same, 0 otherwise * Returns 1 if the two entries are the same, 0 otherwise.
*/ */
static int batadv_compare_dat(const struct hlist_node *node, const void *data2) static int batadv_compare_dat(const struct hlist_node *node, const void *data2)
{ {
...@@ -149,7 +149,7 @@ static int batadv_compare_dat(const struct hlist_node *node, const void *data2) ...@@ -149,7 +149,7 @@ static int batadv_compare_dat(const struct hlist_node *node, const void *data2)
* @skb: ARP packet * @skb: ARP packet
* @hdr_size: size of the possible header before the ARP packet * @hdr_size: size of the possible header before the ARP packet
* *
* Returns the value of the hw_src field in the ARP packet * Returns the value of the hw_src field in the ARP packet.
*/ */
static uint8_t *batadv_arp_hw_src(struct sk_buff *skb, int hdr_size) static uint8_t *batadv_arp_hw_src(struct sk_buff *skb, int hdr_size)
{ {
...@@ -166,7 +166,7 @@ static uint8_t *batadv_arp_hw_src(struct sk_buff *skb, int hdr_size) ...@@ -166,7 +166,7 @@ static uint8_t *batadv_arp_hw_src(struct sk_buff *skb, int hdr_size)
* @skb: ARP packet * @skb: ARP packet
* @hdr_size: size of the possible header before the ARP packet * @hdr_size: size of the possible header before the ARP packet
* *
* Returns the value of the ip_src field in the ARP packet * Returns the value of the ip_src field in the ARP packet.
*/ */
static __be32 batadv_arp_ip_src(struct sk_buff *skb, int hdr_size) static __be32 batadv_arp_ip_src(struct sk_buff *skb, int hdr_size)
{ {
...@@ -178,7 +178,7 @@ static __be32 batadv_arp_ip_src(struct sk_buff *skb, int hdr_size) ...@@ -178,7 +178,7 @@ static __be32 batadv_arp_ip_src(struct sk_buff *skb, int hdr_size)
* @skb: ARP packet * @skb: ARP packet
* @hdr_size: size of the possible header before the ARP packet * @hdr_size: size of the possible header before the ARP packet
* *
* Returns the value of the hw_dst field in the ARP packet * Returns the value of the hw_dst field in the ARP packet.
*/ */
static uint8_t *batadv_arp_hw_dst(struct sk_buff *skb, int hdr_size) static uint8_t *batadv_arp_hw_dst(struct sk_buff *skb, int hdr_size)
{ {
...@@ -190,7 +190,7 @@ static uint8_t *batadv_arp_hw_dst(struct sk_buff *skb, int hdr_size) ...@@ -190,7 +190,7 @@ static uint8_t *batadv_arp_hw_dst(struct sk_buff *skb, int hdr_size)
* @skb: ARP packet * @skb: ARP packet
* @hdr_size: size of the possible header before the ARP packet * @hdr_size: size of the possible header before the ARP packet
* *
* Returns the value of the ip_dst field in the ARP packet * Returns the value of the ip_dst field in the ARP packet.
*/ */
static __be32 batadv_arp_ip_dst(struct sk_buff *skb, int hdr_size) static __be32 batadv_arp_ip_dst(struct sk_buff *skb, int hdr_size)
{ {
...@@ -202,7 +202,7 @@ static __be32 batadv_arp_ip_dst(struct sk_buff *skb, int hdr_size) ...@@ -202,7 +202,7 @@ static __be32 batadv_arp_ip_dst(struct sk_buff *skb, int hdr_size)
* @data: data to hash * @data: data to hash
* @size: size of the hash table * @size: size of the hash table
* *
* Returns the selected index in the hash table for the given data * Returns the selected index in the hash table for the given data.
*/ */
static uint32_t batadv_hash_dat(const void *data, uint32_t size) static uint32_t batadv_hash_dat(const void *data, uint32_t size)
{ {
...@@ -224,12 +224,12 @@ static uint32_t batadv_hash_dat(const void *data, uint32_t size) ...@@ -224,12 +224,12 @@ static uint32_t batadv_hash_dat(const void *data, uint32_t size)
} }
/** /**
* batadv_dat_entry_hash_find - looks for a given dat_entry in the local hash * batadv_dat_entry_hash_find - look for a given dat_entry in the local hash
* table * table
* @bat_priv: the bat priv with all the soft interface information * @bat_priv: the bat priv with all the soft interface information
* @ip: search key * @ip: search key
* *
* Returns the dat_entry if found, NULL otherwise * Returns the dat_entry if found, NULL otherwise.
*/ */
static struct batadv_dat_entry * static struct batadv_dat_entry *
batadv_dat_entry_hash_find(struct batadv_priv *bat_priv, __be32 ip) batadv_dat_entry_hash_find(struct batadv_priv *bat_priv, __be32 ip)
...@@ -343,9 +343,6 @@ static void batadv_dbg_arp(struct batadv_priv *bat_priv, struct sk_buff *skb, ...@@ -343,9 +343,6 @@ static void batadv_dbg_arp(struct batadv_priv *bat_priv, struct sk_buff *skb,
if (hdr_size == 0) if (hdr_size == 0)
return; return;
/* if the ARP packet is encapsulated in a batman packet, let's print
* some debug messages
*/
unicast_4addr_packet = (struct batadv_unicast_4addr_packet *)skb->data; unicast_4addr_packet = (struct batadv_unicast_4addr_packet *)skb->data;
switch (unicast_4addr_packet->u.header.packet_type) { switch (unicast_4addr_packet->u.header.packet_type) {
...@@ -409,7 +406,8 @@ static void batadv_dbg_arp(struct batadv_priv *bat_priv, struct sk_buff *skb, ...@@ -409,7 +406,8 @@ static void batadv_dbg_arp(struct batadv_priv *bat_priv, struct sk_buff *skb,
* @candidate: orig_node under evaluation * @candidate: orig_node under evaluation
* @max_orig_node: last selected candidate * @max_orig_node: last selected candidate
* *
* Returns true if the node has been elected as next candidate or false othrwise * Returns true if the node has been elected as next candidate or false
* otherwise.
*/ */
static bool batadv_is_orig_node_eligible(struct batadv_dat_candidate *res, static bool batadv_is_orig_node_eligible(struct batadv_dat_candidate *res,
int select, batadv_dat_addr_t tmp_max, int select, batadv_dat_addr_t tmp_max,
...@@ -472,7 +470,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv, ...@@ -472,7 +470,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv,
*/ */
cands[select].type = BATADV_DAT_CANDIDATE_NOT_FOUND; cands[select].type = BATADV_DAT_CANDIDATE_NOT_FOUND;
/* iterate over the originator list and find the node with closest /* iterate over the originator list and find the node with the closest
* dat_address which has not been selected yet * dat_address which has not been selected yet
*/ */
for (i = 0; i < hash->size; i++) { for (i = 0; i < hash->size; i++) {
...@@ -480,7 +478,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv, ...@@ -480,7 +478,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv,
rcu_read_lock(); rcu_read_lock();
hlist_for_each_entry_rcu(orig_node, head, hash_entry) { hlist_for_each_entry_rcu(orig_node, head, hash_entry) {
/* the dht space is a ring and addresses are unsigned */ /* the dht space is a ring using unsigned addresses */
tmp_max = BATADV_DAT_ADDR_MAX - orig_node->dat_addr + tmp_max = BATADV_DAT_ADDR_MAX - orig_node->dat_addr +
ip_key; ip_key;
...@@ -512,7 +510,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv, ...@@ -512,7 +510,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv,
} }
/** /**
* batadv_dat_select_candidates - selects the nodes which the DHT message has to * batadv_dat_select_candidates - select the nodes which the DHT message has to
* be sent to * be sent to
* @bat_priv: the bat priv with all the soft interface information * @bat_priv: the bat priv with all the soft interface information
* @ip_dst: ipv4 to look up in the DHT * @ip_dst: ipv4 to look up in the DHT
...@@ -521,7 +519,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv, ...@@ -521,7 +519,7 @@ static void batadv_choose_next_candidate(struct batadv_priv *bat_priv,
* closest values (from the LEFT, with wrap around if needed) then the hash * closest values (from the LEFT, with wrap around if needed) then the hash
* value of the key. ip_dst is the key. * value of the key. ip_dst is the key.
* *
* Returns the candidate array of size BATADV_DAT_CANDIDATE_NUM * Returns the candidate array of size BATADV_DAT_CANDIDATE_NUM.
*/ */
static struct batadv_dat_candidate * static struct batadv_dat_candidate *
batadv_dat_select_candidates(struct batadv_priv *bat_priv, __be32 ip_dst) batadv_dat_select_candidates(struct batadv_priv *bat_priv, __be32 ip_dst)
...@@ -558,10 +556,11 @@ batadv_dat_select_candidates(struct batadv_priv *bat_priv, __be32 ip_dst) ...@@ -558,10 +556,11 @@ batadv_dat_select_candidates(struct batadv_priv *bat_priv, __be32 ip_dst)
* @ip: the DHT key * @ip: the DHT key
* @packet_subtype: unicast4addr packet subtype to use * @packet_subtype: unicast4addr packet subtype to use
* *
* In this function the skb is copied by means of pskb_copy() and is sent as * This function copies the skb with pskb_copy() and is sent as unicast packet
* unicast packet to each of the selected candidates * to each of the selected candidates.
* *
* Returns true if the packet is sent to at least one candidate, false otherwise * Returns true if the packet is sent to at least one candidate, false
* otherwise.
*/ */
static bool batadv_dat_send_data(struct batadv_priv *bat_priv, static bool batadv_dat_send_data(struct batadv_priv *bat_priv,
struct sk_buff *skb, __be32 ip, struct sk_buff *skb, __be32 ip,
...@@ -727,7 +726,7 @@ int batadv_dat_cache_seq_print_text(struct seq_file *seq, void *offset) ...@@ -727,7 +726,7 @@ int batadv_dat_cache_seq_print_text(struct seq_file *seq, void *offset)
* @skb: packet to analyse * @skb: packet to analyse
* @hdr_size: size of the possible header before the ARP packet in the skb * @hdr_size: size of the possible header before the ARP packet in the skb
* *
* Returns the ARP type if the skb contains a valid ARP packet, 0 otherwise * Returns the ARP type if the skb contains a valid ARP packet, 0 otherwise.
*/ */
static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv, static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv,
struct sk_buff *skb, int hdr_size) struct sk_buff *skb, int hdr_size)
...@@ -754,9 +753,7 @@ static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv, ...@@ -754,9 +753,7 @@ static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv,
arphdr = (struct arphdr *)(skb->data + hdr_size + ETH_HLEN); arphdr = (struct arphdr *)(skb->data + hdr_size + ETH_HLEN);
/* Check whether the ARP packet carries a valid /* check whether the ARP packet carries a valid IP information */
* IP information
*/
if (arphdr->ar_hrd != htons(ARPHRD_ETHER)) if (arphdr->ar_hrd != htons(ARPHRD_ETHER))
goto out; goto out;
...@@ -784,7 +781,7 @@ static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv, ...@@ -784,7 +781,7 @@ static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv,
if (is_zero_ether_addr(hw_src) || is_multicast_ether_addr(hw_src)) if (is_zero_ether_addr(hw_src) || is_multicast_ether_addr(hw_src))
goto out; goto out;
/* we don't care about the destination MAC address in ARP requests */ /* don't care about the destination MAC address in ARP requests */
if (arphdr->ar_op != htons(ARPOP_REQUEST)) { if (arphdr->ar_op != htons(ARPOP_REQUEST)) {
hw_dst = batadv_arp_hw_dst(skb, hdr_size); hw_dst = batadv_arp_hw_dst(skb, hdr_size);
if (is_zero_ether_addr(hw_dst) || if (is_zero_ether_addr(hw_dst) ||
...@@ -804,8 +801,8 @@ static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv, ...@@ -804,8 +801,8 @@ static uint16_t batadv_arp_get_type(struct batadv_priv *bat_priv,
* @skb: packet to check * @skb: packet to check
* *
* Returns true if the message has been sent to the dht candidates, false * Returns true if the message has been sent to the dht candidates, false
* otherwise. In case of true the message has to be enqueued to permit the * otherwise. In case of a positive return value the message has to be enqueued
* fallback * to permit the fallback.
*/ */
bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv, bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv,
struct sk_buff *skb) struct sk_buff *skb)
...@@ -867,7 +864,7 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv, ...@@ -867,7 +864,7 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv,
batadv_dbg(BATADV_DBG_DAT, bat_priv, "ARP request replied locally\n"); batadv_dbg(BATADV_DBG_DAT, bat_priv, "ARP request replied locally\n");
ret = true; ret = true;
} else { } else {
/* Send the request on the DHT */ /* Send the request to the DHT */
ret = batadv_dat_send_data(bat_priv, skb, ip_dst, ret = batadv_dat_send_data(bat_priv, skb, ip_dst,
BATADV_P_DAT_DHT_GET); BATADV_P_DAT_DHT_GET);
} }
...@@ -884,7 +881,7 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv, ...@@ -884,7 +881,7 @@ bool batadv_dat_snoop_outgoing_arp_request(struct batadv_priv *bat_priv,
* @skb: packet to check * @skb: packet to check
* @hdr_size: size of the encapsulation header * @hdr_size: size of the encapsulation header
* *
* Returns true if the request has been answered, false otherwise * Returns true if the request has been answered, false otherwise.
*/ */
bool batadv_dat_snoop_incoming_arp_request(struct batadv_priv *bat_priv, bool batadv_dat_snoop_incoming_arp_request(struct batadv_priv *bat_priv,
struct sk_buff *skb, int hdr_size) struct sk_buff *skb, int hdr_size)
...@@ -924,10 +921,9 @@ bool batadv_dat_snoop_incoming_arp_request(struct batadv_priv *bat_priv, ...@@ -924,10 +921,9 @@ bool batadv_dat_snoop_incoming_arp_request(struct batadv_priv *bat_priv,
if (!skb_new) if (!skb_new)
goto out; goto out;
/* to preserve backwards compatibility, here the node has to answer /* To preserve backwards compatibility, the node has choose the outgoing
* using the same packet type it received for the request. This is due * format based on the incoming request packet type. The assumption is
* to that if a node is not using the 4addr packet format it may not * that a node not using the 4addr packet format doesn't support it.
* support it.
*/ */
if (hdr_size == sizeof(struct batadv_unicast_4addr_packet)) if (hdr_size == sizeof(struct batadv_unicast_4addr_packet))
err = batadv_unicast_4addr_send_skb(bat_priv, skb_new, err = batadv_unicast_4addr_send_skb(bat_priv, skb_new,
...@@ -977,7 +973,7 @@ void batadv_dat_snoop_outgoing_arp_reply(struct batadv_priv *bat_priv, ...@@ -977,7 +973,7 @@ void batadv_dat_snoop_outgoing_arp_reply(struct batadv_priv *bat_priv,
batadv_dat_entry_add(bat_priv, ip_dst, hw_dst); batadv_dat_entry_add(bat_priv, ip_dst, hw_dst);
/* Send the ARP reply to the candidates for both the IP addresses that /* Send the ARP reply to the candidates for both the IP addresses that
* the node got within the ARP reply * the node obtained from the ARP reply
*/ */
batadv_dat_send_data(bat_priv, skb, ip_src, BATADV_P_DAT_DHT_PUT); batadv_dat_send_data(bat_priv, skb, ip_src, BATADV_P_DAT_DHT_PUT);
batadv_dat_send_data(bat_priv, skb, ip_dst, BATADV_P_DAT_DHT_PUT); batadv_dat_send_data(bat_priv, skb, ip_dst, BATADV_P_DAT_DHT_PUT);
...@@ -987,7 +983,7 @@ void batadv_dat_snoop_outgoing_arp_reply(struct batadv_priv *bat_priv, ...@@ -987,7 +983,7 @@ void batadv_dat_snoop_outgoing_arp_reply(struct batadv_priv *bat_priv,
* DAT storage only * DAT storage only
* @bat_priv: the bat priv with all the soft interface information * @bat_priv: the bat priv with all the soft interface information
* @skb: packet to check * @skb: packet to check
* @hdr_size: siaze of the encapsulation header * @hdr_size: size of the encapsulation header
*/ */
bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv, bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv,
struct sk_buff *skb, int hdr_size) struct sk_buff *skb, int hdr_size)
...@@ -1031,11 +1027,11 @@ bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv, ...@@ -1031,11 +1027,11 @@ bool batadv_dat_snoop_incoming_arp_reply(struct batadv_priv *bat_priv,
/** /**
* batadv_dat_drop_broadcast_packet - check if an ARP request has to be dropped * batadv_dat_drop_broadcast_packet - check if an ARP request has to be dropped
* (because the node has already got the reply via DAT) or not * (because the node has already obtained the reply via DAT) or not
* @bat_priv: the bat priv with all the soft interface information * @bat_priv: the bat priv with all the soft interface information
* @forw_packet: the broadcast packet * @forw_packet: the broadcast packet
* *
* Returns true if the node can drop the packet, false otherwise * Returns true if the node can drop the packet, false otherwise.
*/ */
bool batadv_dat_drop_broadcast_packet(struct batadv_priv *bat_priv, bool batadv_dat_drop_broadcast_packet(struct batadv_priv *bat_priv,
struct batadv_forw_packet *forw_packet) struct batadv_forw_packet *forw_packet)
......
...@@ -117,6 +117,58 @@ static int batadv_is_valid_iface(const struct net_device *net_dev) ...@@ -117,6 +117,58 @@ static int batadv_is_valid_iface(const struct net_device *net_dev)
return 1; return 1;
} }
/**
* batadv_is_wifi_netdev - check if the given net_device struct is a wifi
* interface
* @net_device: the device to check
*
* Returns true if the net device is a 802.11 wireless device, false otherwise.
*/
static bool batadv_is_wifi_netdev(struct net_device *net_device)
{
#ifdef CONFIG_WIRELESS_EXT
/* pre-cfg80211 drivers have to implement WEXT, so it is possible to
* check for wireless_handlers != NULL
*/
if (net_device->wireless_handlers)
return true;
#endif
/* cfg80211 drivers have to set ieee80211_ptr */
if (net_device->ieee80211_ptr)
return true;
return false;
}
/**
* batadv_is_wifi_iface - check if the given interface represented by ifindex
* is a wifi interface
* @ifindex: interface index to check
*
* Returns true if the interface represented by ifindex is a 802.11 wireless
* device, false otherwise.
*/
bool batadv_is_wifi_iface(int ifindex)
{
struct net_device *net_device = NULL;
bool ret = false;
if (ifindex == BATADV_NULL_IFINDEX)
goto out;
net_device = dev_get_by_index(&init_net, ifindex);
if (!net_device)
goto out;
ret = batadv_is_wifi_netdev(net_device);
out:
if (net_device)
dev_put(net_device);
return ret;
}
static struct batadv_hard_iface * static struct batadv_hard_iface *
batadv_hardif_get_active(const struct net_device *soft_iface) batadv_hardif_get_active(const struct net_device *soft_iface)
{ {
...@@ -525,7 +577,7 @@ batadv_hardif_add_interface(struct net_device *net_dev) ...@@ -525,7 +577,7 @@ batadv_hardif_add_interface(struct net_device *net_dev)
dev_hold(net_dev); dev_hold(net_dev);
hard_iface = kmalloc(sizeof(*hard_iface), GFP_ATOMIC); hard_iface = kzalloc(sizeof(*hard_iface), GFP_ATOMIC);
if (!hard_iface) if (!hard_iface)
goto release_dev; goto release_dev;
...@@ -541,18 +593,16 @@ batadv_hardif_add_interface(struct net_device *net_dev) ...@@ -541,18 +593,16 @@ batadv_hardif_add_interface(struct net_device *net_dev)
INIT_WORK(&hard_iface->cleanup_work, INIT_WORK(&hard_iface->cleanup_work,
batadv_hardif_remove_interface_finish); batadv_hardif_remove_interface_finish);
hard_iface->num_bcasts = BATADV_NUM_BCASTS_DEFAULT;
if (batadv_is_wifi_netdev(net_dev))
hard_iface->num_bcasts = BATADV_NUM_BCASTS_WIRELESS;
/* extra reference for return */ /* extra reference for return */
atomic_set(&hard_iface->refcount, 2); atomic_set(&hard_iface->refcount, 2);
batadv_check_known_mac_addr(hard_iface->net_dev); batadv_check_known_mac_addr(hard_iface->net_dev);
list_add_tail_rcu(&hard_iface->list, &batadv_hardif_list); list_add_tail_rcu(&hard_iface->list, &batadv_hardif_list);
/* This can't be called via a bat_priv callback because
* we have no bat_priv yet.
*/
atomic_set(&hard_iface->bat_iv.ogm_seqno, 1);
hard_iface->bat_iv.ogm_buff = NULL;
return hard_iface; return hard_iface;
free_if: free_if:
...@@ -657,38 +707,6 @@ static int batadv_hard_if_event(struct notifier_block *this, ...@@ -657,38 +707,6 @@ static int batadv_hard_if_event(struct notifier_block *this,
return NOTIFY_DONE; return NOTIFY_DONE;
} }
/* This function returns true if the interface represented by ifindex is a
* 802.11 wireless device
*/
bool batadv_is_wifi_iface(int ifindex)
{
struct net_device *net_device = NULL;
bool ret = false;
if (ifindex == BATADV_NULL_IFINDEX)
goto out;
net_device = dev_get_by_index(&init_net, ifindex);
if (!net_device)
goto out;
#ifdef CONFIG_WIRELESS_EXT
/* pre-cfg80211 drivers have to implement WEXT, so it is possible to
* check for wireless_handlers != NULL
*/
if (net_device->wireless_handlers)
ret = true;
else
#endif
/* cfg80211 drivers have to set ieee80211_ptr */
if (net_device->ieee80211_ptr)
ret = true;
out:
if (net_device)
dev_put(net_device);
return ret;
}
struct notifier_block batadv_hard_if_notifier = { struct notifier_block batadv_hard_if_notifier = {
.notifier_call = batadv_hard_if_event, .notifier_call = batadv_hard_if_event,
}; };
...@@ -177,13 +177,13 @@ static ssize_t batadv_socket_write(struct file *file, const char __user *buff, ...@@ -177,13 +177,13 @@ static ssize_t batadv_socket_write(struct file *file, const char __user *buff,
if (len >= sizeof(struct batadv_icmp_packet_rr)) if (len >= sizeof(struct batadv_icmp_packet_rr))
packet_len = sizeof(struct batadv_icmp_packet_rr); packet_len = sizeof(struct batadv_icmp_packet_rr);
skb = dev_alloc_skb(packet_len + ETH_HLEN + NET_IP_ALIGN); skb = netdev_alloc_skb_ip_align(NULL, packet_len + ETH_HLEN);
if (!skb) { if (!skb) {
len = -ENOMEM; len = -ENOMEM;
goto out; goto out;
} }
skb_reserve(skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(skb, ETH_HLEN);
icmp_packet = (struct batadv_icmp_packet_rr *)skb_put(skb, packet_len); icmp_packet = (struct batadv_icmp_packet_rr *)skb_put(skb, packet_len);
if (copy_from_user(icmp_packet, buff, packet_len)) { if (copy_from_user(icmp_packet, buff, packet_len)) {
......
...@@ -26,7 +26,7 @@ ...@@ -26,7 +26,7 @@
#define BATADV_DRIVER_DEVICE "batman-adv" #define BATADV_DRIVER_DEVICE "batman-adv"
#ifndef BATADV_SOURCE_VERSION #ifndef BATADV_SOURCE_VERSION
#define BATADV_SOURCE_VERSION "2013.2.0" #define BATADV_SOURCE_VERSION "2013.3.0"
#endif #endif
/* B.A.T.M.A.N. parameters */ /* B.A.T.M.A.N. parameters */
...@@ -76,6 +76,11 @@ ...@@ -76,6 +76,11 @@
#define BATADV_LOG_BUF_LEN 8192 /* has to be a power of 2 */ #define BATADV_LOG_BUF_LEN 8192 /* has to be a power of 2 */
/* number of packets to send for broadcasts on different interface types */
#define BATADV_NUM_BCASTS_DEFAULT 1
#define BATADV_NUM_BCASTS_WIRELESS 3
#define BATADV_NUM_BCASTS_MAX 3
/* msecs after which an ARP_REQUEST is sent in broadcast as fallback */ /* msecs after which an ARP_REQUEST is sent in broadcast as fallback */
#define ARP_REQ_DELAY 250 #define ARP_REQ_DELAY 250
/* numbers of originator to contact for any PUT/GET DHT operation */ /* numbers of originator to contact for any PUT/GET DHT operation */
...@@ -157,6 +162,17 @@ enum batadv_uev_type { ...@@ -157,6 +162,17 @@ enum batadv_uev_type {
#include <linux/seq_file.h> #include <linux/seq_file.h>
#include "types.h" #include "types.h"
/**
* batadv_vlan_flags - flags for the four MSB of any vlan ID field
* @BATADV_VLAN_HAS_TAG: whether the field contains a valid vlan tag or not
*/
enum batadv_vlan_flags {
BATADV_VLAN_HAS_TAG = BIT(15),
};
#define BATADV_PRINT_VID(vid) (vid & BATADV_VLAN_HAS_TAG ? \
(int)(vid & VLAN_VID_MASK) : -1)
extern char batadv_routing_algo[]; extern char batadv_routing_algo[];
extern struct list_head batadv_hardif_list; extern struct list_head batadv_hardif_list;
......
...@@ -1245,7 +1245,7 @@ static void batadv_nc_skb_store_before_coding(struct batadv_priv *bat_priv, ...@@ -1245,7 +1245,7 @@ static void batadv_nc_skb_store_before_coding(struct batadv_priv *bat_priv,
return; return;
/* Set the mac header as if we actually sent the packet uncoded */ /* Set the mac header as if we actually sent the packet uncoded */
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
memcpy(ethhdr->h_source, ethhdr->h_dest, ETH_ALEN); memcpy(ethhdr->h_source, ethhdr->h_dest, ETH_ALEN);
memcpy(ethhdr->h_dest, eth_dst_new, ETH_ALEN); memcpy(ethhdr->h_dest, eth_dst_new, ETH_ALEN);
...@@ -1359,18 +1359,17 @@ static bool batadv_nc_skb_add_to_path(struct sk_buff *skb, ...@@ -1359,18 +1359,17 @@ static bool batadv_nc_skb_add_to_path(struct sk_buff *skb,
* buffer * buffer
* @skb: data skb to forward * @skb: data skb to forward
* @neigh_node: next hop to forward packet to * @neigh_node: next hop to forward packet to
* @ethhdr: pointer to the ethernet header inside the skb
* *
* Returns true if the skb was consumed (encoded packet sent) or false otherwise * Returns true if the skb was consumed (encoded packet sent) or false otherwise
*/ */
bool batadv_nc_skb_forward(struct sk_buff *skb, bool batadv_nc_skb_forward(struct sk_buff *skb,
struct batadv_neigh_node *neigh_node, struct batadv_neigh_node *neigh_node)
struct ethhdr *ethhdr)
{ {
const struct net_device *netdev = neigh_node->if_incoming->soft_iface; const struct net_device *netdev = neigh_node->if_incoming->soft_iface;
struct batadv_priv *bat_priv = netdev_priv(netdev); struct batadv_priv *bat_priv = netdev_priv(netdev);
struct batadv_unicast_packet *packet; struct batadv_unicast_packet *packet;
struct batadv_nc_path *nc_path; struct batadv_nc_path *nc_path;
struct ethhdr *ethhdr = eth_hdr(skb);
__be32 packet_id; __be32 packet_id;
u8 *payload; u8 *payload;
...@@ -1423,7 +1422,7 @@ void batadv_nc_skb_store_for_decoding(struct batadv_priv *bat_priv, ...@@ -1423,7 +1422,7 @@ void batadv_nc_skb_store_for_decoding(struct batadv_priv *bat_priv,
{ {
struct batadv_unicast_packet *packet; struct batadv_unicast_packet *packet;
struct batadv_nc_path *nc_path; struct batadv_nc_path *nc_path;
struct ethhdr *ethhdr = (struct ethhdr *)skb_mac_header(skb); struct ethhdr *ethhdr = eth_hdr(skb);
__be32 packet_id; __be32 packet_id;
u8 *payload; u8 *payload;
...@@ -1482,7 +1481,7 @@ void batadv_nc_skb_store_for_decoding(struct batadv_priv *bat_priv, ...@@ -1482,7 +1481,7 @@ void batadv_nc_skb_store_for_decoding(struct batadv_priv *bat_priv,
void batadv_nc_skb_store_sniffed_unicast(struct batadv_priv *bat_priv, void batadv_nc_skb_store_sniffed_unicast(struct batadv_priv *bat_priv,
struct sk_buff *skb) struct sk_buff *skb)
{ {
struct ethhdr *ethhdr = (struct ethhdr *)skb_mac_header(skb); struct ethhdr *ethhdr = eth_hdr(skb);
if (batadv_is_my_mac(bat_priv, ethhdr->h_dest)) if (batadv_is_my_mac(bat_priv, ethhdr->h_dest))
return; return;
...@@ -1533,7 +1532,7 @@ batadv_nc_skb_decode_packet(struct batadv_priv *bat_priv, struct sk_buff *skb, ...@@ -1533,7 +1532,7 @@ batadv_nc_skb_decode_packet(struct batadv_priv *bat_priv, struct sk_buff *skb,
skb_reset_network_header(skb); skb_reset_network_header(skb);
/* Reconstruct original mac header */ /* Reconstruct original mac header */
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
memcpy(ethhdr, &ethhdr_tmp, sizeof(*ethhdr)); memcpy(ethhdr, &ethhdr_tmp, sizeof(*ethhdr));
/* Select the correct unicast header information based on the location /* Select the correct unicast header information based on the location
...@@ -1677,7 +1676,7 @@ static int batadv_nc_recv_coded_packet(struct sk_buff *skb, ...@@ -1677,7 +1676,7 @@ static int batadv_nc_recv_coded_packet(struct sk_buff *skb,
return NET_RX_DROP; return NET_RX_DROP;
coded_packet = (struct batadv_coded_packet *)skb->data; coded_packet = (struct batadv_coded_packet *)skb->data;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
/* Verify frame is destined for us */ /* Verify frame is destined for us */
if (!batadv_is_my_mac(bat_priv, ethhdr->h_dest) && if (!batadv_is_my_mac(bat_priv, ethhdr->h_dest) &&
...@@ -1763,6 +1762,13 @@ int batadv_nc_nodes_seq_print_text(struct seq_file *seq, void *offset) ...@@ -1763,6 +1762,13 @@ int batadv_nc_nodes_seq_print_text(struct seq_file *seq, void *offset)
/* For each orig_node in this bin */ /* For each orig_node in this bin */
rcu_read_lock(); rcu_read_lock();
hlist_for_each_entry_rcu(orig_node, head, hash_entry) { hlist_for_each_entry_rcu(orig_node, head, hash_entry) {
/* no need to print the orig node if it does not have
* network coding neighbors
*/
if (list_empty(&orig_node->in_coding_list) &&
list_empty(&orig_node->out_coding_list))
continue;
seq_printf(seq, "Node: %pM\n", orig_node->orig); seq_printf(seq, "Node: %pM\n", orig_node->orig);
seq_puts(seq, " Ingoing: "); seq_puts(seq, " Ingoing: ");
......
...@@ -36,8 +36,7 @@ void batadv_nc_purge_orig(struct batadv_priv *bat_priv, ...@@ -36,8 +36,7 @@ void batadv_nc_purge_orig(struct batadv_priv *bat_priv,
void batadv_nc_init_bat_priv(struct batadv_priv *bat_priv); void batadv_nc_init_bat_priv(struct batadv_priv *bat_priv);
void batadv_nc_init_orig(struct batadv_orig_node *orig_node); void batadv_nc_init_orig(struct batadv_orig_node *orig_node);
bool batadv_nc_skb_forward(struct sk_buff *skb, bool batadv_nc_skb_forward(struct sk_buff *skb,
struct batadv_neigh_node *neigh_node, struct batadv_neigh_node *neigh_node);
struct ethhdr *ethhdr);
void batadv_nc_skb_store_for_decoding(struct batadv_priv *bat_priv, void batadv_nc_skb_store_for_decoding(struct batadv_priv *bat_priv,
struct sk_buff *skb); struct sk_buff *skb);
void batadv_nc_skb_store_sniffed_unicast(struct batadv_priv *bat_priv, void batadv_nc_skb_store_sniffed_unicast(struct batadv_priv *bat_priv,
...@@ -87,8 +86,7 @@ static inline void batadv_nc_init_orig(struct batadv_orig_node *orig_node) ...@@ -87,8 +86,7 @@ static inline void batadv_nc_init_orig(struct batadv_orig_node *orig_node)
} }
static inline bool batadv_nc_skb_forward(struct sk_buff *skb, static inline bool batadv_nc_skb_forward(struct sk_buff *skb,
struct batadv_neigh_node *neigh_node, struct batadv_neigh_node *neigh_node)
struct ethhdr *ethhdr)
{ {
return false; return false;
} }
......
...@@ -92,7 +92,7 @@ batadv_orig_node_get_router(struct batadv_orig_node *orig_node) ...@@ -92,7 +92,7 @@ batadv_orig_node_get_router(struct batadv_orig_node *orig_node)
struct batadv_neigh_node * struct batadv_neigh_node *
batadv_neigh_node_new(struct batadv_hard_iface *hard_iface, batadv_neigh_node_new(struct batadv_hard_iface *hard_iface,
const uint8_t *neigh_addr, uint32_t seqno) const uint8_t *neigh_addr)
{ {
struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface); struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
struct batadv_neigh_node *neigh_node; struct batadv_neigh_node *neigh_node;
...@@ -110,8 +110,8 @@ batadv_neigh_node_new(struct batadv_hard_iface *hard_iface, ...@@ -110,8 +110,8 @@ batadv_neigh_node_new(struct batadv_hard_iface *hard_iface,
atomic_set(&neigh_node->refcount, 2); atomic_set(&neigh_node->refcount, 2);
batadv_dbg(BATADV_DBG_BATMAN, bat_priv, batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
"Creating new neighbor %pM, initial seqno %d\n", "Creating new neighbor %pM on interface %s\n", neigh_addr,
neigh_addr, seqno); hard_iface->net_dev->name);
out: out:
return neigh_node; return neigh_node;
......
...@@ -31,7 +31,7 @@ struct batadv_orig_node *batadv_get_orig_node(struct batadv_priv *bat_priv, ...@@ -31,7 +31,7 @@ struct batadv_orig_node *batadv_get_orig_node(struct batadv_priv *bat_priv,
const uint8_t *addr); const uint8_t *addr);
struct batadv_neigh_node * struct batadv_neigh_node *
batadv_neigh_node_new(struct batadv_hard_iface *hard_iface, batadv_neigh_node_new(struct batadv_hard_iface *hard_iface,
const uint8_t *neigh_addr, uint32_t seqno); const uint8_t *neigh_addr);
void batadv_neigh_node_free_ref(struct batadv_neigh_node *neigh_node); void batadv_neigh_node_free_ref(struct batadv_neigh_node *neigh_node);
struct batadv_neigh_node * struct batadv_neigh_node *
batadv_orig_node_get_router(struct batadv_orig_node *orig_node); batadv_orig_node_get_router(struct batadv_orig_node *orig_node);
......
/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of version 2 of the GNU General Public
* License as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA
*/
#include "main.h"
#include "ring_buffer.h"
void batadv_ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index,
uint8_t value)
{
lq_recv[*lq_index] = value;
*lq_index = (*lq_index + 1) % BATADV_TQ_GLOBAL_WINDOW_SIZE;
}
uint8_t batadv_ring_buffer_avg(const uint8_t lq_recv[])
{
const uint8_t *ptr;
uint16_t count = 0, i = 0, sum = 0;
ptr = lq_recv;
while (i < BATADV_TQ_GLOBAL_WINDOW_SIZE) {
if (*ptr != 0) {
count++;
sum += *ptr;
}
i++;
ptr++;
}
if (count == 0)
return 0;
return (uint8_t)(sum / count);
}
/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of version 2 of the GNU General Public
* License as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA
*/
#ifndef _NET_BATMAN_ADV_RING_BUFFER_H_
#define _NET_BATMAN_ADV_RING_BUFFER_H_
void batadv_ring_buffer_set(uint8_t lq_recv[], uint8_t *lq_index,
uint8_t value);
uint8_t batadv_ring_buffer_avg(const uint8_t lq_recv[]);
#endif /* _NET_BATMAN_ADV_RING_BUFFER_H_ */
...@@ -34,35 +34,6 @@ ...@@ -34,35 +34,6 @@
static int batadv_route_unicast_packet(struct sk_buff *skb, static int batadv_route_unicast_packet(struct sk_buff *skb,
struct batadv_hard_iface *recv_if); struct batadv_hard_iface *recv_if);
void batadv_slide_own_bcast_window(struct batadv_hard_iface *hard_iface)
{
struct batadv_priv *bat_priv = netdev_priv(hard_iface->soft_iface);
struct batadv_hashtable *hash = bat_priv->orig_hash;
struct hlist_head *head;
struct batadv_orig_node *orig_node;
unsigned long *word;
uint32_t i;
size_t word_index;
uint8_t *w;
for (i = 0; i < hash->size; i++) {
head = &hash->table[i];
rcu_read_lock();
hlist_for_each_entry_rcu(orig_node, head, hash_entry) {
spin_lock_bh(&orig_node->ogm_cnt_lock);
word_index = hard_iface->if_num * BATADV_NUM_WORDS;
word = &(orig_node->bcast_own[word_index]);
batadv_bit_get_packet(bat_priv, word, 1, 0);
w = &orig_node->bcast_own_sum[hard_iface->if_num];
*w = bitmap_weight(word, BATADV_TQ_LOCAL_WINDOW_SIZE);
spin_unlock_bh(&orig_node->ogm_cnt_lock);
}
rcu_read_unlock();
}
}
static void _batadv_update_route(struct batadv_priv *bat_priv, static void _batadv_update_route(struct batadv_priv *bat_priv,
struct batadv_orig_node *orig_node, struct batadv_orig_node *orig_node,
struct batadv_neigh_node *neigh_node) struct batadv_neigh_node *neigh_node)
...@@ -256,7 +227,7 @@ bool batadv_check_management_packet(struct sk_buff *skb, ...@@ -256,7 +227,7 @@ bool batadv_check_management_packet(struct sk_buff *skb,
if (unlikely(!pskb_may_pull(skb, header_len))) if (unlikely(!pskb_may_pull(skb, header_len)))
return false; return false;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
/* packet with broadcast indication but unicast recipient */ /* packet with broadcast indication but unicast recipient */
if (!is_broadcast_ether_addr(ethhdr->h_dest)) if (!is_broadcast_ether_addr(ethhdr->h_dest))
...@@ -314,7 +285,7 @@ static int batadv_recv_my_icmp_packet(struct batadv_priv *bat_priv, ...@@ -314,7 +285,7 @@ static int batadv_recv_my_icmp_packet(struct batadv_priv *bat_priv,
icmp_packet->msg_type = BATADV_ECHO_REPLY; icmp_packet->msg_type = BATADV_ECHO_REPLY;
icmp_packet->header.ttl = BATADV_TTL; icmp_packet->header.ttl = BATADV_TTL;
if (batadv_send_skb_to_orig(skb, orig_node, NULL)) if (batadv_send_skb_to_orig(skb, orig_node, NULL) != NET_XMIT_DROP)
ret = NET_RX_SUCCESS; ret = NET_RX_SUCCESS;
out: out:
...@@ -362,7 +333,7 @@ static int batadv_recv_icmp_ttl_exceeded(struct batadv_priv *bat_priv, ...@@ -362,7 +333,7 @@ static int batadv_recv_icmp_ttl_exceeded(struct batadv_priv *bat_priv,
icmp_packet->msg_type = BATADV_TTL_EXCEEDED; icmp_packet->msg_type = BATADV_TTL_EXCEEDED;
icmp_packet->header.ttl = BATADV_TTL; icmp_packet->header.ttl = BATADV_TTL;
if (batadv_send_skb_to_orig(skb, orig_node, NULL)) if (batadv_send_skb_to_orig(skb, orig_node, NULL) != NET_XMIT_DROP)
ret = NET_RX_SUCCESS; ret = NET_RX_SUCCESS;
out: out:
...@@ -392,7 +363,7 @@ int batadv_recv_icmp_packet(struct sk_buff *skb, ...@@ -392,7 +363,7 @@ int batadv_recv_icmp_packet(struct sk_buff *skb,
if (unlikely(!pskb_may_pull(skb, hdr_size))) if (unlikely(!pskb_may_pull(skb, hdr_size)))
goto out; goto out;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
/* packet with unicast indication but broadcast recipient */ /* packet with unicast indication but broadcast recipient */
if (is_broadcast_ether_addr(ethhdr->h_dest)) if (is_broadcast_ether_addr(ethhdr->h_dest))
...@@ -439,7 +410,7 @@ int batadv_recv_icmp_packet(struct sk_buff *skb, ...@@ -439,7 +410,7 @@ int batadv_recv_icmp_packet(struct sk_buff *skb,
icmp_packet->header.ttl--; icmp_packet->header.ttl--;
/* route it */ /* route it */
if (batadv_send_skb_to_orig(skb, orig_node, recv_if)) if (batadv_send_skb_to_orig(skb, orig_node, recv_if) != NET_XMIT_DROP)
ret = NET_RX_SUCCESS; ret = NET_RX_SUCCESS;
out: out:
...@@ -569,7 +540,7 @@ static int batadv_check_unicast_packet(struct batadv_priv *bat_priv, ...@@ -569,7 +540,7 @@ static int batadv_check_unicast_packet(struct batadv_priv *bat_priv,
if (unlikely(!pskb_may_pull(skb, hdr_size))) if (unlikely(!pskb_may_pull(skb, hdr_size)))
return -ENODATA; return -ENODATA;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
/* packet with unicast indication but broadcast recipient */ /* packet with unicast indication but broadcast recipient */
if (is_broadcast_ether_addr(ethhdr->h_dest)) if (is_broadcast_ether_addr(ethhdr->h_dest))
...@@ -803,8 +774,8 @@ static int batadv_route_unicast_packet(struct sk_buff *skb, ...@@ -803,8 +774,8 @@ static int batadv_route_unicast_packet(struct sk_buff *skb,
struct batadv_orig_node *orig_node = NULL; struct batadv_orig_node *orig_node = NULL;
struct batadv_neigh_node *neigh_node = NULL; struct batadv_neigh_node *neigh_node = NULL;
struct batadv_unicast_packet *unicast_packet; struct batadv_unicast_packet *unicast_packet;
struct ethhdr *ethhdr = (struct ethhdr *)skb_mac_header(skb); struct ethhdr *ethhdr = eth_hdr(skb);
int ret = NET_RX_DROP; int res, ret = NET_RX_DROP;
struct sk_buff *new_skb; struct sk_buff *new_skb;
unicast_packet = (struct batadv_unicast_packet *)skb->data; unicast_packet = (struct batadv_unicast_packet *)skb->data;
...@@ -864,16 +835,19 @@ static int batadv_route_unicast_packet(struct sk_buff *skb, ...@@ -864,16 +835,19 @@ static int batadv_route_unicast_packet(struct sk_buff *skb,
/* decrement ttl */ /* decrement ttl */
unicast_packet->header.ttl--; unicast_packet->header.ttl--;
/* network code packet if possible */ res = batadv_send_skb_to_orig(skb, orig_node, recv_if);
if (batadv_nc_skb_forward(skb, neigh_node, ethhdr)) {
ret = NET_RX_SUCCESS;
} else if (batadv_send_skb_to_orig(skb, orig_node, recv_if)) {
ret = NET_RX_SUCCESS;
/* Update stats counter */ /* translate transmit result into receive result */
if (res == NET_XMIT_SUCCESS) {
/* skb was transmitted and consumed */
batadv_inc_counter(bat_priv, BATADV_CNT_FORWARD); batadv_inc_counter(bat_priv, BATADV_CNT_FORWARD);
batadv_add_counter(bat_priv, BATADV_CNT_FORWARD_BYTES, batadv_add_counter(bat_priv, BATADV_CNT_FORWARD_BYTES,
skb->len + ETH_HLEN); skb->len + ETH_HLEN);
ret = NET_RX_SUCCESS;
} else if (res == NET_XMIT_POLICED) {
/* skb was buffered and consumed */
ret = NET_RX_SUCCESS;
} }
out: out:
...@@ -1165,7 +1139,7 @@ int batadv_recv_bcast_packet(struct sk_buff *skb, ...@@ -1165,7 +1139,7 @@ int batadv_recv_bcast_packet(struct sk_buff *skb,
if (unlikely(!pskb_may_pull(skb, hdr_size))) if (unlikely(!pskb_may_pull(skb, hdr_size)))
goto out; goto out;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
/* packet with broadcast indication but unicast recipient */ /* packet with broadcast indication but unicast recipient */
if (!is_broadcast_ether_addr(ethhdr->h_dest)) if (!is_broadcast_ether_addr(ethhdr->h_dest))
...@@ -1265,7 +1239,7 @@ int batadv_recv_vis_packet(struct sk_buff *skb, ...@@ -1265,7 +1239,7 @@ int batadv_recv_vis_packet(struct sk_buff *skb,
return NET_RX_DROP; return NET_RX_DROP;
vis_packet = (struct batadv_vis_packet *)skb->data; vis_packet = (struct batadv_vis_packet *)skb->data;
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
/* not for me */ /* not for me */
if (!batadv_is_my_mac(bat_priv, ethhdr->h_dest)) if (!batadv_is_my_mac(bat_priv, ethhdr->h_dest))
......
...@@ -20,7 +20,6 @@ ...@@ -20,7 +20,6 @@
#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 batadv_slide_own_bcast_window(struct batadv_hard_iface *hard_iface);
bool batadv_check_management_packet(struct sk_buff *skb, bool batadv_check_management_packet(struct sk_buff *skb,
struct batadv_hard_iface *hard_iface, struct batadv_hard_iface *hard_iface,
int header_len); int header_len);
......
...@@ -61,7 +61,7 @@ int batadv_send_skb_packet(struct sk_buff *skb, ...@@ -61,7 +61,7 @@ int batadv_send_skb_packet(struct sk_buff *skb,
skb_reset_mac_header(skb); skb_reset_mac_header(skb);
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
memcpy(ethhdr->h_source, hard_iface->net_dev->dev_addr, ETH_ALEN); memcpy(ethhdr->h_source, hard_iface->net_dev->dev_addr, ETH_ALEN);
memcpy(ethhdr->h_dest, dst_addr, ETH_ALEN); memcpy(ethhdr->h_dest, dst_addr, ETH_ALEN);
ethhdr->h_proto = __constant_htons(ETH_P_BATMAN); ethhdr->h_proto = __constant_htons(ETH_P_BATMAN);
...@@ -96,26 +96,37 @@ int batadv_send_skb_packet(struct sk_buff *skb, ...@@ -96,26 +96,37 @@ int batadv_send_skb_packet(struct sk_buff *skb,
* host, NULL can be passed as recv_if and no interface alternating is * host, NULL can be passed as recv_if and no interface alternating is
* attempted. * attempted.
* *
* Returns TRUE on success; FALSE otherwise. * Returns NET_XMIT_SUCCESS on success, NET_XMIT_DROP on failure, or
* NET_XMIT_POLICED if the skb is buffered for later transmit.
*/ */
bool batadv_send_skb_to_orig(struct sk_buff *skb, int batadv_send_skb_to_orig(struct sk_buff *skb,
struct batadv_orig_node *orig_node, struct batadv_orig_node *orig_node,
struct batadv_hard_iface *recv_if) struct batadv_hard_iface *recv_if)
{ {
struct batadv_priv *bat_priv = orig_node->bat_priv; struct batadv_priv *bat_priv = orig_node->bat_priv;
struct batadv_neigh_node *neigh_node; struct batadv_neigh_node *neigh_node;
int ret = NET_XMIT_DROP;
/* batadv_find_router() increases neigh_nodes refcount if found. */ /* batadv_find_router() increases neigh_nodes refcount if found. */
neigh_node = batadv_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)
return false; return ret;
/* route it */ /* try to network code the packet, if it is received on an interface
batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr); * (i.e. being forwarded). If the packet originates from this node or if
* network coding fails, then send the packet as usual.
*/
if (recv_if && batadv_nc_skb_forward(skb, neigh_node)) {
ret = NET_XMIT_POLICED;
} else {
batadv_send_skb_packet(skb, neigh_node->if_incoming,
neigh_node->addr);
ret = NET_XMIT_SUCCESS;
}
batadv_neigh_node_free_ref(neigh_node); batadv_neigh_node_free_ref(neigh_node);
return true; return ret;
} }
void batadv_schedule_bat_ogm(struct batadv_hard_iface *hard_iface) void batadv_schedule_bat_ogm(struct batadv_hard_iface *hard_iface)
...@@ -152,8 +163,6 @@ _batadv_add_bcast_packet_to_list(struct batadv_priv *bat_priv, ...@@ -152,8 +163,6 @@ _batadv_add_bcast_packet_to_list(struct batadv_priv *bat_priv,
struct batadv_forw_packet *forw_packet, struct batadv_forw_packet *forw_packet,
unsigned long send_time) unsigned long send_time)
{ {
INIT_HLIST_NODE(&forw_packet->list);
/* add new packet to packet list */ /* add new packet to packet list */
spin_lock_bh(&bat_priv->forw_bcast_list_lock); spin_lock_bh(&bat_priv->forw_bcast_list_lock);
hlist_add_head(&forw_packet->list, &bat_priv->forw_bcast_list); hlist_add_head(&forw_packet->list, &bat_priv->forw_bcast_list);
...@@ -260,6 +269,9 @@ static void batadv_send_outstanding_bcast_packet(struct work_struct *work) ...@@ -260,6 +269,9 @@ static void batadv_send_outstanding_bcast_packet(struct work_struct *work)
if (hard_iface->soft_iface != soft_iface) if (hard_iface->soft_iface != soft_iface)
continue; continue;
if (forw_packet->num_packets >= hard_iface->num_bcasts)
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)
...@@ -271,7 +283,7 @@ static void batadv_send_outstanding_bcast_packet(struct work_struct *work) ...@@ -271,7 +283,7 @@ static void batadv_send_outstanding_bcast_packet(struct work_struct *work)
forw_packet->num_packets++; forw_packet->num_packets++;
/* if we still have some more bcasts to send */ /* if we still have some more bcasts to send */
if (forw_packet->num_packets < 3) { if (forw_packet->num_packets < BATADV_NUM_BCASTS_MAX) {
_batadv_add_bcast_packet_to_list(bat_priv, forw_packet, _batadv_add_bcast_packet_to_list(bat_priv, forw_packet,
msecs_to_jiffies(5)); msecs_to_jiffies(5));
return; return;
......
...@@ -23,9 +23,9 @@ ...@@ -23,9 +23,9 @@
int batadv_send_skb_packet(struct sk_buff *skb, int batadv_send_skb_packet(struct sk_buff *skb,
struct batadv_hard_iface *hard_iface, struct batadv_hard_iface *hard_iface,
const uint8_t *dst_addr); const uint8_t *dst_addr);
bool batadv_send_skb_to_orig(struct sk_buff *skb, int batadv_send_skb_to_orig(struct sk_buff *skb,
struct batadv_orig_node *orig_node, struct batadv_orig_node *orig_node,
struct batadv_hard_iface *recv_if); struct batadv_hard_iface *recv_if);
void batadv_schedule_bat_ogm(struct batadv_hard_iface *hard_iface); void batadv_schedule_bat_ogm(struct batadv_hard_iface *hard_iface);
int batadv_add_bcast_packet_to_list(struct batadv_priv *bat_priv, int batadv_add_bcast_packet_to_list(struct batadv_priv *bat_priv,
const struct sk_buff *skb, const struct sk_buff *skb,
......
...@@ -154,7 +154,7 @@ static int batadv_interface_tx(struct sk_buff *skb, ...@@ -154,7 +154,7 @@ static int batadv_interface_tx(struct sk_buff *skb,
0x00, 0x00}; 0x00, 0x00};
unsigned int header_len = 0; unsigned int header_len = 0;
int data_len = skb->len, ret; int data_len = skb->len, ret;
short vid __maybe_unused = -1; unsigned short vid __maybe_unused = BATADV_NO_FLAGS;
bool do_bcast = false; bool do_bcast = false;
uint32_t seqno; uint32_t seqno;
unsigned long brd_delay = 1; unsigned long brd_delay = 1;
...@@ -303,7 +303,7 @@ void batadv_interface_rx(struct net_device *soft_iface, ...@@ -303,7 +303,7 @@ void batadv_interface_rx(struct net_device *soft_iface,
struct ethhdr *ethhdr; struct ethhdr *ethhdr;
struct vlan_ethhdr *vhdr; struct vlan_ethhdr *vhdr;
struct batadv_header *batadv_header = (struct batadv_header *)skb->data; struct batadv_header *batadv_header = (struct batadv_header *)skb->data;
short vid __maybe_unused = -1; unsigned short vid __maybe_unused = BATADV_NO_FLAGS;
__be16 ethertype = __constant_htons(ETH_P_BATMAN); __be16 ethertype = __constant_htons(ETH_P_BATMAN);
bool is_bcast; bool is_bcast;
...@@ -316,7 +316,7 @@ void batadv_interface_rx(struct net_device *soft_iface, ...@@ -316,7 +316,7 @@ void batadv_interface_rx(struct net_device *soft_iface,
skb_pull_rcsum(skb, hdr_size); skb_pull_rcsum(skb, hdr_size);
skb_reset_mac_header(skb); skb_reset_mac_header(skb);
ethhdr = (struct ethhdr *)skb_mac_header(skb); ethhdr = eth_hdr(skb);
switch (ntohs(ethhdr->h_proto)) { switch (ntohs(ethhdr->h_proto)) {
case ETH_P_8021Q: case ETH_P_8021Q:
......
...@@ -163,10 +163,19 @@ batadv_tt_orig_list_entry_free_ref(struct batadv_tt_orig_list_entry *orig_entry) ...@@ -163,10 +163,19 @@ batadv_tt_orig_list_entry_free_ref(struct batadv_tt_orig_list_entry *orig_entry)
call_rcu(&orig_entry->rcu, batadv_tt_orig_list_entry_free_rcu); call_rcu(&orig_entry->rcu, batadv_tt_orig_list_entry_free_rcu);
} }
/**
* batadv_tt_local_event - store a local TT event (ADD/DEL)
* @bat_priv: the bat priv with all the soft interface information
* @tt_local_entry: the TT entry involved in the event
* @event_flags: flags to store in the event structure
*/
static void batadv_tt_local_event(struct batadv_priv *bat_priv, static void batadv_tt_local_event(struct batadv_priv *bat_priv,
const uint8_t *addr, uint8_t flags) struct batadv_tt_local_entry *tt_local_entry,
uint8_t event_flags)
{ {
struct batadv_tt_change_node *tt_change_node, *entry, *safe; struct batadv_tt_change_node *tt_change_node, *entry, *safe;
struct batadv_tt_common_entry *common = &tt_local_entry->common;
uint8_t flags = common->flags | event_flags;
bool event_removed = false; bool event_removed = false;
bool del_op_requested, del_op_entry; bool del_op_requested, del_op_entry;
...@@ -176,7 +185,7 @@ static void batadv_tt_local_event(struct batadv_priv *bat_priv, ...@@ -176,7 +185,7 @@ static void batadv_tt_local_event(struct batadv_priv *bat_priv,
return; return;
tt_change_node->change.flags = flags; tt_change_node->change.flags = flags;
memcpy(tt_change_node->change.addr, addr, ETH_ALEN); memcpy(tt_change_node->change.addr, common->addr, ETH_ALEN);
del_op_requested = flags & BATADV_TT_CLIENT_DEL; del_op_requested = flags & BATADV_TT_CLIENT_DEL;
...@@ -184,7 +193,7 @@ static void batadv_tt_local_event(struct batadv_priv *bat_priv, ...@@ -184,7 +193,7 @@ static void batadv_tt_local_event(struct batadv_priv *bat_priv,
spin_lock_bh(&bat_priv->tt.changes_list_lock); spin_lock_bh(&bat_priv->tt.changes_list_lock);
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 (!batadv_compare_eth(entry->change.addr, addr)) if (!batadv_compare_eth(entry->change.addr, common->addr))
continue; continue;
/* DEL+ADD in the same orig interval have no effect and can be /* DEL+ADD in the same orig interval have no effect and can be
...@@ -332,7 +341,7 @@ void batadv_tt_local_add(struct net_device *soft_iface, const uint8_t *addr, ...@@ -332,7 +341,7 @@ void batadv_tt_local_add(struct net_device *soft_iface, const uint8_t *addr,
} }
add_event: add_event:
batadv_tt_local_event(bat_priv, addr, tt_local->common.flags); batadv_tt_local_event(bat_priv, tt_local, BATADV_NO_FLAGS);
check_roaming: check_roaming:
/* Check whether it is a roaming, but don't do anything if the roaming /* Check whether it is a roaming, but don't do anything if the roaming
...@@ -529,8 +538,7 @@ batadv_tt_local_set_pending(struct batadv_priv *bat_priv, ...@@ -529,8 +538,7 @@ batadv_tt_local_set_pending(struct batadv_priv *bat_priv,
struct batadv_tt_local_entry *tt_local_entry, struct batadv_tt_local_entry *tt_local_entry,
uint16_t flags, const char *message) uint16_t flags, const char *message)
{ {
batadv_tt_local_event(bat_priv, tt_local_entry->common.addr, batadv_tt_local_event(bat_priv, tt_local_entry, flags);
tt_local_entry->common.flags | flags);
/* 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
...@@ -584,8 +592,7 @@ uint16_t batadv_tt_local_remove(struct batadv_priv *bat_priv, ...@@ -584,8 +592,7 @@ uint16_t batadv_tt_local_remove(struct batadv_priv *bat_priv,
/* if this client has been added right now, it is possible to /* if this client has been added right now, it is possible to
* immediately purge it * immediately purge it
*/ */
batadv_tt_local_event(bat_priv, tt_local_entry->common.addr, batadv_tt_local_event(bat_priv, tt_local_entry, BATADV_TT_CLIENT_DEL);
curr_flags | BATADV_TT_CLIENT_DEL);
hlist_del_rcu(&tt_local_entry->common.hash_entry); hlist_del_rcu(&tt_local_entry->common.hash_entry);
batadv_tt_local_entry_free_ref(tt_local_entry); batadv_tt_local_entry_free_ref(tt_local_entry);
...@@ -791,10 +798,25 @@ batadv_tt_global_orig_entry_add(struct batadv_tt_global_entry *tt_global, ...@@ -791,10 +798,25 @@ batadv_tt_global_orig_entry_add(struct batadv_tt_global_entry *tt_global,
batadv_tt_orig_list_entry_free_ref(orig_entry); batadv_tt_orig_list_entry_free_ref(orig_entry);
} }
/* caller must hold orig_node refcount */ /**
* batadv_tt_global_add - add a new TT global entry or update an existing one
* @bat_priv: the bat priv with all the soft interface information
* @orig_node: the originator announcing the client
* @tt_addr: the mac address of the non-mesh client
* @flags: TT flags that have to be set for this non-mesh client
* @ttvn: the tt version number ever announcing this non-mesh client
*
* Add a new TT global entry for the given originator. If the entry already
* exists add a new reference to the given originator (a global entry can have
* references to multiple originators) and adjust the flags attribute to reflect
* the function argument.
* If a TT local entry exists for this non-mesh client remove it.
*
* The caller must hold orig_node refcount.
*/
int batadv_tt_global_add(struct batadv_priv *bat_priv, int batadv_tt_global_add(struct batadv_priv *bat_priv,
struct batadv_orig_node *orig_node, struct batadv_orig_node *orig_node,
const unsigned char *tt_addr, uint8_t flags, const unsigned char *tt_addr, uint16_t flags,
uint8_t ttvn) uint8_t ttvn)
{ {
struct batadv_tt_global_entry *tt_global_entry; struct batadv_tt_global_entry *tt_global_entry;
...@@ -1600,11 +1622,11 @@ batadv_tt_response_fill_table(uint16_t tt_len, uint8_t ttvn, ...@@ -1600,11 +1622,11 @@ batadv_tt_response_fill_table(uint16_t tt_len, uint8_t ttvn,
tt_tot = tt_len / sizeof(struct batadv_tt_change); tt_tot = tt_len / sizeof(struct batadv_tt_change);
len = tt_query_size + tt_len; len = tt_query_size + tt_len;
skb = dev_alloc_skb(len + ETH_HLEN + NET_IP_ALIGN); skb = netdev_alloc_skb_ip_align(NULL, len + ETH_HLEN);
if (!skb) if (!skb)
goto out; goto out;
skb_reserve(skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(skb, ETH_HLEN);
tt_response = (struct batadv_tt_query_packet *)skb_put(skb, len); tt_response = (struct batadv_tt_query_packet *)skb_put(skb, len);
tt_response->ttvn = ttvn; tt_response->ttvn = ttvn;
...@@ -1665,11 +1687,11 @@ static int batadv_send_tt_request(struct batadv_priv *bat_priv, ...@@ -1665,11 +1687,11 @@ static int batadv_send_tt_request(struct batadv_priv *bat_priv,
if (!tt_req_node) if (!tt_req_node)
goto out; goto out;
skb = dev_alloc_skb(sizeof(*tt_request) + ETH_HLEN + NET_IP_ALIGN); skb = netdev_alloc_skb_ip_align(NULL, sizeof(*tt_request) + ETH_HLEN);
if (!skb) if (!skb)
goto out; goto out;
skb_reserve(skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(skb, ETH_HLEN);
tt_req_len = sizeof(*tt_request); tt_req_len = sizeof(*tt_request);
tt_request = (struct batadv_tt_query_packet *)skb_put(skb, tt_req_len); tt_request = (struct batadv_tt_query_packet *)skb_put(skb, tt_req_len);
...@@ -1691,7 +1713,7 @@ static int batadv_send_tt_request(struct batadv_priv *bat_priv, ...@@ -1691,7 +1713,7 @@ static int batadv_send_tt_request(struct batadv_priv *bat_priv,
batadv_inc_counter(bat_priv, BATADV_CNT_TT_REQUEST_TX); batadv_inc_counter(bat_priv, BATADV_CNT_TT_REQUEST_TX);
if (batadv_send_skb_to_orig(skb, dst_orig_node, NULL)) if (batadv_send_skb_to_orig(skb, dst_orig_node, NULL) != NET_XMIT_DROP)
ret = 0; ret = 0;
out: out:
...@@ -1715,7 +1737,7 @@ batadv_send_other_tt_response(struct batadv_priv *bat_priv, ...@@ -1715,7 +1737,7 @@ batadv_send_other_tt_response(struct batadv_priv *bat_priv,
struct batadv_orig_node *req_dst_orig_node; struct batadv_orig_node *req_dst_orig_node;
struct batadv_orig_node *res_dst_orig_node = NULL; struct batadv_orig_node *res_dst_orig_node = NULL;
uint8_t orig_ttvn, req_ttvn, ttvn; uint8_t orig_ttvn, req_ttvn, ttvn;
int ret = false; int res, ret = false;
unsigned char *tt_buff; unsigned char *tt_buff;
bool full_table; bool full_table;
uint16_t tt_len, tt_tot; uint16_t tt_len, tt_tot;
...@@ -1762,11 +1784,11 @@ batadv_send_other_tt_response(struct batadv_priv *bat_priv, ...@@ -1762,11 +1784,11 @@ batadv_send_other_tt_response(struct batadv_priv *bat_priv,
tt_tot = tt_len / sizeof(struct batadv_tt_change); tt_tot = tt_len / sizeof(struct batadv_tt_change);
len = sizeof(*tt_response) + tt_len; len = sizeof(*tt_response) + tt_len;
skb = dev_alloc_skb(len + ETH_HLEN + NET_IP_ALIGN); skb = netdev_alloc_skb_ip_align(NULL, len + ETH_HLEN);
if (!skb) if (!skb)
goto unlock; goto unlock;
skb_reserve(skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(skb, ETH_HLEN);
packet_pos = skb_put(skb, len); packet_pos = skb_put(skb, len);
tt_response = (struct batadv_tt_query_packet *)packet_pos; tt_response = (struct batadv_tt_query_packet *)packet_pos;
tt_response->ttvn = req_ttvn; tt_response->ttvn = req_ttvn;
...@@ -1810,8 +1832,10 @@ batadv_send_other_tt_response(struct batadv_priv *bat_priv, ...@@ -1810,8 +1832,10 @@ batadv_send_other_tt_response(struct batadv_priv *bat_priv,
batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_TX); batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_TX);
if (batadv_send_skb_to_orig(skb, res_dst_orig_node, NULL)) res = batadv_send_skb_to_orig(skb, res_dst_orig_node, NULL);
if (res != NET_XMIT_DROP)
ret = true; ret = true;
goto out; goto out;
unlock: unlock:
...@@ -1878,11 +1902,11 @@ batadv_send_my_tt_response(struct batadv_priv *bat_priv, ...@@ -1878,11 +1902,11 @@ batadv_send_my_tt_response(struct batadv_priv *bat_priv,
tt_tot = tt_len / sizeof(struct batadv_tt_change); tt_tot = tt_len / sizeof(struct batadv_tt_change);
len = sizeof(*tt_response) + tt_len; len = sizeof(*tt_response) + tt_len;
skb = dev_alloc_skb(len + ETH_HLEN + NET_IP_ALIGN); skb = netdev_alloc_skb_ip_align(NULL, len + ETH_HLEN);
if (!skb) if (!skb)
goto unlock; goto unlock;
skb_reserve(skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(skb, ETH_HLEN);
packet_pos = skb_put(skb, len); packet_pos = skb_put(skb, len);
tt_response = (struct batadv_tt_query_packet *)packet_pos; tt_response = (struct batadv_tt_query_packet *)packet_pos;
tt_response->ttvn = req_ttvn; tt_response->ttvn = req_ttvn;
...@@ -1925,7 +1949,7 @@ batadv_send_my_tt_response(struct batadv_priv *bat_priv, ...@@ -1925,7 +1949,7 @@ batadv_send_my_tt_response(struct batadv_priv *bat_priv,
batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_TX); batadv_inc_counter(bat_priv, BATADV_CNT_TT_RESPONSE_TX);
if (batadv_send_skb_to_orig(skb, orig_node, NULL)) if (batadv_send_skb_to_orig(skb, orig_node, NULL) != NET_XMIT_DROP)
ret = true; ret = true;
goto out; goto out;
...@@ -2212,11 +2236,11 @@ static void batadv_send_roam_adv(struct batadv_priv *bat_priv, uint8_t *client, ...@@ -2212,11 +2236,11 @@ static void batadv_send_roam_adv(struct batadv_priv *bat_priv, uint8_t *client,
if (!batadv_tt_check_roam_count(bat_priv, client)) if (!batadv_tt_check_roam_count(bat_priv, client))
goto out; goto out;
skb = dev_alloc_skb(sizeof(*roam_adv_packet) + ETH_HLEN + NET_IP_ALIGN); skb = netdev_alloc_skb_ip_align(NULL, len + ETH_HLEN);
if (!skb) if (!skb)
goto out; goto out;
skb_reserve(skb, ETH_HLEN + NET_IP_ALIGN); skb_reserve(skb, ETH_HLEN);
roam_adv_packet = (struct batadv_roam_adv_packet *)skb_put(skb, len); roam_adv_packet = (struct batadv_roam_adv_packet *)skb_put(skb, len);
...@@ -2238,7 +2262,7 @@ static void batadv_send_roam_adv(struct batadv_priv *bat_priv, uint8_t *client, ...@@ -2238,7 +2262,7 @@ static void batadv_send_roam_adv(struct batadv_priv *bat_priv, uint8_t *client,
batadv_inc_counter(bat_priv, BATADV_CNT_TT_ROAM_ADV_TX); batadv_inc_counter(bat_priv, BATADV_CNT_TT_ROAM_ADV_TX);
if (batadv_send_skb_to_orig(skb, orig_node, NULL)) if (batadv_send_skb_to_orig(skb, orig_node, NULL) != NET_XMIT_DROP)
ret = 0; ret = 0;
out: out:
......
...@@ -33,7 +33,7 @@ void batadv_tt_global_add_orig(struct batadv_priv *bat_priv, ...@@ -33,7 +33,7 @@ void batadv_tt_global_add_orig(struct batadv_priv *bat_priv,
const unsigned char *tt_buff, int tt_buff_len); const unsigned char *tt_buff, int tt_buff_len);
int batadv_tt_global_add(struct batadv_priv *bat_priv, int batadv_tt_global_add(struct batadv_priv *bat_priv,
struct batadv_orig_node *orig_node, struct batadv_orig_node *orig_node,
const unsigned char *addr, uint8_t flags, const unsigned char *addr, uint16_t flags,
uint8_t ttvn); uint8_t ttvn);
int batadv_tt_global_seq_print_text(struct seq_file *seq, void *offset); int batadv_tt_global_seq_print_text(struct seq_file *seq, void *offset);
void batadv_tt_global_del_orig(struct batadv_priv *bat_priv, void batadv_tt_global_del_orig(struct batadv_priv *bat_priv,
......
...@@ -61,6 +61,7 @@ struct batadv_hard_iface_bat_iv { ...@@ -61,6 +61,7 @@ struct batadv_hard_iface_bat_iv {
* @if_status: status of the interface for batman-adv * @if_status: status of the interface for batman-adv
* @net_dev: pointer to the net_device * @net_dev: pointer to the net_device
* @frag_seqno: last fragment sequence number sent by this interface * @frag_seqno: last fragment sequence number sent by this interface
* @num_bcasts: number of payload re-broadcasts on this interface (ARQ)
* @hardif_obj: kobject of the per interface sysfs "mesh" directory * @hardif_obj: kobject of the per interface sysfs "mesh" directory
* @refcount: number of contexts the object is used * @refcount: number of contexts the object is used
* @batman_adv_ptype: packet type describing packets that should be processed by * @batman_adv_ptype: packet type describing packets that should be processed by
...@@ -76,6 +77,7 @@ struct batadv_hard_iface { ...@@ -76,6 +77,7 @@ struct batadv_hard_iface {
char if_status; char if_status;
struct net_device *net_dev; struct net_device *net_dev;
atomic_t frag_seqno; atomic_t frag_seqno;
uint8_t num_bcasts;
struct kobject *hardif_obj; struct kobject *hardif_obj;
atomic_t refcount; atomic_t refcount;
struct packet_type batman_adv_ptype; struct packet_type batman_adv_ptype;
...@@ -640,7 +642,7 @@ struct batadv_socket_packet { ...@@ -640,7 +642,7 @@ struct batadv_socket_packet {
#ifdef CONFIG_BATMAN_ADV_BLA #ifdef CONFIG_BATMAN_ADV_BLA
struct batadv_bla_backbone_gw { struct batadv_bla_backbone_gw {
uint8_t orig[ETH_ALEN]; uint8_t orig[ETH_ALEN];
short vid; unsigned short vid;
struct hlist_node hash_entry; struct hlist_node hash_entry;
struct batadv_priv *bat_priv; struct batadv_priv *bat_priv;
unsigned long lasttime; unsigned long lasttime;
...@@ -663,7 +665,7 @@ struct batadv_bla_backbone_gw { ...@@ -663,7 +665,7 @@ struct batadv_bla_backbone_gw {
*/ */
struct batadv_bla_claim { struct batadv_bla_claim {
uint8_t addr[ETH_ALEN]; uint8_t addr[ETH_ALEN];
short vid; unsigned short vid;
struct batadv_bla_backbone_gw *backbone_gw; struct batadv_bla_backbone_gw *backbone_gw;
unsigned long lasttime; unsigned long lasttime;
struct hlist_node hash_entry; struct hlist_node hash_entry;
......
...@@ -464,7 +464,7 @@ int batadv_unicast_generic_send_skb(struct batadv_priv *bat_priv, ...@@ -464,7 +464,7 @@ int batadv_unicast_generic_send_skb(struct batadv_priv *bat_priv,
goto out; goto out;
} }
if (batadv_send_skb_to_orig(skb, orig_node, NULL)) if (batadv_send_skb_to_orig(skb, orig_node, NULL) != NET_XMIT_DROP)
ret = 0; ret = 0;
out: out:
......
...@@ -392,12 +392,12 @@ batadv_add_packet(struct batadv_priv *bat_priv, ...@@ -392,12 +392,12 @@ batadv_add_packet(struct batadv_priv *bat_priv,
return NULL; return NULL;
len = sizeof(*packet) + vis_info_len; len = sizeof(*packet) + vis_info_len;
info->skb_packet = dev_alloc_skb(len + ETH_HLEN + NET_IP_ALIGN); info->skb_packet = netdev_alloc_skb_ip_align(NULL, len + ETH_HLEN);
if (!info->skb_packet) { if (!info->skb_packet) {
kfree(info); kfree(info);
return NULL; return NULL;
} }
skb_reserve(info->skb_packet, ETH_HLEN + NET_IP_ALIGN); skb_reserve(info->skb_packet, ETH_HLEN);
packet = (struct batadv_vis_packet *)skb_put(info->skb_packet, len); packet = (struct batadv_vis_packet *)skb_put(info->skb_packet, len);
kref_init(&info->refcount); kref_init(&info->refcount);
...@@ -697,7 +697,7 @@ static void batadv_broadcast_vis_packet(struct batadv_priv *bat_priv, ...@@ -697,7 +697,7 @@ static void batadv_broadcast_vis_packet(struct batadv_priv *bat_priv,
struct batadv_orig_node *orig_node; struct batadv_orig_node *orig_node;
struct batadv_vis_packet *packet; struct batadv_vis_packet *packet;
struct sk_buff *skb; struct sk_buff *skb;
uint32_t i; uint32_t i, res;
packet = (struct batadv_vis_packet *)info->skb_packet->data; packet = (struct batadv_vis_packet *)info->skb_packet->data;
...@@ -724,7 +724,8 @@ static void batadv_broadcast_vis_packet(struct batadv_priv *bat_priv, ...@@ -724,7 +724,8 @@ static void batadv_broadcast_vis_packet(struct batadv_priv *bat_priv,
if (!skb) if (!skb)
continue; continue;
if (!batadv_send_skb_to_orig(skb, orig_node, NULL)) res = batadv_send_skb_to_orig(skb, orig_node, NULL);
if (res == NET_XMIT_DROP)
kfree_skb(skb); kfree_skb(skb);
} }
rcu_read_unlock(); rcu_read_unlock();
...@@ -748,7 +749,7 @@ static void batadv_unicast_vis_packet(struct batadv_priv *bat_priv, ...@@ -748,7 +749,7 @@ static void batadv_unicast_vis_packet(struct batadv_priv *bat_priv,
if (!skb) if (!skb)
goto out; goto out;
if (!batadv_send_skb_to_orig(skb, orig_node, NULL)) if (batadv_send_skb_to_orig(skb, orig_node, NULL) == NET_XMIT_DROP)
kfree_skb(skb); kfree_skb(skb);
out: out:
...@@ -854,13 +855,13 @@ int batadv_vis_init(struct batadv_priv *bat_priv) ...@@ -854,13 +855,13 @@ int batadv_vis_init(struct batadv_priv *bat_priv)
if (!bat_priv->vis.my_info) if (!bat_priv->vis.my_info)
goto err; goto err;
len = sizeof(*packet) + BATADV_MAX_VIS_PACKET_SIZE; len = sizeof(*packet) + BATADV_MAX_VIS_PACKET_SIZE + ETH_HLEN;
len += ETH_HLEN + NET_IP_ALIGN; bat_priv->vis.my_info->skb_packet = netdev_alloc_skb_ip_align(NULL,
bat_priv->vis.my_info->skb_packet = dev_alloc_skb(len); len);
if (!bat_priv->vis.my_info->skb_packet) if (!bat_priv->vis.my_info->skb_packet)
goto free_info; goto free_info;
skb_reserve(bat_priv->vis.my_info->skb_packet, ETH_HLEN + NET_IP_ALIGN); skb_reserve(bat_priv->vis.my_info->skb_packet, ETH_HLEN);
tmp_skb = bat_priv->vis.my_info->skb_packet; tmp_skb = bat_priv->vis.my_info->skb_packet;
packet = (struct batadv_vis_packet *)skb_put(tmp_skb, sizeof(*packet)); packet = (struct batadv_vis_packet *)skb_put(tmp_skb, sizeof(*packet));
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册