2015-10-13 17:22:18

by Jakub Pawlowski

[permalink] [raw]
Subject: [PATCH v2 1/2] Bluetooth: fix autoconnect for pending connect attempt

When adding device to auto connect whitelist when there is pending
connect attempt, there is no need to update scan, or to add it to
pend_le_conns list.

When trying to connect to le device, it is added to pend_le_conns and
background scan is updated. There's no need to repeat this operation when
adding device to auto connect list. Only update of params->auto_connect
value is required.

If both operations try to update background scan, and are quickly queued
together when scan was disabled, second operation might improperly try to
start, instead of restarting scan. This means that adding device to
connect whitelist would report failure, even though it succeeded.

In order to reproduce this bug type in bluetoothctl:
connect D9:00:00:00:00
disconnect D9:00:00:00:00
connect D9:00:00:00:00

and observe bluetoothd logs (error happens during second connect attempt):
src/device.c:device_connect_le() Connection attempt to: D0:5F:B8:52:22:9F
Failed to add device D0:5F:B8:52:22:9F (1): Busy (0x0a)

Signed-off-by: Jakub Pawlowski <[email protected]>
---
net/bluetooth/mgmt.c | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c
index 9f9a70f..b42613a 100644
--- a/net/bluetooth/mgmt.c
+++ b/net/bluetooth/mgmt.c
@@ -6124,7 +6124,11 @@ static int hci_conn_params_set(struct hci_request *req, bdaddr_t *addr,
case HCI_AUTO_CONN_ALWAYS:
if (!is_connected(hdev, addr, addr_type)) {
list_add(&params->action, &hdev->pend_le_conns);
- __hci_update_background_scan(req);
+ /* If we are connecting to device using random address,
+ * we were already added to pend_le_conns and scanning.
+ */
+ if (params->auto_connect != HCI_AUTO_CONN_EXPLICIT)
+ __hci_update_background_scan(req);
}
break;
}
--
2.6.0.rc2.230.g3dd15c0



2015-10-13 17:22:19

by Jakub Pawlowski

[permalink] [raw]
Subject: [PATCH v2 2/2] Bluetooth: fix double scan disable

hci_connect_le_scan_cleanup is conditionally executing
hci_conn_params_del, that is calling hci_update_background_scan. Make the
other case also update scan, and remove reduntand call from
hci_connect_le_scan_remove.

Signed-off-by: Jakub Pawlowski <[email protected]>
---
net/bluetooth/hci_conn.c | 7 ++++---
1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/net/bluetooth/hci_conn.c b/net/bluetooth/hci_conn.c
index b4548c73..2ebcaaa 100644
--- a/net/bluetooth/hci_conn.c
+++ b/net/bluetooth/hci_conn.c
@@ -91,10 +91,12 @@ static void hci_connect_le_scan_cleanup(struct hci_conn *conn)
* autoconnect action, remove them completely. If they are, just unmark
* them as waiting for connection, by clearing explicit_connect field.
*/
- if (params->auto_connect == HCI_AUTO_CONN_EXPLICIT)
+ if (params->auto_connect == HCI_AUTO_CONN_EXPLICIT) {
hci_conn_params_del(conn->hdev, bdaddr, bdaddr_type);
- else
+ } else {
params->explicit_connect = false;
+ hci_update_background_scan(conn->hdev);
+ }
}

/* This function requires the caller holds hdev->lock */
@@ -103,7 +105,6 @@ static void hci_connect_le_scan_remove(struct hci_conn *conn)
hci_connect_le_scan_cleanup(conn);

hci_conn_hash_del(conn->hdev, conn);
- hci_update_background_scan(conn->hdev);
}

static void hci_acl_create_connection(struct hci_conn *conn)
--
2.6.0.rc2.230.g3dd15c0