From 8f287753479310e42043fbd3c1707c4ab7aa053f Mon Sep 17 00:00:00 2001 From: Chris Andreae Date: Fri, 27 Jan 2023 19:30:43 +0900 Subject: [PATCH] feat(ble): add behavior to disconnect from BLE profile Adds new functionality and a behaviour to disconnect an active BLE connection. The motivation for this is that for some devices like phones, the presence of an active BLE connection results in the onscreen keyboard being selected. --- app/include/dt-bindings/zmk/bt.h | 2 ++ app/include/zmk/ble.h | 1 + app/src/behaviors/behavior_bt.c | 2 ++ app/src/ble.c | 21 +++++++++++++++++++++ 4 files changed, 26 insertions(+) diff --git a/app/include/dt-bindings/zmk/bt.h b/app/include/dt-bindings/zmk/bt.h index 8ca10606..215f8559 100644 --- a/app/include/dt-bindings/zmk/bt.h +++ b/app/include/dt-bindings/zmk/bt.h @@ -9,6 +9,7 @@ #define BT_PRV_CMD 2 #define BT_SEL_CMD 3 // #define BT_FULL_RESET_CMD 4 +#define BT_DISCONNECT_CMD 5 /* Note: Some future commands will include additional parameters, so we @@ -19,3 +20,4 @@ defines these aliases up front. #define BT_NXT BT_NXT_CMD 0 #define BT_PRV BT_PRV_CMD 0 #define BT_SEL BT_SEL_CMD +#define BT_DISCONNECT BT_DISCONNECT_CMD diff --git a/app/include/zmk/ble.h b/app/include/zmk/ble.h index 435fde49..92fd595f 100644 --- a/app/include/zmk/ble.h +++ b/app/include/zmk/ble.h @@ -24,6 +24,7 @@ int zmk_ble_clear_bonds(); int zmk_ble_prof_next(); int zmk_ble_prof_prev(); int zmk_ble_prof_select(uint8_t index); +int zmk_ble_prof_disconnect(uint8_t index); int zmk_ble_active_profile_index(); bt_addr_le_t *zmk_ble_active_profile_addr(); diff --git a/app/src/behaviors/behavior_bt.c b/app/src/behaviors/behavior_bt.c index 6d44b5f5..319014b4 100644 --- a/app/src/behaviors/behavior_bt.c +++ b/app/src/behaviors/behavior_bt.c @@ -31,6 +31,8 @@ static int on_keymap_binding_pressed(struct zmk_behavior_binding *binding, return zmk_ble_prof_prev(); case BT_SEL_CMD: return zmk_ble_prof_select(binding->param2); + case BT_DISCONNECT_CMD: + return zmk_ble_prof_disconnect(binding->param2); default: LOG_ERR("Unknown BT command: %d", binding->param1); } diff --git a/app/src/ble.c b/app/src/ble.c index 483bc9d7..1d7f6e86 100644 --- a/app/src/ble.c +++ b/app/src/ble.c @@ -271,6 +271,27 @@ int zmk_ble_prof_prev() { ZMK_BLE_PROFILE_COUNT); }; +int zmk_ble_prof_disconnect(uint8_t index) { + if (index >= ZMK_BLE_PROFILE_COUNT) + return -ERANGE; + + bt_addr_le_t *addr = &profiles[index].peer; + struct bt_conn *conn; + int result; + + if (!bt_addr_le_cmp(addr, BT_ADDR_LE_ANY)) { + return -1; + } else if ((conn = bt_conn_lookup_addr_le(BT_ID_DEFAULT, addr)) == NULL) { + return -1; + } + + result = bt_conn_disconnect(conn, BT_HCI_ERR_REMOTE_USER_TERM_CONN); + LOG_DBG("Disconnected from profile %d: %d", index, result); + + bt_conn_unref(conn); + return result; +} + bt_addr_le_t *zmk_ble_active_profile_addr() { return &profiles[active_profile].peer; } char *zmk_ble_active_profile_name() { return profiles[active_profile].name; }