Commit 3446b9d5 authored by Arnaldo Carvalho de Melo's avatar Arnaldo Carvalho de Melo Committed by David S. Miller

llc: Fix double accounting of received packets

llc_sap_rcv was being preceded by skb_set_owner_r, then calling
llc_state_process that calls sock_queue_rcv_skb, that in turn calls
skb_set_owner_r again making the space allowed to be used by the socket to be
leaked, making the socket to get stuck.

Fix it by setting skb->sk at llc_sap_rcv and leave the accounting to be done
only at sock_queue_rcv_skb.
Reported-by: default avatarDmitry Petukhov <dmgenp@gmail.com>
Tested-by: default avatarDmitry Petukhov <dmgenp@gmail.com>
Signed-off-by: default avatarArnaldo Carvalho de Melo <acme@redhat.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 12293bf9
...@@ -286,12 +286,14 @@ void llc_build_and_send_xid_pkt(struct llc_sap *sap, struct sk_buff *skb, ...@@ -286,12 +286,14 @@ void llc_build_and_send_xid_pkt(struct llc_sap *sap, struct sk_buff *skb,
* *
* Sends received pdus to the sap state machine. * Sends received pdus to the sap state machine.
*/ */
static void llc_sap_rcv(struct llc_sap *sap, struct sk_buff *skb) static void llc_sap_rcv(struct llc_sap *sap, struct sk_buff *skb,
struct sock *sk)
{ {
struct llc_sap_state_ev *ev = llc_sap_ev(skb); struct llc_sap_state_ev *ev = llc_sap_ev(skb);
ev->type = LLC_SAP_EV_TYPE_PDU; ev->type = LLC_SAP_EV_TYPE_PDU;
ev->reason = 0; ev->reason = 0;
skb->sk = sk;
llc_sap_state_process(sap, skb); llc_sap_state_process(sap, skb);
} }
...@@ -360,8 +362,7 @@ static void llc_sap_mcast(struct llc_sap *sap, ...@@ -360,8 +362,7 @@ static void llc_sap_mcast(struct llc_sap *sap,
break; break;
sock_hold(sk); sock_hold(sk);
skb_set_owner_r(skb1, sk); llc_sap_rcv(sap, skb1, sk);
llc_sap_rcv(sap, skb1);
sock_put(sk); sock_put(sk);
} }
read_unlock_bh(&sap->sk_list.lock); read_unlock_bh(&sap->sk_list.lock);
...@@ -381,8 +382,7 @@ void llc_sap_handler(struct llc_sap *sap, struct sk_buff *skb) ...@@ -381,8 +382,7 @@ void llc_sap_handler(struct llc_sap *sap, struct sk_buff *skb)
} else { } else {
struct sock *sk = llc_lookup_dgram(sap, &laddr); struct sock *sk = llc_lookup_dgram(sap, &laddr);
if (sk) { if (sk) {
skb_set_owner_r(skb, sk); llc_sap_rcv(sap, skb, sk);
llc_sap_rcv(sap, skb);
sock_put(sk); sock_put(sk);
} else } else
kfree_skb(skb); kfree_skb(skb);
......
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