| .. SPDX-License-Identifier: GPL-2.0 |
| |
| =============== |
| Tracing Remotes |
| =============== |
| |
| :Author: Vincent Donnefort <vdonnefort@google.com> |
| |
| Overview |
| ======== |
| Firmware and hypervisors are black boxes to the kernel. Having a way to see what |
| they are doing can be useful to debug both. This is where remote tracing buffers |
| come in. A remote tracing buffer is a ring buffer executed by the firmware or |
| hypervisor into memory that is memory mapped to the host kernel. This is similar |
| to how user space memory maps the kernel ring buffer but in this case the kernel |
| is acting like user space and the firmware or hypervisor is the "kernel" side. |
| With a trace remote ring buffer, the firmware and hypervisor can record events |
| for which the host kernel can see and expose to user space. |
| |
| Register a remote |
| ================= |
| A remote must provide a set of callbacks `struct trace_remote_callbacks` whom |
| description can be found below. Those callbacks allows Tracefs to enable and |
| disable tracing and events, to load and unload a tracing buffer (a set of |
| ring-buffers) and to swap a reader page with the head page, which enables |
| consuming reading. |
| |
| .. kernel-doc:: include/linux/trace_remote.h |
| |
| Once registered, an instance will appear for this remote in the Tracefs |
| directory **remotes/**. Buffers can then be read using the usual Tracefs files |
| **trace_pipe** and **trace**. |
| |
| Declare a remote event |
| ====================== |
| Macros are provided to ease the declaration of remote events, in a similar |
| fashion to in-kernel events. A declaration must provide an ID, a description of |
| the event arguments and how to print the event: |
| |
| .. code-block:: c |
| |
| REMOTE_EVENT(foo, EVENT_FOO_ID, |
| RE_STRUCT( |
| re_field(u64, bar) |
| ), |
| RE_PRINTK("bar=%lld", __entry->bar) |
| ); |
| |
| Then those events must be declared in a C file with the following: |
| |
| .. code-block:: c |
| |
| #define REMOTE_EVENT_INCLUDE_FILE foo_events.h |
| #include <trace/define_remote_events.h> |
| |
| This will provide a `struct remote_event remote_event_foo` that can be given to |
| `trace_remote_register`. |
| |
| Registered events appear in the remote directory under **events/**. |
| |
| Simple ring-buffer |
| ================== |
| A simple implementation for a ring-buffer writer can be found in |
| kernel/trace/simple_ring_buffer.c. |
| |
| .. kernel-doc:: include/linux/simple_ring_buffer.h |