1 /* 2 * Copyright (c) 2018 Intel Corporation 3 * 4 * SPDX-License-Identifier: Apache-2.0 5 */ 6 #ifndef ZEPHYR_INCLUDE_TRACING_TRACING_MACROS_H_ 7 #define ZEPHYR_INCLUDE_TRACING_TRACING_MACROS_H_ 8 9 #include <zephyr/sys/util_macro.h> 10 11 #if !defined(CONFIG_TRACING) && !defined(__DOXYGEN__) 12 13 #define SYS_PORT_TRACING_FUNC(type, func, ...) do { } while (false) 14 #define SYS_PORT_TRACING_FUNC_ENTER(type, func, ...) do { } while (false) 15 #define SYS_PORT_TRACING_FUNC_BLOCKING(type, func, ...) do { } while (false) 16 #define SYS_PORT_TRACING_FUNC_EXIT(type, func, ...) do { } while (false) 17 #define SYS_PORT_TRACING_OBJ_INIT(obj_type, obj, ...) do { } while (false) 18 #define SYS_PORT_TRACING_OBJ_FUNC(obj_type, func, obj, ...) do { } while (false) 19 #define SYS_PORT_TRACING_OBJ_FUNC_ENTER(obj_type, func, obj, ...) do { } while (false) 20 #define SYS_PORT_TRACING_OBJ_FUNC_BLOCKING(obj_type, func, obj, ...) do { } while (false) 21 #define SYS_PORT_TRACING_OBJ_FUNC_EXIT(obj_type, func, obj, ...) do { } while (false) 22 23 #define SYS_PORT_TRACING_TRACKING_FIELD(type) 24 25 #else 26 27 /** 28 * @brief Tracing utility macros 29 * @defgroup subsys_tracing_macros Tracing utility macros 30 * @ingroup subsys_tracing 31 * @{ 32 */ 33 34 /** @cond INTERNAL_HIDDEN */ 35 36 /* 37 * Helper macros used by the extended tracing system 38 */ 39 40 #define _SYS_PORT_TRACING_TYPE_MASK(type) \ 41 sys_port_trace_type_mask_ ## type 42 #define _SYS_PORT_TRACING_FUNC(name, func) \ 43 sys_port_trace_ ## name ## _ ## func 44 #define _SYS_PORT_TRACING_FUNC_ENTER(name, func) \ 45 sys_port_trace_ ## name ## _ ## func ## _enter 46 #define _SYS_PORT_TRACING_FUNC_BLOCKING(name, func) \ 47 sys_port_trace_ ## name ## _ ## func ## _blocking 48 #define _SYS_PORT_TRACING_FUNC_EXIT(name, func) \ 49 sys_port_trace_ ## name ## _ ## func ## _exit 50 #define _SYS_PORT_TRACING_OBJ_INIT(name) \ 51 sys_port_trace_ ## name ## _init 52 #define _SYS_PORT_TRACING_OBJ_FUNC(name, func) \ 53 sys_port_trace_ ## name ## _ ## func 54 #define _SYS_PORT_TRACING_OBJ_FUNC_ENTER(name, func) \ 55 sys_port_trace_ ## name ## _ ## func ## _enter 56 #define _SYS_PORT_TRACING_OBJ_FUNC_BLOCKING(name, func) \ 57 sys_port_trace_ ## name ## _ ## func ## _blocking 58 #define _SYS_PORT_TRACING_OBJ_FUNC_EXIT(name, func) \ 59 sys_port_trace_ ## name ## _ ## func ## _exit 60 61 /* 62 * Helper macros for the object tracking system 63 */ 64 65 #define _SYS_PORT_TRACKING_OBJ_INIT(name) \ 66 sys_port_track_ ## name ## _init 67 #define _SYS_PORT_TRACKING_OBJ_FUNC(name, func) \ 68 sys_port_track_ ## name ## _ ## func 69 70 /* 71 * Object trace macros part of the system for checking if certain 72 * objects should be traced or not depending on the tracing configuration. 73 */ 74 #if defined(CONFIG_TRACING_THREAD) 75 #define sys_port_trace_type_mask_k_thread(trace_call) trace_call 76 #else 77 #define sys_port_trace_type_mask_k_thread(trace_call) 78 #define sys_port_trace_k_thread_is_disabled 1 79 #endif 80 81 #if defined(CONFIG_TRACING_WORK) 82 #define sys_port_trace_type_mask_k_work(trace_call) trace_call 83 #define sys_port_trace_type_mask_k_work_queue(trace_call) trace_call 84 #define sys_port_trace_type_mask_k_work_delayable(trace_call) trace_call 85 #define sys_port_trace_type_mask_k_work_poll(trace_call) trace_call 86 #else 87 #define sys_port_trace_type_mask_k_work(trace_call) 88 #define sys_port_trace_type_mask_k_work_queue(trace_call) 89 #define sys_port_trace_type_mask_k_work_delayable(trace_call) 90 #define sys_port_trace_type_mask_k_work_poll(trace_call) 91 #endif 92 93 #if defined(CONFIG_TRACING_SEMAPHORE) 94 #define sys_port_trace_type_mask_k_sem(trace_call) trace_call 95 #else 96 #define sys_port_trace_type_mask_k_sem(trace_call) 97 #endif 98 99 #if defined(CONFIG_TRACING_MUTEX) 100 #define sys_port_trace_type_mask_k_mutex(trace_call) trace_call 101 #else 102 #define sys_port_trace_type_mask_k_mutex(trace_call) 103 #endif 104 105 #if defined(CONFIG_TRACING_CONDVAR) 106 #define sys_port_trace_type_mask_k_condvar(trace_call) trace_call 107 #else 108 #define sys_port_trace_type_mask_k_condvar(trace_call) 109 #endif 110 111 #if defined(CONFIG_TRACING_QUEUE) 112 #define sys_port_trace_type_mask_k_queue(trace_call) trace_call 113 #else 114 #define sys_port_trace_type_mask_k_queue(trace_call) 115 #endif 116 117 #if defined(CONFIG_TRACING_FIFO) 118 #define sys_port_trace_type_mask_k_fifo(trace_call) trace_call 119 #else 120 #define sys_port_trace_type_mask_k_fifo(trace_call) 121 #endif 122 123 #if defined(CONFIG_TRACING_LIFO) 124 #define sys_port_trace_type_mask_k_lifo(trace_call) trace_call 125 #else 126 #define sys_port_trace_type_mask_k_lifo(trace_call) 127 #endif 128 129 #if defined(CONFIG_TRACING_STACK) 130 #define sys_port_trace_type_mask_k_stack(trace_call) trace_call 131 #else 132 #define sys_port_trace_type_mask_k_stack(trace_call) 133 #endif 134 135 #if defined(CONFIG_TRACING_MESSAGE_QUEUE) 136 #define sys_port_trace_type_mask_k_msgq(trace_call) trace_call 137 #else 138 #define sys_port_trace_type_mask_k_msgq(trace_call) 139 #endif 140 141 #if defined(CONFIG_TRACING_MAILBOX) 142 #define sys_port_trace_type_mask_k_mbox(trace_call) trace_call 143 #else 144 #define sys_port_trace_type_mask_k_mbox(trace_call) 145 #endif 146 147 #if defined(CONFIG_TRACING_PIPE) 148 #define sys_port_trace_type_mask_k_pipe(trace_call) trace_call 149 #else 150 #define sys_port_trace_type_mask_k_pipe(trace_call) 151 #endif 152 153 #if defined(CONFIG_TRACING_HEAP) 154 #define sys_port_trace_type_mask_k_heap(trace_call) trace_call 155 #define sys_port_trace_type_mask_k_heap_sys(trace_call) trace_call 156 #else 157 #define sys_port_trace_type_mask_k_heap(trace_call) 158 #define sys_port_trace_type_mask_k_heap_sys(trace_call) 159 #endif 160 161 #if defined(CONFIG_TRACING_MEMORY_SLAB) 162 #define sys_port_trace_type_mask_k_mem_slab(trace_call) trace_call 163 #else 164 #define sys_port_trace_type_mask_k_mem_slab(trace_call) 165 #endif 166 167 #if defined(CONFIG_TRACING_TIMER) 168 #define sys_port_trace_type_mask_k_timer(trace_call) trace_call 169 #else 170 #define sys_port_trace_type_mask_k_timer(trace_call) 171 #endif 172 173 #if defined(CONFIG_TRACING_EVENT) 174 #define sys_port_trace_type_mask_k_event(trace_call) trace_call 175 #else 176 #define sys_port_trace_type_mask_k_event(trace_call) 177 #endif 178 179 #ifndef CONFIG_TRACING_POLLING 180 #define sys_port_trace_k_poll_api_is_disabled 1 181 #define sys_port_trace_k_work_poll_is_disabled 1 182 #endif 183 184 #ifndef CONFIG_TRACING_PM 185 #define sys_port_trace_pm_is_disabled 1 186 #endif 187 188 /* 189 * We cannot positively enumerate all traced APIs, as applications may trace 190 * arbitrary custom APIs we know nothing about. Therefore we demand that tracing 191 * of an API must be actively disabled. 192 * 193 * This contrasts with object tracing/tracking as all traceable objects are well 194 * known, see the SYS_PORT_TRACING_TYPE_MASK approach below. 195 */ 196 #define _SYS_PORT_TRACE_IS_DISABLED(type) sys_port_trace_##type##_is_disabled 197 #define _SYS_PORT_TRACE_WRAP(func, ...) do { func(__VA_ARGS__); } while (false) 198 #define _SYS_PORT_TRACE_IF_NOT_DISABLED(type, func, ...) \ 199 COND_CODE_1(_SYS_PORT_TRACE_IS_DISABLED(type), (), \ 200 (_SYS_PORT_TRACE_WRAP(func, __VA_ARGS__))) 201 202 /** @endcond */ 203 204 /** 205 * @brief Checks if an object type should be traced or not. 206 * 207 * @param type Tracing event type/object 208 * @param trace_call Tracing call 209 */ 210 #define SYS_PORT_TRACING_TYPE_MASK(type, trace_call) \ 211 _SYS_PORT_TRACING_TYPE_MASK(type)(trace_call) 212 213 /** 214 * @brief Tracing macro for function calls which are not directly 215 * associated with a specific type of object. 216 * 217 * @param type Type of tracing event or object type 218 * @param func Name of the function responsible for the call. This does not need to exactly 219 * match the name of the function but should rather match what the user called in case of 220 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 221 * @param ... Additional parameters relevant to the tracing call 222 */ 223 #define SYS_PORT_TRACING_FUNC(type, func, ...) \ 224 _SYS_PORT_TRACE_IF_NOT_DISABLED(type, _SYS_PORT_TRACING_FUNC(type, func), __VA_ARGS__) 225 226 /** 227 * @brief Tracing macro for the entry into a function that might or might not return 228 * a value. 229 * 230 * @param type Type of tracing event or object type 231 * @param func Name of the function responsible for the call. This does not need to exactly 232 * match the name of the function but should rather match what the user called in case of 233 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 234 * @param ... Additional parameters relevant to the tracing call 235 */ 236 #define SYS_PORT_TRACING_FUNC_ENTER(type, func, ...) \ 237 _SYS_PORT_TRACE_IF_NOT_DISABLED(type, _SYS_PORT_TRACING_FUNC_ENTER(type, func), __VA_ARGS__) 238 239 /** 240 * @brief Tracing macro for when a function blocks during its execution. 241 * 242 * @param type Type of tracing event or object type 243 * @param func Name of the function responsible for the call. This does not need to exactly 244 * match the name of the function but should rather match what the user called in case of 245 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 246 * @param ... Additional parameters relevant to the tracing call 247 */ 248 #define SYS_PORT_TRACING_FUNC_BLOCKING(type, func, ...) \ 249 _SYS_PORT_TRACE_IF_NOT_DISABLED(type, _SYS_PORT_TRACING_FUNC_BLOCKING(type, func), \ 250 __VA_ARGS__) 251 252 /** 253 * @brief Tracing macro for when a function ends its execution. Potential return values 254 * can be given as additional arguments. 255 * 256 * @param type Type of tracing event or object type 257 * @param func Name of the function responsible for the call. This does not need to exactly 258 * match the name of the function but should rather match what the user called in case of 259 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 260 * @param ... Additional parameters relevant to the tracing call 261 */ 262 #define SYS_PORT_TRACING_FUNC_EXIT(type, func, ...) \ 263 _SYS_PORT_TRACE_IF_NOT_DISABLED(type, _SYS_PORT_TRACING_FUNC_EXIT(type, func), __VA_ARGS__) 264 265 /** 266 * @brief Tracing macro for the initialization of an object. 267 * 268 * @param obj_type The type of object associated with the call (k_thread, k_sem, k_mutex etc.) 269 * @param obj Object 270 */ 271 #define SYS_PORT_TRACING_OBJ_INIT(obj_type, obj, ...) \ 272 do { \ 273 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 274 _SYS_PORT_TRACING_OBJ_INIT(obj_type)(obj, ##__VA_ARGS__)); \ 275 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 276 _SYS_PORT_TRACKING_OBJ_INIT(obj_type)(obj, ##__VA_ARGS__)); \ 277 } while (false) 278 279 /** 280 * @brief Tracing macro for simple object function calls often without returns or branching. 281 * 282 * @param obj_type The type of object associated with the call (k_thread, k_sem, k_mutex etc.) 283 * @param func Name of the function responsible for the call. This does not need to exactly 284 * match the name of the function but should rather match what the user called in case of 285 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 286 * @param obj Object 287 * @param ... Additional parameters relevant to the tracing call 288 */ 289 #define SYS_PORT_TRACING_OBJ_FUNC(obj_type, func, obj, ...) \ 290 do { \ 291 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 292 _SYS_PORT_TRACING_OBJ_FUNC(obj_type, func)(obj, ##__VA_ARGS__)); \ 293 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 294 _SYS_PORT_TRACKING_OBJ_FUNC(obj_type, func)(obj, ##__VA_ARGS__)); \ 295 } while (false) 296 297 /** 298 * @brief Tracing macro for the entry into a function that might or might not return 299 * a value. 300 * 301 * @param obj_type The type of object associated with the call (k_thread, k_sem, k_mutex etc.) 302 * @param func Name of the function responsible for the call. This does not need to exactly 303 * match the name of the function but should rather match what the user called in case of 304 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 305 * @param obj Object 306 * @param ... Additional parameters relevant to the tracing call 307 */ 308 #define SYS_PORT_TRACING_OBJ_FUNC_ENTER(obj_type, func, obj, ...) \ 309 do { \ 310 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 311 _SYS_PORT_TRACING_OBJ_FUNC_ENTER(obj_type, func)(obj, ##__VA_ARGS__)); \ 312 } while (false) 313 314 /** 315 * @brief Tracing macro for when a function blocks during its execution. 316 * 317 * @param obj_type The type of object associated with the call (k_thread, k_sem, k_mutex etc.) 318 * @param func Name of the function responsible for the call. This does not need to exactly 319 * match the name of the function but should rather match what the user called in case of 320 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 321 * @param obj Object 322 * @param timeout Timeout 323 * @param ... Additional parameters relevant to the tracing call 324 */ 325 #define SYS_PORT_TRACING_OBJ_FUNC_BLOCKING(obj_type, func, obj, timeout, ...) \ 326 do { \ 327 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 328 _SYS_PORT_TRACING_OBJ_FUNC_BLOCKING(obj_type, func) \ 329 (obj, timeout, ##__VA_ARGS__)); \ 330 } while (false) 331 332 /** 333 * @brief Tracing macro for when a function ends its execution. Potential return values 334 * can be given as additional arguments. 335 * 336 * @param obj_type The type of object associated with the call (k_thread, k_sem, k_mutex etc.) 337 * @param func Name of the function responsible for the call. This does not need to exactly 338 * match the name of the function but should rather match what the user called in case of 339 * system calls etc. That is, we can often omit the z_vrfy/z_impl part of the name. 340 * @param obj Object 341 * @param ... Additional parameters relevant to the tracing call 342 */ 343 #define SYS_PORT_TRACING_OBJ_FUNC_EXIT(obj_type, func, obj, ...) \ 344 do { \ 345 SYS_PORT_TRACING_TYPE_MASK(obj_type, \ 346 _SYS_PORT_TRACING_OBJ_FUNC_EXIT(obj_type, func)(obj, ##__VA_ARGS__)); \ 347 } while (false) 348 349 /** 350 * @brief Field added to kernel objects so they are tracked. 351 * 352 * @param type Type of object being tracked (k_thread, k_sem, etc.) 353 */ 354 #define SYS_PORT_TRACING_TRACKING_FIELD(type) \ 355 SYS_PORT_TRACING_TYPE_MASK(type, struct type *_obj_track_next;) 356 357 /** @} */ /* end of subsys_tracing_macros */ 358 359 #endif /* CONFIG_TRACING */ 360 361 #endif /* ZEPHYR_INCLUDE_TRACING_TRACING_MACROS_H_ */ 362