From 19718fd6da47ee2d81bcaa2c05c4b0b62f2a294a Mon Sep 17 00:00:00 2001 From: Trond Einar Snekvik Date: Wed, 15 Jan 2020 16:45:11 +0100 Subject: [PATCH] Bluetooth: Mesh: Skip publish if update fails Allow models to skip a periodic publish interval by returning an error from the publish update callback. Previously, an error return from publish update would cancel periodic publishing. This can't be recovered from, and as such, no valid model implementation could return an error from this callback, and there was no way to skip a periodic publish. Signed-off-by: Trond Einar Snekvik --- include/bluetooth/mesh/access.h | 3 +++ subsys/bluetooth/mesh/access.c | 18 +++++++++++++----- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/include/bluetooth/mesh/access.h b/include/bluetooth/mesh/access.h index 3ffd49cdf04..8c8d23cdbc7 100644 --- a/include/bluetooth/mesh/access.h +++ b/include/bluetooth/mesh/access.h @@ -424,6 +424,9 @@ struct bt_mesh_model_pub { * @ref bt_mesh_model_pub.msg with a valid publication * message. * + * If the callback returns non-zero, the publication is skipped + * and will resume on the next periodic publishing interval. + * * @param mod The Model the Publication Context belogs to. * * @return Zero on success or (negative) error code otherwise. diff --git a/subsys/bluetooth/mesh/access.c b/subsys/bluetooth/mesh/access.c index 7c21ad846cb..099abd31c86 100644 --- a/subsys/bluetooth/mesh/access.c +++ b/subsys/bluetooth/mesh/access.c @@ -187,6 +187,14 @@ static int publish_retransmit(struct bt_mesh_model *mod) return bt_mesh_trans_send(&tx, &sdu, &pub_sent_cb, mod); } +static void publish_retransmit_end(int err, struct bt_mesh_model_pub *pub) +{ + /* Cancel all retransmits for this publish attempt */ + pub->count = 0U; + /* Make sure the publish timer gets reset */ + publish_sent(err, pub->mod); +} + static void mod_publish(struct k_work *work) { struct bt_mesh_model_pub *pub = CONTAINER_OF(work, @@ -224,7 +232,10 @@ static void mod_publish(struct k_work *work) err = pub->update(pub->mod); if (err) { - BT_ERR("Failed to update publication message"); + /* Cancel this publish attempt. */ + BT_DBG("Update failed, skipping publish (err: %d)", err); + pub->period_start = k_uptime_get_32(); + publish_retransmit_end(err, pub); return; } @@ -744,10 +755,7 @@ int bt_mesh_model_publish(struct bt_mesh_model *model) err = model_send(model, &tx, true, &sdu, &pub_sent_cb, model); if (err) { - /* Don't try retransmissions for this publish attempt */ - pub->count = 0U; - /* Make sure the publish timer gets reset */ - publish_sent(err, model); + publish_retransmit_end(err, pub); return err; }