Bluetooth: host: Optionally disable GATT sec re-establishment

Some centrals deal poorly with receiving a security request immediately
after reconnection whenever reconnecting with characteristics that are
notifiable or indicatable and requiring security. In particular,
Android 9 and earlier devices may lose bond information when this
happens, some Microsoft Surface devices will enter an invalid state
and, on top of that, Apple's Bluetooth Low Energy guidelines explicitly
discourage this behavior.

In order to allow interoperability with those devices, make the GATT
automatic security request sending as a peripheral optional by
introducing a new Kconfig option, BT_GATT_AUTO_SEC_REQ.

Signed-off-by: Carles Cufi <carles.cufi@nordicsemi.no>
This commit is contained in:
Carles Cufi 2021-06-08 11:05:18 +02:00 committed by Johan Hedberg
commit d9848b155d
2 changed files with 20 additions and 0 deletions

View file

@ -55,6 +55,24 @@ config BT_EATT_SEC_LEVEL
endif # BT_EATT endif # BT_EATT
config BT_GATT_AUTO_SEC_REQ
bool "Automatic security re-establishment request as a peripheral"
default y
depends on BT_SMP
help
This option requests security re-establishment automatically whenever
a reconnection to a GATT client is established and
there are notifiable or indicatable characteristics for which security
is required. This configuration option only applies to the peripheral
role, which sends a Security Request for this purpose.
When disabled, it is the application's responsibility to call
bt_conn_set_security() to re-establish security prior to sending any
notifications or indications on the characteristics that require
security (unless the central does that first).
This option has been introduced to avoid interoperability issues with
commercially available central devices that react negatively to
receiving a Security Request immediately after reconnection.
config BT_GATT_SERVICE_CHANGED config BT_GATT_SERVICE_CHANGED
bool "GATT Service Changed support" bool "GATT Service Changed support"
default y default y

View file

@ -4861,6 +4861,8 @@ void bt_gatt_connected(struct bt_conn *conn)
* enabling encryption will fail. * enabling encryption will fail.
*/ */
if (IS_ENABLED(CONFIG_BT_SMP) && if (IS_ENABLED(CONFIG_BT_SMP) &&
(conn->role == BT_HCI_ROLE_MASTER ||
IS_ENABLED(CONFIG_BT_GATT_AUTO_SEC_REQ)) &&
bt_conn_get_security(conn) < data.sec) { bt_conn_get_security(conn) < data.sec) {
int err = bt_conn_set_security(conn, data.sec); int err = bt_conn_set_security(conn, data.sec);