]> git.karo-electronics.de Git - karo-tx-linux.git/blobdiff - net/bluetooth/hci_sock.c
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input
[karo-tx-linux.git] / net / bluetooth / hci_sock.c
index 2c245fdf319a60022328e8f3918251db526f88f8..1d65c5be7c823a282bc74a4d9691db53eb37b8d3 100644 (file)
@@ -216,11 +216,39 @@ void hci_send_to_control(struct sk_buff *skb, struct sock *skip_sk)
        read_unlock(&hci_sk_list.lock);
 }
 
+static void queue_monitor_skb(struct sk_buff *skb)
+{
+       struct sock *sk;
+
+       BT_DBG("len %d", skb->len);
+
+       read_lock(&hci_sk_list.lock);
+
+       sk_for_each(sk, &hci_sk_list.head) {
+               struct sk_buff *nskb;
+
+               if (sk->sk_state != BT_BOUND)
+                       continue;
+
+               if (hci_pi(sk)->channel != HCI_CHANNEL_MONITOR)
+                       continue;
+
+               nskb = skb_clone(skb, GFP_ATOMIC);
+               if (!nskb)
+                       continue;
+
+               if (sock_queue_rcv_skb(sk, nskb))
+                       kfree_skb(nskb);
+       }
+
+       read_unlock(&hci_sk_list.lock);
+}
+
 /* Send frame to monitor socket */
 void hci_send_to_monitor(struct hci_dev *hdev, struct sk_buff *skb)
 {
-       struct sock *sk;
        struct sk_buff *skb_copy = NULL;
+       struct hci_mon_hdr *hdr;
        __le16 opcode;
 
        if (!atomic_read(&monitor_promisc))
@@ -251,74 +279,21 @@ void hci_send_to_monitor(struct hci_dev *hdev, struct sk_buff *skb)
                return;
        }
 
-       read_lock(&hci_sk_list.lock);
-
-       sk_for_each(sk, &hci_sk_list.head) {
-               struct sk_buff *nskb;
-
-               if (sk->sk_state != BT_BOUND)
-                       continue;
-
-               if (hci_pi(sk)->channel != HCI_CHANNEL_MONITOR)
-                       continue;
-
-               if (!skb_copy) {
-                       struct hci_mon_hdr *hdr;
-
-                       /* Create a private copy with headroom */
-                       skb_copy = __pskb_copy_fclone(skb, HCI_MON_HDR_SIZE,
-                                                     GFP_ATOMIC, true);
-                       if (!skb_copy)
-                               continue;
-
-                       /* Put header before the data */
-                       hdr = (void *) skb_push(skb_copy, HCI_MON_HDR_SIZE);
-                       hdr->opcode = opcode;
-                       hdr->index = cpu_to_le16(hdev->id);
-                       hdr->len = cpu_to_le16(skb->len);
-               }
-
-               nskb = skb_clone(skb_copy, GFP_ATOMIC);
-               if (!nskb)
-                       continue;
-
-               if (sock_queue_rcv_skb(sk, nskb))
-                       kfree_skb(nskb);
-       }
+       /* Create a private copy with headroom */
+       skb_copy = __pskb_copy_fclone(skb, HCI_MON_HDR_SIZE, GFP_ATOMIC, true);
+       if (!skb_copy)
+               return;
 
-       read_unlock(&hci_sk_list.lock);
+       /* Put header before the data */
+       hdr = (void *) skb_push(skb_copy, HCI_MON_HDR_SIZE);
+       hdr->opcode = opcode;
+       hdr->index = cpu_to_le16(hdev->id);
+       hdr->len = cpu_to_le16(skb->len);
 
+       queue_monitor_skb(skb_copy);
        kfree_skb(skb_copy);
 }
 
-static void send_monitor_event(struct sk_buff *skb)
-{
-       struct sock *sk;
-
-       BT_DBG("len %d", skb->len);
-
-       read_lock(&hci_sk_list.lock);
-
-       sk_for_each(sk, &hci_sk_list.head) {
-               struct sk_buff *nskb;
-
-               if (sk->sk_state != BT_BOUND)
-                       continue;
-
-               if (hci_pi(sk)->channel != HCI_CHANNEL_MONITOR)
-                       continue;
-
-               nskb = skb_clone(skb, GFP_ATOMIC);
-               if (!nskb)
-                       continue;
-
-               if (sock_queue_rcv_skb(sk, nskb))
-                       kfree_skb(nskb);
-       }
-
-       read_unlock(&hci_sk_list.lock);
-}
-
 static struct sk_buff *create_monitor_event(struct hci_dev *hdev, int event)
 {
        struct hci_mon_hdr *hdr;
@@ -422,7 +397,7 @@ void hci_sock_dev_event(struct hci_dev *hdev, int event)
 
                skb = create_monitor_event(hdev, event);
                if (skb) {
-                       send_monitor_event(skb);
+                       queue_monitor_skb(skb);
                        kfree_skb(skb);
                }
        }
@@ -1230,6 +1205,8 @@ int __init hci_sock_init(void)
 {
        int err;
 
+       BUILD_BUG_ON(sizeof(struct sockaddr_hci) > sizeof(struct sockaddr));
+
        err = proto_register(&hci_sk_proto, 0);
        if (err < 0)
                return err;