Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 14 additions & 0 deletions include/zephyr/bluetooth/gatt.h
Original file line number Diff line number Diff line change
Expand Up @@ -1167,6 +1167,20 @@ ssize_t bt_gatt_attr_write_ccc(struct bt_conn *conn,
BT_GATT_CCC_MANAGED(((struct _bt_gatt_ccc[]) \
{BT_GATT_CCC_INITIALIZER(_changed, NULL, NULL)}), _perm)

/**
* @brief Client Characteristic Configuration Declaration Macro with write callback.
*
* Helper macro to declare a CCC attribute with a write callback.
*
* @param _changed Configuration changed callback.
* @param _write Configuration write callback.
* @param _perm CCC access permissions,
* a bitmap of @ref bt_gatt_perm values.
*/
#define BT_GATT_CCC_WITH_WRITE_CB(_changed, _write, _perm) \
BT_GATT_CCC_MANAGED(((struct _bt_gatt_ccc[]) \
{BT_GATT_CCC_INITIALIZER(_changed, _write, NULL) }), _perm)

/** @brief Read Characteristic Extended Properties Attribute helper
*
* Read CEP attribute value from local database storing the result into buffer
Expand Down
4 changes: 4 additions & 0 deletions subsys/bluetooth/host/cs.c
Original file line number Diff line number Diff line change
Expand Up @@ -606,6 +606,10 @@ int bt_le_cs_start_test(const struct bt_le_cs_test_param *params)

cp->override_parameters_length = override_parameters_length;

struct bt_hci_cmd_hdr *hdr = (struct bt_hci_cmd_hdr *)buf->data;

hdr->param_len += override_parameters_length;

return bt_hci_cmd_send_sync(BT_HCI_OP_LE_CS_TEST, buf, NULL);
}
#endif /* CONFIG_BT_CHANNEL_SOUNDING_TEST */
Expand Down
27 changes: 27 additions & 0 deletions tests/bluetooth/gatt/src/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,11 @@
nfy_enabled = (value == BT_GATT_CCC_NOTIFY) ? 1 : 0;
}

static ssize_t test1_ccc_cfg_write_cb(struct bt_conn *conn, const struct bt_gatt_attr *attr, uint16_t value)

Check warning on line 42 in tests/bluetooth/gatt/src/main.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

LONG_LINE

tests/bluetooth/gatt/src/main.c:42 line length of 108 exceeds 100 columns
{
return sizeof(value);
}

static ssize_t read_test(struct bt_conn *conn, const struct bt_gatt_attr *attr,
void *buf, uint16_t len, uint16_t offset)
{
Expand Down Expand Up @@ -507,3 +512,25 @@
zassert_not_null(bt_gatt_err_to_str(-i), ": %d", i);
}
}

ZTEST(test_gatt, test_gatt_ccc_write_cb)
{
struct bt_gatt_attr test_write_cb_attrs[] = {
/* Vendor Primary Service Declaration */
BT_GATT_PRIMARY_SERVICE(&test1_uuid),

BT_GATT_CHARACTERISTIC(&test1_nfy_uuid.uuid,
BT_GATT_CHRC_NOTIFY, BT_GATT_PERM_NONE,
NULL, NULL, &nfy_enabled),
BT_GATT_CCC_WITH_WRITE_CB(test1_ccc_cfg_changed,
test1_ccc_cfg_write_cb,
BT_GATT_PERM_READ_ENCRYPT | BT_GATT_PERM_WRITE_ENCRYPT),
};

struct bt_gatt_service test_write_cb_svc = BT_GATT_SERVICE(test_write_cb_attrs);

zassert_false(bt_gatt_service_register(&test_write_cb_svc),
"Test service registration failed");
zassert_false(bt_gatt_service_unregister(&test_write_cb_svc),
"Test service1 unregister failed");
}
12 changes: 12 additions & 0 deletions tests/bsim/bluetooth/host/gatt/ccc_store/src/central.c
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ static struct bt_conn *default_conn;

static struct bt_conn_cb central_cb;

DEFINE_FLAG_STATIC(gatt_subscribed_rejected_flag);
DEFINE_FLAG_STATIC(gatt_subscribed_flag);

static uint8_t notify_cb(struct bt_conn *conn, struct bt_gatt_subscribe_params *params,
Expand Down Expand Up @@ -69,6 +70,9 @@ static uint8_t notify_cb(struct bt_conn *conn, struct bt_gatt_subscribe_params *
static void subscribe_cb(struct bt_conn *conn, uint8_t err, struct bt_gatt_subscribe_params *params)
{
if (err) {
if (err == BT_ATT_ERR_WRITE_NOT_PERMITTED) {
SET_FLAG(gatt_subscribed_rejected_flag);
}
return;
}

Expand All @@ -81,6 +85,7 @@ static void ccc_subscribe(void)
{
int err;

UNSET_FLAG(gatt_subscribed_rejected_flag);
UNSET_FLAG(gatt_subscribed_flag);

subscribe_params.notify = notify_cb;
Expand All @@ -94,6 +99,13 @@ static void ccc_subscribe(void)
TEST_FAIL("Failed to subscribe (att err %d)", err);
}

WAIT_FOR_FLAG(gatt_subscribed_rejected_flag);

err = bt_gatt_subscribe(default_conn, &subscribe_params);
if (err) {
TEST_FAIL("Failed to subscribe (att err %d)", err);
}

WAIT_FOR_FLAG(gatt_subscribed_flag);
}

Expand Down
18 changes: 17 additions & 1 deletion tests/bsim/bluetooth/host/gatt/ccc_store/src/peripheral.c
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@

static struct bt_conn_cb peripheral_cb;

static bool notif_write_allowed;

static void ccc_cfg_changed(const struct bt_gatt_attr *attr, uint16_t value)
{
ARG_UNUSED(attr);
Expand All @@ -52,10 +54,24 @@
SET_FLAG(ccc_cfg_changed_flag);
}

static ssize_t ccc_cfg_write_cb(struct bt_conn *conn, const struct bt_gatt_attr *attr, uint16_t value)

Check warning on line 57 in tests/bsim/bluetooth/host/gatt/ccc_store/src/peripheral.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

LONG_LINE

tests/bsim/bluetooth/host/gatt/ccc_store/src/peripheral.c:57 line length of 102 exceeds 100 columns
{
if (notif_write_allowed) {
LOG_INF("CCC Write Request accepted.");
return sizeof(value);
} else {

Check warning on line 62 in tests/bsim/bluetooth/host/gatt/ccc_store/src/peripheral.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

UNNECESSARY_ELSE

tests/bsim/bluetooth/host/gatt/ccc_store/src/peripheral.c:62 else is not generally useful after a break or return
LOG_INF("CCC Write Request rejected.");
notif_write_allowed = true;
return BT_GATT_ERR(BT_ATT_ERR_WRITE_NOT_PERMITTED);
}
}

BT_GATT_SERVICE_DEFINE(dummy_svc, BT_GATT_PRIMARY_SERVICE(&dummy_service),
BT_GATT_CHARACTERISTIC(&notify_characteristic_uuid.uuid, BT_GATT_CHRC_NOTIFY,
BT_GATT_PERM_NONE, NULL, NULL, NULL),
BT_GATT_CCC(ccc_cfg_changed, BT_GATT_PERM_READ | BT_GATT_PERM_WRITE));
BT_GATT_CCC_WITH_WRITE_CB(ccc_cfg_changed, ccc_cfg_write_cb,
BT_GATT_PERM_READ | BT_GATT_PERM_WRITE)
);

static void create_adv(struct bt_le_ext_adv **adv)
{
Expand Down
Loading