Bluetooth: Mesh: Introduce user data for the advertising callback

This simplifies the callback implementations since they no-longer need
to do their own look-ups of the needed context.

Signed-off-by: Johan Hedberg <johan.hedberg@intel.com>
This commit is contained in:
Johan Hedberg 2017-11-17 11:58:06 +02:00 committed by Johan Hedberg
commit 8beb6784d3
11 changed files with 66 additions and 78 deletions

View file

@ -76,7 +76,8 @@ static inline void adv_sent(struct net_buf *buf, u16_t duration, int err)
BT_MESH_ADV(buf)->busy = 0;
if (BT_MESH_ADV(buf)->sent) {
BT_MESH_ADV(buf)->sent(buf, duration, err);
BT_MESH_ADV(buf)->sent(buf, duration, err,
BT_MESH_ADV(buf)->user_data);
}
}
@ -208,12 +209,14 @@ struct net_buf *bt_mesh_adv_create(enum bt_mesh_adv_type type, u8_t xmit_count,
xmit_count, xmit_int, timeout);
}
void bt_mesh_adv_send(struct net_buf *buf, bt_mesh_adv_func_t sent)
void bt_mesh_adv_send(struct net_buf *buf, bt_mesh_adv_func_t sent,
void *user_data)
{
BT_DBG("type 0x%02x len %u: %s", BT_MESH_ADV(buf)->type, buf->len,
bt_hex(buf->data, buf->len));
BT_MESH_ADV(buf)->sent = sent;
BT_MESH_ADV(buf)->user_data = user_data;
BT_MESH_ADV(buf)->busy = 1;
net_buf_put(&adv_queue, net_buf_ref(buf));

View file

@ -21,24 +21,22 @@ enum bt_mesh_adv_type {
};
typedef void (*bt_mesh_adv_func_t)(struct net_buf *buf, u16_t duration,
int err);
int err, void *user_data);
struct bt_mesh_adv {
bt_mesh_adv_func_t sent;
void *user_data;
u8_t type:2,
busy:1;
u8_t count:3,
adv_int:5;
union {
/* Generic User Data */
u8_t user_data[2];
/* Address, used e.g. for Friend Queue messages */
u16_t addr;
/* For transport layer segment sending */
struct {
u8_t tx_id;
u8_t attempts;
} seg;
};
@ -56,7 +54,8 @@ struct net_buf *bt_mesh_adv_create_from_pool(struct net_buf_pool *pool,
u8_t xmit_count, u8_t xmit_int,
s32_t timeout);
void bt_mesh_adv_send(struct net_buf *buf, bt_mesh_adv_func_t sent);
void bt_mesh_adv_send(struct net_buf *buf, bt_mesh_adv_func_t sent,
void *user_data);
void bt_mesh_adv_update(void);

View file

@ -73,13 +73,13 @@ static void cache_add(u8_t data[21], u16_t net_idx)
memcpy(beacon_cache[net_idx].data, data, 21);
}
static void beacon_complete(struct net_buf *buf, u16_t duration, int err)
static void beacon_complete(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct bt_mesh_subnet *sub;
struct bt_mesh_subnet *sub = user_data;
BT_DBG("err %d", err);
sub = &bt_mesh.sub[BT_MESH_ADV(buf)->user_data[0]];
sub->beacon_sent = k_uptime_get_32() + duration;
}
@ -151,11 +151,9 @@ static int secure_beacon_send(void)
return -ENOBUFS;
}
BT_MESH_ADV(buf)->user_data[0] = i;
bt_mesh_beacon_create(sub, &buf->b);
bt_mesh_adv_send(buf, beacon_complete);
bt_mesh_adv_send(buf, beacon_complete, sub);
net_buf_unref(buf);
}
@ -182,7 +180,7 @@ static int unprovisioned_beacon_send(void)
/* OOB Info (2 bytes) + URI Hash (4 bytes) */
memset(net_buf_add(buf, 2 + 4), 0, 2 + 4);
bt_mesh_adv_send(buf, NULL);
bt_mesh_adv_send(buf, NULL, NULL);
net_buf_unref(buf);
#endif /* CONFIG_BT_MESH_PB_ADV */

View file

@ -89,7 +89,7 @@ static void hb_send(struct bt_mesh_model *model)
BT_DBG("InitTTL %u feat 0x%04x", cfg->hb_pub.ttl, feat);
bt_mesh_ctl_send(&tx, TRANS_CTL_OP_HEARTBEAT, &hb, sizeof(hb),
NULL, NULL);
NULL, NULL, NULL);
}
static int comp_add_elem(struct net_buf_simple *buf, struct bt_mesh_elem *elem,

View file

@ -272,7 +272,7 @@ int bt_mesh_friend_clear(struct bt_mesh_net_rx *rx, struct net_buf_simple *buf)
cfm.lpn_counter = msg->lpn_counter;
bt_mesh_ctl_send(&tx, TRANS_CTL_OP_FRIEND_CLEAR_CFM, &cfm,
sizeof(cfm), NULL, NULL);
sizeof(cfm), NULL, NULL, NULL);
friend_clear(frnd);
@ -604,18 +604,10 @@ static struct bt_mesh_friend *find_clear(u16_t prev_friend)
return NULL;
}
static void friend_clear_sent(struct net_buf *buf, u16_t duration, int err)
static void friend_clear_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct bt_mesh_friend *frnd;
BT_DBG("addr 0x%02x", BT_MESH_ADV(buf)->addr);
frnd = find_clear(BT_MESH_ADV(buf)->addr);
if (!frnd) {
BT_WARN("No matching clear procedure found for 0x%02x",
BT_MESH_ADV(buf)->addr);
return;
}
struct bt_mesh_friend *frnd = user_data;
k_delayed_work_submit(&frnd->clear.timer,
duration + K_SECONDS(frnd->clear.repeat_sec));
@ -644,7 +636,7 @@ static void send_friend_clear(struct bt_mesh_friend *frnd)
BT_DBG("");
bt_mesh_ctl_send(&tx, TRANS_CTL_OP_FRIEND_CLEAR, &req,
sizeof(req), NULL, friend_clear_sent);
sizeof(req), NULL, friend_clear_sent, frnd);
}
static void clear_timeout(struct k_work *work)
@ -953,24 +945,13 @@ static void enqueue_friend_pdu(struct bt_mesh_friend *frnd,
}
}
static void buf_sent(struct net_buf *buf, u16_t duration, int err)
static void buf_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct bt_mesh_friend *frnd = NULL;
int i;
struct bt_mesh_friend *frnd = user_data;
BT_DBG("buf %p err %d", buf, err);
for (i = 0; i < ARRAY_SIZE(bt_mesh.frnd); i++) {
if (bt_mesh.frnd[i].last == buf) {
frnd = &bt_mesh.frnd[i];
break;
}
}
if (!frnd) {
return;
}
frnd->pending_buf = 0;
if (frnd->established) {
@ -1024,7 +1005,7 @@ static void friend_timeout(struct k_work *work)
send_last:
frnd->pending_buf = 1;
bt_mesh_adv_send(frnd->last, buf_sent);
bt_mesh_adv_send(frnd->last, buf_sent, frnd);
}
int bt_mesh_friend_init(void)

View file

@ -103,7 +103,8 @@ static inline void lpn_set_state(int state)
static void clear_friendship(bool force, bool disable);
static void friend_clear_sent(struct net_buf *buf, u16_t duration, int err)
static void friend_clear_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct bt_mesh_lpn *lpn = &bt_mesh.lpn;
@ -147,7 +148,7 @@ static int send_friend_clear(void)
BT_DBG("");
return bt_mesh_ctl_send(&tx, TRANS_CTL_OP_FRIEND_CLEAR, &req,
sizeof(req), NULL, friend_clear_sent);
sizeof(req), NULL, friend_clear_sent, NULL);
}
static void clear_friendship(bool force, bool disable)
@ -198,7 +199,8 @@ static void clear_friendship(bool force, bool disable)
k_delayed_work_submit(&lpn->timer, FRIEND_REQ_RETRY_TIMEOUT);
}
static void friend_req_sent(struct net_buf *buf, u16_t duration, int err)
static void friend_req_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct bt_mesh_lpn *lpn = &bt_mesh.lpn;
@ -246,7 +248,7 @@ static int send_friend_req(struct bt_mesh_lpn *lpn)
BT_DBG("");
return bt_mesh_ctl_send(&tx, TRANS_CTL_OP_FRIEND_REQ, &req,
sizeof(req), NULL, friend_req_sent);
sizeof(req), NULL, friend_req_sent, NULL);
}
static inline void group_zero(atomic_t *target)
@ -288,7 +290,8 @@ static inline void group_clear(atomic_t *target, atomic_t *source)
#endif
}
static void req_sent(struct net_buf *buf, u16_t duration, int err)
static void req_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct bt_mesh_lpn *lpn = &bt_mesh.lpn;
@ -350,7 +353,7 @@ static int send_friend_poll(void)
}
err = bt_mesh_ctl_send(&tx, TRANS_CTL_OP_FRIEND_POLL, &fsn, 1,
NULL, req_sent);
NULL, req_sent, NULL);
if (err == 0) {
lpn->pending_poll = 0;
lpn->sent_req = TRANS_CTL_OP_FRIEND_POLL;
@ -669,7 +672,8 @@ static bool sub_update(u8_t op)
req.xact = lpn->xact_next++;
if (bt_mesh_ctl_send(&tx, op, &req, 1 + g * 2, NULL, req_sent) < 0) {
if (bt_mesh_ctl_send(&tx, op, &req, 1 + g * 2, NULL,
req_sent, NULL) < 0) {
group_zero(lpn->pending);
return false;
}

View file

@ -670,7 +670,7 @@ do_update:
}
int bt_mesh_net_resend(struct bt_mesh_subnet *sub, struct net_buf *buf,
bool new_key, bt_mesh_adv_func_t cb)
bool new_key, bt_mesh_adv_func_t cb, void *user_data)
{
const u8_t *enc, *priv;
int err;
@ -710,7 +710,7 @@ int bt_mesh_net_resend(struct bt_mesh_subnet *sub, struct net_buf *buf,
return err;
}
bt_mesh_adv_send(buf, cb);
bt_mesh_adv_send(buf, cb, user_data);
if (!bt_mesh.iv_update && bt_mesh.seq > IV_UPDATE_SEQ_LIMIT) {
bt_mesh_beacon_ivu_initiator(true);
@ -799,7 +799,7 @@ int bt_mesh_net_encode(struct bt_mesh_net_tx *tx, struct net_buf_simple *buf,
}
int bt_mesh_net_send(struct bt_mesh_net_tx *tx, struct net_buf *buf,
bt_mesh_adv_func_t cb)
bt_mesh_adv_func_t cb, void *user_data)
{
int err;
@ -832,11 +832,11 @@ int bt_mesh_net_send(struct bt_mesh_net_tx *tx, struct net_buf *buf,
bt_mesh_elem_find(tx->ctx->addr)) {
net_buf_slist_put(&bt_mesh.local_queue, net_buf_ref(buf));
if (cb) {
cb(buf, 0, 0);
cb(buf, 0, 0, user_data);
}
k_work_submit(&bt_mesh.local_work);
} else {
bt_mesh_adv_send(buf, cb);
bt_mesh_adv_send(buf, cb, user_data);
}
done:
@ -1101,7 +1101,7 @@ static void bt_mesh_net_relay(struct net_buf_simple *sbuf,
}
}
bt_mesh_adv_send(buf, NULL);
bt_mesh_adv_send(buf, NULL, NULL);
done:
net_buf_unref(buf);

View file

@ -310,10 +310,10 @@ int bt_mesh_net_encode(struct bt_mesh_net_tx *tx, struct net_buf_simple *buf,
bool proxy);
int bt_mesh_net_send(struct bt_mesh_net_tx *tx, struct net_buf *buf,
bt_mesh_adv_func_t cb);
bt_mesh_adv_func_t cb, void *user_data);
int bt_mesh_net_resend(struct bt_mesh_subnet *sub, struct net_buf *buf,
bool new_key, bt_mesh_adv_func_t cb);
bool new_key, bt_mesh_adv_func_t cb, void *user_data);
int bt_mesh_net_decode(struct net_buf_simple *data, enum bt_mesh_net_if net_if,
struct bt_mesh_net_rx *rx, struct net_buf_simple *buf);

View file

@ -188,7 +188,8 @@ static const struct bt_mesh_prov *prov;
static void close_link(u8_t err, u8_t reason);
#if defined(CONFIG_BT_MESH_PB_ADV)
static void buf_sent(struct net_buf *buf, u16_t duration, int err)
static void buf_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
if (!link.tx.buf[0]) {
return;
@ -271,7 +272,8 @@ static struct net_buf *adv_buf_create(void)
static u8_t pending_ack = XACT_NVAL;
static void ack_complete(struct net_buf *buf, u16_t duration, int err)
static void ack_complete(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
BT_DBG("xact %u complete", (u8_t)pending_ack);
pending_ack = XACT_NVAL;
@ -305,7 +307,7 @@ static void gen_prov_ack_send(u8_t xact_id)
net_buf_add_u8(buf, xact_id);
net_buf_add_u8(buf, GPC_ACK);
bt_mesh_adv_send(buf, complete);
bt_mesh_adv_send(buf, complete, NULL);
net_buf_unref(buf);
}
@ -323,9 +325,9 @@ static void send_reliable(void)
}
if (i + 1 < ARRAY_SIZE(link.tx.buf) && link.tx.buf[i + 1]) {
bt_mesh_adv_send(buf, NULL);
bt_mesh_adv_send(buf, NULL, NULL);
} else {
bt_mesh_adv_send(buf, buf_sent);
bt_mesh_adv_send(buf, buf_sent, NULL);
}
}
}
@ -1135,9 +1137,9 @@ static void prov_retransmit(struct k_work *work)
BT_DBG("%u bytes: %s", buf->len, bt_hex(buf->data, buf->len));
if (i + 1 < ARRAY_SIZE(link.tx.buf) && link.tx.buf[i + 1]) {
bt_mesh_adv_send(buf, NULL);
bt_mesh_adv_send(buf, NULL, NULL);
} else {
bt_mesh_adv_send(buf, buf_sent);
bt_mesh_adv_send(buf, buf_sent, NULL);
}
}

View file

@ -136,7 +136,7 @@ static int send_unseg(struct bt_mesh_net_tx *tx, u8_t aid,
}
}
return bt_mesh_net_send(tx, buf, NULL);
return bt_mesh_net_send(tx, buf, NULL, NULL);
}
bool bt_mesh_tx_in_progress(void)
@ -198,9 +198,10 @@ static inline void seg_tx_complete(struct seg_tx *tx, int err)
seg_tx_reset(tx);
}
static void seg_sent(struct net_buf *buf, u16_t duration, int err)
static void seg_sent(struct net_buf *buf, u16_t duration, int err,
void *user_data)
{
struct seg_tx *tx = &seg_tx[BT_MESH_ADV(buf)->seg.tx_id];
struct seg_tx *tx = user_data;
k_delayed_work_submit(&tx->retransmit,
duration + SEG_RETRANSMIT_TIMEOUT);
@ -230,7 +231,8 @@ static void seg_tx_send_unacked(struct seg_tx *tx)
BT_DBG("resending %u/%u", i, tx->seg_n);
err = bt_mesh_net_resend(tx->sub, seg, tx->new_key, seg_sent);
err = bt_mesh_net_resend(tx->sub, seg, tx->new_key, seg_sent,
tx);
if (err) {
BT_ERR("Sending segment failed");
seg_tx_complete(tx, -EIO);
@ -316,7 +318,6 @@ static int send_seg(struct bt_mesh_net_tx *net_tx, u8_t aid,
return -ENOBUFS;
}
BT_MESH_ADV(seg)->seg.tx_id = tx - seg_tx;
BT_MESH_ADV(seg)->seg.attempts = SEG_RETRANSMIT_ATTEMPTS;
net_buf_reserve(seg, BT_MESH_NET_HDR_LEN);
@ -356,7 +357,7 @@ static int send_seg(struct bt_mesh_net_tx *net_tx, u8_t aid,
BT_DBG("Sending %u/%u", seg_o, tx->seg_n);
err = bt_mesh_net_send(net_tx, seg, seg_sent);
err = bt_mesh_net_send(net_tx, seg, seg_sent, tx);
if (err) {
BT_ERR("Sending segment failed");
seg_tx_reset(tx);
@ -822,7 +823,8 @@ static inline s32_t ack_timeout(struct seg_rx *rx)
}
int bt_mesh_ctl_send(struct bt_mesh_net_tx *tx, u8_t ctl_op, void *data,
size_t data_len, u64_t *seq_auth, bt_mesh_adv_func_t cb)
size_t data_len, u64_t *seq_auth, bt_mesh_adv_func_t cb,
void *user_data)
{
struct net_buf *buf;
@ -838,8 +840,6 @@ int bt_mesh_ctl_send(struct bt_mesh_net_tx *tx, u8_t ctl_op, void *data,
return -ENOBUFS;
}
BT_MESH_ADV(buf)->addr = tx->ctx->addr;
net_buf_reserve(buf, BT_MESH_NET_HDR_LEN);
net_buf_add_u8(buf, TRANS_CTL_HDR(ctl_op, 0));
@ -858,7 +858,7 @@ int bt_mesh_ctl_send(struct bt_mesh_net_tx *tx, u8_t ctl_op, void *data,
}
}
return bt_mesh_net_send(tx, buf, cb);
return bt_mesh_net_send(tx, buf, cb, user_data);
}
static int send_ack(struct bt_mesh_subnet *sub, u16_t src, u16_t dst,
@ -898,7 +898,7 @@ static int send_ack(struct bt_mesh_subnet *sub, u16_t src, u16_t dst,
sys_put_be32(block, &buf[2]);
return bt_mesh_ctl_send(&tx, TRANS_CTL_OP_ACK, buf, sizeof(buf),
NULL, NULL);
NULL, NULL, NULL);
}
static void seg_rx_reset(struct seg_rx *rx)

View file

@ -83,7 +83,8 @@ bool bt_mesh_tx_in_progress(void);
void bt_mesh_rx_reset(void);
int bt_mesh_ctl_send(struct bt_mesh_net_tx *tx, u8_t ctl_op, void *data,
size_t data_len, u64_t *seq_auth, bt_mesh_adv_func_t cb);
size_t data_len, u64_t *seq_auth, bt_mesh_adv_func_t cb,
void *user_data);
int bt_mesh_trans_send(struct bt_mesh_net_tx *tx, struct net_buf_simple *msg,
bt_mesh_cb_t cb, void *cb_data);