Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
linux
Commits
dcfd9cdc
Commit
dcfd9cdc
authored
May 02, 2011
by
David S. Miller
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'batman-adv/next' of
git://git.open-mesh.org/ecsv/linux-merge
parents
56157872
32ae9b22
Changes
14
Hide whitespace changes
Inline
Side-by-side
Showing
14 changed files
with
292 additions
and
138 deletions
+292
-138
net/batman-adv/aggregation.c
net/batman-adv/aggregation.c
+0
-1
net/batman-adv/gateway_client.c
net/batman-adv/gateway_client.c
+27
-18
net/batman-adv/hard-interface.c
net/batman-adv/hard-interface.c
+57
-26
net/batman-adv/hard-interface.h
net/batman-adv/hard-interface.h
+18
-0
net/batman-adv/icmp_socket.c
net/batman-adv/icmp_socket.c
+14
-5
net/batman-adv/main.h
net/batman-adv/main.h
+2
-0
net/batman-adv/originator.c
net/batman-adv/originator.c
+21
-13
net/batman-adv/routing.c
net/batman-adv/routing.c
+14
-20
net/batman-adv/send.c
net/batman-adv/send.c
+13
-5
net/batman-adv/soft-interface.c
net/batman-adv/soft-interface.c
+45
-19
net/batman-adv/translation-table.c
net/batman-adv/translation-table.c
+43
-14
net/batman-adv/types.h
net/batman-adv/types.h
+1
-1
net/batman-adv/unicast.c
net/batman-adv/unicast.c
+11
-5
net/batman-adv/vis.c
net/batman-adv/vis.c
+26
-11
No files found.
net/batman-adv/aggregation.c
View file @
dcfd9cdc
...
@@ -95,7 +95,6 @@ static bool can_aggregate_with(struct batman_packet *new_batman_packet,
...
@@ -95,7 +95,6 @@ static bool can_aggregate_with(struct batman_packet *new_batman_packet,
return
false
;
return
false
;
}
}
#define atomic_dec_not_zero(v) atomic_add_unless((v), -1, 0)
/* create a new aggregated packet and add this packet to it */
/* create a new aggregated packet and add this packet to it */
static
void
new_aggregated_packet
(
unsigned
char
*
packet_buff
,
int
packet_len
,
static
void
new_aggregated_packet
(
unsigned
char
*
packet_buff
,
int
packet_len
,
unsigned
long
send_time
,
bool
direct_link
,
unsigned
long
send_time
,
bool
direct_link
,
...
...
net/batman-adv/gateway_client.c
View file @
dcfd9cdc
...
@@ -127,7 +127,7 @@ void gw_election(struct bat_priv *bat_priv)
...
@@ -127,7 +127,7 @@ void gw_election(struct bat_priv *bat_priv)
return
;
return
;
curr_gw
=
gw_get_selected_gw_node
(
bat_priv
);
curr_gw
=
gw_get_selected_gw_node
(
bat_priv
);
if
(
!
curr_gw
)
if
(
curr_gw
)
goto
out
;
goto
out
;
rcu_read_lock
();
rcu_read_lock
();
...
@@ -310,9 +310,13 @@ void gw_node_update(struct bat_priv *bat_priv,
...
@@ -310,9 +310,13 @@ void gw_node_update(struct bat_priv *bat_priv,
struct
hlist_node
*
node
;
struct
hlist_node
*
node
;
struct
gw_node
*
gw_node
,
*
curr_gw
;
struct
gw_node
*
gw_node
,
*
curr_gw
;
/**
* Note: We don't need a NULL check here, since curr_gw never gets
* dereferenced. If curr_gw is NULL we also should not exit as we may
* have this gateway in our list (duplication check!) even though we
* have no currently selected gateway.
*/
curr_gw
=
gw_get_selected_gw_node
(
bat_priv
);
curr_gw
=
gw_get_selected_gw_node
(
bat_priv
);
if
(
!
curr_gw
)
goto
out
;
rcu_read_lock
();
rcu_read_lock
();
hlist_for_each_entry_rcu
(
gw_node
,
node
,
&
bat_priv
->
gw_list
,
list
)
{
hlist_for_each_entry_rcu
(
gw_node
,
node
,
&
bat_priv
->
gw_list
,
list
)
{
...
@@ -350,7 +354,7 @@ void gw_node_update(struct bat_priv *bat_priv,
...
@@ -350,7 +354,7 @@ void gw_node_update(struct bat_priv *bat_priv,
gw_deselect
(
bat_priv
);
gw_deselect
(
bat_priv
);
unlock:
unlock:
rcu_read_unlock
();
rcu_read_unlock
();
out:
if
(
curr_gw
)
if
(
curr_gw
)
gw_node_free_ref
(
curr_gw
);
gw_node_free_ref
(
curr_gw
);
}
}
...
@@ -435,30 +439,32 @@ int gw_client_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -435,30 +439,32 @@ int gw_client_seq_print_text(struct seq_file *seq, void *offset)
{
{
struct
net_device
*
net_dev
=
(
struct
net_device
*
)
seq
->
private
;
struct
net_device
*
net_dev
=
(
struct
net_device
*
)
seq
->
private
;
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
hard_iface
*
primary_if
;
struct
gw_node
*
gw_node
;
struct
gw_node
*
gw_node
;
struct
hlist_node
*
node
;
struct
hlist_node
*
node
;
int
gw_count
=
0
;
int
gw_count
=
0
,
ret
=
0
;
if
(
!
bat_priv
->
primary_if
)
{
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
{
return
seq_printf
(
seq
,
"BATMAN mesh %s disabled - please "
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - please "
"specify interfaces to enable it
\n
"
,
"specify interfaces to enable it
\n
"
,
net_dev
->
name
);
net_dev
->
name
);
goto
out
;
}
}
if
(
bat_priv
->
primary_if
->
if_status
!=
IF_ACTIVE
)
{
if
(
primary_if
->
if_status
!=
IF_ACTIVE
)
{
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
return
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
"primary interface not active
\n
"
,
"primary interface not active
\n
"
,
net_dev
->
name
);
net_dev
->
name
)
;
goto
out
;
}
}
seq_printf
(
seq
,
" %-12s (%s/%i) %17s [%10s]: gw_class ... "
seq_printf
(
seq
,
" %-12s (%s/%i) %17s [%10s]: gw_class ... "
"[B.A.T.M.A.N. adv %s%s, MainIF/MAC: %s/%pM (%s)]
\n
"
,
"[B.A.T.M.A.N. adv %s%s, MainIF/MAC: %s/%pM (%s)]
\n
"
,
"Gateway"
,
"#"
,
TQ_MAX_VALUE
,
"Nexthop"
,
"Gateway"
,
"#"
,
TQ_MAX_VALUE
,
"Nexthop"
,
"outgoingIF"
,
SOURCE_VERSION
,
REVISION_VERSION_STR
,
"outgoingIF"
,
SOURCE_VERSION
,
REVISION_VERSION_STR
,
bat_priv
->
primary_if
->
net_dev
->
name
,
primary_if
->
net_dev
->
name
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
net_dev
->
name
);
primary_if
->
net_dev
->
dev_addr
,
net_dev
->
name
);
rcu_read_lock
();
rcu_read_lock
();
hlist_for_each_entry_rcu
(
gw_node
,
node
,
&
bat_priv
->
gw_list
,
list
)
{
hlist_for_each_entry_rcu
(
gw_node
,
node
,
&
bat_priv
->
gw_list
,
list
)
{
...
@@ -476,7 +482,10 @@ int gw_client_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -476,7 +482,10 @@ int gw_client_seq_print_text(struct seq_file *seq, void *offset)
if
(
gw_count
==
0
)
if
(
gw_count
==
0
)
seq_printf
(
seq
,
"No gateways in range ...
\n
"
);
seq_printf
(
seq
,
"No gateways in range ...
\n
"
);
return
0
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
int
gw_is_target
(
struct
bat_priv
*
bat_priv
,
struct
sk_buff
*
skb
)
int
gw_is_target
(
struct
bat_priv
*
bat_priv
,
struct
sk_buff
*
skb
)
...
...
net/batman-adv/hard-interface.c
View file @
dcfd9cdc
...
@@ -110,47 +110,60 @@ static struct hard_iface *hardif_get_active(struct net_device *soft_iface)
...
@@ -110,47 +110,60 @@ static struct hard_iface *hardif_get_active(struct net_device *soft_iface)
return
hard_iface
;
return
hard_iface
;
}
}
static
void
update_primary
_addr
(
struct
bat_priv
*
bat_priv
)
static
void
primary_if_update
_addr
(
struct
bat_priv
*
bat_priv
)
{
{
struct
vis_packet
*
vis_packet
;
struct
vis_packet
*
vis_packet
;
struct
hard_iface
*
primary_if
;
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
out
;
vis_packet
=
(
struct
vis_packet
*
)
vis_packet
=
(
struct
vis_packet
*
)
bat_priv
->
my_vis_info
->
skb_packet
->
data
;
bat_priv
->
my_vis_info
->
skb_packet
->
data
;
memcpy
(
vis_packet
->
vis_orig
,
memcpy
(
vis_packet
->
vis_orig
,
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
memcpy
(
vis_packet
->
sender_orig
,
memcpy
(
vis_packet
->
sender_orig
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
}
}
static
void
set_primary_if
(
struct
bat_priv
*
bat_priv
,
static
void
primary_if_select
(
struct
bat_priv
*
bat_priv
,
struct
hard_iface
*
hard_iface
)
struct
hard_iface
*
new_
hard_iface
)
{
{
struct
hard_iface
*
curr_hard_iface
;
struct
batman_packet
*
batman_packet
;
struct
batman_packet
*
batman_packet
;
struct
hard_iface
*
old_if
;
if
(
hard_iface
&&
!
atomic_inc_not_zero
(
&
hard_iface
->
refcount
))
spin_lock_bh
(
&
hardif_list_lock
);
hard_iface
=
NULL
;
old_if
=
bat_priv
->
primary_if
;
if
(
new_hard_iface
&&
!
atomic_inc_not_zero
(
&
new_hard_iface
->
refcount
))
bat_priv
->
primary_if
=
hard_iface
;
new_hard_iface
=
NULL
;
if
(
old_if
)
curr_hard_iface
=
bat_priv
->
primary_if
;
hardif_free_ref
(
old_if
);
rcu_assign_pointer
(
bat_priv
->
primary_if
,
new_hard_iface
);
if
(
!
bat_priv
->
primary_if
)
if
(
curr_hard_iface
)
return
;
hardif_free_ref
(
curr_hard_iface
)
;
batman_packet
=
(
struct
batman_packet
*
)(
hard_iface
->
packet_buff
);
if
(
!
new_hard_iface
)
goto
out
;
batman_packet
=
(
struct
batman_packet
*
)(
new_hard_iface
->
packet_buff
);
batman_packet
->
flags
=
PRIMARIES_FIRST_HOP
;
batman_packet
->
flags
=
PRIMARIES_FIRST_HOP
;
batman_packet
->
ttl
=
TTL
;
batman_packet
->
ttl
=
TTL
;
update_primary
_addr
(
bat_priv
);
primary_if_update
_addr
(
bat_priv
);
/***
/***
* hacky trick to make sure that we send the HNA information via
* hacky trick to make sure that we send the HNA information via
* our new primary interface
* our new primary interface
*/
*/
atomic_set
(
&
bat_priv
->
hna_local_changed
,
1
);
atomic_set
(
&
bat_priv
->
hna_local_changed
,
1
);
out:
spin_unlock_bh
(
&
hardif_list_lock
);
}
}
static
bool
hardif_is_iface_up
(
struct
hard_iface
*
hard_iface
)
static
bool
hardif_is_iface_up
(
struct
hard_iface
*
hard_iface
)
...
@@ -236,9 +249,10 @@ void update_min_mtu(struct net_device *soft_iface)
...
@@ -236,9 +249,10 @@ void update_min_mtu(struct net_device *soft_iface)
static
void
hardif_activate_interface
(
struct
hard_iface
*
hard_iface
)
static
void
hardif_activate_interface
(
struct
hard_iface
*
hard_iface
)
{
{
struct
bat_priv
*
bat_priv
;
struct
bat_priv
*
bat_priv
;
struct
hard_iface
*
primary_if
=
NULL
;
if
(
hard_iface
->
if_status
!=
IF_INACTIVE
)
if
(
hard_iface
->
if_status
!=
IF_INACTIVE
)
return
;
goto
out
;
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
...
@@ -249,14 +263,18 @@ static void hardif_activate_interface(struct hard_iface *hard_iface)
...
@@ -249,14 +263,18 @@ static void hardif_activate_interface(struct hard_iface *hard_iface)
* the first active interface becomes our primary interface or
* the first active interface becomes our primary interface or
* the next active interface after the old primay interface was removed
* the next active interface after the old primay interface was removed
*/
*/
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
set_primary_if
(
bat_priv
,
hard_iface
);
if
(
!
primary_if
)
primary_if_select
(
bat_priv
,
hard_iface
);
bat_info
(
hard_iface
->
soft_iface
,
"Interface activated: %s
\n
"
,
bat_info
(
hard_iface
->
soft_iface
,
"Interface activated: %s
\n
"
,
hard_iface
->
net_dev
->
name
);
hard_iface
->
net_dev
->
name
);
update_min_mtu
(
hard_iface
->
soft_iface
);
update_min_mtu
(
hard_iface
->
soft_iface
);
return
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
}
}
static
void
hardif_deactivate_interface
(
struct
hard_iface
*
hard_iface
)
static
void
hardif_deactivate_interface
(
struct
hard_iface
*
hard_iface
)
...
@@ -386,12 +404,13 @@ int hardif_enable_interface(struct hard_iface *hard_iface, char *iface_name)
...
@@ -386,12 +404,13 @@ int hardif_enable_interface(struct hard_iface *hard_iface, char *iface_name)
void
hardif_disable_interface
(
struct
hard_iface
*
hard_iface
)
void
hardif_disable_interface
(
struct
hard_iface
*
hard_iface
)
{
{
struct
bat_priv
*
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
struct
hard_iface
*
primary_if
=
NULL
;
if
(
hard_iface
->
if_status
==
IF_ACTIVE
)
if
(
hard_iface
->
if_status
==
IF_ACTIVE
)
hardif_deactivate_interface
(
hard_iface
);
hardif_deactivate_interface
(
hard_iface
);
if
(
hard_iface
->
if_status
!=
IF_INACTIVE
)
if
(
hard_iface
->
if_status
!=
IF_INACTIVE
)
return
;
goto
out
;
bat_info
(
hard_iface
->
soft_iface
,
"Removing interface: %s
\n
"
,
bat_info
(
hard_iface
->
soft_iface
,
"Removing interface: %s
\n
"
,
hard_iface
->
net_dev
->
name
);
hard_iface
->
net_dev
->
name
);
...
@@ -400,11 +419,12 @@ void hardif_disable_interface(struct hard_iface *hard_iface)
...
@@ -400,11 +419,12 @@ void hardif_disable_interface(struct hard_iface *hard_iface)
bat_priv
->
num_ifaces
--
;
bat_priv
->
num_ifaces
--
;
orig_hash_del_if
(
hard_iface
,
bat_priv
->
num_ifaces
);
orig_hash_del_if
(
hard_iface
,
bat_priv
->
num_ifaces
);
if
(
hard_iface
==
bat_priv
->
primary_if
)
{
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
hard_iface
==
primary_if
)
{
struct
hard_iface
*
new_if
;
struct
hard_iface
*
new_if
;
new_if
=
hardif_get_active
(
hard_iface
->
soft_iface
);
new_if
=
hardif_get_active
(
hard_iface
->
soft_iface
);
set_primary_if
(
bat_priv
,
new_if
);
primary_if_select
(
bat_priv
,
new_if
);
if
(
new_if
)
if
(
new_if
)
hardif_free_ref
(
new_if
);
hardif_free_ref
(
new_if
);
...
@@ -425,6 +445,10 @@ void hardif_disable_interface(struct hard_iface *hard_iface)
...
@@ -425,6 +445,10 @@ void hardif_disable_interface(struct hard_iface *hard_iface)
hard_iface
->
soft_iface
=
NULL
;
hard_iface
->
soft_iface
=
NULL
;
hardif_free_ref
(
hard_iface
);
hardif_free_ref
(
hard_iface
);
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
}
}
static
struct
hard_iface
*
hardif_add_interface
(
struct
net_device
*
net_dev
)
static
struct
hard_iface
*
hardif_add_interface
(
struct
net_device
*
net_dev
)
...
@@ -514,6 +538,7 @@ static int hard_if_event(struct notifier_block *this,
...
@@ -514,6 +538,7 @@ static int hard_if_event(struct notifier_block *this,
{
{
struct
net_device
*
net_dev
=
(
struct
net_device
*
)
ptr
;
struct
net_device
*
net_dev
=
(
struct
net_device
*
)
ptr
;
struct
hard_iface
*
hard_iface
=
hardif_get_by_netdev
(
net_dev
);
struct
hard_iface
*
hard_iface
=
hardif_get_by_netdev
(
net_dev
);
struct
hard_iface
*
primary_if
=
NULL
;
struct
bat_priv
*
bat_priv
;
struct
bat_priv
*
bat_priv
;
if
(
!
hard_iface
&&
event
==
NETDEV_REGISTER
)
if
(
!
hard_iface
&&
event
==
NETDEV_REGISTER
)
...
@@ -549,8 +574,12 @@ static int hard_if_event(struct notifier_block *this,
...
@@ -549,8 +574,12 @@ static int hard_if_event(struct notifier_block *this,
update_mac_addresses
(
hard_iface
);
update_mac_addresses
(
hard_iface
);
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
if
(
hard_iface
==
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
update_primary_addr
(
bat_priv
);
if
(
!
primary_if
)
goto
hardif_put
;
if
(
hard_iface
==
primary_if
)
primary_if_update_addr
(
bat_priv
);
break
;
break
;
default:
default:
break
;
break
;
...
@@ -559,6 +588,8 @@ static int hard_if_event(struct notifier_block *this,
...
@@ -559,6 +588,8 @@ static int hard_if_event(struct notifier_block *this,
hardif_put:
hardif_put:
hardif_free_ref
(
hard_iface
);
hardif_free_ref
(
hard_iface
);
out:
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
NOTIFY_DONE
;
return
NOTIFY_DONE
;
}
}
...
...
net/batman-adv/hard-interface.h
View file @
dcfd9cdc
...
@@ -45,4 +45,22 @@ static inline void hardif_free_ref(struct hard_iface *hard_iface)
...
@@ -45,4 +45,22 @@ static inline void hardif_free_ref(struct hard_iface *hard_iface)
call_rcu
(
&
hard_iface
->
rcu
,
hardif_free_rcu
);
call_rcu
(
&
hard_iface
->
rcu
,
hardif_free_rcu
);
}
}
static
inline
struct
hard_iface
*
primary_if_get_selected
(
struct
bat_priv
*
bat_priv
)
{
struct
hard_iface
*
hard_iface
;
rcu_read_lock
();
hard_iface
=
rcu_dereference
(
bat_priv
->
primary_if
);
if
(
!
hard_iface
)
goto
out
;
if
(
!
atomic_inc_not_zero
(
&
hard_iface
->
refcount
))
hard_iface
=
NULL
;
out:
rcu_read_unlock
();
return
hard_iface
;
}
#endif
/* _NET_BATMAN_ADV_HARD_INTERFACE_H_ */
#endif
/* _NET_BATMAN_ADV_HARD_INTERFACE_H_ */
net/batman-adv/icmp_socket.c
View file @
dcfd9cdc
...
@@ -153,6 +153,7 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
...
@@ -153,6 +153,7 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
{
{
struct
socket_client
*
socket_client
=
file
->
private_data
;
struct
socket_client
*
socket_client
=
file
->
private_data
;
struct
bat_priv
*
bat_priv
=
socket_client
->
bat_priv
;
struct
bat_priv
*
bat_priv
=
socket_client
->
bat_priv
;
struct
hard_iface
*
primary_if
=
NULL
;
struct
sk_buff
*
skb
;
struct
sk_buff
*
skb
;
struct
icmp_packet_rr
*
icmp_packet
;
struct
icmp_packet_rr
*
icmp_packet
;
...
@@ -167,15 +168,21 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
...
@@ -167,15 +168,21 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
return
-
EINVAL
;
return
-
EINVAL
;
}
}
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
return
-
EFAULT
;
if
(
!
primary_if
)
{
len
=
-
EFAULT
;
goto
out
;
}
if
(
len
>=
sizeof
(
struct
icmp_packet_rr
))
if
(
len
>=
sizeof
(
struct
icmp_packet_rr
))
packet_len
=
sizeof
(
struct
icmp_packet_rr
);
packet_len
=
sizeof
(
struct
icmp_packet_rr
);
skb
=
dev_alloc_skb
(
packet_len
+
sizeof
(
struct
ethhdr
));
skb
=
dev_alloc_skb
(
packet_len
+
sizeof
(
struct
ethhdr
));
if
(
!
skb
)
if
(
!
skb
)
{
return
-
ENOMEM
;
len
=
-
ENOMEM
;
goto
out
;
}
skb_reserve
(
skb
,
sizeof
(
struct
ethhdr
));
skb_reserve
(
skb
,
sizeof
(
struct
ethhdr
));
icmp_packet
=
(
struct
icmp_packet_rr
*
)
skb_put
(
skb
,
packet_len
);
icmp_packet
=
(
struct
icmp_packet_rr
*
)
skb_put
(
skb
,
packet_len
);
...
@@ -233,7 +240,7 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
...
@@ -233,7 +240,7 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
goto
dst_unreach
;
goto
dst_unreach
;
memcpy
(
icmp_packet
->
orig
,
memcpy
(
icmp_packet
->
orig
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
if
(
packet_len
==
sizeof
(
struct
icmp_packet_rr
))
if
(
packet_len
==
sizeof
(
struct
icmp_packet_rr
))
memcpy
(
icmp_packet
->
rr
,
memcpy
(
icmp_packet
->
rr
,
...
@@ -248,6 +255,8 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
...
@@ -248,6 +255,8 @@ static ssize_t bat_socket_write(struct file *file, const char __user *buff,
free_skb:
free_skb:
kfree_skb
(
skb
);
kfree_skb
(
skb
);
out:
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
if
(
neigh_node
)
if
(
neigh_node
)
neigh_node_free_ref
(
neigh_node
);
neigh_node_free_ref
(
neigh_node
);
if
(
orig_node
)
if
(
orig_node
)
...
...
net/batman-adv/main.h
View file @
dcfd9cdc
...
@@ -175,4 +175,6 @@ static inline int compare_eth(void *data1, void *data2)
...
@@ -175,4 +175,6 @@ static inline int compare_eth(void *data1, void *data2)
return
(
memcmp
(
data1
,
data2
,
ETH_ALEN
)
==
0
?
1
:
0
);
return
(
memcmp
(
data1
,
data2
,
ETH_ALEN
)
==
0
?
1
:
0
);
}
}
#define atomic_dec_not_zero(v) atomic_add_unless((v), -1, 0)
#endif
/* _NET_BATMAN_ADV_MAIN_H_ */
#endif
/* _NET_BATMAN_ADV_MAIN_H_ */
net/batman-adv/originator.c
View file @
dcfd9cdc
...
@@ -405,29 +405,34 @@ int orig_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -405,29 +405,34 @@ int orig_seq_print_text(struct seq_file *seq, void *offset)
struct
hashtable_t
*
hash
=
bat_priv
->
orig_hash
;
struct
hashtable_t
*
hash
=
bat_priv
->
orig_hash
;
struct
hlist_node
*
node
,
*
node_tmp
;
struct
hlist_node
*
node
,
*
node_tmp
;
struct
hlist_head
*
head
;
struct
hlist_head
*
head
;
struct
hard_iface
*
primary_if
;
struct
orig_node
*
orig_node
;
struct
orig_node
*
orig_node
;
struct
neigh_node
*
neigh_node
,
*
neigh_node_tmp
;
struct
neigh_node
*
neigh_node
,
*
neigh_node_tmp
;
int
batman_count
=
0
;
int
batman_count
=
0
;
int
last_seen_secs
;
int
last_seen_secs
;
int
last_seen_msecs
;
int
last_seen_msecs
;
int
i
;
int
i
,
ret
=
0
;
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
(
!
bat_priv
->
primary_if
)
||
if
(
!
primary_if
)
{
(
bat_priv
->
primary_if
->
if_status
!=
IF_ACTIVE
))
{
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
if
(
!
bat_priv
->
primary_if
)
"please specify interfaces to enable it
\n
"
,
return
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
net_dev
->
name
);
"please specify interfaces to enable it
\n
"
,
goto
out
;
net_dev
->
name
);
}
return
seq_printf
(
seq
,
"BATMAN mesh %s "
if
(
primary_if
->
if_status
!=
IF_ACTIVE
)
{
"disabled - primary interface not active
\n
"
,
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s "
net_dev
->
name
);
"disabled - primary interface not active
\n
"
,
net_dev
->
name
);
goto
out
;
}
}
seq_printf
(
seq
,
"[B.A.T.M.A.N. adv %s%s, MainIF/MAC: %s/%pM (%s)]
\n
"
,
seq_printf
(
seq
,
"[B.A.T.M.A.N. adv %s%s, MainIF/MAC: %s/%pM (%s)]
\n
"
,
SOURCE_VERSION
,
REVISION_VERSION_STR
,
SOURCE_VERSION
,
REVISION_VERSION_STR
,
bat_priv
->
primary_if
->
net_dev
->
name
,
primary_if
->
net_dev
->
name
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
net_dev
->
name
);
primary_if
->
net_dev
->
dev_addr
,
net_dev
->
name
);
seq_printf
(
seq
,
" %-15s %s (%s/%i) %17s [%10s]: %20s ...
\n
"
,
seq_printf
(
seq
,
" %-15s %s (%s/%i) %17s [%10s]: %20s ...
\n
"
,
"Originator"
,
"last-seen"
,
"#"
,
TQ_MAX_VALUE
,
"Nexthop"
,
"Originator"
,
"last-seen"
,
"#"
,
TQ_MAX_VALUE
,
"Nexthop"
,
"outgoingIF"
,
"Potential nexthops"
);
"outgoingIF"
,
"Potential nexthops"
);
...
@@ -474,7 +479,10 @@ int orig_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -474,7 +479,10 @@ int orig_seq_print_text(struct seq_file *seq, void *offset)
if
(
batman_count
==
0
)
if
(
batman_count
==
0
)
seq_printf
(
seq
,
"No batman nodes in range ...
\n
"
);
seq_printf
(
seq
,
"No batman nodes in range ...
\n
"
);
return
0
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
static
int
orig_node_add_if
(
struct
orig_node
*
orig_node
,
int
max_if_num
)
static
int
orig_node_add_if
(
struct
orig_node
*
orig_node
,
int
max_if_num
)
...
...
net/batman-adv/routing.c
View file @
dcfd9cdc
...
@@ -904,6 +904,7 @@ int recv_bat_packet(struct sk_buff *skb, struct hard_iface *hard_iface)
...
@@ -904,6 +904,7 @@ int recv_bat_packet(struct sk_buff *skb, struct hard_iface *hard_iface)
static
int
recv_my_icmp_packet
(
struct
bat_priv
*
bat_priv
,
static
int
recv_my_icmp_packet
(
struct
bat_priv
*
bat_priv
,
struct
sk_buff
*
skb
,
size_t
icmp_len
)
struct
sk_buff
*
skb
,
size_t
icmp_len
)
{
{
struct
hard_iface
*
primary_if
=
NULL
;
struct
orig_node
*
orig_node
=
NULL
;
struct
orig_node
*
orig_node
=
NULL
;
struct
neigh_node
*
router
=
NULL
;
struct
neigh_node
*
router
=
NULL
;
struct
icmp_packet_rr
*
icmp_packet
;
struct
icmp_packet_rr
*
icmp_packet
;
...
@@ -917,7 +918,8 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
...
@@ -917,7 +918,8 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
goto
out
;
goto
out
;
}
}
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
out
;
goto
out
;
/* answer echo request (ping) */
/* answer echo request (ping) */
...
@@ -937,8 +939,7 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
...
@@ -937,8 +939,7 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
icmp_packet
=
(
struct
icmp_packet_rr
*
)
skb
->
data
;
icmp_packet
=
(
struct
icmp_packet_rr
*
)
skb
->
data
;
memcpy
(
icmp_packet
->
dst
,
icmp_packet
->
orig
,
ETH_ALEN
);
memcpy
(
icmp_packet
->
dst
,
icmp_packet
->
orig
,
ETH_ALEN
);
memcpy
(
icmp_packet
->
orig
,
memcpy
(
icmp_packet
->
orig
,
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
icmp_packet
->
msg_type
=
ECHO_REPLY
;
icmp_packet
->
msg_type
=
ECHO_REPLY
;
icmp_packet
->
ttl
=
TTL
;
icmp_packet
->
ttl
=
TTL
;
...
@@ -946,6 +947,8 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
...
@@ -946,6 +947,8 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
ret
=
NET_RX_SUCCESS
;
ret
=
NET_RX_SUCCESS
;
out:
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
if
(
router
)
if
(
router
)
neigh_node_free_ref
(
router
);
neigh_node_free_ref
(
router
);
if
(
orig_node
)
if
(
orig_node
)
...
@@ -956,6 +959,7 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
...
@@ -956,6 +959,7 @@ static int recv_my_icmp_packet(struct bat_priv *bat_priv,
static
int
recv_icmp_ttl_exceeded
(
struct
bat_priv
*
bat_priv
,
static
int
recv_icmp_ttl_exceeded
(
struct
bat_priv
*
bat_priv
,
struct
sk_buff
*
skb
)
struct
sk_buff
*
skb
)
{
{
struct
hard_iface
*
primary_if
=
NULL
;
struct
orig_node
*
orig_node
=
NULL
;
struct
orig_node
*
orig_node
=
NULL
;
struct
neigh_node
*
router
=
NULL
;
struct
neigh_node
*
router
=
NULL
;
struct
icmp_packet
*
icmp_packet
;
struct
icmp_packet
*
icmp_packet
;
...
@@ -971,7 +975,8 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
...
@@ -971,7 +975,8 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
goto
out
;
goto
out
;
}
}
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
out
;
goto
out
;
/* get routing information */
/* get routing information */
...
@@ -990,8 +995,7 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
...
@@ -990,8 +995,7 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
icmp_packet
=
(
struct
icmp_packet
*
)
skb
->
data
;
icmp_packet
=
(
struct
icmp_packet
*
)
skb
->
data
;
memcpy
(
icmp_packet
->
dst
,
icmp_packet
->
orig
,
ETH_ALEN
);
memcpy
(
icmp_packet
->
dst
,
icmp_packet
->
orig
,
ETH_ALEN
);
memcpy
(
icmp_packet
->
orig
,
memcpy
(
icmp_packet
->
orig
,
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
icmp_packet
->
msg_type
=
TTL_EXCEEDED
;
icmp_packet
->
msg_type
=
TTL_EXCEEDED
;
icmp_packet
->
ttl
=
TTL
;
icmp_packet
->
ttl
=
TTL
;
...
@@ -999,6 +1003,8 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
...
@@ -999,6 +1003,8 @@ static int recv_icmp_ttl_exceeded(struct bat_priv *bat_priv,
ret
=
NET_RX_SUCCESS
;
ret
=
NET_RX_SUCCESS
;
out:
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
if
(
router
)
if
(
router
)
neigh_node_free_ref
(
router
);
neigh_node_free_ref
(
router
);
if
(
orig_node
)
if
(
orig_node
)
...
@@ -1310,13 +1316,10 @@ int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
...
@@ -1310,13 +1316,10 @@ int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
}
}
/* get routing information */
/* get routing information */
rcu_read_lock
();
orig_node
=
orig_hash_find
(
bat_priv
,
unicast_packet
->
dest
);
orig_node
=
orig_hash_find
(
bat_priv
,
unicast_packet
->
dest
);
if
(
!
orig_node
)
if
(
!
orig_node
)
goto
unlock
;
goto
out
;
rcu_read_unlock
();
/* find_router() increases neigh_nodes refcount if found. */
/* find_router() increases neigh_nodes refcount if found. */
neigh_node
=
find_router
(
bat_priv
,
orig_node
,
recv_if
);
neigh_node
=
find_router
(
bat_priv
,
orig_node
,
recv_if
);
...
@@ -1362,10 +1365,7 @@ int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
...
@@ -1362,10 +1365,7 @@ int route_unicast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
/* route it */
/* route it */
send_skb_packet
(
skb
,
neigh_node
->
if_incoming
,
neigh_node
->
addr
);
send_skb_packet
(
skb
,
neigh_node
->
if_incoming
,
neigh_node
->
addr
);
ret
=
NET_RX_SUCCESS
;
ret
=
NET_RX_SUCCESS
;
goto
out
;
unlock:
rcu_read_unlock
();
out:
out:
if
(
neigh_node
)
if
(
neigh_node
)
neigh_node_free_ref
(
neigh_node
);
neigh_node_free_ref
(
neigh_node
);
...
@@ -1464,13 +1464,10 @@ int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
...
@@ -1464,13 +1464,10 @@ int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
if
(
bcast_packet
->
ttl
<
2
)
if
(
bcast_packet
->
ttl
<
2
)
goto
out
;
goto
out
;
rcu_read_lock
();
orig_node
=
orig_hash_find
(
bat_priv
,
bcast_packet
->
orig
);
orig_node
=
orig_hash_find
(
bat_priv
,
bcast_packet
->
orig
);
if
(
!
orig_node
)
if
(
!
orig_node
)
goto
rcu_unlock
;
goto
out
;
rcu_read_unlock
();
spin_lock_bh
(
&
orig_node
->
bcast_seqno_lock
);
spin_lock_bh
(
&
orig_node
->
bcast_seqno_lock
);
...
@@ -1501,9 +1498,6 @@ int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
...
@@ -1501,9 +1498,6 @@ int recv_bcast_packet(struct sk_buff *skb, struct hard_iface *recv_if)
ret
=
NET_RX_SUCCESS
;
ret
=
NET_RX_SUCCESS
;
goto
out
;
goto
out
;
rcu_unlock:
rcu_read_unlock
();
goto
out
;
spin_unlock:
spin_unlock:
spin_unlock_bh
(
&
orig_node
->
bcast_seqno_lock
);
spin_unlock_bh
(
&
orig_node
->
bcast_seqno_lock
);
out:
out:
...
...
net/batman-adv/send.c
View file @
dcfd9cdc
...
@@ -244,6 +244,7 @@ static void rebuild_batman_packet(struct bat_priv *bat_priv,
...
@@ -244,6 +244,7 @@ static void rebuild_batman_packet(struct bat_priv *bat_priv,
void
schedule_own_packet
(
struct
hard_iface
*
hard_iface
)
void
schedule_own_packet
(
struct
hard_iface
*
hard_iface
)
{
{
struct
bat_priv
*
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
hard_iface
->
soft_iface
);
struct
hard_iface
*
primary_if
;
unsigned
long
send_time
;
unsigned
long
send_time
;
struct
batman_packet
*
batman_packet
;
struct
batman_packet
*
batman_packet
;
int
vis_server
;
int
vis_server
;
...
@@ -253,6 +254,7 @@ void schedule_own_packet(struct hard_iface *hard_iface)
...
@@ -253,6 +254,7 @@ void schedule_own_packet(struct hard_iface *hard_iface)
return
;
return
;
vis_server
=
atomic_read
(
&
bat_priv
->
vis_mode
);
vis_server
=
atomic_read
(
&
bat_priv
->
vis_mode
);
primary_if
=
primary_if_get_selected
(
bat_priv
);
/**
/**
* the interface gets activated here to avoid race conditions between
* the interface gets activated here to avoid race conditions between
...
@@ -266,7 +268,7 @@ void schedule_own_packet(struct hard_iface *hard_iface)
...
@@ -266,7 +268,7 @@ void schedule_own_packet(struct hard_iface *hard_iface)
/* if local hna has changed and interface is a primary interface */
/* if local hna has changed and interface is a primary interface */
if
((
atomic_read
(
&
bat_priv
->
hna_local_changed
))
&&
if
((
atomic_read
(
&
bat_priv
->
hna_local_changed
))
&&
(
hard_iface
==
bat_priv
->
primary_if
))
(
hard_iface
==
primary_if
))
rebuild_batman_packet
(
bat_priv
,
hard_iface
);
rebuild_batman_packet
(
bat_priv
,
hard_iface
);
/**
/**
...
@@ -284,7 +286,7 @@ void schedule_own_packet(struct hard_iface *hard_iface)
...
@@ -284,7 +286,7 @@ void schedule_own_packet(struct hard_iface *hard_iface)
else
else
batman_packet
->
flags
&=
~
VIS_SERVER
;
batman_packet
->
flags
&=
~
VIS_SERVER
;
if
((
hard_iface
==
bat_priv
->
primary_if
)
&&
if
((
hard_iface
==
primary_if
)
&&
(
atomic_read
(
&
bat_priv
->
gw_mode
)
==
GW_MODE_SERVER
))
(
atomic_read
(
&
bat_priv
->
gw_mode
)
==
GW_MODE_SERVER
))
batman_packet
->
gw_flags
=
batman_packet
->
gw_flags
=
(
uint8_t
)
atomic_read
(
&
bat_priv
->
gw_bandwidth
);
(
uint8_t
)
atomic_read
(
&
bat_priv
->
gw_bandwidth
);
...
@@ -299,6 +301,9 @@ void schedule_own_packet(struct hard_iface *hard_iface)
...
@@ -299,6 +301,9 @@ void schedule_own_packet(struct hard_iface *hard_iface)
hard_iface
->
packet_buff
,
hard_iface
->
packet_buff
,
hard_iface
->
packet_len
,
hard_iface
->
packet_len
,
hard_iface
,
1
,
send_time
);
hard_iface
,
1
,
send_time
);
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
}
}
void
schedule_forward_packet
(
struct
orig_node
*
orig_node
,
void
schedule_forward_packet
(
struct
orig_node
*
orig_node
,
...
@@ -393,7 +398,6 @@ static void _add_bcast_packet_to_list(struct bat_priv *bat_priv,
...
@@ -393,7 +398,6 @@ static void _add_bcast_packet_to_list(struct bat_priv *bat_priv,
send_time
);
send_time
);
}
}
#define atomic_dec_not_zero(v) atomic_add_unless((v), -1, 0)
/* add a broadcast packet to the queue and setup timers. broadcast packets
/* add a broadcast packet to the queue and setup timers. broadcast packets
* are sent multiple times to increase probability for beeing received.
* are sent multiple times to increase probability for beeing received.
*
*
...
@@ -404,6 +408,7 @@ static void _add_bcast_packet_to_list(struct bat_priv *bat_priv,
...
@@ -404,6 +408,7 @@ static void _add_bcast_packet_to_list(struct bat_priv *bat_priv,
* skb is freed. */
* skb is freed. */
int
add_bcast_packet_to_list
(
struct
bat_priv
*
bat_priv
,
struct
sk_buff
*
skb
)
int
add_bcast_packet_to_list
(
struct
bat_priv
*
bat_priv
,
struct
sk_buff
*
skb
)
{
{
struct
hard_iface
*
primary_if
=
NULL
;
struct
forw_packet
*
forw_packet
;
struct
forw_packet
*
forw_packet
;
struct
bcast_packet
*
bcast_packet
;
struct
bcast_packet
*
bcast_packet
;
...
@@ -412,7 +417,8 @@ int add_bcast_packet_to_list(struct bat_priv *bat_priv, struct sk_buff *skb)
...
@@ -412,7 +417,8 @@ int add_bcast_packet_to_list(struct bat_priv *bat_priv, struct sk_buff *skb)
goto
out
;
goto
out
;
}
}
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
out
;
goto
out
;
forw_packet
=
kmalloc
(
sizeof
(
struct
forw_packet
),
GFP_ATOMIC
);
forw_packet
=
kmalloc
(
sizeof
(
struct
forw_packet
),
GFP_ATOMIC
);
...
@@ -431,7 +437,7 @@ int add_bcast_packet_to_list(struct bat_priv *bat_priv, struct sk_buff *skb)
...
@@ -431,7 +437,7 @@ int add_bcast_packet_to_list(struct bat_priv *bat_priv, struct sk_buff *skb)
skb_reset_mac_header
(
skb
);
skb_reset_mac_header
(
skb
);
forw_packet
->
skb
=
skb
;
forw_packet
->
skb
=
skb
;
forw_packet
->
if_incoming
=
bat_priv
->
primary_if
;
forw_packet
->
if_incoming
=
primary_if
;
/* how often did we send the bcast packet ? */
/* how often did we send the bcast packet ? */
forw_packet
->
num_packets
=
0
;
forw_packet
->
num_packets
=
0
;
...
@@ -444,6 +450,8 @@ int add_bcast_packet_to_list(struct bat_priv *bat_priv, struct sk_buff *skb)
...
@@ -444,6 +450,8 @@ int add_bcast_packet_to_list(struct bat_priv *bat_priv, struct sk_buff *skb)
out_and_inc:
out_and_inc:
atomic_inc
(
&
bat_priv
->
bcast_queue_left
);
atomic_inc
(
&
bat_priv
->
bcast_queue_left
);
out:
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
NETDEV_TX_BUSY
;
return
NETDEV_TX_BUSY
;
}
}
...
...
net/batman-adv/soft-interface.c
View file @
dcfd9cdc
...
@@ -211,13 +211,24 @@ int softif_neigh_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -211,13 +211,24 @@ int softif_neigh_seq_print_text(struct seq_file *seq, void *offset)
struct
net_device
*
net_dev
=
(
struct
net_device
*
)
seq
->
private
;
struct
net_device
*
net_dev
=
(
struct
net_device
*
)
seq
->
private
;
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
softif_neigh
*
softif_neigh
;
struct
softif_neigh
*
softif_neigh
;
struct
hard_iface
*
primary_if
;
struct
hlist_node
*
node
;
struct
hlist_node
*
node
;
struct
softif_neigh
*
curr_softif_neigh
;
struct
softif_neigh
*
curr_softif_neigh
;
int
ret
=
0
;
if
(
!
bat_priv
->
primary_if
)
{
primary_if
=
primary_if_get_selected
(
bat_priv
);
return
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
if
(
!
primary_if
)
{
"please specify interfaces to enable it
\n
"
,
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
net_dev
->
name
);
"please specify interfaces to enable it
\n
"
,
net_dev
->
name
);
goto
out
;
}
if
(
primary_if
->
if_status
!=
IF_ACTIVE
)
{
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s "
"disabled - primary interface not active
\n
"
,
net_dev
->
name
);
goto
out
;
}
}
seq_printf
(
seq
,
"Softif neighbor list (%s)
\n
"
,
net_dev
->
name
);
seq_printf
(
seq
,
"Softif neighbor list (%s)
\n
"
,
net_dev
->
name
);
...
@@ -234,7 +245,10 @@ int softif_neigh_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -234,7 +245,10 @@ int softif_neigh_seq_print_text(struct seq_file *seq, void *offset)
if
(
curr_softif_neigh
)
if
(
curr_softif_neigh
)
softif_neigh_free_ref
(
curr_softif_neigh
);
softif_neigh_free_ref
(
curr_softif_neigh
);
return
0
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
static
void
softif_batman_recv
(
struct
sk_buff
*
skb
,
struct
net_device
*
dev
,
static
void
softif_batman_recv
(
struct
sk_buff
*
skb
,
struct
net_device
*
dev
,
...
@@ -243,7 +257,8 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
...
@@ -243,7 +257,8 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
struct
bat_priv
*
bat_priv
=
netdev_priv
(
dev
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
dev
);
struct
ethhdr
*
ethhdr
=
(
struct
ethhdr
*
)
skb
->
data
;
struct
ethhdr
*
ethhdr
=
(
struct
ethhdr
*
)
skb
->
data
;
struct
batman_packet
*
batman_packet
;
struct
batman_packet
*
batman_packet
;
struct
softif_neigh
*
softif_neigh
;
struct
softif_neigh
*
softif_neigh
=
NULL
;
struct
hard_iface
*
primary_if
=
NULL
;
struct
softif_neigh
*
curr_softif_neigh
=
NULL
;
struct
softif_neigh
*
curr_softif_neigh
=
NULL
;
if
(
ntohs
(
ethhdr
->
h_proto
)
==
ETH_P_8021Q
)
if
(
ntohs
(
ethhdr
->
h_proto
)
==
ETH_P_8021Q
)
...
@@ -253,28 +268,34 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
...
@@ -253,28 +268,34 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
batman_packet
=
(
struct
batman_packet
*
)(
skb
->
data
+
ETH_HLEN
);
batman_packet
=
(
struct
batman_packet
*
)(
skb
->
data
+
ETH_HLEN
);
if
(
batman_packet
->
version
!=
COMPAT_VERSION
)
if
(
batman_packet
->
version
!=
COMPAT_VERSION
)
goto
err
;
goto
out
;
if
(
batman_packet
->
packet_type
!=
BAT_PACKET
)
if
(
batman_packet
->
packet_type
!=
BAT_PACKET
)
goto
err
;
goto
out
;
if
(
!
(
batman_packet
->
flags
&
PRIMARIES_FIRST_HOP
))
if
(
!
(
batman_packet
->
flags
&
PRIMARIES_FIRST_HOP
))
goto
err
;
goto
out
;
if
(
is_my_mac
(
batman_packet
->
orig
))
if
(
is_my_mac
(
batman_packet
->
orig
))
goto
err
;
goto
out
;
softif_neigh
=
softif_neigh_get
(
bat_priv
,
batman_packet
->
orig
,
vid
);
softif_neigh
=
softif_neigh_get
(
bat_priv
,
batman_packet
->
orig
,
vid
);
if
(
!
softif_neigh
)
if
(
!
softif_neigh
)
goto
err
;
goto
out
;
curr_softif_neigh
=
softif_neigh_get_selected
(
bat_priv
);
curr_softif_neigh
=
softif_neigh_get_selected
(
bat_priv
);
if
(
!
curr_softif_neigh
)
goto
out
;
if
(
curr_softif_neigh
==
softif_neigh
)
if
(
curr_softif_neigh
==
softif_neigh
)
goto
out
;
goto
out
;
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
out
;
/* we got a neighbor but its mac is 'bigger' than ours */
/* we got a neighbor but its mac is 'bigger' than ours */
if
(
memcmp
(
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
if
(
memcmp
(
primary_if
->
net_dev
->
dev_addr
,
softif_neigh
->
addr
,
ETH_ALEN
)
<
0
)
softif_neigh
->
addr
,
ETH_ALEN
)
<
0
)
goto
out
;
goto
out
;
...
@@ -296,7 +317,7 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
...
@@ -296,7 +317,7 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
/* close own batX device and use softif_neigh as exit node */
/* close own batX device and use softif_neigh as exit node */
if
((
!
curr_softif_neigh
)
&&
if
((
!
curr_softif_neigh
)
&&
(
memcmp
(
softif_neigh
->
addr
,
(
memcmp
(
softif_neigh
->
addr
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
)
<
0
))
{
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
)
<
0
))
{
bat_dbg
(
DBG_ROUTES
,
bat_priv
,
bat_dbg
(
DBG_ROUTES
,
bat_priv
,
"Setting mesh exit point to %pM (vid: %d).
\n
"
,
"Setting mesh exit point to %pM (vid: %d).
\n
"
,
softif_neigh
->
addr
,
softif_neigh
->
vid
);
softif_neigh
->
addr
,
softif_neigh
->
vid
);
...
@@ -306,12 +327,13 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
...
@@ -306,12 +327,13 @@ static void softif_batman_recv(struct sk_buff *skb, struct net_device *dev,
}
}
out:
out:
softif_neigh_free_ref
(
softif_neigh
);
err:
kfree_skb
(
skb
);
kfree_skb
(
skb
);
if
(
softif_neigh
)
softif_neigh_free_ref
(
softif_neigh
);
if
(
curr_softif_neigh
)
if
(
curr_softif_neigh
)
softif_neigh_free_ref
(
curr_softif_neigh
);
softif_neigh_free_ref
(
curr_softif_neigh
);
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
;
return
;
}
}
...
@@ -367,6 +389,7 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
...
@@ -367,6 +389,7 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
{
{
struct
ethhdr
*
ethhdr
=
(
struct
ethhdr
*
)
skb
->
data
;
struct
ethhdr
*
ethhdr
=
(
struct
ethhdr
*
)
skb
->
data
;
struct
bat_priv
*
bat_priv
=
netdev_priv
(
soft_iface
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
soft_iface
);
struct
hard_iface
*
primary_if
=
NULL
;
struct
bcast_packet
*
bcast_packet
;
struct
bcast_packet
*
bcast_packet
;
struct
vlan_ethhdr
*
vhdr
;
struct
vlan_ethhdr
*
vhdr
;
struct
softif_neigh
*
curr_softif_neigh
=
NULL
;
struct
softif_neigh
*
curr_softif_neigh
=
NULL
;
...
@@ -416,7 +439,8 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
...
@@ -416,7 +439,8 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
/* ethernet packet should be broadcasted */
/* ethernet packet should be broadcasted */
if
(
do_bcast
)
{
if
(
do_bcast
)
{
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
dropped
;
goto
dropped
;
if
(
my_skb_head_push
(
skb
,
sizeof
(
struct
bcast_packet
))
<
0
)
if
(
my_skb_head_push
(
skb
,
sizeof
(
struct
bcast_packet
))
<
0
)
...
@@ -432,7 +456,7 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
...
@@ -432,7 +456,7 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
/* hw address of first interface is the orig mac because only
/* hw address of first interface is the orig mac because only
* this mac is known throughout the mesh */
* this mac is known throughout the mesh */
memcpy
(
bcast_packet
->
orig
,
memcpy
(
bcast_packet
->
orig
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
/* set broadcast sequence number */
/* set broadcast sequence number */
bcast_packet
->
seqno
=
bcast_packet
->
seqno
=
...
@@ -462,6 +486,8 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
...
@@ -462,6 +486,8 @@ int interface_tx(struct sk_buff *skb, struct net_device *soft_iface)
end:
end:
if
(
curr_softif_neigh
)
if
(
curr_softif_neigh
)
softif_neigh_free_ref
(
curr_softif_neigh
);
softif_neigh_free_ref
(
curr_softif_neigh
);
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
NETDEV_TX_OK
;
return
NETDEV_TX_OK
;
}
}
...
...
net/batman-adv/translation-table.c
View file @
dcfd9cdc
...
@@ -22,6 +22,7 @@
...
@@ -22,6 +22,7 @@
#include "main.h"
#include "main.h"
#include "translation-table.h"
#include "translation-table.h"
#include "soft-interface.h"
#include "soft-interface.h"
#include "hard-interface.h"
#include "hash.h"
#include "hash.h"
#include "originator.h"
#include "originator.h"
...
@@ -237,16 +238,26 @@ int hna_local_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -237,16 +238,26 @@ int hna_local_seq_print_text(struct seq_file *seq, void *offset)
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
hashtable_t
*
hash
=
bat_priv
->
hna_local_hash
;
struct
hashtable_t
*
hash
=
bat_priv
->
hna_local_hash
;
struct
hna_local_entry
*
hna_local_entry
;
struct
hna_local_entry
*
hna_local_entry
;
struct
hard_iface
*
primary_if
;
struct
hlist_node
*
node
;
struct
hlist_node
*
node
;
struct
hlist_head
*
head
;
struct
hlist_head
*
head
;
size_t
buf_size
,
pos
;
size_t
buf_size
,
pos
;
char
*
buff
;
char
*
buff
;
int
i
;
int
i
,
ret
=
0
;
if
(
!
bat_priv
->
primary_if
)
{
primary_if
=
primary_if_get_selected
(
bat_priv
);
return
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
if
(
!
primary_if
)
{
"please specify interfaces to enable it
\n
"
,
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
net_dev
->
name
);
"please specify interfaces to enable it
\n
"
,
net_dev
->
name
);
goto
out
;
}
if
(
primary_if
->
if_status
!=
IF_ACTIVE
)
{
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
"primary interface not active
\n
"
,
net_dev
->
name
);
goto
out
;
}
}
seq_printf
(
seq
,
"Locally retrieved addresses (from %s) "
seq_printf
(
seq
,
"Locally retrieved addresses (from %s) "
...
@@ -269,7 +280,8 @@ int hna_local_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -269,7 +280,8 @@ int hna_local_seq_print_text(struct seq_file *seq, void *offset)
buff
=
kmalloc
(
buf_size
,
GFP_ATOMIC
);
buff
=
kmalloc
(
buf_size
,
GFP_ATOMIC
);
if
(
!
buff
)
{
if
(
!
buff
)
{
spin_unlock_bh
(
&
bat_priv
->
hna_lhash_lock
);
spin_unlock_bh
(
&
bat_priv
->
hna_lhash_lock
);
return
-
ENOMEM
;
ret
=
-
ENOMEM
;
goto
out
;
}
}
buff
[
0
]
=
'\0'
;
buff
[
0
]
=
'\0'
;
...
@@ -291,7 +303,10 @@ int hna_local_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -291,7 +303,10 @@ int hna_local_seq_print_text(struct seq_file *seq, void *offset)
seq_printf
(
seq
,
"%s"
,
buff
);
seq_printf
(
seq
,
"%s"
,
buff
);
kfree
(
buff
);
kfree
(
buff
);
return
0
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
static
void
_hna_local_del
(
struct
hlist_node
*
node
,
void
*
arg
)
static
void
_hna_local_del
(
struct
hlist_node
*
node
,
void
*
arg
)
...
@@ -468,16 +483,26 @@ int hna_global_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -468,16 +483,26 @@ int hna_global_seq_print_text(struct seq_file *seq, void *offset)
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
bat_priv
*
bat_priv
=
netdev_priv
(
net_dev
);
struct
hashtable_t
*
hash
=
bat_priv
->
hna_global_hash
;
struct
hashtable_t
*
hash
=
bat_priv
->
hna_global_hash
;
struct
hna_global_entry
*
hna_global_entry
;
struct
hna_global_entry
*
hna_global_entry
;
struct
hard_iface
*
primary_if
;
struct
hlist_node
*
node
;
struct
hlist_node
*
node
;
struct
hlist_head
*
head
;
struct
hlist_head
*
head
;
size_t
buf_size
,
pos
;
size_t
buf_size
,
pos
;
char
*
buff
;
char
*
buff
;
int
i
;
int
i
,
ret
=
0
;
if
(
!
bat_priv
->
primary_if
)
{
primary_if
=
primary_if_get_selected
(
bat_priv
);
return
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
if
(
!
primary_if
)
{
"please specify interfaces to enable it
\n
"
,
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - please "
net_dev
->
name
);
"specify interfaces to enable it
\n
"
,
net_dev
->
name
);
goto
out
;
}
if
(
primary_if
->
if_status
!=
IF_ACTIVE
)
{
ret
=
seq_printf
(
seq
,
"BATMAN mesh %s disabled - "
"primary interface not active
\n
"
,
net_dev
->
name
);
goto
out
;
}
}
seq_printf
(
seq
,
"Globally announced HNAs received via the mesh %s
\n
"
,
seq_printf
(
seq
,
"Globally announced HNAs received via the mesh %s
\n
"
,
...
@@ -499,7 +524,8 @@ int hna_global_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -499,7 +524,8 @@ int hna_global_seq_print_text(struct seq_file *seq, void *offset)
buff
=
kmalloc
(
buf_size
,
GFP_ATOMIC
);
buff
=
kmalloc
(
buf_size
,
GFP_ATOMIC
);
if
(
!
buff
)
{
if
(
!
buff
)
{
spin_unlock_bh
(
&
bat_priv
->
hna_ghash_lock
);
spin_unlock_bh
(
&
bat_priv
->
hna_ghash_lock
);
return
-
ENOMEM
;
ret
=
-
ENOMEM
;
goto
out
;
}
}
buff
[
0
]
=
'\0'
;
buff
[
0
]
=
'\0'
;
pos
=
0
;
pos
=
0
;
...
@@ -522,7 +548,10 @@ int hna_global_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -522,7 +548,10 @@ int hna_global_seq_print_text(struct seq_file *seq, void *offset)
seq_printf
(
seq
,
"%s"
,
buff
);
seq_printf
(
seq
,
"%s"
,
buff
);
kfree
(
buff
);
kfree
(
buff
);
return
0
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
static
void
_hna_global_del_orig
(
struct
bat_priv
*
bat_priv
,
static
void
_hna_global_del_orig
(
struct
bat_priv
*
bat_priv
,
...
...
net/batman-adv/types.h
View file @
dcfd9cdc
...
@@ -149,7 +149,6 @@ struct bat_priv {
...
@@ -149,7 +149,6 @@ struct bat_priv {
struct
hlist_head
softif_neigh_list
;
struct
hlist_head
softif_neigh_list
;
struct
softif_neigh
__rcu
*
softif_neigh
;
struct
softif_neigh
__rcu
*
softif_neigh
;
struct
debug_log
*
debug_log
;
struct
debug_log
*
debug_log
;
struct
hard_iface
*
primary_if
;
struct
kobject
*
mesh_obj
;
struct
kobject
*
mesh_obj
;
struct
dentry
*
debug_dir
;
struct
dentry
*
debug_dir
;
struct
hlist_head
forw_bat_list
;
struct
hlist_head
forw_bat_list
;
...
@@ -174,6 +173,7 @@ struct bat_priv {
...
@@ -174,6 +173,7 @@ struct bat_priv {
struct
delayed_work
orig_work
;
struct
delayed_work
orig_work
;
struct
delayed_work
vis_work
;
struct
delayed_work
vis_work
;
struct
gw_node
__rcu
*
curr_gw
;
/* rcu protected pointer */
struct
gw_node
__rcu
*
curr_gw
;
/* rcu protected pointer */
struct
hard_iface
__rcu
*
primary_if
;
/* rcu protected pointer */
struct
vis_info
*
my_vis_info
;
struct
vis_info
*
my_vis_info
;
};
};
...
...
net/batman-adv/unicast.c
View file @
dcfd9cdc
...
@@ -221,15 +221,17 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
...
@@ -221,15 +221,17 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
struct
hard_iface
*
hard_iface
,
uint8_t
dstaddr
[])
struct
hard_iface
*
hard_iface
,
uint8_t
dstaddr
[])
{
{
struct
unicast_packet
tmp_uc
,
*
unicast_packet
;
struct
unicast_packet
tmp_uc
,
*
unicast_packet
;
struct
hard_iface
*
primary_if
;
struct
sk_buff
*
frag_skb
;
struct
sk_buff
*
frag_skb
;
struct
unicast_frag_packet
*
frag1
,
*
frag2
;
struct
unicast_frag_packet
*
frag1
,
*
frag2
;
int
uc_hdr_len
=
sizeof
(
struct
unicast_packet
);
int
uc_hdr_len
=
sizeof
(
struct
unicast_packet
);
int
ucf_hdr_len
=
sizeof
(
struct
unicast_frag_packet
);
int
ucf_hdr_len
=
sizeof
(
struct
unicast_frag_packet
);
int
data_len
=
skb
->
len
-
uc_hdr_len
;
int
data_len
=
skb
->
len
-
uc_hdr_len
;
int
large_tail
=
0
;
int
large_tail
=
0
,
ret
=
NET_RX_DROP
;
uint16_t
seqno
;
uint16_t
seqno
;
if
(
!
bat_priv
->
primary_if
)
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
dropped
;
goto
dropped
;
frag_skb
=
dev_alloc_skb
(
data_len
-
(
data_len
/
2
)
+
ucf_hdr_len
);
frag_skb
=
dev_alloc_skb
(
data_len
-
(
data_len
/
2
)
+
ucf_hdr_len
);
...
@@ -254,7 +256,7 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
...
@@ -254,7 +256,7 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
frag1
->
version
=
COMPAT_VERSION
;
frag1
->
version
=
COMPAT_VERSION
;
frag1
->
packet_type
=
BAT_UNICAST_FRAG
;
frag1
->
packet_type
=
BAT_UNICAST_FRAG
;
memcpy
(
frag1
->
orig
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
memcpy
(
frag1
->
orig
,
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
memcpy
(
frag2
,
frag1
,
sizeof
(
struct
unicast_frag_packet
));
memcpy
(
frag2
,
frag1
,
sizeof
(
struct
unicast_frag_packet
));
if
(
data_len
&
1
)
if
(
data_len
&
1
)
...
@@ -269,13 +271,17 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
...
@@ -269,13 +271,17 @@ int frag_send_skb(struct sk_buff *skb, struct bat_priv *bat_priv,
send_skb_packet
(
skb
,
hard_iface
,
dstaddr
);
send_skb_packet
(
skb
,
hard_iface
,
dstaddr
);
send_skb_packet
(
frag_skb
,
hard_iface
,
dstaddr
);
send_skb_packet
(
frag_skb
,
hard_iface
,
dstaddr
);
return
NET_RX_SUCCESS
;
ret
=
NET_RX_SUCCESS
;
goto
out
;
drop_frag:
drop_frag:
kfree_skb
(
frag_skb
);
kfree_skb
(
frag_skb
);
dropped:
dropped:
kfree_skb
(
skb
);
kfree_skb
(
skb
);
return
NET_RX_DROP
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
int
unicast_send_skb
(
struct
sk_buff
*
skb
,
struct
bat_priv
*
bat_priv
)
int
unicast_send_skb
(
struct
sk_buff
*
skb
,
struct
bat_priv
*
bat_priv
)
...
...
net/batman-adv/vis.c
View file @
dcfd9cdc
...
@@ -204,6 +204,7 @@ static ssize_t vis_data_read_entry(char *buff, struct vis_info_entry *entry,
...
@@ -204,6 +204,7 @@ static ssize_t vis_data_read_entry(char *buff, struct vis_info_entry *entry,
int
vis_seq_print_text
(
struct
seq_file
*
seq
,
void
*
offset
)
int
vis_seq_print_text
(
struct
seq_file
*
seq
,
void
*
offset
)
{
{
struct
hard_iface
*
primary_if
;
struct
hlist_node
*
node
;
struct
hlist_node
*
node
;
struct
hlist_head
*
head
;
struct
hlist_head
*
head
;
struct
vis_info
*
info
;
struct
vis_info
*
info
;
...
@@ -215,15 +216,18 @@ int vis_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -215,15 +216,18 @@ int vis_seq_print_text(struct seq_file *seq, void *offset)
HLIST_HEAD
(
vis_if_list
);
HLIST_HEAD
(
vis_if_list
);
struct
if_list_entry
*
entry
;
struct
if_list_entry
*
entry
;
struct
hlist_node
*
pos
,
*
n
;
struct
hlist_node
*
pos
,
*
n
;
int
i
,
j
;
int
i
,
j
,
ret
=
0
;
int
vis_server
=
atomic_read
(
&
bat_priv
->
vis_mode
);
int
vis_server
=
atomic_read
(
&
bat_priv
->
vis_mode
);
size_t
buff_pos
,
buf_size
;
size_t
buff_pos
,
buf_size
;
char
*
buff
;
char
*
buff
;
int
compare
;
int
compare
;
if
((
!
bat_priv
->
primary_if
)
||
primary_if
=
primary_if_get_selected
(
bat_priv
);
(
vis_server
==
VIS_TYPE_CLIENT_UPDATE
))
if
(
!
primary_if
)
return
0
;
goto
out
;
if
(
vis_server
==
VIS_TYPE_CLIENT_UPDATE
)
goto
out
;
buf_size
=
1
;
buf_size
=
1
;
/* Estimate length */
/* Estimate length */
...
@@ -270,7 +274,8 @@ int vis_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -270,7 +274,8 @@ int vis_seq_print_text(struct seq_file *seq, void *offset)
buff
=
kmalloc
(
buf_size
,
GFP_ATOMIC
);
buff
=
kmalloc
(
buf_size
,
GFP_ATOMIC
);
if
(
!
buff
)
{
if
(
!
buff
)
{
spin_unlock_bh
(
&
bat_priv
->
vis_hash_lock
);
spin_unlock_bh
(
&
bat_priv
->
vis_hash_lock
);
return
-
ENOMEM
;
ret
=
-
ENOMEM
;
goto
out
;
}
}
buff
[
0
]
=
'\0'
;
buff
[
0
]
=
'\0'
;
buff_pos
=
0
;
buff_pos
=
0
;
...
@@ -328,7 +333,10 @@ int vis_seq_print_text(struct seq_file *seq, void *offset)
...
@@ -328,7 +333,10 @@ int vis_seq_print_text(struct seq_file *seq, void *offset)
seq_printf
(
seq
,
"%s"
,
buff
);
seq_printf
(
seq
,
"%s"
,
buff
);
kfree
(
buff
);
kfree
(
buff
);
return
0
;
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
return
ret
;
}
}
/* add the info packet to the send list, if it was not
/* add the info packet to the send list, if it was not
...
@@ -815,16 +823,20 @@ static void unicast_vis_packet(struct bat_priv *bat_priv,
...
@@ -815,16 +823,20 @@ static void unicast_vis_packet(struct bat_priv *bat_priv,
/* only send one vis packet. called from send_vis_packets() */
/* only send one vis packet. called from send_vis_packets() */
static
void
send_vis_packet
(
struct
bat_priv
*
bat_priv
,
struct
vis_info
*
info
)
static
void
send_vis_packet
(
struct
bat_priv
*
bat_priv
,
struct
vis_info
*
info
)
{
{
struct
hard_iface
*
primary_if
;
struct
vis_packet
*
packet
;
struct
vis_packet
*
packet
;
primary_if
=
primary_if_get_selected
(
bat_priv
);
if
(
!
primary_if
)
goto
out
;
packet
=
(
struct
vis_packet
*
)
info
->
skb_packet
->
data
;
packet
=
(
struct
vis_packet
*
)
info
->
skb_packet
->
data
;
if
(
packet
->
ttl
<
2
)
{
if
(
packet
->
ttl
<
2
)
{
pr_debug
(
"Error - can't send vis packet: ttl exceeded
\n
"
);
pr_debug
(
"Error - can't send vis packet: ttl exceeded
\n
"
);
return
;
goto
out
;
}
}
memcpy
(
packet
->
sender_orig
,
bat_priv
->
primary_if
->
net_dev
->
dev_addr
,
memcpy
(
packet
->
sender_orig
,
primary_if
->
net_dev
->
dev_addr
,
ETH_ALEN
);
ETH_ALEN
);
packet
->
ttl
--
;
packet
->
ttl
--
;
if
(
is_broadcast_ether_addr
(
packet
->
target_orig
))
if
(
is_broadcast_ether_addr
(
packet
->
target_orig
))
...
@@ -832,6 +844,10 @@ static void send_vis_packet(struct bat_priv *bat_priv, struct vis_info *info)
...
@@ -832,6 +844,10 @@ static void send_vis_packet(struct bat_priv *bat_priv, struct vis_info *info)
else
else
unicast_vis_packet
(
bat_priv
,
info
);
unicast_vis_packet
(
bat_priv
,
info
);
packet
->
ttl
++
;
/* restore TTL */
packet
->
ttl
++
;
/* restore TTL */
out:
if
(
primary_if
)
hardif_free_ref
(
primary_if
);
}
}
/* called from timer; send (and maybe generate) vis packet. */
/* called from timer; send (and maybe generate) vis packet. */
...
@@ -858,8 +874,7 @@ static void send_vis_packets(struct work_struct *work)
...
@@ -858,8 +874,7 @@ static void send_vis_packets(struct work_struct *work)
kref_get
(
&
info
->
refcount
);
kref_get
(
&
info
->
refcount
);
spin_unlock_bh
(
&
bat_priv
->
vis_hash_lock
);
spin_unlock_bh
(
&
bat_priv
->
vis_hash_lock
);
if
(
bat_priv
->
primary_if
)
send_vis_packet
(
bat_priv
,
info
);
send_vis_packet
(
bat_priv
,
info
);
spin_lock_bh
(
&
bat_priv
->
vis_hash_lock
);
spin_lock_bh
(
&
bat_priv
->
vis_hash_lock
);
send_list_del
(
info
);
send_list_del
(
info
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment