Merge branch 'master' of master.kernel.org:/pub/scm/linux/kernel/git/padovan/bluetoot...
authorJohn W. Linville <linville@tuxdriver.com>
Tue, 5 Jul 2011 18:33:09 +0000 (14:33 -0400)
committerJohn W. Linville <linville@tuxdriver.com>
Tue, 5 Jul 2011 18:33:09 +0000 (14:33 -0400)
net/bluetooth/hci_conn.c
net/bluetooth/hidp/core.c
net/bluetooth/hidp/hidp.h
net/bluetooth/l2cap_core.c

index d3a05b9ade7a487fe7c84680883cb3ceca7621a1..bcd158f40bb9e4d7a7fa5c167c1281779d60847d 100644 (file)
@@ -393,6 +393,9 @@ int hci_conn_del(struct hci_conn *conn)
 
        hci_dev_put(hdev);
 
+       if (conn->handle == 0)
+               kfree(conn);
+
        return 0;
 }
 
index c405a954a603341b52b51a98592ecccd618398e9..43b4c2deb7cc05bdc875e3f7b23a999468f5c1a4 100644 (file)
@@ -464,7 +464,8 @@ static void hidp_idle_timeout(unsigned long arg)
 {
        struct hidp_session *session = (struct hidp_session *) arg;
 
-       kthread_stop(session->task);
+       atomic_inc(&session->terminate);
+       wake_up_process(session->task);
 }
 
 static void hidp_set_timer(struct hidp_session *session)
@@ -535,7 +536,8 @@ static void hidp_process_hid_control(struct hidp_session *session,
                skb_queue_purge(&session->ctrl_transmit);
                skb_queue_purge(&session->intr_transmit);
 
-               kthread_stop(session->task);
+               atomic_inc(&session->terminate);
+               wake_up_process(current);
        }
 }
 
@@ -706,9 +708,8 @@ static int hidp_session(void *arg)
        add_wait_queue(sk_sleep(intr_sk), &intr_wait);
        session->waiting_for_startup = 0;
        wake_up_interruptible(&session->startup_queue);
-       while (!kthread_should_stop()) {
-               set_current_state(TASK_INTERRUPTIBLE);
-
+       set_current_state(TASK_INTERRUPTIBLE);
+       while (!atomic_read(&session->terminate)) {
                if (ctrl_sk->sk_state != BT_CONNECTED ||
                                intr_sk->sk_state != BT_CONNECTED)
                        break;
@@ -726,6 +727,7 @@ static int hidp_session(void *arg)
                hidp_process_transmit(session);
 
                schedule();
+               set_current_state(TASK_INTERRUPTIBLE);
        }
        set_current_state(TASK_RUNNING);
        remove_wait_queue(sk_sleep(intr_sk), &intr_wait);
@@ -1060,7 +1062,8 @@ int hidp_add_connection(struct hidp_connadd_req *req, struct socket *ctrl_sock,
 err_add_device:
        hid_destroy_device(session->hid);
        session->hid = NULL;
-       kthread_stop(session->task);
+       atomic_inc(&session->terminate);
+       wake_up_process(session->task);
 
 unlink:
        hidp_del_timer(session);
@@ -1111,7 +1114,8 @@ int hidp_del_connection(struct hidp_conndel_req *req)
                        skb_queue_purge(&session->ctrl_transmit);
                        skb_queue_purge(&session->intr_transmit);
 
-                       kthread_stop(session->task);
+                       atomic_inc(&session->terminate);
+                       wake_up_process(session->task);
                }
        } else
                err = -ENOENT;
index 19e95004b28654fb14bb009d40efeec81b56eca1..af1bcc823f26d8196587be3624b8f091f29f1d8f 100644 (file)
@@ -142,6 +142,7 @@ struct hidp_session {
        uint ctrl_mtu;
        uint intr_mtu;
 
+       atomic_t terminate;
        struct task_struct *task;
 
        unsigned char keys[8];
index 56fdd9162da929fcacd0b31cd5e537c71a421c4b..ebff14c690786ae8e4e0766dfd51cc7e16d3e2ce 100644 (file)
@@ -2323,7 +2323,8 @@ static inline int l2cap_config_req(struct l2cap_conn *conn, struct l2cap_cmd_hdr
 
        sk = chan->sk;
 
-       if (sk->sk_state != BT_CONFIG) {
+       if ((bt_sk(sk)->defer_setup && sk->sk_state != BT_CONNECT2) ||
+                (!bt_sk(sk)->defer_setup && sk->sk_state != BT_CONFIG)) {
                struct l2cap_cmd_rej rej;
 
                rej.reason = cpu_to_le16(0x0002);
@@ -2334,7 +2335,7 @@ static inline int l2cap_config_req(struct l2cap_conn *conn, struct l2cap_cmd_hdr
 
        /* Reject if config buffer is too small. */
        len = cmd_len - sizeof(*req);
-       if (chan->conf_len + len > sizeof(chan->conf_req)) {
+       if (len < 0 || chan->conf_len + len > sizeof(chan->conf_req)) {
                l2cap_send_cmd(conn, cmd->ident, L2CAP_CONF_RSP,
                                l2cap_build_conf_rsp(chan, rsp,
                                        L2CAP_CONF_REJECT, flags), rsp);
This page took 0.030929 seconds and 5 git commands to generate.