// Copyright 2016 The Fuchsia Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. library fuchsia.tracelink; using zx; // The provider interface which applications must implement and register // with the |TraceRegistry| to participate in tracing. // // See //zircon/system/ulib/trace-provider/ for a C++ implementation of // this interface which can easily be configured by an application. interface Provider { // Starts writing trace records for events in the specified |categories| // into |buffer| using |fifo| for signaling. // // |buffering_mode| specifies what happens when the buffer fills. // ONESHOT: The provider must stop tracing. // CIRCULAR: Continue tracing, dropping oldest records to make room // for new ones. // STREAMING: As the buffer fills notify TraceManager that it needs to be // saved so that tracing can continue without dropping records. Whether // records get dropped depends on how fast TraceManager is able to save // intermediate buffers. No guarantee is made that records won't be // dropped. Coordination of the saving of buffers is done via |fifo|. // See trace-provider/provider.h for details. // // When the trace provider observes |ZX_FIFO_PEER_CLOSED| on |fifo|, it must // assume the trace manager has terminated abnormally (since |Stop| was // not received as usual) and stop tracing automatically, discarding // any in-flight trace data. // // At most one trace can be running at a time. If the trace provider // receives a request to start tracing while already tracing, it must // ignore the request. // // There is no result. If the provider successfully starts it must send a // TRACE_PROVIDER_STARTED packet on |fifo|. // #include to get |TRACE_PROVIDER_STARTED|. // To indicate failure to start close |fifo|. 1: Start(BufferingMode buffering_mode, handle buffer, handle fifo, vector:100 categories); // Stops tracing. // // Once the provider has finished writing any final events to the trace // buffer, it must close both |buffer| and |fifo| to indicate to the trace // manager that tracing is finished. 2: Stop(); }; // The service which trace providers use to register themselves with // the tracing system. // Note that one property of this interface is that once registration is made // the provider can drop this connection. [Discoverable, Layout="Simple"] interface Registry { // Registers the trace provider. // Note: Registration is asynchronous, it's only at some point after this // returns that the provider is actually registered. // To unregister, simply close the TraceProvider pipe. 1: RegisterTraceProviderDeprecated(Provider provider); // Registers the trace provider. // Note: Registration is asynchronous, it's only at some point after this // returns that the provider is actually registered. // To unregister, simply close the TraceProvider pipe. 2: RegisterTraceProvider(Provider provider, zx.koid pid, string:100 name); // Registers the trace provider synchronously. The call doesn't return // until the provider is registered. // On return |s| is ZX_OK if registration was successful. // |started| is true if tracing has already started, which is a hint to // the provider to wait for the Start() message before continuing if it // wishes to not drop trace records before Start() is received. // To unregister, simply close the TraceProvider pipe. 3: RegisterTraceProviderSynchronously(Provider provider, zx.koid pid, string:100 name) -> (zx.status s, bool started); }; // The trace buffering mode. enum BufferingMode : uint8 { // In oneshot mode there is only one buffer that is not reused. When the // buffer fills the provider just keeps dropping records, keeping a count, // and then when tracing stops the header is updated to record final state. ONESHOT = 0; // In circular mode, the buffer is effectively split into two pieces. // When a buffer fills writing immediately continues with the other // buffer, and this continues until tracing stops. CIRCULAR = 1; // In streaming mode, the buffer is effectively split into two pieces. // When a buffer fills the provider: // - TODO(dje): Say more here. // and then, when the buffer is saved, the manager: // - TODO(dje): Say more here. // If the manager hasn't saved the buffer in time, and the other buffer // fills, then the provider is required to keep dropping records until // the buffer is ready. STREAMING = 2; };