1 /*
2  * Copyright (c) 2019 Intel corporation
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #ifndef _TRACE_BACKEND_H
8 #define _TRACE_BACKEND_H
9 
10 #include <string.h>
11 #include <sys/util.h>
12 
13 #ifdef __cplusplus
14 extern "C" {
15 #endif
16 
17 /**
18  * @brief Tracing backend
19  * @defgroup Tracing_backend Tracing backend
20  * @{
21  * @}
22  */
23 
24 struct tracing_backend;
25 
26 /**
27  * @brief Tracing backend API.
28  */
29 struct tracing_backend_api {
30 	void (*init)(void);
31 	void (*output)(const struct tracing_backend *backend,
32 		       uint8_t *data, uint32_t length);
33 };
34 
35 /**
36  * @brief Tracing backend structure.
37  */
38 struct tracing_backend {
39 	const char *name;
40 	const struct tracing_backend_api *api;
41 };
42 
43 /**
44  * @brief Create tracing_backend instance.
45  *
46  * @param _name Instance name.
47  * @param _api  Tracing backend API.
48  */
49 #define TRACING_BACKEND_DEFINE(_name, _api)                              \
50 	static const STRUCT_SECTION_ITERABLE(tracing_backend, _name) = { \
51 		.name = STRINGIFY(_name),                                \
52 		.api = &_api                                             \
53 	}
54 
55 /**
56  * @brief Initialize tracing backend.
57  *
58  * @param backend Pointer to tracing_backend instance.
59  */
tracing_backend_init(const struct tracing_backend * backend)60 static inline void tracing_backend_init(
61 		const struct tracing_backend *backend)
62 {
63 	if (backend && backend->api && backend->api->init) {
64 		backend->api->init();
65 	}
66 }
67 
68 /**
69  * @brief Output tracing packet with tracing backend.
70  *
71  * @param backend Pointer to tracing_backend instance.
72  * @param data    Address of outputing buffer.
73  * @param length  Length of outputing buffer.
74  */
tracing_backend_output(const struct tracing_backend * backend,uint8_t * data,uint32_t length)75 static inline void tracing_backend_output(
76 		const struct tracing_backend *backend,
77 		uint8_t *data, uint32_t length)
78 {
79 	if (backend && backend->api) {
80 		backend->api->output(backend, data, length);
81 	}
82 }
83 
84 /**
85  * @brief Get tracing backend based on the name of
86  *        tracing backend in tracing backend section.
87  *
88  * @param name Name of wanted tracing backend.
89  *
90  * @return Pointer of the wanted backend or NULL.
91  */
tracing_backend_get(char * name)92 static inline struct tracing_backend *tracing_backend_get(char *name)
93 {
94 	STRUCT_SECTION_FOREACH(tracing_backend, backend) {
95 		if (strcmp(backend->name, name) == 0) {
96 			return backend;
97 		}
98 	}
99 
100 	return NULL;
101 }
102 
103 #ifdef __cplusplus
104 }
105 #endif
106 
107 #endif
108