1// -*- mode:doc; -*- 2// vim: set syntax=asciidoc tw=0 3 4coap_async(3) 5============= 6:doctype: manpage 7:man source: coap_async 8:man version: @PACKAGE_VERSION@ 9:man manual: libcoap Manual 10 11NAME 12---- 13coap_async, 14coap_async_is_supported, 15coap_register_async, 16coap_async_trigger, 17coap_async_set_delay, 18coap_find_async, 19coap_free_async, 20coap_async_set_app_data, 21coap_async_get_app_data 22- Work with CoAP async support 23 24SYNOPSIS 25-------- 26*#include <coap@LIBCOAP_API_VERSION@/coap.h>* 27 28*int coap_async_is_supported(void);* 29 30*coap_async_t *coap_register_async(coap_session_t *_session_, 31const coap_pdu_t *_request_, coap_tick_t _delay_);* 32 33*void coap_async_trigger(coap_async_t *_async_);* 34 35*void coap_async_set_delay(coap_async_t *_async_, coap_tick_t _delay_);* 36 37*void coap_free_async(coap_session_t *_session_, coap_async_t *_async_);* 38 39*coap_async_t *coap_find_async(coap_session_t *_session_, 40coap_bin_const_t _token_);* 41 42*void coap_async_set_app_data(coap_async_t *_async_, void *_app_data_);* 43 44*void *coap_async_get_app_data(const coap_async_t *_async_);* 45 46For specific (D)TLS library support, link with 47*-lcoap-@LIBCOAP_API_VERSION@-notls*, *-lcoap-@LIBCOAP_API_VERSION@-gnutls*, 48*-lcoap-@LIBCOAP_API_VERSION@-openssl*, *-lcoap-@LIBCOAP_API_VERSION@-mbedtls* 49or *-lcoap-@LIBCOAP_API_VERSION@-tinydtls*. Otherwise, link with 50*-lcoap-@LIBCOAP_API_VERSION@* to get the default (D)TLS library support. 51 52DESCRIPTION 53----------- 54CoAP server responses can be piggybacked 55("https://rfc-editor.org/rfc/rfc7252#section-5.2.1[RFC7252 5.2.1. Piggybacked]") 56or separate 57("https://rfc-editor.org/rfc/rfc7252#section-5.2.2[RFC7252 5.2.2. Separate]"). 58 59For piggybacked responses, the response packet contains both the status and 60any data. 61 62For separate responses, there is an initial empty ACK response (Confirmable 63only - to stop the client re-transmitting the request) followed at a later time 64by a packet containing the status and any data. 65 66Usually responses are piggybacked, but this man page focuses on a mechanism 67for providing separate (async) support. 68 69*NOTE:* If a server is providing Proxy support, then the server code should 70return from the request handler with no response code set (i.e. respond with 71empty ACK) and then send back the response as provided by the upstream server 72when received, so no need to use the async support. 73 74FUNCTIONS 75--------- 76 77*Function: coap_async_is_supported()* 78 79The *coap_async_is_supported*() function is used to determine if there is 80async support or not compiled into libcoap. 81 82*Function: coap_register_async()* 83 84The *coap_register_async*() function is used to set up an asynchronous delayed 85request for the _request_ PDU associated with the _session_. The 86application request handler will get called with a copy of _request_ after 87_delay_ ticks which will then cause a response to be sent. If _delay_ is 0, 88then the application request handler will not get called until 89*coap_async_trigger*() or *coap_async_set_delay*() is called. 90 91*Function: coap_async_trigger()* 92 93The *coap_async_trigger*() function is used to expire the delay for the 94_async_ definition, so the application request handler is almost 95immediately called. 96 97*Function: coap_async_set_delay()* 98 99The *coap_async_set_delay*() function is used to update the remaining _delay_ 100before the application request handler is called for the _async_ definition. If 101_delay_ is set to 0, then the application request handler will not get called. 102 103An example of usage here is *coap_register_async*() sets _delay_ to 0, and 104then when the response is ready at an indeterminate point in the future, 105*coap_async_set_delay*() is called setting _delay_ to 1. Alternatively, 106*coap_async_trigger*() can be called. 107 108*Function: coap_free_async()* 109 110The *coap_free_async*() function is used to delete an _async_ definition. 111 112*Function: coap_find_async()* 113 114The *coap_find_async*() function is used to determine if there is an async 115definition based on the _session_ and token _token_. 116 117*Function: coap_async_set_app_data()* 118 119The *coap_async_set_app_data*() function is used to add in user defined 120_app_data_ to the _async_ definition. It is the responsibility of the 121application to release this data if appropriate. This would usually be done 122when the application request handler is called under 'async' control. 123 124*Function: coap_async_get_app_data()* 125 126The *coap_async_get_app_data*() function is used to retrieve any defined 127application data from the _async_ definition. 128 129RETURN VALUES 130------------- 131 132*coap_async_is_supported*() returns 1 if support is available, 0 otherwise. 133 134*coap_register_async*() and *coap_find_async*() return a pointer to an async 135definition or NULL if there is an error. 136 137*coap_async_get_app_data*() returns a pointer to the user defined data. 138 139EXAMPLES 140-------- 141*CoAP Server Non-Encrypted Setup* 142 143[source, c] 144---- 145#include <coap@LIBCOAP_API_VERSION@/coap.h> 146 147/* 148 * This example is used to demonstrate how to set up and use a "separate" 149 * response (empty ACK followed by data response at a later stage). 150 */ 151static void 152hnd_get_with_delay(coap_session_t *session, 153 coap_resource_t *resource, 154 coap_pdu_t *request, 155 coap_string_t *query, 156 coap_pdu_t *response) { 157 unsigned long delay = 5; 158 size_t size; 159 coap_async_t *async; 160 coap_bin_const_t token = coap_pdu_get_token(request); 161 162 /* 163 * See if this is the initial, or delayed request 164 */ 165 166 async = coap_find_async(session, token); 167 if (!async) { 168 /* Set up an async request to trigger delay in the future */ 169 if (query) { 170 const uint8_t *p = query->s; 171 172 delay = 0; 173 for (size = query->length; size; --size, ++p) 174 delay = delay * 10 + (*p - '0'); 175 if (delay == 0) { 176 coap_log_info("async: delay of 0 not supported\n"); 177 coap_pdu_set_code(response, COAP_RESPONSE_CODE_BAD_REQUEST); 178 return; 179 } 180 } 181 async = coap_register_async(session, 182 request, 183 COAP_TICKS_PER_SECOND * delay); 184 if (async == NULL) { 185 coap_pdu_set_code(response, COAP_RESPONSE_CODE_SERVICE_UNAVAILABLE); 186 return; 187 } 188 /* 189 * Not setting response code will cause empty ACK to be sent 190 * if Confirmable 191 */ 192 return; 193 } 194 /* async is set up, so this is the delayed request */ 195 196 /* remove any stored app data associated with 'async' here */ 197 198 /* Send back the appropriate data */ 199 coap_add_data_large_response(resource, session, request, response, 200 query, COAP_MEDIATYPE_TEXT_PLAIN, -1, 0, 4, 201 (const uint8_t *)"done", NULL, NULL); 202 coap_pdu_set_code(response, COAP_RESPONSE_CODE_CONTENT); 203 204 /* async is automatically removed by libcoap on return from this handler */ 205} 206 207---- 208 209SEE ALSO 210-------- 211*coap_handler*(3) 212 213FURTHER INFORMATION 214------------------- 215See 216 217"https://rfc-editor.org/rfc/rfc7252[RFC7252: The Constrained Application Protocol (CoAP)]" 218 219for further information. 220 221BUGS 222---- 223Please report bugs on the mailing list for libcoap: 224libcoap-developers@lists.sourceforge.net or raise an issue on GitHub at 225https://github.com/obgm/libcoap/issues 226 227AUTHORS 228------- 229The libcoap project <libcoap-developers@lists.sourceforge.net> 230