diff --git a/subsys/net/lib/lwm2m/Kconfig b/subsys/net/lib/lwm2m/Kconfig index 41ac5bcf1ce5048..d826e5cd599a5c5 100644 --- a/subsys/net/lib/lwm2m/Kconfig +++ b/subsys/net/lib/lwm2m/Kconfig @@ -83,6 +83,8 @@ config LWM2M_COAP_BLOCK_TRANSFER help LwM2M messages with a big body that exceed the block size will be split into blocks for sending. + To append CoAP ETag option into outgoing block transfers, CONFIG_SYS_HASH_FUNC32 should + be enabled. config LWM2M_CANCEL_OBSERVE_BY_PATH bool "Use path matching as fallback for cancel-observe" diff --git a/subsys/net/lib/lwm2m/lwm2m_message_handling.c b/subsys/net/lib/lwm2m/lwm2m_message_handling.c index da5858d464db4fd..da03cbce9ca21fa 100644 --- a/subsys/net/lib/lwm2m/lwm2m_message_handling.c +++ b/subsys/net/lib/lwm2m/lwm2m_message_handling.c @@ -33,6 +33,7 @@ LOG_MODULE_REGISTER(LOG_MODULE_NAME); #include #include #include +#include #if defined(CONFIG_LWM2M_DTLS_SUPPORT) #include @@ -376,6 +377,7 @@ STATIC int prepare_msg_for_send(struct lwm2m_message *msg) { int ret; uint16_t len; + const uint8_t *payload; /* save the big buffer for later use (splitting blocks) */ msg->body_encode_buffer = msg->cpkt; @@ -385,7 +387,7 @@ STATIC int prepare_msg_for_send(struct lwm2m_message *msg) msg->cpkt.offset = 0; msg->cpkt.max_len = MAX_PACKET_SIZE; - coap_packet_get_payload(&msg->body_encode_buffer, &len); + payload = coap_packet_get_payload(&msg->body_encode_buffer, &len); if (len <= CONFIG_LWM2M_COAP_MAX_MSG_SIZE) { /* copy the packet */ @@ -404,6 +406,16 @@ STATIC int prepare_msg_for_send(struct lwm2m_message *msg) NET_ASSERT(msg->out.block_ctx == NULL, "Expecting to have no context to release"); } else { + /* Before splitting the content, append Etag option to protect the integrity of + * the payload. + */ + if (IS_ENABLED(CONFIG_SYS_HASH_FUNC32)) { + uint32_t hash = sys_hash32(payload, len); + + coap_packet_append_option(&msg->body_encode_buffer, COAP_OPTION_ETAG, + (const uint8_t *)&hash, sizeof(hash)); + } + ret = build_msg_block_for_send(msg, 0); if (ret != 0) { return ret;