Commit 1d36cb47 authored by Frank Blaschka's avatar Frank Blaschka Committed by David S. Miller

qeth: l3 fix rcu splat in xmit

when use dst_get_neighbour to get neighbour, we need
rcu_read_lock to protect, since dst_get_neighbour uses
rcu_dereference.
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 1d503563
...@@ -2756,11 +2756,13 @@ int inline qeth_l3_get_cast_type(struct qeth_card *card, struct sk_buff *skb) ...@@ -2756,11 +2756,13 @@ int inline qeth_l3_get_cast_type(struct qeth_card *card, struct sk_buff *skb)
struct neighbour *n = NULL; struct neighbour *n = NULL;
struct dst_entry *dst; struct dst_entry *dst;
rcu_read_lock();
dst = skb_dst(skb); dst = skb_dst(skb);
if (dst) if (dst)
n = dst_get_neighbour(dst); n = dst_get_neighbour(dst);
if (n) { if (n) {
cast_type = n->type; cast_type = n->type;
rcu_read_unlock();
if ((cast_type == RTN_BROADCAST) || if ((cast_type == RTN_BROADCAST) ||
(cast_type == RTN_MULTICAST) || (cast_type == RTN_MULTICAST) ||
(cast_type == RTN_ANYCAST)) (cast_type == RTN_ANYCAST))
...@@ -2768,6 +2770,8 @@ int inline qeth_l3_get_cast_type(struct qeth_card *card, struct sk_buff *skb) ...@@ -2768,6 +2770,8 @@ int inline qeth_l3_get_cast_type(struct qeth_card *card, struct sk_buff *skb)
else else
return RTN_UNSPEC; return RTN_UNSPEC;
} }
rcu_read_unlock();
/* try something else */ /* try something else */
if (skb->protocol == ETH_P_IPV6) if (skb->protocol == ETH_P_IPV6)
return (skb_network_header(skb)[24] == 0xff) ? return (skb_network_header(skb)[24] == 0xff) ?
...@@ -2847,6 +2851,8 @@ static void qeth_l3_fill_header(struct qeth_card *card, struct qeth_hdr *hdr, ...@@ -2847,6 +2851,8 @@ static void qeth_l3_fill_header(struct qeth_card *card, struct qeth_hdr *hdr,
} }
hdr->hdr.l3.length = skb->len - sizeof(struct qeth_hdr); hdr->hdr.l3.length = skb->len - sizeof(struct qeth_hdr);
rcu_read_lock();
dst = skb_dst(skb); dst = skb_dst(skb);
if (dst) if (dst)
n = dst_get_neighbour(dst); n = dst_get_neighbour(dst);
...@@ -2893,6 +2899,7 @@ static void qeth_l3_fill_header(struct qeth_card *card, struct qeth_hdr *hdr, ...@@ -2893,6 +2899,7 @@ static void qeth_l3_fill_header(struct qeth_card *card, struct qeth_hdr *hdr,
QETH_CAST_UNICAST | QETH_HDR_PASSTHRU; QETH_CAST_UNICAST | QETH_HDR_PASSTHRU;
} }
} }
rcu_read_unlock();
} }
static inline void qeth_l3_hdr_csum(struct qeth_card *card, static inline void qeth_l3_hdr_csum(struct qeth_card *card,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment