Skip to content

Commit

Permalink
Bluetooth: Add wait_queue to wait ack of all sent packets
Browse files Browse the repository at this point in the history
To guarantee that all packets we sent were received we need to wait for
theirs ack before shutdown the socket.

Signed-off-by: Gustavo F. Padovan <padovan@profusion.mobi>
Reviewed-by: João Paulo Rechi Vita <jprvita@profusion.mobi>
Signed-off-by: Marcel Holtmann <marcel@holtmann.org>
  • Loading branch information
Gustavo F. Padovan authored and Marcel Holtmann committed May 10, 2010
1 parent 1890d36 commit 6161c03
Showing 1 changed file with 34 additions and 0 deletions.
34 changes: 34 additions & 0 deletions net/bluetooth/l2cap.c
Original file line number Diff line number Diff line change
Expand Up @@ -1242,6 +1242,37 @@ static int l2cap_sock_getname(struct socket *sock, struct sockaddr *addr, int *l
return 0;
}

static int __l2cap_wait_ack(struct sock *sk)
{
DECLARE_WAITQUEUE(wait, current);
int err = 0;
int timeo = HZ/5;

add_wait_queue(sk->sk_sleep, &wait);
while ((l2cap_pi(sk)->unacked_frames > 0 && l2cap_pi(sk)->conn)) {
set_current_state(TASK_INTERRUPTIBLE);

if (!timeo)
timeo = HZ/5;

if (signal_pending(current)) {
err = sock_intr_errno(timeo);
break;
}

release_sock(sk);
timeo = schedule_timeout(timeo);
lock_sock(sk);

err = sock_error(sk);
if (err)
break;
}
set_current_state(TASK_RUNNING);
remove_wait_queue(sk->sk_sleep, &wait);
return err;
}

static void l2cap_monitor_timeout(unsigned long arg)
{
struct sock *sk = (void *) arg;
Expand Down Expand Up @@ -2059,6 +2090,9 @@ static int l2cap_sock_shutdown(struct socket *sock, int how)

lock_sock(sk);
if (!sk->sk_shutdown) {
if (l2cap_pi(sk)->mode == L2CAP_MODE_ERTM)
err = __l2cap_wait_ack(sk);

sk->sk_shutdown = SHUTDOWN_MASK;
l2cap_sock_clear_timer(sk);
__l2cap_sock_close(sk, 0);
Expand Down

0 comments on commit 6161c03

Please sign in to comment.