1 /*
2  * Copyright (c) 2017 Linaro Limited
3  * Copyright (c) 2017-2019 Foundries.io
4  *
5  * SPDX-License-Identifier: Apache-2.0
6  */
7 
8 /** @file lwm2m.h
9  *
10  * @brief LwM2M high-level API
11  *
12  * @details
13  * LwM2M high-level interface is defined in this header.
14  *
15  * @note The implementation assumes UDP module is enabled.
16  *
17  * @note For more information refer to Technical Specification
18  * OMA-TS-LightweightM2M_Core-V1_1_1-20190617-A
19  *
20  * @defgroup lwm2m_api LwM2M high-level API
21  * @since 1.9
22  * @version 0.8.0
23  * @ingroup networking
24  * @{
25  */
26 
27 #ifndef ZEPHYR_INCLUDE_NET_LWM2M_H_
28 #define ZEPHYR_INCLUDE_NET_LWM2M_H_
29 
30 #include <time.h>
31 #include <zephyr/kernel.h>
32 #include <zephyr/sys/mutex.h>
33 #include <zephyr/net/coap.h>
34 #include <zephyr/net/lwm2m_path.h>
35 
36 #ifdef __cplusplus
37 extern "C" {
38 #endif
39 
40 /**
41  * @name LwM2M Objects managed by OMA for LwM2M tech specification.
42  * Objects in this range have IDs from 0 to 1023.
43  * @{
44  */
45 
46 /* clang-format off */
47 #define LWM2M_OBJECT_SECURITY_ID                0  /**< Security object */
48 #define LWM2M_OBJECT_SERVER_ID                  1  /**< Server object */
49 #define LWM2M_OBJECT_ACCESS_CONTROL_ID          2  /**< Access Control object */
50 #define LWM2M_OBJECT_DEVICE_ID                  3  /**< Device object */
51 #define LWM2M_OBJECT_CONNECTIVITY_MONITORING_ID 4  /**< Connectivity Monitoring object */
52 #define LWM2M_OBJECT_FIRMWARE_ID                5  /**< Firmware object */
53 #define LWM2M_OBJECT_LOCATION_ID                6  /**< Location object */
54 #define LWM2M_OBJECT_CONNECTIVITY_STATISTICS_ID 7  /**< Connectivity Statistics object */
55 #define LWM2M_OBJECT_SOFTWARE_MANAGEMENT_ID     9  /**< Software Management object */
56 #define LWM2M_OBJECT_PORTFOLIO_ID               16 /**< Portfolio object */
57 #define LWM2M_OBJECT_BINARYAPPDATACONTAINER_ID  19 /**< Binary App Data Container object */
58 #define LWM2M_OBJECT_EVENT_LOG_ID               20 /**< Event Log object */
59 #define LWM2M_OBJECT_OSCORE_ID                  21 /**< OSCORE object */
60 #define LWM2M_OBJECT_GATEWAY_ID                 25 /**< Gateway object */
61 /* clang-format on */
62 
63 /** @} */
64 
65 /**
66  * @name LwM2M Objects produced by 3rd party Standards Development
67  * Organizations.
68  * Refer to the OMA LightweightM2M (LwM2M) Object and Resource Registry:
69  * http://www.openmobilealliance.org/wp/OMNA/LwM2M/LwM2MRegistry.html
70  * @{
71  */
72 
73 /* clang-format off */
74 #define IPSO_OBJECT_GENERIC_SENSOR_ID       3300 /**< IPSO Generic Sensor object */
75 #define IPSO_OBJECT_TEMP_SENSOR_ID          3303 /**< IPSO Temperature Sensor object */
76 #define IPSO_OBJECT_HUMIDITY_SENSOR_ID      3304 /**< IPSO Humidity Sensor object */
77 #define IPSO_OBJECT_LIGHT_CONTROL_ID        3311 /**< IPSO Light Control object */
78 #define IPSO_OBJECT_ACCELEROMETER_ID        3313 /**< IPSO Accelerometer object */
79 #define IPSO_OBJECT_VOLTAGE_SENSOR_ID       3316 /**< IPSO Voltage Sensor object */
80 #define IPSO_OBJECT_CURRENT_SENSOR_ID       3317 /**< IPSO Current Sensor object */
81 #define IPSO_OBJECT_PRESSURE_ID             3323 /**< IPSO Pressure Sensor object */
82 #define IPSO_OBJECT_BUZZER_ID               3338 /**< IPSO Buzzer object */
83 #define IPSO_OBJECT_TIMER_ID                3340 /**< IPSO Timer object */
84 #define IPSO_OBJECT_ONOFF_SWITCH_ID         3342 /**< IPSO On/Off Switch object */
85 #define IPSO_OBJECT_PUSH_BUTTON_ID          3347 /**< IPSO Push Button object */
86 #define UCIFI_OBJECT_BATTERY_ID             3411 /**< uCIFI Battery object */
87 #define IPSO_OBJECT_FILLING_LEVEL_SENSOR_ID 3435 /**< IPSO Filling Level Sensor object */
88 /* clang-format on */
89 
90 /** @} */
91 
92 /**
93  * @brief Callback function called when a socket error is encountered
94  *
95  * @param error Error code
96  */
97 typedef void (*lwm2m_socket_fault_cb_t)(int error);
98 
99 /** @brief LwM2M object path structure */
100 struct lwm2m_obj_path {
101 	uint16_t obj_id;         /**< Object ID */
102 	uint16_t obj_inst_id;    /**< Object instance ID */
103 	uint16_t res_id;         /**< Resource ID */
104 	uint16_t res_inst_id;    /**< Resource instance ID */
105 	uint8_t  level;          /**< Path level (0-4). Ex. 4 = resource instance. */
106 };
107 
108 /**
109  * @brief Observe callback events
110  */
111 enum lwm2m_observe_event {
112 	LWM2M_OBSERVE_EVENT_OBSERVER_ADDED,    /**< Observer added */
113 	LWM2M_OBSERVE_EVENT_OBSERVER_REMOVED,  /**< Observer removed */
114 	LWM2M_OBSERVE_EVENT_NOTIFY_ACK,        /**< Notification ACKed */
115 	LWM2M_OBSERVE_EVENT_NOTIFY_TIMEOUT,    /**< Notification timed out */
116 };
117 
118 /**
119  * @brief Observe callback indicating observer adds and deletes, and
120  *	  notification ACKs and timeouts
121  *
122  * @param[in] event Observer add/delete or notification ack/timeout
123  * @param[in] path LwM2M path
124  * @param[in] user_data Pointer to user_data buffer, as provided in
125  *			send_traceable_notification(). Used to determine for which
126  *			data the ACKed/timed out notification was.
127  */
128 typedef void (*lwm2m_observe_cb_t)(enum lwm2m_observe_event event, struct lwm2m_obj_path *path,
129 				   void *user_data);
130 
131 
132 struct lwm2m_ctx;
133 
134 /**
135  * @brief LwM2M RD client events
136  *
137  * LwM2M client events are passed back to the event_cb function in
138  * lwm2m_rd_client_start()
139  */
140 enum lwm2m_rd_client_event {
141 	/** Invalid event */
142 	LWM2M_RD_CLIENT_EVENT_NONE,
143 	/** Bootstrap registration failure */
144 	LWM2M_RD_CLIENT_EVENT_BOOTSTRAP_REG_FAILURE,
145 	/** Bootstrap registration complete */
146 	LWM2M_RD_CLIENT_EVENT_BOOTSTRAP_REG_COMPLETE,
147 	/** Bootstrap transfer complete */
148 	LWM2M_RD_CLIENT_EVENT_BOOTSTRAP_TRANSFER_COMPLETE,
149 	/** Registration failure */
150 	LWM2M_RD_CLIENT_EVENT_REGISTRATION_FAILURE,
151 	/** Registration complete */
152 	LWM2M_RD_CLIENT_EVENT_REGISTRATION_COMPLETE,
153 	/** Registration timeout */
154 	LWM2M_RD_CLIENT_EVENT_REG_TIMEOUT,
155 	/** Registration update complete */
156 	LWM2M_RD_CLIENT_EVENT_REG_UPDATE_COMPLETE,
157 	/** De-registration failure */
158 	LWM2M_RD_CLIENT_EVENT_DEREGISTER_FAILURE,
159 	/** Disconnected */
160 	LWM2M_RD_CLIENT_EVENT_DISCONNECT,
161 	/** Queue mode RX off */
162 	LWM2M_RD_CLIENT_EVENT_QUEUE_MODE_RX_OFF,
163 	/** Engine suspended */
164 	LWM2M_RD_CLIENT_EVENT_ENGINE_SUSPENDED,
165 	/** Network error */
166 	LWM2M_RD_CLIENT_EVENT_NETWORK_ERROR,
167 	/** Registration update */
168 	LWM2M_RD_CLIENT_EVENT_REG_UPDATE,
169 	/** De-register */
170 	LWM2M_RD_CLIENT_EVENT_DEREGISTER,
171 	/** Server disabled */
172 	LWM2M_RD_CLIENT_EVENT_SERVER_DISABLED,
173 };
174 
175 
176 /**
177  * @brief Asynchronous RD client event callback
178  *
179  * @param[in] ctx LwM2M context generating the event
180  * @param[in] event LwM2M RD client event code
181  */
182 typedef void (*lwm2m_ctx_event_cb_t)(struct lwm2m_ctx *ctx,
183 				     enum lwm2m_rd_client_event event);
184 
185 typedef int (*lwm2m_set_sockopt_cb_t)(struct lwm2m_ctx *client_ctx);
186 
187 /**
188  * @brief Different traffic states of the LwM2M socket.
189  *
190  * This information can be used to give hints for the network interface
191  * that can decide what kind of power management should be used.
192  *
193  * These hints are given from CoAP layer messages, so usage of DTLS might affect the
194  * actual number of expected datagrams.
195  */
196 enum lwm2m_socket_states {
197 	LWM2M_SOCKET_STATE_ONGOING,	 /**< Ongoing traffic is expected. */
198 	LWM2M_SOCKET_STATE_ONE_RESPONSE, /**< One response is expected for the next message. */
199 	LWM2M_SOCKET_STATE_LAST,	 /**< Next message is the last one. */
200 	LWM2M_SOCKET_STATE_NO_DATA,	 /**< No more data is expected. */
201 };
202 
203 /**
204  * @brief LwM2M context structure to maintain information for a single
205  * LwM2M connection.
206  */
207 struct lwm2m_ctx {
208 	/** Destination address storage */
209 	struct sockaddr remote_addr;
210 
211 	/** @cond INTERNAL_HIDDEN
212 	 * Private CoAP and networking structures + 1 is for RD Client own message
213 	 */
214 	struct coap_pending pendings[CONFIG_LWM2M_ENGINE_MAX_PENDING + 1];
215 	struct coap_reply replies[CONFIG_LWM2M_ENGINE_MAX_REPLIES + 1];
216 	sys_slist_t pending_sends;
217 #if defined(CONFIG_LWM2M_QUEUE_MODE_ENABLED)
218 	sys_slist_t queued_messages;
219 #endif
220 	sys_slist_t observer;
221 	struct k_mutex lock;
222 	/** @endcond */
223 
224 	/** A pointer to currently processed request, for internal LwM2M engine
225 	 *  use. The underlying type is ``struct lwm2m_message``, but since it's
226 	 *  declared in a private header and not exposed to the application,
227 	 *  it's stored as a void pointer.
228 	 */
229 	void *processed_req;
230 
231 #if defined(CONFIG_LWM2M_DTLS_SUPPORT) || defined(__DOXYGEN__)
232 	/**
233 	 * @name DTLS related information
234 	 * Available only when @kconfig{CONFIG_LWM2M_DTLS_SUPPORT} is enabled and
235 	 * @ref lwm2m_ctx.use_dtls is set to true.
236 	 * @{
237 	 */
238 	/** TLS tag is set by client as a reference used when the
239 	 *  LwM2M engine calls tls_credential_(add|delete)
240 	 */
241 	int tls_tag;
242 
243 	/** Destination hostname.
244 	 *  When MBEDTLS SNI is enabled socket must be set with destination
245 	 *  server hostname.
246 	 */
247 	char *desthostname;
248 	/** Destination hostname length */
249 	uint16_t desthostnamelen;
250 
251 	/** Custom load_credentials function.
252 	 *  Client can set load_credentials function as a way of overriding
253 	 *  the default behavior of load_tls_credential() in lwm2m_engine.c
254 	 */
255 	int (*load_credentials)(struct lwm2m_ctx *client_ctx);
256 	/** @} */
257 #endif
258 	/** Custom socket options.
259 	 * Client can override default socket options by providing
260 	 * a callback that is called after a socket is created and before
261 	 * connect.
262 	 */
263 	lwm2m_set_sockopt_cb_t set_socketoptions;
264 
265 	/** Flag to indicate if context should use DTLS.
266 	 *  Enabled via the use of coaps:// protocol prefix in connection
267 	 *  information.
268 	 *  NOTE: requires @kconfig{CONFIG_LWM2M_DTLS_SUPPORT}
269 	 */
270 	bool use_dtls;
271 
272 	/**
273 	 * Flag to indicate that the socket connection is suspended.
274 	 * With queue mode, this will tell if there is a need to reconnect.
275 	 */
276 	bool connection_suspended;
277 
278 #if defined(CONFIG_LWM2M_QUEUE_MODE_ENABLED) || defined(__DOXYGEN__)
279 	/**
280 	 * Flag to indicate that the client is buffering Notifications and Send messages.
281 	 * True value buffer Notifications and Send messages.
282 	 */
283 	bool buffer_client_messages;
284 #endif
285 	/** Current index of Security Object used for server credentials */
286 	int sec_obj_inst;
287 
288 	/** Current index of Server Object used in this context. */
289 	int srv_obj_inst;
290 
291 	/** Flag to enable BOOTSTRAP interface. See Section "Bootstrap Interface"
292 	 *  of LwM2M Technical Specification for more information.
293 	 */
294 	bool bootstrap_mode;
295 
296 	/** Socket File Descriptor */
297 	int sock_fd;
298 
299 	/** Socket fault callback. LwM2M processing thread will call this
300 	 *  callback in case of socket errors on receive.
301 	 */
302 	lwm2m_socket_fault_cb_t fault_cb;
303 
304 	/** Callback for new or cancelled observations, and acknowledged or timed
305 	 *  out notifications.
306 	 */
307 	lwm2m_observe_cb_t observe_cb;
308 
309 	/** Callback for client events */
310 	lwm2m_ctx_event_cb_t event_cb;
311 
312 	/** Validation buffer. Used as a temporary buffer to decode the resource
313 	 *  value before validation. On successful validation, its content is
314 	 *  copied into the actual resource buffer.
315 	 */
316 	uint8_t validate_buf[CONFIG_LWM2M_ENGINE_VALIDATION_BUFFER_SIZE];
317 
318 	/**
319 	 * Callback to indicate transmission states.
320 	 * Client application may request LwM2M engine to indicate hints about
321 	 * transmission states and use that information to control various power
322 	 * saving modes.
323 	 */
324 	void (*set_socket_state)(int fd, enum lwm2m_socket_states state);
325 };
326 
327 /**
328  * LwM2M Time series data structure
329  */
330 struct lwm2m_time_series_elem {
331 	/** Cached data Unix timestamp */
332 	time_t t;
333 	/** Element value */
334 	union {
335 		/** @cond INTERNAL_HIDDEN */
336 		uint8_t u8;
337 		uint16_t u16;
338 		uint32_t u32;
339 		uint64_t u64;
340 		int8_t i8;
341 		int16_t i16;
342 		int32_t i32;
343 		int64_t i64;
344 		time_t time;
345 		double f;
346 		bool b;
347 		/** @endcond */
348 	};
349 };
350 
351 /**
352  * @brief Asynchronous callback to get a resource buffer and length.
353  *
354  * Prior to accessing the data buffer of a resource, the engine can
355  * use this callback to get the buffer pointer and length instead
356  * of using the resource's data buffer.
357  *
358  * The client or LwM2M objects can register a function of this type via:
359  * lwm2m_register_read_callback()
360  * lwm2m_register_pre_write_callback()
361  *
362  * @param[in] obj_inst_id Object instance ID generating the callback.
363  * @param[in] res_id Resource ID generating the callback.
364  * @param[in] res_inst_id Resource instance ID generating the callback
365  *                        (typically 0 for non-multi instance resources).
366  * @param[out] data_len Length of the data buffer.
367  *
368  * @return Callback returns a pointer to the data buffer or NULL for failure.
369  */
370 typedef void *(*lwm2m_engine_get_data_cb_t)(uint16_t obj_inst_id,
371 					    uint16_t res_id,
372 					    uint16_t res_inst_id,
373 					    size_t *data_len);
374 
375 /**
376  * @brief Asynchronous callback when data has been set to a resource buffer.
377  *
378  * After changing the data of a resource buffer, the LwM2M engine can
379  * make use of this callback to pass the data back to the client or LwM2M
380  * objects.
381  *
382  * On a block-wise transfers the handler is called multiple times with the data blocks
383  * and increasing offset. The last block has the last_block flag set to true.
384  * Beginning of the block transfer has the offset set to 0.
385  *
386  * A function of this type can be registered via:
387  * lwm2m_register_validate_callback()
388  * lwm2m_register_post_write_callback()
389  *
390  * @param[in] obj_inst_id Object instance ID generating the callback.
391  * @param[in] res_id Resource ID generating the callback.
392  * @param[in] res_inst_id Resource instance ID generating the callback
393  *                        (typically 0 for non-multi instance resources).
394  * @param[in] data Pointer to data.
395  * @param[in] data_len Length of the data.
396  * @param[in] last_block Flag used during block transfer to indicate the last
397  *                       block of data. For non-block transfers this is always
398  *                       false.
399  * @param[in] total_size Expected total size of data for a block transfer.
400  *                       For non-block transfers this is 0.
401  * @param[in] offset Offset of the data block. For non-block transfers this is always 0.
402  *
403  * @return Callback returns a negative error code (errno.h) indicating
404  *         reason of failure or 0 for success.
405  */
406 typedef int (*lwm2m_engine_set_data_cb_t)(uint16_t obj_inst_id,
407 					  uint16_t res_id, uint16_t res_inst_id,
408 					  uint8_t *data, uint16_t data_len,
409 					  bool last_block, size_t total_size, size_t offset);
410 
411 /**
412  * @brief Asynchronous event notification callback.
413  *
414  * Various object instance and resource-based events in the LwM2M engine
415  * can trigger a callback of this function type: object instance create,
416  * and object instance delete.
417  *
418  * Register a function of this type via:
419  * lwm2m_register_create_callback()
420  * lwm2m_register_delete_callback()
421  *
422  * @param[in] obj_inst_id Object instance ID generating the callback.
423  *
424  * @return Callback returns a negative error code (errno.h) indicating
425  *         reason of failure or 0 for success.
426  */
427 typedef int (*lwm2m_engine_user_cb_t)(uint16_t obj_inst_id);
428 
429 /**
430  * @brief Asynchronous execute notification callback.
431  *
432  * Resource executes trigger a callback of this type.
433  *
434  * Register a function of this type via:
435  * lwm2m_register_exec_callback()
436  *
437  * @param[in] obj_inst_id Object instance ID generating the callback.
438  * @param[in] args Pointer to execute arguments payload. (This can be
439  *            NULL if no arguments are provided)
440  * @param[in] args_len Length of argument payload in bytes.
441  *
442  * @return Callback returns a negative error code (errno.h) indicating
443  *         reason of failure or 0 for success.
444  */
445 typedef int (*lwm2m_engine_execute_cb_t)(uint16_t obj_inst_id,
446 					 uint8_t *args, uint16_t args_len);
447 
448 /**
449  * @name Power source types used for the "Available Power Sources" resource of
450  * the LwM2M Device object (3/0/6).
451  * @{
452  */
453 #define LWM2M_DEVICE_PWR_SRC_TYPE_DC_POWER	0 /**< DC power */
454 #define LWM2M_DEVICE_PWR_SRC_TYPE_BAT_INT	1 /**< Internal battery */
455 #define LWM2M_DEVICE_PWR_SRC_TYPE_BAT_EXT	2 /**< External battery */
456 #define LWM2M_DEVICE_PWR_SRC_TYPE_FUEL_CELL	3 /**< Fuel cell */
457 #define LWM2M_DEVICE_PWR_SRC_TYPE_PWR_OVER_ETH	4 /**< Power over Ethernet */
458 #define LWM2M_DEVICE_PWR_SRC_TYPE_USB		5 /**< USB */
459 #define LWM2M_DEVICE_PWR_SRC_TYPE_AC_POWER	6 /**< AC (mains) power */
460 #define LWM2M_DEVICE_PWR_SRC_TYPE_SOLAR		7 /**< Solar */
461 #define LWM2M_DEVICE_PWR_SRC_TYPE_MAX		8 /**< Max value for Available Power Source type */
462 /** @} */
463 
464 /**
465  * @name Error codes used for the "Error Code" resource of the LwM2M Device
466  * object.
467  * An LwM2M client can register one of the following error codes via
468  * the lwm2m_device_add_err() function.
469  * @{
470  */
471 #define LWM2M_DEVICE_ERROR_NONE			0 /**< No error */
472 #define LWM2M_DEVICE_ERROR_LOW_POWER		1 /**< Low battery power */
473 #define LWM2M_DEVICE_ERROR_EXT_POWER_SUPPLY_OFF	2 /**< External power supply off */
474 #define LWM2M_DEVICE_ERROR_GPS_FAILURE		3 /**< GPS module failure */
475 #define LWM2M_DEVICE_ERROR_LOW_SIGNAL_STRENGTH	4 /**< Low received signal strength */
476 #define LWM2M_DEVICE_ERROR_OUT_OF_MEMORY	5 /**< Out of memory */
477 #define LWM2M_DEVICE_ERROR_SMS_FAILURE		6 /**< SMS failure */
478 #define LWM2M_DEVICE_ERROR_NETWORK_FAILURE	7 /**< IP Connectivity failure */
479 #define LWM2M_DEVICE_ERROR_PERIPHERAL_FAILURE	8 /**< Peripheral malfunction */
480 
481 /** @} */
482 
483 /**
484  * @name Battery status codes used for the "Battery Status" resource (3/0/20)
485  *        of the LwM2M Device object.  As the battery status changes, an LwM2M
486  *        client can set one of the following codes via:
487  *        lwm2m_set_u8("3/0/20", [battery status])
488  * @{
489  */
490 #define LWM2M_DEVICE_BATTERY_STATUS_NORMAL	0 /**< The battery is operating normally and not on
491 						    *   power
492 						    */
493 #define LWM2M_DEVICE_BATTERY_STATUS_CHARGING	1 /**< The battery is currently charging */
494 #define LWM2M_DEVICE_BATTERY_STATUS_CHARGE_COMP	2 /**< The battery is fully charged and the charger
495 						    *   is still connected
496 						    */
497 #define LWM2M_DEVICE_BATTERY_STATUS_DAMAGED	3 /**< The battery has some problem */
498 #define LWM2M_DEVICE_BATTERY_STATUS_LOW		4 /**< The battery is low on charge */
499 #define LWM2M_DEVICE_BATTERY_STATUS_NOT_INST	5 /**< The battery is not installed */
500 #define LWM2M_DEVICE_BATTERY_STATUS_UNKNOWN	6 /**< The battery information is not available */
501 
502 /** @} */
503 
504 /**
505  * @brief Register a new error code with LwM2M Device object.
506  *
507  * @param[in] error_code New error code.
508  *
509  * @return 0 for success or negative in case of error.
510  */
511 int lwm2m_device_add_err(uint8_t error_code);
512 
513 
514 /**
515  * @name LWM2M Firmware Update object states
516  *
517  * An LwM2M client or the LwM2M Firmware Update object use the following codes
518  * to represent the LwM2M Firmware Update state (5/0/3).
519  * @{
520  */
521 
522 /**
523  * Idle. Before downloading or after successful updating.
524  */
525 #define STATE_IDLE		0
526 /**
527  * Downloading. The data sequence is being downloaded.
528  */
529 #define STATE_DOWNLOADING	1
530 /**
531  * Downloaded. The whole data sequence has been downloaded.
532  */
533 #define STATE_DOWNLOADED	2
534 /**
535  * Updating. The device is being updated.
536  */
537 #define STATE_UPDATING		3
538 
539 /** @} */
540 
541 /**
542  * @name LWM2M Firmware Update object result codes
543  *
544  * After processing a firmware update, the client sets the result via one of
545  * the following codes via lwm2m_set_u8("5/0/5", [result code])
546  * @{
547  */
548 
549 #define RESULT_DEFAULT		0	/**< Initial value */
550 #define RESULT_SUCCESS		1	/**< Firmware updated successfully */
551 #define RESULT_NO_STORAGE	2	/**< Not enough flash memory for the new firmware package */
552 #define RESULT_OUT_OF_MEM	3	/**< Out of RAM during downloading process */
553 #define RESULT_CONNECTION_LOST	4	/**< Connection lost during downloading process */
554 #define RESULT_INTEGRITY_FAILED	5	/**< Integrity check failure for new downloaded package */
555 #define RESULT_UNSUP_FW		6	/**< Unsupported package type */
556 #define RESULT_INVALID_URI	7	/**< Invalid URI */
557 #define RESULT_UPDATE_FAILED	8	/**< Firmware update failed */
558 #define RESULT_UNSUP_PROTO	9	/**< Unsupported protocol */
559 
560 /** @} */
561 
562 #if defined(CONFIG_LWM2M_FIRMWARE_UPDATE_OBJ_SUPPORT) || defined(__DOXYGEN__)
563 /**
564  * @brief Set data callback for firmware block transfer.
565  *
566  * LwM2M clients use this function to register a callback for receiving the
567  * block transfer data when performing a firmware update.
568  *
569  * @param[in] cb A callback function to receive the block transfer data
570  */
571 void lwm2m_firmware_set_write_cb(lwm2m_engine_set_data_cb_t cb);
572 
573 /**
574  * @brief Get the data callback for firmware block transfer writes.
575  *
576  * @return A registered callback function to receive the block transfer data
577  */
578 lwm2m_engine_set_data_cb_t lwm2m_firmware_get_write_cb(void);
579 
580 /**
581  * @brief Set data callback for firmware block transfer.
582  *
583  * LwM2M clients use this function to register a callback for receiving the
584  * block transfer data when performing a firmware update.
585  *
586  * @param[in] obj_inst_id Object instance ID
587  * @param[in] cb A callback function to receive the block transfer data
588  */
589 void lwm2m_firmware_set_write_cb_inst(uint16_t obj_inst_id, lwm2m_engine_set_data_cb_t cb);
590 
591 /**
592  * @brief Get the data callback for firmware block transfer writes.
593  *
594  * @param[in] obj_inst_id Object instance ID
595  * @return A registered callback function to receive the block transfer data
596  */
597 lwm2m_engine_set_data_cb_t lwm2m_firmware_get_write_cb_inst(uint16_t obj_inst_id);
598 
599 /**
600  * @brief Set callback for firmware update cancel.
601  *
602  * LwM2M clients use this function to register a callback to perform actions
603  * on firmware update cancel.
604  *
605  * @param[in] cb A callback function perform actions on firmware update cancel.
606  */
607 void lwm2m_firmware_set_cancel_cb(lwm2m_engine_user_cb_t cb);
608 
609 /**
610  * @brief Get a callback for firmware update cancel.
611  *
612  * @return A registered callback function perform actions on firmware update cancel.
613  */
614 lwm2m_engine_user_cb_t lwm2m_firmware_get_cancel_cb(void);
615 
616 /**
617  * @brief Set data callback for firmware update cancel.
618  *
619  * LwM2M clients use this function to register a callback to perform actions
620  * on firmware update cancel.
621  *
622  * @param[in] obj_inst_id Object instance ID
623  * @param[in] cb A callback function perform actions on firmware update cancel.
624  */
625 void lwm2m_firmware_set_cancel_cb_inst(uint16_t obj_inst_id, lwm2m_engine_user_cb_t cb);
626 
627 /**
628  * @brief Get the callback for firmware update cancel.
629  *
630  * @param[in] obj_inst_id Object instance ID
631  * @return A registered callback function perform actions on firmware update cancel.
632  */
633 lwm2m_engine_user_cb_t lwm2m_firmware_get_cancel_cb_inst(uint16_t obj_inst_id);
634 
635 /**
636  * @brief Set data callback to handle firmware update execute events.
637  *
638  * LwM2M clients use this function to register a callback for receiving the
639  * update resource "execute" operation on the LwM2M Firmware Update object.
640  *
641  * @param[in] cb A callback function to receive the execute event.
642  */
643 void lwm2m_firmware_set_update_cb(lwm2m_engine_execute_cb_t cb);
644 
645 /**
646  * @brief Get the event callback for firmware update execute events.
647  *
648  * @return A registered callback function to receive the execute event.
649  */
650 lwm2m_engine_execute_cb_t lwm2m_firmware_get_update_cb(void);
651 
652 /**
653  * @brief Set data callback to handle firmware update execute events.
654  *
655  * LwM2M clients use this function to register a callback for receiving the
656  * update resource "execute" operation on the LwM2M Firmware Update object.
657  *
658  * @param[in] obj_inst_id Object instance ID
659  * @param[in] cb A callback function to receive the execute event.
660  */
661 void lwm2m_firmware_set_update_cb_inst(uint16_t obj_inst_id, lwm2m_engine_execute_cb_t cb);
662 
663 /**
664  * @brief Get the event callback for firmware update execute events.
665  *
666  * @param[in] obj_inst_id Object instance ID
667  * @return A registered callback function to receive the execute event.
668  */
669 lwm2m_engine_execute_cb_t lwm2m_firmware_get_update_cb_inst(uint16_t obj_inst_id);
670 #endif
671 
672 #if defined(CONFIG_LWM2M_SWMGMT_OBJ_SUPPORT) || defined(__DOXYGEN__)
673 
674 /**
675  * @brief Set callback to handle software activation requests
676  *
677  * The callback will be executed when the LWM2M execute operation gets called
678  * on the corresponding object's Activate resource instance.
679  *
680  * @param[in] obj_inst_id The instance number to set the callback for.
681  * @param[in] cb A callback function to receive the execute event.
682  *
683  * @return 0 on success, otherwise a negative integer.
684  */
685 int lwm2m_swmgmt_set_activate_cb(uint16_t obj_inst_id, lwm2m_engine_execute_cb_t cb);
686 
687 /**
688  * @brief Set callback to handle software deactivation requests
689  *
690  * The callback will be executed when the LWM2M execute operation gets called
691  * on the corresponding object's Deactivate resource instance.
692  *
693  * @param[in] obj_inst_id The instance number to set the callback for.
694  * @param[in] cb A callback function to receive the execute event.
695  *
696  * @return 0 on success, otherwise a negative integer.
697  */
698 int lwm2m_swmgmt_set_deactivate_cb(uint16_t obj_inst_id, lwm2m_engine_execute_cb_t cb);
699 
700 /**
701  * @brief Set callback to handle software install requests
702  *
703  * The callback will be executed when the LWM2M execute operation gets called
704  * on the corresponding object's Install resource instance.
705  *
706  * @param[in] obj_inst_id The instance number to set the callback for.
707  * @param[in] cb A callback function to receive the execute event.
708  *
709  * @return 0 on success, otherwise a negative integer.
710  */
711 int lwm2m_swmgmt_set_install_package_cb(uint16_t obj_inst_id, lwm2m_engine_execute_cb_t cb);
712 
713 /**
714  * @brief Set callback to handle software uninstall requests
715  *
716  * The callback will be executed when the LWM2M execute operation gets called
717  * on the corresponding object's Uninstall resource instance.
718  *
719  * @param[in] obj_inst_id The instance number to set the callback for.
720  * @param[in] cb A callback function for handling the execute event.
721  *
722  * @return 0 on success, otherwise a negative integer.
723  */
724 int lwm2m_swmgmt_set_delete_package_cb(uint16_t obj_inst_id, lwm2m_engine_execute_cb_t cb);
725 
726 /**
727  * @brief Set callback to read software package
728  *
729  * The callback will be executed when the LWM2M read operation gets called
730  * on the corresponding object.
731  *
732  * @param[in] obj_inst_id The instance number to set the callback for.
733  * @param[in] cb A callback function for handling the read event.
734  *
735  * @return 0 on success, otherwise a negative integer.
736  */
737 int lwm2m_swmgmt_set_read_package_version_cb(uint16_t obj_inst_id, lwm2m_engine_get_data_cb_t cb);
738 
739 /**
740  * @brief Set data callback for software management block transfer.
741  *
742  * The callback will be executed when the LWM2M block write operation gets called
743  * on the corresponding object's resource instance.
744  *
745  * @param[in] obj_inst_id The instance number to set the callback for.
746  * @param[in] cb A callback function for handling the block write event.
747  *
748  * @return 0 on success, otherwise a negative integer.
749  */
750 int lwm2m_swmgmt_set_write_package_cb(uint16_t obj_inst_id, lwm2m_engine_set_data_cb_t cb);
751 
752 /**
753  * Function to be called when a Software Management object instance
754  * completed the Install operation.
755  *
756  * @param[in] obj_inst_id The Software Management object instance
757  * @param[in] error_code The result code of the operation. Zero on success
758  * otherwise it should be a negative integer.
759  *
760  * return 0 on success, otherwise a negative integer.
761  */
762 int lwm2m_swmgmt_install_completed(uint16_t obj_inst_id, int error_code);
763 
764 #endif
765 
766 #if defined(CONFIG_LWM2M_EVENT_LOG_OBJ_SUPPORT) || defined(__DOXYGEN__)
767 
768 /**
769  * @brief Set callback to read log data
770  *
771  * The callback will be executed when the LWM2M read operation gets called
772  * on the corresponding object.
773  *
774  * @param[in] cb A callback function for handling the read event.
775  */
776 void lwm2m_event_log_set_read_log_data_cb(lwm2m_engine_get_data_cb_t cb);
777 
778 #endif
779 
780 /**
781  * @brief Maximum value for Objlnk resource fields
782  */
783 #define LWM2M_OBJLNK_MAX_ID USHRT_MAX
784 
785 /**
786  * @brief LWM2M Objlnk resource type structure
787  */
788 struct lwm2m_objlnk {
789 	uint16_t obj_id;     /**< Object ID */
790 	uint16_t obj_inst;   /**< Object instance ID */
791 };
792 
793 /**
794  * @brief Change an observer's pmin value.
795  *
796  * LwM2M clients use this function to modify the pmin attribute
797  * for an observation being made.
798  * Example to update the pmin of a temperature sensor value being observed:
799  * lwm2m_update_observer_min_period(client_ctx, &LWM2M_OBJ(3303, 0, 5700), 5);
800  *
801  * @param[in] client_ctx LwM2M context
802  * @param[in] path LwM2M path as a struct
803  * @param[in] period_s Value of pmin to be given (in seconds).
804  *
805  * @return 0 for success or negative in case of error.
806  */
807 int lwm2m_update_observer_min_period(struct lwm2m_ctx *client_ctx,
808 				     const struct lwm2m_obj_path *path, uint32_t period_s);
809 
810 /**
811  * @brief Change an observer's pmax value.
812  *
813  * LwM2M clients use this function to modify the pmax attribute
814  * for an observation being made.
815  * Example to update the pmax of a temperature sensor value being observed:
816  * lwm2m__update_observer_max_period(client_ctx, &LWM2M_OBJ(3303, 0, 5700), 5);
817  *
818  * @param[in] client_ctx LwM2M context
819  * @param[in] path LwM2M path as a struct
820  * @param[in] period_s Value of pmax to be given (in seconds).
821  *
822  * @return 0 for success or negative in case of error.
823  */
824 int lwm2m_update_observer_max_period(struct lwm2m_ctx *client_ctx,
825 				     const struct lwm2m_obj_path *path, uint32_t period_s);
826 
827 /**
828  * @brief Create an LwM2M object instance.
829  *
830  * LwM2M clients use this function to create non-default LwM2M objects:
831  * Example to create first temperature sensor object:
832  * lwm2m_create_obj_inst(&LWM2M_OBJ(3303, 0));
833  *
834  * @param[in] path LwM2M path as a struct
835  *
836  * @return 0 for success or negative in case of error.
837  */
838 int lwm2m_create_object_inst(const struct lwm2m_obj_path *path);
839 
840 /**
841  * @brief Delete an LwM2M object instance.
842  *
843  * LwM2M clients use this function to delete LwM2M objects.
844  *
845  * @param[in] path LwM2M path as a struct
846  *
847  * @return 0 for success or negative in case of error.
848  */
849 int lwm2m_delete_object_inst(const struct lwm2m_obj_path *path);
850 
851 /**
852  * @brief Locks the registry for this thread.
853  *
854  * Use this function before writing to multiple resources. This halts the
855  * lwm2m main thread until all the write-operations are finished.
856  *
857  */
858 void lwm2m_registry_lock(void);
859 
860 /**
861  * @brief Unlocks the registry previously locked by lwm2m_registry_lock().
862  *
863  */
864 void lwm2m_registry_unlock(void);
865 
866 /**
867  * @brief Set resource (instance) value (opaque buffer)
868  *
869  * @param[in] path LwM2M path as a struct
870  * @param[in] data_ptr Data buffer
871  * @param[in] data_len Length of buffer
872  *
873  * @return 0 for success or negative in case of error.
874  */
875 int lwm2m_set_opaque(const struct lwm2m_obj_path *path, const char *data_ptr, uint16_t data_len);
876 
877 /**
878  * @brief Set resource (instance) value (string)
879  *
880  * @param[in] path LwM2M path as a struct
881  * @param[in] data_ptr NULL terminated char buffer
882  *
883  * @return 0 for success or negative in case of error.
884  */
885 int lwm2m_set_string(const struct lwm2m_obj_path *path, const char *data_ptr);
886 
887 /**
888  * @brief Set resource (instance) value (u8)
889  *
890  * @param[in] path LwM2M path as a struct
891  * @param[in] value u8 value
892  *
893  * @return 0 for success or negative in case of error.
894  */
895 int lwm2m_set_u8(const struct lwm2m_obj_path *path, uint8_t value);
896 
897 /**
898  * @brief Set resource (instance) value (u16)
899  *
900  * @param[in] path LwM2M path as a struct
901  * @param[in] value u16 value
902  *
903  * @return 0 for success or negative in case of error.
904  */
905 int lwm2m_set_u16(const struct lwm2m_obj_path *path, uint16_t value);
906 
907 /**
908  * @brief Set resource (instance) value (u32)
909  *
910  * @param[in] path LwM2M path as a struct
911  * @param[in] value u32 value
912  *
913  * @return 0 for success or negative in case of error.
914  */
915 int lwm2m_set_u32(const struct lwm2m_obj_path *path, uint32_t value);
916 
917 /**
918  * @brief Set resource (instance) value (s8)
919  *
920  * @param[in] path LwM2M path as a struct
921  * @param[in] value s8 value
922  *
923  * @return 0 for success or negative in case of error.
924  */
925 int lwm2m_set_s8(const struct lwm2m_obj_path *path, int8_t value);
926 
927 /**
928  * @brief Set resource (instance) value (s16)
929  *
930  * @param[in] path LwM2M path as a struct
931  * @param[in] value s16 value
932  *
933  * @return 0 for success or negative in case of error.
934  */
935 int lwm2m_set_s16(const struct lwm2m_obj_path *path, int16_t value);
936 
937 /**
938  * @brief Set resource (instance) value (s32)
939  *
940  * @param[in] path LwM2M path as a struct
941  * @param[in] value s32 value
942  *
943  * @return 0 for success or negative in case of error.
944  */
945 int lwm2m_set_s32(const struct lwm2m_obj_path *path, int32_t value);
946 
947 /**
948  * @brief Set resource (instance) value (s64)
949  *
950  * @param[in] path LwM2M path as a struct
951  * @param[in] value s64 value
952  *
953  * @return 0 for success or negative in case of error.
954  */
955 int lwm2m_set_s64(const struct lwm2m_obj_path *path, int64_t value);
956 
957 /**
958  * @brief Set resource (instance) value (bool)
959  *
960  * @param[in] path LwM2M path as a struct
961  * @param[in] value bool value
962  *
963  * @return 0 for success or negative in case of error.
964  */
965 int lwm2m_set_bool(const struct lwm2m_obj_path *path, bool value);
966 
967 /**
968  * @brief Set resource (instance) value (double)
969  *
970  * @param[in] path LwM2M path as a struct
971  * @param[in] value double value
972  *
973  * @return 0 for success or negative in case of error.
974  */
975 int lwm2m_set_f64(const struct lwm2m_obj_path *path, const double value);
976 
977 /**
978  * @brief Set resource (instance) value (Objlnk)
979  *
980  * @param[in] path LwM2M path as a struct
981  * @param[in] value pointer to the lwm2m_objlnk structure
982  *
983  * @return 0 for success or negative in case of error.
984  */
985 int lwm2m_set_objlnk(const struct lwm2m_obj_path *path, const struct lwm2m_objlnk *value);
986 
987 /**
988  * @brief Set resource (instance) value (Time)
989  *
990  * @param[in] path LwM2M path as a struct
991  * @param[in] value Epoch timestamp
992  *
993  * @return 0 for success or negative in case of error.
994  */
995 int lwm2m_set_time(const struct lwm2m_obj_path *path, time_t value);
996 
997 /**
998  * @brief LwM2M resource item structure
999  *
1000  * Value type must match the target resource as no type conversion are
1001  * done and the value is just memcopied.
1002  *
1003  * Following C types are used for resource types:
1004  * * BOOL is uint8_t
1005  * * U8 is uint8_t
1006  * * S8 is int8_t
1007  * * U16 is uint16_t
1008  * * S16 is int16_t
1009  * * U32 is uint32_t
1010  * * S32 is int32_t
1011  * * S64 is int64_t
1012  * * TIME is time_t
1013  * * FLOAT is double
1014  * * OBJLNK is struct lwm2m_objlnk
1015  * * STRING is char * and the null-terminator should be included in the size.
1016  * * OPAQUE is any binary data. When null-terminated string is written in OPAQUE
1017  *   resource, the terminator should not be included in size.
1018  *
1019  */
1020 struct lwm2m_res_item {
1021 	/** Pointer to LwM2M path as a struct */
1022 	struct lwm2m_obj_path *path;
1023 	/** Pointer to resource value */
1024 	void *value;
1025 	/** Size of the value. For string resources, it should contain the null-terminator. */
1026 	uint16_t size;
1027 };
1028 
1029 /**
1030  * @brief Set multiple resource (instance) values
1031  *
1032  * NOTE: Value type must match the target resource as this function
1033  * does not do any type conversion.
1034  * See struct @ref lwm2m_res_item for list of resource types.
1035  *
1036  * @param[in] res_list LwM2M resource item list
1037  * @param[in] res_list_size Length of resource list
1038  *
1039  * @return 0 for success or negative in case of error.
1040  */
1041 int lwm2m_set_bulk(const struct lwm2m_res_item res_list[], size_t res_list_size);
1042 
1043 /**
1044  * @brief Get resource (instance) value (opaque buffer)
1045  *
1046  * @param[in] path LwM2M path as a struct
1047  * @param[out] buf Data buffer to copy data into
1048  * @param[in] buflen Length of buffer
1049  *
1050  * @return 0 for success or negative in case of error.
1051  */
1052 int lwm2m_get_opaque(const struct lwm2m_obj_path *path, void *buf, uint16_t buflen);
1053 
1054 /**
1055  * @brief Get resource (instance) value (string)
1056  *
1057  * @param[in] path LwM2M path as a struct
1058  * @param[out] str String buffer to copy data into
1059  * @param[in] buflen Length of buffer
1060  *
1061  * @return 0 for success or negative in case of error.
1062  */
1063 int lwm2m_get_string(const struct lwm2m_obj_path *path, void *str, uint16_t buflen);
1064 
1065 /**
1066  * @brief Get resource (instance) value (u8)
1067  *
1068  * @param[in] path LwM2M path as a struct
1069  * @param[out] value u8 buffer to copy data into
1070  *
1071  * @return 0 for success or negative in case of error.
1072  */
1073 int lwm2m_get_u8(const struct lwm2m_obj_path *path, uint8_t *value);
1074 
1075 /**
1076  * @brief Get resource (instance) value (u16)
1077  *
1078  * @param[in] path LwM2M path as a struct
1079  * @param[out] value u16 buffer to copy data into
1080  *
1081  * @return 0 for success or negative in case of error.
1082  */
1083 int lwm2m_get_u16(const struct lwm2m_obj_path *path, uint16_t *value);
1084 
1085 /**
1086  * @brief Get resource (instance) value (u32)
1087  *
1088  * @param[in] path LwM2M path as a struct
1089  * @param[out] value u32 buffer to copy data into
1090  *
1091  * @return 0 for success or negative in case of error.
1092  */
1093 int lwm2m_get_u32(const struct lwm2m_obj_path *path, uint32_t *value);
1094 
1095 /**
1096  * @brief Get resource (instance) value (s8)
1097  *
1098  * @param[in] path LwM2M path as a struct
1099  * @param[out] value s8 buffer to copy data into
1100  *
1101  * @return 0 for success or negative in case of error.
1102  */
1103 int lwm2m_get_s8(const struct lwm2m_obj_path *path, int8_t *value);
1104 
1105 /**
1106  * @brief Get resource (instance) value (s16)
1107  *
1108  * @param[in] path LwM2M path as a struct
1109  * @param[out] value s16 buffer to copy data into
1110  *
1111  * @return 0 for success or negative in case of error.
1112  */
1113 int lwm2m_get_s16(const struct lwm2m_obj_path *path, int16_t *value);
1114 
1115 /**
1116  * @brief Get resource (instance) value (s32)
1117  *
1118  * @param[in] path LwM2M path as a struct
1119  * @param[out] value s32 buffer to copy data into
1120  *
1121  * @return 0 for success or negative in case of error.
1122  */
1123 int lwm2m_get_s32(const struct lwm2m_obj_path *path, int32_t *value);
1124 
1125 /**
1126  * @brief Get resource (instance) value (s64)
1127  *
1128  * @param[in] path LwM2M path as a struct
1129  * @param[out] value s64 buffer to copy data into
1130  *
1131  * @return 0 for success or negative in case of error.
1132  */
1133 int lwm2m_get_s64(const struct lwm2m_obj_path *path, int64_t *value);
1134 
1135 /**
1136  * @brief Get resource (instance) value (bool)
1137  *
1138  * @param[in] path LwM2M path as a struct
1139  * @param[out] value bool buffer to copy data into
1140  *
1141  * @return 0 for success or negative in case of error.
1142  */
1143 int lwm2m_get_bool(const struct lwm2m_obj_path *path, bool *value);
1144 
1145 /**
1146  * @brief Get resource (instance) value (double)
1147  *
1148  * @param[in] path LwM2M path as a struct
1149  * @param[out] value double buffer to copy data into
1150  *
1151  * @return 0 for success or negative in case of error.
1152  */
1153 int lwm2m_get_f64(const struct lwm2m_obj_path *path, double *value);
1154 
1155 /**
1156  * @brief Get resource (instance) value (Objlnk)
1157  *
1158  * @param[in] path LwM2M path as a struct
1159  * @param[out] buf lwm2m_objlnk buffer to copy data into
1160  *
1161  * @return 0 for success or negative in case of error.
1162  */
1163 int lwm2m_get_objlnk(const struct lwm2m_obj_path *path, struct lwm2m_objlnk *buf);
1164 
1165 /**
1166  * @brief Get resource (instance) value (Time)
1167  *
1168  * @param[in] path LwM2M path as a struct
1169  * @param[out] buf time_t pointer to copy data
1170  *
1171  * @return 0 for success or negative in case of error.
1172  */
1173 int lwm2m_get_time(const struct lwm2m_obj_path *path, time_t *buf);
1174 
1175 /**
1176  * @brief Set resource (instance) read callback
1177  *
1178  * LwM2M clients can use this to set the callback function for resource reads when data
1179  * handling in the LwM2M engine needs to be bypassed.
1180  * For example reading back opaque binary data from external storage.
1181  *
1182  * This callback should not generally be used for any data that might be observed as
1183  * engine does not have any knowledge of data changes.
1184  *
1185  * When separate buffer for data should be used, use lwm2m_set_res_buf() instead
1186  * to set the storage.
1187  *
1188  * @param[in] path LwM2M path as a struct
1189  * @param[in] cb Read resource callback
1190  *
1191  * @return 0 for success or negative in case of error.
1192  */
1193 int lwm2m_register_read_callback(const struct lwm2m_obj_path *path, lwm2m_engine_get_data_cb_t cb);
1194 
1195 /**
1196  * @brief Set resource (instance) pre-write callback
1197  *
1198  * This callback is triggered before setting the value of a resource.  It
1199  * can pass a special data buffer to the engine so that the actual resource
1200  * value can be calculated later, etc.
1201  *
1202  * @param[in] path LwM2M path as a struct
1203  * @param[in] cb Pre-write resource callback
1204  *
1205  * @return 0 for success or negative in case of error.
1206  */
1207 int lwm2m_register_pre_write_callback(const struct lwm2m_obj_path *path,
1208 				      lwm2m_engine_get_data_cb_t cb);
1209 
1210 /**
1211  * @brief Set resource (instance) validation callback
1212  *
1213  * This callback is triggered before setting the value of a resource to the
1214  * resource data buffer.
1215  *
1216  * The callback allows an LwM2M client or object to validate the data before
1217  * writing and notify an error if the data should be discarded for any reason
1218  * (by returning a negative error code).
1219  *
1220  * @note All resources that have a validation callback registered are initially
1221  *       decoded into a temporary validation buffer. Make sure that
1222  *       ``CONFIG_LWM2M_ENGINE_VALIDATION_BUFFER_SIZE`` is large enough to
1223  *       store each of the validated resources (individually).
1224  *
1225  * @param[in] path LwM2M path as a struct
1226  * @param[in] cb Validate resource data callback
1227  *
1228  * @return 0 for success or negative in case of error.
1229  */
1230 int lwm2m_register_validate_callback(const struct lwm2m_obj_path *path,
1231 				     lwm2m_engine_set_data_cb_t cb);
1232 
1233 /**
1234  * @brief Set resource (instance) post-write callback
1235  *
1236  * This callback is triggered after setting the value of a resource to the
1237  * resource data buffer.
1238  *
1239  * It allows an LwM2M client or object to post-process the value of a resource
1240  * or trigger other related resource calculations.
1241  *
1242  * @param[in] path LwM2M path as a struct
1243  * @param[in] cb Post-write resource callback
1244  *
1245  * @return 0 for success or negative in case of error.
1246  */
1247 int lwm2m_register_post_write_callback(const struct lwm2m_obj_path *path,
1248 				       lwm2m_engine_set_data_cb_t cb);
1249 
1250 /**
1251  * @brief Set resource execute event callback
1252  *
1253  * This event is triggered when the execute method of a resource is enabled.
1254  *
1255  * @param[in] path LwM2M path as a struct
1256  * @param[in] cb Execute resource callback
1257  *
1258  * @return 0 for success or negative in case of error.
1259  */
1260 int lwm2m_register_exec_callback(const struct lwm2m_obj_path *path, lwm2m_engine_execute_cb_t cb);
1261 
1262 /**
1263  * @brief Set object instance create event callback
1264  *
1265  * This event is triggered when an object instance is created.
1266  *
1267  * @param[in] obj_id LwM2M object id
1268  * @param[in] cb Create object instance callback
1269  *
1270  * @return 0 for success or negative in case of error.
1271  */
1272 int lwm2m_register_create_callback(uint16_t obj_id,
1273 				   lwm2m_engine_user_cb_t cb);
1274 
1275 /**
1276  * @brief Set object instance delete event callback
1277  *
1278  * This event is triggered when an object instance is deleted.
1279  *
1280  * @param[in] obj_id LwM2M object id
1281  * @param[in] cb Delete object instance callback
1282  *
1283  * @return 0 for success or negative in case of error.
1284  */
1285 int lwm2m_register_delete_callback(uint16_t obj_id,
1286 					  lwm2m_engine_user_cb_t cb);
1287 
1288 /**
1289  * @brief Resource read-only value bit
1290  */
1291 #define LWM2M_RES_DATA_READ_ONLY	0
1292 
1293 /**
1294  * @brief Resource read-only flag
1295  */
1296 #define LWM2M_RES_DATA_FLAG_RO		BIT(LWM2M_RES_DATA_READ_ONLY)
1297 
1298 /**
1299  * @brief Read resource flags helper macro
1300  */
1301 #define LWM2M_HAS_RES_FLAG(res, f)	((res->data_flags & f) == f)
1302 
1303 /**
1304  * @brief Set data buffer for a resource
1305  *
1306  * Use this function to set the data buffer and flags for the specified LwM2M
1307  * resource.
1308  *
1309  * @param[in] path LwM2M path as a struct
1310  * @param[in] buffer_ptr Data buffer pointer
1311  * @param[in] buffer_len Length of buffer
1312  * @param[in] data_len Length of existing data in the buffer
1313  * @param[in] data_flags Data buffer flags (such as read-only, etc)
1314  *
1315  * @return 0 for success or negative in case of error.
1316  */
1317 int lwm2m_set_res_buf(const struct lwm2m_obj_path *path, void *buffer_ptr, uint16_t buffer_len,
1318 		      uint16_t data_len, uint8_t data_flags);
1319 
1320 /**
1321  * @brief Update data size for a resource
1322  *
1323  * Use this function to set the new size of data in the buffer if you write
1324  * to a buffer received by lwm2m_get_res_buf().
1325  *
1326  * @param[in] path LwM2M path as a struct
1327  * @param[in] data_len Length of data
1328  * @return 0 for success or negative in case of error.
1329  */
1330 int lwm2m_set_res_data_len(const struct lwm2m_obj_path *path, uint16_t data_len);
1331 
1332 /**
1333  * @brief Get data buffer for a resource
1334  *
1335  * Use this function to get the data buffer information for the specified LwM2M
1336  * resource.
1337  *
1338  * If you directly write into the buffer, you must use lwm2m_set_res_data_len()
1339  * function to update the new size of the written data.
1340  *
1341  * All parameters, except for the pathstr, can be NULL if you don't want to read those values.
1342  *
1343  * @param[in] path LwM2M path as a struct
1344  * @param[out] buffer_ptr Data buffer pointer
1345  * @param[out] buffer_len Length of buffer
1346  * @param[out] data_len Length of existing data in the buffer
1347  * @param[out] data_flags Data buffer flags (such as read-only, etc)
1348  *
1349  * @return 0 for success or negative in case of error.
1350  */
1351 int lwm2m_get_res_buf(const struct lwm2m_obj_path *path, void **buffer_ptr, uint16_t *buffer_len,
1352 		      uint16_t *data_len, uint8_t *data_flags);
1353 
1354 /**
1355  * @brief Create a resource instance
1356  *
1357  * LwM2M clients use this function to create multi-resource instances:
1358  * Example to create 0 instance of device available power sources:
1359  * lwm2m_create_res_inst(&LWM2M_OBJ(3, 0, 6, 0));
1360  *
1361  * @param[in] path LwM2M path as a struct
1362  *
1363  * @return 0 for success or negative in case of error.
1364  */
1365 int lwm2m_create_res_inst(const struct lwm2m_obj_path *path);
1366 
1367 /**
1368  * @brief Delete a resource instance
1369  *
1370  * Use this function to remove an existing resource instance
1371  *
1372  * @param[in] path LwM2M path as a struct
1373  *
1374  * @return 0 for success or negative in case of error.
1375  */
1376 int lwm2m_delete_res_inst(const struct lwm2m_obj_path *path);
1377 
1378 /**
1379  * @brief Update the period of the device service.
1380  *
1381  * Change the duration of the periodic device service that notifies the
1382  * current time.
1383  *
1384  * @param[in] period_ms New period for the device service (in milliseconds)
1385  *
1386  * @return 0 for success or negative in case of error.
1387  */
1388 int lwm2m_update_device_service_period(uint32_t period_ms);
1389 
1390 /**
1391  * @brief Check whether a path is observed
1392  *
1393  * @param[in] path LwM2M path as a struct to check
1394  *
1395  * @return true when there exists an observation of the same level
1396  *         or lower as the given path, false if it doesn't or path is not a
1397  *         valid LwM2M-path.
1398  *         E.g. true if path refers to a resource and the parent object has an
1399  *         observation, false for the inverse.
1400  */
1401 bool lwm2m_path_is_observed(const struct lwm2m_obj_path *path);
1402 
1403 /**
1404  * @brief Stop the LwM2M engine
1405  *
1406  * LwM2M clients normally do not need to call this function as it is called
1407  * within lwm2m_rd_client. However, if the client does not use the RD
1408  * client implementation, it will need to be called manually.
1409  *
1410  * @param[in] client_ctx LwM2M context
1411  *
1412  * @return 0 for success or negative in case of error.
1413  */
1414 int lwm2m_engine_stop(struct lwm2m_ctx *client_ctx);
1415 
1416 /**
1417  * @brief Start the LwM2M engine
1418  *
1419  * LwM2M clients normally do not need to call this function as it is called
1420  * by lwm2m_rd_client_start().  However, if the client does not use the RD
1421  * client implementation, it will need to be called manually.
1422  *
1423  * @param[in] client_ctx LwM2M context
1424  *
1425  * @return 0 for success or negative in case of error.
1426  */
1427 int lwm2m_engine_start(struct lwm2m_ctx *client_ctx);
1428 
1429 /**
1430  * @brief Acknowledge the currently processed request with an empty ACK.
1431  *
1432  * LwM2M engine by default sends piggybacked responses for requests.
1433  * This function allows to send an empty ACK for a request earlier (from the
1434  * application callback). The LwM2M engine will then send the actual response
1435  * as a separate CON message after all callbacks are executed.
1436  *
1437  * @param[in] client_ctx LwM2M context
1438  *
1439  */
1440 void lwm2m_acknowledge(struct lwm2m_ctx *client_ctx);
1441 
1442 /*
1443  * LwM2M RD client flags, used to configure LwM2M session.
1444  */
1445 
1446 /**
1447  * @brief Run bootstrap procedure in current session.
1448  */
1449 #define LWM2M_RD_CLIENT_FLAG_BOOTSTRAP BIT(0)
1450 
1451 /**
1452  * @brief Start the LwM2M RD (Registration / Discovery) Client
1453  *
1454  * The RD client sits just above the LwM2M engine and performs the necessary
1455  * actions to implement the "Registration interface".
1456  * For more information see Section "Client Registration Interface" of
1457  * LwM2M Technical Specification.
1458  *
1459  * NOTE: lwm2m_engine_start() is called automatically by this function.
1460  *
1461  * @param[in] client_ctx LwM2M context
1462  * @param[in] ep_name Registered endpoint name
1463  * @param[in] flags Flags used to configure current LwM2M session.
1464  * @param[in] event_cb Client event callback function
1465  * @param[in] observe_cb Observe callback function called when an observer was
1466  *			 added or deleted, and when a notification was acked or
1467  *			 has timed out
1468  *
1469  * @return 0 for success, -EINPROGRESS when client is already running
1470  *         or negative error codes in case of failure.
1471  */
1472 int lwm2m_rd_client_start(struct lwm2m_ctx *client_ctx, const char *ep_name,
1473 			   uint32_t flags, lwm2m_ctx_event_cb_t event_cb,
1474 			   lwm2m_observe_cb_t observe_cb);
1475 
1476 /**
1477  * @brief Stop the LwM2M RD (De-register) Client
1478  *
1479  * The RD client sits just above the LwM2M engine and performs the necessary
1480  * actions to implement the "Registration interface".
1481  * For more information see Section "Client Registration Interface" of the
1482  * LwM2M Technical Specification.
1483  *
1484  * @param[in] client_ctx LwM2M context
1485  * @param[in] event_cb Client event callback function
1486  * @param[in] deregister True to deregister the client if registered.
1487  *                       False to force close the connection.
1488  *
1489  * @return 0 for success or negative in case of error.
1490  */
1491 int lwm2m_rd_client_stop(struct lwm2m_ctx *client_ctx,
1492 			  lwm2m_ctx_event_cb_t event_cb, bool deregister);
1493 
1494 /**
1495  * @brief Suspend the LwM2M engine Thread
1496  *
1497  * Suspend LwM2M engine. Use case could be when network connection is down.
1498  * LwM2M Engine indicate before it suspend by
1499  * LWM2M_RD_CLIENT_EVENT_ENGINE_SUSPENDED event.
1500  *
1501  * @return 0 for success or negative in case of error.
1502  */
1503 int lwm2m_engine_pause(void);
1504 
1505 /**
1506  * @brief Resume the LwM2M engine thread
1507  *
1508  * Resume suspended LwM2M engine. After successful resume call engine will do
1509  * full registration or registration update based on suspended time.
1510  * Event's LWM2M_RD_CLIENT_EVENT_REGISTRATION_COMPLETE or LWM2M_RD_CLIENT_EVENT_REG_UPDATE_COMPLETE
1511  * indicate that client is connected to server.
1512  *
1513  * @return 0 for success or negative in case of error.
1514  */
1515 int lwm2m_engine_resume(void);
1516 
1517 /**
1518  * @brief Trigger a Registration Update of the LwM2M RD Client
1519  */
1520 void lwm2m_rd_client_update(void);
1521 
1522 /**
1523  * @brief LwM2M path maximum length
1524  */
1525 #define LWM2M_MAX_PATH_STR_SIZE sizeof("/65535/65535/65535/65535")
1526 
1527 /**
1528  * @brief Helper function to print path objects' contents to log
1529  *
1530  * @param[in] buf The buffer to use for formatting the string
1531  * @param[in] path The path to stringify
1532  *
1533  * @return Resulting formatted path string
1534  */
1535 char *lwm2m_path_log_buf(char *buf, struct lwm2m_obj_path *path);
1536 
1537 /**
1538  * @brief LwM2M send status
1539  *
1540  * LwM2M send status are generated back to the lwm2m_send_cb_t function in
1541  * lwm2m_send_cb()
1542  */
1543 enum lwm2m_send_status {
1544 	LWM2M_SEND_STATUS_SUCCESS,  /**< Succeed */
1545 	LWM2M_SEND_STATUS_FAILURE,  /**< Failure */
1546 	LWM2M_SEND_STATUS_TIMEOUT,  /**< Timeout */
1547 };
1548 
1549 /**
1550  * @typedef lwm2m_send_cb_t
1551  * @brief Callback returning send status
1552  */
1553 typedef void (*lwm2m_send_cb_t)(enum lwm2m_send_status status);
1554 
1555 /** 
1556  * @brief LwM2M SEND operation to given path list asynchronously with confirmation callback
1557  *
1558  * @param ctx LwM2M context
1559  * @param path_list LwM2M path struct list
1560  * @param path_list_size Length of path list. Max size is CONFIG_LWM2M_COMPOSITE_PATH_LIST_SIZE
1561  * @param reply_cb Callback triggered with confirmation state or NULL if not used
1562  *
1563  * @return 0 for success or negative in case of error.
1564  *
1565  */
1566 int lwm2m_send_cb(struct lwm2m_ctx *ctx, const struct lwm2m_obj_path path_list[],
1567 			  uint8_t path_list_size, lwm2m_send_cb_t reply_cb);
1568 
1569 /** 
1570  * @brief Returns LwM2M client context
1571  *
1572  * @return ctx LwM2M context
1573  *
1574  */
1575 struct lwm2m_ctx *lwm2m_rd_client_ctx(void);
1576 
1577 /** 
1578  * @brief Enable data cache for a resource.
1579  *
1580  * Application may enable caching of resource data by allocating buffer for LwM2M engine to use.
1581  * Buffer must be size of struct @ref lwm2m_time_series_elem times cache_len
1582  *
1583  * @param path LwM2M path to resource as a struct
1584  * @param data_cache Pointer to Data cache array
1585  * @param cache_len number of cached entries
1586  *
1587  * @return 0 for success or negative in case of error.
1588  *
1589  */
1590 int lwm2m_enable_cache(const struct lwm2m_obj_path *path, struct lwm2m_time_series_elem *data_cache,
1591 		       size_t cache_len);
1592 
1593 /**
1594  * @brief Security modes as defined in LwM2M Security object.
1595  */
1596 enum lwm2m_security_mode_e {
1597 	LWM2M_SECURITY_PSK = 0,      /**< Pre-Shared Key mode */
1598 	LWM2M_SECURITY_RAW_PK = 1,   /**< Raw Public Key mode */
1599 	LWM2M_SECURITY_CERT = 2,     /**< Certificate mode */
1600 	LWM2M_SECURITY_NOSEC = 3,    /**< NoSec mode */
1601 	LWM2M_SECURITY_CERT_EST = 4, /**< Certificate mode with EST */
1602 };
1603 
1604 /**
1605  * @brief Read security mode from selected security object instance.
1606  *
1607  * This data is valid only if RD client is running.
1608  *
1609  * @param ctx Pointer to client context.
1610  * @return int Positive values are @ref lwm2m_security_mode_e, negative error codes otherwise.
1611  */
1612 int lwm2m_security_mode(struct lwm2m_ctx *ctx);
1613 
1614 /**
1615  * @brief Set default socket options for DTLS connections.
1616  *
1617  * The engine calls this when @ref lwm2m_ctx::set_socketoptions is not overwritten.
1618  * You can call this from the overwritten callback to set extra options after or
1619  * before defaults.
1620  *
1621  * @param ctx Client context
1622  * @return 0 for success or negative in case of error.
1623  */
1624 int lwm2m_set_default_sockopt(struct lwm2m_ctx *ctx);
1625 
1626 /**
1627  * @brief Set the @ref lwm2m_ctx::set_socketoptions callback for the pull context's client.
1628  *
1629  * This allows setting specific socket options on the socket that is used to pull
1630  * firmware updates. The callback will be called after the pull context socket has been
1631  * created and before it will connect.
1632  *
1633  * @param[in] set_sockopt_cb A callback function to set sockopts for the pull context client.
1634  */
1635 void lwm2m_pull_context_set_sockopt_callback(lwm2m_set_sockopt_cb_t set_sockopt_cb);
1636 
1637 #ifdef __cplusplus
1638 }
1639 #endif
1640 
1641 #endif	/* ZEPHYR_INCLUDE_NET_LWM2M_H_ */
1642 /**@}  */
1643