From c6f965446136154217fbccfa2cfb4297553f2004 Mon Sep 17 00:00:00 2001 From: Benjamin Valentin Date: Fri, 28 Oct 2022 13:58:30 +0200 Subject: [PATCH 1/4] nanocoap: request context to coap_handle_req() --- sys/include/net/nanocoap.h | 9 ++++--- sys/net/application_layer/nanocoap/nanocoap.c | 27 ++++++++----------- .../nanocoap/nanocoap_internal.h | 2 +- sys/net/application_layer/nanocoap/sock.c | 6 ++++- 4 files changed, 22 insertions(+), 22 deletions(-) diff --git a/sys/include/net/nanocoap.h b/sys/include/net/nanocoap.h index c782ea2345..19298a3d65 100644 --- a/sys/include/net/nanocoap.h +++ b/sys/include/net/nanocoap.h @@ -353,8 +353,6 @@ uint32_t coap_request_ctx_get_tl_type(const coap_request_ctx_t *ctx); /** * @brief Get the remote endpoint from which the request was received * - * @note This is currently only implemented for GCoAP - * * @param[in] ctx The request context * * @return Remote endpoint from which the request originated @@ -1846,11 +1844,13 @@ ssize_t coap_build_reply(coap_pkt_t *pkt, unsigned code, * @param[in] pkt pointer to (parsed) CoAP packet * @param[out] resp_buf buffer for response * @param[in] resp_buf_len size of response buffer + * @param[in] ctx CoAP request context information * * @returns size of reply packet on success * @returns <0 on error */ -ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_len); +ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_len, + coap_request_ctx_t *ctx); /** * @brief Pass a coap request to a matching handler @@ -1861,6 +1861,7 @@ ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_le * @param[in] pkt pointer to (parsed) CoAP packet * @param[out] resp_buf buffer for response * @param[in] resp_buf_len size of response buffer + * @param[in] ctx CoAP request context information * @param[in] resources Array of coap endpoint resources * @param[in] resources_numof length of the coap endpoint resources * @@ -1868,7 +1869,7 @@ ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_le * @returns <0 on error */ ssize_t coap_tree_handler(coap_pkt_t *pkt, uint8_t *resp_buf, - unsigned resp_buf_len, + unsigned resp_buf_len, coap_request_ctx_t *ctx, const coap_resource_t *resources, size_t resources_numof); diff --git a/sys/net/application_layer/nanocoap/nanocoap.c b/sys/net/application_layer/nanocoap/nanocoap.c index 937b40568f..e877ce8ccf 100644 --- a/sys/net/application_layer/nanocoap/nanocoap.c +++ b/sys/net/application_layer/nanocoap/nanocoap.c @@ -414,8 +414,11 @@ bool coap_has_unprocessed_critical_options(const coap_pkt_t *pkt) return false; } -ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_len) +ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_len, + coap_request_ctx_t *ctx) { + assert(ctx); + if (coap_get_code_class(pkt) != COAP_REQ) { DEBUG("coap_handle_req(): not a request.\n"); return -EBADMSG; @@ -424,8 +427,8 @@ ssize_t coap_handle_req(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_le if (pkt->hdr->code == 0) { return coap_build_reply(pkt, COAP_CODE_EMPTY, resp_buf, resp_buf_len, 0); } - return coap_tree_handler(pkt, resp_buf, resp_buf_len, coap_resources, - coap_resources_numof); + return coap_tree_handler(pkt, resp_buf, resp_buf_len, ctx, + coap_resources, coap_resources_numof); } ssize_t coap_subtree_handler(coap_pkt_t *pkt, uint8_t *buf, size_t len, @@ -433,13 +436,12 @@ ssize_t coap_subtree_handler(coap_pkt_t *pkt, uint8_t *buf, size_t len, { assert(context); coap_resource_subtree_t *subtree = coap_request_ctx_get_context(context); - return coap_tree_handler(pkt, buf, len, subtree->resources, + return coap_tree_handler(pkt, buf, len, context, subtree->resources, subtree->resources_numof); } -ssize_t coap_tree_handler(coap_pkt_t *pkt, uint8_t *resp_buf, - unsigned resp_buf_len, - const coap_resource_t *resources, +ssize_t coap_tree_handler(coap_pkt_t *pkt, uint8_t *resp_buf, unsigned resp_buf_len, + coap_request_ctx_t *ctx, const coap_resource_t *resources, size_t resources_numof) { coap_method_flags_t method_flag = coap_method2flag(coap_get_code_detail(pkt)); @@ -461,10 +463,8 @@ ssize_t coap_tree_handler(coap_pkt_t *pkt, uint8_t *resp_buf, continue; } - coap_request_ctx_t ctx = { - .resource = resource, - }; - return resource->handler(pkt, resp_buf, resp_buf_len, &ctx); + ctx->resource = resource; + return resource->handler(pkt, resp_buf, resp_buf_len, ctx); } return coap_build_reply(pkt, COAP_CODE_404, resp_buf, resp_buf_len, 0); @@ -1282,10 +1282,5 @@ uint32_t coap_request_ctx_get_tl_type(const coap_request_ctx_t *ctx) const sock_udp_ep_t *coap_request_ctx_get_remote_udp(const coap_request_ctx_t *ctx) { -#ifdef MODULE_GCOAP return ctx->remote; -#else - (void)ctx; - return NULL; -#endif } diff --git a/sys/net/application_layer/nanocoap/nanocoap_internal.h b/sys/net/application_layer/nanocoap/nanocoap_internal.h index cada93135f..a9819c24bb 100644 --- a/sys/net/application_layer/nanocoap/nanocoap_internal.h +++ b/sys/net/application_layer/nanocoap/nanocoap_internal.h @@ -35,6 +35,7 @@ extern "C" { */ struct _coap_request_ctx { const coap_resource_t *resource; /**< resource of the request */ + sock_udp_ep_t *remote; /**< remote endpoint of the request */ #if defined(MODULE_GCOAP) || DOXYGEN /** * @brief transport the packet was received over @@ -43,7 +44,6 @@ struct _coap_request_ctx { * cyclically include the @ref net_gcoap header. */ uint32_t tl_type; - sock_udp_ep_t *remote; /**< remote endpoint of the request */ #endif }; diff --git a/sys/net/application_layer/nanocoap/sock.c b/sys/net/application_layer/nanocoap/sock.c index d440d2fff5..3261d16215 100644 --- a/sys/net/application_layer/nanocoap/sock.c +++ b/sys/net/application_layer/nanocoap/sock.c @@ -26,6 +26,7 @@ #include #include "atomic_utils.h" +#include "nanocoap_internal.h" #include "net/nanocoap_sock.h" #include "net/sock/util.h" #include "net/sock/udp.h" @@ -643,6 +644,9 @@ int nanocoap_server(sock_udp_ep_t *local, uint8_t *buf, size_t bufsize) { nanocoap_sock_t sock; sock_udp_ep_t remote; + coap_request_ctx_t ctx = { + .remote = &remote, + }; if (!local->port) { local->port = COAP_PORT; @@ -664,7 +668,7 @@ int nanocoap_server(sock_udp_ep_t *local, uint8_t *buf, size_t bufsize) DEBUG("error parsing packet\n"); continue; } - if ((res = coap_handle_req(&pkt, buf, bufsize)) > 0) { + if ((res = coap_handle_req(&pkt, buf, bufsize, &ctx)) > 0) { sock_udp_send(&sock, buf, res, &remote); } else { From 55e13a9d611feb85567612bcc610fd23fcae5518 Mon Sep 17 00:00:00 2001 From: Benjamin Valentin Date: Fri, 28 Oct 2022 14:16:13 +0200 Subject: [PATCH 2/4] nanocoap: add coap_request_ctx_init() --- sys/include/net/nanocoap.h | 27 +++++++++++++++++++ sys/net/application_layer/nanocoap/nanocoap.c | 9 +++++++ 2 files changed, 36 insertions(+) diff --git a/sys/include/net/nanocoap.h b/sys/include/net/nanocoap.h index 19298a3d65..8588d9249e 100644 --- a/sys/include/net/nanocoap.h +++ b/sys/include/net/nanocoap.h @@ -322,6 +322,33 @@ typedef const struct { const size_t resources_numof; /**< number of entries in array */ } coap_resource_subtree_t; +/** + * @brief Size of the CoAP request context struct + */ +#define COAP_REQUEST_CTX_SIZE (2 * sizeof(void *) + \ + IS_USED(MODULE_GCOAP) * sizeof(uint32_t)) + +/** + * @brief Define and initialize CoAP request context struct + * + * @param[in] ctx Name of the request context variable + * @param[in] remote Remote endpoint that made the request + */ +#define COAP_REQUEST_CTX_INIT(ctx, remote) \ + uint8_t ctx ## _buffer[COAP_REQUEST_CTX_SIZE]; \ + coap_request_ctx_t *ctx = (void *)ctx ## _buffer; \ + coap_request_ctx_init(ctx, remote) + +/** + * @brief Initialize CoAP request context + * Called by @ref COAP_REQUEST_CTX_INIT + * @internal + * + * @param[in] ctx Pointer to the request context to initialize + * @param[in] remote Remote endpoint that made the request + */ +void coap_request_ctx_init(coap_request_ctx_t *ctx, sock_udp_ep_t *remote); + /** * @brief Get resource path associated with a CoAP request * diff --git a/sys/net/application_layer/nanocoap/nanocoap.c b/sys/net/application_layer/nanocoap/nanocoap.c index e877ce8ccf..c9944dcf12 100644 --- a/sys/net/application_layer/nanocoap/nanocoap.c +++ b/sys/net/application_layer/nanocoap/nanocoap.c @@ -1260,6 +1260,15 @@ unsigned coap_get_len(coap_pkt_t *pkt) return pktlen; } +void coap_request_ctx_init(coap_request_ctx_t *ctx, sock_udp_ep_t *remote) +{ + static_assert(COAP_REQUEST_CTX_SIZE == sizeof(coap_request_ctx_t), + "COAP_REQUEST_CTX_SIZE define does not match actual size"); + + memset(ctx, 0, sizeof(*ctx)); + ctx->remote = remote; +} + const char *coap_request_ctx_get_path(const coap_request_ctx_t *ctx) { return ctx->resource->path; From fd42f72b208bad55b67e34c088275b1137c93dc6 Mon Sep 17 00:00:00 2001 From: Benjamin Valentin Date: Fri, 28 Oct 2022 14:16:40 +0200 Subject: [PATCH 3/4] tests/nanocoap_cli: provide coap_request_ctx_t --- tests/nanocoap_cli/nanocli_server.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/tests/nanocoap_cli/nanocli_server.c b/tests/nanocoap_cli/nanocli_server.c index 58a79c95e4..620fb59e65 100644 --- a/tests/nanocoap_cli/nanocli_server.c +++ b/tests/nanocoap_cli/nanocli_server.c @@ -59,11 +59,15 @@ static int _nanocoap_server(sock_udp_ep_t *local, uint8_t *buf, size_t bufsize, } else { coap_pkt_t pkt; + coap_request_ctx_t ctx = { + .remote = &remote, + }; + if (coap_parse(&pkt, (uint8_t *)buf, res) < 0) { DEBUG("nanocoap: error parsing packet\n"); continue; } - if ((res = coap_handle_req(&pkt, buf, bufsize)) > 0) { + if ((res = coap_handle_req(&pkt, buf, bufsize, &ctx)) > 0) { res = sock_udp_send(&sock, buf, res, &remote); } } From 8a11ca2f8715b6840e191eba815546f47be9b2fe Mon Sep 17 00:00:00 2001 From: Benjamin Valentin Date: Tue, 8 Nov 2022 19:27:45 +0100 Subject: [PATCH 4/4] nanocoap: don't hide coap_request_ctx_t content --- sys/include/net/nanocoap.h | 42 +++++++-------- sys/net/application_layer/gcoap/gcoap.c | 1 - sys/net/application_layer/nanocoap/nanocoap.c | 5 +- .../nanocoap/nanocoap_internal.h | 54 ------------------- sys/net/application_layer/nanocoap/sock.c | 1 - 5 files changed, 19 insertions(+), 84 deletions(-) delete mode 100644 sys/net/application_layer/nanocoap/nanocoap_internal.h diff --git a/sys/include/net/nanocoap.h b/sys/include/net/nanocoap.h index 8588d9249e..fc857ad05c 100644 --- a/sys/include/net/nanocoap.h +++ b/sys/include/net/nanocoap.h @@ -239,11 +239,6 @@ typedef struct { /** * @brief Forward declaration of internal CoAP resource request handler context */ -struct _coap_request_ctx; - -/** - * @brief CoAP resource request handler context - */ typedef struct _coap_request_ctx coap_request_ctx_t; /** @@ -322,33 +317,32 @@ typedef const struct { const size_t resources_numof; /**< number of entries in array */ } coap_resource_subtree_t; -/** - * @brief Size of the CoAP request context struct - */ -#define COAP_REQUEST_CTX_SIZE (2 * sizeof(void *) + \ - IS_USED(MODULE_GCOAP) * sizeof(uint32_t)) - -/** - * @brief Define and initialize CoAP request context struct - * - * @param[in] ctx Name of the request context variable - * @param[in] remote Remote endpoint that made the request - */ -#define COAP_REQUEST_CTX_INIT(ctx, remote) \ - uint8_t ctx ## _buffer[COAP_REQUEST_CTX_SIZE]; \ - coap_request_ctx_t *ctx = (void *)ctx ## _buffer; \ - coap_request_ctx_init(ctx, remote) - /** * @brief Initialize CoAP request context - * Called by @ref COAP_REQUEST_CTX_INIT - * @internal * * @param[in] ctx Pointer to the request context to initialize * @param[in] remote Remote endpoint that made the request */ void coap_request_ctx_init(coap_request_ctx_t *ctx, sock_udp_ep_t *remote); +/** + * @brief CoAP resource request handler context + * @internal + */ +struct _coap_request_ctx { + const coap_resource_t *resource; /**< resource of the request */ + sock_udp_ep_t *remote; /**< remote endpoint of the request */ +#if defined(MODULE_GCOAP) || DOXYGEN + /** + * @brief transport the packet was received over + * @see @ref gcoap_socket_type_t for values. + * @note @ref gcoap_socket_type_t can not be used, as this would + * cyclically include the @ref net_gcoap header. + */ + uint32_t tl_type; +#endif +}; + /** * @brief Get resource path associated with a CoAP request * diff --git a/sys/net/application_layer/gcoap/gcoap.c b/sys/net/application_layer/gcoap/gcoap.c index aaa0e1afba..aa7909de1e 100644 --- a/sys/net/application_layer/gcoap/gcoap.c +++ b/sys/net/application_layer/gcoap/gcoap.c @@ -29,7 +29,6 @@ #include "net/coap.h" #include "net/gcoap.h" #include "net/gcoap/forward_proxy.h" -#include "nanocoap_internal.h" #include "net/nanocoap/cache.h" #include "net/sock/async/event.h" #include "net/sock/util.h" diff --git a/sys/net/application_layer/nanocoap/nanocoap.c b/sys/net/application_layer/nanocoap/nanocoap.c index c9944dcf12..f768ffd8d4 100644 --- a/sys/net/application_layer/nanocoap/nanocoap.c +++ b/sys/net/application_layer/nanocoap/nanocoap.c @@ -27,7 +27,7 @@ #include #include "bitarithm.h" -#include "nanocoap_internal.h" +#include "net/nanocoap.h" #define ENABLE_DEBUG 0 #include "debug.h" @@ -1262,9 +1262,6 @@ unsigned coap_get_len(coap_pkt_t *pkt) void coap_request_ctx_init(coap_request_ctx_t *ctx, sock_udp_ep_t *remote) { - static_assert(COAP_REQUEST_CTX_SIZE == sizeof(coap_request_ctx_t), - "COAP_REQUEST_CTX_SIZE define does not match actual size"); - memset(ctx, 0, sizeof(*ctx)); ctx->remote = remote; } diff --git a/sys/net/application_layer/nanocoap/nanocoap_internal.h b/sys/net/application_layer/nanocoap/nanocoap_internal.h deleted file mode 100644 index a9819c24bb..0000000000 --- a/sys/net/application_layer/nanocoap/nanocoap_internal.h +++ /dev/null @@ -1,54 +0,0 @@ -/* - * Copyright (C) 2022 ML!PA Consulting GmbH - * - * This file is subject to the terms and conditions of the GNU Lesser - * General Public License v2.1. See the file LICENSE in the top level - * directory for more details. - */ - -/** - * @ingroup net_nanocoap - * @{ - * - * @file - * @brief NanoCoAP internals - * - * @author Benjamin Valentin - */ - -#ifndef NANOCOAP_INTERNAL_H -#define NANOCOAP_INTERNAL_H - -#include "net/nanocoap.h" -#if defined(MODULE_SOCK_UDP) || defined(DOXYGEN) -#include "net/sock/udp.h" -#else -typedef void sock_udp_ep_t; -#endif - -#ifdef __cplusplus -extern "C" { -#endif - -/** - * @brief Internal CoAP resource request handler context - */ -struct _coap_request_ctx { - const coap_resource_t *resource; /**< resource of the request */ - sock_udp_ep_t *remote; /**< remote endpoint of the request */ -#if defined(MODULE_GCOAP) || DOXYGEN - /** - * @brief transport the packet was received over - * @see @ref gcoap_socket_type_t for values. - * @note @ref gcoap_socket_type_t can not be used, as this would - * cyclically include the @ref net_gcoap header. - */ - uint32_t tl_type; -#endif -}; - -#ifdef __cplusplus -} -#endif -#endif /* NANOCOAP_INTERNAL_H */ -/** @} */ diff --git a/sys/net/application_layer/nanocoap/sock.c b/sys/net/application_layer/nanocoap/sock.c index 3261d16215..a0699215f5 100644 --- a/sys/net/application_layer/nanocoap/sock.c +++ b/sys/net/application_layer/nanocoap/sock.c @@ -26,7 +26,6 @@ #include #include "atomic_utils.h" -#include "nanocoap_internal.h" #include "net/nanocoap_sock.h" #include "net/sock/util.h" #include "net/sock/udp.h"