From 4c58ffb5ab7cfedf84a991cabe6b33eebd9a604c Mon Sep 17 00:00:00 2001 From: Michael Scott Date: Fri, 23 Mar 2018 10:49:44 -0700 Subject: [PATCH] net: lwm2m: dont release reply for duplicate block transfer During normal use, a CoAP packet can be resent due to network congestion and other causes. During block transfer the LwM2M client checks to make sure the block received is the one we expect and if not generates a "duplicate" warning. When this happened, we were releasing the reply handler and when the correct block was received the client would generate a "No handler" error. To avoid releasing the reply handler too early, let's set the coap_reply "user_data" field to an error condition (1). Then, once the reply processing is complete we can check the user_data field to be sure that it's ok to release the reply handler. Signed-off-by: Michael Scott --- subsys/net/lib/lwm2m/lwm2m_engine.c | 9 +++++++++ subsys/net/lib/lwm2m/lwm2m_engine.h | 4 ++++ subsys/net/lib/lwm2m/lwm2m_obj_firmware_pull.c | 3 +++ 3 files changed, 16 insertions(+) diff --git a/subsys/net/lib/lwm2m/lwm2m_engine.c b/subsys/net/lib/lwm2m/lwm2m_engine.c index 3d0371857f3..9434b834a79 100644 --- a/subsys/net/lib/lwm2m/lwm2m_engine.c +++ b/subsys/net/lib/lwm2m/lwm2m_engine.c @@ -1018,6 +1018,7 @@ int lwm2m_init_message(struct lwm2m_message *msg) goto cleanup; } + coap_reply_clear(msg->reply); coap_reply_init(msg->reply, &msg->cpkt); msg->reply->reply = msg->reply_cb; } @@ -3446,6 +3447,14 @@ void lwm2m_udp_receive(struct lwm2m_ctx *client_ctx, struct net_pkt *pkt, } if (reply || pending) { + /* skip release if reply->user_data has error condition */ + if (reply && reply->user_data != COAP_REPLY_STATUS_NONE) { + /* reset reply->user_data for next time */ + reply->user_data = (void *)COAP_REPLY_STATUS_NONE; + SYS_LOG_DBG("reply %p NOT removed", reply); + goto cleanup; + } + /* free up msg resources */ if (msg) { lwm2m_reset_message(msg, true); diff --git a/subsys/net/lib/lwm2m/lwm2m_engine.h b/subsys/net/lib/lwm2m/lwm2m_engine.h index 4555ce7216b..135b9eabb3d 100644 --- a/subsys/net/lib/lwm2m/lwm2m_engine.h +++ b/subsys/net/lib/lwm2m/lwm2m_engine.h @@ -40,6 +40,10 @@ /* length of time in milliseconds to wait for buffer allocations */ #define BUF_ALLOC_TIMEOUT K_SECONDS(1) +/* coap reply status */ +#define COAP_REPLY_STATUS_NONE 0 +#define COAP_REPLY_STATUS_ERROR 1 + struct lwm2m_message; /* Establish a message timeout callback */ diff --git a/subsys/net/lib/lwm2m/lwm2m_obj_firmware_pull.c b/subsys/net/lib/lwm2m/lwm2m_obj_firmware_pull.c index fbab08d7a38..043b5f7761a 100644 --- a/subsys/net/lib/lwm2m/lwm2m_obj_firmware_pull.c +++ b/subsys/net/lib/lwm2m/lwm2m_obj_firmware_pull.c @@ -308,6 +308,9 @@ do_firmware_transfer_reply_cb(const struct coap_packet *response, /* restore main firmware block context */ memcpy(&firmware_block_ctx, &received_block_ctx, sizeof(firmware_block_ctx)); + + /* set reply->user_data to error to avoid releasing */ + reply->user_data = (void *)COAP_REPLY_STATUS_ERROR; return 0; }