Skip to content

Commit

Permalink
Bluetooth: Host: Define bt_att_err_to_str()
Browse files Browse the repository at this point in the history
This can be useful if application developers
want to print them in the applications.

Later we can also use them in
the host to improve debuggability.

Signed-off-by: Rubin Gerritsen <[email protected]>
  • Loading branch information
rugeGerritsen authored and aescolar committed Jun 20, 2024
1 parent e96cfe0 commit 94d712e
Show file tree
Hide file tree
Showing 3 changed files with 92 additions and 0 deletions.
16 changes: 16 additions & 0 deletions include/zephyr/bluetooth/att.h
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,22 @@ extern "C" {
#define BT_ATT_LAST_ATTRIBUTE_HANDLE 0xffff
#define BT_ATT_LAST_ATTTRIBUTE_HANDLE __DEPRECATED_MACRO BT_ATT_LAST_ATTRIBUTE_HANDLE

/** Converts a ATT error to string.
*
* The error codes are described in the Bluetooth Core specification,
* Vol 3, Part F, Section 3.4.1.1 and in
* The Supplement to the Bluetooth Core Specification (CSS), v11,
* Part B, Section 1.2.
*
* The ATT and GATT documentation found in Vol 4, Part F and
* Part G describe when the different error codes are used.
*
* See also the defined BT_ATT_ERR_* macros.
*
* @return The string representation of the ATT error code.
*/
const char *bt_att_err_to_str(uint8_t att_err);

#if defined(CONFIG_BT_EATT)
#if defined(CONFIG_BT_TESTING)

Expand Down
55 changes: 55 additions & 0 deletions subsys/bluetooth/host/att.c
Original file line number Diff line number Diff line change
Expand Up @@ -185,6 +185,61 @@ static struct bt_att_tx_meta_data tx_meta_data_storage[CONFIG_BT_ATT_TX_COUNT];
struct bt_att_tx_meta_data *bt_att_get_tx_meta_data(const struct net_buf *buf);
static void att_on_sent_cb(struct bt_att_tx_meta_data *meta);


const char *bt_att_err_to_str(uint8_t att_err)
{
/* To mapping tables are used to avoid a big gap with NULL-entries. */
#define ATT_ERR(err) [err] = #err
#define ATT_ERR_SECOND(err) [err - BT_ATT_ERR_WRITE_REQ_REJECTED] = #err

const char * const first_mapping_table[] = {
ATT_ERR(BT_ATT_ERR_SUCCESS),
ATT_ERR(BT_ATT_ERR_INVALID_HANDLE),
ATT_ERR(BT_ATT_ERR_READ_NOT_PERMITTED),
ATT_ERR(BT_ATT_ERR_WRITE_NOT_PERMITTED),
ATT_ERR(BT_ATT_ERR_INVALID_PDU),
ATT_ERR(BT_ATT_ERR_AUTHENTICATION),
ATT_ERR(BT_ATT_ERR_NOT_SUPPORTED),
ATT_ERR(BT_ATT_ERR_INVALID_OFFSET),
ATT_ERR(BT_ATT_ERR_AUTHORIZATION),
ATT_ERR(BT_ATT_ERR_PREPARE_QUEUE_FULL),
ATT_ERR(BT_ATT_ERR_ATTRIBUTE_NOT_FOUND),
ATT_ERR(BT_ATT_ERR_ATTRIBUTE_NOT_LONG),
ATT_ERR(BT_ATT_ERR_ENCRYPTION_KEY_SIZE),
ATT_ERR(BT_ATT_ERR_INVALID_ATTRIBUTE_LEN),
ATT_ERR(BT_ATT_ERR_UNLIKELY),
ATT_ERR(BT_ATT_ERR_INSUFFICIENT_ENCRYPTION),
ATT_ERR(BT_ATT_ERR_UNSUPPORTED_GROUP_TYPE),
ATT_ERR(BT_ATT_ERR_INSUFFICIENT_RESOURCES),
ATT_ERR(BT_ATT_ERR_DB_OUT_OF_SYNC),
ATT_ERR(BT_ATT_ERR_VALUE_NOT_ALLOWED),
};

const char * const second_mapping_table[] = {
ATT_ERR_SECOND(BT_ATT_ERR_WRITE_REQ_REJECTED),
ATT_ERR_SECOND(BT_ATT_ERR_CCC_IMPROPER_CONF),
ATT_ERR_SECOND(BT_ATT_ERR_PROCEDURE_IN_PROGRESS),
ATT_ERR_SECOND(BT_ATT_ERR_OUT_OF_RANGE),
};


if (att_err < ARRAY_SIZE(first_mapping_table) && first_mapping_table[att_err]) {
return first_mapping_table[att_err];
} else if (att_err >= BT_ATT_ERR_WRITE_REQ_REJECTED) {
const uint8_t second_index = att_err - BT_ATT_ERR_WRITE_REQ_REJECTED;

if (second_index < ARRAY_SIZE(second_mapping_table) &&
second_mapping_table[second_index]) {
return second_mapping_table[second_index];
}
}

return "(unknown)";

#undef ATT_ERR
#undef ATT_ERR_SECOND
}

static void att_tx_destroy(struct net_buf *buf)
{
struct bt_att_tx_meta_data *p_meta = bt_att_get_tx_meta_data(buf);
Expand Down
21 changes: 21 additions & 0 deletions tests/bluetooth/gatt/src/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -274,3 +274,24 @@ ZTEST(test_gatt, test_gatt_write)
zassert_mem_equal(value, test_value, ret,
"Attribute write value don't match");
}

ZTEST(test_gatt, test_bt_att_err_to_str)
{
/* Test a couple of entries */
zassert_str_equal(bt_att_err_to_str(BT_ATT_ERR_SUCCESS),
"BT_ATT_ERR_SUCCESS");
zassert_str_equal(bt_att_err_to_str(BT_ATT_ERR_INSUFFICIENT_ENCRYPTION),
"BT_ATT_ERR_INSUFFICIENT_ENCRYPTION");
zassert_str_equal(bt_att_err_to_str(BT_ATT_ERR_OUT_OF_RANGE),
"BT_ATT_ERR_OUT_OF_RANGE");

/* Test a entries that is not used */
zassert_mem_equal(bt_att_err_to_str(0x14),
"(unknown)", strlen("(unknown)"));
zassert_mem_equal(bt_att_err_to_str(0xFB),
"(unknown)", strlen("(unknown)"));

for (uint16_t i = 0; i <= UINT8_MAX; i++) {
zassert_not_null(bt_att_err_to_str(i), ": %d", i);
}
}

0 comments on commit 94d712e

Please sign in to comment.