aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--net/bluetooth/mgmt.c78
1 files changed, 43 insertions, 35 deletions
diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c
index 5e18d5a451f4..497928d2b257 100644
--- a/net/bluetooth/mgmt.c
+++ b/net/bluetooth/mgmt.c
@@ -435,11 +435,51 @@ static u32 get_current_settings(struct hci_dev *hdev)
435 435
436#define PNP_INFO_SVCLASS_ID 0x1200 436#define PNP_INFO_SVCLASS_ID 0x1200
437 437
438static u8 *create_uuid16_list(struct hci_dev *hdev, u8 *data, ptrdiff_t len)
439{
440 u8 *ptr = data, *uuids_start = NULL;
441 struct bt_uuid *uuid;
442
443 if (len < 4)
444 return ptr;
445
446 list_for_each_entry(uuid, &hdev->uuids, list) {
447 u16 uuid16;
448
449 if (uuid->size != 16)
450 continue;
451
452 uuid16 = get_unaligned_le16(&uuid->uuid[12]);
453 if (uuid16 < 0x1100)
454 continue;
455
456 if (uuid16 == PNP_INFO_SVCLASS_ID)
457 continue;
458
459 if (!uuids_start) {
460 uuids_start = ptr;
461 uuids_start[0] = 1;
462 uuids_start[1] = EIR_UUID16_ALL;
463 ptr += 2;
464 }
465
466 /* Stop if not enough space to put next UUID */
467 if ((ptr - data) + sizeof(u16) > len) {
468 uuids_start[1] = EIR_UUID16_SOME;
469 break;
470 }
471
472 *ptr++ = (uuid16 & 0x00ff);
473 *ptr++ = (uuid16 & 0xff00) >> 8;
474 uuids_start[0] += sizeof(uuid16);
475 }
476
477 return ptr;
478}
479
438static void create_eir(struct hci_dev *hdev, u8 *data) 480static void create_eir(struct hci_dev *hdev, u8 *data)
439{ 481{
440 u8 *ptr = data; 482 u8 *ptr = data;
441 u8 *uuids_start;
442 struct bt_uuid *uuid;
443 size_t name_len; 483 size_t name_len;
444 484
445 name_len = strlen(hdev->dev_name); 485 name_len = strlen(hdev->dev_name);
@@ -480,39 +520,7 @@ static void create_eir(struct hci_dev *hdev, u8 *data)
480 ptr += 10; 520 ptr += 10;
481 } 521 }
482 522
483 uuids_start = NULL; 523 ptr = create_uuid16_list(hdev, ptr, HCI_MAX_EIR_LENGTH - (ptr - data));
484
485 /* Group all UUID16 types */
486 list_for_each_entry(uuid, &hdev->uuids, list) {
487 u16 uuid16;
488
489 if (uuid->size != 16)
490 continue;
491
492 uuid16 = get_unaligned_le16(&uuid->uuid[12]);
493 if (uuid16 < 0x1100)
494 continue;
495
496 if (uuid16 == PNP_INFO_SVCLASS_ID)
497 continue;
498
499 if (!uuids_start) {
500 uuids_start = ptr;
501 uuids_start[0] = 1;
502 uuids_start[1] = EIR_UUID16_ALL;
503 ptr += 2;
504 }
505
506 /* Stop if not enough space to put next UUID */
507 if ((ptr - data) + 2 + sizeof(u16) > HCI_MAX_EIR_LENGTH) {
508 uuids_start[1] = EIR_UUID16_SOME;
509 break;
510 }
511
512 *ptr++ = (uuid16 & 0x00ff);
513 *ptr++ = (uuid16 & 0xff00) >> 8;
514 uuids_start[0] += sizeof(uuid16);
515 }
516} 524}
517 525
518static int update_eir(struct hci_dev *hdev) 526static int update_eir(struct hci_dev *hdev)