From d80fa1497dca0147e71d0391f33fce4da37e16f5 Mon Sep 17 00:00:00 2001 From: Jon Shallow Date: Sat, 20 Dec 2025 11:03:56 +0000 Subject: [PATCH] Client: Remove (D)TLS / WebSocket startup call-back timing window Add in new functions coap_new_client_session3() coap_new_client_session_pki3() coap_new_client_session_psk3() coap_new_client_session_oscore3() coap_new_client_session_oscore_pki3() coap_new_client_session_oscore_psk3() which effectively does coap_session_set_app_data2() and coap_ws_set_host_request() early on in the session set up cycle. --- configure.ac | 2 +- examples/coap-client.c | 44 +++--- examples/coap-server.c | 6 +- examples/lwip/client-coap.c | 8 +- .../examples_libcoap_client/client_coap.c | 12 +- .../riot/tests_pkg_libcoap/libcoap-test.c | 8 +- examples/tiny.c | 2 +- examples/zephyr/client-src/src/main.c | 4 +- include/coap3/coap_dtls_internal.h | 2 +- include/coap3/coap_net.h | 2 +- include/coap3/coap_oscore.h | 129 ++++++++++++++++++ include/coap3/coap_oscore_internal.h | 91 +++++++++--- include/coap3/coap_session.h | 128 ++++++++++++++++- include/coap3/coap_session_internal.h | 83 ++++++++--- libcoap-3.map | 6 + libcoap-3.sym | 6 + man/Makefile.am | 12 +- man/coap_deprecated.txt.in | 79 ++++++++++- man/coap_endpoint_client.txt.in | 90 ++++++++---- man/coap_io.txt.in | 4 +- man/coap_oscore.txt.in | 73 +++++++--- ...oap_io_loop.txt.in => coap_threads.txt.in} | 69 ++++++++-- src/coap_oscore.c | 118 ++++++++++++---- src/coap_proxy.c | 36 +++-- src/coap_session.c | 116 +++++++++++++--- 25 files changed, 918 insertions(+), 212 deletions(-) rename man/{coap_io_loop.txt.in => coap_threads.txt.in} (76%) diff --git a/configure.ac b/configure.ac index 776e00d3..aa02d3eb 100644 --- a/configure.ac +++ b/configure.ac @@ -1362,7 +1362,6 @@ man/coap_endpoint_server.txt man/coap_handler.txt man/coap_init.txt man/coap_io.txt -man/coap_io_loop.txt man/coap_keepalive.txt man/coap_locking.txt man/coap_logging.txt @@ -1379,6 +1378,7 @@ man/coap_resource.txt man/coap_session.txt man/coap_string.txt man/coap_supported.txt +man/coap_threads.txt man/coap_tls_library.txt man/coap_uri.txt man/coap_websockets.txt diff --git a/examples/coap-client.c b/examples/coap-client.c index 7b9c91fd..368b9d8d 100644 --- a/examples/coap-client.c +++ b/examples/coap-client.c @@ -1689,6 +1689,11 @@ open_session(coap_context_t *ctx, const uint8_t *key, size_t key_len) { coap_session_t *session; + coap_str_const_t *ws_host = NULL; + + if (proto == COAP_PROTO_WS || proto == COAP_PROTO_WSS) { + ws_host = &uri.host; + } if (proto == COAP_PROTO_DTLS || proto == COAP_PROTO_TLS || proto == COAP_PROTO_WSS) { @@ -1697,44 +1702,41 @@ open_session(coap_context_t *ctx, /* Setup PKI session */ coap_dtls_pki_t *dtls_pki = setup_pki(ctx, COAP_DTLS_ROLE_CLIENT); if (doing_oscore) { - session = coap_new_client_session_oscore_pki(ctx, bind_addr, dst, - proto, dtls_pki, - oscore_conf); + session = coap_new_client_session_oscore_pki3(ctx, bind_addr, dst, + proto, dtls_pki, + oscore_conf, NULL, NULL, ws_host); } else - session = coap_new_client_session_pki(ctx, bind_addr, dst, proto, - dtls_pki); + session = coap_new_client_session_pki3(ctx, bind_addr, dst, proto, + dtls_pki, NULL, NULL, ws_host); } else if (identity || key) { /* Setup PSK session */ coap_dtls_cpsk_t *dtls_psk = setup_psk(identity, identity_len, key, key_len); if (doing_oscore) { - session = coap_new_client_session_oscore_psk(ctx, bind_addr, dst, - proto, dtls_psk, - oscore_conf); + session = coap_new_client_session_oscore_psk3(ctx, bind_addr, dst, + proto, dtls_psk, + oscore_conf, NULL, NULL, ws_host); } else - session = coap_new_client_session_psk2(ctx, bind_addr, dst, proto, - dtls_psk); + session = coap_new_client_session_psk3(ctx, bind_addr, dst, proto, + dtls_psk, NULL, NULL, ws_host); } else { /* No PKI or PSK defined, as encrypted, use PKI */ coap_dtls_pki_t *dtls_pki = setup_pki(ctx, COAP_DTLS_ROLE_CLIENT); if (doing_oscore) { - session = coap_new_client_session_oscore_pki(ctx, bind_addr, dst, - proto, dtls_pki, - oscore_conf); + session = coap_new_client_session_oscore_pki3(ctx, bind_addr, dst, + proto, dtls_pki, + oscore_conf, NULL, NULL, ws_host); } else - session = coap_new_client_session_pki(ctx, bind_addr, dst, proto, - dtls_pki); + session = coap_new_client_session_pki3(ctx, bind_addr, dst, proto, + dtls_pki, NULL, NULL, ws_host); } } else { /* Non-encrypted session */ if (doing_oscore) { - session = coap_new_client_session_oscore(ctx, bind_addr, dst, proto, - oscore_conf); + session = coap_new_client_session_oscore3(ctx, bind_addr, dst, proto, + oscore_conf, NULL, NULL, ws_host); } else - session = coap_new_client_session(ctx, bind_addr, dst, proto); - } - if (session && (proto == COAP_PROTO_WS || proto == COAP_PROTO_WSS)) { - coap_ws_set_host_request(session, &uri.host); + session = coap_new_client_session3(ctx, bind_addr, dst, proto, NULL, NULL, ws_host); } return session; } diff --git a/examples/coap-server.c b/examples/coap-server.c index 9b80cbf1..c9abedcb 100644 --- a/examples/coap-server.c +++ b/examples/coap-server.c @@ -1778,7 +1778,7 @@ do_call_home(coap_context_t *ctx) { case COAP_URI_SCHEME_COAP: case COAP_URI_SCHEME_COAP_TCP: case COAP_URI_SCHEME_COAP_WS: - session = coap_new_client_session(ctx, NULL, &dst, proto); + session = coap_new_client_session3(ctx, NULL, &dst, proto, NULL, NULL, NULL); break; case COAP_URI_SCHEME_COAPS: case COAP_URI_SCHEME_COAPS_TCP: @@ -1788,12 +1788,12 @@ do_call_home(coap_context_t *ctx) { /* Use our defined PKI certs (or NULL) */ coap_dtls_pki_t *dtls_pki = setup_pki(ctx, COAP_DTLS_ROLE_CLIENT, client_sni); - session = coap_new_client_session_pki(ctx, NULL, &dst, proto, dtls_pki); + session = coap_new_client_session_pki3(ctx, NULL, &dst, proto, dtls_pki, NULL, NULL, NULL); } else { /* Use our defined PSK */ coap_dtls_cpsk_t *dtls_cpsk = setup_cpsk(client_sni); - session = coap_new_client_session_psk2(ctx, NULL, &dst, proto, dtls_cpsk); + session = coap_new_client_session_psk3(ctx, NULL, &dst, proto, dtls_cpsk, NULL, NULL, NULL); } break; case COAP_URI_SCHEME_HTTP: diff --git a/examples/lwip/client-coap.c b/examples/lwip/client-coap.c index 450a804c..6366a9cf 100644 --- a/examples/lwip/client-coap.c +++ b/examples/lwip/client-coap.c @@ -192,11 +192,11 @@ client_coap_init(coap_lwip_input_wait_handler_t input_wait, void *input_arg, dtls_psk.psk_info.key.s = (const uint8_t *)use_psk; dtls_psk.psk_info.key.length = strlen(use_psk); - session = coap_new_client_session_psk2(main_coap_context, NULL, &dst, - COAP_PROTO_DTLS, &dtls_psk); + session = coap_new_client_session_psk3(main_coap_context, NULL, &dst, + COAP_PROTO_DTLS, &dtls_psk, NULL, NULL, NULL); } else { - session = coap_new_client_session(main_coap_context, NULL, &dst, - proto); + session = coap_new_client_session3(main_coap_context, NULL, &dst, + proto, NULL, NULL, NULL); } LWIP_ASSERT("Failed to create session", session != NULL); diff --git a/examples/riot/examples_libcoap_client/client_coap.c b/examples/riot/examples_libcoap_client/client_coap.c index 2594399d..329b3594 100644 --- a/examples/riot/examples_libcoap_client/client_coap.c +++ b/examples/riot/examples_libcoap_client/client_coap.c @@ -171,12 +171,12 @@ client_coap_init(int argc, char **argv) coap_context_set_block_mode(main_coap_context, COAP_BLOCK_USE_LIBCOAP); if (uri.scheme == COAP_URI_SCHEME_COAP) { - session = coap_new_client_session(main_coap_context, NULL, &dst, - COAP_PROTO_UDP); + session = coap_new_client_session3(main_coap_context, NULL, &dst, + COAP_PROTO_UDP, NULL, NULL, NULL); } else if (uri.scheme == COAP_URI_SCHEME_COAP_TCP) { - session = coap_new_client_session(main_coap_context, NULL, &dst, - COAP_PROTO_TCP); + session = coap_new_client_session3(main_coap_context, NULL, &dst, + COAP_PROTO_TCP, NULL, NULL, NULL); #if defined (COAP_USE_PSK) && defined(COAP_USE_PSK_ID) } else { @@ -192,8 +192,8 @@ client_coap_init(int argc, char **argv) dtls_psk.psk_info.key.s = (const uint8_t *)COAP_USE_PSK; dtls_psk.psk_info.key.length = strlen(COAP_USE_PSK); - session = coap_new_client_session_psk2(main_coap_context, NULL, &dst, - COAP_PROTO_DTLS, &dtls_psk); + session = coap_new_client_session_psk3(main_coap_context, NULL, &dst, + COAP_PROTO_DTLS, &dtls_psk, NULL, NULL, NULL); #else /* ! COAP_USE_PSK && ! COAP_USE_PSK_ID */ coap_log_err("CONFIG_LIBCOAP_USE_PSK and CONFIG_LIBCOAP_USE_PSK_ID not defined\n"); goto fail; diff --git a/examples/riot/tests_pkg_libcoap/libcoap-test.c b/examples/riot/tests_pkg_libcoap/libcoap-test.c index bbf435a0..65f530ad 100644 --- a/examples/riot/tests_pkg_libcoap/libcoap-test.c +++ b/examples/riot/tests_pkg_libcoap/libcoap-test.c @@ -205,8 +205,8 @@ coap_client_init(coap_context_t *ctx) } if (uri.scheme == COAP_URI_SCHEME_COAP) { - session = coap_new_client_session(ctx, NULL, &dst, - COAP_PROTO_UDP); + session = coap_new_client_session3(ctx, NULL, &dst, + COAP_PROTO_UDP, NULL, NULL, NULL); } else if (uri.scheme == COAP_URI_SCHEME_COAP_TCP) { goto fail; @@ -235,8 +235,8 @@ coap_client_init(coap_context_t *ctx) dtls_psk.psk_info.key.s = (const uint8_t *)COAP_USE_PSK; dtls_psk.psk_info.key.length = strlen(COAP_USE_PSK); - session = coap_new_client_session_psk2(ctx, NULL, &dst, - COAP_PROTO_DTLS, &dtls_psk); + session = coap_new_client_session_psk3(ctx, NULL, &dst, + COAP_PROTO_DTLS, &dtls_psk, NULL, NULL, NULL); #else /* ! COAP_USE_PSK && ! COAP_USE_PSK_ID */ coap_log_err("CONFIG_LIBCOAP_USE_PSK and CONFIG_LIBCOAP_USE_PSK_ID not defined\n"); goto fail; diff --git a/examples/tiny.c b/examples/tiny.c index 45ce6a2b..4c26d06e 100644 --- a/examples/tiny.c +++ b/examples/tiny.c @@ -114,7 +114,7 @@ get_session(coap_context_t *ctx, const char *group) { addr.size = rp->ai_addrlen; memcpy(&addr.addr, rp->ai_addr, rp->ai_addrlen); - session = coap_new_client_session(ctx, NULL, &addr, COAP_PROTO_UDP); + session = coap_new_client_session3(ctx, NULL, &addr, COAP_PROTO_UDP, NULL, NULL, NULL); if (!session) continue; diff --git a/examples/zephyr/client-src/src/main.c b/examples/zephyr/client-src/src/main.c index 9be310cb..9071b822 100644 --- a/examples/zephyr/client-src/src/main.c +++ b/examples/zephyr/client-src/src/main.c @@ -100,7 +100,7 @@ static int coap_client_init(coap_context_t *ctx) } if (uri.scheme == COAP_URI_SCHEME_COAP) { - session = coap_new_client_session(ctx, NULL, &dst, COAP_PROTO_UDP); + session = coap_new_client_session3(ctx, NULL, &dst, COAP_PROTO_UDP, NULL, NULL, NULL); } else if (uri.scheme == COAP_URI_SCHEME_COAP_TCP) { goto fail; } else if (uri.scheme == COAP_URI_SCHEME_COAPS_TCP) { @@ -125,7 +125,7 @@ static int coap_client_init(coap_context_t *ctx) dtls_psk.psk_info.key.s = (const uint8_t *)COAP_USE_PSK; dtls_psk.psk_info.key.length = strlen(COAP_USE_PSK); - session = coap_new_client_session_psk2(ctx, NULL, &dst, COAP_PROTO_DTLS, &dtls_psk); + session = coap_new_client_session_psk3(ctx, NULL, &dst, COAP_PROTO_DTLS, &dtls_psk, NULL, NULL, NULL); #else /* ! COAP_USE_PSK && ! COAP_USE_PSK_ID */ coap_log_err("CONFIG_LIBCOAP_USE_PSK and CONFIG_LIBCOAP_USE_PSK_ID not defined\n"); goto fail; diff --git a/include/coap3/coap_dtls_internal.h b/include/coap3/coap_dtls_internal.h index eae41944..78dd97b3 100644 --- a/include/coap3/coap_dtls_internal.h +++ b/include/coap3/coap_dtls_internal.h @@ -93,7 +93,7 @@ int coap_dtls_context_set_spsk(coap_context_t *coap_context, * * @param coap_context The CoAP context. * @param setup_data A structure containing setup data originally passed into - * coap_new_client_session_psk2_lkd(). + * coap_new_client_session_psk3_lkd(). * * @return @c 1 if successful, else @c 0. */ diff --git a/include/coap3/coap_net.h b/include/coap3/coap_net.h index 09a0454f..79d5ac63 100644 --- a/include/coap3/coap_net.h +++ b/include/coap3/coap_net.h @@ -548,7 +548,7 @@ COAP_API uint16_t coap_new_message_id(coap_session_t *session); COAP_API void coap_free_context(coap_context_t *context); /** - * @deprecated Use coap_context_set_app_data() instead. + * @deprecated Use coap_context_set_app_data2() instead. * * Stores @p data with the given CoAP context. This function * overwrites any value that has previously been stored with @p diff --git a/include/coap3/coap_oscore.h b/include/coap3/coap_oscore.h index 01cb60f6..a9ab4425 100644 --- a/include/coap3/coap_oscore.h +++ b/include/coap3/coap_oscore.h @@ -36,6 +36,8 @@ extern "C" { * Creates a new client session to the designated server, protecting the data * using OSCORE. * + * @deprecated Use coap_new_client_session_oscore3() instead. + * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL * to let the operating system choose a suitable local @@ -57,10 +59,52 @@ COAP_API coap_session_t *coap_new_client_session_oscore(coap_context_t *ctx, coap_proto_t proto, coap_oscore_conf_t *oscore_conf); +/** + * Creates a new client session to the designated server, protecting the data + * using OSCORE, along with app_data information (as per coap_session_set_app_data2()) + * and optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back in startup instead of doing + * coap_new_client_session_oscore(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_oscore(); + * coap_ws_set_host_request(); + * + * @param ctx The CoAP context. + * @param local_if Address of local interface. It is recommended to use NULL + * to let the operating system choose a suitable local + * interface. If an address is specified, the port number + * should be zero, which means that a free port is + * automatically selected. + * @param server The server's address. If the port number is zero, the default + * port for the protocol will be used. + * @param proto CoAP Protocol. + * @param oscore_conf OSCORE configuration information. This structure is + * freed off by this call. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release() + * to free. + */ +COAP_API coap_session_t *coap_new_client_session_oscore3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host); + /** * Creates a new client session to the designated server with PSK credentials * as well as protecting the data using OSCORE. * + * @deprecated Use coap_new_client_session_oscore_psk3() instead. + * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to * let the operating system choose a suitable local interface. @@ -83,10 +127,54 @@ COAP_API coap_session_t *coap_new_client_session_oscore_psk(coap_context_t *ctx, coap_dtls_cpsk_t *psk_data, coap_oscore_conf_t *oscore_conf); +/** + * Creates a new client session to the designated server, with PSK credentials + * protecting the data using OSCORE, along with app_data information (as per + * coap_session_set_app_data2()) and optional WebSockets host (as per + * coap_ws_set_host_request()) to remove timing window call-back in (D)TLS startup + * instead of doing + * coap_new_client_session_oscore_psk(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_oscore_psk(); + * coap_ws_set_host_request(); + * + * @param ctx The CoAP context. + * @param local_if Address of local interface. It is recommended to use NULL to + * let the operating system choose a suitable local interface. + * If an address is specified, the port number should be zero, + * which means that a free port is automatically selected. + * @param server The server's address. If the port number is zero, the default + * port for the protocol will be used. + * @param proto CoAP Protocol. + * @param psk_data PSK parameters. + * @param oscore_conf OSCORE configuration information. This structure is + * freed off by this call. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release() + * to free. + */ +COAP_API coap_session_t *coap_new_client_session_oscore_psk3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *psk_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host); + /** * Creates a new client session to the designated server with PKI credentials * as well as protecting the data using OSCORE. * + * @deprecated Use coap_new_client_session_oscore_pki3() instead. + * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to * let the operating system choose a suitable local interface. @@ -109,6 +197,47 @@ COAP_API coap_session_t *coap_new_client_session_oscore_pki(coap_context_t *ctx, coap_dtls_pki_t *pki_data, coap_oscore_conf_t *oscore_conf); +/** + * Creates a new client session to the designated server, with PKI credentials + * protecting the data using OSCORE, along with app_data information (as per + * coap_session_set_app_data2()) and optional WebSockets host (as per + * coap_ws_set_host_request()) to remove timing window call-back in (D)TLS startup + * instead of doing + * coap_new_client_session_oscore_pki(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_oscore_pki(); + * coap_ws_set_host_request(); + * + * @param ctx The CoAP context. + * @param local_if Address of local interface. It is recommended to use NULL to + * let the operating system choose a suitable local interface. + * If an address is specified, the port number should be zero, + * which means that a free port is automatically selected. + * @param server The server's address. If the port number is zero, the default + * port for the protocol will be used. + * @param proto CoAP Protocol. + * @param pki_data PKI parameters. + * @param oscore_conf OSCORE configuration information. This structure is + * freed off by this call. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release() + * to free. + */ +COAP_API coap_session_t *coap_new_client_session_oscore_pki3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *pki_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host); /** * Set the context's default OSCORE configuration for a server. * diff --git a/include/coap3/coap_oscore_internal.h b/include/coap3/coap_oscore_internal.h index 77b7f190..8189b798 100644 --- a/include/coap3/coap_oscore_internal.h +++ b/include/coap3/coap_oscore_internal.h @@ -199,7 +199,14 @@ int coap_delete_oscore_recipient_lkd(coap_context_t *context, /** * Creates a new client session to the designated server, protecting the data - * using OSCORE. + * using OSCORE, along with app_data information (as per coap_session_set_app_data2()) + * and optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back instead of doing + * coap_new_client_session_oscore(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_oscore(); + * coap_ws_set_host_request(); * * Note: This function must be called in the locked state. * @@ -214,19 +221,35 @@ int coap_delete_oscore_recipient_lkd(coap_context_t *context, * @param proto CoAP Protocol. * @param oscore_conf OSCORE configuration information. This structure is * freed off by this call. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. * * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() * to free. */ -coap_session_t *coap_new_client_session_oscore_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_oscore_conf_t *oscore_conf); +coap_session_t *coap_new_client_session_oscore3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host); /** - * Creates a new client session to the designated server with PKI credentials - * as well as protecting the data using OSCORE. + * Creates a new client session to the designated server, with PKI credentials + * protecting the data using OSCORE, along with app_data information (as per + * coap_session_set_app_data2()) and optional WebSockets host (as per + * coap_ws_set_host_request()) to remove timing window call-back in (D)TLS startup + * instead of doing + * coap_new_client_session_oscore_pki(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_oscore_pki(); + * coap_ws_set_host_request(); * * Note: This function must be called in the locked state. * @@ -241,20 +264,36 @@ coap_session_t *coap_new_client_session_oscore_lkd(coap_context_t *ctx, * @param pki_data PKI parameters. * @param oscore_conf OSCORE configuration information. This structure is * freed off by this call. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. * * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() * to free. */ -coap_session_t *coap_new_client_session_oscore_pki_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_dtls_pki_t *pki_data, - coap_oscore_conf_t *oscore_conf); +coap_session_t *coap_new_client_session_oscore_pki3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *pki_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host); /** - * Creates a new client session to the designated server with PSK credentials - * as well as protecting the data using OSCORE. + * Creates a new client session to the designated server, with PSK credentials + * protecting the data using OSCORE, along with app_data information (as per + * coap_session_set_app_data2()) and optional WebSockets host (as per + * coap_ws_set_host_request()) to remove timing window call-back in (D)TLS startup + * instead of doing + * coap_new_client_session_oscore_psk(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_oscore_psk(); + * coap_ws_set_host_request(); * * Note: This function must be called in the locked state. * @@ -269,16 +308,24 @@ coap_session_t *coap_new_client_session_oscore_pki_lkd(coap_context_t *ctx, * @param psk_data PSK parameters. * @param oscore_conf OSCORE configuration information. This structure is * freed off by this call. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. * * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() * to free. */ -coap_session_t *coap_new_client_session_oscore_psk_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_dtls_cpsk_t *psk_data, - coap_oscore_conf_t *oscore_conf); +coap_session_t *coap_new_client_session_oscore_psk3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *psk_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host); /** * Add in the specific Recipient ID into the OSCORE context (server only). diff --git a/include/coap3/coap_session.h b/include/coap3/coap_session.h index fedb2b07..19d300fa 100644 --- a/include/coap3/coap_session.h +++ b/include/coap3/coap_session.h @@ -310,6 +310,8 @@ COAP_API size_t coap_session_max_pdu_size(const coap_session_t *session); /** * Creates a new client session to the designated server. * + * @deprecated Use coap_new_client_session3() instead. + * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to let * the operating system choose a suitable local interface. If an @@ -327,10 +329,46 @@ COAP_API coap_session_t *coap_new_client_session(coap_context_t *ctx, coap_proto_t proto ); +/** + * Creates a new client session to the designated server, along with app_data + * information (as per coap_session_set_app_data2()) and optional WebSockets host + * (as per coap_ws_set_host_request()) to remove timing window call-back instead + * of doing + * coap_new_client_session(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session(); + * coap_ws_set_host_request(); + * + * @param ctx The CoAP context. + * @param local_if Address of local interface. It is recommended to use NULL to let + * the operating system choose a suitable local interface. If an + * address is specified, the port number should be zero, which means + * that a free port is automatically selected. + * @param server The server's address. If the port number is zero, the default port + * for the protocol will be used. + * @param proto Protocol. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release to free. + */ +COAP_API coap_session_t *coap_new_client_session3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host + ); + /** * Creates a new client session to the designated server with PSK credentials * - * @deprecated Use coap_new_client_session_psk2() instead. + * @deprecated Use coap_new_client_session_psk3() instead. * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to let @@ -356,7 +394,10 @@ COAP_API coap_session_t *coap_new_client_session_psk(coap_context_t *ctx, ); /** - * Creates a new client session to the designated server with PSK credentials + * Creates a new client session to the designated server with PSK credentials. + * + * @deprecated Use coap_new_client_session_psk3() instead. + * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to * let the operating system choose a suitable local interface. @@ -377,6 +418,45 @@ COAP_API coap_session_t *coap_new_client_session_psk2(coap_context_t *ctx, coap_dtls_cpsk_t *setup_data ); +/** + * Creates a new client session to the designated server, with PSK credentials + * along with app_data information (as per coap_session_set_app_data2()) and + * optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back in (D)TLS startup instead of doing + * coap_new_client_session_psk2(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_psk2(); + * coap_ws_set_host_request(); + * + * @param ctx The CoAP context. + * @param local_if Address of local interface. It is recommended to use NULL to + * let the operating system choose a suitable local interface. + * If an address is specified, the port number should be zero, + * which means that a free port is automatically selected. + * @param server The server's address. If the port number is zero, the default + * port for the protocol will be used. + * @param proto CoAP Protocol. + * @param setup_data PSK parameters. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() + * to free. + */ +coap_session_t *coap_new_client_session_psk3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host + ); + /** * Get the server session's current Identity Hint (PSK). * @@ -407,7 +487,10 @@ const coap_bin_const_t *coap_session_get_psk_key( const coap_session_t *session); /** - * Creates a new client session to the designated server with PKI credentials + * Creates a new client session to the designated server with PKI credentials. + * + * @deprecated Use coap_new_client_session_pki3() instead. + * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to * let the operating system choose a suitable local interface. @@ -428,6 +511,45 @@ COAP_API coap_session_t *coap_new_client_session_pki(coap_context_t *ctx, coap_dtls_pki_t *setup_data ); +/** + * Creates a new client session to the designated server, with PKI credentials + * along with app_data information (as per coap_session_set_app_data2()) and + * optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back in (D)TLS startup instead of doing + * coap_new_client_session_psk2(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_psk2(); + * coap_ws_set_host_request(); + * + * @param ctx The CoAP context. + * @param local_if Address of local interface. It is recommended to use NULL to + * let the operating system choose a suitable local interface. + * If an address is specified, the port number should be zero, + * which means that a free port is automatically selected. + * @param server The server's address. If the port number is zero, the default + * port for the protocol will be used. + * @param proto CoAP Protocol. + * @param setup_data PKI parameters. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() + * to free. + */ +COAP_API coap_session_t *coap_new_client_session_pki3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host + ); + /** * Initializes the token value to use as a starting point. * diff --git a/include/coap3/coap_session_internal.h b/include/coap3/coap_session_internal.h index c70c4a79..e1597504 100644 --- a/include/coap3/coap_session_internal.h +++ b/include/coap3/coap_session_internal.h @@ -531,7 +531,15 @@ size_t coap_session_max_pdu_rcv_size(const coap_session_t *session); size_t coap_session_max_pdu_size_lkd(const coap_session_t *session); /** - * Creates a new client session to the designated server. + * Creates a new client session to the designated server, with PSK credentials + * along with app_data information (as per coap_session_set_app_data2()) and + * optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back instead of doing + * coap_new_client_session(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session(); + * coap_ws_set_host_request(); * * Note: This function must be called in the locked state. * @@ -543,18 +551,33 @@ size_t coap_session_max_pdu_size_lkd(const coap_session_t *session); * @param server The server's address. If the port number is zero, the default port * for the protocol will be used. * @param proto Protocol. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. * * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd to free. */ -coap_session_t *coap_new_client_session_lkd( - coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto -); +coap_session_t *coap_new_client_session3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host + ); /** - * Creates a new client session to the designated server with PKI credentials + * Creates a new client session to the designated server, with PKI credentials + * along with app_data information (as per coap_session_set_app_data2()) and + * optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back in (D)TLS startup instead of doing + * coap_new_client_session_pki(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_pki(); + * coap_ws_set_host_request(); * * Note: This function must be called in the locked state. * @@ -567,24 +590,30 @@ coap_session_t *coap_new_client_session_lkd( * port for the protocol will be used. * @param proto CoAP Protocol. * @param setup_data PKI parameters. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. * * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() * to free. */ -coap_session_t *coap_new_client_session_pki_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_dtls_pki_t *setup_data - ); +coap_session_t *coap_new_client_session_pki3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host + ); /** * Creates a new client session to the designated server with PSK credentials * * Note: This function must be called in the locked state. * - * @deprecated Use coap_new_client_session_psk2_lkd() instead. - * * @param ctx The CoAP context. * @param local_if Address of local interface. It is recommended to use NULL to let * the operating system choose a suitable local interface. If an @@ -609,7 +638,15 @@ coap_session_t *coap_new_client_session_psk_lkd(coap_context_t *ctx, ); /** - * Creates a new client session to the designated server with PSK credentials + * Creates a new client session to the designated server, with PSK credentials + * along with app_data information (as per coap_session_set_app_data2()) and + * optional WebSockets host (as per coap_ws_set_host_request()) to remove timing + * window call-back in (D)TLS startup instead of doing + * coap_new_client_session_psk2(); + * coap_session_set_app_data2(); + * or + * coap_new_client_session_psk2(); + * coap_ws_set_host_request(); * * Note: This function must be called in the locked state. * @@ -622,15 +659,23 @@ coap_session_t *coap_new_client_session_psk_lkd(coap_context_t *ctx, * port for the protocol will be used. * @param proto CoAP Protocol. * @param setup_data PSK parameters. + * @param app_data The pointer to the application data to store or NULL. + * @param callback The optional release call-back for app_data on session + * removal or NULL. + * @param ws_host If proto is COAP_PROTO_WS or COAP_PROTO_WSS, then set the + * Host parameter accordingly. * * @return A new CoAP session or NULL if failed. Call coap_session_release_lkd() * to free. */ -coap_session_t *coap_new_client_session_psk2_lkd(coap_context_t *ctx, +coap_session_t *coap_new_client_session_psk3_lkd(coap_context_t *ctx, const coap_address_t *local_if, const coap_address_t *server, coap_proto_t proto, - coap_dtls_cpsk_t *setup_data + coap_dtls_cpsk_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host ); /** diff --git a/libcoap-3.map b/libcoap-3.map index f7e092b5..0f71dba2 100644 --- a/libcoap-3.map +++ b/libcoap-3.map @@ -160,13 +160,19 @@ global: coap_new_bin_const; coap_new_binary; coap_new_cache_entry; + coap_new_client_session3; coap_new_client_session; + coap_new_client_session_oscore3; coap_new_client_session_oscore; + coap_new_client_session_oscore_pki3; coap_new_client_session_oscore_pki; + coap_new_client_session_oscore_psk3; coap_new_client_session_oscore_psk; + coap_new_client_session_pki3; coap_new_client_session_pki; coap_new_client_session_proxy; coap_new_client_session_psk2; + coap_new_client_session_psk3; coap_new_client_session_psk; coap_new_context; coap_new_endpoint; diff --git a/libcoap-3.sym b/libcoap-3.sym index 8f0f2c46..a6856d37 100644 --- a/libcoap-3.sym +++ b/libcoap-3.sym @@ -159,13 +159,19 @@ coap_new_bin_const coap_new_binary coap_new_cache_entry coap_new_client_session +coap_new_client_session3 coap_new_client_session_oscore +coap_new_client_session_oscore3 coap_new_client_session_oscore_pki +coap_new_client_session_oscore_pki3 coap_new_client_session_oscore_psk +coap_new_client_session_oscore_psk3 coap_new_client_session_pki +coap_new_client_session_pki3 coap_new_client_session_proxy coap_new_client_session_psk coap_new_client_session_psk2 +coap_new_client_session_psk3 coap_new_context coap_new_endpoint coap_new_error_response diff --git a/man/Makefile.am b/man/Makefile.am index a73ec74d..738838f1 100644 --- a/man/Makefile.am +++ b/man/Makefile.am @@ -32,7 +32,6 @@ TXT3 = coap_address.txt \ coap_handler.txt \ coap_init.txt \ coap_io.txt \ - coap_io_loop.txt \ coap_keepalive.txt \ coap_locking.txt \ coap_logging.txt \ @@ -49,6 +48,7 @@ TXT3 = coap_address.txt \ coap_session.txt \ coap_string.txt \ coap_supported.txt \ + coap_threads.txt \ coap_tls_library.txt \ coap_uri.txt \ coap_websockets.txt @@ -132,8 +132,12 @@ install-man: install-man3 install-man5 install-man7 @echo ".so man3/coap_context.3" > coap_context_set_session_reconnect_time.3 @echo ".so man3/coap_context.3" > coap_context_set_session_reconnect_time2.3 @echo ".so man3/coap_context.3" > coap_register_option.3 - @echo ".so man3/coap_deprecated.3" > coap_set_app_data.3 - @echo ".so man3/coap_deprecated.3" > coap_get_app_data.3 + @echo ".so man3/coap_deprecated.3" > coap_new_client_session_oscore_psk.3 + @echo ".so man3/coap_deprecated.3" > coap_new_client_session_psk.3 + @echo ".so man3/coap_deprecated.3" > coap_new_client_session_psk2.3 + @echo ".so man3/coap_deprecated.3" > coap_new_client_session_pki.3 + @echo ".so man3/coap_deprecated.3" > coap_option_clrb.3 + @echo ".so man3/coap_deprecated.3" > coap_option_getb.3 @echo ".so man3/coap_deprecated.3" > coap_option_setb.3 @echo ".so man3/coap_deprecated.3" > coap_read.3 @echo ".so man3/coap_deprecated.3" > coap_register_handler.3 @@ -141,6 +145,8 @@ install-man: install-man3 install-man5 install-man7 @echo ".so man3/coap_deprecated.3" > coap_run_once.3 @echo ".so man3/coap_deprecated.3" > coap_set_event_handler.3 @echo ".so man3/coap_deprecated.3" > coap_write.3 + @echo ".so man3/coap_deprecated.3" > coap_get_app_data.3 + @echo ".so man3/coap_deprecated.3" > coap_set_app_data.3 @echo ".so man3/coap_deprecated.3" > coap_async_set_app_data.3 @echo ".so man3/coap_deprecated.3" > coap_cache_set_app_data.3 @echo ".so man3/coap_deprecated.3" > coap_context_set_app_data.3 diff --git a/man/coap_deprecated.txt.in b/man/coap_deprecated.txt.in index 274e20b0..756d326f 100644 --- a/man/coap_deprecated.txt.in +++ b/man/coap_deprecated.txt.in @@ -16,7 +16,13 @@ coap_context_get_csm_timeout, coap_context_set_csm_timeout, coap_context_set_psk, coap_encode_var_bytes, +coap_new_client_session, +coap_new_client_session_oscore, +coap_new_client_session_oscore_pki, +coap_new_client_session_oscore_psk, +coap_new_client_session_pki, coap_new_client_session_psk, +coap_new_client_session_psk2, coap_option_clrb, coap_option_getb, coap_option_setb, @@ -50,11 +56,37 @@ const uint8_t *_key_, size_t _key_len_);* *int coap_encode_var_bytes(uint8_t *_buffer_, unsigned int _value_);* +*coap_session_t *coap_new_client_session(coap_context_t *_context_, +const coap_address_t *_local_if_, const coap_address_t *_server_, +coap_proto_t _proto_);* + +*coap_session_t *coap_new_client_session_oscore(coap_context_t *_context_, +const coap_address_t *_local_if_, const coap_address_t *_server_, +coap_proto_t _proto_, coap_oscore_conf_t *_oscore_conf_);* + +*coap_session_t *coap_new_client_session_oscore_psk(coap_context_t *_context_, +const coap_address_t *_local_if_, const coap_address_t *_server_, +coap_proto_t _proto_, coap_dtls_cpsk_t *_psk_data_, +coap_oscore_conf_t *_oscore_conf_);* + +*coap_session_t *coap_new_client_session_oscore_pki(coap_context_t *_context_, +const coap_address_t *_local_if_, const coap_address_t *_server_, +coap_proto_t _proto_, coap_dtls_pki_t *_pki_data_, +coap_oscore_conf_t *_oscore_conf_);* + +*coap_session_t *coap_new_client_session_pki(coap_context_t *_context_, +const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t +_proto_, coap_dtls_pki_t *_setup_data_);* + *coap_session_t *coap_new_client_session_psk(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t _proto_, const char *_identity_, const uint8_t *_key_, unsigned _key_len_);* +*coap_session_t *coap_new_client_session_psk2(coap_context_t *_context_, +const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t +_proto_, coap_dtls_cpsk_t *_setup_data_);* + *int coap_option_clrb(coap_opt_filter_t *_filter_, uint16_t _type_);* *int coap_option_getb(coap_opt_filter_t *_filter_, uint16_t _type_);* @@ -135,11 +167,48 @@ by the use of the coap_dtls_spsk_t structure. The *coap_encode_var_bytes*() function is replaced by *coap_encode_var_safe*(3). +*Function: coap_new_client_session()* + +The *coap_new_client_session*() function is replaced by +*coap_new_client_session3*(3) which supports additional session app_data to +remove startup call-back timing issues. + +*Function: coap_new_client_session_oscore()* + +The *coap_new_client_session_oscore*() function is replaced by +*coap_new_client_session_oscore3*(3) which supports additional session app_data and +ws_host to remove startup call-back timing issues. + +*Function: coap_new_client_session_oscore_pki()* + +The *coap_new_client_session_oscore_pki*() function is replaced by +*coap_new_client_session_oscore_pki3*(3) which supports additional session app_data and +ws_host to remove startup call-back timing issues. + +*Function: coap_new_client_session_oscore_psk()* + +The *coap_new_client_session_oscore_psk*() function is replaced by +*coap_new_client_session_oscore_psk3*(3) which supports additional session app_data and +ws_host to remove startup call-back timing issues. + +*Function: coap_new_client_session_pki()* + +The *coap_new_client_session_pki*() function is replaced by +*coap_new_client_session_pki3*(3) which supports additional session app_data and +ws_host to remove startup call-back timing issues. + *Function: coap_new_client_session_psk()* The *coap_new_client_session_psk*() function is replaced by -*coap_new_client_session_psk2*(3) which gives additional PSK configuration capability -by the use of the coap_dtls_cpsk_t structure. +*coap_new_client_session_psk3*(3) which gives additional PSK configuration capability +by the use of the coap_dtls_cpsk_t structure along with additional session app_data and +ws_host to remove startup call-back timing issues. + +*Function: coap_new_client_session_psk2()* + +The *coap_new_client_session_psk2*() function is replaced by +*coap_new_client_session_psk3*(3) which supports additional session app_data and +ws_host to remove startup call-back timing issues. *Function: coap_option_clrb()* @@ -218,8 +287,10 @@ negotiation response from the peer. *coap_encode_var_bytes*() returns either the length of bytes encoded (which can be 0 when encoding 0) or 0 on failure. -*coap_new_client_session_psk*() returns a new session if success, NULL on -failure. +*coap_new_client_session*(), *coap_new_client_session_oscore*(), +*coap_new_client_session_oscore_psk*(), *coap_new_client_session_oscore_pki*(), +*coap_new_client_session_psk*(), *coap_new_client_session_psk2*() and +*coap_new_client_session_pki*() return a new session if success, NULL on failure. *coap_option_clrb*() returns 1 if bit was set, -1 otherwise. diff --git a/man/coap_endpoint_client.txt.in b/man/coap_endpoint_client.txt.in index 302a4ef6..bfd03873 100644 --- a/man/coap_endpoint_client.txt.in +++ b/man/coap_endpoint_client.txt.in @@ -11,9 +11,9 @@ coap_endpoint_client(3) NAME ---- coap_endpoint_client, -coap_new_client_session, -coap_new_client_session_psk2, -coap_new_client_session_pki, +coap_new_client_session3, +coap_new_client_session_psk3, +coap_new_client_session_pki3, coap_session_set_mtu, coap_session_max_pdu_size, coap_mcast_set_hops @@ -23,17 +23,20 @@ SYNOPSIS -------- *#include * -*coap_session_t *coap_new_client_session(coap_context_t *_context_, +*coap_session_t *coap_new_client_session3(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, -coap_proto_t _proto_);* +coap_proto_t _proto_, void *_app_data_, coap_app_data_free_callback_t _callback_, +coap_str_const_t *_ws_host_);* -*coap_session_t *coap_new_client_session_psk2(coap_context_t *_context_, +*coap_session_t *coap_new_client_session_psk3(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t -_proto_, coap_dtls_cpsk_t *_setup_data_);* +_proto_, coap_dtls_cpsk_t *_setup_data_, void *_app_data_, +coap_app_data_free_callback_t _callback_, coap_str_const_t *_ws_host_);* -*coap_session_t *coap_new_client_session_pki(coap_context_t *_context_, +*coap_session_t *coap_new_client_session_pki3(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t -_proto_, coap_dtls_pki_t *_setup_data_);* +_proto_, coap_dtls_pki_t *_setup_data_, void *_app_data_, +coap_app_data_free_callback_t _callback_, coap_str_const_t *_ws_host_);* *void coap_session_set_mtu(coap_session_t *_session_, unsigned _mtu_);* @@ -88,7 +91,7 @@ In principle the set-up sequence for CoAP client endpoints looks like ---- coap_new_context() coap_context_set_pki_root_cas() - if the root CAs need to be updated and using PKI -coap_new_client_session(), coap_new_client_session_pki() or coap_new_client_session_psk2() +coap_new_client_session3(), coap_new_client_session_pki3() or coap_new_client_session_psk3() ---- Multiple client endpoints and hence sessions are supported per _context_. @@ -136,9 +139,9 @@ unix domain path to connect to must be specified. FUNCTIONS --------- -*Function: coap_new_client_session()* +*Function: coap_new_client_session3()* -The *coap_new_client_session*() function creates a client endpoint for a +The *coap_new_client_session3*() function creates a client endpoint for a specific _context_ and initiates a new client session to the specified _server_ using the CoAP protocol _proto_ as defined above. If the port is set to 0 in _server_ (for AF_INET or AF_INET6), then the default CoAP port is used. @@ -150,13 +153,23 @@ appropriate *coap_address_t*. If _local_if_ is defined, the address families for _local_if_ and _server_ must be identical. The session will initially have a reference count of 1. +_app_data_ and _callback_ are added to the returned session early on in the +session create cycle to remove any potential timing issues on a multi-threaded +system. If not required, then these can be set to NULL. See +*coap_session_set_app_data2*() for further information. + +For _proto_ COAP_PROTO_WS or COAP_PROTO_WSS, _ws_host_ is added to the returned +session early on in the session create cycle to remove any potential timing +issues on a multi-threaded system. If not required, then this can be set to NULL. +See *coap_ws_set_host_request*(3) for further information. + To stop using a client session, the reference count must be decremented to 0 by calling *coap_session_release*(3). See *coap_session*(3). This will remove the client endpoint's _session_ and all its associated information. -*Function: coap_new_client_session_pki()* +*Function: coap_new_client_session_pki3()* -The *coap_new_client_session_pki*() function, for a specific _context_, is +The *coap_new_client_session_pki3*() function, for a specific _context_, is used to configure the (D)TLS context using the _setup_data_ variables as defined in the coap_dtls_pki_t structure in the newly created endpoint session - see *coap_encryption*(3). The connection is to the specified _server_ using @@ -170,13 +183,23 @@ appropriate *coap_address_t*. If _local_if_ is defined, the address families for _local_if_ and _server_ must be identical. The session will initially have a reference count of 1. +_app_data_ and _callback_ are added to the returned session early on in the +session create cycle to remove any potential timing issues on a multi-threaded +system. If not required, then these can be set to NULL. See +*coap_session_set_app_data2*() for further information. + +For _proto_ COAP_PROTO_WS or COAP_PROTO_WSS, _ws_host_ is added to the returned +session early on in the session create cycle to remove any potential timing +issues on a multi-threaded system. If not required, then this can be set to NULL. +See *coap_ws_set_host_request*(3) for further information. + To stop using a client session, the reference count must be decremented to 0 by calling *coap_session_release*(3). See *coap_session*(3). This will remove the client endpoint's _session_ and all its associated information. -*Function: coap_new_client_session_psk2()* +*Function: coap_new_client_session_psk3()* -The *coap_new_client_session_psk2*() function, for a specific _context_, is +The *coap_new_client_session_psk3*() function, for a specific _context_, is used to configure the (D)TLS context using the _setup_data_ variables as defined in the coap_dtls_cpsk_t structure in the newly created endpoint session - see *coap_encryption*(3). The connection is to the specified _server_ using @@ -190,6 +213,16 @@ appropriate *coap_address_t*. If _local_if_ is defined, the address families for _local_if_ and _server_ must be identical. The session will initially have a reference count of 1. +_app_data_ and _callback_ are added to the returned session early on in the +session create cycle to remove any potential timing issues on a multi-threaded +system. If not required, then these can be set to NULL. See +*coap_session_set_app_data2*() for further information. + +For _proto_ COAP_PROTO_WS or COAP_PROTO_WSS, _ws_host_ is added to the returned +session early on in the session create cycle to remove any potential timing +issues on a multi-threaded system. If not required, then this can be set to NULL. +See *coap_ws_set_host_request*(3) for further information. + To stop using a client session, the reference count must be decremented to 0 by calling *coap_session_release*(3). See *coap_session*(3). This will remove the client endpoint's _session_ and all its associated information. @@ -216,8 +249,8 @@ _session_. RETURN VALUES ------------- -*coap_new_client_session*(), *coap_new_client_session_psk2*(), -*coap_new_client_session_pki*() return a newly created client +*coap_new_client_session3*(), *coap_new_client_session_psk3*(), +*coap_new_client_session_pki3*() return a newly created client session or NULL if there is a creation failure. *coap_session_max_pdu_size*() returns the MTU size. @@ -253,7 +286,8 @@ setup_client_session(struct in_addr ip_address) { server.addr.sin.sin_addr = ip_address; server.addr.sin.sin_port = htons(5683); - session = coap_new_client_session(context, NULL, &server, COAP_PROTO_UDP); + session = coap_new_client_session3(context, NULL, &server, COAP_PROTO_UDP, + NULL, NULL, NULL); if (!session) { coap_free_context(context); return NULL; @@ -301,7 +335,8 @@ setup_client_session(const char *server_ud) { /* Only do this if you know it is safe to do so */ unlink(local.addr.cun.sun_path); - session = coap_new_client_session(context, &local, &server, COAP_PROTO_UDP); + session = coap_new_client_session3(context, &local, &server, COAP_PROTO_UDP, + NULL, NULL, NULL); if (!session) { coap_free_context(context); return NULL; @@ -399,8 +434,9 @@ setup_client_session_pki(const char *host, dtls_pki.pki_key.key.pem.public_cert = public_cert_file; dtls_pki.pki_key.key.pem.private_key = private_key_file; - session = coap_new_client_session_pki(context, NULL, &server, - COAP_PROTO_DTLS, &dtls_pki); + session = coap_new_client_session_pki3(context, NULL, &server, + COAP_PROTO_DTLS, &dtls_pki, + NULL, NULL, NULL); if (!session) { coap_free_context(context); return NULL; @@ -475,8 +511,9 @@ setup_client_session_psk(const char *host, dtls_psk.psk_info.identity.length = identity_len; dtls_psk.psk_info.key.s = key; dtls_psk.psk_info.key.length = key_len; - session = coap_new_client_session_psk2(context, NULL, &server, - COAP_PROTO_DTLS, &dtls_psk); + session = coap_new_client_session_psk3(context, NULL, &server, + COAP_PROTO_DTLS, &dtls_psk, + NULL, NULL, NULL); if (!session) { coap_free_context(context); return NULL; @@ -513,8 +550,9 @@ setup_client_session_dtls(struct in_addr ip_address) { server.addr.sin.sin_addr = ip_address; server.addr.sin.sin_port = htons(5683); - session = coap_new_client_session(context, NULL, &server, - COAP_PROTO_DTLS); + session = coap_new_client_session3(context, NULL, &server, + COAP_PROTO_DTLS, + NULL, NULL, NULL); if (!session) { coap_free_context(context); return NULL; diff --git a/man/coap_io.txt.in b/man/coap_io.txt.in index 34ec3631..29e848c6 100644 --- a/man/coap_io.txt.in +++ b/man/coap_io.txt.in @@ -137,8 +137,10 @@ _timeout_ms_ set to COAP_IO_NO_WAIT. + will then be using *epoll* internally to process all the file descriptors of the different sessions. -:NOTE:* With multi-threading protection enabled, it is possible to +*NOTE:* With multi-threading protection enabled, it is possible to call *coap_io_process*() from multiple threads to do some load balancing. +However, *coap_io_process*() must not be called from within a call-back +handler (as that may recursively call the same call-back handler). See EXAMPLES below. diff --git a/man/coap_oscore.txt.in b/man/coap_oscore.txt.in index 0af0e257..d18b2423 100644 --- a/man/coap_oscore.txt.in +++ b/man/coap_oscore.txt.in @@ -15,9 +15,9 @@ coap_new_oscore_conf, coap_delete_oscore_conf, coap_new_oscore_recipient, coap_delete_oscore_recipient, -coap_new_client_session_oscore, -coap_new_client_session_oscore_pki, -coap_new_client_session_oscore_psk, +coap_new_client_session_oscore3, +coap_new_client_session_oscore_pki3, +coap_new_client_session_oscore_psk3, coap_context_oscore_server - Work with CoAP OSCORE @@ -37,19 +37,22 @@ coap_bin_const_t *_recipient_id_);* *int coap_delete_oscore_recipient(coap_context_t *_context_, coap_bin_const_t *_recipient_id_);* -*coap_session_t *coap_new_client_session_oscore(coap_context_t *_context_, +*coap_session_t *coap_new_client_session_oscore3(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, -coap_proto_t _proto_, coap_oscore_conf_t *_oscore_conf_);* +coap_proto_t _proto_, coap_oscore_conf_t *_oscore_conf_, void *_app_data_, +coap_app_data_free_callback_t _callback_, coap_str_const_t *_ws_host_);* -*coap_session_t *coap_new_client_session_oscore_psk(coap_context_t *_context_, +*coap_session_t *coap_new_client_session_oscore_psk3(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t _proto_, coap_dtls_cpsk_t *_psk_data_, -coap_oscore_conf_t *_oscore_conf_);* +coap_oscore_conf_t *_oscore_conf_, void *_app_data_, +coap_app_data_free_callback_t _callback_, coap_str_const_t *_ws_host_);* -*coap_session_t *coap_new_client_session_oscore_pki(coap_context_t *_context_, +*coap_session_t *coap_new_client_session_oscore_pki3(coap_context_t *_context_, const coap_address_t *_local_if_, const coap_address_t *_server_, coap_proto_t _proto_, coap_dtls_pki_t *_pki_data_, -coap_oscore_conf_t *_oscore_conf_);* +coap_oscore_conf_t *_oscore_conf_, void *_app_data_, +coap_app_data_free_callback_t _callback_, coap_str_const_t *_ws_host_);* *int coap_context_oscore_server(coap_context_t *_context_, coap_oscore_conf_t *_oscore_conf_);* @@ -144,10 +147,10 @@ coap_oscore_conf_t structure _oscore_conf_ as returned by *coap_new_oscore_conf*(). Normally this function never needs to be called as _oscore_conf_ is freed off by the call the client or server setup functions. -*Function: coap_new_client_session_oscore()* +*Function: coap_new_client_session_oscore3()* -The *coap_new_client_session_oscore*() is basically the same as -*coap_new_client_session*(3), but has an additional parameter _oscore_conf_ +The *coap_new_client_session_oscore3*() is basically the same as +*coap_new_client_session3*(3), but has an additional parameter _oscore_conf_ that is created by *coap_new_oscore_conf*(). This function creates a client endpoint for a specific _context_ and initiates a new client session to the specified _server_ using the CoAP protocol _proto_ and OSCORE @@ -157,10 +160,20 @@ Normally _local_if_ would be set to NULL, but by specifying _local_if_ the source of the network session can be bound to a specific IP address or port. The session will initially have a reference count of 1. -*Function: coap_new_client_session_oscore_psk()* +_app_data_ and _callback_ are added to the returned session early on in the +session create cycle to remove any potential timing issues on a multi-threaded +system. If not required, then these can be set to NULL. See +*coap_session_set_app_data2*() for further information. -The *coap_new_client_session_oscore_psk*() is basically the same as -*coap_new_client_session_psk2*(3), but has an additional parameter +For _proto_ COAP_PROTO_WS or COAP_PROTO_WSS, _ws_host_ is added to the returned +session early on in the session create cycle to remove any potential timing +issues on a multi-threaded system. If not required, then this can be set to NULL. +See *coap_ws_set_host_request*(3) for further information. + +*Function: coap_new_client_session_oscore_psk3()* + +The *coap_new_client_session_oscore_psk3*() is basically the same as +*coap_new_client_session_psk3*(3), but has an additional parameter _oscore_conf_ that is created by *coap_new_oscore_conf*(). This function, for a specific _context_, is used to configure the TLS context using the _setup_data_ variables as defined in the coap_dtls_cpsk_t structure @@ -172,10 +185,20 @@ port is used. Normally _local_if_ would be set to NULL, but by specifying _local_if_ the source of the network session can be bound to a specific IP address or port. The session will initially have a reference count of 1. -*Function: coap_new_client_session_oscore_pki()* +_app_data_ and _callback_ are added to the returned session early on in the +session create cycle to remove any potential timing issues on a multi-threaded +system. If not required, then these can be set to NULL. See +*coap_session_set_app_data2*() for further information. -The *coap_new_client_session_oscore_pki*() is basically the same as -*coap_new_client_session_pki*(3), but has an additional parameter +For _proto_ COAP_PROTO_WS or COAP_PROTO_WSS, _ws_host_ is added to the returned +session early on in the session create cycle to remove any potential timing +issues on a multi-threaded system. If not required, then this can be set to NULL. +See *coap_ws_set_host_request*(3) for further information. + +*Function: coap_new_client_session_oscore_pki3()* + +The *coap_new_client_session_oscore_pki3*() is basically the same as +*coap_new_client_session_pki3*(3), but has an additional parameter _oscore_conf_ that is created by *coap_new_oscore_conf*(). This function, for a specific _context_, is used to configure the TLS context using the _setup_data_ variables as defined in the coap_dtls_pki_t structure in the @@ -187,6 +210,16 @@ Normally _local_if_ would be set to NULL, but by specifying _local_if_ the source of the network session can be bound to a specific IP address or port. The session will initially have a reference count of 1. +_app_data_ and _callback_ are added to the returned session early on in the +session create cycle to remove any potential timing issues on a multi-threaded +system. If not required, then these can be set to NULL. See +*coap_session_set_app_data2*() for further information. + +For _proto_ COAP_PROTO_WS or COAP_PROTO_WSS, _ws_host_ is added to the returned +session early on in the session create cycle to remove any potential timing +issues on a multi-threaded system. If not required, then this can be set to NULL. +See *coap_ws_set_host_request*(3) for further information. + *Function: coap_context_oscore_server()* The *coap_context_oscore_server*() function is used to enable the server to @@ -195,8 +228,8 @@ configure _oscore_conf_ (which is freed off by this call). RETURN VALUES ------------- -*coap_new_client_session_oscore*(), *coap_new_client_session_oscore_psk*() -and *coap_new_client_session_oscore_pki*() return a newly created +*coap_new_client_session_oscore3*(), *coap_new_client_session_oscore_psk3*() +and *coap_new_client_session_oscore_pki3*() return a newly created client session or NULL if there is a malloc or parameter failure. *coap_new_oscore_conf*() returns a _coap_oscore_conf_t_ diff --git a/man/coap_io_loop.txt.in b/man/coap_threads.txt.in similarity index 76% rename from man/coap_io_loop.txt.in rename to man/coap_threads.txt.in index f3c9cbf6..d6d5a852 100644 --- a/man/coap_io_loop.txt.in +++ b/man/coap_threads.txt.in @@ -1,21 +1,21 @@ // -*- mode:doc; -*- // vim: set syntax=asciidoc tw=0 -coap_io_loop(3) +coap_threads(3) =============== :doctype: manpage -:man source: coap_io_loop +:man source: coap_threads :man version: @PACKAGE_VERSION@ :man manual: libcoap Manual NAME ---- -coap_io_loop, +coap_threads, coap_io_process_loop, coap_io_process_terminate_loop, coap_io_process_configure_threads, coap_io_process_remove_threads -- Work with CoAP threads doing coap_io_process +- Work with CoAP threads SYNOPSIS -------- @@ -42,14 +42,59 @@ or *-lcoap-@LIBCOAP_API_VERSION@-tinydtls*. Otherwise, link with DESCRIPTION ----------- This man page focuses on setting up and supporting multiple threads, each one -invoking *coap_io_process*(3) in a loop. +invoking *coap_io_process*(3) in a loop. There is no reason why an +application cannot set up and manage its own threading model. -Each thread can receive a packet (a different packet for each thread), call the -appropriate application call-back handler and potentially be spending time of -consequence in that handler without blocking the reciept of other input traffic. +Each thread calling *coap_io_process*(3) can receive a packet (a different packet +for each thread), call the appropriate application call-back handler and +potentially be spending time of consequence in that handler without blocking the +reciept of other input traffic. -These functions should be called from the main thread. It is assumed that -thread-safe code has been enabled. +These above listed functions should be called from the main thread. It is +assumed that thread-safe code has been enabled. + +*CAUTION:* The thread interaction lock protection is done within the libcoap +library. There are several things that can cause thread interaction issues. + +Any application thread that is not executing in the libcoap library or in +a libcoap call-back function must not modify any libcoap structure other +than by calling a libcoap Public API as there is no locking protection. + +There are two types of libcoap call-back. + +The first type of call-back is executing under the libcoap library lock protections +and so changes can safely be made to any structure that libcoap is using including +invoking any libcoap Public API calls. + +The second type of call-back is executing without the libcoap lock protections and +so no mofications must take place other than by using the libcoap Public API. The +second type is used when there is a likelyhood that the call-back may block on an +external event and libcoap in general should not be blocked. + +The list of the second type of call-backs are set up by the following functions: + +[source, c] +---- +coap_io_process_loop() +coap_register_request_handler() +coap_register_dynamic_resource_handler() +coap_register_response_handler() +coap_register_proxy_response_handler() +coap_lwip_set_input_wait_handler() +---- + +*coap_io_process*(3) must not be called from within a call-back handler as +*coap_io_process*(3) may then recursively call the same call-back handler. + +Calling a Public API that initiates a process that will invoke a call-back +(potentially on a different thread) that requires external information to +be already set up may fail if this information is provided in a subsequent +Public API call (which may be done too late) sequentially done by the caller +of the initial Public API. An example of this is calling +*coap_new_client_session_psk2*(3) followed by *coap_session_set_app_data2*(3) +and the (D)TLS Identity call-cack is called before +*coap_session_set_app_data2*(3) completes. Use *coap_new_client_session_psk3*(3) +instead. FUNCTIONS --------- @@ -63,8 +108,8 @@ The thread calling *coap_io_process_loop*() will also be in a separate loop that is calling *coap_io_process*(3), optionally calling _main_loop_code_ (if not NULL) with argument _main_loop_code_arg_. For the thread calling *coap_io_process_loop*(), it will call _main_loop_code_ at least every -_timeout_ms_ milli-secs, the call to _main_loop_code_ start time aligned to -the nearest second. +_timeout_ms_ milli-secs, with the call to _main_loop_code_ start time is rounded +down to the nearest second if _timeout_ms_ is >= 1000. _context_ defines the context to associate the threads with. _thread_count_ is the number of threads to be running *coap_io_process*(3) which includes the diff --git a/src/coap_oscore.c b/src/coap_oscore.c index b96636be..1e5b4da9 100644 --- a/src/coap_oscore.c +++ b/src/coap_oscore.c @@ -71,19 +71,41 @@ coap_new_client_session_oscore(coap_context_t *ctx, coap_session_t *session; coap_lock_lock(return NULL); - session = coap_new_client_session_oscore_lkd(ctx, local_if, server, proto, oscore_conf); + session = coap_new_client_session_oscore3_lkd(ctx, local_if, server, proto, oscore_conf, NULL, + NULL, NULL); + coap_lock_unlock(); + return session; +} + +COAP_API coap_session_t * +coap_new_client_session_oscore3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { + coap_session_t *session; + + coap_lock_lock(return NULL); + session = coap_new_client_session_oscore3_lkd(ctx, local_if, server, proto, oscore_conf, app_data, + callback, ws_host); coap_lock_unlock(); return session; } coap_session_t * -coap_new_client_session_oscore_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_oscore_conf_t *oscore_conf) { +coap_new_client_session_oscore3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session = - coap_new_client_session_lkd(ctx, local_if, server, proto); + coap_new_client_session3_lkd(ctx, local_if, server, proto, app_data, callback, ws_host); if (!session) return NULL; @@ -105,23 +127,46 @@ coap_new_client_session_oscore_psk(coap_context_t *ctx, coap_session_t *session; coap_lock_lock(return NULL); - session = coap_new_client_session_oscore_psk_lkd(ctx, local_if, server, proto, psk_data, - oscore_conf); + session = coap_new_client_session_oscore_psk3_lkd(ctx, local_if, server, proto, psk_data, + oscore_conf, NULL, NULL, NULL); + coap_lock_unlock(); + return session; +} + +COAP_API coap_session_t * +coap_new_client_session_oscore_psk3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *psk_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { + coap_session_t *session; + + coap_lock_lock(return NULL); + session = coap_new_client_session_oscore_psk3_lkd(ctx, local_if, server, proto, psk_data, + oscore_conf, app_data, callback, ws_host); coap_lock_unlock(); return session; } coap_session_t * -coap_new_client_session_oscore_psk_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_dtls_cpsk_t *psk_data, - coap_oscore_conf_t *oscore_conf) { +coap_new_client_session_oscore_psk3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *psk_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session; coap_lock_check_locked(); - session = coap_new_client_session_psk2_lkd(ctx, local_if, server, proto, psk_data); + session = coap_new_client_session_psk3_lkd(ctx, local_if, server, proto, psk_data, + app_data, callback, ws_host); if (!session) return NULL; @@ -143,23 +188,46 @@ coap_new_client_session_oscore_pki(coap_context_t *ctx, coap_session_t *session; coap_lock_lock(return NULL); - session = coap_new_client_session_oscore_pki_lkd(ctx, local_if, server, proto, pki_data, - oscore_conf); + session = coap_new_client_session_oscore_pki3_lkd(ctx, local_if, server, proto, pki_data, + oscore_conf, NULL, NULL, NULL); + coap_lock_unlock(); + return session; +} + +COAP_API coap_session_t * +coap_new_client_session_oscore_pki3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *pki_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { + coap_session_t *session; + + coap_lock_lock(return NULL); + session = coap_new_client_session_oscore_pki3_lkd(ctx, local_if, server, proto, pki_data, + oscore_conf, app_data, callback, ws_host); coap_lock_unlock(); return session; } coap_session_t * -coap_new_client_session_oscore_pki_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_dtls_pki_t *pki_data, - coap_oscore_conf_t *oscore_conf) { +coap_new_client_session_oscore_pki3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *pki_data, + coap_oscore_conf_t *oscore_conf, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session; coap_lock_check_locked(); - session = coap_new_client_session_pki_lkd(ctx, local_if, server, proto, pki_data); + session = coap_new_client_session_pki3_lkd(ctx, local_if, server, proto, pki_data, + app_data, callback, ws_host); if (!session) return NULL; diff --git a/src/coap_proxy.c b/src/coap_proxy.c index 4836d5e4..dbfe6f96 100644 --- a/src/coap_proxy.c +++ b/src/coap_proxy.c @@ -644,12 +644,14 @@ coap_proxy_get_ongoing_session(coap_session_t *session, #if COAP_OSCORE_SUPPORT if (server_use.oscore_conf) { proxy_entry->ongoing = - coap_new_client_session_oscore_lkd(context, local_addr, &dst, - proto, server_use.oscore_conf); + coap_new_client_session_oscore3_lkd(context, local_addr, &dst, + proto, server_use.oscore_conf, + NULL, NULL, NULL); } else { #endif /* COAP_OSCORE_SUPPORT */ proxy_entry->ongoing = - coap_new_client_session_lkd(context, local_addr, &dst, proto); + coap_new_client_session3_lkd(context, local_addr, &dst, proto, + NULL, NULL, NULL); #if COAP_OSCORE_SUPPORT } #endif /* COAP_OSCORE_SUPPORT */ @@ -662,13 +664,17 @@ coap_proxy_get_ongoing_session(coap_session_t *session, if (server_use.dtls_pki) { server_use.dtls_pki->client_sni = client_sni; proxy_entry->ongoing = - coap_new_client_session_oscore_pki_lkd(context, local_addr, &dst, - proto, server_use.dtls_pki, server_use.oscore_conf); + coap_new_client_session_oscore_pki3_lkd(context, local_addr, &dst, + proto, server_use.dtls_pki, + server_use.oscore_conf, + NULL, NULL, NULL); } else if (server_use.dtls_cpsk) { server_use.dtls_cpsk->client_sni = client_sni; proxy_entry->ongoing = - coap_new_client_session_oscore_psk_lkd(context, local_addr, &dst, - proto, server_use.dtls_cpsk, server_use.oscore_conf); + coap_new_client_session_oscore_psk3_lkd(context, local_addr, &dst, + proto, server_use.dtls_cpsk, + server_use.oscore_conf, + NULL, NULL, NULL); } else { coap_log_warn("Proxy: (D)TLS not configured for secure session\n"); } @@ -678,17 +684,20 @@ coap_proxy_get_ongoing_session(coap_session_t *session, if (server_use.dtls_pki) { server_use.dtls_pki->client_sni = client_sni; proxy_entry->ongoing = - coap_new_client_session_pki_lkd(context, local_addr, &dst, - proto, server_use.dtls_pki); + coap_new_client_session_pki3_lkd(context, local_addr, &dst, + proto, server_use.dtls_pki, + NULL, NULL, NULL); } else if (server_use.dtls_cpsk) { server_use.dtls_cpsk->client_sni = client_sni; proxy_entry->ongoing = - coap_new_client_session_psk2_lkd(context, local_addr, &dst, - proto, server_use.dtls_cpsk); + coap_new_client_session_psk3_lkd(context, local_addr, &dst, + proto, server_use.dtls_cpsk, + NULL, NULL, NULL); } else { /* Using client anonymous PKI */ proxy_entry->ongoing = - coap_new_client_session_lkd(context, local_addr, &dst, proto); + coap_new_client_session3_lkd(context, local_addr, &dst, proto, + NULL, NULL, NULL); } #if COAP_OSCORE_SUPPORT } @@ -1613,7 +1622,8 @@ coap_new_client_session_proxy_lkd(coap_context_t *ctx, return NULL; } - session = coap_new_client_session_lkd(ctx, NULL, &info_list->addr, COAP_PROTO_UDP); + session = coap_new_client_session3_lkd(ctx, NULL, &info_list->addr, COAP_PROTO_UDP, + NULL, NULL, NULL); if (session) { session->server_list = server_list; diff --git a/src/coap_session.c b/src/coap_session.c index 0cee53a1..34b9a1e5 100644 --- a/src/coap_session.c +++ b/src/coap_session.c @@ -1459,7 +1459,10 @@ static coap_session_t * coap_session_create_client(coap_context_t *ctx, const coap_address_t *local_if, const coap_address_t *server, - coap_proto_t proto) { + coap_proto_t proto, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session = NULL; int default_port = COAP_DEFAULT_PORT; @@ -1520,6 +1523,16 @@ coap_session_create_client(coap_context_t *ctx, memcpy(&session->sock.lfunc, coap_layers_coap[proto], sizeof(session->sock.lfunc)); + session->app_data = app_data; + session->app_cb = app_data ? callback : NULL; +#if COAP_WS_SUPPORT + if (ws_host) { + session->ws_host = coap_new_str_const(ws_host->s, ws_host->length); + } +#else /* ! COAP_WS_SUPPORT */ + (void)ws_host; +#endif /* ! COAP_WS_SUPPORT */ + if (COAP_PROTO_NOT_RELIABLE(proto)) { coap_session_t *s, *rtmp; if (!coap_netif_dgrm_connect(session, local_if, server, default_port)) { @@ -1707,21 +1720,40 @@ coap_new_client_session(coap_context_t *ctx, coap_session_t *session; coap_lock_lock(return NULL); - session = coap_new_client_session_lkd(ctx, local_if, server, proto); + session = coap_new_client_session3_lkd(ctx, local_if, server, proto, NULL, NULL, NULL); + coap_lock_unlock(); + return session; +} + +COAP_API coap_session_t * +coap_new_client_session3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { + coap_session_t *session; + + coap_lock_lock(return NULL); + session = coap_new_client_session3_lkd(ctx, local_if, server, proto, app_data, callback, ws_host); coap_lock_unlock(); return session; } coap_session_t * -coap_new_client_session_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto) { +coap_new_client_session3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session; coap_lock_check_locked(); session = coap_session_create_client(ctx, local_if, server, - proto); + proto, app_data, callback, ws_host); if (session) { coap_log_debug("***%s: session %p: created outgoing session\n", coap_session_str(session), (void *)session); @@ -1766,8 +1798,8 @@ coap_new_client_session_psk_lkd(coap_context_t *ctx, setup_data.psk_info.key.length = key_len; } - return coap_new_client_session_psk2_lkd(ctx, local_if, server, - proto, &setup_data); + return coap_new_client_session_psk3_lkd(ctx, local_if, server, + proto, &setup_data, NULL, NULL, NULL); } /* @@ -1894,21 +1926,43 @@ coap_new_client_session_psk2(coap_context_t *ctx, coap_session_t *session; coap_lock_lock(return NULL); - session = coap_new_client_session_psk2_lkd(ctx, local_if, server, proto, setup_data); + session = coap_new_client_session_psk3_lkd(ctx, local_if, server, proto, setup_data, + NULL, NULL, NULL); + coap_lock_unlock(); + return session; +} + +COAP_API coap_session_t * +coap_new_client_session_psk3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { + coap_session_t *session; + + coap_lock_lock(return NULL); + session = coap_new_client_session_psk3_lkd(ctx, local_if, server, proto, + setup_data, app_data, callback, ws_host); coap_lock_unlock(); return session; } coap_session_t * -coap_new_client_session_psk2_lkd(coap_context_t *ctx, +coap_new_client_session_psk3_lkd(coap_context_t *ctx, const coap_address_t *local_if, const coap_address_t *server, coap_proto_t proto, - coap_dtls_cpsk_t *setup_data) { + coap_dtls_cpsk_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session; coap_lock_check_locked(); - session = coap_session_create_client(ctx, local_if, server, proto); + session = coap_session_create_client(ctx, local_if, server, proto, app_data, callback, ws_host); if (!session || !setup_data) return NULL; @@ -2082,17 +2136,39 @@ coap_new_client_session_pki(coap_context_t *ctx, coap_session_t *session; coap_lock_lock(return NULL); - session = coap_new_client_session_pki_lkd(ctx, local_if, server, proto, setup_data); + session = coap_new_client_session_pki3_lkd(ctx, local_if, server, proto, setup_data, + NULL, NULL, NULL); + coap_lock_unlock(); + return session; +} + +COAP_API coap_session_t * +coap_new_client_session_pki3(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { + coap_session_t *session; + + coap_lock_lock(return NULL); + session = coap_new_client_session_pki3_lkd(ctx, local_if, server, proto, setup_data, + app_data, callback, ws_host); coap_lock_unlock(); return session; } coap_session_t * -coap_new_client_session_pki_lkd(coap_context_t *ctx, - const coap_address_t *local_if, - const coap_address_t *server, - coap_proto_t proto, - coap_dtls_pki_t *setup_data) { +coap_new_client_session_pki3_lkd(coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *setup_data, + void *app_data, + coap_app_data_free_callback_t callback, + coap_str_const_t *ws_host) { coap_session_t *session; coap_dtls_pki_t l_setup_data; @@ -2107,7 +2183,7 @@ coap_new_client_session_pki_lkd(coap_context_t *ctx, l_setup_data = *setup_data; coap_sanitize_client_sni(&l_setup_data.client_sni); - session = coap_session_create_client(ctx, local_if, server, proto); + session = coap_session_create_client(ctx, local_if, server, proto, app_data, callback, ws_host); if (!session) { return NULL;