]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
Bluetooth: hci_core: Fix not checking skb length on hci_acldata_packet
authorLuiz Augusto von Dentz <luiz.von.dentz@intel.com>
Tue, 8 Oct 2024 14:16:48 +0000 (10:16 -0400)
committerLuiz Augusto von Dentz <luiz.von.dentz@intel.com>
Thu, 14 Nov 2024 20:29:54 +0000 (15:29 -0500)
This fixes not checking if skb really contains an ACL header otherwise
the code may attempt to access some uninitilized/invalid memory past the
valid skb->data.

Reported-by: syzbot+6ea290ba76d8c1eb1ac2@syzkaller.appspotmail.com
Tested-by: syzbot+6ea290ba76d8c1eb1ac2@syzkaller.appspotmail.com
Closes: https://syzkaller.appspot.com/bug?extid=6ea290ba76d8c1eb1ac2
Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
net/bluetooth/hci_core.c

index 96d097b21d13f2f52cee5f998fe2174ae8b97a06..f9e1df409015952843d7bddb38c9c08e4fdcfa83 100644 (file)
@@ -3771,18 +3771,22 @@ static void hci_tx_work(struct work_struct *work)
 /* ACL data packet */
 static void hci_acldata_packet(struct hci_dev *hdev, struct sk_buff *skb)
 {
-       struct hci_acl_hdr *hdr = (void *) skb->data;
+       struct hci_acl_hdr *hdr;
        struct hci_conn *conn;
        __u16 handle, flags;
 
-       skb_pull(skb, HCI_ACL_HDR_SIZE);
+       hdr = skb_pull_data(skb, sizeof(*hdr));
+       if (!hdr) {
+               bt_dev_err(hdev, "ACL packet too small");
+               goto drop;
+       }
 
        handle = __le16_to_cpu(hdr->handle);
        flags  = hci_flags(handle);
        handle = hci_handle(handle);
 
-       BT_DBG("%s len %d handle 0x%4.4x flags 0x%4.4x", hdev->name, skb->len,
-              handle, flags);
+       bt_dev_dbg(hdev, "len %d handle 0x%4.4x flags 0x%4.4x", skb->len,
+                  handle, flags);
 
        hdev->stat.acl_rx++;
 
@@ -3803,6 +3807,7 @@ static void hci_acldata_packet(struct hci_dev *hdev, struct sk_buff *skb)
                           handle);
        }
 
+drop:
        kfree_skb(skb);
 }