xref: /aosp_15_r20/external/perfetto/src/perfetto_cmd/perfetto_cmd.h (revision 6dbdd20afdafa5e3ca9b8809fa73465d530080dc)
1*6dbdd20aSAndroid Build Coastguard Worker /*
2*6dbdd20aSAndroid Build Coastguard Worker  * Copyright (C) 2018 The Android Open Source Project
3*6dbdd20aSAndroid Build Coastguard Worker  *
4*6dbdd20aSAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
5*6dbdd20aSAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
6*6dbdd20aSAndroid Build Coastguard Worker  * You may obtain a copy of the License at
7*6dbdd20aSAndroid Build Coastguard Worker  *
8*6dbdd20aSAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
9*6dbdd20aSAndroid Build Coastguard Worker  *
10*6dbdd20aSAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
11*6dbdd20aSAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
12*6dbdd20aSAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*6dbdd20aSAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
14*6dbdd20aSAndroid Build Coastguard Worker  * limitations under the License.
15*6dbdd20aSAndroid Build Coastguard Worker  */
16*6dbdd20aSAndroid Build Coastguard Worker 
17*6dbdd20aSAndroid Build Coastguard Worker #ifndef SRC_PERFETTO_CMD_PERFETTO_CMD_H_
18*6dbdd20aSAndroid Build Coastguard Worker #define SRC_PERFETTO_CMD_PERFETTO_CMD_H_
19*6dbdd20aSAndroid Build Coastguard Worker 
20*6dbdd20aSAndroid Build Coastguard Worker #include <cstdint>
21*6dbdd20aSAndroid Build Coastguard Worker #include <functional>
22*6dbdd20aSAndroid Build Coastguard Worker #include <list>
23*6dbdd20aSAndroid Build Coastguard Worker #include <memory>
24*6dbdd20aSAndroid Build Coastguard Worker #include <optional>
25*6dbdd20aSAndroid Build Coastguard Worker #include <string>
26*6dbdd20aSAndroid Build Coastguard Worker #include <vector>
27*6dbdd20aSAndroid Build Coastguard Worker 
28*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/base/build_config.h"
29*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/event_fd.h"
30*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/pipe.h"
31*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/scoped_file.h"
32*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/thread_task_runner.h"
33*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/unix_task_runner.h"
34*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/uuid.h"
35*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/weak_ptr.h"
36*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/tracing/core/basic_types.h"
37*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/tracing/core/consumer.h"
38*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/tracing/ipc/consumer_ipc_client.h"
39*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/tracing/core/forward_decls.h"
40*6dbdd20aSAndroid Build Coastguard Worker #include "src/android_stats/perfetto_atoms.h"
41*6dbdd20aSAndroid Build Coastguard Worker #include "src/perfetto_cmd/packet_writer.h"
42*6dbdd20aSAndroid Build Coastguard Worker 
43*6dbdd20aSAndroid Build Coastguard Worker namespace perfetto {
44*6dbdd20aSAndroid Build Coastguard Worker 
45*6dbdd20aSAndroid Build Coastguard Worker // Directory for local state and temporary files. This is automatically
46*6dbdd20aSAndroid Build Coastguard Worker // created by the system by setting setprop persist.traced.enable=1.
47*6dbdd20aSAndroid Build Coastguard Worker extern const char* kStateDir;
48*6dbdd20aSAndroid Build Coastguard Worker 
49*6dbdd20aSAndroid Build Coastguard Worker class PerfettoCmd : public Consumer {
50*6dbdd20aSAndroid Build Coastguard Worker  public:
51*6dbdd20aSAndroid Build Coastguard Worker   PerfettoCmd();
52*6dbdd20aSAndroid Build Coastguard Worker   ~PerfettoCmd() override;
53*6dbdd20aSAndroid Build Coastguard Worker 
54*6dbdd20aSAndroid Build Coastguard Worker   // The main() is split in two stages: cmdline parsing and actual interaction
55*6dbdd20aSAndroid Build Coastguard Worker   // with traced. This is to allow tools like tracebox to avoid spawning the
56*6dbdd20aSAndroid Build Coastguard Worker   // service for no reason if the cmdline parsing fails.
57*6dbdd20aSAndroid Build Coastguard Worker   // Return value:
58*6dbdd20aSAndroid Build Coastguard Worker   //   std::nullopt: no error, the caller should call
59*6dbdd20aSAndroid Build Coastguard Worker   //   ConnectToServiceRunAndMaybeNotify.
60*6dbdd20aSAndroid Build Coastguard Worker   //   0-N: the caller should exit() with the given exit code.
61*6dbdd20aSAndroid Build Coastguard Worker   std::optional<int> ParseCmdlineAndMaybeDaemonize(int argc, char** argv);
62*6dbdd20aSAndroid Build Coastguard Worker   int ConnectToServiceRunAndMaybeNotify();
63*6dbdd20aSAndroid Build Coastguard Worker 
64*6dbdd20aSAndroid Build Coastguard Worker   // perfetto::Consumer implementation.
65*6dbdd20aSAndroid Build Coastguard Worker   void OnConnect() override;
66*6dbdd20aSAndroid Build Coastguard Worker   void OnDisconnect() override;
67*6dbdd20aSAndroid Build Coastguard Worker   void OnTracingDisabled(const std::string& error) override;
68*6dbdd20aSAndroid Build Coastguard Worker   void OnTraceData(std::vector<TracePacket>, bool has_more) override;
69*6dbdd20aSAndroid Build Coastguard Worker   void OnDetach(bool) override;
70*6dbdd20aSAndroid Build Coastguard Worker   void OnAttach(bool, const TraceConfig&) override;
71*6dbdd20aSAndroid Build Coastguard Worker   void OnTraceStats(bool, const TraceStats&) override;
72*6dbdd20aSAndroid Build Coastguard Worker   void OnObservableEvents(const ObservableEvents&) override;
73*6dbdd20aSAndroid Build Coastguard Worker   void OnSessionCloned(const OnSessionClonedArgs&) override;
74*6dbdd20aSAndroid Build Coastguard Worker 
SignalCtrlC()75*6dbdd20aSAndroid Build Coastguard Worker   void SignalCtrlC() { ctrl_c_evt_.Notify(); }
76*6dbdd20aSAndroid Build Coastguard Worker 
77*6dbdd20aSAndroid Build Coastguard Worker  private:
78*6dbdd20aSAndroid Build Coastguard Worker   struct SnapshotTriggerInfo;
79*6dbdd20aSAndroid Build Coastguard Worker 
80*6dbdd20aSAndroid Build Coastguard Worker   enum CloneThreadMode { kSingleExtraThread, kNewThreadPerRequest };
81*6dbdd20aSAndroid Build Coastguard Worker 
82*6dbdd20aSAndroid Build Coastguard Worker   bool OpenOutputFile();
83*6dbdd20aSAndroid Build Coastguard Worker   void SetupCtrlCSignalHandler();
84*6dbdd20aSAndroid Build Coastguard Worker   void FinalizeTraceAndExit();
85*6dbdd20aSAndroid Build Coastguard Worker   void PrintUsage(const char* argv0);
86*6dbdd20aSAndroid Build Coastguard Worker   void PrintServiceState(bool success, const TracingServiceState&);
87*6dbdd20aSAndroid Build Coastguard Worker   void CloneAllBugreportTraces(bool success, const TracingServiceState&);
88*6dbdd20aSAndroid Build Coastguard Worker 
89*6dbdd20aSAndroid Build Coastguard Worker   void CloneSessionOnThread(TracingSessionID,
90*6dbdd20aSAndroid Build Coastguard Worker                             const std::string& cmdline,  // \0 separated.
91*6dbdd20aSAndroid Build Coastguard Worker                             CloneThreadMode,
92*6dbdd20aSAndroid Build Coastguard Worker                             const std::optional<SnapshotTriggerInfo>& trigger,
93*6dbdd20aSAndroid Build Coastguard Worker                             std::function<void()> on_clone_callback);
94*6dbdd20aSAndroid Build Coastguard Worker   void OnTimeout();
is_detach()95*6dbdd20aSAndroid Build Coastguard Worker   bool is_detach() const { return !detach_key_.empty(); }
is_attach()96*6dbdd20aSAndroid Build Coastguard Worker   bool is_attach() const { return !attach_key_.empty(); }
is_clone()97*6dbdd20aSAndroid Build Coastguard Worker   bool is_clone() const {
98*6dbdd20aSAndroid Build Coastguard Worker     return clone_tsid_.has_value() || !clone_name_.empty();
99*6dbdd20aSAndroid Build Coastguard Worker   }
100*6dbdd20aSAndroid Build Coastguard Worker 
101*6dbdd20aSAndroid Build Coastguard Worker   // Once we call ReadBuffers we expect one or more calls to OnTraceData
102*6dbdd20aSAndroid Build Coastguard Worker   // with the last call having |has_more| set to false. However we should
103*6dbdd20aSAndroid Build Coastguard Worker   // gracefully handle the service failing to ever call OnTraceData or
104*6dbdd20aSAndroid Build Coastguard Worker   // setting |has_more| incorrectly. To do this we maintain a timeout
105*6dbdd20aSAndroid Build Coastguard Worker   // which finalizes and exits the client if we don't receive OnTraceData
106*6dbdd20aSAndroid Build Coastguard Worker   // within OnTraceDataTimeoutMs of when we expected to.
107*6dbdd20aSAndroid Build Coastguard Worker   void CheckTraceDataTimeout();
108*6dbdd20aSAndroid Build Coastguard Worker 
109*6dbdd20aSAndroid Build Coastguard Worker   int ConnectToServiceAndRun();
110*6dbdd20aSAndroid Build Coastguard Worker 
111*6dbdd20aSAndroid Build Coastguard Worker   void ReadbackTraceDataAndQuit(const std::string& error);
112*6dbdd20aSAndroid Build Coastguard Worker 
113*6dbdd20aSAndroid Build Coastguard Worker   enum BgProcessStatus : char {
114*6dbdd20aSAndroid Build Coastguard Worker     kBackgroundOk = 0,
115*6dbdd20aSAndroid Build Coastguard Worker     kBackgroundOtherError = 1,
116*6dbdd20aSAndroid Build Coastguard Worker     kBackgroundTimeout = 2,
117*6dbdd20aSAndroid Build Coastguard Worker   };
118*6dbdd20aSAndroid Build Coastguard Worker 
119*6dbdd20aSAndroid Build Coastguard Worker   // Used to implement the --background-wait flag.
120*6dbdd20aSAndroid Build Coastguard Worker   //
121*6dbdd20aSAndroid Build Coastguard Worker   // Waits (up to 30s) for the child process to signal (success or an error).
122*6dbdd20aSAndroid Build Coastguard Worker   //
123*6dbdd20aSAndroid Build Coastguard Worker   // Returns the status received from the child process or kTimeout, in case of
124*6dbdd20aSAndroid Build Coastguard Worker   // timeout.
125*6dbdd20aSAndroid Build Coastguard Worker   BgProcessStatus WaitOnBgProcessPipe();
126*6dbdd20aSAndroid Build Coastguard Worker 
127*6dbdd20aSAndroid Build Coastguard Worker   // Used to implement the --background-wait flag.
128*6dbdd20aSAndroid Build Coastguard Worker   //
129*6dbdd20aSAndroid Build Coastguard Worker   // Signals the parent process (if there is one) that it can exit (successfully
130*6dbdd20aSAndroid Build Coastguard Worker   // or with an error).
131*6dbdd20aSAndroid Build Coastguard Worker   //
132*6dbdd20aSAndroid Build Coastguard Worker   // Only the first time this function is called is significant. Further calls
133*6dbdd20aSAndroid Build Coastguard Worker   // will have no effect.
134*6dbdd20aSAndroid Build Coastguard Worker   void NotifyBgProcessPipe(BgProcessStatus status);
135*6dbdd20aSAndroid Build Coastguard Worker 
136*6dbdd20aSAndroid Build Coastguard Worker   void OnCloneSnapshotTriggerReceived(TracingSessionID,
137*6dbdd20aSAndroid Build Coastguard Worker                                       const SnapshotTriggerInfo& trigger);
138*6dbdd20aSAndroid Build Coastguard Worker 
139*6dbdd20aSAndroid Build Coastguard Worker #if PERFETTO_BUILDFLAG(PERFETTO_OS_ANDROID)
140*6dbdd20aSAndroid Build Coastguard Worker   static base::ScopedFile CreateUnlinkedTmpFile();
141*6dbdd20aSAndroid Build Coastguard Worker   void SaveTraceIntoIncidentOrCrash();
142*6dbdd20aSAndroid Build Coastguard Worker   void SaveOutputToIncidentTraceOrCrash();
143*6dbdd20aSAndroid Build Coastguard Worker   void ReportTraceToAndroidFrameworkOrCrash();
144*6dbdd20aSAndroid Build Coastguard Worker #endif
145*6dbdd20aSAndroid Build Coastguard Worker   void LogUploadEvent(PerfettoStatsdAtom atom);
146*6dbdd20aSAndroid Build Coastguard Worker   void LogUploadEvent(PerfettoStatsdAtom atom, const std::string& trigger_name);
147*6dbdd20aSAndroid Build Coastguard Worker   void LogTriggerEvents(PerfettoTriggerAtom atom,
148*6dbdd20aSAndroid Build Coastguard Worker                         const std::vector<std::string>& trigger_names);
149*6dbdd20aSAndroid Build Coastguard Worker 
150*6dbdd20aSAndroid Build Coastguard Worker   base::UnixTaskRunner task_runner_;
151*6dbdd20aSAndroid Build Coastguard Worker 
152*6dbdd20aSAndroid Build Coastguard Worker   std::unique_ptr<perfetto::TracingService::ConsumerEndpoint>
153*6dbdd20aSAndroid Build Coastguard Worker       consumer_endpoint_;
154*6dbdd20aSAndroid Build Coastguard Worker   std::unique_ptr<TraceConfig> trace_config_;
155*6dbdd20aSAndroid Build Coastguard Worker   std::optional<PacketWriter> packet_writer_;
156*6dbdd20aSAndroid Build Coastguard Worker   base::ScopedFstream trace_out_stream_;
157*6dbdd20aSAndroid Build Coastguard Worker   std::vector<std::string> triggers_to_activate_;
158*6dbdd20aSAndroid Build Coastguard Worker   std::string trace_out_path_;
159*6dbdd20aSAndroid Build Coastguard Worker   base::EventFd ctrl_c_evt_;
160*6dbdd20aSAndroid Build Coastguard Worker   bool ctrl_c_handler_installed_ = false;
161*6dbdd20aSAndroid Build Coastguard Worker   base::Pipe background_wait_pipe_;
162*6dbdd20aSAndroid Build Coastguard Worker   bool save_to_incidentd_ = false;
163*6dbdd20aSAndroid Build Coastguard Worker   bool report_to_android_framework_ = false;
164*6dbdd20aSAndroid Build Coastguard Worker   bool statsd_logging_ = false;
165*6dbdd20aSAndroid Build Coastguard Worker   bool tracing_succeeded_ = false;
166*6dbdd20aSAndroid Build Coastguard Worker   uint64_t bytes_written_ = 0;
167*6dbdd20aSAndroid Build Coastguard Worker   std::string detach_key_;
168*6dbdd20aSAndroid Build Coastguard Worker   std::string attach_key_;
169*6dbdd20aSAndroid Build Coastguard Worker   bool stop_trace_once_attached_ = false;
170*6dbdd20aSAndroid Build Coastguard Worker   bool redetach_once_attached_ = false;
171*6dbdd20aSAndroid Build Coastguard Worker   bool query_service_ = false;
172*6dbdd20aSAndroid Build Coastguard Worker   bool query_service_output_raw_ = false;
173*6dbdd20aSAndroid Build Coastguard Worker   bool query_service_long_ = false;
174*6dbdd20aSAndroid Build Coastguard Worker   bool clone_all_bugreport_traces_ = false;
175*6dbdd20aSAndroid Build Coastguard Worker   bool bugreport_ = false;
176*6dbdd20aSAndroid Build Coastguard Worker   bool background_ = false;
177*6dbdd20aSAndroid Build Coastguard Worker   bool background_wait_ = false;
178*6dbdd20aSAndroid Build Coastguard Worker   bool ignore_guardrails_ = false;
179*6dbdd20aSAndroid Build Coastguard Worker   bool upload_flag_ = false;
180*6dbdd20aSAndroid Build Coastguard Worker   bool connected_ = false;
181*6dbdd20aSAndroid Build Coastguard Worker   std::string uuid_;
182*6dbdd20aSAndroid Build Coastguard Worker   std::optional<TracingSessionID> clone_tsid_{};
183*6dbdd20aSAndroid Build Coastguard Worker   std::string clone_name_;
184*6dbdd20aSAndroid Build Coastguard Worker   bool clone_for_bugreport_ = false;
185*6dbdd20aSAndroid Build Coastguard Worker   std::function<void()> on_session_cloned_;
186*6dbdd20aSAndroid Build Coastguard Worker 
187*6dbdd20aSAndroid Build Coastguard Worker   // How long we expect to trace for or 0 if the trace is indefinite.
188*6dbdd20aSAndroid Build Coastguard Worker   uint32_t expected_duration_ms_ = 0;
189*6dbdd20aSAndroid Build Coastguard Worker   bool trace_data_timeout_armed_ = false;
190*6dbdd20aSAndroid Build Coastguard Worker 
191*6dbdd20aSAndroid Build Coastguard Worker   // The aux threads used to invoke secondary instances of PerfettoCmd to create
192*6dbdd20aSAndroid Build Coastguard Worker   // snapshots. This is used only when the trace config involves a
193*6dbdd20aSAndroid Build Coastguard Worker   // CLONE_SNAPSHOT trigger or when using --save-all-for-bugreport.
194*6dbdd20aSAndroid Build Coastguard Worker   std::list<base::ThreadTaskRunner> snapshot_threads_;
195*6dbdd20aSAndroid Build Coastguard Worker   int snapshot_count_ = 0;
196*6dbdd20aSAndroid Build Coastguard Worker   std::string snapshot_config_;
197*6dbdd20aSAndroid Build Coastguard Worker   // If the trigger caused the clone operation, we want to save the information
198*6dbdd20aSAndroid Build Coastguard Worker   // about that trigger to the trace We may get multiple triggers with the same
199*6dbdd20aSAndroid Build Coastguard Worker   // name, so we pass the entire structure to uniquely identify the trigger
200*6dbdd20aSAndroid Build Coastguard Worker   // later. This structure is identical to the
201*6dbdd20aSAndroid Build Coastguard Worker   // `TracingServiceImpl::TriggerInfo`.
202*6dbdd20aSAndroid Build Coastguard Worker   struct SnapshotTriggerInfo {
203*6dbdd20aSAndroid Build Coastguard Worker     uint64_t boot_time_ns = 0;
204*6dbdd20aSAndroid Build Coastguard Worker     std::string trigger_name;
205*6dbdd20aSAndroid Build Coastguard Worker     std::string producer_name;
206*6dbdd20aSAndroid Build Coastguard Worker     uid_t producer_uid = 0;
207*6dbdd20aSAndroid Build Coastguard Worker   };
208*6dbdd20aSAndroid Build Coastguard Worker   std::optional<SnapshotTriggerInfo> snapshot_trigger_info_;
209*6dbdd20aSAndroid Build Coastguard Worker 
210*6dbdd20aSAndroid Build Coastguard Worker   base::WeakPtrFactory<PerfettoCmd> weak_factory_{this};
211*6dbdd20aSAndroid Build Coastguard Worker };
212*6dbdd20aSAndroid Build Coastguard Worker 
213*6dbdd20aSAndroid Build Coastguard Worker }  // namespace perfetto
214*6dbdd20aSAndroid Build Coastguard Worker 
215*6dbdd20aSAndroid Build Coastguard Worker #endif  // SRC_PERFETTO_CMD_PERFETTO_CMD_H_
216