xref: /dpdk/doc/guides/prog_guide/trace_lib.rst (revision 24cd1b529f35f106d323ebdd4df0203261824dcc)
1..  SPDX-License-Identifier: BSD-3-Clause
2    Copyright(C) 2020 Marvell International Ltd.
3
4Trace Library
5=============
6
7Overview
8--------
9
10*Tracing* is a technique used to understand what goes on in a running software
11system. The software used for tracing is called a *tracer*, which is
12conceptually similar to a tape recorder.
13When recording, specific instrumentation points placed in the software source
14code generate events that are saved on a giant tape: a trace file.
15The trace file then later can be opened in *trace viewers* to visualize and
16analyze the trace events with timestamps and multi-core views.
17Such a mechanism will be useful for resolving a wide range of problems such as
18multi-core synchronization issues, latency measurements, finding out the
19post analysis information like CPU idle time, etc that would otherwise be
20extremely challenging to get.
21
22Tracing is often compared to *logging*. However, tracers and loggers are two
23different tools, serving two different purposes.
24Tracers are designed to record much lower-level events that occur much more
25frequently than log messages, often in the range of thousands per second, with
26very little execution overhead.
27Logging is more appropriate for a very high-level analysis of less frequent
28events: user accesses, exceptional conditions (errors and warnings, for
29example), database transactions, instant messaging communications, and such.
30Simply put, logging is one of the many use cases that can be satisfied with
31tracing.
32
33DPDK tracing library features
34-----------------------------
35
36- A framework to add tracepoints in control and fast path APIs with minimum
37  impact on performance.
38  Typical trace overhead is ~20 cycles and instrumentation overhead is 1 cycle.
39- Enable and disable the tracepoints at runtime.
40- Save the trace buffer to the filesystem at any point in time.
41- Support ``overwrite`` and ``discard`` trace mode operations.
42- String-based tracepoint object lookup.
43- Enable and disable a set of tracepoints based on regular expression and/or
44  globbing.
45- Generate trace in ``Common Trace Format (CTF)``. ``CTF`` is an open-source
46  trace format and is compatible with ``LTTng``.
47  For detailed information, refer to
48  `Common Trace Format <https://diamon.org/ctf/>`_.
49
50How to add a tracepoint?
51------------------------
52
53This section steps you through the details of adding a simple tracepoint.
54
55.. _create_tracepoint_header_file:
56
57Create the tracepoint header file
58~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
59
60.. code-block:: c
61
62 #include <rte_trace_point.h>
63
64 RTE_TRACE_POINT(
65        app_trace_string,
66        RTE_TRACE_POINT_ARGS(const char *str),
67        rte_trace_point_emit_string(str);
68 )
69
70The above macro creates ``app_trace_string`` tracepoint.
71The user can choose any name for the tracepoint.
72However, when adding a tracepoint in the DPDK library, the
73``rte_<library_name>_trace_[<domain>_]<name>`` naming convention must be
74followed.
75The examples are ``rte_eal_trace_generic_str``, ``rte_mempool_trace_create``.
76
77The ``RTE_TRACE_POINT`` macro expands from above definition as the following
78function template:
79
80.. code-block:: c
81
82 static __rte_always_inline void
83 app_trace_string(const char *str)
84 {
85         /* Trace subsystem hooks */
86         ...
87         rte_trace_point_emit_string(str);
88 }
89
90The consumer of this tracepoint can invoke
91``app_trace_string(const char *str)`` to emit the trace event to the trace
92buffer.
93
94Register the tracepoint
95~~~~~~~~~~~~~~~~~~~~~~~
96
97.. code-block:: c
98
99 #include <rte_trace_point_register.h>
100
101 #include <my_tracepoint.h>
102
103 RTE_TRACE_POINT_DEFINE(app_trace_string);
104
105 RTE_INIT(app_trace_init)
106 {
107       RTE_TRACE_POINT_REGISTER(app_trace_string, app.trace.string);
108 }
109
110The above code snippet registers the ``app_trace_string`` tracepoint to
111trace library. Here, the ``my_tracepoint.h`` is the header file
112that the user created in the first step :ref:`create_tracepoint_header_file`.
113
114The second argument for the ``RTE_TRACE_POINT_REGISTER`` is the name for the
115tracepoint. This string will be used for tracepoint lookup or regular
116expression and/or glob based tracepoint operations.
117There is no requirement for the tracepoint function and its name to be similar.
118However, it is recommended to have a similar name for a better naming
119convention.
120
121The user must register the tracepoint before the ``rte_eal_init`` invocation.
122The user can use the ``RTE_INIT`` construction scheme to achieve this.
123
124.. note::
125
126   The ``rte_trace_point_register.h`` header must be included before any
127   inclusion of the ``rte_trace_point.h`` header.
128
129.. note::
130
131   The ``RTE_TRACE_POINT_DEFINE`` defines the placeholder for the
132   ``rte_trace_point_t`` tracepoint object. The user must export a
133   ``__<trace_function_name>`` symbol in the library ``.map`` file for this
134   tracepoint to be used out of the library, in shared builds.
135   For example, ``__app_trace_string`` will be the exported symbol in the
136   above example.
137
138Fast path tracepoint
139--------------------
140
141In order to avoid performance impact in fast path code, the library introduced
142``RTE_TRACE_POINT_FP``. When adding the tracepoint in fast path code,
143the user must use ``RTE_TRACE_POINT_FP`` instead of ``RTE_TRACE_POINT``.
144
145``RTE_TRACE_POINT_FP`` is compiled out by default and it can be enabled using
146``CONFIG_RTE_ENABLE_TRACE_FP`` configuration parameter.
147The ``enable_trace_fp`` option shall be used for the same for meson build.
148
149Event record mode
150-----------------
151
152Event record mode is an attribute of trace buffers. Trace library exposes the
153following modes:
154
155Overwrite
156   When the trace buffer is full, new trace events overwrites the existing
157   captured events in the trace buffer.
158Discard
159   When the trace buffer is full, new trace events will be discarded.
160
161The mode can be configured either using EAL command line parameter
162``--trace-mode`` on application boot up or use ``rte_trace_mode_set()`` API to
163configure at runtime.
164
165Trace file location
166-------------------
167
168On ``rte_trace_save()`` or ``rte_eal_cleanup()`` invocation, the library saves
169the trace buffers to the filesystem. By default, the trace files are stored in
170``$HOME/dpdk-traces/rte-yyyy-mm-dd-[AP]M-hh-mm-ss/``.
171It can be overridden by the ``--trace-dir=<directory path>`` EAL command line
172option.
173
174For more information, refer to :doc:`../linux_gsg/linux_eal_parameters` for
175trace EAL command line options.
176
177View and analyze the recorded events
178------------------------------------
179
180Once the trace directory is available, the user can view/inspect the recorded
181events.
182
183There are many tools you can use to read DPDK traces:
184
1851. ``babeltrace`` is a command-line utility that converts trace formats; it
186supports the format that DPDK trace library produces, CTF, as well as a
187basic text output that can be grep'ed.
188The babeltrace command is part of the Open Source Babeltrace project.
189
1902. ``Trace Compass`` is a graphical user interface for viewing and analyzing
191any type of logs or traces, including DPDK traces.
192
193Use the babeltrace command-line tool
194~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
195
196The simplest way to list all the recorded events of a trace is to pass its path
197to babeltrace with no options::
198
199    babeltrace </path-to-trace-events/rte-yyyy-mm-dd-[AP]M-hh-mm-ss/>
200
201``babeltrace`` finds all traces recursively within the given path and prints
202all their events, merging them in chronological order.
203
204You can pipe the output of the babeltrace into a tool like grep(1) for further
205filtering. Below example grep the events for ``ethdev`` only::
206
207    babeltrace /tmp/my-dpdk-trace | grep ethdev
208
209You can pipe the output of babeltrace into a tool like wc(1) to count the
210recorded events. Below example count the number of ``ethdev`` events::
211
212    babeltrace /tmp/my-dpdk-trace | grep ethdev | wc --lines
213
214Use the tracecompass GUI tool
215~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
216
217``Tracecompass`` is another tool to view/analyze the DPDK traces which gives
218a graphical view of events. Like ``babeltrace``, tracecompass also provides
219an interface to search for a particular event.
220To use ``tracecompass``, following are the minimum required steps:
221
222- Install ``tracecompass`` to the localhost. Variants are available for Linux,
223  Windows, and OS-X.
224- Launch ``tracecompass`` which will open a graphical window with trace
225  management interfaces.
226- Open a trace using ``File->Open Trace`` option and select metadata file which
227  is to be viewed/analyzed.
228
229For more details, refer
230`Trace Compass <https://www.eclipse.org/tracecompass/>`_.
231
232Quick start
233-----------
234
235This section steps you through the details of generating trace and viewing it.
236
237- Start the dpdk-test::
238
239    echo "quit" | ./build/app/test/dpdk-test --no-huge --trace=.*
240
241- View the traces with babeltrace viewer::
242
243    babeltrace $HOME/dpdk-traces/rte-yyyy-mm-dd-[AP]M-hh-mm-ss/
244
245Implementation details
246----------------------
247
248As DPDK trace library is designed to generate traces that uses ``Common Trace
249Format (CTF)``. ``CTF`` specification consists of the following units to create
250a trace.
251
252- ``Stream`` Sequence of packets.
253- ``Packet`` Header and one or more events.
254- ``Event`` Header and payload.
255
256For detailed information, refer to
257`Common Trace Format <https://diamon.org/ctf/>`_.
258
259The implementation details broadly divided into the following areas:
260
261Trace metadata creation
262~~~~~~~~~~~~~~~~~~~~~~~
263
264Based on the ``CTF`` specification, one of a CTF trace's streams is mandatory:
265the metadata stream. It contains exactly what you would expect: data about the
266trace itself. The metadata stream contains a textual description of the binary
267layouts of all the other streams.
268
269This description is written using the Trace Stream Description Language (TSDL),
270a declarative language that exists only in the realm of CTF.
271The purpose of the metadata stream is to make CTF readers know how to parse a
272trace's binary streams of events without CTF specifying any fixed layout.
273The only stream layout known in advance is, in fact, the metadata stream's one.
274
275The internal ``trace_metadata_create()`` function generates the metadata.
276
277Trace memory
278~~~~~~~~~~~~
279
280The trace memory will be allocated through an internal function
281``__rte_trace_mem_per_thread_alloc()``. The trace memory will be allocated
282per thread to enable lock less trace-emit function.
283The memory for the trace memory for DPDK lcores will be allocated on
284``rte_eal_init()`` if the trace is enabled through a EAL option.
285For non DPDK threads, on the first trace emission, the memory will be
286allocated.
287
288Trace memory layout
289~~~~~~~~~~~~~~~~~~~
290
291.. _table_trace_mem_layout:
292
293.. table:: Trace memory layout.
294
295  +-------------------+
296  |   packet.header   |
297  +-------------------+
298  |   packet.context  |
299  +-------------------+
300  |   trace 0 header  |
301  +-------------------+
302  |   trace 0 payload |
303  +-------------------+
304  |   trace 1 header  |
305  +-------------------+
306  |   trace 1 payload |
307  +-------------------+
308  |   trace N header  |
309  +-------------------+
310  |   trace N payload |
311  +-------------------+
312
313packet.header
314^^^^^^^^^^^^^
315
316.. _table_packet_header:
317
318.. table:: Packet header layout.
319
320  +-------------------+
321  |   uint32_t magic  |
322  +-------------------+
323  |   rte_uuid_t uuid |
324  +-------------------+
325
326packet.context
327^^^^^^^^^^^^^^
328
329.. _table_packet_context:
330
331.. table:: Packet context layout.
332
333  +----------------------+
334  |  uint32_t thread_id  |
335  +----------------------+
336  | char thread_name[32] |
337  +----------------------+
338
339trace.header
340^^^^^^^^^^^^
341
342.. _table_trace_header:
343
344.. table:: Trace header layout.
345
346  +----------------------+
347  | event_id  [63:48]    |
348  +----------------------+
349  | timestamp [47:0]     |
350  +----------------------+
351
352The trace header is 64 bits, it consists of 48 bits of timestamp and 16 bits
353event ID.
354
355The ``packet.header`` and ``packet.context`` will be written in the slow path
356at the time of trace memory creation. The ``trace.header`` and trace payload
357will be emitted when the tracepoint function is invoked.
358