Bluetooth: Mesh: Fix not sending all segments through the Friend Queue

The code was incorrectly bailing out with "return 0" rather than
continue. Also, it was incorrectly making a reference to
tx->seg[seg_o] since when a PDU goes through the friend queue we don't
use the usual retransmission mechanism.

Fixes: #17932

Signed-off-by: Johan Hedberg <johan.hedberg@intel.com>
This commit is contained in:
Johan Hedberg 2019-08-13 16:29:47 +03:00 committed by Johan Hedberg
commit 680d778f57

View file

@ -383,8 +383,6 @@ static int send_seg(struct bt_mesh_net_tx *net_tx, struct net_buf_simple *sdu,
net_buf_add_mem(seg, sdu->data, len);
net_buf_simple_pull(sdu, len);
tx->seg[seg_o] = net_buf_ref(seg);
if (IS_ENABLED(CONFIG_BT_MESH_FRIEND)) {
enum bt_mesh_friend_pdu_type type;
@ -402,10 +400,12 @@ static int send_seg(struct bt_mesh_net_tx *net_tx, struct net_buf_simple *sdu,
* out through the Friend Queue.
*/
net_buf_unref(seg);
return 0;
continue;
}
}
tx->seg[seg_o] = net_buf_ref(seg);
BT_DBG("Sending %u/%u", seg_o, tx->seg_n);
err = bt_mesh_net_send(net_tx, seg,
@ -418,6 +418,25 @@ static int send_seg(struct bt_mesh_net_tx *net_tx, struct net_buf_simple *sdu,
}
}
/* This can happen if segments only went into the Friend Queue */
if (IS_ENABLED(CONFIG_BT_MESH_FRIEND) && !tx->seg[0]) {
seg_tx_reset(tx);
/* If there was a callback notify sending immediately since
* there's no other way to track this (at least currently)
* with the Friend Queue.
*/
if (cb) {
if (cb->start) {
cb->start(0, 0, cb_data);
}
if (cb->end) {
cb->end(0, cb_data);
}
}
}
if (IS_ENABLED(CONFIG_BT_MESH_LOW_POWER) &&
bt_mesh_lpn_established()) {
bt_mesh_lpn_poll();