summaryrefslogtreecommitdiffstats
path: root/net/bluetooth/mgmt.c
diff options
context:
space:
mode:
authorAlfonso Acosta <fons@spotify.com>2014-10-07 08:44:11 +0000
committerMarcel Holtmann <marcel@holtmann.org>2014-10-25 07:56:24 +0200
commitfd45ada9105635a69cbaa2d142d502d402eef6fe (patch)
treef4b6d3ca91123813a9163f3764c244fe64d4b8c5 /net/bluetooth/mgmt.c
parent48ec92fa4f16c0f71e95c31490c03b6c9e0e793b (diff)
downloadop-kernel-dev-fd45ada9105635a69cbaa2d142d502d402eef6fe.zip
op-kernel-dev-fd45ada9105635a69cbaa2d142d502d402eef6fe.tar.gz
Bluetooth: Include ADV_IND report in Device Connected event
There are scenarios when autoconnecting to a device after the reception of an ADV_IND report (action 0x02), in which userland might want to examine the report's contents. For instance, the Service Data might have changed and it would be useful to know ahead of time before starting any GATT procedures. Also, the ADV_IND may contain Manufacturer Specific data which would be lost if not propagated to userland. In fact, this patch results from the need to rebond with a device lacking persistent storage which notifies about losing its LTK in ADV_IND reports. This patch appends the ADV_IND report which triggered the autoconnection to the EIR Data in the Device Connected event. Signed-off-by: Alfonso Acosta <fons@spotify.com> Signed-off-by: Johan Hedberg <johan.hedberg@intel.com>
Diffstat (limited to 'net/bluetooth/mgmt.c')
-rw-r--r--net/bluetooth/mgmt.c24
1 files changed, 18 insertions, 6 deletions
diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c
index fc275dc..10caab5 100644
--- a/net/bluetooth/mgmt.c
+++ b/net/bluetooth/mgmt.c
@@ -6183,13 +6183,25 @@ void mgmt_device_connected(struct hci_dev *hdev, struct hci_conn *conn,
ev->flags = __cpu_to_le32(flags);
- if (name_len > 0)
- eir_len = eir_append_data(ev->eir, 0, EIR_NAME_COMPLETE,
- name, name_len);
+ /* We must ensure that the EIR Data fields are ordered and
+ * unique. Keep it simple for now and avoid the problem by not
+ * adding any BR/EDR data to the LE adv.
+ */
+ if (conn->le_adv_data_len > 0) {
+ memcpy(&ev->eir[eir_len],
+ conn->le_adv_data, conn->le_adv_data_len);
+ eir_len = conn->le_adv_data_len;
+ } else {
+ if (name_len > 0)
+ eir_len = eir_append_data(ev->eir, 0, EIR_NAME_COMPLETE,
+ name, name_len);
- if (conn->dev_class && memcmp(conn->dev_class, "\0\0\0", 3) != 0)
- eir_len = eir_append_data(ev->eir, eir_len,
- EIR_CLASS_OF_DEV, conn->dev_class, 3);
+ if (conn->dev_class &&
+ memcmp(conn->dev_class, "\0\0\0", 3) != 0)
+ eir_len = eir_append_data(ev->eir, eir_len,
+ EIR_CLASS_OF_DEV,
+ conn->dev_class, 3);
+ }
ev->eir_len = cpu_to_le16(eir_len);
OpenPOWER on IntegriCloud