Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 321985
b: refs/heads/master
c: aadf31d
h: refs/heads/master
i:
  321983: a97139e
v: v3
  • Loading branch information
Ben Hutchings authored and David S. Miller committed Aug 14, 2012
1 parent 7167968 commit 8b98ad2
Show file tree
Hide file tree
Showing 3 changed files with 19 additions and 6 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: f4f8720febf0d785a054fc09bde5e3ad09728a58
refs/heads/master: aadf31de16a7b2878af00a02e6557df84efa784b
21 changes: 17 additions & 4 deletions trunk/net/llc/llc_input.c
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ static void (*llc_type_handlers[2])(struct llc_sap *sap,
void llc_add_pack(int type, void (*handler)(struct llc_sap *sap,
struct sk_buff *skb))
{
smp_wmb(); /* ensure initialisation is complete before it's called */
if (type == LLC_DEST_SAP || type == LLC_DEST_CONN)
llc_type_handlers[type - 1] = handler;
}
Expand All @@ -50,11 +51,19 @@ void llc_remove_pack(int type)
{
if (type == LLC_DEST_SAP || type == LLC_DEST_CONN)
llc_type_handlers[type - 1] = NULL;
synchronize_net();
}

void llc_set_station_handler(void (*handler)(struct sk_buff *skb))
{
/* Ensure initialisation is complete before it's called */
if (handler)
smp_wmb();

llc_station_handler = handler;

if (!handler)
synchronize_net();
}

/**
Expand Down Expand Up @@ -150,6 +159,8 @@ int llc_rcv(struct sk_buff *skb, struct net_device *dev,
int dest;
int (*rcv)(struct sk_buff *, struct net_device *,
struct packet_type *, struct net_device *);
void (*sta_handler)(struct sk_buff *skb);
void (*sap_handler)(struct llc_sap *sap, struct sk_buff *skb);

if (!net_eq(dev_net(dev), &init_net))
goto drop;
Expand Down Expand Up @@ -182,7 +193,8 @@ int llc_rcv(struct sk_buff *skb, struct net_device *dev,
*/
rcv = rcu_dereference(sap->rcv_func);
dest = llc_pdu_type(skb);
if (unlikely(!dest || !llc_type_handlers[dest - 1])) {
sap_handler = dest ? ACCESS_ONCE(llc_type_handlers[dest - 1]) : NULL;
if (unlikely(!sap_handler)) {
if (rcv)
rcv(skb, dev, pt, orig_dev);
else
Expand All @@ -193,7 +205,7 @@ int llc_rcv(struct sk_buff *skb, struct net_device *dev,
if (cskb)
rcv(cskb, dev, pt, orig_dev);
}
llc_type_handlers[dest - 1](sap, skb);
sap_handler(sap, skb);
}
llc_sap_put(sap);
out:
Expand All @@ -202,9 +214,10 @@ int llc_rcv(struct sk_buff *skb, struct net_device *dev,
kfree_skb(skb);
goto out;
handle_station:
if (!llc_station_handler)
sta_handler = ACCESS_ONCE(llc_station_handler);
if (!sta_handler)
goto drop;
llc_station_handler(skb);
sta_handler(skb);
goto out;
}

Expand Down
2 changes: 1 addition & 1 deletion trunk/net/llc/llc_station.c
Original file line number Diff line number Diff line change
Expand Up @@ -696,9 +696,9 @@ void __init llc_station_init(void)
(unsigned long)&llc_main_station);
llc_main_station.ack_timer.expires = jiffies +
sysctl_llc_station_ack_timeout;
llc_set_station_handler(llc_station_rcv);
llc_main_station.maximum_retry = 1;
llc_main_station.state = LLC_STATION_STATE_UP;
llc_set_station_handler(llc_station_rcv);
}

void llc_station_exit(void)
Expand Down

0 comments on commit 8b98ad2

Please sign in to comment.