xref: /aosp_15_r20/external/perfetto/test/cmdline_integrationtest.cc (revision 6dbdd20afdafa5e3ca9b8809fa73465d530080dc)
1*6dbdd20aSAndroid Build Coastguard Worker /*
2*6dbdd20aSAndroid Build Coastguard Worker  * Copyright (C) 2022 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 #include <functional>
18*6dbdd20aSAndroid Build Coastguard Worker #include <initializer_list>
19*6dbdd20aSAndroid Build Coastguard Worker #include <thread>
20*6dbdd20aSAndroid Build Coastguard Worker 
21*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/base/build_config.h"
22*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/base/logging.h"
23*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/pipe.h"
24*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/string_utils.h"
25*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/base/utils.h"
26*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/ext/traced/traced.h"
27*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/protozero/scattered_heap_buffer.h"
28*6dbdd20aSAndroid Build Coastguard Worker #include "perfetto/tracing/core/tracing_service_state.h"
29*6dbdd20aSAndroid Build Coastguard Worker #include "src/base/test/test_task_runner.h"
30*6dbdd20aSAndroid Build Coastguard Worker #include "src/base/test/utils.h"
31*6dbdd20aSAndroid Build Coastguard Worker #include "src/perfetto_cmd/bugreport_path.h"
32*6dbdd20aSAndroid Build Coastguard Worker #include "src/protozero/filtering/filter_bytecode_generator.h"
33*6dbdd20aSAndroid Build Coastguard Worker #include "test/gtest_and_gmock.h"
34*6dbdd20aSAndroid Build Coastguard Worker #include "test/test_helper.h"
35*6dbdd20aSAndroid Build Coastguard Worker 
36*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/config/test_config.gen.h"
37*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/config/trace_config.gen.h"
38*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/trace/test_event.gen.h"
39*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/trace/trace.gen.h"
40*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/trace/trace_packet.gen.h"
41*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/trace/trace_packet.pbzero.h"
42*6dbdd20aSAndroid Build Coastguard Worker #include "protos/perfetto/trace/trigger.gen.h"
43*6dbdd20aSAndroid Build Coastguard Worker 
44*6dbdd20aSAndroid Build Coastguard Worker namespace perfetto {
45*6dbdd20aSAndroid Build Coastguard Worker 
46*6dbdd20aSAndroid Build Coastguard Worker namespace {
47*6dbdd20aSAndroid Build Coastguard Worker 
48*6dbdd20aSAndroid Build Coastguard Worker using ::testing::ContainsRegex;
49*6dbdd20aSAndroid Build Coastguard Worker using ::testing::Each;
50*6dbdd20aSAndroid Build Coastguard Worker using ::testing::ElementsAre;
51*6dbdd20aSAndroid Build Coastguard Worker using ::testing::ElementsAreArray;
52*6dbdd20aSAndroid Build Coastguard Worker using ::testing::Eq;
53*6dbdd20aSAndroid Build Coastguard Worker using ::testing::HasSubstr;
54*6dbdd20aSAndroid Build Coastguard Worker using ::testing::IsEmpty;
55*6dbdd20aSAndroid Build Coastguard Worker using ::testing::Property;
56*6dbdd20aSAndroid Build Coastguard Worker using ::testing::SizeIs;
57*6dbdd20aSAndroid Build Coastguard Worker 
RandomTraceFileName()58*6dbdd20aSAndroid Build Coastguard Worker std::string RandomTraceFileName() {
59*6dbdd20aSAndroid Build Coastguard Worker #if PERFETTO_BUILDFLAG(PERFETTO_OS_ANDROID)
60*6dbdd20aSAndroid Build Coastguard Worker   constexpr char kSysTmpPath[] = "/data/misc/perfetto-traces";
61*6dbdd20aSAndroid Build Coastguard Worker #else
62*6dbdd20aSAndroid Build Coastguard Worker   constexpr char kSysTmpPath[] = "/tmp";
63*6dbdd20aSAndroid Build Coastguard Worker #endif
64*6dbdd20aSAndroid Build Coastguard Worker   static int suffix = 0;
65*6dbdd20aSAndroid Build Coastguard Worker 
66*6dbdd20aSAndroid Build Coastguard Worker   std::string path;
67*6dbdd20aSAndroid Build Coastguard Worker   path.assign(kSysTmpPath);
68*6dbdd20aSAndroid Build Coastguard Worker   path.append("/trace-");
69*6dbdd20aSAndroid Build Coastguard Worker   path.append(std::to_string(base::GetBootTimeNs().count()));
70*6dbdd20aSAndroid Build Coastguard Worker   path.append("-");
71*6dbdd20aSAndroid Build Coastguard Worker   path.append(std::to_string(suffix++));
72*6dbdd20aSAndroid Build Coastguard Worker   return path;
73*6dbdd20aSAndroid Build Coastguard Worker }
74*6dbdd20aSAndroid Build Coastguard Worker 
75*6dbdd20aSAndroid Build Coastguard Worker // For the SaveForBugreport* tests.
CreateTraceConfigForBugreportTest(int score=1,bool add_filter=false,uint32_t msg_count=3,uint32_t msg_size=10)76*6dbdd20aSAndroid Build Coastguard Worker TraceConfig CreateTraceConfigForBugreportTest(int score = 1,
77*6dbdd20aSAndroid Build Coastguard Worker                                               bool add_filter = false,
78*6dbdd20aSAndroid Build Coastguard Worker                                               uint32_t msg_count = 3,
79*6dbdd20aSAndroid Build Coastguard Worker                                               uint32_t msg_size = 10) {
80*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig trace_config;
81*6dbdd20aSAndroid Build Coastguard Worker   trace_config.add_buffers()->set_size_kb(32768);
82*6dbdd20aSAndroid Build Coastguard Worker   trace_config.set_duration_ms(60000);  // Will never hit this.
83*6dbdd20aSAndroid Build Coastguard Worker   trace_config.set_bugreport_score(score);
84*6dbdd20aSAndroid Build Coastguard Worker 
85*6dbdd20aSAndroid Build Coastguard Worker   if (add_filter) {
86*6dbdd20aSAndroid Build Coastguard Worker     // Add a trace filter which disallows the trace config echo-back.
87*6dbdd20aSAndroid Build Coastguard Worker     protozero::FilterBytecodeGenerator filt;
88*6dbdd20aSAndroid Build Coastguard Worker     filt.AddNestedField(1 /* root trace.packet*/, 1);
89*6dbdd20aSAndroid Build Coastguard Worker     filt.EndMessage();
90*6dbdd20aSAndroid Build Coastguard Worker     // Add a random unrelated field to keep the generator happy.
91*6dbdd20aSAndroid Build Coastguard Worker     filt.AddSimpleField(protos::pbzero::TracePacket::kTraceUuidFieldNumber);
92*6dbdd20aSAndroid Build Coastguard Worker     filt.EndMessage();
93*6dbdd20aSAndroid Build Coastguard Worker     trace_config.mutable_trace_filter()->set_bytecode_v2(filt.Serialize());
94*6dbdd20aSAndroid Build Coastguard Worker   }
95*6dbdd20aSAndroid Build Coastguard Worker 
96*6dbdd20aSAndroid Build Coastguard Worker   auto* ds_config = trace_config.add_data_sources()->mutable_config();
97*6dbdd20aSAndroid Build Coastguard Worker   ds_config->set_name("android.perfetto.FakeProducer");
98*6dbdd20aSAndroid Build Coastguard Worker 
99*6dbdd20aSAndroid Build Coastguard Worker   ds_config->mutable_for_testing()->set_message_count(msg_count);
100*6dbdd20aSAndroid Build Coastguard Worker   ds_config->mutable_for_testing()->set_message_size(msg_size);
101*6dbdd20aSAndroid Build Coastguard Worker   return trace_config;
102*6dbdd20aSAndroid Build Coastguard Worker }
103*6dbdd20aSAndroid Build Coastguard Worker 
104*6dbdd20aSAndroid Build Coastguard Worker // For the regular tests.
CreateTraceConfigForTest(uint32_t test_msg_count=11,uint32_t test_msg_size=32)105*6dbdd20aSAndroid Build Coastguard Worker TraceConfig CreateTraceConfigForTest(uint32_t test_msg_count = 11,
106*6dbdd20aSAndroid Build Coastguard Worker                                      uint32_t test_msg_size = 32) {
107*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig trace_config;
108*6dbdd20aSAndroid Build Coastguard Worker   trace_config.add_buffers()->set_size_kb(1024);
109*6dbdd20aSAndroid Build Coastguard Worker   auto* ds_config = trace_config.add_data_sources()->mutable_config();
110*6dbdd20aSAndroid Build Coastguard Worker   ds_config->set_name("android.perfetto.FakeProducer");
111*6dbdd20aSAndroid Build Coastguard Worker   ds_config->mutable_for_testing()->set_message_count(test_msg_count);
112*6dbdd20aSAndroid Build Coastguard Worker   ds_config->mutable_for_testing()->set_message_size(test_msg_size);
113*6dbdd20aSAndroid Build Coastguard Worker   return trace_config;
114*6dbdd20aSAndroid Build Coastguard Worker }
115*6dbdd20aSAndroid Build Coastguard Worker 
ExpectTraceContainsTestMessages(const protos::gen::Trace & trace,uint32_t count)116*6dbdd20aSAndroid Build Coastguard Worker void ExpectTraceContainsTestMessages(const protos::gen::Trace& trace,
117*6dbdd20aSAndroid Build Coastguard Worker                                      uint32_t count) {
118*6dbdd20aSAndroid Build Coastguard Worker   ssize_t actual_test_packets_count = std::count_if(
119*6dbdd20aSAndroid Build Coastguard Worker       trace.packet().begin(), trace.packet().end(),
120*6dbdd20aSAndroid Build Coastguard Worker       [](const protos::gen::TracePacket& tp) { return tp.has_for_testing(); });
121*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(count, static_cast<uint32_t>(actual_test_packets_count));
122*6dbdd20aSAndroid Build Coastguard Worker }
123*6dbdd20aSAndroid Build Coastguard Worker 
ExpectTraceContainsTestMessagesWithSize(const protos::gen::Trace & trace,uint32_t message_size)124*6dbdd20aSAndroid Build Coastguard Worker void ExpectTraceContainsTestMessagesWithSize(const protos::gen::Trace& trace,
125*6dbdd20aSAndroid Build Coastguard Worker                                              uint32_t message_size) {
126*6dbdd20aSAndroid Build Coastguard Worker   for (const auto& packet : trace.packet()) {
127*6dbdd20aSAndroid Build Coastguard Worker     if (packet.has_for_testing()) {
128*6dbdd20aSAndroid Build Coastguard Worker       EXPECT_EQ(message_size, packet.for_testing().str().size());
129*6dbdd20aSAndroid Build Coastguard Worker     }
130*6dbdd20aSAndroid Build Coastguard Worker   }
131*6dbdd20aSAndroid Build Coastguard Worker }
132*6dbdd20aSAndroid Build Coastguard Worker 
ExpectTraceContainsConfigWithTriggerMode(const protos::gen::Trace & trace,protos::gen::TraceConfig::TriggerConfig::TriggerMode trigger_mode)133*6dbdd20aSAndroid Build Coastguard Worker void ExpectTraceContainsConfigWithTriggerMode(
134*6dbdd20aSAndroid Build Coastguard Worker     const protos::gen::Trace& trace,
135*6dbdd20aSAndroid Build Coastguard Worker     protos::gen::TraceConfig::TriggerConfig::TriggerMode trigger_mode) {
136*6dbdd20aSAndroid Build Coastguard Worker   // GTest three level nested Property matcher is hard to read, so we use
137*6dbdd20aSAndroid Build Coastguard Worker   // 'find_if' with lambda to ensure the trace config properly includes the
138*6dbdd20aSAndroid Build Coastguard Worker   // trigger mode we set.
139*6dbdd20aSAndroid Build Coastguard Worker   auto found =
140*6dbdd20aSAndroid Build Coastguard Worker       std::find_if(trace.packet().begin(), trace.packet().end(),
141*6dbdd20aSAndroid Build Coastguard Worker                    [trigger_mode](const protos::gen::TracePacket& tp) {
142*6dbdd20aSAndroid Build Coastguard Worker                      return tp.has_trace_config() &&
143*6dbdd20aSAndroid Build Coastguard Worker                             tp.trace_config().trigger_config().trigger_mode() ==
144*6dbdd20aSAndroid Build Coastguard Worker                                 trigger_mode;
145*6dbdd20aSAndroid Build Coastguard Worker                    });
146*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_NE(found, trace.packet().end())
147*6dbdd20aSAndroid Build Coastguard Worker       << "Trace config doesn't include expected trigger mode.";
148*6dbdd20aSAndroid Build Coastguard Worker }
149*6dbdd20aSAndroid Build Coastguard Worker 
150*6dbdd20aSAndroid Build Coastguard Worker class ScopedFileRemove {
151*6dbdd20aSAndroid Build Coastguard Worker  public:
ScopedFileRemove(const std::string & path)152*6dbdd20aSAndroid Build Coastguard Worker   explicit ScopedFileRemove(const std::string& path) : path_(path) {}
~ScopedFileRemove()153*6dbdd20aSAndroid Build Coastguard Worker   ~ScopedFileRemove() { remove(path_.c_str()); }
154*6dbdd20aSAndroid Build Coastguard Worker   std::string path_;
155*6dbdd20aSAndroid Build Coastguard Worker };
156*6dbdd20aSAndroid Build Coastguard Worker 
ParseNotEmptyTraceFromFile(const std::string & trace_path,protos::gen::Trace & out)157*6dbdd20aSAndroid Build Coastguard Worker bool ParseNotEmptyTraceFromFile(const std::string& trace_path,
158*6dbdd20aSAndroid Build Coastguard Worker                                 protos::gen::Trace& out) {
159*6dbdd20aSAndroid Build Coastguard Worker   std::string trace_str;
160*6dbdd20aSAndroid Build Coastguard Worker   if (!base::ReadFile(trace_path, &trace_str))
161*6dbdd20aSAndroid Build Coastguard Worker     return false;
162*6dbdd20aSAndroid Build Coastguard Worker   if (trace_str.empty())
163*6dbdd20aSAndroid Build Coastguard Worker     return false;
164*6dbdd20aSAndroid Build Coastguard Worker   return out.ParseFromString(trace_str);
165*6dbdd20aSAndroid Build Coastguard Worker }
166*6dbdd20aSAndroid Build Coastguard Worker 
GetReceivedTriggerNames(const protos::gen::Trace & trace)167*6dbdd20aSAndroid Build Coastguard Worker std::vector<std::string> GetReceivedTriggerNames(
168*6dbdd20aSAndroid Build Coastguard Worker     const protos::gen::Trace& trace) {
169*6dbdd20aSAndroid Build Coastguard Worker   std::vector<std::string> triggers;
170*6dbdd20aSAndroid Build Coastguard Worker   for (const protos::gen::TracePacket& packet : trace.packet()) {
171*6dbdd20aSAndroid Build Coastguard Worker     if (packet.has_trigger()) {
172*6dbdd20aSAndroid Build Coastguard Worker       triggers.push_back(packet.trigger().trigger_name());
173*6dbdd20aSAndroid Build Coastguard Worker     }
174*6dbdd20aSAndroid Build Coastguard Worker   }
175*6dbdd20aSAndroid Build Coastguard Worker   return triggers;
176*6dbdd20aSAndroid Build Coastguard Worker }
177*6dbdd20aSAndroid Build Coastguard Worker 
178*6dbdd20aSAndroid Build Coastguard Worker class PerfettoCmdlineTest : public ::testing::Test {
179*6dbdd20aSAndroid Build Coastguard Worker  public:
StartServiceIfRequiredNoNewExecsAfterThis()180*6dbdd20aSAndroid Build Coastguard Worker   void StartServiceIfRequiredNoNewExecsAfterThis() {
181*6dbdd20aSAndroid Build Coastguard Worker     exec_allowed_ = false;
182*6dbdd20aSAndroid Build Coastguard Worker     test_helper_.StartServiceIfRequired();
183*6dbdd20aSAndroid Build Coastguard Worker   }
184*6dbdd20aSAndroid Build Coastguard Worker 
test_helper()185*6dbdd20aSAndroid Build Coastguard Worker   TestHelper& test_helper() { return test_helper_; }
186*6dbdd20aSAndroid Build Coastguard Worker 
187*6dbdd20aSAndroid Build Coastguard Worker   // Creates a process that represents the perfetto binary that will
188*6dbdd20aSAndroid Build Coastguard Worker   // start when Run() is called. |args| will be passed as part of
189*6dbdd20aSAndroid Build Coastguard Worker   // the command line and |std_in| will be piped into std::cin.
ExecPerfetto(std::initializer_list<std::string> args,std::string std_in="")190*6dbdd20aSAndroid Build Coastguard Worker   Exec ExecPerfetto(std::initializer_list<std::string> args,
191*6dbdd20aSAndroid Build Coastguard Worker                     std::string std_in = "") {
192*6dbdd20aSAndroid Build Coastguard Worker     // You can not fork after you've started the service due to risk of
193*6dbdd20aSAndroid Build Coastguard Worker     // deadlocks.
194*6dbdd20aSAndroid Build Coastguard Worker     PERFETTO_CHECK(exec_allowed_);
195*6dbdd20aSAndroid Build Coastguard Worker     return Exec("perfetto", std::move(args), std::move(std_in));
196*6dbdd20aSAndroid Build Coastguard Worker   }
197*6dbdd20aSAndroid Build Coastguard Worker 
198*6dbdd20aSAndroid Build Coastguard Worker   // Creates a process that represents the trigger_perfetto binary that will
199*6dbdd20aSAndroid Build Coastguard Worker   // start when Run() is called. |args| will be passed as part of
200*6dbdd20aSAndroid Build Coastguard Worker   // the command line and |std_in| will be piped into std::cin.
ExecTrigger(std::initializer_list<std::string> args,std::string std_in="")201*6dbdd20aSAndroid Build Coastguard Worker   Exec ExecTrigger(std::initializer_list<std::string> args,
202*6dbdd20aSAndroid Build Coastguard Worker                    std::string std_in = "") {
203*6dbdd20aSAndroid Build Coastguard Worker     // You can not fork after you've started the service due to risk of
204*6dbdd20aSAndroid Build Coastguard Worker     // deadlocks.
205*6dbdd20aSAndroid Build Coastguard Worker     PERFETTO_CHECK(exec_allowed_);
206*6dbdd20aSAndroid Build Coastguard Worker     return Exec("trigger_perfetto", std::move(args), std::move(std_in));
207*6dbdd20aSAndroid Build Coastguard Worker   }
208*6dbdd20aSAndroid Build Coastguard Worker 
209*6dbdd20aSAndroid Build Coastguard Worker   // This is in common to the 3 TEST_F SaveForBugreport* fixtures, which differ
210*6dbdd20aSAndroid Build Coastguard Worker   // only in the config, passed here as input.
RunBugreportTest(protos::gen::TraceConfig trace_config,bool check_original_trace=true,bool use_explicit_clone=false)211*6dbdd20aSAndroid Build Coastguard Worker   void RunBugreportTest(protos::gen::TraceConfig trace_config,
212*6dbdd20aSAndroid Build Coastguard Worker                         bool check_original_trace = true,
213*6dbdd20aSAndroid Build Coastguard Worker                         bool use_explicit_clone = false) {
214*6dbdd20aSAndroid Build Coastguard Worker     const std::string path = RandomTraceFileName();
215*6dbdd20aSAndroid Build Coastguard Worker     ScopedFileRemove remove_on_test_exit(path);
216*6dbdd20aSAndroid Build Coastguard Worker 
217*6dbdd20aSAndroid Build Coastguard Worker     auto perfetto_proc = ExecPerfetto(
218*6dbdd20aSAndroid Build Coastguard Worker         {
219*6dbdd20aSAndroid Build Coastguard Worker             "-o",
220*6dbdd20aSAndroid Build Coastguard Worker             path,
221*6dbdd20aSAndroid Build Coastguard Worker             "-c",
222*6dbdd20aSAndroid Build Coastguard Worker             "-",
223*6dbdd20aSAndroid Build Coastguard Worker         },
224*6dbdd20aSAndroid Build Coastguard Worker         trace_config.SerializeAsString());
225*6dbdd20aSAndroid Build Coastguard Worker 
226*6dbdd20aSAndroid Build Coastguard Worker     Exec perfetto_br_proc =
227*6dbdd20aSAndroid Build Coastguard Worker         use_explicit_clone
228*6dbdd20aSAndroid Build Coastguard Worker             ? ExecPerfetto({"--out", GetBugreportTracePath(), "--clone", "-1"})
229*6dbdd20aSAndroid Build Coastguard Worker             : ExecPerfetto({"--save-for-bugreport"});
230*6dbdd20aSAndroid Build Coastguard Worker 
231*6dbdd20aSAndroid Build Coastguard Worker     // Start the service and connect a simple fake producer.
232*6dbdd20aSAndroid Build Coastguard Worker     StartServiceIfRequiredNoNewExecsAfterThis();
233*6dbdd20aSAndroid Build Coastguard Worker 
234*6dbdd20aSAndroid Build Coastguard Worker     auto* fake_producer = test_helper().ConnectFakeProducer();
235*6dbdd20aSAndroid Build Coastguard Worker     ASSERT_TRUE(fake_producer);
236*6dbdd20aSAndroid Build Coastguard Worker 
237*6dbdd20aSAndroid Build Coastguard Worker     std::thread background_trace([&perfetto_proc]() {
238*6dbdd20aSAndroid Build Coastguard Worker       std::string stderr_str;
239*6dbdd20aSAndroid Build Coastguard Worker       ASSERT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
240*6dbdd20aSAndroid Build Coastguard Worker     });
241*6dbdd20aSAndroid Build Coastguard Worker 
242*6dbdd20aSAndroid Build Coastguard Worker     // Wait for the producer to start, and then write out packets.
243*6dbdd20aSAndroid Build Coastguard Worker     test_helper().WaitForProducerEnabled();
244*6dbdd20aSAndroid Build Coastguard Worker     auto on_data_written = task_runner_.CreateCheckpoint("data_written");
245*6dbdd20aSAndroid Build Coastguard Worker     fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
246*6dbdd20aSAndroid Build Coastguard Worker     task_runner_.RunUntilCheckpoint("data_written");
247*6dbdd20aSAndroid Build Coastguard Worker 
248*6dbdd20aSAndroid Build Coastguard Worker     ASSERT_EQ(0, perfetto_br_proc.Run(&stderr_)) << "stderr: " << stderr_;
249*6dbdd20aSAndroid Build Coastguard Worker     perfetto_proc.SendSigterm();
250*6dbdd20aSAndroid Build Coastguard Worker     background_trace.join();
251*6dbdd20aSAndroid Build Coastguard Worker 
252*6dbdd20aSAndroid Build Coastguard Worker     uint32_t expected_packets = 0;
253*6dbdd20aSAndroid Build Coastguard Worker     for (auto& ds : trace_config.data_sources()) {
254*6dbdd20aSAndroid Build Coastguard Worker       if (ds.config().has_for_testing())
255*6dbdd20aSAndroid Build Coastguard Worker         expected_packets = ds.config().for_testing().message_count();
256*6dbdd20aSAndroid Build Coastguard Worker     }
257*6dbdd20aSAndroid Build Coastguard Worker 
258*6dbdd20aSAndroid Build Coastguard Worker     auto check_trace_contents = [expected_packets](std::string trace_path) {
259*6dbdd20aSAndroid Build Coastguard Worker       // Read the trace written in the fixed location
260*6dbdd20aSAndroid Build Coastguard Worker       // (/data/misc/perfetto-traces/ on Android, /tmp/ on Linux/Mac) and make
261*6dbdd20aSAndroid Build Coastguard Worker       // sure it has the right contents.
262*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::Trace trace;
263*6dbdd20aSAndroid Build Coastguard Worker       ASSERT_TRUE(ParseNotEmptyTraceFromFile(trace_path, trace));
264*6dbdd20aSAndroid Build Coastguard Worker       uint32_t test_packets = 0;
265*6dbdd20aSAndroid Build Coastguard Worker       for (const auto& p : trace.packet())
266*6dbdd20aSAndroid Build Coastguard Worker         test_packets += p.has_for_testing() ? 1 : 0;
267*6dbdd20aSAndroid Build Coastguard Worker       ASSERT_EQ(test_packets, expected_packets) << trace_path;
268*6dbdd20aSAndroid Build Coastguard Worker     };
269*6dbdd20aSAndroid Build Coastguard Worker 
270*6dbdd20aSAndroid Build Coastguard Worker     // Verify that both the original trace and the cloned bugreport contain
271*6dbdd20aSAndroid Build Coastguard Worker     // the expected contents.
272*6dbdd20aSAndroid Build Coastguard Worker     check_trace_contents(GetBugreportTracePath());
273*6dbdd20aSAndroid Build Coastguard Worker     if (check_original_trace)
274*6dbdd20aSAndroid Build Coastguard Worker       check_trace_contents(path);
275*6dbdd20aSAndroid Build Coastguard Worker   }
276*6dbdd20aSAndroid Build Coastguard Worker 
277*6dbdd20aSAndroid Build Coastguard Worker   // Tests are allowed to freely use these variables.
278*6dbdd20aSAndroid Build Coastguard Worker   std::string stderr_;
279*6dbdd20aSAndroid Build Coastguard Worker   base::TestTaskRunner task_runner_;
280*6dbdd20aSAndroid Build Coastguard Worker 
281*6dbdd20aSAndroid Build Coastguard Worker   // We use these two constants to set test data payload parameters and assert
282*6dbdd20aSAndroid Build Coastguard Worker   // it was correctly written to the trace.
283*6dbdd20aSAndroid Build Coastguard Worker   static constexpr size_t kTestMessageCount = 11;
284*6dbdd20aSAndroid Build Coastguard Worker   static constexpr size_t kTestMessageSize = 32;
285*6dbdd20aSAndroid Build Coastguard Worker 
286*6dbdd20aSAndroid Build Coastguard Worker  private:
287*6dbdd20aSAndroid Build Coastguard Worker   bool exec_allowed_ = true;
288*6dbdd20aSAndroid Build Coastguard Worker   TestHelper test_helper_{&task_runner_};
289*6dbdd20aSAndroid Build Coastguard Worker };
290*6dbdd20aSAndroid Build Coastguard Worker 
291*6dbdd20aSAndroid Build Coastguard Worker }  // namespace
292*6dbdd20aSAndroid Build Coastguard Worker 
293*6dbdd20aSAndroid Build Coastguard Worker #if PERFETTO_BUILDFLAG(PERFETTO_OS_ANDROID)
294*6dbdd20aSAndroid Build Coastguard Worker #define AndroidOnly(x) x
295*6dbdd20aSAndroid Build Coastguard Worker #else
296*6dbdd20aSAndroid Build Coastguard Worker #define AndroidOnly(x) DISABLED_##x
297*6dbdd20aSAndroid Build Coastguard Worker #endif
298*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,InvalidCases)299*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, InvalidCases) {
300*6dbdd20aSAndroid Build Coastguard Worker   std::string cfg("duration_ms: 100");
301*6dbdd20aSAndroid Build Coastguard Worker 
302*6dbdd20aSAndroid Build Coastguard Worker   auto invalid_arg = ExecPerfetto({"--invalid-arg"});
303*6dbdd20aSAndroid Build Coastguard Worker   auto empty_config = ExecPerfetto({"-c", "-", "-o", "-"}, "");
304*6dbdd20aSAndroid Build Coastguard Worker 
305*6dbdd20aSAndroid Build Coastguard Worker   // Cannot make assertions on --dropbox because on standalone builds it fails
306*6dbdd20aSAndroid Build Coastguard Worker   // prematurely due to lack of dropbox.
307*6dbdd20aSAndroid Build Coastguard Worker   auto missing_dropbox =
308*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-c", "-", "--txt", "-o", "-", "--dropbox=foo"}, cfg);
309*6dbdd20aSAndroid Build Coastguard Worker   auto either_out_or_dropbox = ExecPerfetto({"-c", "-", "--txt"}, cfg);
310*6dbdd20aSAndroid Build Coastguard Worker 
311*6dbdd20aSAndroid Build Coastguard Worker   // Disallow mixing simple and file config.
312*6dbdd20aSAndroid Build Coastguard Worker   auto simple_and_file_1 =
313*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-o", "-", "-c", "-", "-t", "2s"}, cfg);
314*6dbdd20aSAndroid Build Coastguard Worker   auto simple_and_file_2 =
315*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-o", "-", "-c", "-", "-b", "2m"}, cfg);
316*6dbdd20aSAndroid Build Coastguard Worker   auto simple_and_file_3 =
317*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-o", "-", "-c", "-", "-s", "2m"}, cfg);
318*6dbdd20aSAndroid Build Coastguard Worker 
319*6dbdd20aSAndroid Build Coastguard Worker   // Invalid --attach / --detach cases.
320*6dbdd20aSAndroid Build Coastguard Worker   auto invalid_stop =
321*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-c", "-", "--txt", "-o", "-", "--stop"}, cfg);
322*6dbdd20aSAndroid Build Coastguard Worker   auto attach_and_config_1 =
323*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-c", "-", "--txt", "-o", "-", "--attach=foo"}, cfg);
324*6dbdd20aSAndroid Build Coastguard Worker   auto attach_and_config_2 =
325*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-t", "2s", "-o", "-", "--attach=foo"}, cfg);
326*6dbdd20aSAndroid Build Coastguard Worker   auto attach_needs_argument = ExecPerfetto({"--attach"}, cfg);
327*6dbdd20aSAndroid Build Coastguard Worker   auto detach_needs_argument =
328*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-t", "2s", "-o", "-", "--detach"}, cfg);
329*6dbdd20aSAndroid Build Coastguard Worker   auto detach_without_out_or_dropbox =
330*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-t", "2s", "--detach=foo"}, cfg);
331*6dbdd20aSAndroid Build Coastguard Worker 
332*6dbdd20aSAndroid Build Coastguard Worker   // Cannot trace and use --query.
333*6dbdd20aSAndroid Build Coastguard Worker   auto trace_and_query_1 = ExecPerfetto({"-t", "2s", "--query"}, cfg);
334*6dbdd20aSAndroid Build Coastguard Worker   auto trace_and_query_2 = ExecPerfetto({"-c", "-", "--query"}, cfg);
335*6dbdd20aSAndroid Build Coastguard Worker 
336*6dbdd20aSAndroid Build Coastguard Worker   // Ensure all Exec:: calls have been saved to prevent deadlocks.
337*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
338*6dbdd20aSAndroid Build Coastguard Worker 
339*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, invalid_arg.Run(&stderr_));
340*6dbdd20aSAndroid Build Coastguard Worker 
341*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, empty_config.Run(&stderr_));
342*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("TraceConfig is empty"));
343*6dbdd20aSAndroid Build Coastguard Worker 
344*6dbdd20aSAndroid Build Coastguard Worker   // Cannot make assertions on --upload because on standalone builds it fails
345*6dbdd20aSAndroid Build Coastguard Worker   // prematurely due to lack of dropbox.
346*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, missing_dropbox.Run(&stderr_));
347*6dbdd20aSAndroid Build Coastguard Worker 
348*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, either_out_or_dropbox.Run(&stderr_));
349*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Either --out or --upload"));
350*6dbdd20aSAndroid Build Coastguard Worker 
351*6dbdd20aSAndroid Build Coastguard Worker   // Disallow mixing simple and file config.
352*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, simple_and_file_1.Run(&stderr_));
353*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify both -c"));
354*6dbdd20aSAndroid Build Coastguard Worker 
355*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, simple_and_file_2.Run(&stderr_));
356*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify both -c"));
357*6dbdd20aSAndroid Build Coastguard Worker 
358*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, simple_and_file_3.Run(&stderr_));
359*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify both -c"));
360*6dbdd20aSAndroid Build Coastguard Worker 
361*6dbdd20aSAndroid Build Coastguard Worker   // Invalid --attach / --detach cases.
362*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, invalid_stop.Run(&stderr_));
363*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("--stop is supported only in combination"));
364*6dbdd20aSAndroid Build Coastguard Worker 
365*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, attach_and_config_1.Run(&stderr_));
366*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify a trace config"));
367*6dbdd20aSAndroid Build Coastguard Worker 
368*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, attach_and_config_2.Run(&stderr_));
369*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify a trace config"));
370*6dbdd20aSAndroid Build Coastguard Worker 
371*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, attach_needs_argument.Run(&stderr_));
372*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, ContainsRegex("option.*--attach.*requires an argument"));
373*6dbdd20aSAndroid Build Coastguard Worker 
374*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, detach_needs_argument.Run(&stderr_));
375*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, ContainsRegex("option.*--detach.*requires an argument"));
376*6dbdd20aSAndroid Build Coastguard Worker 
377*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, detach_without_out_or_dropbox.Run(&stderr_));
378*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("--out or --upload is required"));
379*6dbdd20aSAndroid Build Coastguard Worker 
380*6dbdd20aSAndroid Build Coastguard Worker   // Cannot trace and use --query.
381*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, trace_and_query_1.Run(&stderr_));
382*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify a trace config"));
383*6dbdd20aSAndroid Build Coastguard Worker 
384*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(1, trace_and_query_2.Run(&stderr_));
385*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Cannot specify a trace config"));
386*6dbdd20aSAndroid Build Coastguard Worker }
387*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,Version)388*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, Version) {
389*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto = ExecPerfetto({"--version"});
390*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto.Run(&stderr_)) << stderr_;
391*6dbdd20aSAndroid Build Coastguard Worker }
392*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,TxtConfig)393*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, TxtConfig) {
394*6dbdd20aSAndroid Build Coastguard Worker   std::string cfg("duration_ms: 100");
395*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto = ExecPerfetto({"-c", "-", "--txt", "-o", "-"}, cfg);
396*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
397*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto.Run(&stderr_)) << stderr_;
398*6dbdd20aSAndroid Build Coastguard Worker }
399*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,SimpleConfig)400*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, SimpleConfig) {
401*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto = ExecPerfetto({"-o", "-", "-c", "-", "-t", "100ms"});
402*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
403*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto.Run(&stderr_)) << stderr_;
404*6dbdd20aSAndroid Build Coastguard Worker }
405*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,DetachAndAttach)406*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, DetachAndAttach) {
407*6dbdd20aSAndroid Build Coastguard Worker   auto attach_to_not_existing = ExecPerfetto({"--attach=not_existent"});
408*6dbdd20aSAndroid Build Coastguard Worker 
409*6dbdd20aSAndroid Build Coastguard Worker   std::string cfg("duration_ms: 10000; write_into_file: true");
410*6dbdd20aSAndroid Build Coastguard Worker   auto detach_valid_stop =
411*6dbdd20aSAndroid Build Coastguard Worker       ExecPerfetto({"-o", "-", "-c", "-", "--txt", "--detach=valid_stop"}, cfg);
412*6dbdd20aSAndroid Build Coastguard Worker   auto stop_valid_stop = ExecPerfetto({"--attach=valid_stop", "--stop"});
413*6dbdd20aSAndroid Build Coastguard Worker 
414*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
415*6dbdd20aSAndroid Build Coastguard Worker 
416*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_NE(0, attach_to_not_existing.Run(&stderr_));
417*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("Session re-attach failed"));
418*6dbdd20aSAndroid Build Coastguard Worker 
419*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, detach_valid_stop.Run(&stderr_)) << stderr_;
420*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, stop_valid_stop.Run(&stderr_));
421*6dbdd20aSAndroid Build Coastguard Worker }
422*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,StartTracingTrigger)423*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, StartTracingTrigger) {
424*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
425*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
426*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
427*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
428*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::START_TRACING);
429*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(15000);
430*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
431*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
432*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
433*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
434*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
435*6dbdd20aSAndroid Build Coastguard Worker   // time.
436*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
437*6dbdd20aSAndroid Build Coastguard Worker 
438*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
439*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
440*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
441*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
442*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
443*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
444*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
445*6dbdd20aSAndroid Build Coastguard Worker       {
446*6dbdd20aSAndroid Build Coastguard Worker           "-o",
447*6dbdd20aSAndroid Build Coastguard Worker           path,
448*6dbdd20aSAndroid Build Coastguard Worker           "-c",
449*6dbdd20aSAndroid Build Coastguard Worker           "-",
450*6dbdd20aSAndroid Build Coastguard Worker       },
451*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
452*6dbdd20aSAndroid Build Coastguard Worker 
453*6dbdd20aSAndroid Build Coastguard Worker   auto trigger_proc = ExecTrigger({"trigger_name"});
454*6dbdd20aSAndroid Build Coastguard Worker 
455*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
456*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
457*6dbdd20aSAndroid Build Coastguard Worker 
458*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
459*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
460*6dbdd20aSAndroid Build Coastguard Worker 
461*6dbdd20aSAndroid Build Coastguard Worker   // Start a background thread that will deliver the config now that we've
462*6dbdd20aSAndroid Build Coastguard Worker   // started the service. See |perfetto_proc| above for the args passed.
463*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
464*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
465*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
466*6dbdd20aSAndroid Build Coastguard Worker   });
467*6dbdd20aSAndroid Build Coastguard Worker 
468*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerSetup();
469*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, trigger_proc.Run(&stderr_));
470*6dbdd20aSAndroid Build Coastguard Worker 
471*6dbdd20aSAndroid Build Coastguard Worker   // Wait for the producer to start, and then write out some test packets.
472*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
473*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written");
474*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
475*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written");
476*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
477*6dbdd20aSAndroid Build Coastguard Worker 
478*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
479*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(path, trace));
480*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsConfigWithTriggerMode(
481*6dbdd20aSAndroid Build Coastguard Worker       trace, protos::gen::TraceConfig::TriggerConfig::START_TRACING);
482*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(GetReceivedTriggerNames(trace), ElementsAre("trigger_name"));
483*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kTestMessageCount);
484*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kTestMessageSize);
485*6dbdd20aSAndroid Build Coastguard Worker }
486*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,StopTracingTrigger)487*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, StopTracingTrigger) {
488*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
489*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
490*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
491*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
492*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
493*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(15000);
494*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
495*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
496*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
497*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
498*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
499*6dbdd20aSAndroid Build Coastguard Worker   // time.
500*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
501*6dbdd20aSAndroid Build Coastguard Worker   trigger = trigger_cfg->add_triggers();
502*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name_3");
503*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(60000);
504*6dbdd20aSAndroid Build Coastguard Worker 
505*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
506*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
507*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
508*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
509*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
510*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
511*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
512*6dbdd20aSAndroid Build Coastguard Worker       {
513*6dbdd20aSAndroid Build Coastguard Worker           "-o",
514*6dbdd20aSAndroid Build Coastguard Worker           path,
515*6dbdd20aSAndroid Build Coastguard Worker           "-c",
516*6dbdd20aSAndroid Build Coastguard Worker           "-",
517*6dbdd20aSAndroid Build Coastguard Worker       },
518*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
519*6dbdd20aSAndroid Build Coastguard Worker 
520*6dbdd20aSAndroid Build Coastguard Worker   auto trigger_proc =
521*6dbdd20aSAndroid Build Coastguard Worker       ExecTrigger({"trigger_name_2", "trigger_name", "trigger_name_3"});
522*6dbdd20aSAndroid Build Coastguard Worker 
523*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
524*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
525*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
526*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
527*6dbdd20aSAndroid Build Coastguard Worker 
528*6dbdd20aSAndroid Build Coastguard Worker   // Start a background thread that will deliver the config now that we've
529*6dbdd20aSAndroid Build Coastguard Worker   // started the service. See |perfetto_proc| above for the args passed.
530*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
531*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
532*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
533*6dbdd20aSAndroid Build Coastguard Worker   });
534*6dbdd20aSAndroid Build Coastguard Worker 
535*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
536*6dbdd20aSAndroid Build Coastguard Worker   // Wait for the producer to start, and then write out some test packets,
537*6dbdd20aSAndroid Build Coastguard Worker   // before the trace actually starts (the trigger is seen).
538*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written_1");
539*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
540*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written_1");
541*6dbdd20aSAndroid Build Coastguard Worker 
542*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, trigger_proc.Run(&stderr_)) << "stderr: " << stderr_;
543*6dbdd20aSAndroid Build Coastguard Worker 
544*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
545*6dbdd20aSAndroid Build Coastguard Worker 
546*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
547*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(path, trace));
548*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsConfigWithTriggerMode(
549*6dbdd20aSAndroid Build Coastguard Worker       trace, protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
550*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(GetReceivedTriggerNames(trace),
551*6dbdd20aSAndroid Build Coastguard Worker               ElementsAre("trigger_name", "trigger_name_3"));
552*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kTestMessageCount);
553*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kTestMessageSize);
554*6dbdd20aSAndroid Build Coastguard Worker }
555*6dbdd20aSAndroid Build Coastguard Worker 
556*6dbdd20aSAndroid Build Coastguard Worker // Dropbox on the commandline client only works on android builds. So disable
557*6dbdd20aSAndroid Build Coastguard Worker // this test on all other builds.
TEST_F(PerfettoCmdlineTest,AndroidOnly (NoDataNoFileWithoutTrigger))558*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, AndroidOnly(NoDataNoFileWithoutTrigger)) {
559*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
560*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
561*6dbdd20aSAndroid Build Coastguard Worker   auto* incident_config = trace_config.mutable_incident_report_config();
562*6dbdd20aSAndroid Build Coastguard Worker   incident_config->set_destination_package("foo.bar.baz");
563*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
564*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
565*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
566*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(1000);
567*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
568*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
569*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
570*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
571*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
572*6dbdd20aSAndroid Build Coastguard Worker   // time.
573*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
574*6dbdd20aSAndroid Build Coastguard Worker   trigger = trigger_cfg->add_triggers();
575*6dbdd20aSAndroid Build Coastguard Worker 
576*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
577*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
578*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
579*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
580*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
581*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
582*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
583*6dbdd20aSAndroid Build Coastguard Worker       {
584*6dbdd20aSAndroid Build Coastguard Worker           "--dropbox",
585*6dbdd20aSAndroid Build Coastguard Worker           "TAG",
586*6dbdd20aSAndroid Build Coastguard Worker           "--no-guardrails",
587*6dbdd20aSAndroid Build Coastguard Worker           "-c",
588*6dbdd20aSAndroid Build Coastguard Worker           "-",
589*6dbdd20aSAndroid Build Coastguard Worker       },
590*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
591*6dbdd20aSAndroid Build Coastguard Worker 
592*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
593*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
594*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
595*6dbdd20aSAndroid Build Coastguard Worker 
596*6dbdd20aSAndroid Build Coastguard Worker   std::string stderr_str;
597*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc, &stderr_str]() {
598*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str));
599*6dbdd20aSAndroid Build Coastguard Worker   });
600*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
601*6dbdd20aSAndroid Build Coastguard Worker 
602*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_str,
603*6dbdd20aSAndroid Build Coastguard Worker               ::testing::HasSubstr("Skipping write to incident. Empty trace."));
604*6dbdd20aSAndroid Build Coastguard Worker }
605*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,StopTracingTriggerFromConfig)606*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, StopTracingTriggerFromConfig) {
607*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
608*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
609*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
610*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
611*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
612*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(15000);
613*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
614*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
615*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
616*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
617*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
618*6dbdd20aSAndroid Build Coastguard Worker   // time.
619*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
620*6dbdd20aSAndroid Build Coastguard Worker   trigger = trigger_cfg->add_triggers();
621*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name_3");
622*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(60000);
623*6dbdd20aSAndroid Build Coastguard Worker 
624*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
625*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
626*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
627*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
628*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
629*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
630*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
631*6dbdd20aSAndroid Build Coastguard Worker       {
632*6dbdd20aSAndroid Build Coastguard Worker           "-o",
633*6dbdd20aSAndroid Build Coastguard Worker           path,
634*6dbdd20aSAndroid Build Coastguard Worker           "-c",
635*6dbdd20aSAndroid Build Coastguard Worker           "-",
636*6dbdd20aSAndroid Build Coastguard Worker       },
637*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
638*6dbdd20aSAndroid Build Coastguard Worker 
639*6dbdd20aSAndroid Build Coastguard Worker   std::string triggers = R"(
640*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name_2"
641*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name"
642*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name_3"
643*6dbdd20aSAndroid Build Coastguard Worker   )";
644*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc_2 = ExecPerfetto(
645*6dbdd20aSAndroid Build Coastguard Worker       {
646*6dbdd20aSAndroid Build Coastguard Worker           "-o",
647*6dbdd20aSAndroid Build Coastguard Worker           path,
648*6dbdd20aSAndroid Build Coastguard Worker           "-c",
649*6dbdd20aSAndroid Build Coastguard Worker           "-",
650*6dbdd20aSAndroid Build Coastguard Worker           "--txt",
651*6dbdd20aSAndroid Build Coastguard Worker       },
652*6dbdd20aSAndroid Build Coastguard Worker       triggers);
653*6dbdd20aSAndroid Build Coastguard Worker 
654*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
655*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
656*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
657*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
658*6dbdd20aSAndroid Build Coastguard Worker 
659*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
660*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
661*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
662*6dbdd20aSAndroid Build Coastguard Worker   });
663*6dbdd20aSAndroid Build Coastguard Worker 
664*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
665*6dbdd20aSAndroid Build Coastguard Worker   // Wait for the producer to start, and then write out some test packets,
666*6dbdd20aSAndroid Build Coastguard Worker   // before the trace actually starts (the trigger is seen).
667*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written_1");
668*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
669*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written_1");
670*6dbdd20aSAndroid Build Coastguard Worker 
671*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_proc_2.Run(&stderr_)) << "stderr: " << stderr_;
672*6dbdd20aSAndroid Build Coastguard Worker 
673*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
674*6dbdd20aSAndroid Build Coastguard Worker 
675*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
676*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(path, trace));
677*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_LT(static_cast<int>(kTestMessageCount), trace.packet_size());
678*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsConfigWithTriggerMode(
679*6dbdd20aSAndroid Build Coastguard Worker       trace, protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
680*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(GetReceivedTriggerNames(trace),
681*6dbdd20aSAndroid Build Coastguard Worker               ElementsAre("trigger_name", "trigger_name_3"));
682*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kTestMessageCount);
683*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kTestMessageSize);
684*6dbdd20aSAndroid Build Coastguard Worker }
685*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,TriggerFromConfigStopsFileOpening)686*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, TriggerFromConfigStopsFileOpening) {
687*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
688*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
689*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
690*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
691*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
692*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(15000);
693*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
694*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
695*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
696*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
697*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
698*6dbdd20aSAndroid Build Coastguard Worker   // time.
699*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
700*6dbdd20aSAndroid Build Coastguard Worker   trigger = trigger_cfg->add_triggers();
701*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name_3");
702*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(60000);
703*6dbdd20aSAndroid Build Coastguard Worker 
704*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
705*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
706*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
707*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
708*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
709*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
710*6dbdd20aSAndroid Build Coastguard Worker   std::string triggers = R"(
711*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name_2"
712*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name"
713*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name_3"
714*6dbdd20aSAndroid Build Coastguard Worker   )";
715*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
716*6dbdd20aSAndroid Build Coastguard Worker       {
717*6dbdd20aSAndroid Build Coastguard Worker           "-o",
718*6dbdd20aSAndroid Build Coastguard Worker           path,
719*6dbdd20aSAndroid Build Coastguard Worker           "-c",
720*6dbdd20aSAndroid Build Coastguard Worker           "-",
721*6dbdd20aSAndroid Build Coastguard Worker           "--txt",
722*6dbdd20aSAndroid Build Coastguard Worker       },
723*6dbdd20aSAndroid Build Coastguard Worker       triggers);
724*6dbdd20aSAndroid Build Coastguard Worker 
725*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
726*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
727*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
728*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
729*6dbdd20aSAndroid Build Coastguard Worker 
730*6dbdd20aSAndroid Build Coastguard Worker   std::string trace_str;
731*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_FALSE(base::ReadFile(path, &trace_str));
732*6dbdd20aSAndroid Build Coastguard Worker 
733*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_proc.Run(&stderr_)) << "stderr: " << stderr_;
734*6dbdd20aSAndroid Build Coastguard Worker 
735*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_FALSE(base::ReadFile(path, &trace_str));
736*6dbdd20aSAndroid Build Coastguard Worker }
737*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,Query)738*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, Query) {
739*6dbdd20aSAndroid Build Coastguard Worker   auto query = ExecPerfetto({"--query"});
740*6dbdd20aSAndroid Build Coastguard Worker   auto query_raw = ExecPerfetto({"--query-raw"});
741*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
742*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, query.Run(&stderr_)) << stderr_;
743*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, query_raw.Run(&stderr_)) << stderr_;
744*6dbdd20aSAndroid Build Coastguard Worker }
745*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,AndroidOnly (CmdTriggerWithUploadFlag))746*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, AndroidOnly(CmdTriggerWithUploadFlag)) {
747*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
748*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
749*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
750*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
751*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::STOP_TRACING);
752*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(15000);
753*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
754*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
755*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
756*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
757*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
758*6dbdd20aSAndroid Build Coastguard Worker   // time.
759*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
760*6dbdd20aSAndroid Build Coastguard Worker 
761*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
762*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
763*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
764*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
765*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
766*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
767*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
768*6dbdd20aSAndroid Build Coastguard Worker       {
769*6dbdd20aSAndroid Build Coastguard Worker           "-o",
770*6dbdd20aSAndroid Build Coastguard Worker           path,
771*6dbdd20aSAndroid Build Coastguard Worker           "-c",
772*6dbdd20aSAndroid Build Coastguard Worker           "-",
773*6dbdd20aSAndroid Build Coastguard Worker       },
774*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
775*6dbdd20aSAndroid Build Coastguard Worker 
776*6dbdd20aSAndroid Build Coastguard Worker   std::string triggers = R"(
777*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name"
778*6dbdd20aSAndroid Build Coastguard Worker   )";
779*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc_2 = ExecPerfetto(
780*6dbdd20aSAndroid Build Coastguard Worker       {
781*6dbdd20aSAndroid Build Coastguard Worker           "--upload",
782*6dbdd20aSAndroid Build Coastguard Worker           "-c",
783*6dbdd20aSAndroid Build Coastguard Worker           "-",
784*6dbdd20aSAndroid Build Coastguard Worker           "--txt",
785*6dbdd20aSAndroid Build Coastguard Worker       },
786*6dbdd20aSAndroid Build Coastguard Worker       triggers);
787*6dbdd20aSAndroid Build Coastguard Worker 
788*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
789*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
790*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
791*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
792*6dbdd20aSAndroid Build Coastguard Worker 
793*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
794*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
795*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
796*6dbdd20aSAndroid Build Coastguard Worker   });
797*6dbdd20aSAndroid Build Coastguard Worker 
798*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
799*6dbdd20aSAndroid Build Coastguard Worker   // Wait for the producer to start, and then write out some test packets,
800*6dbdd20aSAndroid Build Coastguard Worker   // before the trace actually starts (the trigger is seen).
801*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written_1");
802*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
803*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written_1");
804*6dbdd20aSAndroid Build Coastguard Worker 
805*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_proc_2.Run(&stderr_)) << "stderr: " << stderr_;
806*6dbdd20aSAndroid Build Coastguard Worker 
807*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
808*6dbdd20aSAndroid Build Coastguard Worker 
809*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
810*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(path, trace));
811*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kTestMessageCount);
812*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kTestMessageSize);
813*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_LT(static_cast<int>(kTestMessageCount), trace.packet_size());
814*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(trace.packet(),
815*6dbdd20aSAndroid Build Coastguard Worker               Contains(Property(&protos::gen::TracePacket::trigger,
816*6dbdd20aSAndroid Build Coastguard Worker                                 Property(&protos::gen::Trigger::trigger_name,
817*6dbdd20aSAndroid Build Coastguard Worker                                          Eq("trigger_name")))));
818*6dbdd20aSAndroid Build Coastguard Worker }
819*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,TriggerCloneSnapshot)820*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, TriggerCloneSnapshot) {
821*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
822*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
823*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
824*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
825*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::CLONE_SNAPSHOT);
826*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(600000);
827*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
828*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
829*6dbdd20aSAndroid Build Coastguard Worker   // |stop_delay_ms| must be long enough that we can write the packets in
830*6dbdd20aSAndroid Build Coastguard Worker   // before the trace finishes. This has to be long enough for the slowest
831*6dbdd20aSAndroid Build Coastguard Worker   // emulator. But as short as possible to prevent the test running a long
832*6dbdd20aSAndroid Build Coastguard Worker   // time.
833*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
834*6dbdd20aSAndroid Build Coastguard Worker 
835*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
836*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
837*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
838*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
839*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
840*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
841*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
842*6dbdd20aSAndroid Build Coastguard Worker       {
843*6dbdd20aSAndroid Build Coastguard Worker           "-o",
844*6dbdd20aSAndroid Build Coastguard Worker           path,
845*6dbdd20aSAndroid Build Coastguard Worker           "-c",
846*6dbdd20aSAndroid Build Coastguard Worker           "-",
847*6dbdd20aSAndroid Build Coastguard Worker       },
848*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
849*6dbdd20aSAndroid Build Coastguard Worker 
850*6dbdd20aSAndroid Build Coastguard Worker   std::string triggers = R"(
851*6dbdd20aSAndroid Build Coastguard Worker     activate_triggers: "trigger_name"
852*6dbdd20aSAndroid Build Coastguard Worker   )";
853*6dbdd20aSAndroid Build Coastguard Worker   auto trigger_proc = ExecPerfetto(
854*6dbdd20aSAndroid Build Coastguard Worker       {
855*6dbdd20aSAndroid Build Coastguard Worker           "-c",
856*6dbdd20aSAndroid Build Coastguard Worker           "-",
857*6dbdd20aSAndroid Build Coastguard Worker           "--txt",
858*6dbdd20aSAndroid Build Coastguard Worker       },
859*6dbdd20aSAndroid Build Coastguard Worker       triggers);
860*6dbdd20aSAndroid Build Coastguard Worker 
861*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
862*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
863*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
864*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
865*6dbdd20aSAndroid Build Coastguard Worker 
866*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
867*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
868*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
869*6dbdd20aSAndroid Build Coastguard Worker   });
870*6dbdd20aSAndroid Build Coastguard Worker 
871*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
872*6dbdd20aSAndroid Build Coastguard Worker   // Wait for the producer to start, and then write out some test packets,
873*6dbdd20aSAndroid Build Coastguard Worker   // before the trace actually starts (the trigger is seen).
874*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written_1");
875*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
876*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written_1");
877*6dbdd20aSAndroid Build Coastguard Worker 
878*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, trigger_proc.Run(&stderr_)) << "stderr: " << stderr_;
879*6dbdd20aSAndroid Build Coastguard Worker 
880*6dbdd20aSAndroid Build Coastguard Worker   // Now we need to wait that the `perfetto_proc` creates the snapshot trace
881*6dbdd20aSAndroid Build Coastguard Worker   // file in the trace/path.0 file (appending .0). Once that is done we can
882*6dbdd20aSAndroid Build Coastguard Worker   // kill the perfetto cmd (otherwise it will keep running for the whole
883*6dbdd20aSAndroid Build Coastguard Worker   // trigger_timeout_ms, unlike the case of STOP_TRACING.
884*6dbdd20aSAndroid Build Coastguard Worker   std::string snapshot_path = path + ".0";
885*6dbdd20aSAndroid Build Coastguard Worker   for (int i = 0; i < 100 && !base::FileExists(snapshot_path); i++) {
886*6dbdd20aSAndroid Build Coastguard Worker     std::this_thread::sleep_for(std::chrono::milliseconds(100));
887*6dbdd20aSAndroid Build Coastguard Worker   }
888*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(base::FileExists(snapshot_path));
889*6dbdd20aSAndroid Build Coastguard Worker 
890*6dbdd20aSAndroid Build Coastguard Worker   perfetto_proc.SendSigterm();
891*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
892*6dbdd20aSAndroid Build Coastguard Worker 
893*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
894*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(snapshot_path, trace));
895*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kTestMessageCount);
896*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kTestMessageSize);
897*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_LT(static_cast<int>(kTestMessageCount), trace.packet_size());
898*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(trace.packet(),
899*6dbdd20aSAndroid Build Coastguard Worker               Contains(Property(&protos::gen::TracePacket::trigger,
900*6dbdd20aSAndroid Build Coastguard Worker                                 Property(&protos::gen::Trigger::trigger_name,
901*6dbdd20aSAndroid Build Coastguard Worker                                          Eq("trigger_name")))));
902*6dbdd20aSAndroid Build Coastguard Worker }
903*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,MultipleTriggersCloneSnapshot)904*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, MultipleTriggersCloneSnapshot) {
905*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
906*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
907*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_cfg = trace_config.mutable_trigger_config();
908*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_mode(
909*6dbdd20aSAndroid Build Coastguard Worker       protos::gen::TraceConfig::TriggerConfig::CLONE_SNAPSHOT);
910*6dbdd20aSAndroid Build Coastguard Worker   trigger_cfg->set_trigger_timeout_ms(600000);
911*6dbdd20aSAndroid Build Coastguard Worker   // Add two triggers, the "trigger_name_2" hits before "trigger_name_1".
912*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_cfg->add_triggers();
913*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name_1");
914*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(1500);
915*6dbdd20aSAndroid Build Coastguard Worker   trigger = trigger_cfg->add_triggers();
916*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name_2");
917*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(500);
918*6dbdd20aSAndroid Build Coastguard Worker 
919*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
920*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
921*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
922*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
923*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
924*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
925*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
926*6dbdd20aSAndroid Build Coastguard Worker       {
927*6dbdd20aSAndroid Build Coastguard Worker           "-o",
928*6dbdd20aSAndroid Build Coastguard Worker           path,
929*6dbdd20aSAndroid Build Coastguard Worker           "-c",
930*6dbdd20aSAndroid Build Coastguard Worker           "-",
931*6dbdd20aSAndroid Build Coastguard Worker       },
932*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
933*6dbdd20aSAndroid Build Coastguard Worker 
934*6dbdd20aSAndroid Build Coastguard Worker   auto triggers_proc = ExecTrigger({"trigger_name_1", "trigger_name_2"});
935*6dbdd20aSAndroid Build Coastguard Worker 
936*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
937*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
938*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
939*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
940*6dbdd20aSAndroid Build Coastguard Worker 
941*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
942*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
943*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
944*6dbdd20aSAndroid Build Coastguard Worker   });
945*6dbdd20aSAndroid Build Coastguard Worker 
946*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
947*6dbdd20aSAndroid Build Coastguard Worker   // Wait for the producer to start, and then write out some test packets,
948*6dbdd20aSAndroid Build Coastguard Worker   // before the trace actually starts (the trigger is seen).
949*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written_1");
950*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
951*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written_1");
952*6dbdd20aSAndroid Build Coastguard Worker 
953*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, triggers_proc.Run(&stderr_)) << "stderr: " << stderr_;
954*6dbdd20aSAndroid Build Coastguard Worker 
955*6dbdd20aSAndroid Build Coastguard Worker   // Wait for both clone triggers to hit and wait for two snapshot files.
956*6dbdd20aSAndroid Build Coastguard Worker   std::string snapshot_path = path + ".0";
957*6dbdd20aSAndroid Build Coastguard Worker   for (int i = 0; i < 100 && !base::FileExists(snapshot_path); i++) {
958*6dbdd20aSAndroid Build Coastguard Worker     std::this_thread::sleep_for(std::chrono::milliseconds(100));
959*6dbdd20aSAndroid Build Coastguard Worker   }
960*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(base::FileExists(snapshot_path));
961*6dbdd20aSAndroid Build Coastguard Worker 
962*6dbdd20aSAndroid Build Coastguard Worker   std::string snapshot_path_2 = path + ".1";
963*6dbdd20aSAndroid Build Coastguard Worker   for (int i = 0; i < 100 && !base::FileExists(snapshot_path_2); i++) {
964*6dbdd20aSAndroid Build Coastguard Worker     std::this_thread::sleep_for(std::chrono::milliseconds(100));
965*6dbdd20aSAndroid Build Coastguard Worker   }
966*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(base::FileExists(snapshot_path_2));
967*6dbdd20aSAndroid Build Coastguard Worker 
968*6dbdd20aSAndroid Build Coastguard Worker   perfetto_proc.SendSigterm();
969*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
970*6dbdd20aSAndroid Build Coastguard Worker 
971*6dbdd20aSAndroid Build Coastguard Worker   // We now have two traces, the first one was cloned by "trigger_name_2",
972*6dbdd20aSAndroid Build Coastguard Worker   // the second was cloned by "trigger_name_1".
973*6dbdd20aSAndroid Build Coastguard Worker 
974*6dbdd20aSAndroid Build Coastguard Worker   // Asserts for the first trace.
975*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
976*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(snapshot_path, trace));
977*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_LT(static_cast<int>(kTestMessageCount), trace.packet_size());
978*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(GetReceivedTriggerNames(trace),
979*6dbdd20aSAndroid Build Coastguard Worker               ElementsAre("trigger_name_1", "trigger_name_2"));
980*6dbdd20aSAndroid Build Coastguard Worker 
981*6dbdd20aSAndroid Build Coastguard Worker   std::vector<protos::gen::TracePacket> clone_trigger_packets;
982*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TracePacket trigger_packet;
983*6dbdd20aSAndroid Build Coastguard Worker   for (const auto& packet : trace.packet()) {
984*6dbdd20aSAndroid Build Coastguard Worker     if (packet.has_clone_snapshot_trigger()) {
985*6dbdd20aSAndroid Build Coastguard Worker       clone_trigger_packets.push_back(packet);
986*6dbdd20aSAndroid Build Coastguard Worker     } else if (packet.has_trigger() &&
987*6dbdd20aSAndroid Build Coastguard Worker                packet.trigger().trigger_name() == "trigger_name_2") {
988*6dbdd20aSAndroid Build Coastguard Worker       trigger_packet = packet;
989*6dbdd20aSAndroid Build Coastguard Worker     }
990*6dbdd20aSAndroid Build Coastguard Worker   }
991*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_EQ(clone_trigger_packets.size(), 1ul);
992*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(clone_trigger_packets[0].clone_snapshot_trigger().trigger_name(),
993*6dbdd20aSAndroid Build Coastguard Worker             "trigger_name_2");
994*6dbdd20aSAndroid Build Coastguard Worker   // Assert that all fields of 'clone_snapshot_trigger' equal to the same fields
995*6dbdd20aSAndroid Build Coastguard Worker   // of a 'trigger'.
996*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(clone_trigger_packets[0].timestamp(), trigger_packet.timestamp());
997*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(clone_trigger_packets[0].clone_snapshot_trigger(),
998*6dbdd20aSAndroid Build Coastguard Worker             trigger_packet.trigger());
999*6dbdd20aSAndroid Build Coastguard Worker 
1000*6dbdd20aSAndroid Build Coastguard Worker   // Asserts for the second trace.
1001*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace_2;
1002*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(snapshot_path_2, trace_2));
1003*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_LT(static_cast<int>(kTestMessageCount), trace_2.packet_size());
1004*6dbdd20aSAndroid Build Coastguard Worker   // List of received triggers from the main session was cleaned after the first
1005*6dbdd20aSAndroid Build Coastguard Worker   // clone operation happened, the list is empty in the second trace.
1006*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(GetReceivedTriggerNames(trace_2), IsEmpty());
1007*6dbdd20aSAndroid Build Coastguard Worker 
1008*6dbdd20aSAndroid Build Coastguard Worker   std::vector<protos::gen::TracePacket> clone_trigger_packets_2;
1009*6dbdd20aSAndroid Build Coastguard Worker   for (const auto& packet : trace_2.packet()) {
1010*6dbdd20aSAndroid Build Coastguard Worker     if (packet.has_clone_snapshot_trigger()) {
1011*6dbdd20aSAndroid Build Coastguard Worker       clone_trigger_packets_2.push_back(packet);
1012*6dbdd20aSAndroid Build Coastguard Worker     }
1013*6dbdd20aSAndroid Build Coastguard Worker   }
1014*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_EQ(clone_trigger_packets_2.size(), 1ul);
1015*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(clone_trigger_packets_2[0].clone_snapshot_trigger().trigger_name(),
1016*6dbdd20aSAndroid Build Coastguard Worker             "trigger_name_1");
1017*6dbdd20aSAndroid Build Coastguard Worker 
1018*6dbdd20aSAndroid Build Coastguard Worker   // There is no triggers in the second snapshot, but we can compare the
1019*6dbdd20aSAndroid Build Coastguard Worker   // "clone_snapshot_trigger" with the trigger saved into the first snapshot.
1020*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TracePacket trigger_packet_from_first_snapshot;
1021*6dbdd20aSAndroid Build Coastguard Worker   for (const auto& packet : trace.packet()) {
1022*6dbdd20aSAndroid Build Coastguard Worker     if (packet.has_trigger() &&
1023*6dbdd20aSAndroid Build Coastguard Worker         packet.trigger().trigger_name() == "trigger_name_1") {
1024*6dbdd20aSAndroid Build Coastguard Worker       trigger_packet_from_first_snapshot = packet;
1025*6dbdd20aSAndroid Build Coastguard Worker     }
1026*6dbdd20aSAndroid Build Coastguard Worker   }
1027*6dbdd20aSAndroid Build Coastguard Worker   // Assert that all fields of 'clone_snapshot_trigger' equal to the same fields
1028*6dbdd20aSAndroid Build Coastguard Worker   // of a 'trigger'.
1029*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(clone_trigger_packets_2[0].timestamp(),
1030*6dbdd20aSAndroid Build Coastguard Worker             trigger_packet_from_first_snapshot.timestamp());
1031*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(clone_trigger_packets_2[0].clone_snapshot_trigger(),
1032*6dbdd20aSAndroid Build Coastguard Worker             trigger_packet_from_first_snapshot.trigger());
1033*6dbdd20aSAndroid Build Coastguard Worker }
1034*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,SaveForBugreport)1035*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, SaveForBugreport) {
1036*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig trace_config = CreateTraceConfigForBugreportTest();
1037*6dbdd20aSAndroid Build Coastguard Worker   RunBugreportTest(std::move(trace_config));
1038*6dbdd20aSAndroid Build Coastguard Worker }
1039*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,SaveForBugreport_WriteIntoFile)1040*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, SaveForBugreport_WriteIntoFile) {
1041*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig trace_config = CreateTraceConfigForBugreportTest();
1042*6dbdd20aSAndroid Build Coastguard Worker   trace_config.set_file_write_period_ms(60000);  // Will never hit this.
1043*6dbdd20aSAndroid Build Coastguard Worker   trace_config.set_write_into_file(true);
1044*6dbdd20aSAndroid Build Coastguard Worker   RunBugreportTest(std::move(trace_config));
1045*6dbdd20aSAndroid Build Coastguard Worker }
1046*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,Clone)1047*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, Clone) {
1048*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig trace_config = CreateTraceConfigForBugreportTest();
1049*6dbdd20aSAndroid Build Coastguard Worker   RunBugreportTest(std::move(trace_config), /*check_original_trace=*/true,
1050*6dbdd20aSAndroid Build Coastguard Worker                    /*use_explicit_clone=*/true);
1051*6dbdd20aSAndroid Build Coastguard Worker }
1052*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,CloneByName)1053*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, CloneByName) {
1054*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::TraceConfig trace_config =
1055*6dbdd20aSAndroid Build Coastguard Worker       CreateTraceConfigForTest(kTestMessageCount, kTestMessageSize);
1056*6dbdd20aSAndroid Build Coastguard Worker   trace_config.set_unique_session_name("my_unique_session_name");
1057*6dbdd20aSAndroid Build Coastguard Worker 
1058*6dbdd20aSAndroid Build Coastguard Worker   // We have to construct all the processes we want to fork before we start the
1059*6dbdd20aSAndroid Build Coastguard Worker   // service with |StartServiceIfRequired()|. this is because it is unsafe
1060*6dbdd20aSAndroid Build Coastguard Worker   // (could deadlock) to fork after we've spawned some threads which might
1061*6dbdd20aSAndroid Build Coastguard Worker   // printf (and thus hold locks).
1062*6dbdd20aSAndroid Build Coastguard Worker   const std::string path = RandomTraceFileName();
1063*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(path);
1064*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc = ExecPerfetto(
1065*6dbdd20aSAndroid Build Coastguard Worker       {
1066*6dbdd20aSAndroid Build Coastguard Worker           "-o",
1067*6dbdd20aSAndroid Build Coastguard Worker           path,
1068*6dbdd20aSAndroid Build Coastguard Worker           "-c",
1069*6dbdd20aSAndroid Build Coastguard Worker           "-",
1070*6dbdd20aSAndroid Build Coastguard Worker       },
1071*6dbdd20aSAndroid Build Coastguard Worker       trace_config.SerializeAsString());
1072*6dbdd20aSAndroid Build Coastguard Worker 
1073*6dbdd20aSAndroid Build Coastguard Worker   const std::string path_cloned = RandomTraceFileName();
1074*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove path_cloned_remove(path_cloned);
1075*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc_clone = ExecPerfetto({
1076*6dbdd20aSAndroid Build Coastguard Worker       "-o",
1077*6dbdd20aSAndroid Build Coastguard Worker       path_cloned,
1078*6dbdd20aSAndroid Build Coastguard Worker       "--clone-by-name",
1079*6dbdd20aSAndroid Build Coastguard Worker       "my_unique_session_name",
1080*6dbdd20aSAndroid Build Coastguard Worker   });
1081*6dbdd20aSAndroid Build Coastguard Worker 
1082*6dbdd20aSAndroid Build Coastguard Worker   const std::string path_cloned_2 = RandomTraceFileName();
1083*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove path_cloned_2_remove(path_cloned_2);
1084*6dbdd20aSAndroid Build Coastguard Worker   auto perfetto_proc_clone_2 = ExecPerfetto({
1085*6dbdd20aSAndroid Build Coastguard Worker       "-o",
1086*6dbdd20aSAndroid Build Coastguard Worker       path_cloned_2,
1087*6dbdd20aSAndroid Build Coastguard Worker       "--clone-by-name",
1088*6dbdd20aSAndroid Build Coastguard Worker       "non_existing_session_name",
1089*6dbdd20aSAndroid Build Coastguard Worker   });
1090*6dbdd20aSAndroid Build Coastguard Worker 
1091*6dbdd20aSAndroid Build Coastguard Worker   // Start the service and connect a simple fake producer.
1092*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
1093*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
1094*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
1095*6dbdd20aSAndroid Build Coastguard Worker 
1096*6dbdd20aSAndroid Build Coastguard Worker   std::thread background_trace([&perfetto_proc]() {
1097*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
1098*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_EQ(0, perfetto_proc.Run(&stderr_str)) << stderr_str;
1099*6dbdd20aSAndroid Build Coastguard Worker   });
1100*6dbdd20aSAndroid Build Coastguard Worker 
1101*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForProducerEnabled();
1102*6dbdd20aSAndroid Build Coastguard Worker 
1103*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written_1");
1104*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
1105*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written_1");
1106*6dbdd20aSAndroid Build Coastguard Worker 
1107*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_proc_clone.Run(&stderr_)) << "stderr: " << stderr_;
1108*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(base::FileExists(path_cloned));
1109*6dbdd20aSAndroid Build Coastguard Worker 
1110*6dbdd20aSAndroid Build Coastguard Worker   // The command still returns 0, but doesn't create a file.
1111*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_proc_clone_2.Run(&stderr_)) << "stderr: " << stderr_;
1112*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_FALSE(base::FileExists(path_cloned_2));
1113*6dbdd20aSAndroid Build Coastguard Worker 
1114*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace cloned_trace;
1115*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(path_cloned, cloned_trace));
1116*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(cloned_trace, kTestMessageCount);
1117*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(cloned_trace, kTestMessageSize);
1118*6dbdd20aSAndroid Build Coastguard Worker 
1119*6dbdd20aSAndroid Build Coastguard Worker   perfetto_proc.SendSigterm();
1120*6dbdd20aSAndroid Build Coastguard Worker   background_trace.join();
1121*6dbdd20aSAndroid Build Coastguard Worker 
1122*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
1123*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(path, trace));
1124*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kTestMessageCount);
1125*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kTestMessageSize);
1126*6dbdd20aSAndroid Build Coastguard Worker }
1127*6dbdd20aSAndroid Build Coastguard Worker 
1128*6dbdd20aSAndroid Build Coastguard Worker // Regression test for b/279753347: --save-for-bugreport would create an empty
1129*6dbdd20aSAndroid Build Coastguard Worker // file if no session with bugreport_score was active.
TEST_F(PerfettoCmdlineTest,UnavailableBugreportLeavesNoEmptyFiles)1130*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, UnavailableBugreportLeavesNoEmptyFiles) {
1131*6dbdd20aSAndroid Build Coastguard Worker   ScopedFileRemove remove_on_test_exit(GetBugreportTracePath());
1132*6dbdd20aSAndroid Build Coastguard Worker   Exec perfetto_br_proc = ExecPerfetto({"--save-for-bugreport"});
1133*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
1134*6dbdd20aSAndroid Build Coastguard Worker   perfetto_br_proc.Run(&stderr_);
1135*6dbdd20aSAndroid Build Coastguard Worker   // No file exists. Great.
1136*6dbdd20aSAndroid Build Coastguard Worker   if (!base::FileExists(GetBugreportTracePath())) {
1137*6dbdd20aSAndroid Build Coastguard Worker     return;
1138*6dbdd20aSAndroid Build Coastguard Worker   }
1139*6dbdd20aSAndroid Build Coastguard Worker   // A file exists. There are two possiblilities:
1140*6dbdd20aSAndroid Build Coastguard Worker   // 1. There was a bugreport_score session.
1141*6dbdd20aSAndroid Build Coastguard Worker   // 2. There was no bugreport_score session and we're hitting b/279753347.
1142*6dbdd20aSAndroid Build Coastguard Worker   //
1143*6dbdd20aSAndroid Build Coastguard Worker   // Let's check that we're not hitting b/279753347, by checking that the file
1144*6dbdd20aSAndroid Build Coastguard Worker   // is not empty.
1145*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_NE(base::GetFileSize(GetBugreportTracePath()), 0);
1146*6dbdd20aSAndroid Build Coastguard Worker }
1147*6dbdd20aSAndroid Build Coastguard Worker 
1148*6dbdd20aSAndroid Build Coastguard Worker // Tests that SaveTraceForBugreport() works also if the trace has triggers
1149*6dbdd20aSAndroid Build Coastguard Worker // defined and those triggers have not been hit. This is a regression test for
1150*6dbdd20aSAndroid Build Coastguard Worker // b/188008375 .
1151*6dbdd20aSAndroid Build Coastguard Worker #if PERFETTO_BUILDFLAG(PERFETTO_ANDROID_BUILD)
1152*6dbdd20aSAndroid Build Coastguard Worker // Disabled due to b/191940560
1153*6dbdd20aSAndroid Build Coastguard Worker #define MAYBE_SaveForBugreport_Triggers DISABLED_SaveForBugreport_Triggers
1154*6dbdd20aSAndroid Build Coastguard Worker #else
1155*6dbdd20aSAndroid Build Coastguard Worker #define MAYBE_SaveForBugreport_Triggers SaveForBugreport_Triggers
1156*6dbdd20aSAndroid Build Coastguard Worker #endif
TEST_F(PerfettoCmdlineTest,MAYBE_SaveForBugreport_Triggers)1157*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, MAYBE_SaveForBugreport_Triggers) {
1158*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig trace_config = CreateTraceConfigForBugreportTest();
1159*6dbdd20aSAndroid Build Coastguard Worker   trace_config.set_duration_ms(0);  // set_trigger_timeout_ms is used instead.
1160*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger_config = trace_config.mutable_trigger_config();
1161*6dbdd20aSAndroid Build Coastguard Worker   trigger_config->set_trigger_timeout_ms(8.64e+7);
1162*6dbdd20aSAndroid Build Coastguard Worker   trigger_config->set_trigger_mode(TraceConfig::TriggerConfig::STOP_TRACING);
1163*6dbdd20aSAndroid Build Coastguard Worker   auto* trigger = trigger_config->add_triggers();
1164*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_name("trigger_name");
1165*6dbdd20aSAndroid Build Coastguard Worker   trigger->set_stop_delay_ms(1);
1166*6dbdd20aSAndroid Build Coastguard Worker   RunBugreportTest(std::move(trace_config), /*check_original_trace=*/false);
1167*6dbdd20aSAndroid Build Coastguard Worker }
1168*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,SaveAllForBugreport_NoTraces)1169*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, SaveAllForBugreport_NoTraces) {
1170*6dbdd20aSAndroid Build Coastguard Worker   auto save_all_cmd = ExecPerfetto({"--save-all-for-bugreport"});
1171*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
1172*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, save_all_cmd.Run(&stderr_));
1173*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_THAT(stderr_, HasSubstr("No tracing sessions eligible"));
1174*6dbdd20aSAndroid Build Coastguard Worker }
1175*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,SaveAllForBugreport_FourTraces)1176*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, SaveAllForBugreport_FourTraces) {
1177*6dbdd20aSAndroid Build Coastguard Worker   struct TraceProc {
1178*6dbdd20aSAndroid Build Coastguard Worker     explicit TraceProc(TraceConfig c) : cfg(std::move(c)) {}
1179*6dbdd20aSAndroid Build Coastguard Worker 
1180*6dbdd20aSAndroid Build Coastguard Worker     TraceConfig cfg;
1181*6dbdd20aSAndroid Build Coastguard Worker     std::optional<Exec> proc;
1182*6dbdd20aSAndroid Build Coastguard Worker     std::thread thd;
1183*6dbdd20aSAndroid Build Coastguard Worker   };
1184*6dbdd20aSAndroid Build Coastguard Worker 
1185*6dbdd20aSAndroid Build Coastguard Worker   auto remove_br_files = [] {
1186*6dbdd20aSAndroid Build Coastguard Worker     remove((GetBugreportTraceDir() + "/systrace.pftrace").c_str());
1187*6dbdd20aSAndroid Build Coastguard Worker     remove((GetBugreportTraceDir() + "/custom_name.pftrace").c_str());
1188*6dbdd20aSAndroid Build Coastguard Worker     remove((GetBugreportTraceDir() + "/custom_name_1.pftrace").c_str());
1189*6dbdd20aSAndroid Build Coastguard Worker     remove((GetBugreportTraceDir() + "/systrace_1.pftrace").c_str());
1190*6dbdd20aSAndroid Build Coastguard Worker   };
1191*6dbdd20aSAndroid Build Coastguard Worker 
1192*6dbdd20aSAndroid Build Coastguard Worker   remove_br_files();  // Remove both before and after ending the test.
1193*6dbdd20aSAndroid Build Coastguard Worker   auto remove_on_exit = base::OnScopeExit(remove_br_files);
1194*6dbdd20aSAndroid Build Coastguard Worker 
1195*6dbdd20aSAndroid Build Coastguard Worker   auto session_prefix = "bugreport_test_" +
1196*6dbdd20aSAndroid Build Coastguard Worker                         std::to_string(base::GetWallTimeNs().count() % 1000000);
1197*6dbdd20aSAndroid Build Coastguard Worker 
1198*6dbdd20aSAndroid Build Coastguard Worker   // Create four tracing sessions with different bugreport scores.
1199*6dbdd20aSAndroid Build Coastguard Worker   // Two of them will have the default "systrace.pftrace" name.
1200*6dbdd20aSAndroid Build Coastguard Worker   std::vector<TraceProc> traces;
1201*6dbdd20aSAndroid Build Coastguard Worker   const bool add_filt = true;
1202*6dbdd20aSAndroid Build Coastguard Worker   traces.emplace_back(CreateTraceConfigForBugreportTest(/*score=*/1, add_filt));
1203*6dbdd20aSAndroid Build Coastguard Worker   traces.back().cfg.set_unique_session_name(session_prefix + "_1");
1204*6dbdd20aSAndroid Build Coastguard Worker 
1205*6dbdd20aSAndroid Build Coastguard Worker   traces.emplace_back(CreateTraceConfigForBugreportTest(/*score=*/2, add_filt));
1206*6dbdd20aSAndroid Build Coastguard Worker   traces.back().cfg.set_bugreport_filename("custom_name.pftrace");
1207*6dbdd20aSAndroid Build Coastguard Worker   traces.back().cfg.set_unique_session_name(session_prefix + "_2");
1208*6dbdd20aSAndroid Build Coastguard Worker 
1209*6dbdd20aSAndroid Build Coastguard Worker   traces.emplace_back(CreateTraceConfigForBugreportTest(/*score=*/3, add_filt));
1210*6dbdd20aSAndroid Build Coastguard Worker   traces.back().cfg.set_bugreport_filename("custom_name.pftrace");
1211*6dbdd20aSAndroid Build Coastguard Worker   traces.back().cfg.set_unique_session_name(session_prefix + "_3");
1212*6dbdd20aSAndroid Build Coastguard Worker 
1213*6dbdd20aSAndroid Build Coastguard Worker   traces.emplace_back(CreateTraceConfigForBugreportTest(/*score=*/4, add_filt));
1214*6dbdd20aSAndroid Build Coastguard Worker   traces.back().cfg.set_unique_session_name(session_prefix + "_4");
1215*6dbdd20aSAndroid Build Coastguard Worker 
1216*6dbdd20aSAndroid Build Coastguard Worker   for (auto& trace : traces) {
1217*6dbdd20aSAndroid Build Coastguard Worker     std::string cfg = trace.cfg.SerializeAsString();
1218*6dbdd20aSAndroid Build Coastguard Worker     trace.proc = ExecPerfetto({"-o", base::kDevNull, "-c", "-"}, cfg);
1219*6dbdd20aSAndroid Build Coastguard Worker   }
1220*6dbdd20aSAndroid Build Coastguard Worker 
1221*6dbdd20aSAndroid Build Coastguard Worker   Exec perfetto_br_proc = ExecPerfetto({"--save-all-for-bugreport"});
1222*6dbdd20aSAndroid Build Coastguard Worker 
1223*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
1224*6dbdd20aSAndroid Build Coastguard Worker 
1225*6dbdd20aSAndroid Build Coastguard Worker   for (auto& trace : traces) {
1226*6dbdd20aSAndroid Build Coastguard Worker     trace.thd = std::thread([&trace] {
1227*6dbdd20aSAndroid Build Coastguard Worker       std::string stderr_str;
1228*6dbdd20aSAndroid Build Coastguard Worker       ASSERT_EQ(0, trace.proc->Run(&stderr_str)) << stderr_str;
1229*6dbdd20aSAndroid Build Coastguard Worker       PERFETTO_DLOG("perfetto-cmd output:\n%s", stderr_str.c_str());
1230*6dbdd20aSAndroid Build Coastguard Worker     });
1231*6dbdd20aSAndroid Build Coastguard Worker   }
1232*6dbdd20aSAndroid Build Coastguard Worker 
1233*6dbdd20aSAndroid Build Coastguard Worker   // Wait that all tracing sessions are started.
1234*6dbdd20aSAndroid Build Coastguard Worker   // Note that in CTS mode, the Android test infra will start other tracing
1235*6dbdd20aSAndroid Build Coastguard Worker   // sessions for performance reasons. We can't just wait to see 4 sessions,
1236*6dbdd20aSAndroid Build Coastguard Worker   // we need to actually check the unique session name.
1237*6dbdd20aSAndroid Build Coastguard Worker   test_helper().ConnectConsumer();
1238*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForConsumerConnect();
1239*6dbdd20aSAndroid Build Coastguard Worker   for (;;) {
1240*6dbdd20aSAndroid Build Coastguard Worker     auto state = test_helper().QueryServiceStateAndWait();
1241*6dbdd20aSAndroid Build Coastguard Worker     const auto& sessions = state.tracing_sessions();
1242*6dbdd20aSAndroid Build Coastguard Worker     if (std::count_if(sessions.begin(), sessions.end(),
1243*6dbdd20aSAndroid Build Coastguard Worker                       [&](const TracingServiceState::TracingSession& s) {
1244*6dbdd20aSAndroid Build Coastguard Worker                         return base::StartsWith(s.unique_session_name(),
1245*6dbdd20aSAndroid Build Coastguard Worker                                                 session_prefix);
1246*6dbdd20aSAndroid Build Coastguard Worker                       }) >= 4) {
1247*6dbdd20aSAndroid Build Coastguard Worker       break;
1248*6dbdd20aSAndroid Build Coastguard Worker     }
1249*6dbdd20aSAndroid Build Coastguard Worker     base::SleepMicroseconds(100 * 1000);
1250*6dbdd20aSAndroid Build Coastguard Worker   }
1251*6dbdd20aSAndroid Build Coastguard Worker 
1252*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_br_proc.Run(&stderr_)) << stderr_;
1253*6dbdd20aSAndroid Build Coastguard Worker   PERFETTO_DLOG("perfetto --save-all-for-bugreport output:\n-----\n%s\n-----\n",
1254*6dbdd20aSAndroid Build Coastguard Worker                 stderr_.c_str());
1255*6dbdd20aSAndroid Build Coastguard Worker 
1256*6dbdd20aSAndroid Build Coastguard Worker   // Stop all the four ongoing traces, which by now got cloned.
1257*6dbdd20aSAndroid Build Coastguard Worker   for (auto& trace : traces) {
1258*6dbdd20aSAndroid Build Coastguard Worker     trace.proc->SendSigterm();
1259*6dbdd20aSAndroid Build Coastguard Worker     trace.thd.join();
1260*6dbdd20aSAndroid Build Coastguard Worker   }
1261*6dbdd20aSAndroid Build Coastguard Worker 
1262*6dbdd20aSAndroid Build Coastguard Worker   auto check_trace = [&](std::string fname, int expected_score) {
1263*6dbdd20aSAndroid Build Coastguard Worker     std::string fpath = GetBugreportTraceDir() + "/" + fname;
1264*6dbdd20aSAndroid Build Coastguard Worker     ASSERT_TRUE(base::FileExists(fpath)) << fpath;
1265*6dbdd20aSAndroid Build Coastguard Worker     protos::gen::Trace trace;
1266*6dbdd20aSAndroid Build Coastguard Worker     ASSERT_TRUE(ParseNotEmptyTraceFromFile(fpath, trace)) << fpath;
1267*6dbdd20aSAndroid Build Coastguard Worker     EXPECT_THAT(
1268*6dbdd20aSAndroid Build Coastguard Worker         trace.packet(),
1269*6dbdd20aSAndroid Build Coastguard Worker         Contains(Property(&protos::gen::TracePacket::trace_config,
1270*6dbdd20aSAndroid Build Coastguard Worker                           Property(&protos::gen::TraceConfig::bugreport_score,
1271*6dbdd20aSAndroid Build Coastguard Worker                                    Eq(expected_score)))));
1272*6dbdd20aSAndroid Build Coastguard Worker   };
1273*6dbdd20aSAndroid Build Coastguard Worker 
1274*6dbdd20aSAndroid Build Coastguard Worker   check_trace("systrace.pftrace", /*expected_score=*/4);
1275*6dbdd20aSAndroid Build Coastguard Worker   check_trace("custom_name.pftrace", /*expected_score=*/3);
1276*6dbdd20aSAndroid Build Coastguard Worker   check_trace("custom_name_1.pftrace", /*expected_score=*/2);
1277*6dbdd20aSAndroid Build Coastguard Worker   check_trace("systrace_1.pftrace", /*expected_score=*/1);
1278*6dbdd20aSAndroid Build Coastguard Worker }
1279*6dbdd20aSAndroid Build Coastguard Worker 
TEST_F(PerfettoCmdlineTest,SaveAllForBugreport_LargeTrace)1280*6dbdd20aSAndroid Build Coastguard Worker TEST_F(PerfettoCmdlineTest, SaveAllForBugreport_LargeTrace) {
1281*6dbdd20aSAndroid Build Coastguard Worker   auto remove_br_files = [] {
1282*6dbdd20aSAndroid Build Coastguard Worker     remove((GetBugreportTraceDir() + "/systrace.pftrace").c_str());
1283*6dbdd20aSAndroid Build Coastguard Worker   };
1284*6dbdd20aSAndroid Build Coastguard Worker 
1285*6dbdd20aSAndroid Build Coastguard Worker   remove_br_files();  // Remove both before and after ending the test.
1286*6dbdd20aSAndroid Build Coastguard Worker   auto remove_on_exit = base::OnScopeExit(remove_br_files);
1287*6dbdd20aSAndroid Build Coastguard Worker 
1288*6dbdd20aSAndroid Build Coastguard Worker   const uint32_t kMsgCount = 10000;
1289*6dbdd20aSAndroid Build Coastguard Worker   const uint32_t kMsgSize = 1024;
1290*6dbdd20aSAndroid Build Coastguard Worker   TraceConfig cfg = CreateTraceConfigForBugreportTest(
1291*6dbdd20aSAndroid Build Coastguard Worker       /*score=*/1, /*add_filter=*/false, kMsgCount, kMsgSize);
1292*6dbdd20aSAndroid Build Coastguard Worker 
1293*6dbdd20aSAndroid Build Coastguard Worker   auto session_name = "bugreport_test_" +
1294*6dbdd20aSAndroid Build Coastguard Worker                       std::to_string(base::GetWallTimeNs().count() % 1000000);
1295*6dbdd20aSAndroid Build Coastguard Worker 
1296*6dbdd20aSAndroid Build Coastguard Worker   cfg.set_unique_session_name(session_name);
1297*6dbdd20aSAndroid Build Coastguard Worker   std::string cfg_str = cfg.SerializeAsString();
1298*6dbdd20aSAndroid Build Coastguard Worker   Exec trace_proc = ExecPerfetto({"-o", base::kDevNull, "-c", "-"}, cfg_str);
1299*6dbdd20aSAndroid Build Coastguard Worker   Exec perfetto_br_proc = ExecPerfetto({"--save-all-for-bugreport"});
1300*6dbdd20aSAndroid Build Coastguard Worker 
1301*6dbdd20aSAndroid Build Coastguard Worker   StartServiceIfRequiredNoNewExecsAfterThis();
1302*6dbdd20aSAndroid Build Coastguard Worker 
1303*6dbdd20aSAndroid Build Coastguard Worker   auto* fake_producer = test_helper().ConnectFakeProducer();
1304*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_TRUE(fake_producer);
1305*6dbdd20aSAndroid Build Coastguard Worker 
1306*6dbdd20aSAndroid Build Coastguard Worker   std::thread thd([&trace_proc] {
1307*6dbdd20aSAndroid Build Coastguard Worker     std::string stderr_str;
1308*6dbdd20aSAndroid Build Coastguard Worker     ASSERT_EQ(0, trace_proc.Run(&stderr_str)) << stderr_str;
1309*6dbdd20aSAndroid Build Coastguard Worker     PERFETTO_DLOG("perfetto-cmd output:\n%s", stderr_str.c_str());
1310*6dbdd20aSAndroid Build Coastguard Worker   });
1311*6dbdd20aSAndroid Build Coastguard Worker 
1312*6dbdd20aSAndroid Build Coastguard Worker   // Wait that the tracing session is started.
1313*6dbdd20aSAndroid Build Coastguard Worker   test_helper().ConnectConsumer();
1314*6dbdd20aSAndroid Build Coastguard Worker   test_helper().WaitForConsumerConnect();
1315*6dbdd20aSAndroid Build Coastguard Worker   for (;;) {
1316*6dbdd20aSAndroid Build Coastguard Worker     auto state = test_helper().QueryServiceStateAndWait();
1317*6dbdd20aSAndroid Build Coastguard Worker     const auto& sessions = state.tracing_sessions();
1318*6dbdd20aSAndroid Build Coastguard Worker     if (std::count_if(sessions.begin(), sessions.end(),
1319*6dbdd20aSAndroid Build Coastguard Worker                       [&](const TracingServiceState::TracingSession& s) {
1320*6dbdd20aSAndroid Build Coastguard Worker                         return s.unique_session_name() == session_name;
1321*6dbdd20aSAndroid Build Coastguard Worker                       }) >= 1) {
1322*6dbdd20aSAndroid Build Coastguard Worker       break;
1323*6dbdd20aSAndroid Build Coastguard Worker     }
1324*6dbdd20aSAndroid Build Coastguard Worker     base::SleepMicroseconds(100 * 1000);
1325*6dbdd20aSAndroid Build Coastguard Worker   }
1326*6dbdd20aSAndroid Build Coastguard Worker   test_helper().SyncAndWaitProducer();
1327*6dbdd20aSAndroid Build Coastguard Worker 
1328*6dbdd20aSAndroid Build Coastguard Worker   auto on_data_written = task_runner_.CreateCheckpoint("data_written");
1329*6dbdd20aSAndroid Build Coastguard Worker   fake_producer->ProduceEventBatch(test_helper().WrapTask(on_data_written));
1330*6dbdd20aSAndroid Build Coastguard Worker   task_runner_.RunUntilCheckpoint("data_written");
1331*6dbdd20aSAndroid Build Coastguard Worker 
1332*6dbdd20aSAndroid Build Coastguard Worker   EXPECT_EQ(0, perfetto_br_proc.Run(&stderr_)) << stderr_;
1333*6dbdd20aSAndroid Build Coastguard Worker   PERFETTO_DLOG("perfetto --save-all-for-bugreport output:\n-----\n%s\n-----\n",
1334*6dbdd20aSAndroid Build Coastguard Worker                 stderr_.c_str());
1335*6dbdd20aSAndroid Build Coastguard Worker 
1336*6dbdd20aSAndroid Build Coastguard Worker   // Stop the ongoing trace, which by now got cloned.
1337*6dbdd20aSAndroid Build Coastguard Worker   trace_proc.SendSigterm();
1338*6dbdd20aSAndroid Build Coastguard Worker   thd.join();
1339*6dbdd20aSAndroid Build Coastguard Worker 
1340*6dbdd20aSAndroid Build Coastguard Worker   std::string fpath = GetBugreportTraceDir() + "/systrace.pftrace";
1341*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(base::FileExists(fpath)) << fpath;
1342*6dbdd20aSAndroid Build Coastguard Worker   protos::gen::Trace trace;
1343*6dbdd20aSAndroid Build Coastguard Worker   ASSERT_TRUE(ParseNotEmptyTraceFromFile(fpath, trace)) << fpath;
1344*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessages(trace, kMsgCount);
1345*6dbdd20aSAndroid Build Coastguard Worker   ExpectTraceContainsTestMessagesWithSize(trace, kMsgSize);
1346*6dbdd20aSAndroid Build Coastguard Worker }
1347*6dbdd20aSAndroid Build Coastguard Worker 
1348*6dbdd20aSAndroid Build Coastguard Worker }  // namespace perfetto
1349