1 /*
2 * coap_debug.h -- debug utilities
3 *
4 * Copyright (C) 2010-2011,2014-2023 Olaf Bergmann <bergmann@tzi.org>
5 *
6 * SPDX-License-Identifier: BSD-2-Clause
7 *
8 * This file is part of the CoAP library libcoap. Please see README for terms
9 * of use.
10 */
11
12 /**
13 * @file coap_debug.h
14 * @brief CoAP Logging support
15 */
16
17 #ifndef COAP_DEBUG_H_
18 #define COAP_DEBUG_H_
19
20 /**
21 * @ingroup application_api
22 * @defgroup logging Logging Support
23 * API for logging support
24 * @{
25 */
26
27 #ifndef COAP_DEBUG_FD
28 /**
29 * Used for output for @c COAP_LOG_OSCORE to @c COAP_LOG_ERR.
30 */
31 #define COAP_DEBUG_FD stdout
32 #endif
33
34 #ifndef COAP_ERR_FD
35 /**
36 * Used for output for @c COAP_LOG_CRIT to @c COAP_LOG_EMERG.
37 */
38 #define COAP_ERR_FD stderr
39 #endif
40
41 #ifndef COAP_MAX_LOGGING_LEVEL
42 #define COAP_MAX_LOGGING_LEVEL 8
43 #endif /* ! COAP_MAX_LOGGING_LEVEL */
44
45 /**
46 * Logging type. These should be used where possible in the code instead
47 * of the syslog definitions, or alternatively use the coap_log_*() functions
48 * to reduce line length.
49 */
50 typedef enum {
51 COAP_LOG_EMERG = 0, /* 0 */
52 COAP_LOG_ALERT, /* 1 */
53 COAP_LOG_CRIT, /* 2 */
54 COAP_LOG_ERR, /* 3 */
55 COAP_LOG_WARN, /* 4 */
56 COAP_LOG_NOTICE, /* 5 */
57 COAP_LOG_INFO, /* 6 */
58 COAP_LOG_DEBUG, /* 7 */
59 COAP_LOG_OSCORE, /* 8 */
60 COAP_LOG_DTLS_BASE,
61 #define COAP_LOG_CIPHERS COAP_LOG_DTLS_BASE /* For backward compatability */
62 } coap_log_t;
63
64 /*
65 * These have the same values, but can be used in #if tests for better
66 * readability
67 */
68 #define _COAP_LOG_EMERG 0
69 #define _COAP_LOG_ALERT 1
70 #define _COAP_LOG_CRIT 2
71 #define _COAP_LOG_ERR 3
72 #define _COAP_LOG_WARN 4
73 #define _COAP_LOG_NOTICE 5
74 #define _COAP_LOG_INFO 6
75 #define _COAP_LOG_DEBUG 7
76 #define _COAP_LOG_OSCORE 8
77
78 COAP_STATIC_INLINE void
coap_no_log(void)79 coap_no_log(void) { }
80
81 #define coap_log_emerg(...) coap_log(COAP_LOG_EMERG, __VA_ARGS__)
82
83 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_ALERT)
84 #define coap_log_alert(...) coap_log(COAP_LOG_ALERT, __VA_ARGS__)
85 #else
86 #define coap_log_alert(...) coap_no_log()
87 #endif
88
89 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_CRIT)
90 #define coap_log_crit(...) coap_log(COAP_LOG_CRIT, __VA_ARGS__)
91 #else
92 #define coap_log_crit(...) coap_no_log()
93 #endif
94
95 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_ERR)
96 #define coap_log_err(...) coap_log(COAP_LOG_ERR, __VA_ARGS__)
97 #else
98 #define coap_log_err(...) coap_no_log()
99 #endif
100
101 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_WARN)
102 #define coap_log_warn(...) coap_log(COAP_LOG_WARN, __VA_ARGS__)
103 #else
104 #define coap_log_warn(...) coap_no_log()
105 #endif
106
107 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_INFO)
108 #define coap_log_info(...) coap_log(COAP_LOG_INFO, __VA_ARGS__)
109 #else
110 #define coap_log_info(...) coap_no_log()
111 #endif
112
113 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_NOTICE)
114 #define coap_log_notice(...) coap_log(COAP_LOG_NOTICE, __VA_ARGS__)
115 #else
116 #define coap_log_notice(...) coap_no_log()
117 #endif
118
119 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_DEBUG)
120 #define coap_log_debug(...) coap_log(COAP_LOG_DEBUG, __VA_ARGS__)
121 #else
122 #define coap_log_debug(...) coap_no_log()
123 #endif
124
125 #if (COAP_MAX_LOGGING_LEVEL >= _COAP_LOG_OSCORE)
126 #define coap_log_oscore(...) coap_log(COAP_LOG_OSCORE, __VA_ARGS__)
127 #else
128 #define coap_log_oscore(...) coap_no_log()
129 #endif
130
131 /*
132 * These entries are left here for backward compatability in applications
133 * (which should really "#include <syslog.h>").
134 * and MUST NOT be used anywhere within the libcoap code.
135 *
136 * If clashes occur during a particilar OS port, they can be safely deleted.
137 *
138 * In a future update, they will get removed.
139 */
140 #if !defined(RIOT_VERSION) && !defined(WITH_LWIP) && !defined(WITH_CONTIKI)
141 #ifndef LOG_EMERG
142 # define LOG_EMERG COAP_LOG_EMERG
143 #endif
144 #ifndef LOG_ALERT
145 # define LOG_ALERT COAP_LOG_ALERT
146 #endif
147 #ifndef LOG_CRIT
148 # define LOG_CRIT COAP_LOG_CRIT
149 #endif
150 #ifndef LOG_ERR
151 # define LOG_ERR COAP_LOG_ERR
152 #endif
153 #ifndef LOG_WARNING
154 # define LOG_WARNING COAP_LOG_WARN
155 #endif
156 #ifndef LOG_NOTICE
157 # define LOG_NOTICE COAP_LOG_NOTICE
158 #endif
159 #ifndef LOG_INFO
160 # define LOG_INFO COAP_LOG_INFO
161 #endif
162 #ifndef LOG_DEBUG
163 # define LOG_DEBUG COAP_LOG_DEBUG
164 #endif
165 #endif /* ! RIOT_VERSION && ! WITH_LWIP && ! WITH_CONTIKI */
166
167 /**
168 * Get the current logging level.
169 *
170 * @return One of the COAP_LOG_* values.
171 */
172 coap_log_t coap_get_log_level(void);
173
174 /**
175 * Sets the log level to the specified value.
176 *
177 * @param level One of the COAP_LOG_* values.
178 */
179 void coap_set_log_level(coap_log_t level);
180
181 /**
182 * Sets the (D)TLS logging level to the specified @p level.
183 *
184 * @param level One of the COAP_LOG_* values.
185 */
186 void coap_dtls_set_log_level(coap_log_t level);
187
188 /**
189 * Get the current (D)TLS logging.
190 *
191 * @return One of the COAP_LOG_* values.
192 */
193 coap_log_t coap_dtls_get_log_level(void);
194
195 /**
196 * Logging callback handler definition.
197 *
198 * @param level One of the COAP_LOG_* values, or if used for (D)TLS logging,
199 * COAP_LOG_DTLS_BASE + one of the COAP_LOG_* values.
200 * @param message Zero-terminated string message to log.
201 */
202 typedef void (*coap_log_handler_t)(coap_log_t level, const char *message);
203
204 /**
205 * Add a custom log callback handler.
206 *
207 * @param handler The logging handler to use or @p NULL to use default handler.
208 * This handler will be used for both CoAP and (D)TLS logging.
209 */
210 void coap_set_log_handler(coap_log_handler_t handler);
211
212 /**
213 * Get the library package name.
214 *
215 * @return Zero-terminated string with the name of this library.
216 */
217 const char *coap_package_name(void);
218
219 /**
220 * Get the library package version.
221 *
222 * @return Zero-terminated string with the library version.
223 */
224 const char *coap_package_version(void);
225
226 /**
227 * Get the library package build.
228 *
229 * @return Zero-terminated string with the library build.
230 */
231 const char *coap_package_build(void);
232
233 /**
234 * Writes the given text to @c COAP_ERR_FD (for @p level <= @c COAP_LOG_CRIT) or
235 * @c COAP_DEBUG_FD (for @p level >= @c COAP_LOG_ERR). The text is output only
236 * when @p level is below or equal to the log level that set by
237 * coap_set_log_level().
238 *
239 * Internal function.
240 *
241 * @param level One of the COAP_LOG_* values.
242 & @param format The format string to use.
243 */
244 #if (defined(__GNUC__))
245 void coap_log_impl(coap_log_t level,
246 const char *format, ...) __attribute__((format(printf, 2, 3)));
247 #else
248 void coap_log_impl(coap_log_t level, const char *format, ...);
249 #endif
250
251 #ifndef coap_log
252 #ifdef WITH_CONTIKI
253 #include <stdio.h>
254
255 #ifndef LOG_CONF_LEVEL_COAP
256 #define LOG_CONF_LEVEL_COAP 0 /* = LOG_LEVEL_NONE */
257 #endif
258
259 void coap_print_contiki_prefix(coap_log_t level);
260
261 #define coap_log(level, ...) do { \
262 if (LOG_CONF_LEVEL_COAP && \
263 ((int)((level)) <= (int)coap_get_log_level())) { \
264 coap_print_contiki_prefix(level); \
265 printf(__VA_ARGS__); \
266 } \
267 } while(0)
268 #else /* !WITH_CONTIKI */
269 /**
270 * Logging function.
271 * Writes the given text to @c COAP_ERR_FD (for @p level <= @c COAP_LOG_CRIT) or @c
272 * COAP_DEBUG_FD (for @p level >= @c COAP_LOG_ERR). The text is output only when
273 * @p level is below or equal to the log level that set by coap_set_log_level().
274 *
275 * @param level One of the COAP_LOG_* values.
276 */
277 #define coap_log(level, ...) do { \
278 if ((int)((level))<=(int)coap_get_log_level()) \
279 coap_log_impl((level), __VA_ARGS__); \
280 } while(0)
281 #endif /* !WITH_CONTIKI */
282 #endif
283
284 #ifndef coap_dtls_log
285 /**
286 * Logging function.
287 * Writes the given text to @c COAP_ERR_FD (for @p level <= @c COAP_LOG_CRIT) or @c
288 * COAP_DEBUG_FD (for @p level >= @c COAP_LOG_ERR). The text is output only when
289 * @p level is below or equal to the log level that set by coap_dtls_set_log_level().
290 *
291 * @param level One of the COAP_LOG_* values.
292 */
293 #define coap_dtls_log(level, ...) do { \
294 if ((int)((level))<=(int)coap_dtls_get_log_level()) \
295 coap_log_impl((level)+COAP_LOG_DTLS_BASE, __VA_ARGS__); \
296 } while(0)
297 #endif
298
299 #include "coap_pdu.h"
300
301 /**
302 * Defines the output mode for the coap_show_pdu() function.
303 *
304 * @param use_fprintf @p 1 if the output is to use fprintf() (the default)
305 * @p 0 if the output is to use coap_log().
306 */
307 void coap_set_show_pdu_output(int use_fprintf);
308
309 /**
310 * Display the contents of the specified @p pdu.
311 * Note: The output method of coap_show_pdu() is dependent on the setting of
312 * coap_set_show_pdu_output().
313 *
314 * @param level The required minimum logging level.
315 * @param pdu The PDU to decode.
316 */
317 void coap_show_pdu(coap_log_t level, const coap_pdu_t *pdu);
318
319 /**
320 * Display the current (D)TLS library linked with and built for version.
321 *
322 * @param level The required minimum logging level.
323 */
324 void coap_show_tls_version(coap_log_t level);
325
326 /**
327 * Build a string containing the current (D)TLS library linked with and
328 * built for version.
329 *
330 * @param buffer The buffer to put the string into.
331 * @param bufsize The size of the buffer to put the string into.
332 *
333 * @return A pointer to the provided buffer.
334 */
335 char *coap_string_tls_version(char *buffer, size_t bufsize);
336
337 /**
338 * Build a string containing the current (D)TLS library support
339 *
340 * @param buffer The buffer to put the string into.
341 * @param bufsize The size of the buffer to put the string into.
342 *
343 * @return A pointer to the provided buffer.
344 */
345 char *coap_string_tls_support(char *buffer, size_t bufsize);
346
347 /**
348 * Print the address into the defined buffer.
349 *
350 * @param address The address to print.
351 * @param buffer The buffer to print into.
352 * @param size The size of the buffer to print into.
353 *
354 * @return The amount written into the buffer.
355 */
356 size_t coap_print_addr(const coap_address_t *address,
357 unsigned char *buffer, size_t size);
358
359 /**
360 * Print the IP address into the defined buffer.
361 *
362 * @param address The address to print.
363 * @param buffer The buffer to print into.
364 * @param size The size of the buffer to print into.
365 *
366 * @return The pointer to provided buffer with as much of the IP address added
367 * as possible.
368 */
369 const char *coap_print_ip_addr(const coap_address_t *address,
370 char *buffer, size_t size);
371
372 /** @} */
373
374 /**
375 * Set the packet loss level for testing. This can be in one of two forms.
376 *
377 * Percentage : 0% to 100%. Use the specified probability.
378 * 0% is send all packets, 100% is drop all packets.
379 *
380 * List: A comma separated list of numbers or number ranges that are the
381 * packets to drop.
382 *
383 * @param loss_level The defined loss level (percentage or list).
384 *
385 * @return @c 1 If loss level set, @c 0 if there is an error.
386 */
387 int coap_debug_set_packet_loss(const char *loss_level);
388
389 #endif /* COAP_DEBUG_H_ */
390