1 /*
2 * Percepio Trace Recorder for Tracealyzer v4.8.1
3 * Copyright 2023 Percepio AB
4 * www.percepio.com
5 *
6 * SPDX-License-Identifier: Apache-2.0
7 */
8 
9 /**
10  * @file
11  *
12  * @brief Public trace print APIs.
13  */
14 
15 #ifndef TRC_PRINT_H
16 #define TRC_PRINT_H
17 
18 #if (TRC_USE_TRACEALYZER_RECORDER == 1)
19 
20 #if (TRC_CFG_RECORDER_MODE == TRC_RECORDER_MODE_STREAMING)
21 
22 #include <stdarg.h>
23 #include <trcTypes.h>
24 
25 #ifdef __cplusplus
26 extern "C" {
27 #endif
28 
29 /**
30  * @defgroup trace_print_apis Trace Print APIs
31  * @ingroup trace_recorder_apis
32  * @{
33  */
34 
35 #if (TRC_CFG_INCLUDE_USER_EVENTS == 1)
36 
37 typedef struct TracePrintData	/* Aligned */
38 {
39 	TraceStringHandle_t defaultChannel;
40 	TraceStringHandle_t consoleChannel;
41 } TracePrintData_t;
42 
43 /**
44  * @internal Initialize print trace system.
45  *
46  * @param[in] pxBuffer Pointer to memory that will be used by the print
47  * trace system.
48  *
49  * @retval TRC_FAIL Failure
50  * @retval TRC_SUCCESS Success
51  */
52 traceResult xTracePrintInitialize(TracePrintData_t* pxBuffer);
53 
54 /**
55  * @brief Generate a "User Event". Channel and format string are only stored in ELF.
56  *
57  * This is a compact version of xTracePrintF(). Only addresses to channel and format strings are stored and an ELF file must be provided to interpret the trace.
58  * NOTE! All parameters must be cast to TraceUnsignedBaseType_t/TraceBaseType_t!
59  *
60  * Example:
61  *	xTracePrintCompact("MyChannel", "MyFormat %d", 1);
62  *
63  * @param[in] szChannel Channel string.
64  * @param[in] szFormat Format string.
65  *
66  * @retval TRC_FAIL Failure
67  * @retval TRC_SUCCESS Success
68  */
69 traceResult xTracePrintCompactF(const char* szChannel, const char* szFormat, ...);
70 
71 /**
72  * @brief Generate a "User Event" with 0 parameters. Channel and format string are only stored in ELF.
73  *
74  * This is a compact and fixed version of xTracePrintF(). Only addresses to channel and format strings are stored and an ELF file must be provided to interpret the trace.
75  *
76  * Example:
77  *	xTraceDependencyRegister("my_project.elf", TRC_DEPENDENCY_TYPE_ELF);
78  *	...
79  *	xTracePrintCompactF0("MyChannel", "MyText");
80  *
81  * @param[in] szChannel Channel string.
82  * @param[in] szFormat Format string.
83  *
84  * @retval TRC_FAIL Failure
85  * @retval TRC_SUCCESS Success
86  */
87 #define xTracePrintCompactF0(szChannel, szFormat) xTraceEventCreate2(PSF_EVENT_USER_EVENT_FIXED, (TraceUnsignedBaseType_t)(szChannel), (TraceUnsignedBaseType_t)(szFormat))
88 
89 /**
90  * @brief Generate a "User Event" with 1 parameter. Channel and format string are only stored in ELF.
91  *
92  * This is a compact and fixed version of xTracePrintF(). Only addresses to channel and format strings are stored and an ELF file must be provided to interpret the trace.
93  *
94  * Example:
95  *	xTraceDependencyRegister("my_project.elf", TRC_DEPENDENCY_TYPE_ELF);
96  *	...
97  *	xTracePrintCompactF1("MyChannel", "MyFormat %u", 1);
98  *
99  * @param[in] szChannel Channel string.
100  * @param[in] szFormat Format string.
101  * @param[in] uxParam1 First parameter.
102  *
103  * @retval TRC_FAIL Failure
104  * @retval TRC_SUCCESS Success
105  */
106 #define xTracePrintCompactF1(szChannel, szFormat, uxParam1) xTraceEventCreate3(PSF_EVENT_USER_EVENT_FIXED + 1, (TraceUnsignedBaseType_t)(szChannel), (TraceUnsignedBaseType_t)(szFormat), uxParam1)
107 
108 /**
109  * @brief Generate a "User Event" with 2 parameters. Channel and format string are only stored in ELF.
110  *
111  * This is a compact and fixed version of xTracePrintF(). Only addresses to channel and format strings are stored and an ELF file must be provided to interpret the trace.
112  *
113  * Example
114  *	xTraceDependencyRegister("my_project.elf", TRC_DEPENDENCY_TYPE_ELF);
115  *	...
116  *	xTracePrintCompactF2("MyChannel", "MyFormat %u %u", 1, 2);
117  *
118  * @param[in] szChannel Channel string.
119  * @param[in] szFormat Format string.
120  * @param[in] uxParam1 First parameter.
121  * @param[in] uxParam2 Second parameter.
122  *
123  * @retval TRC_FAIL Failure
124  * @retval TRC_SUCCESS Success
125  */
126 #define xTracePrintCompactF2(szChannel, szFormat, uxParam1, uxParam2) xTraceEventCreate4(PSF_EVENT_USER_EVENT_FIXED + 2, (TraceUnsignedBaseType_t)(szChannel), (TraceUnsignedBaseType_t)(szFormat), uxParam1, uxParam2)
127 
128 /**
129  * @brief Generate a "User Event" with 3 parameters. Channel and format string are only stored in ELF.
130  *
131  * This is a compact and fixed version of xTracePrintF(). Only addresses to channel and format strings are stored and an ELF file must be provided to interpret the trace.
132  *
133  * Example:
134  *	xTraceDependencyRegister("my_project.elf", TRC_DEPENDENCY_TYPE_ELF);
135  *	...
136  *	xTracePrintCompactF3("MyChannel", "MyFormat %u %u %u", 1, 2, 3);
137  *
138  * @param[in] szChannel Channel string.
139  * @param[in] szFormat Format string.
140  * @param[in] uxParam1 First parameter.
141  * @param[in] uxParam2 Second parameter.
142  * @param[in] uxParam3 Third parameter.
143  *
144  * @retval TRC_FAIL Failure
145  * @retval TRC_SUCCESS Success
146  */
147 #define xTracePrintCompactF3(szChannel, szFormat, uxParam1, uxParam2, uxParam3) xTraceEventCreate5(PSF_EVENT_USER_EVENT_FIXED + 3, (TraceUnsignedBaseType_t)(szChannel), (TraceUnsignedBaseType_t)(szFormat), uxParam1, uxParam2, uxParam3)
148 
149 /**
150  * @brief Generate a "User Event" with 4 parameters. Channel and format string are only stored in ELF.
151  *
152  * This is a compact and fixed version of xTracePrintF(). Only addresses to channel and format strings are stored and an ELF file must be provided to interpret the trace.
153  *
154  * Example:
155  *	xTraceDependencyRegister("my_project.elf", TRC_DEPENDENCY_TYPE_ELF);
156  *	...
157  *	xTracePrintCompactF4("MyChannel", "MyFormat %u %u %u %u", 1, 2, 3, 4);
158  *
159  * @param[in] szChannel Channel string.
160  * @param[in] szFormat Format string.
161  * @param[in] uxParam1 First parameter.
162  * @param[in] uxParam2 Second parameter.
163  * @param[in] uxParam3 Third parameter.
164  * @param[in] uxParam4 Fourth parameter.
165  *
166  * @retval TRC_FAIL Failure
167  * @retval TRC_SUCCESS Success
168  */
169 #define xTracePrintCompactF4(szChannel, szFormat, uxParam1, uxParam2, uxParam3, uxParam4) xTraceEventCreate6(PSF_EVENT_USER_EVENT_FIXED + 4, (TraceUnsignedBaseType_t)(szChannel), (TraceUnsignedBaseType_t)(szFormat), uxParam1, uxParam2, uxParam3, uxParam4)
170 
171 /**
172  * @brief Generate a "User Event" with 0 parameters.
173  *
174  * This is a highly optimized version of xTracePrintF().
175  * The channel and format string must be registered using xTraceStringRegister().
176  *
177  * Example:
178  * 	TraceStringHandle_t xChannel;
179  * 	TraceStringHandle_t xHelloWorld;
180  *
181  *	xTraceStringRegister("MyChannel", &xChannel);
182  *	xTraceStringRegister("Hello world!", &xHelloWorld);
183  *	...
184  *	xTracePrintFormat0(xChannel, xHelloWorld);
185  *
186  * @param[in] xChannel Channel handle.
187  * @param[in] xFormatStringHandle Format string handle.
188  *
189  * @retval TRC_FAIL Failure
190  * @retval TRC_SUCCESS Success
191  */
192 #define xTracePrintF0(xChannelStringHandle, xFormatStringHandle) xTraceEventCreate2(PSF_EVENT_USER_EVENT_FIXED, (TraceUnsignedBaseType_t)(xChannelStringHandle), (TraceUnsignedBaseType_t)(xFormatStringHandle))
193 
194 /**
195  * @brief Generate a "User Event" with 1 parameter.
196  *
197  * This is a highly optimized version of xTracePrintF().
198  * The channel and format string must be registered using xTraceStringRegister().
199  *
200  * Example:
201  * 	TraceStringHandle_t xChannel;
202  * 	TraceStringHandle_t xHelloWorld;
203  *
204  *	xTraceStringRegister("MyChannel", &xChannel);
205  *	xTraceStringRegister("Hello world! %d", &xHelloWorld);
206  *	...
207  *	xTracePrintFormat1(xChannel, xHelloWorld, 1);
208  *
209  * @param[in] xChannel Channel handle.
210  * @param[in] xFormatStringHandle Format string handle.
211  * @param[in] uxParam1 First parameter.
212  *
213  * @retval TRC_FAIL Failure
214  * @retval TRC_SUCCESS Success
215  */
216 #define xTracePrintF1(xChannelStringHandle, xFormatStringHandle, uxParam1) xTraceEventCreate3(PSF_EVENT_USER_EVENT_FIXED + 1, (TraceUnsignedBaseType_t)(xChannelStringHandle), (TraceUnsignedBaseType_t)(xFormatStringHandle), uxParam1)
217 
218 /**
219  * @brief Generate a "User Event" with 2 parameters.
220  *
221  * This is a highly optimized version of xTracePrintF().
222  * The channel and format string must be registered using xTraceStringRegister().
223  *
224  * Example:
225  * 	TraceStringHandle_t xChannel;
226  * 	TraceStringHandle_t xHelloWorld;
227  *
228  *	xTraceStringRegister("MyChannel", &xChannel);
229  *	xTraceStringRegister("Hello world! %d %d", &xHelloWorld);
230  *	...
231  *	xTracePrintFormat2(xChannel, xHelloWorld, 1, 2);
232  *
233  * @param[in] xChannel Channel handle.
234  * @param[in] xFormatStringHandle Format string handle.
235  * @param[in] uxParam1 First parameter.
236  * @param[in] uxParam2 Second parameter.
237  *
238  * @retval TRC_FAIL Failure
239  * @retval TRC_SUCCESS Success
240  */
241 #define xTracePrintF2(xChannelStringHandle, xFormatStringHandle, uxParam1, uxParam2) xTraceEventCreate4(PSF_EVENT_USER_EVENT_FIXED + 2, (TraceUnsignedBaseType_t)(xChannelStringHandle), (TraceUnsignedBaseType_t)(xFormatStringHandle), uxParam1, uxParam2)
242 
243 /**
244  * @brief Generate a "User Event" with 3 parameters.
245  *
246  * This is a highly optimized version of xTracePrintF().
247  * The channel and format string must be registered using xTraceStringRegister().
248  *
249  * Example:
250  * 	TraceStringHandle_t xChannel;
251  * 	TraceStringHandle_t xHelloWorld;
252  *
253  *	xTraceStringRegister("MyChannel", &xChannel);
254  *	xTraceStringRegister("Hello world! %d %d %d", &xHelloWorld);
255  *	...
256  *	xTracePrintFormat3(xChannel, xHelloWorld, 1, 2, 3);
257  *
258  * @param[in] xChannel Channel handle.
259  * @param[in] xFormatStringHandle Format string handle.
260  * @param[in] uxParam1 First parameter.
261  * @param[in] uxParam2 Second parameter.
262  * @param[in] uxParam3 Third parameter.
263  *
264  * @retval TRC_FAIL Failure
265  * @retval TRC_SUCCESS Success
266  */
267 #define xTracePrintF3(xChannelStringHandle, xFormatStringHandle, uxParam1, uxParam2, uxParam3) xTraceEventCreate5(PSF_EVENT_USER_EVENT_FIXED + 3, (TraceUnsignedBaseType_t)(xChannelStringHandle), (TraceUnsignedBaseType_t)(xFormatStringHandle), uxParam1, uxParam2, uxParam3)
268 
269 /**
270  * @brief Generate a "User Event" with 4 parameters.
271  *
272  * This is a highly optimized version of xTracePrintF().
273  * The channel and format string must be registered using xTraceStringRegister().
274  *
275  * Example:
276  * 	TraceStringHandle_t xChannel;
277  * 	TraceStringHandle_t xHelloWorld;
278  *
279  *	xTraceStringRegister("MyChannel", &xChannel);
280  *	xTraceStringRegister("Hello world! %d %d %d %d", &xHelloWorld);
281  *	...
282  *	xTracePrintFormat4(xChannel, xHelloWorld, 1, 2, 3, 4);
283  *
284  * @param[in] xChannel Channel handle.
285  * @param[in] xFormatStringHandle Format string handle.
286  * @param[in] uxParam1 First parameter.
287  * @param[in] uxParam2 Second parameter.
288  * @param[in] uxParam3 Third parameter.
289  * @param[in] uxParam4 Fourth parameter.
290  *
291  * @retval TRC_FAIL Failure
292  * @retval TRC_SUCCESS Success
293  */
294 #define xTracePrintF4(xChannelStringHandle, xFormatStringHandle, uxParam1, uxParam2, uxParam3, uxParam4) xTraceEventCreate6(PSF_EVENT_USER_EVENT_FIXED + 4, (TraceUnsignedBaseType_t)(xChannelStringHandle), (TraceUnsignedBaseType_t)(xFormatStringHandle), uxParam1, uxParam2, uxParam3, uxParam4)
295 
296 /**
297  * @brief Generate "User Events" with unformatted text.
298  *
299  * User Events can be used for very efficient application logging, and are shown
300  * as yellow labels in the main trace view.
301  *
302  * You may group User Events into User Event Channels. The yellow User Event
303  * labels shows the logged string, preceded by the channel  name within
304  * brackets. For example:
305  *
306  *  "[MyChannel] Hello World!"
307  *
308  * The User Event Channels are shown in the View Filter, which makes it easy to
309  * select what User Events you wish to display. User Event Channels are created
310  * using xTraceStringRegister().
311  *
312  * Example:
313  *
314  *	 TraceStringHandle_t xChannel;
315  *	 xTraceStringRegister("MyChannel", &xChannel);
316  *	 ...
317  *	 xTracePrint(xChannel, "Hello World!");
318  *
319  * @param[in] xChannel Channel.
320  * @param[in] szString String.
321  *
322  * @retval TRC_FAIL Failure
323  * @retval TRC_SUCCESS Success
324  */
325 traceResult xTracePrint(TraceStringHandle_t xChannel, const char* szString);
326 
327 /**
328  * @brief Wrapper for xTracePrintF for printing to default channel.
329  *
330  * Wrapper for vTracePrintF, using the default channel. Can be used as a drop-in
331  * replacement for printf and similar functions, e.g. in a debug logging macro.
332  * NOTE! All parameters must be cast to TraceUnsignedBaseType_t/TraceBaseType_t!
333  *
334  * Example:
335  * 	// Old: #define LogString debug_console_printf
336  *
337  *  // New, log to Tracealyzer instead:
338  *  #define LogString xTraceConsoleChannelPrintF
339  *  ...
340  *  LogString("My value is: %d", myValue);
341  *
342  * @param[in] szFormat Format.
343  * @param[in] ... Parameters.
344  *
345  * @retval TRC_FAIL Failure
346  * @retval TRC_SUCCESS Success
347  */
348 traceResult xTraceConsoleChannelPrintF(const char* szFormat, ...);
349 
350 /**
351  * @brief Generates "User Events" with formatted text and data.
352  *
353  * Generates "User Events", with formatted text and data, similar to a "printf".
354  * It is very fast since the actual formatting is done on the host side when the
355  * trace is displayed.
356  *
357  * User Events can be used for very efficient application logging, and are shown
358  * as yellow labels in the main trace view.
359  * An advantage of User Events is that data can be plotted in the "User Event
360  * Signal Plot" view, visualizing any data you log as User Events, discrete
361  * states or control system signals (e.g. system inputs or outputs).
362  *
363  * You may group User Events into User Event Channels. The yellow User Event
364  * labels show the logged string, preceded by the channel name within brackets.
365  *
366  * Example:
367  *
368  *  "[MyChannel] Hello World!"
369  *
370  * The User Event Channels are shown in the View Filter, which makes it easy to
371  * select what User Events you wish to display. User Event Channels are created
372  * using xTraceStringRegister().
373  *
374  * Example:
375  *
376  *	 TraceStringHandle_t adc_uechannel;
377  *	 xTraceStringRegister("ADC User Events", &adc_uechannel);
378  *	 ...
379  *	 xTracePrintF(adc_uechannel,
380  *				 "ADC channel %d: %d volts",
381  *				 ch, adc_reading);
382  *
383  * NOTE! All data arguments are assumed to be TraceUnsignedBaseType_t/TraceBaseType_t. The following formats are
384  * supported:
385  * %d - signed integer. The following width and padding format is supported: "%05d" -> "-0042" and "%5d" -> "  -42"
386  * %u - unsigned integer. The following width and padding format is supported: "%05u" -> "00042" and "%5u" -> "   42"
387  * %X - hexadecimal (uppercase). The following width and padding format is supported: "%04X" -> "002A" and "%4X" -> "  2A"
388  * %x - hexadecimal (lowercase). The following width and padding format is supported: "%04x" -> "002a" and "%4x" -> "  2a"
389  * %s - string (currently, this must be an earlier stored symbol name)
390  *
391  * Up to 15 data arguments are allowed, with a total size of maximum 60 byte
392  * including 8 byte for the base event fields and the format string. So with
393  * one data argument, the maximum string length is 48 chars. If this is exceeded
394  * the string is truncated (4 bytes at a time).
395  *
396  * @param[in] xChannel Channel.
397  * @param[in] szFormat Format.
398  * @param[in] ... Parameters.
399  *
400  * @retval TRC_FAIL Failure
401  * @retval TRC_SUCCESS Success
402  */
403 traceResult xTracePrintF(TraceStringHandle_t xChannel, const char* szFormat, ...);
404 
405 /**
406  * @brief Generates "User Events" with formatted text and data.
407  *
408  * @param[in] xChannel Channel.
409  * @param[in] szFormat Format.
410  * @param[in] pxVariableList Pointer to variable list arguments.
411  *
412  * @retval TRC_FAIL Failure
413  * @retval TRC_SUCCESS Success
414  */
415 traceResult xTraceVPrintF(TraceStringHandle_t xChannel, const char* szFormat, va_list* pxVariableList);
416 
417 #else
418 
419 typedef struct TracePrintData
420 {
421 	TraceUnsignedBaseType_t buffer[1];
422 } TracePrintData_t;
423 
424 #define xTracePrintInitialize(p) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_2((void)p, p != 0 ? TRC_SUCCESS : TRC_FAIL)
425 
426 #define xTracePrint(_c, _s) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_3((void)(_c), (void)(_s), TRC_SUCCESS)
427 
428 #define xTracePrintF(_c, _s, ...) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_3((void)(_c), (void)(_s), TRC_SUCCESS)
429 
430 #define xTraceConsoleChannelPrintF(_s, ...) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_2((void)(_s), TRC_SUCCESS)
431 
432 #define xTraceVPrintF(_c, _s, _v) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_4((void)(_c), (void)(_s), (void)(_v), TRC_SUCCESS)
433 
434 #define xTracePrintF0(_c, _f) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_3((void)(_c), (void)(_f), TRC_SUCCESS)
435 #define xTracePrintF1(_c, _f, _p1) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_4((void)(_c), (void)(_f), (void)(_p1), TRC_SUCCESS)
436 #define xTracePrintF2(_c, _f, _p1, _p2) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_5((void)(_c), (void)(_f), (void)(_p1), (void)(_p2), TRC_SUCCESS)
437 #define xTracePrintF3(_c, _f, _p1, _p2, _p3) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_6((void)(_c), (void)(_f), (void)(_p1), (void)(_p2), (void)(_p3), TRC_SUCCESS)
438 #define xTracePrintF4(_c, _f, _p1, _p2, _p3, _p4) TRC_COMMA_EXPR_TO_STATEMENT_EXPR_7((void)(_c), (void)(_f), (void)(_p1), (void)(_p2), (void)(_p3), (void)(_p4), TRC_SUCCESS)
439 
440 #define xTracePrintCompactF xTracePrintF
441 #define xTracePrintCompactF0 xTracePrintF0
442 #define xTracePrintCompactF1 xTracePrintF1
443 #define xTracePrintCompactF2 xTracePrintF2
444 #define xTracePrintCompactF3 xTracePrintF3
445 #define xTracePrintCompactF4 xTracePrintF4
446 
447 #endif
448 
449 /** @} */
450 
451 #ifdef __cplusplus
452 }
453 #endif
454 
455 #endif
456 
457 #endif
458 
459 
460 #endif
461