The tracing service is a long-lived entity (a system daemon on Linux/Android, a service in Chrome) that has the following responsibilities:
A producer is an untrusted entity that offers the ability to contribute to the trace. In a multiprocess model, a producer almost always corresponds to a client process of the tracing service. It advertises its ability to contribute to the trace with one or more data sources. Each producer has exactly:
A producer is completely decoupled (both technically and conceptually) from consumer(s). A producer knows nothing about:
NOTE: In rare circumstances a process can host more than one producer and hence more than one shared memory buffer. This can be the case for a process bundling third-party libraries that in turn include the Perfetto client library.
Concrete example: at some point in the future Chrome might expose one Producer for tracing within the main project, one for V8 and one for Skia (for each child process).
A consumer is a trusted entity (a cmdline client on Linux/Android, an interface of the Browser process in Chrome) that controls (non-exclusively) the tracing service and reads back (destructively) the trace buffers. A consumer has the ability to:
A data source is a capability, exposed by a Producer, of providing some tracing data. A data source almost always defines its own schema (a protobuf) consisting of:
Different producers may expose the same data source. Concrete example:
At some point in the near future we might offer, as part of Perfetto, a library for in-process heap profiling. In such case more than one producer, linking against the updated Perfetto library, will expose the heap profiler data source, for its own process. **
In a multiprocess scenario, each producer and each consumer interact with the service using an IPC channel. IPC is used only in non-fast-path interactions, mostly handshakes such as enabling/disabling trace (consumer), (un)registering and starting/stopping data sources (producer). The IPC is typically NOT employed to transport the protobufs for the trace. Perfetto provides a POSIX-friendly IPC implementation, based on protobufs over a UNIX socket (see Socket protocol).
That IPC implementation is not mandated. Perfetto allows the embedder:
PostTask(s)
.Producer(s) write tracing data, in the form of protobuf-encoded binary blobs, directly into its shared memory buffer, using a special library called ProtoZero. The shared memory buffer:
Each chunk:
TracePacket(s)
, or fragments of that. A TracePacket
can span across several chunks, the fragmentation is not exposed to the consumers (consumers always see whole packets as if they were never fragmented).TraceWriter
.WriterID
: packets in a sequence are guaranteed to be read back in order, without gaps and without repetitions.See the comments in shared_memory_abi.h for more details about the binary format of this buffer.