Bluetooth: Add bt_att_send API

This adds bt_att_send which will be used by GATT client API to send
requests.

Note: bt_att_send can only handle one request at time but once the
requirements are clarified it will probably be extended to support
more requests to attend multiple applications probably using a fifo.

Change-Id: If9e89f7f6f0d3827a7f11c8feb4f1f1045d800be
Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
This commit is contained in:
Luiz Augusto von Dentz 2015-06-29 14:40:40 +03:00 committed by Anas Nashif
commit 8fe7db3e17
2 changed files with 75 additions and 0 deletions

View file

@ -70,11 +70,20 @@
#define BT_ATT_OP_CMD_MASK (BT_ATT_OP_WRITE_CMD & \
BT_ATT_OP_SIGNED_WRITE_CMD)
/* ATT request context */
struct bt_att_req {
bt_att_func_t func;
void *user_data;
bt_att_destroy_t destroy;
};
/* ATT channel specific context */
struct bt_att {
/* The connection this context is associated with */
struct bt_conn *conn;
uint16_t mtu;
struct bt_att_req req;
/* TODO: Allow more than one pending request */
};
static struct bt_att bt_att_pool[CONFIG_BLUETOOTH_MAX_CONN];
@ -89,6 +98,15 @@ static const struct bt_uuid secondary_uuid = {
.u16 = BT_UUID_GATT_SECONDARY,
};
static void att_req_destroy(struct bt_att *att)
{
if (att->req.destroy) {
att->req.destroy(att->req.user_data);
}
memset(&att->req, 0, sizeof(att->req));
}
static void send_err_rsp(struct bt_conn *conn, uint8_t req, uint16_t handle,
uint8_t err)
{
@ -1244,3 +1262,49 @@ void bt_att_init(void)
bt_l2cap_chan_register(&chan);
}
int bt_att_send(struct bt_conn *conn, struct bt_buf *buf, bt_att_func_t func,
void *user_data, bt_att_destroy_t destroy)
{
struct bt_att *att;
if (!conn) {
return -EINVAL;
}
att = conn->att;
if (!att) {
return -ENOTCONN;
}
if (func) {
/* Check if there is a request pending */
if (att->req.func) {
/* TODO: Allow more than one pending request */
return -EBUSY;
}
att->req.func = func;
att->req.user_data = user_data;
att->req.destroy = destroy;
}
bt_l2cap_send(conn, BT_L2CAP_CID_ATT, buf);
return 0;
}
void bt_att_cancel(struct bt_conn *conn)
{
struct bt_att *att;
if (!conn) {
return;
}
att = conn->att;
if (!att) {
return;
}
att_req_destroy(att);
}

View file

@ -276,3 +276,14 @@ struct bt_att_signed_write_cmd {
void bt_att_init();
struct bt_buf *bt_att_create_pdu(struct bt_conn *conn, uint8_t op, size_t len);
typedef void (*bt_att_func_t)(uint8_t err, const void *pdu, uint16_t length,
void *user_data);
typedef void (*bt_att_destroy_t)(void *user_data);
/* Send ATT PDU over a connection */
int bt_att_send(struct bt_conn *conn, struct bt_buf *buf, bt_att_func_t func,
void *user_data, bt_att_destroy_t destroy);
/* Cancel ATT request */
void bt_att_cancel(struct bt_conn *conn);