Bluetooth: CAP: Fix issue with parallel CAP discover

The bt_cap_common_discover function relied on a global variable
used to  indicate that a discovery was in process.
This global variable prevented multiple discoveries to take place
on multiple ACL connections, where the intention was to stop
multiple discoveries on the same ACL.
This has been fixed by moving the variable into the
struct bt_cap_common_client, so that it applies per
connection, rather than a global check.

Signed-off-by: Emil Gydesen <emil.gydesen@nordicsemi.no>
This commit is contained in:
Emil Gydesen 2024-05-02 09:57:00 +02:00 committed by Carles Cufí
commit 68ea1c4fe4
2 changed files with 16 additions and 11 deletions

View file

@ -17,7 +17,6 @@ LOG_MODULE_REGISTER(bt_cap_common, CONFIG_BT_CAP_COMMON_LOG_LEVEL);
static struct bt_cap_common_client bt_cap_common_clients[CONFIG_BT_MAX_CONN];
static const struct bt_uuid *cas_uuid = BT_UUID_CAS;
static struct bt_cap_common_proc active_proc;
static bt_cap_common_discover_func_t discover_cb_func;
struct bt_cap_common_proc *bt_cap_common_get_active_proc(void)
{
@ -258,10 +257,13 @@ struct bt_cap_common_client *bt_cap_common_get_client(enum bt_cap_set_type type,
static void cap_common_discover_complete(struct bt_conn *conn, int err,
const struct bt_csip_set_coordinator_csis_inst *csis_inst)
{
if (discover_cb_func != NULL) {
const bt_cap_common_discover_func_t cb_func = discover_cb_func;
struct bt_cap_common_client *client;
discover_cb_func = NULL;
client = bt_cap_common_get_client_by_acl(conn);
if (client != NULL && client->discover_cb_func != NULL) {
const bt_cap_common_discover_func_t cb_func = client->discover_cb_func;
client->discover_cb_func = NULL;
cb_func(conn, err, csis_inst);
}
}
@ -386,24 +388,26 @@ static uint8_t bt_cap_common_discover_cas_cb(struct bt_conn *conn, const struct
int bt_cap_common_discover(struct bt_conn *conn, bt_cap_common_discover_func_t func)
{
struct bt_gatt_discover_params *param;
struct bt_cap_common_client *client;
int err;
if (discover_cb_func != NULL) {
client = bt_cap_common_get_client_by_acl(conn);
if (client->discover_cb_func != NULL) {
return -EBUSY;
}
param = &bt_cap_common_clients[bt_conn_index(conn)].param;
param = &client->param;
param->func = bt_cap_common_discover_cas_cb;
param->uuid = cas_uuid;
param->type = BT_GATT_DISCOVER_PRIMARY;
param->start_handle = BT_ATT_FIRST_ATTRIBUTE_HANDLE;
param->end_handle = BT_ATT_LAST_ATTRIBUTE_HANDLE;
discover_cb_func = func;
client->discover_cb_func = func;
err = bt_gatt_discover(conn, param);
if (err != 0) {
discover_cb_func = NULL;
client->discover_cb_func = NULL;
/* Report expected possible errors */
if (err == -ENOTCONN || err == -ENOMEM) {

View file

@ -101,6 +101,9 @@ struct bt_cap_commander_proc_param {
};
};
typedef void (*bt_cap_common_discover_func_t)(
struct bt_conn *conn, int err, const struct bt_csip_set_coordinator_csis_inst *csis_inst);
struct bt_cap_common_proc_param {
union {
#if defined(CONFIG_BT_CAP_INITIATOR_UNICAST)
@ -133,6 +136,7 @@ struct bt_cap_common_proc {
struct bt_cap_common_client {
struct bt_conn *conn;
struct bt_gatt_discover_params param;
bt_cap_common_discover_func_t discover_cb_func;
uint16_t csis_start_handle;
const struct bt_csip_set_coordinator_csis_inst *csis_inst;
bool cas_found;
@ -158,7 +162,4 @@ struct bt_cap_common_client *
bt_cap_common_get_client_by_csis(const struct bt_csip_set_coordinator_csis_inst *csis_inst);
struct bt_cap_common_client *bt_cap_common_get_client(enum bt_cap_set_type type,
const union bt_cap_set_member *member);
typedef void (*bt_cap_common_discover_func_t)(
struct bt_conn *conn, int err, const struct bt_csip_set_coordinator_csis_inst *csis_inst);
int bt_cap_common_discover(struct bt_conn *conn, bt_cap_common_discover_func_t func);