Commit ecc7ca1b authored by Lingao Meng's avatar Lingao Meng Committed by Anas Nashif
Browse files

Bluetooth: Mesh: Fix friend buf send end not called.



As frnd->last will keep reference, so that net buffer
destructor function will not be call.

Signed-off-by: default avatarLingao Meng <menglingao@xiaomi.com>
parent 86f94eba
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -40,7 +40,7 @@ const uint8_t bt_mesh_adv_type[BT_MESH_ADV_TYPES] = {

K_FIFO_DEFINE(bt_mesh_adv_queue);

void bt_mesh_adv_buf_destroy(struct net_buf *buf)
static void adv_buf_destroy(struct net_buf *buf)
{
	struct bt_mesh_adv adv = *BT_MESH_ADV(buf);

@@ -51,7 +51,7 @@ void bt_mesh_adv_buf_destroy(struct net_buf *buf)

NET_BUF_POOL_DEFINE(adv_buf_pool, CONFIG_BT_MESH_ADV_BUF_COUNT,
		    BT_MESH_ADV_DATA_SIZE, BT_MESH_ADV_USER_DATA_SIZE,
		    bt_mesh_adv_buf_destroy);
		    adv_buf_destroy);

static struct bt_mesh_adv adv_pool[CONFIG_BT_MESH_ADV_BUF_COUNT];

+0 −2
Original line number Diff line number Diff line
@@ -46,8 +46,6 @@ extern struct k_fifo bt_mesh_adv_queue;
/* Lookup table for Advertising data types for bt_mesh_adv_type: */
extern const uint8_t bt_mesh_adv_type[BT_MESH_ADV_TYPES];

void bt_mesh_adv_buf_destroy(struct net_buf *buf);

/* xmit_count: Number of retransmissions, i.e. 0 == 1 transmission */
struct net_buf *bt_mesh_adv_create(enum bt_mesh_adv_type type, uint8_t xmit,
				   k_timeout_t timeout);
+20 −15
Original line number Diff line number Diff line
@@ -32,8 +32,6 @@
#define FRIEND_BUF_COUNT    ((CONFIG_BT_MESH_FRIEND_QUEUE_SIZE + 1) * \
			     CONFIG_BT_MESH_FRIEND_LPN_COUNT)

#define FRIEND_ADV(buf) CONTAINER_OF(BT_MESH_ADV(buf), struct friend_adv, adv)

/* PDUs from Friend to the LPN should only be transmitted once with the
 * smallest possible interval (20ms).
 */
@@ -52,17 +50,18 @@ struct friend_pdu_info {
};

NET_BUF_POOL_FIXED_DEFINE(friend_buf_pool, FRIEND_BUF_COUNT,
			  BT_MESH_ADV_DATA_SIZE, bt_mesh_adv_buf_destroy);
			  BT_MESH_ADV_DATA_SIZE, NULL);

static struct friend_adv {
	struct bt_mesh_adv adv;
	uint16_t app_idx;
} adv_pool[FRIEND_BUF_COUNT];

static struct bt_mesh_adv *adv_alloc(int id)
#define FRIEND_ADV(buf) (*(struct friend_adv **)net_buf_user_data(buf))

static struct friend_adv *adv_alloc(int id)
{
	adv_pool[id].app_idx = BT_MESH_KEY_UNUSED;
	return &adv_pool[id].adv;
	return &adv_pool[id];
}

static bool friend_is_allocated(const struct bt_mesh_friend *frnd)
@@ -158,11 +157,6 @@ static void friend_clear(struct bt_mesh_friend *frnd)
	memset(frnd->cred, 0, sizeof(frnd->cred));

	if (frnd->last) {
		/* Cancel the sending if necessary */
		if (frnd->pending_buf) {
			BT_MESH_ADV(frnd->last)->busy = 0U;
		}

		net_buf_unref(frnd->last);
		frnd->last = NULL;
	}
@@ -317,13 +311,14 @@ static struct net_buf *create_friend_pdu(struct bt_mesh_friend *frnd,
{
	struct net_buf *buf;

	buf = bt_mesh_adv_create_from_pool(&friend_buf_pool, adv_alloc,
					   BT_MESH_ADV_DATA,
					   FRIEND_XMIT, K_NO_WAIT);

	buf = net_buf_alloc(&friend_buf_pool, K_NO_WAIT);
	if (!buf) {
		return NULL;
	}

	FRIEND_ADV(buf) = adv_alloc(net_buf_id(buf));

	net_buf_add_u8(buf, (info->iv_index & 1) << 7); /* Will be reset in encryption */

	if (info->ctl) {
@@ -1217,6 +1212,7 @@ static void friend_timeout(struct k_work *work)
		.start = buf_send_start,
		.end = buf_send_end,
	};
	struct net_buf *buf;
	uint8_t md;

	if (!friend_is_allocated(frnd)) {
@@ -1265,9 +1261,18 @@ static void friend_timeout(struct k_work *work)
	frnd->queue_size--;

send_last:
	buf = bt_mesh_adv_create(BT_MESH_ADV_DATA, FRIEND_XMIT, K_NO_WAIT);
	if (!buf) {
		BT_ERR("Unable to allocate friend adv buffer");
		return;
	}

	net_buf_add_mem(buf, frnd->last->data, frnd->last->len);

	frnd->pending_req = 0U;
	frnd->pending_buf = 1U;
	bt_mesh_adv_send(frnd->last, &buf_sent_cb, frnd);
	bt_mesh_adv_send(buf, &buf_sent_cb, frnd);
	net_buf_unref(buf);
}

static void subnet_evt(struct bt_mesh_subnet *sub, enum bt_mesh_key_evt evt)