• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (C) 2017 The Android Open Source Project
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //      http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #include "statsd_test_util.h"
16 
17 #include <aggregator.pb.h>
18 #include <aidl/android/util/StatsEventParcel.h>
19 #include <android-base/properties.h>
20 #include <android-base/stringprintf.h>
21 
22 #include "matchers/SimpleAtomMatchingTracker.h"
23 #include "stats_event.h"
24 #include "stats_util.h"
25 
26 using aidl::android::util::StatsEventParcel;
27 using android::base::SetProperty;
28 using android::base::StringPrintf;
29 using std::shared_ptr;
30 using zetasketch::android::AggregatorStateProto;
31 
32 namespace android {
33 namespace os {
34 namespace statsd {
35 
sendConfig(const StatsdConfig & config)36 bool StatsServiceConfigTest::sendConfig(const StatsdConfig& config) {
37     string str;
38     config.SerializeToString(&str);
39     std::vector<uint8_t> configAsVec(str.begin(), str.end());
40     return service->addConfiguration(kConfigKey, configAsVec, kCallingUid).isOk();
41 }
42 
getReports(sp<StatsLogProcessor> processor,int64_t timestamp,bool include_current)43 ConfigMetricsReport StatsServiceConfigTest::getReports(sp<StatsLogProcessor> processor,
44                                                        int64_t timestamp, bool include_current) {
45     vector<uint8_t> output;
46     ConfigKey configKey(kCallingUid, kConfigKey);
47     processor->onDumpReport(configKey, timestamp, include_current /* include_current_bucket*/,
48                             true /* erase_data */, ADB_DUMP, NO_TIME_CONSTRAINTS, &output);
49     ConfigMetricsReportList reports;
50     reports.ParseFromArray(output.data(), output.size());
51     EXPECT_EQ(1, reports.reports_size());
52     return reports.reports(0);
53 }
54 
outputStreamToProto(ProtoOutputStream * proto)55 StatsLogReport outputStreamToProto(ProtoOutputStream* proto) {
56     vector<uint8_t> bytes;
57     bytes.resize(proto->size());
58     size_t pos = 0;
59     sp<ProtoReader> reader = proto->data();
60 
61     while (reader->readBuffer() != NULL) {
62         size_t toRead = reader->currentToRead();
63         std::memcpy(&((bytes)[pos]), reader->readBuffer(), toRead);
64         pos += toRead;
65         reader->move(toRead);
66     }
67 
68     StatsLogReport report;
69     report.ParseFromArray(bytes.data(), bytes.size());
70     return report;
71 }
72 
CreateSimpleAtomMatcher(const string & name,int atomId)73 AtomMatcher CreateSimpleAtomMatcher(const string& name, int atomId) {
74     AtomMatcher atom_matcher;
75     atom_matcher.set_id(StringToId(name));
76     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
77     simple_atom_matcher->set_atom_id(atomId);
78     return atom_matcher;
79 }
80 
CreateTemperatureAtomMatcher()81 AtomMatcher CreateTemperatureAtomMatcher() {
82     return CreateSimpleAtomMatcher("TemperatureMatcher", util::TEMPERATURE);
83 }
84 
CreateScheduledJobStateChangedAtomMatcher(const string & name,ScheduledJobStateChanged::State state)85 AtomMatcher CreateScheduledJobStateChangedAtomMatcher(const string& name,
86                                                       ScheduledJobStateChanged::State state) {
87     AtomMatcher atom_matcher;
88     atom_matcher.set_id(StringToId(name));
89     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
90     simple_atom_matcher->set_atom_id(util::SCHEDULED_JOB_STATE_CHANGED);
91     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
92     field_value_matcher->set_field(3);  // State field.
93     field_value_matcher->set_eq_int(state);
94     return atom_matcher;
95 }
96 
CreateStartScheduledJobAtomMatcher()97 AtomMatcher CreateStartScheduledJobAtomMatcher() {
98     return CreateScheduledJobStateChangedAtomMatcher("ScheduledJobStart",
99                                                      ScheduledJobStateChanged::STARTED);
100 }
101 
CreateFinishScheduledJobAtomMatcher()102 AtomMatcher CreateFinishScheduledJobAtomMatcher() {
103     return CreateScheduledJobStateChangedAtomMatcher("ScheduledJobFinish",
104                                                      ScheduledJobStateChanged::FINISHED);
105 }
106 
CreateScheduleScheduledJobAtomMatcher()107 AtomMatcher CreateScheduleScheduledJobAtomMatcher() {
108     return CreateScheduledJobStateChangedAtomMatcher("ScheduledJobSchedule",
109                                                      ScheduledJobStateChanged::SCHEDULED);
110 }
111 
CreateScreenBrightnessChangedAtomMatcher()112 AtomMatcher CreateScreenBrightnessChangedAtomMatcher() {
113     AtomMatcher atom_matcher;
114     atom_matcher.set_id(StringToId("ScreenBrightnessChanged"));
115     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
116     simple_atom_matcher->set_atom_id(util::SCREEN_BRIGHTNESS_CHANGED);
117     return atom_matcher;
118 }
119 
CreateUidProcessStateChangedAtomMatcher()120 AtomMatcher CreateUidProcessStateChangedAtomMatcher() {
121     AtomMatcher atom_matcher;
122     atom_matcher.set_id(StringToId("UidProcessStateChanged"));
123     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
124     simple_atom_matcher->set_atom_id(util::UID_PROCESS_STATE_CHANGED);
125     return atom_matcher;
126 }
127 
CreateWakelockStateChangedAtomMatcher(const string & name,WakelockStateChanged::State state)128 AtomMatcher CreateWakelockStateChangedAtomMatcher(const string& name,
129                                                   WakelockStateChanged::State state) {
130     AtomMatcher atom_matcher;
131     atom_matcher.set_id(StringToId(name));
132     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
133     simple_atom_matcher->set_atom_id(util::WAKELOCK_STATE_CHANGED);
134     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
135     field_value_matcher->set_field(4);  // State field.
136     field_value_matcher->set_eq_int(state);
137     return atom_matcher;
138 }
139 
CreateAcquireWakelockAtomMatcher()140 AtomMatcher CreateAcquireWakelockAtomMatcher() {
141     return CreateWakelockStateChangedAtomMatcher("AcquireWakelock", WakelockStateChanged::ACQUIRE);
142 }
143 
CreateReleaseWakelockAtomMatcher()144 AtomMatcher CreateReleaseWakelockAtomMatcher() {
145     return CreateWakelockStateChangedAtomMatcher("ReleaseWakelock", WakelockStateChanged::RELEASE);
146 }
147 
CreateBatterySaverModeStateChangedAtomMatcher(const string & name,BatterySaverModeStateChanged::State state)148 AtomMatcher CreateBatterySaverModeStateChangedAtomMatcher(
149     const string& name, BatterySaverModeStateChanged::State state) {
150     AtomMatcher atom_matcher;
151     atom_matcher.set_id(StringToId(name));
152     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
153     simple_atom_matcher->set_atom_id(util::BATTERY_SAVER_MODE_STATE_CHANGED);
154     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
155     field_value_matcher->set_field(1);  // State field.
156     field_value_matcher->set_eq_int(state);
157     return atom_matcher;
158 }
159 
CreateBatterySaverModeStartAtomMatcher()160 AtomMatcher CreateBatterySaverModeStartAtomMatcher() {
161     return CreateBatterySaverModeStateChangedAtomMatcher(
162         "BatterySaverModeStart", BatterySaverModeStateChanged::ON);
163 }
164 
165 
CreateBatterySaverModeStopAtomMatcher()166 AtomMatcher CreateBatterySaverModeStopAtomMatcher() {
167     return CreateBatterySaverModeStateChangedAtomMatcher(
168         "BatterySaverModeStop", BatterySaverModeStateChanged::OFF);
169 }
170 
CreateBatteryStateChangedAtomMatcher(const string & name,BatteryPluggedStateEnum state)171 AtomMatcher CreateBatteryStateChangedAtomMatcher(const string& name,
172                                                  BatteryPluggedStateEnum state) {
173     AtomMatcher atom_matcher;
174     atom_matcher.set_id(StringToId(name));
175     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
176     simple_atom_matcher->set_atom_id(util::PLUGGED_STATE_CHANGED);
177     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
178     field_value_matcher->set_field(1);  // State field.
179     field_value_matcher->set_eq_int(state);
180     return atom_matcher;
181 }
182 
CreateBatteryStateNoneMatcher()183 AtomMatcher CreateBatteryStateNoneMatcher() {
184     return CreateBatteryStateChangedAtomMatcher("BatteryPluggedNone",
185                                                 BatteryPluggedStateEnum::BATTERY_PLUGGED_NONE);
186 }
187 
CreateBatteryStateUsbMatcher()188 AtomMatcher CreateBatteryStateUsbMatcher() {
189     return CreateBatteryStateChangedAtomMatcher("BatteryPluggedUsb",
190                                                 BatteryPluggedStateEnum::BATTERY_PLUGGED_USB);
191 }
192 
CreateScreenStateChangedAtomMatcher(const string & name,android::view::DisplayStateEnum state)193 AtomMatcher CreateScreenStateChangedAtomMatcher(
194     const string& name, android::view::DisplayStateEnum state) {
195     AtomMatcher atom_matcher;
196     atom_matcher.set_id(StringToId(name));
197     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
198     simple_atom_matcher->set_atom_id(util::SCREEN_STATE_CHANGED);
199     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
200     field_value_matcher->set_field(1);  // State field.
201     field_value_matcher->set_eq_int(state);
202     return atom_matcher;
203 }
204 
CreateScreenTurnedOnAtomMatcher()205 AtomMatcher CreateScreenTurnedOnAtomMatcher() {
206     return CreateScreenStateChangedAtomMatcher("ScreenTurnedOn",
207             android::view::DisplayStateEnum::DISPLAY_STATE_ON);
208 }
209 
CreateScreenTurnedOffAtomMatcher()210 AtomMatcher CreateScreenTurnedOffAtomMatcher() {
211     return CreateScreenStateChangedAtomMatcher("ScreenTurnedOff",
212             ::android::view::DisplayStateEnum::DISPLAY_STATE_OFF);
213 }
214 
CreateSyncStateChangedAtomMatcher(const string & name,SyncStateChanged::State state)215 AtomMatcher CreateSyncStateChangedAtomMatcher(
216     const string& name, SyncStateChanged::State state) {
217     AtomMatcher atom_matcher;
218     atom_matcher.set_id(StringToId(name));
219     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
220     simple_atom_matcher->set_atom_id(util::SYNC_STATE_CHANGED);
221     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
222     field_value_matcher->set_field(3);  // State field.
223     field_value_matcher->set_eq_int(state);
224     return atom_matcher;
225 }
226 
CreateSyncStartAtomMatcher()227 AtomMatcher CreateSyncStartAtomMatcher() {
228     return CreateSyncStateChangedAtomMatcher("SyncStart", SyncStateChanged::ON);
229 }
230 
CreateSyncEndAtomMatcher()231 AtomMatcher CreateSyncEndAtomMatcher() {
232     return CreateSyncStateChangedAtomMatcher("SyncEnd", SyncStateChanged::OFF);
233 }
234 
CreateActivityForegroundStateChangedAtomMatcher(const string & name,ActivityForegroundStateChanged::State state)235 AtomMatcher CreateActivityForegroundStateChangedAtomMatcher(
236     const string& name, ActivityForegroundStateChanged::State state) {
237     AtomMatcher atom_matcher;
238     atom_matcher.set_id(StringToId(name));
239     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
240     simple_atom_matcher->set_atom_id(util::ACTIVITY_FOREGROUND_STATE_CHANGED);
241     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
242     field_value_matcher->set_field(4);  // Activity field.
243     field_value_matcher->set_eq_int(state);
244     return atom_matcher;
245 }
246 
CreateMoveToBackgroundAtomMatcher()247 AtomMatcher CreateMoveToBackgroundAtomMatcher() {
248     return CreateActivityForegroundStateChangedAtomMatcher(
249         "Background", ActivityForegroundStateChanged::BACKGROUND);
250 }
251 
CreateMoveToForegroundAtomMatcher()252 AtomMatcher CreateMoveToForegroundAtomMatcher() {
253     return CreateActivityForegroundStateChangedAtomMatcher(
254         "Foreground", ActivityForegroundStateChanged::FOREGROUND);
255 }
256 
CreateProcessLifeCycleStateChangedAtomMatcher(const string & name,ProcessLifeCycleStateChanged::State state)257 AtomMatcher CreateProcessLifeCycleStateChangedAtomMatcher(
258     const string& name, ProcessLifeCycleStateChanged::State state) {
259     AtomMatcher atom_matcher;
260     atom_matcher.set_id(StringToId(name));
261     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
262     simple_atom_matcher->set_atom_id(util::PROCESS_LIFE_CYCLE_STATE_CHANGED);
263     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
264     field_value_matcher->set_field(3);  // Process state field.
265     field_value_matcher->set_eq_int(state);
266     return atom_matcher;
267 }
268 
CreateProcessCrashAtomMatcher()269 AtomMatcher CreateProcessCrashAtomMatcher() {
270     return CreateProcessLifeCycleStateChangedAtomMatcher(
271         "Crashed", ProcessLifeCycleStateChanged::CRASHED);
272 }
273 
CreateAppStartOccurredAtomMatcher()274 AtomMatcher CreateAppStartOccurredAtomMatcher() {
275     return CreateSimpleAtomMatcher("AppStartOccurredMatcher", util::APP_START_OCCURRED);
276 }
277 
CreateTestAtomRepeatedStateAtomMatcher(const string & name,TestAtomReported::State state,Position position)278 AtomMatcher CreateTestAtomRepeatedStateAtomMatcher(const string& name,
279                                                    TestAtomReported::State state,
280                                                    Position position) {
281     AtomMatcher atom_matcher = CreateSimpleAtomMatcher(name, util::TEST_ATOM_REPORTED);
282     auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
283     auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
284     field_value_matcher->set_field(14);  // Repeated enum field.
285     field_value_matcher->set_eq_int(state);
286     field_value_matcher->set_position(position);
287     return atom_matcher;
288 }
289 
CreateTestAtomRepeatedStateFirstOffAtomMatcher()290 AtomMatcher CreateTestAtomRepeatedStateFirstOffAtomMatcher() {
291     return CreateTestAtomRepeatedStateAtomMatcher("TestFirstStateOff", TestAtomReported::OFF,
292                                                   Position::FIRST);
293 }
294 
CreateTestAtomRepeatedStateFirstOnAtomMatcher()295 AtomMatcher CreateTestAtomRepeatedStateFirstOnAtomMatcher() {
296     return CreateTestAtomRepeatedStateAtomMatcher("TestFirstStateOn", TestAtomReported::ON,
297                                                   Position::FIRST);
298 }
299 
CreateTestAtomRepeatedStateAnyOnAtomMatcher()300 AtomMatcher CreateTestAtomRepeatedStateAnyOnAtomMatcher() {
301     return CreateTestAtomRepeatedStateAtomMatcher("TestAnyStateOn", TestAtomReported::ON,
302                                                   Position::ANY);
303 }
304 
addMatcherToMatcherCombination(const AtomMatcher & matcher,AtomMatcher * combinationMatcher)305 void addMatcherToMatcherCombination(const AtomMatcher& matcher, AtomMatcher* combinationMatcher) {
306     combinationMatcher->mutable_combination()->add_matcher(matcher.id());
307 }
308 
CreateScheduledJobPredicate()309 Predicate CreateScheduledJobPredicate() {
310     Predicate predicate;
311     predicate.set_id(StringToId("ScheduledJobRunningPredicate"));
312     predicate.mutable_simple_predicate()->set_start(StringToId("ScheduledJobStart"));
313     predicate.mutable_simple_predicate()->set_stop(StringToId("ScheduledJobFinish"));
314     return predicate;
315 }
316 
CreateBatterySaverModePredicate()317 Predicate CreateBatterySaverModePredicate() {
318     Predicate predicate;
319     predicate.set_id(StringToId("BatterySaverIsOn"));
320     predicate.mutable_simple_predicate()->set_start(StringToId("BatterySaverModeStart"));
321     predicate.mutable_simple_predicate()->set_stop(StringToId("BatterySaverModeStop"));
322     return predicate;
323 }
324 
CreateDeviceUnpluggedPredicate()325 Predicate CreateDeviceUnpluggedPredicate() {
326     Predicate predicate;
327     predicate.set_id(StringToId("DeviceUnplugged"));
328     predicate.mutable_simple_predicate()->set_start(StringToId("BatteryPluggedNone"));
329     predicate.mutable_simple_predicate()->set_stop(StringToId("BatteryPluggedUsb"));
330     return predicate;
331 }
332 
CreateScreenIsOnPredicate()333 Predicate CreateScreenIsOnPredicate() {
334     Predicate predicate;
335     predicate.set_id(StringToId("ScreenIsOn"));
336     predicate.mutable_simple_predicate()->set_start(StringToId("ScreenTurnedOn"));
337     predicate.mutable_simple_predicate()->set_stop(StringToId("ScreenTurnedOff"));
338     return predicate;
339 }
340 
CreateScreenIsOffPredicate()341 Predicate CreateScreenIsOffPredicate() {
342     Predicate predicate;
343     predicate.set_id(StringToId("ScreenIsOff"));
344     predicate.mutable_simple_predicate()->set_start(StringToId("ScreenTurnedOff"));
345     predicate.mutable_simple_predicate()->set_stop(StringToId("ScreenTurnedOn"));
346     return predicate;
347 }
348 
CreateHoldingWakelockPredicate()349 Predicate CreateHoldingWakelockPredicate() {
350     Predicate predicate;
351     predicate.set_id(StringToId("HoldingWakelock"));
352     predicate.mutable_simple_predicate()->set_start(StringToId("AcquireWakelock"));
353     predicate.mutable_simple_predicate()->set_stop(StringToId("ReleaseWakelock"));
354     return predicate;
355 }
356 
CreateIsSyncingPredicate()357 Predicate CreateIsSyncingPredicate() {
358     Predicate predicate;
359     predicate.set_id(StringToId("IsSyncing"));
360     predicate.mutable_simple_predicate()->set_start(StringToId("SyncStart"));
361     predicate.mutable_simple_predicate()->set_stop(StringToId("SyncEnd"));
362     return predicate;
363 }
364 
CreateIsInBackgroundPredicate()365 Predicate CreateIsInBackgroundPredicate() {
366     Predicate predicate;
367     predicate.set_id(StringToId("IsInBackground"));
368     predicate.mutable_simple_predicate()->set_start(StringToId("Background"));
369     predicate.mutable_simple_predicate()->set_stop(StringToId("Foreground"));
370     return predicate;
371 }
372 
CreateTestAtomRepeatedStateFirstOffPredicate()373 Predicate CreateTestAtomRepeatedStateFirstOffPredicate() {
374     Predicate predicate;
375     predicate.set_id(StringToId("TestFirstStateIsOff"));
376     predicate.mutable_simple_predicate()->set_start(StringToId("TestFirstStateOff"));
377     predicate.mutable_simple_predicate()->set_stop(StringToId("TestFirstStateOn"));
378     return predicate;
379 }
380 
CreateScreenState()381 State CreateScreenState() {
382     State state;
383     state.set_id(StringToId("ScreenState"));
384     state.set_atom_id(util::SCREEN_STATE_CHANGED);
385     return state;
386 }
387 
CreateUidProcessState()388 State CreateUidProcessState() {
389     State state;
390     state.set_id(StringToId("UidProcessState"));
391     state.set_atom_id(util::UID_PROCESS_STATE_CHANGED);
392     return state;
393 }
394 
CreateOverlayState()395 State CreateOverlayState() {
396     State state;
397     state.set_id(StringToId("OverlayState"));
398     state.set_atom_id(util::OVERLAY_STATE_CHANGED);
399     return state;
400 }
401 
CreateScreenStateWithOnOffMap(int64_t screenOnId,int64_t screenOffId)402 State CreateScreenStateWithOnOffMap(int64_t screenOnId, int64_t screenOffId) {
403     State state;
404     state.set_id(StringToId("ScreenStateOnOff"));
405     state.set_atom_id(util::SCREEN_STATE_CHANGED);
406 
407     auto map = CreateScreenStateOnOffMap(screenOnId, screenOffId);
408     *state.mutable_map() = map;
409 
410     return state;
411 }
412 
CreateScreenStateWithSimpleOnOffMap(int64_t screenOnId,int64_t screenOffId)413 State CreateScreenStateWithSimpleOnOffMap(int64_t screenOnId, int64_t screenOffId) {
414     State state;
415     state.set_id(StringToId("ScreenStateSimpleOnOff"));
416     state.set_atom_id(util::SCREEN_STATE_CHANGED);
417 
418     auto map = CreateScreenStateSimpleOnOffMap(screenOnId, screenOffId);
419     *state.mutable_map() = map;
420 
421     return state;
422 }
423 
CreateScreenStateOnGroup(int64_t screenOnId)424 StateMap_StateGroup CreateScreenStateOnGroup(int64_t screenOnId) {
425     StateMap_StateGroup group;
426     group.set_group_id(screenOnId);
427     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_ON);
428     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_VR);
429     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_ON_SUSPEND);
430     return group;
431 }
432 
CreateScreenStateOffGroup(int64_t screenOffId)433 StateMap_StateGroup CreateScreenStateOffGroup(int64_t screenOffId) {
434     StateMap_StateGroup group;
435     group.set_group_id(screenOffId);
436     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_OFF);
437     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_DOZE);
438     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_DOZE_SUSPEND);
439     return group;
440 }
441 
CreateScreenStateSimpleOnGroup(int64_t screenOnId)442 StateMap_StateGroup CreateScreenStateSimpleOnGroup(int64_t screenOnId) {
443     StateMap_StateGroup group;
444     group.set_group_id(screenOnId);
445     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_ON);
446     return group;
447 }
448 
CreateScreenStateSimpleOffGroup(int64_t screenOffId)449 StateMap_StateGroup CreateScreenStateSimpleOffGroup(int64_t screenOffId) {
450     StateMap_StateGroup group;
451     group.set_group_id(screenOffId);
452     group.add_value(android::view::DisplayStateEnum::DISPLAY_STATE_OFF);
453     return group;
454 }
455 
CreateScreenStateOnOffMap(int64_t screenOnId,int64_t screenOffId)456 StateMap CreateScreenStateOnOffMap(int64_t screenOnId, int64_t screenOffId) {
457     StateMap map;
458     *map.add_group() = CreateScreenStateOnGroup(screenOnId);
459     *map.add_group() = CreateScreenStateOffGroup(screenOffId);
460     return map;
461 }
462 
CreateScreenStateSimpleOnOffMap(int64_t screenOnId,int64_t screenOffId)463 StateMap CreateScreenStateSimpleOnOffMap(int64_t screenOnId, int64_t screenOffId) {
464     StateMap map;
465     *map.add_group() = CreateScreenStateSimpleOnGroup(screenOnId);
466     *map.add_group() = CreateScreenStateSimpleOffGroup(screenOffId);
467     return map;
468 }
469 
addPredicateToPredicateCombination(const Predicate & predicate,Predicate * combinationPredicate)470 void addPredicateToPredicateCombination(const Predicate& predicate,
471                                         Predicate* combinationPredicate) {
472     combinationPredicate->mutable_combination()->add_predicate(predicate.id());
473 }
474 
CreateAttributionUidDimensions(const int atomId,const std::vector<Position> & positions)475 FieldMatcher CreateAttributionUidDimensions(const int atomId,
476                                             const std::vector<Position>& positions) {
477     FieldMatcher dimensions;
478     dimensions.set_field(atomId);
479     for (const auto position : positions) {
480         auto child = dimensions.add_child();
481         child->set_field(1);
482         child->set_position(position);
483         child->add_child()->set_field(1);
484     }
485     return dimensions;
486 }
487 
CreateAttributionUidAndTagDimensions(const int atomId,const std::vector<Position> & positions)488 FieldMatcher CreateAttributionUidAndTagDimensions(const int atomId,
489                                                  const std::vector<Position>& positions) {
490     FieldMatcher dimensions;
491     dimensions.set_field(atomId);
492     for (const auto position : positions) {
493         auto child = dimensions.add_child();
494         child->set_field(1);
495         child->set_position(position);
496         child->add_child()->set_field(1);
497         child->add_child()->set_field(2);
498     }
499     return dimensions;
500 }
501 
CreateDimensions(const int atomId,const std::vector<int> & fields)502 FieldMatcher CreateDimensions(const int atomId, const std::vector<int>& fields) {
503     FieldMatcher dimensions;
504     dimensions.set_field(atomId);
505     for (const int field : fields) {
506         dimensions.add_child()->set_field(field);
507     }
508     return dimensions;
509 }
510 
CreateRepeatedDimensions(const int atomId,const std::vector<int> & fields,const std::vector<Position> & positions)511 FieldMatcher CreateRepeatedDimensions(const int atomId, const std::vector<int>& fields,
512                                       const std::vector<Position>& positions) {
513     FieldMatcher dimensions;
514     if (fields.size() != positions.size()) {
515         return dimensions;
516     }
517 
518     dimensions.set_field(atomId);
519     for (size_t i = 0; i < fields.size(); i++) {
520         auto child = dimensions.add_child();
521         child->set_field(fields[i]);
522         child->set_position(positions[i]);
523     }
524     return dimensions;
525 }
526 
CreateAttributionUidAndOtherDimensions(const int atomId,const std::vector<Position> & positions,const std::vector<int> & fields)527 FieldMatcher CreateAttributionUidAndOtherDimensions(const int atomId,
528                                                     const std::vector<Position>& positions,
529                                                     const std::vector<int>& fields) {
530     FieldMatcher dimensions = CreateAttributionUidDimensions(atomId, positions);
531 
532     for (const int field : fields) {
533         dimensions.add_child()->set_field(field);
534     }
535     return dimensions;
536 }
537 
createEventMetric(const string & name,const int64_t what,const optional<int64_t> & condition)538 EventMetric createEventMetric(const string& name, const int64_t what,
539                               const optional<int64_t>& condition) {
540     EventMetric metric;
541     metric.set_id(StringToId(name));
542     metric.set_what(what);
543     if (condition) {
544         metric.set_condition(condition.value());
545     }
546     return metric;
547 }
548 
createCountMetric(const string & name,const int64_t what,const optional<int64_t> & condition,const vector<int64_t> & states)549 CountMetric createCountMetric(const string& name, const int64_t what,
550                               const optional<int64_t>& condition, const vector<int64_t>& states) {
551     CountMetric metric;
552     metric.set_id(StringToId(name));
553     metric.set_what(what);
554     metric.set_bucket(TEN_MINUTES);
555     if (condition) {
556         metric.set_condition(condition.value());
557     }
558     for (const int64_t state : states) {
559         metric.add_slice_by_state(state);
560     }
561     return metric;
562 }
563 
createDurationMetric(const string & name,const int64_t what,const optional<int64_t> & condition,const vector<int64_t> & states)564 DurationMetric createDurationMetric(const string& name, const int64_t what,
565                                     const optional<int64_t>& condition,
566                                     const vector<int64_t>& states) {
567     DurationMetric metric;
568     metric.set_id(StringToId(name));
569     metric.set_what(what);
570     metric.set_bucket(TEN_MINUTES);
571     if (condition) {
572         metric.set_condition(condition.value());
573     }
574     for (const int64_t state : states) {
575         metric.add_slice_by_state(state);
576     }
577     return metric;
578 }
579 
createGaugeMetric(const string & name,const int64_t what,const GaugeMetric::SamplingType samplingType,const optional<int64_t> & condition,const optional<int64_t> & triggerEvent)580 GaugeMetric createGaugeMetric(const string& name, const int64_t what,
581                               const GaugeMetric::SamplingType samplingType,
582                               const optional<int64_t>& condition,
583                               const optional<int64_t>& triggerEvent) {
584     GaugeMetric metric;
585     metric.set_id(StringToId(name));
586     metric.set_what(what);
587     metric.set_bucket(TEN_MINUTES);
588     metric.set_sampling_type(samplingType);
589     if (condition) {
590         metric.set_condition(condition.value());
591     }
592     if (triggerEvent) {
593         metric.set_trigger_event(triggerEvent.value());
594     }
595     metric.mutable_gauge_fields_filter()->set_include_all(true);
596     return metric;
597 }
598 
createValueMetric(const string & name,const AtomMatcher & what,const int valueField,const optional<int64_t> & condition,const vector<int64_t> & states)599 ValueMetric createValueMetric(const string& name, const AtomMatcher& what, const int valueField,
600                               const optional<int64_t>& condition, const vector<int64_t>& states) {
601     ValueMetric metric;
602     metric.set_id(StringToId(name));
603     metric.set_what(what.id());
604     metric.set_bucket(TEN_MINUTES);
605     metric.mutable_value_field()->set_field(what.simple_atom_matcher().atom_id());
606     metric.mutable_value_field()->add_child()->set_field(valueField);
607     if (condition) {
608         metric.set_condition(condition.value());
609     }
610     for (const int64_t state : states) {
611         metric.add_slice_by_state(state);
612     }
613     return metric;
614 }
615 
createKllMetric(const string & name,const AtomMatcher & what,const int kllField,const optional<int64_t> & condition)616 KllMetric createKllMetric(const string& name, const AtomMatcher& what, const int kllField,
617                           const optional<int64_t>& condition) {
618     KllMetric metric;
619     metric.set_id(StringToId(name));
620     metric.set_what(what.id());
621     metric.set_bucket(TEN_MINUTES);
622     metric.mutable_kll_field()->set_field(what.simple_atom_matcher().atom_id());
623     metric.mutable_kll_field()->add_child()->set_field(kllField);
624     if (condition) {
625         metric.set_condition(condition.value());
626     }
627     return metric;
628 }
629 
createAlert(const string & name,const int64_t metricId,const int buckets,const int64_t triggerSum)630 Alert createAlert(const string& name, const int64_t metricId, const int buckets,
631                   const int64_t triggerSum) {
632     Alert alert;
633     alert.set_id(StringToId(name));
634     alert.set_metric_id(metricId);
635     alert.set_num_buckets(buckets);
636     alert.set_trigger_if_sum_gt(triggerSum);
637     return alert;
638 }
639 
createAlarm(const string & name,const int64_t offsetMillis,const int64_t periodMillis)640 Alarm createAlarm(const string& name, const int64_t offsetMillis, const int64_t periodMillis) {
641     Alarm alarm;
642     alarm.set_id(StringToId(name));
643     alarm.set_offset_millis(offsetMillis);
644     alarm.set_period_millis(periodMillis);
645     return alarm;
646 }
647 
createSubscription(const string & name,const Subscription_RuleType type,const int64_t ruleId)648 Subscription createSubscription(const string& name, const Subscription_RuleType type,
649                                 const int64_t ruleId) {
650     Subscription subscription;
651     subscription.set_id(StringToId(name));
652     subscription.set_rule_type(type);
653     subscription.set_rule_id(ruleId);
654     subscription.mutable_broadcast_subscriber_details();
655     return subscription;
656 }
657 
658 // START: get primary key functions
getUidProcessKey(int uid,HashableDimensionKey * key)659 void getUidProcessKey(int uid, HashableDimensionKey* key) {
660     int pos1[] = {1, 0, 0};
661     Field field1(27 /* atom id */, pos1, 0 /* depth */);
662     Value value1((int32_t)uid);
663 
664     key->addValue(FieldValue(field1, value1));
665 }
666 
getOverlayKey(int uid,string packageName,HashableDimensionKey * key)667 void getOverlayKey(int uid, string packageName, HashableDimensionKey* key) {
668     int pos1[] = {1, 0, 0};
669     int pos2[] = {2, 0, 0};
670 
671     Field field1(59 /* atom id */, pos1, 0 /* depth */);
672     Field field2(59 /* atom id */, pos2, 0 /* depth */);
673 
674     Value value1((int32_t)uid);
675     Value value2(packageName);
676 
677     key->addValue(FieldValue(field1, value1));
678     key->addValue(FieldValue(field2, value2));
679 }
680 
getPartialWakelockKey(int uid,const std::string & tag,HashableDimensionKey * key)681 void getPartialWakelockKey(int uid, const std::string& tag, HashableDimensionKey* key) {
682     int pos1[] = {1, 1, 1};
683     int pos3[] = {2, 0, 0};
684     int pos4[] = {3, 0, 0};
685 
686     Field field1(10 /* atom id */, pos1, 2 /* depth */);
687 
688     Field field3(10 /* atom id */, pos3, 0 /* depth */);
689     Field field4(10 /* atom id */, pos4, 0 /* depth */);
690 
691     Value value1((int32_t)uid);
692     Value value3((int32_t)1 /*partial*/);
693     Value value4(tag);
694 
695     key->addValue(FieldValue(field1, value1));
696     key->addValue(FieldValue(field3, value3));
697     key->addValue(FieldValue(field4, value4));
698 }
699 
getPartialWakelockKey(int uid,HashableDimensionKey * key)700 void getPartialWakelockKey(int uid, HashableDimensionKey* key) {
701     int pos1[] = {1, 1, 1};
702     int pos3[] = {2, 0, 0};
703 
704     Field field1(10 /* atom id */, pos1, 2 /* depth */);
705     Field field3(10 /* atom id */, pos3, 0 /* depth */);
706 
707     Value value1((int32_t)uid);
708     Value value3((int32_t)1 /*partial*/);
709 
710     key->addValue(FieldValue(field1, value1));
711     key->addValue(FieldValue(field3, value3));
712 }
713 // END: get primary key functions
714 
writeAttribution(AStatsEvent * statsEvent,const vector<int> & attributionUids,const vector<string> & attributionTags)715 void writeAttribution(AStatsEvent* statsEvent, const vector<int>& attributionUids,
716                       const vector<string>& attributionTags) {
717     vector<const char*> cTags(attributionTags.size());
718     for (int i = 0; i < cTags.size(); i++) {
719         cTags[i] = attributionTags[i].c_str();
720     }
721 
722     AStatsEvent_writeAttributionChain(statsEvent,
723                                       reinterpret_cast<const uint32_t*>(attributionUids.data()),
724                                       cTags.data(), attributionUids.size());
725 }
726 
parseStatsEventToLogEvent(AStatsEvent * statsEvent,LogEvent * logEvent)727 void parseStatsEventToLogEvent(AStatsEvent* statsEvent, LogEvent* logEvent) {
728     AStatsEvent_build(statsEvent);
729 
730     size_t size;
731     uint8_t* buf = AStatsEvent_getBuffer(statsEvent, &size);
732     logEvent->parseBuffer(buf, size);
733 
734     AStatsEvent_release(statsEvent);
735 }
736 
CreateTwoValueLogEvent(LogEvent * logEvent,int atomId,int64_t eventTimeNs,int32_t value1,int32_t value2)737 void CreateTwoValueLogEvent(LogEvent* logEvent, int atomId, int64_t eventTimeNs, int32_t value1,
738                             int32_t value2) {
739     AStatsEvent* statsEvent = AStatsEvent_obtain();
740     AStatsEvent_setAtomId(statsEvent, atomId);
741     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
742 
743     AStatsEvent_writeInt32(statsEvent, value1);
744     AStatsEvent_writeInt32(statsEvent, value2);
745 
746     parseStatsEventToLogEvent(statsEvent, logEvent);
747 }
748 
CreateTwoValueLogEvent(int atomId,int64_t eventTimeNs,int32_t value1,int32_t value2)749 shared_ptr<LogEvent> CreateTwoValueLogEvent(int atomId, int64_t eventTimeNs, int32_t value1,
750                                             int32_t value2) {
751     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
752     CreateTwoValueLogEvent(logEvent.get(), atomId, eventTimeNs, value1, value2);
753     return logEvent;
754 }
755 
CreateThreeValueLogEvent(LogEvent * logEvent,int atomId,int64_t eventTimeNs,int32_t value1,int32_t value2,int32_t value3)756 void CreateThreeValueLogEvent(LogEvent* logEvent, int atomId, int64_t eventTimeNs, int32_t value1,
757                               int32_t value2, int32_t value3) {
758     AStatsEvent* statsEvent = AStatsEvent_obtain();
759     AStatsEvent_setAtomId(statsEvent, atomId);
760     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
761 
762     AStatsEvent_writeInt32(statsEvent, value1);
763     AStatsEvent_writeInt32(statsEvent, value2);
764     AStatsEvent_writeInt32(statsEvent, value3);
765 
766     parseStatsEventToLogEvent(statsEvent, logEvent);
767 }
768 
CreateThreeValueLogEvent(int atomId,int64_t eventTimeNs,int32_t value1,int32_t value2,int32_t value3)769 shared_ptr<LogEvent> CreateThreeValueLogEvent(int atomId, int64_t eventTimeNs, int32_t value1,
770                                               int32_t value2, int32_t value3) {
771     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
772     CreateThreeValueLogEvent(logEvent.get(), atomId, eventTimeNs, value1, value2, value3);
773     return logEvent;
774 }
775 
CreateRepeatedValueLogEvent(LogEvent * logEvent,int atomId,int64_t eventTimeNs,int32_t value)776 void CreateRepeatedValueLogEvent(LogEvent* logEvent, int atomId, int64_t eventTimeNs,
777                                  int32_t value) {
778     AStatsEvent* statsEvent = AStatsEvent_obtain();
779     AStatsEvent_setAtomId(statsEvent, atomId);
780     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
781 
782     AStatsEvent_writeInt32(statsEvent, value);
783     AStatsEvent_writeInt32(statsEvent, value);
784 
785     parseStatsEventToLogEvent(statsEvent, logEvent);
786 }
787 
CreateRepeatedValueLogEvent(int atomId,int64_t eventTimeNs,int32_t value)788 shared_ptr<LogEvent> CreateRepeatedValueLogEvent(int atomId, int64_t eventTimeNs, int32_t value) {
789     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
790     CreateRepeatedValueLogEvent(logEvent.get(), atomId, eventTimeNs, value);
791     return logEvent;
792 }
793 
CreateNoValuesLogEvent(LogEvent * logEvent,int atomId,int64_t eventTimeNs)794 void CreateNoValuesLogEvent(LogEvent* logEvent, int atomId, int64_t eventTimeNs) {
795     AStatsEvent* statsEvent = AStatsEvent_obtain();
796     AStatsEvent_setAtomId(statsEvent, atomId);
797     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
798 
799     parseStatsEventToLogEvent(statsEvent, logEvent);
800 }
801 
CreateNoValuesLogEvent(int atomId,int64_t eventTimeNs)802 shared_ptr<LogEvent> CreateNoValuesLogEvent(int atomId, int64_t eventTimeNs) {
803     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
804     CreateNoValuesLogEvent(logEvent.get(), atomId, eventTimeNs);
805     return logEvent;
806 }
807 
makeUidStatsEvent(int atomId,int64_t eventTimeNs,int uid,int data1,int data2)808 AStatsEvent* makeUidStatsEvent(int atomId, int64_t eventTimeNs, int uid, int data1, int data2) {
809     AStatsEvent* statsEvent = AStatsEvent_obtain();
810     AStatsEvent_setAtomId(statsEvent, atomId);
811     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
812 
813     AStatsEvent_writeInt32(statsEvent, uid);
814     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
815     AStatsEvent_writeInt32(statsEvent, data1);
816     AStatsEvent_writeInt32(statsEvent, data2);
817 
818     return statsEvent;
819 }
820 
makeUidStatsEvent(int atomId,int64_t eventTimeNs,int uid,int data1,const vector<int> & data2)821 AStatsEvent* makeUidStatsEvent(int atomId, int64_t eventTimeNs, int uid, int data1,
822                                const vector<int>& data2) {
823     AStatsEvent* statsEvent = AStatsEvent_obtain();
824     AStatsEvent_setAtomId(statsEvent, atomId);
825     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
826     AStatsEvent_writeInt32(statsEvent, uid);
827     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
828     AStatsEvent_writeInt32(statsEvent, data1);
829     AStatsEvent_writeInt32Array(statsEvent, data2.data(), data2.size());
830 
831     return statsEvent;
832 }
833 
makeUidLogEvent(int atomId,int64_t eventTimeNs,int uid,int data1,int data2)834 shared_ptr<LogEvent> makeUidLogEvent(int atomId, int64_t eventTimeNs, int uid, int data1,
835                                      int data2) {
836     AStatsEvent* statsEvent = makeUidStatsEvent(atomId, eventTimeNs, uid, data1, data2);
837 
838     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
839     parseStatsEventToLogEvent(statsEvent, logEvent.get());
840     return logEvent;
841 }
842 
makeUidLogEvent(int atomId,int64_t eventTimeNs,int uid,int data1,const vector<int> & data2)843 shared_ptr<LogEvent> makeUidLogEvent(int atomId, int64_t eventTimeNs, int uid, int data1,
844                                      const vector<int>& data2) {
845     AStatsEvent* statsEvent = makeUidStatsEvent(atomId, eventTimeNs, uid, data1, data2);
846 
847     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
848     parseStatsEventToLogEvent(statsEvent, logEvent.get());
849     return logEvent;
850 }
851 
makeExtraUidsLogEvent(int atomId,int64_t eventTimeNs,int uid1,int data1,int data2,const vector<int> & extraUids)852 shared_ptr<LogEvent> makeExtraUidsLogEvent(int atomId, int64_t eventTimeNs, int uid1, int data1,
853                                            int data2, const vector<int>& extraUids) {
854     AStatsEvent* statsEvent = makeUidStatsEvent(atomId, eventTimeNs, uid1, data1, data2);
855     for (const int extraUid : extraUids) {
856         AStatsEvent_writeInt32(statsEvent, extraUid);
857         AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
858     }
859 
860     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
861     parseStatsEventToLogEvent(statsEvent, logEvent.get());
862     return logEvent;
863 }
864 
makeRepeatedUidLogEvent(int atomId,int64_t eventTimeNs,const vector<int> & uids)865 shared_ptr<LogEvent> makeRepeatedUidLogEvent(int atomId, int64_t eventTimeNs,
866                                              const vector<int>& uids) {
867     AStatsEvent* statsEvent = AStatsEvent_obtain();
868     AStatsEvent_setAtomId(statsEvent, atomId);
869     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
870     AStatsEvent_writeInt32Array(statsEvent, uids.data(), uids.size());
871     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
872 
873     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
874     parseStatsEventToLogEvent(statsEvent, logEvent.get());
875 
876     return logEvent;
877 }
878 
makeRepeatedUidLogEvent(int atomId,int64_t eventTimeNs,const vector<int> & uids,int data1,int data2)879 shared_ptr<LogEvent> makeRepeatedUidLogEvent(int atomId, int64_t eventTimeNs,
880                                              const vector<int>& uids, int data1, int data2) {
881     AStatsEvent* statsEvent = AStatsEvent_obtain();
882     AStatsEvent_setAtomId(statsEvent, atomId);
883     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
884     AStatsEvent_writeInt32Array(statsEvent, uids.data(), uids.size());
885     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
886     AStatsEvent_writeInt32(statsEvent, data1);
887     AStatsEvent_writeInt32(statsEvent, data2);
888 
889     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
890     parseStatsEventToLogEvent(statsEvent, logEvent.get());
891 
892     return logEvent;
893 }
894 
makeRepeatedUidLogEvent(int atomId,int64_t eventTimeNs,const vector<int> & uids,int data1,const vector<int> & data2)895 shared_ptr<LogEvent> makeRepeatedUidLogEvent(int atomId, int64_t eventTimeNs,
896                                              const vector<int>& uids, int data1,
897                                              const vector<int>& data2) {
898     AStatsEvent* statsEvent = AStatsEvent_obtain();
899     AStatsEvent_setAtomId(statsEvent, atomId);
900     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
901     AStatsEvent_writeInt32Array(statsEvent, uids.data(), uids.size());
902     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
903     AStatsEvent_writeInt32(statsEvent, data1);
904     AStatsEvent_writeInt32Array(statsEvent, data2.data(), data2.size());
905 
906     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
907     parseStatsEventToLogEvent(statsEvent, logEvent.get());
908 
909     return logEvent;
910 }
911 
makeAttributionLogEvent(int atomId,int64_t eventTimeNs,const vector<int> & uids,const vector<string> & tags,int data1,int data2)912 shared_ptr<LogEvent> makeAttributionLogEvent(int atomId, int64_t eventTimeNs,
913                                              const vector<int>& uids, const vector<string>& tags,
914                                              int data1, int data2) {
915     AStatsEvent* statsEvent = AStatsEvent_obtain();
916     AStatsEvent_setAtomId(statsEvent, atomId);
917     AStatsEvent_overwriteTimestamp(statsEvent, eventTimeNs);
918 
919     writeAttribution(statsEvent, uids, tags);
920     AStatsEvent_writeInt32(statsEvent, data1);
921     AStatsEvent_writeInt32(statsEvent, data2);
922 
923     shared_ptr<LogEvent> logEvent = std::make_shared<LogEvent>(/*uid=*/0, /*pid=*/0);
924     parseStatsEventToLogEvent(statsEvent, logEvent.get());
925     return logEvent;
926 }
927 
makeMockUidMapForHosts(const map<int,vector<int>> & hostUidToIsolatedUidsMap)928 sp<MockUidMap> makeMockUidMapForHosts(const map<int, vector<int>>& hostUidToIsolatedUidsMap) {
929     sp<MockUidMap> uidMap = new NaggyMock<MockUidMap>();
930     EXPECT_CALL(*uidMap, getHostUidOrSelf(_)).WillRepeatedly(ReturnArg<0>());
931     for (const auto& [hostUid, isolatedUids] : hostUidToIsolatedUidsMap) {
932         for (const int isolatedUid : isolatedUids) {
933             EXPECT_CALL(*uidMap, getHostUidOrSelf(isolatedUid)).WillRepeatedly(Return(hostUid));
934         }
935     }
936 
937     return uidMap;
938 }
939 
makeMockUidMapForPackage(const string & pkg,const set<int32_t> & uids)940 sp<MockUidMap> makeMockUidMapForPackage(const string& pkg, const set<int32_t>& uids) {
941     sp<MockUidMap> uidMap = new StrictMock<MockUidMap>();
942     EXPECT_CALL(*uidMap, getAppUid(_)).Times(AnyNumber());
943     EXPECT_CALL(*uidMap, getAppUid(pkg)).WillRepeatedly(Return(uids));
944 
945     return uidMap;
946 }
947 
CreateScreenStateChangedEvent(uint64_t timestampNs,const android::view::DisplayStateEnum state,int loggerUid)948 std::unique_ptr<LogEvent> CreateScreenStateChangedEvent(uint64_t timestampNs,
949                                                         const android::view::DisplayStateEnum state,
950                                                         int loggerUid) {
951     AStatsEvent* statsEvent = AStatsEvent_obtain();
952     AStatsEvent_setAtomId(statsEvent, util::SCREEN_STATE_CHANGED);
953     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
954     AStatsEvent_writeInt32(statsEvent, state);
955     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
956     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, false);
957 
958     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(loggerUid, /*pid=*/0);
959     parseStatsEventToLogEvent(statsEvent, logEvent.get());
960     return logEvent;
961 }
962 
CreateBatterySaverOnEvent(uint64_t timestampNs)963 std::unique_ptr<LogEvent> CreateBatterySaverOnEvent(uint64_t timestampNs) {
964     AStatsEvent* statsEvent = AStatsEvent_obtain();
965     AStatsEvent_setAtomId(statsEvent, util::BATTERY_SAVER_MODE_STATE_CHANGED);
966     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
967     AStatsEvent_writeInt32(statsEvent, BatterySaverModeStateChanged::ON);
968     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
969     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, false);
970 
971     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
972     parseStatsEventToLogEvent(statsEvent, logEvent.get());
973     return logEvent;
974 }
975 
CreateBatterySaverOffEvent(uint64_t timestampNs)976 std::unique_ptr<LogEvent> CreateBatterySaverOffEvent(uint64_t timestampNs) {
977     AStatsEvent* statsEvent = AStatsEvent_obtain();
978     AStatsEvent_setAtomId(statsEvent, util::BATTERY_SAVER_MODE_STATE_CHANGED);
979     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
980     AStatsEvent_writeInt32(statsEvent, BatterySaverModeStateChanged::OFF);
981     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
982     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, false);
983 
984     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
985     parseStatsEventToLogEvent(statsEvent, logEvent.get());
986     return logEvent;
987 }
988 
CreateBatteryStateChangedEvent(const uint64_t timestampNs,const BatteryPluggedStateEnum state)989 std::unique_ptr<LogEvent> CreateBatteryStateChangedEvent(const uint64_t timestampNs, const BatteryPluggedStateEnum state) {
990     AStatsEvent* statsEvent = AStatsEvent_obtain();
991     AStatsEvent_setAtomId(statsEvent, util::PLUGGED_STATE_CHANGED);
992     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
993     AStatsEvent_writeInt32(statsEvent, state);
994 
995     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
996     parseStatsEventToLogEvent(statsEvent, logEvent.get());
997     return logEvent;
998 }
999 
CreateScreenBrightnessChangedEvent(uint64_t timestampNs,int level)1000 std::unique_ptr<LogEvent> CreateScreenBrightnessChangedEvent(uint64_t timestampNs, int level) {
1001     AStatsEvent* statsEvent = AStatsEvent_obtain();
1002     AStatsEvent_setAtomId(statsEvent, util::SCREEN_BRIGHTNESS_CHANGED);
1003     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1004     AStatsEvent_writeInt32(statsEvent, level);
1005 
1006     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1007     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1008     return logEvent;
1009 }
1010 
CreateScheduledJobStateChangedEvent(const vector<int> & attributionUids,const vector<string> & attributionTags,const string & jobName,const ScheduledJobStateChanged::State state,uint64_t timestampNs)1011 std::unique_ptr<LogEvent> CreateScheduledJobStateChangedEvent(
1012         const vector<int>& attributionUids, const vector<string>& attributionTags,
1013         const string& jobName, const ScheduledJobStateChanged::State state, uint64_t timestampNs) {
1014     AStatsEvent* statsEvent = AStatsEvent_obtain();
1015     AStatsEvent_setAtomId(statsEvent, util::SCHEDULED_JOB_STATE_CHANGED);
1016     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1017 
1018     writeAttribution(statsEvent, attributionUids, attributionTags);
1019     AStatsEvent_writeString(statsEvent, jobName.c_str());
1020     AStatsEvent_writeInt32(statsEvent, state);
1021 
1022     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1023     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1024     return logEvent;
1025 }
1026 
CreateStartScheduledJobEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & jobName)1027 std::unique_ptr<LogEvent> CreateStartScheduledJobEvent(uint64_t timestampNs,
1028                                                        const vector<int>& attributionUids,
1029                                                        const vector<string>& attributionTags,
1030                                                        const string& jobName) {
1031     return CreateScheduledJobStateChangedEvent(attributionUids, attributionTags, jobName,
1032                                                ScheduledJobStateChanged::STARTED, timestampNs);
1033 }
1034 
1035 // Create log event when scheduled job finishes.
CreateFinishScheduledJobEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & jobName)1036 std::unique_ptr<LogEvent> CreateFinishScheduledJobEvent(uint64_t timestampNs,
1037                                                         const vector<int>& attributionUids,
1038                                                         const vector<string>& attributionTags,
1039                                                         const string& jobName) {
1040     return CreateScheduledJobStateChangedEvent(attributionUids, attributionTags, jobName,
1041                                                ScheduledJobStateChanged::FINISHED, timestampNs);
1042 }
1043 
1044 // Create log event when scheduled job is scheduled.
CreateScheduleScheduledJobEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & jobName)1045 std::unique_ptr<LogEvent> CreateScheduleScheduledJobEvent(uint64_t timestampNs,
1046                                                           const vector<int>& attributionUids,
1047                                                           const vector<string>& attributionTags,
1048                                                           const string& jobName) {
1049     return CreateScheduledJobStateChangedEvent(attributionUids, attributionTags, jobName,
1050                                                ScheduledJobStateChanged::SCHEDULED, timestampNs);
1051 }
1052 
CreateTestAtomReportedEventVariableRepeatedFields(uint64_t timestampNs,const vector<int> & repeatedIntField,const vector<int64_t> & repeatedLongField,const vector<float> & repeatedFloatField,const vector<string> & repeatedStringField,const bool * repeatedBoolField,const size_t repeatedBoolFieldLength,const vector<int> & repeatedEnumField)1053 std::unique_ptr<LogEvent> CreateTestAtomReportedEventVariableRepeatedFields(
1054         uint64_t timestampNs, const vector<int>& repeatedIntField,
1055         const vector<int64_t>& repeatedLongField, const vector<float>& repeatedFloatField,
1056         const vector<string>& repeatedStringField, const bool* repeatedBoolField,
1057         const size_t repeatedBoolFieldLength, const vector<int>& repeatedEnumField) {
1058     return CreateTestAtomReportedEvent(timestampNs, {1001, 1002}, {"app1", "app2"}, 5, 1000l, 21.9f,
1059                                        "string", 1, TestAtomReported::ON, {8, 1, 8, 2, 8, 3},
1060                                        repeatedIntField, repeatedLongField, repeatedFloatField,
1061                                        repeatedStringField, repeatedBoolField,
1062                                        repeatedBoolFieldLength, repeatedEnumField);
1063 }
1064 
CreateTestAtomReportedEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const int intField,const long longField,const float floatField,const string & stringField,const bool boolField,const TestAtomReported::State enumField,const vector<uint8_t> & bytesField,const vector<int> & repeatedIntField,const vector<int64_t> & repeatedLongField,const vector<float> & repeatedFloatField,const vector<string> & repeatedStringField,const bool * repeatedBoolField,const size_t repeatedBoolFieldLength,const vector<int> & repeatedEnumField)1065 std::unique_ptr<LogEvent> CreateTestAtomReportedEvent(
1066         uint64_t timestampNs, const vector<int>& attributionUids,
1067         const vector<string>& attributionTags, const int intField, const long longField,
1068         const float floatField, const string& stringField, const bool boolField,
1069         const TestAtomReported::State enumField, const vector<uint8_t>& bytesField,
1070         const vector<int>& repeatedIntField, const vector<int64_t>& repeatedLongField,
1071         const vector<float>& repeatedFloatField, const vector<string>& repeatedStringField,
1072         const bool* repeatedBoolField, const size_t repeatedBoolFieldLength,
1073         const vector<int>& repeatedEnumField) {
1074     vector<const char*> cRepeatedStringField(repeatedStringField.size());
1075     for (int i = 0; i < cRepeatedStringField.size(); i++) {
1076         cRepeatedStringField[i] = repeatedStringField[i].c_str();
1077     }
1078 
1079     AStatsEvent* statsEvent = AStatsEvent_obtain();
1080     AStatsEvent_setAtomId(statsEvent, util::TEST_ATOM_REPORTED);
1081     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1082 
1083     writeAttribution(statsEvent, attributionUids, attributionTags);
1084     AStatsEvent_writeInt32(statsEvent, intField);
1085     AStatsEvent_writeInt64(statsEvent, longField);
1086     AStatsEvent_writeFloat(statsEvent, floatField);
1087     AStatsEvent_writeString(statsEvent, stringField.c_str());
1088     AStatsEvent_writeBool(statsEvent, boolField);
1089     AStatsEvent_writeInt32(statsEvent, enumField);
1090     AStatsEvent_writeByteArray(statsEvent, bytesField.data(), bytesField.size());
1091     AStatsEvent_writeInt32Array(statsEvent, repeatedIntField.data(), repeatedIntField.size());
1092     AStatsEvent_writeInt64Array(statsEvent, repeatedLongField.data(), repeatedLongField.size());
1093     AStatsEvent_writeFloatArray(statsEvent, repeatedFloatField.data(), repeatedFloatField.size());
1094     AStatsEvent_writeStringArray(statsEvent, cRepeatedStringField.data(),
1095                                  repeatedStringField.size());
1096     AStatsEvent_writeBoolArray(statsEvent, repeatedBoolField, repeatedBoolFieldLength);
1097     AStatsEvent_writeInt32Array(statsEvent, repeatedEnumField.data(), repeatedEnumField.size());
1098 
1099     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1100     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1101     return logEvent;
1102 }
1103 
CreateWakelockStateChangedEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & wakelockName,const WakelockStateChanged::State state)1104 std::unique_ptr<LogEvent> CreateWakelockStateChangedEvent(uint64_t timestampNs,
1105                                                           const vector<int>& attributionUids,
1106                                                           const vector<string>& attributionTags,
1107                                                           const string& wakelockName,
1108                                                           const WakelockStateChanged::State state) {
1109     AStatsEvent* statsEvent = AStatsEvent_obtain();
1110     AStatsEvent_setAtomId(statsEvent, util::WAKELOCK_STATE_CHANGED);
1111     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1112 
1113     writeAttribution(statsEvent, attributionUids, attributionTags);
1114     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD_FIRST_UID,
1115                                   true);
1116     AStatsEvent_writeInt32(statsEvent, android::os::WakeLockLevelEnum::PARTIAL_WAKE_LOCK);
1117     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1118     AStatsEvent_writeString(statsEvent, wakelockName.c_str());
1119     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1120     AStatsEvent_writeInt32(statsEvent, state);
1121     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
1122     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, true);
1123 
1124     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1125     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1126     return logEvent;
1127 }
1128 
CreateAcquireWakelockEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & wakelockName)1129 std::unique_ptr<LogEvent> CreateAcquireWakelockEvent(uint64_t timestampNs,
1130                                                      const vector<int>& attributionUids,
1131                                                      const vector<string>& attributionTags,
1132                                                      const string& wakelockName) {
1133     return CreateWakelockStateChangedEvent(timestampNs, attributionUids, attributionTags,
1134                                            wakelockName, WakelockStateChanged::ACQUIRE);
1135 }
1136 
CreateReleaseWakelockEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & wakelockName)1137 std::unique_ptr<LogEvent> CreateReleaseWakelockEvent(uint64_t timestampNs,
1138                                                      const vector<int>& attributionUids,
1139                                                      const vector<string>& attributionTags,
1140                                                      const string& wakelockName) {
1141     return CreateWakelockStateChangedEvent(timestampNs, attributionUids, attributionTags,
1142                                            wakelockName, WakelockStateChanged::RELEASE);
1143 }
1144 
CreateActivityForegroundStateChangedEvent(uint64_t timestampNs,const int uid,const ActivityForegroundStateChanged::State state)1145 std::unique_ptr<LogEvent> CreateActivityForegroundStateChangedEvent(
1146         uint64_t timestampNs, const int uid, const ActivityForegroundStateChanged::State state) {
1147     AStatsEvent* statsEvent = AStatsEvent_obtain();
1148     AStatsEvent_setAtomId(statsEvent, util::ACTIVITY_FOREGROUND_STATE_CHANGED);
1149     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1150 
1151     AStatsEvent_writeInt32(statsEvent, uid);
1152     AStatsEvent_writeString(statsEvent, "pkg_name");
1153     AStatsEvent_writeString(statsEvent, "class_name");
1154     AStatsEvent_writeInt32(statsEvent, state);
1155 
1156     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1157     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1158     return logEvent;
1159 }
1160 
CreateMoveToBackgroundEvent(uint64_t timestampNs,const int uid)1161 std::unique_ptr<LogEvent> CreateMoveToBackgroundEvent(uint64_t timestampNs, const int uid) {
1162     return CreateActivityForegroundStateChangedEvent(timestampNs, uid,
1163                                                      ActivityForegroundStateChanged::BACKGROUND);
1164 }
1165 
CreateMoveToForegroundEvent(uint64_t timestampNs,const int uid)1166 std::unique_ptr<LogEvent> CreateMoveToForegroundEvent(uint64_t timestampNs, const int uid) {
1167     return CreateActivityForegroundStateChangedEvent(timestampNs, uid,
1168                                                      ActivityForegroundStateChanged::FOREGROUND);
1169 }
1170 
CreateSyncStateChangedEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & name,const SyncStateChanged::State state)1171 std::unique_ptr<LogEvent> CreateSyncStateChangedEvent(uint64_t timestampNs,
1172                                                       const vector<int>& attributionUids,
1173                                                       const vector<string>& attributionTags,
1174                                                       const string& name,
1175                                                       const SyncStateChanged::State state) {
1176     AStatsEvent* statsEvent = AStatsEvent_obtain();
1177     AStatsEvent_setAtomId(statsEvent, util::SYNC_STATE_CHANGED);
1178     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1179 
1180     writeAttribution(statsEvent, attributionUids, attributionTags);
1181     AStatsEvent_writeString(statsEvent, name.c_str());
1182     AStatsEvent_writeInt32(statsEvent, state);
1183 
1184     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1185     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1186     return logEvent;
1187 }
1188 
CreateSyncStartEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & name)1189 std::unique_ptr<LogEvent> CreateSyncStartEvent(uint64_t timestampNs,
1190                                                const vector<int>& attributionUids,
1191                                                const vector<string>& attributionTags,
1192                                                const string& name) {
1193     return CreateSyncStateChangedEvent(timestampNs, attributionUids, attributionTags, name,
1194                                        SyncStateChanged::ON);
1195 }
1196 
CreateSyncEndEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const string & name)1197 std::unique_ptr<LogEvent> CreateSyncEndEvent(uint64_t timestampNs,
1198                                              const vector<int>& attributionUids,
1199                                              const vector<string>& attributionTags,
1200                                              const string& name) {
1201     return CreateSyncStateChangedEvent(timestampNs, attributionUids, attributionTags, name,
1202                                        SyncStateChanged::OFF);
1203 }
1204 
CreateProcessLifeCycleStateChangedEvent(uint64_t timestampNs,const int uid,const ProcessLifeCycleStateChanged::State state)1205 std::unique_ptr<LogEvent> CreateProcessLifeCycleStateChangedEvent(
1206         uint64_t timestampNs, const int uid, const ProcessLifeCycleStateChanged::State state) {
1207     AStatsEvent* statsEvent = AStatsEvent_obtain();
1208     AStatsEvent_setAtomId(statsEvent, util::PROCESS_LIFE_CYCLE_STATE_CHANGED);
1209     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1210 
1211     AStatsEvent_writeInt32(statsEvent, uid);
1212     AStatsEvent_writeString(statsEvent, "");
1213     AStatsEvent_writeInt32(statsEvent, state);
1214 
1215     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1216     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1217     return logEvent;
1218 }
1219 
CreateAppCrashEvent(uint64_t timestampNs,const int uid)1220 std::unique_ptr<LogEvent> CreateAppCrashEvent(uint64_t timestampNs, const int uid) {
1221     return CreateProcessLifeCycleStateChangedEvent(timestampNs, uid,
1222                                                    ProcessLifeCycleStateChanged::CRASHED);
1223 }
1224 
CreateAppCrashOccurredEvent(uint64_t timestampNs,const int uid)1225 std::unique_ptr<LogEvent> CreateAppCrashOccurredEvent(uint64_t timestampNs, const int uid) {
1226     AStatsEvent* statsEvent = AStatsEvent_obtain();
1227     AStatsEvent_setAtomId(statsEvent, util::APP_CRASH_OCCURRED);
1228     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1229 
1230     AStatsEvent_writeInt32(statsEvent, uid);
1231     AStatsEvent_writeString(statsEvent, "eventType");
1232     AStatsEvent_writeString(statsEvent, "processName");
1233 
1234     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1235     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1236     return logEvent;
1237 }
1238 
CreateIsolatedUidChangedEvent(uint64_t timestampNs,int hostUid,int isolatedUid,bool is_create)1239 std::unique_ptr<LogEvent> CreateIsolatedUidChangedEvent(uint64_t timestampNs, int hostUid,
1240                                                         int isolatedUid, bool is_create) {
1241     AStatsEvent* statsEvent = AStatsEvent_obtain();
1242     AStatsEvent_setAtomId(statsEvent, util::ISOLATED_UID_CHANGED);
1243     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1244 
1245     AStatsEvent_writeInt32(statsEvent, hostUid);
1246     AStatsEvent_writeInt32(statsEvent, isolatedUid);
1247     AStatsEvent_writeInt32(statsEvent, is_create);
1248 
1249     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1250     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1251     return logEvent;
1252 }
1253 
CreateUidProcessStateChangedEvent(uint64_t timestampNs,int uid,const android::app::ProcessStateEnum state)1254 std::unique_ptr<LogEvent> CreateUidProcessStateChangedEvent(
1255         uint64_t timestampNs, int uid, const android::app::ProcessStateEnum state) {
1256     AStatsEvent* statsEvent = AStatsEvent_obtain();
1257     AStatsEvent_setAtomId(statsEvent, util::UID_PROCESS_STATE_CHANGED);
1258     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1259 
1260     AStatsEvent_writeInt32(statsEvent, uid);
1261     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
1262     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1263     AStatsEvent_writeInt32(statsEvent, state);
1264     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
1265     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, false);
1266 
1267     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1268     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1269     return logEvent;
1270 }
1271 
CreateBleScanStateChangedEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const BleScanStateChanged::State state,const bool filtered,const bool firstMatch,const bool opportunistic)1272 std::unique_ptr<LogEvent> CreateBleScanStateChangedEvent(uint64_t timestampNs,
1273                                                          const vector<int>& attributionUids,
1274                                                          const vector<string>& attributionTags,
1275                                                          const BleScanStateChanged::State state,
1276                                                          const bool filtered, const bool firstMatch,
1277                                                          const bool opportunistic) {
1278     AStatsEvent* statsEvent = AStatsEvent_obtain();
1279     AStatsEvent_setAtomId(statsEvent, util::BLE_SCAN_STATE_CHANGED);
1280     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1281 
1282     writeAttribution(statsEvent, attributionUids, attributionTags);
1283     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD_FIRST_UID,
1284                                   true);
1285     AStatsEvent_writeInt32(statsEvent, state);
1286     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
1287     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, true);
1288     if (state == util::BLE_SCAN_STATE_CHANGED__STATE__RESET) {
1289         AStatsEvent_addInt32Annotation(statsEvent, ASTATSLOG_ANNOTATION_ID_TRIGGER_STATE_RESET,
1290                                        util::BLE_SCAN_STATE_CHANGED__STATE__OFF);
1291     }
1292     AStatsEvent_writeBool(statsEvent, filtered);  // filtered
1293     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1294     AStatsEvent_writeBool(statsEvent, firstMatch);  // first match
1295     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1296     AStatsEvent_writeBool(statsEvent, opportunistic);  // opportunistic
1297     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1298 
1299     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1300     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1301     return logEvent;
1302 }
1303 
CreateOverlayStateChangedEvent(int64_t timestampNs,const int32_t uid,const string & packageName,const bool usingAlertWindow,const OverlayStateChanged::State state)1304 std::unique_ptr<LogEvent> CreateOverlayStateChangedEvent(int64_t timestampNs, const int32_t uid,
1305                                                          const string& packageName,
1306                                                          const bool usingAlertWindow,
1307                                                          const OverlayStateChanged::State state) {
1308     AStatsEvent* statsEvent = AStatsEvent_obtain();
1309     AStatsEvent_setAtomId(statsEvent, util::OVERLAY_STATE_CHANGED);
1310     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1311 
1312     AStatsEvent_writeInt32(statsEvent, uid);
1313     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_IS_UID, true);
1314     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1315     AStatsEvent_writeString(statsEvent, packageName.c_str());
1316     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_PRIMARY_FIELD, true);
1317     AStatsEvent_writeBool(statsEvent, usingAlertWindow);
1318     AStatsEvent_writeInt32(statsEvent, state);
1319     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_EXCLUSIVE_STATE, true);
1320     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_STATE_NESTED, false);
1321 
1322     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1323     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1324     return logEvent;
1325 }
1326 
CreateAppStartOccurredEvent(uint64_t timestampNs,const int uid,const string & pkgName,AppStartOccurred::TransitionType type,const string & activityName,const string & callingPkgName,const bool isInstantApp,int64_t activityStartMs)1327 std::unique_ptr<LogEvent> CreateAppStartOccurredEvent(
1328         uint64_t timestampNs, const int uid, const string& pkgName,
1329         AppStartOccurred::TransitionType type, const string& activityName,
1330         const string& callingPkgName, const bool isInstantApp, int64_t activityStartMs) {
1331     AStatsEvent* statsEvent = AStatsEvent_obtain();
1332     AStatsEvent_setAtomId(statsEvent, util::APP_START_OCCURRED);
1333     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1334 
1335     AStatsEvent_writeInt32(statsEvent, uid);
1336     AStatsEvent_writeString(statsEvent, pkgName.c_str());
1337     AStatsEvent_writeInt32(statsEvent, type);
1338     AStatsEvent_writeString(statsEvent, activityName.c_str());
1339     AStatsEvent_writeString(statsEvent, callingPkgName.c_str());
1340     AStatsEvent_writeInt32(statsEvent, isInstantApp);
1341     AStatsEvent_writeInt32(statsEvent, activityStartMs);
1342 
1343     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1344     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1345     return logEvent;
1346 }
1347 
CreateBleScanResultReceivedEvent(uint64_t timestampNs,const vector<int> & attributionUids,const vector<string> & attributionTags,const int numResults)1348 std::unique_ptr<LogEvent> CreateBleScanResultReceivedEvent(uint64_t timestampNs,
1349                                                            const vector<int>& attributionUids,
1350                                                            const vector<string>& attributionTags,
1351                                                            const int numResults) {
1352     AStatsEvent* statsEvent = AStatsEvent_obtain();
1353     AStatsEvent_setAtomId(statsEvent, util::BLE_SCAN_RESULT_RECEIVED);
1354     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1355 
1356     writeAttribution(statsEvent, attributionUids, attributionTags);
1357     AStatsEvent_writeInt32(statsEvent, numResults);
1358 
1359     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1360     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1361     return logEvent;
1362 }
1363 
CreateRestrictedLogEvent(int atomTag,int64_t timestampNs)1364 std::unique_ptr<LogEvent> CreateRestrictedLogEvent(int atomTag, int64_t timestampNs) {
1365     AStatsEvent* statsEvent = AStatsEvent_obtain();
1366     AStatsEvent_setAtomId(statsEvent, atomTag);
1367     AStatsEvent_addInt32Annotation(statsEvent, ASTATSLOG_ANNOTATION_ID_RESTRICTION_CATEGORY,
1368                                    ASTATSLOG_RESTRICTION_CATEGORY_DIAGNOSTIC);
1369     AStatsEvent_writeInt32(statsEvent, 10);
1370     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1371     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1372     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1373     return logEvent;
1374 }
1375 
CreateNonRestrictedLogEvent(int atomTag,int64_t timestampNs)1376 std::unique_ptr<LogEvent> CreateNonRestrictedLogEvent(int atomTag, int64_t timestampNs) {
1377     AStatsEvent* statsEvent = AStatsEvent_obtain();
1378     AStatsEvent_setAtomId(statsEvent, atomTag);
1379     AStatsEvent_writeInt32(statsEvent, 10);
1380     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1381     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1382     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1383     return logEvent;
1384 }
1385 
CreatePhoneSignalStrengthChangedEvent(int64_t timestampNs,::telephony::SignalStrengthEnum state)1386 std::unique_ptr<LogEvent> CreatePhoneSignalStrengthChangedEvent(
1387         int64_t timestampNs, ::telephony::SignalStrengthEnum state) {
1388     AStatsEvent* statsEvent = AStatsEvent_obtain();
1389     AStatsEvent_setAtomId(statsEvent, util::PHONE_SIGNAL_STRENGTH_CHANGED);
1390     AStatsEvent_addBoolAnnotation(statsEvent, ASTATSLOG_ANNOTATION_ID_TRUNCATE_TIMESTAMP, true);
1391     AStatsEvent_overwriteTimestamp(statsEvent, timestampNs);
1392     AStatsEvent_writeInt32(statsEvent, state);
1393 
1394     std::unique_ptr<LogEvent> logEvent = std::make_unique<LogEvent>(/*uid=*/0, /*pid=*/0);
1395     parseStatsEventToLogEvent(statsEvent, logEvent.get());
1396     return logEvent;
1397 }
1398 
CreateStatsLogProcessor(const int64_t timeBaseNs,const int64_t currentTimeNs,const StatsdConfig & config,const ConfigKey & key,const shared_ptr<IPullAtomCallback> & puller,const int32_t atomTag,const sp<UidMap> uidMap,const shared_ptr<LogEventFilter> & logEventFilter)1399 sp<StatsLogProcessor> CreateStatsLogProcessor(const int64_t timeBaseNs, const int64_t currentTimeNs,
1400                                               const StatsdConfig& config, const ConfigKey& key,
1401                                               const shared_ptr<IPullAtomCallback>& puller,
1402                                               const int32_t atomTag, const sp<UidMap> uidMap,
1403                                               const shared_ptr<LogEventFilter>& logEventFilter) {
1404     sp<StatsPullerManager> pullerManager = new StatsPullerManager();
1405     if (puller != nullptr) {
1406         pullerManager->RegisterPullAtomCallback(/*uid=*/0, atomTag, NS_PER_SEC, NS_PER_SEC * 10, {},
1407                                                 puller);
1408     }
1409     sp<AlarmMonitor> anomalyAlarmMonitor =
1410         new AlarmMonitor(1,
1411                          [](const shared_ptr<IStatsCompanionService>&, int64_t){},
1412                          [](const shared_ptr<IStatsCompanionService>&){});
1413     sp<AlarmMonitor> periodicAlarmMonitor =
1414         new AlarmMonitor(1,
1415                          [](const shared_ptr<IStatsCompanionService>&, int64_t){},
1416                          [](const shared_ptr<IStatsCompanionService>&){});
1417     sp<StatsLogProcessor> processor = new StatsLogProcessor(
1418             uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor, timeBaseNs,
1419             [](const ConfigKey&) { return true; },
1420             [](const int&, const vector<int64_t>&) { return true; },
1421             [](const ConfigKey&, const string&, const vector<int64_t>&) {}, logEventFilter);
1422 
1423     processor->OnConfigUpdated(currentTimeNs, key, config);
1424     return processor;
1425 }
1426 
CreateAtomIdSetDefault()1427 LogEventFilter::AtomIdSet CreateAtomIdSetDefault() {
1428     LogEventFilter::AtomIdSet resultList(std::move(StatsLogProcessor::getDefaultAtomIdSet()));
1429     StateManager::getInstance().addAllAtomIds(resultList);
1430     return resultList;
1431 }
1432 
CreateAtomIdSetFromConfig(const StatsdConfig & config)1433 LogEventFilter::AtomIdSet CreateAtomIdSetFromConfig(const StatsdConfig& config) {
1434     LogEventFilter::AtomIdSet resultList(std::move(StatsLogProcessor::getDefaultAtomIdSet()));
1435 
1436     // Parse the config for atom ids. A combination atom matcher is a combination of (in the end)
1437     // simple atom matchers. So by adding all the atoms from the simple atom matchers
1438     // function adds all of the atoms.
1439     for (int i = 0; i < config.atom_matcher_size(); i++) {
1440         const AtomMatcher& matcher = config.atom_matcher(i);
1441         if (matcher.has_simple_atom_matcher()) {
1442             EXPECT_TRUE(matcher.simple_atom_matcher().has_atom_id());
1443             resultList.insert(matcher.simple_atom_matcher().atom_id());
1444         }
1445     }
1446 
1447     for (int i = 0; i < config.state_size(); i++) {
1448         const State& state = config.state(i);
1449         EXPECT_TRUE(state.has_atom_id());
1450         resultList.insert(state.atom_id());
1451     }
1452 
1453     return resultList;
1454 }
1455 
sortLogEventsByTimestamp(std::vector<std::unique_ptr<LogEvent>> * events)1456 void sortLogEventsByTimestamp(std::vector<std::unique_ptr<LogEvent>> *events) {
1457   std::sort(events->begin(), events->end(),
1458             [](const std::unique_ptr<LogEvent>& a, const std::unique_ptr<LogEvent>& b) {
1459               return a->GetElapsedTimestampNs() < b->GetElapsedTimestampNs();
1460             });
1461 }
1462 
StringToId(const string & str)1463 int64_t StringToId(const string& str) {
1464     return static_cast<int64_t>(std::hash<std::string>()(str));
1465 }
1466 
createEventMatcherWizard(int tagId,int matcherIndex,const vector<FieldValueMatcher> & fieldValueMatchers)1467 sp<EventMatcherWizard> createEventMatcherWizard(
1468         int tagId, int matcherIndex, const vector<FieldValueMatcher>& fieldValueMatchers) {
1469     sp<UidMap> uidMap = new UidMap();
1470     SimpleAtomMatcher atomMatcher;
1471     atomMatcher.set_atom_id(tagId);
1472     for (const FieldValueMatcher& fvm : fieldValueMatchers) {
1473         *atomMatcher.add_field_value_matcher() = fvm;
1474     }
1475     uint64_t matcherHash = 0x12345678;
1476     int64_t matcherId = 678;
1477     return new EventMatcherWizard({new SimpleAtomMatchingTracker(
1478             matcherId, matcherIndex, matcherHash, atomMatcher, uidMap)});
1479 }
1480 
CreateAttributionUidDimensionsValueParcel(const int atomId,const int uid)1481 StatsDimensionsValueParcel CreateAttributionUidDimensionsValueParcel(const int atomId,
1482                                                                      const int uid) {
1483     StatsDimensionsValueParcel root;
1484     root.field = atomId;
1485     root.valueType = STATS_DIMENSIONS_VALUE_TUPLE_TYPE;
1486     StatsDimensionsValueParcel attrNode;
1487     attrNode.field = 1;
1488     attrNode.valueType = STATS_DIMENSIONS_VALUE_TUPLE_TYPE;
1489     StatsDimensionsValueParcel posInAttrChain;
1490     posInAttrChain.field = 1;
1491     posInAttrChain.valueType = STATS_DIMENSIONS_VALUE_TUPLE_TYPE;
1492     StatsDimensionsValueParcel uidNode;
1493     uidNode.field = 1;
1494     uidNode.valueType = STATS_DIMENSIONS_VALUE_INT_TYPE;
1495     uidNode.intValue = uid;
1496     posInAttrChain.tupleValue.push_back(uidNode);
1497     attrNode.tupleValue.push_back(posInAttrChain);
1498     root.tupleValue.push_back(attrNode);
1499     return root;
1500 }
1501 
ValidateUidDimension(const DimensionsValue & value,int atomId,int uid)1502 void ValidateUidDimension(const DimensionsValue& value, int atomId, int uid) {
1503     EXPECT_EQ(value.field(), atomId);
1504     ASSERT_EQ(value.value_tuple().dimensions_value_size(), 1);
1505     EXPECT_EQ(value.value_tuple().dimensions_value(0).field(), 1);
1506     EXPECT_EQ(value.value_tuple().dimensions_value(0).value_int(), uid);
1507 }
1508 
ValidateWakelockAttributionUidAndTagDimension(const DimensionsValue & value,const int atomId,const int uid,const string & tag)1509 void ValidateWakelockAttributionUidAndTagDimension(const DimensionsValue& value, const int atomId,
1510                                                    const int uid, const string& tag) {
1511     EXPECT_EQ(value.field(), atomId);
1512     ASSERT_EQ(value.value_tuple().dimensions_value_size(), 2);
1513     // Attribution field.
1514     EXPECT_EQ(value.value_tuple().dimensions_value(0).field(), 1);
1515     // Uid field.
1516     ASSERT_EQ(value.value_tuple().dimensions_value(0).value_tuple().dimensions_value_size(), 1);
1517     EXPECT_EQ(value.value_tuple().dimensions_value(0).value_tuple().dimensions_value(0).field(), 1);
1518     EXPECT_EQ(value.value_tuple().dimensions_value(0).value_tuple().dimensions_value(0).value_int(),
1519               uid);
1520     // Tag field.
1521     EXPECT_EQ(value.value_tuple().dimensions_value(1).field(), 3);
1522     EXPECT_EQ(value.value_tuple().dimensions_value(1).value_str(), tag);
1523 }
1524 
ValidateAttributionUidDimension(const DimensionsValue & value,int atomId,int uid)1525 void ValidateAttributionUidDimension(const DimensionsValue& value, int atomId, int uid) {
1526     EXPECT_EQ(value.field(), atomId);
1527     ASSERT_EQ(value.value_tuple().dimensions_value_size(), 1);
1528     // Attribution field.
1529     EXPECT_EQ(value.value_tuple().dimensions_value(0).field(), 1);
1530     // Uid only.
1531     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1532         .value_tuple().dimensions_value_size(), 1);
1533     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1534         .value_tuple().dimensions_value(0).field(), 1);
1535     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1536         .value_tuple().dimensions_value(0).value_int(), uid);
1537 }
1538 
ValidateUidDimension(const DimensionsValue & value,int node_idx,int atomId,int uid)1539 void ValidateUidDimension(const DimensionsValue& value, int node_idx, int atomId, int uid) {
1540     EXPECT_EQ(value.field(), atomId);
1541     ASSERT_GT(value.value_tuple().dimensions_value_size(), node_idx);
1542     // Attribution field.
1543     EXPECT_EQ(value.value_tuple().dimensions_value(node_idx).field(), 1);
1544     EXPECT_EQ(value.value_tuple().dimensions_value(node_idx)
1545         .value_tuple().dimensions_value(0).field(), 1);
1546     EXPECT_EQ(value.value_tuple().dimensions_value(node_idx)
1547         .value_tuple().dimensions_value(0).value_int(), uid);
1548 }
1549 
ValidateAttributionUidAndTagDimension(const DimensionsValue & value,int node_idx,int atomId,int uid,const std::string & tag)1550 void ValidateAttributionUidAndTagDimension(
1551     const DimensionsValue& value, int node_idx, int atomId, int uid, const std::string& tag) {
1552     EXPECT_EQ(value.field(), atomId);
1553     ASSERT_GT(value.value_tuple().dimensions_value_size(), node_idx);
1554     // Attribution field.
1555     EXPECT_EQ(1, value.value_tuple().dimensions_value(node_idx).field());
1556     // Uid only.
1557     EXPECT_EQ(2, value.value_tuple().dimensions_value(node_idx)
1558         .value_tuple().dimensions_value_size());
1559     EXPECT_EQ(1, value.value_tuple().dimensions_value(node_idx)
1560         .value_tuple().dimensions_value(0).field());
1561     EXPECT_EQ(uid, value.value_tuple().dimensions_value(node_idx)
1562         .value_tuple().dimensions_value(0).value_int());
1563     EXPECT_EQ(2, value.value_tuple().dimensions_value(node_idx)
1564         .value_tuple().dimensions_value(1).field());
1565     EXPECT_EQ(tag, value.value_tuple().dimensions_value(node_idx)
1566         .value_tuple().dimensions_value(1).value_str());
1567 }
1568 
ValidateAttributionUidAndTagDimension(const DimensionsValue & value,int atomId,int uid,const std::string & tag)1569 void ValidateAttributionUidAndTagDimension(
1570     const DimensionsValue& value, int atomId, int uid, const std::string& tag) {
1571     EXPECT_EQ(value.field(), atomId);
1572     ASSERT_EQ(1, value.value_tuple().dimensions_value_size());
1573     // Attribution field.
1574     EXPECT_EQ(1, value.value_tuple().dimensions_value(0).field());
1575     // Uid only.
1576     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1577         .value_tuple().dimensions_value_size(), 2);
1578     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1579         .value_tuple().dimensions_value(0).field(), 1);
1580     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1581         .value_tuple().dimensions_value(0).value_int(), uid);
1582     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1583         .value_tuple().dimensions_value(1).field(), 2);
1584     EXPECT_EQ(value.value_tuple().dimensions_value(0)
1585         .value_tuple().dimensions_value(1).value_str(), tag);
1586 }
1587 
ValidateStateValue(const google::protobuf::RepeatedPtrField<StateValue> & stateValues,int atomId,int64_t value)1588 void ValidateStateValue(const google::protobuf::RepeatedPtrField<StateValue>& stateValues,
1589                         int atomId, int64_t value) {
1590     ASSERT_EQ(stateValues.size(), 1);
1591     ASSERT_EQ(stateValues[0].atom_id(), atomId);
1592     switch (stateValues[0].contents_case()) {
1593         case StateValue::ContentsCase::kValue:
1594             EXPECT_EQ(stateValues[0].value(), (int32_t)value);
1595             break;
1596         case StateValue::ContentsCase::kGroupId:
1597             EXPECT_EQ(stateValues[0].group_id(), value);
1598             break;
1599         default:
1600             FAIL() << "State value should have either a value or a group id";
1601     }
1602 }
1603 
ValidateCountBucket(const CountBucketInfo & countBucket,int64_t startTimeNs,int64_t endTimeNs,int64_t count,int64_t conditionTrueNs)1604 void ValidateCountBucket(const CountBucketInfo& countBucket, int64_t startTimeNs, int64_t endTimeNs,
1605                          int64_t count, int64_t conditionTrueNs) {
1606     EXPECT_EQ(countBucket.start_bucket_elapsed_nanos(), startTimeNs);
1607     EXPECT_EQ(countBucket.end_bucket_elapsed_nanos(), endTimeNs);
1608     EXPECT_EQ(countBucket.count(), count);
1609     EXPECT_EQ(countBucket.condition_true_nanos(), conditionTrueNs);
1610 }
1611 
ValidateDurationBucket(const DurationBucketInfo & bucket,int64_t startTimeNs,int64_t endTimeNs,int64_t durationNs,int64_t conditionTrueNs)1612 void ValidateDurationBucket(const DurationBucketInfo& bucket, int64_t startTimeNs,
1613                             int64_t endTimeNs, int64_t durationNs, int64_t conditionTrueNs) {
1614     EXPECT_EQ(bucket.start_bucket_elapsed_nanos(), startTimeNs);
1615     EXPECT_EQ(bucket.end_bucket_elapsed_nanos(), endTimeNs);
1616     EXPECT_EQ(bucket.duration_nanos(), durationNs);
1617     EXPECT_EQ(bucket.condition_true_nanos(), conditionTrueNs);
1618 }
1619 
ValidateGaugeBucketTimes(const GaugeBucketInfo & gaugeBucket,int64_t startTimeNs,int64_t endTimeNs,vector<int64_t> eventTimesNs)1620 void ValidateGaugeBucketTimes(const GaugeBucketInfo& gaugeBucket, int64_t startTimeNs,
1621                               int64_t endTimeNs, vector<int64_t> eventTimesNs) {
1622     EXPECT_EQ(gaugeBucket.start_bucket_elapsed_nanos(), startTimeNs);
1623     EXPECT_EQ(gaugeBucket.end_bucket_elapsed_nanos(), endTimeNs);
1624     EXPECT_EQ(gaugeBucket.elapsed_timestamp_nanos_size(), eventTimesNs.size());
1625     for (int i = 0; i < eventTimesNs.size(); i++) {
1626         EXPECT_EQ(gaugeBucket.elapsed_timestamp_nanos(i), eventTimesNs[i]);
1627     }
1628 }
1629 
ValidateValueBucket(const ValueBucketInfo & bucket,int64_t startTimeNs,int64_t endTimeNs,const vector<int64_t> & values,int64_t conditionTrueNs,int64_t conditionCorrectionNs)1630 void ValidateValueBucket(const ValueBucketInfo& bucket, int64_t startTimeNs, int64_t endTimeNs,
1631                          const vector<int64_t>& values, int64_t conditionTrueNs,
1632                          int64_t conditionCorrectionNs) {
1633     EXPECT_EQ(bucket.start_bucket_elapsed_nanos(), startTimeNs);
1634     EXPECT_EQ(bucket.end_bucket_elapsed_nanos(), endTimeNs);
1635     ASSERT_EQ(bucket.values_size(), values.size());
1636     for (int i = 0; i < values.size(); ++i) {
1637         if (bucket.values(i).has_value_double()) {
1638             EXPECT_EQ((int64_t)bucket.values(i).value_double(), values[i]);
1639         } else {
1640             EXPECT_EQ(bucket.values(i).value_long(), values[i]);
1641         }
1642     }
1643     if (conditionTrueNs > 0) {
1644         EXPECT_EQ(bucket.condition_true_nanos(), conditionTrueNs);
1645         if (conditionCorrectionNs > 0) {
1646             EXPECT_EQ(bucket.condition_correction_nanos(), conditionCorrectionNs);
1647         }
1648     }
1649 }
1650 
ValidateKllBucket(const KllBucketInfo & bucket,int64_t startTimeNs,int64_t endTimeNs,const vector<int64_t> sketchSizes,int64_t conditionTrueNs)1651 void ValidateKllBucket(const KllBucketInfo& bucket, int64_t startTimeNs, int64_t endTimeNs,
1652                        const vector<int64_t> sketchSizes, int64_t conditionTrueNs) {
1653     EXPECT_EQ(bucket.start_bucket_elapsed_nanos(), startTimeNs);
1654     EXPECT_EQ(bucket.end_bucket_elapsed_nanos(), endTimeNs);
1655     ASSERT_EQ(bucket.sketches_size(), sketchSizes.size());
1656     for (int i = 0; i < sketchSizes.size(); ++i) {
1657         AggregatorStateProto aggProto;
1658         EXPECT_TRUE(aggProto.ParseFromString(bucket.sketches(i).kll_sketch()));
1659         EXPECT_EQ(aggProto.num_values(), sketchSizes[i]);
1660     }
1661     if (conditionTrueNs > 0) {
1662         EXPECT_EQ(bucket.condition_true_nanos(), conditionTrueNs);
1663     }
1664 }
1665 
EqualsTo(const DimensionsValue & s1,const DimensionsValue & s2)1666 bool EqualsTo(const DimensionsValue& s1, const DimensionsValue& s2) {
1667     if (s1.field() != s2.field()) {
1668         return false;
1669     }
1670     if (s1.value_case() != s2.value_case()) {
1671         return false;
1672     }
1673     switch (s1.value_case()) {
1674         case DimensionsValue::ValueCase::kValueStr:
1675             return (s1.value_str() == s2.value_str());
1676         case DimensionsValue::ValueCase::kValueInt:
1677             return s1.value_int() == s2.value_int();
1678         case DimensionsValue::ValueCase::kValueLong:
1679             return s1.value_long() == s2.value_long();
1680         case DimensionsValue::ValueCase::kValueBool:
1681             return s1.value_bool() == s2.value_bool();
1682         case DimensionsValue::ValueCase::kValueFloat:
1683             return s1.value_float() == s2.value_float();
1684         case DimensionsValue::ValueCase::kValueTuple: {
1685             if (s1.value_tuple().dimensions_value_size() !=
1686                 s2.value_tuple().dimensions_value_size()) {
1687                 return false;
1688             }
1689             bool allMatched = true;
1690             for (int i = 0; allMatched && i < s1.value_tuple().dimensions_value_size(); ++i) {
1691                 allMatched &= EqualsTo(s1.value_tuple().dimensions_value(i),
1692                                        s2.value_tuple().dimensions_value(i));
1693             }
1694             return allMatched;
1695         }
1696         case DimensionsValue::ValueCase::VALUE_NOT_SET:
1697         default:
1698             return true;
1699     }
1700 }
1701 
LessThan(const google::protobuf::RepeatedPtrField<StateValue> & s1,const google::protobuf::RepeatedPtrField<StateValue> & s2)1702 bool LessThan(const google::protobuf::RepeatedPtrField<StateValue>& s1,
1703               const google::protobuf::RepeatedPtrField<StateValue>& s2) {
1704     if (s1.size() != s2.size()) {
1705         return s1.size() < s2.size();
1706     }
1707     for (int i = 0; i < s1.size(); i++) {
1708         const StateValue& state1 = s1[i];
1709         const StateValue& state2 = s2[i];
1710         if (state1.atom_id() != state2.atom_id()) {
1711             return state1.atom_id() < state2.atom_id();
1712         }
1713         if (state1.value() != state2.value()) {
1714             return state1.value() < state2.value();
1715         }
1716         if (state1.group_id() != state2.group_id()) {
1717             return state1.group_id() < state2.group_id();
1718         }
1719     }
1720     return false;
1721 }
1722 
LessThan(const DimensionsValue & s1,const DimensionsValue & s2)1723 bool LessThan(const DimensionsValue& s1, const DimensionsValue& s2) {
1724     if (s1.field() != s2.field()) {
1725         return s1.field() < s2.field();
1726     }
1727     if (s1.value_case() != s2.value_case()) {
1728         return s1.value_case() < s2.value_case();
1729     }
1730     switch (s1.value_case()) {
1731         case DimensionsValue::ValueCase::kValueStr:
1732             return s1.value_str() < s2.value_str();
1733         case DimensionsValue::ValueCase::kValueInt:
1734             return s1.value_int() < s2.value_int();
1735         case DimensionsValue::ValueCase::kValueLong:
1736             return s1.value_long() < s2.value_long();
1737         case DimensionsValue::ValueCase::kValueBool:
1738             return (int)s1.value_bool() < (int)s2.value_bool();
1739         case DimensionsValue::ValueCase::kValueFloat:
1740             return s1.value_float() < s2.value_float();
1741         case DimensionsValue::ValueCase::kValueTuple: {
1742             if (s1.value_tuple().dimensions_value_size() !=
1743                 s2.value_tuple().dimensions_value_size()) {
1744                 return s1.value_tuple().dimensions_value_size() <
1745                        s2.value_tuple().dimensions_value_size();
1746             }
1747             for (int i = 0; i < s1.value_tuple().dimensions_value_size(); ++i) {
1748                 if (EqualsTo(s1.value_tuple().dimensions_value(i),
1749                              s2.value_tuple().dimensions_value(i))) {
1750                     continue;
1751                 } else {
1752                     return LessThan(s1.value_tuple().dimensions_value(i),
1753                                     s2.value_tuple().dimensions_value(i));
1754                 }
1755             }
1756             return false;
1757         }
1758         case DimensionsValue::ValueCase::VALUE_NOT_SET:
1759         default:
1760             return false;
1761     }
1762 }
1763 
LessThan(const DimensionsPair & s1,const DimensionsPair & s2)1764 bool LessThan(const DimensionsPair& s1, const DimensionsPair& s2) {
1765     if (LessThan(s1.dimInWhat, s2.dimInWhat)) {
1766         return true;
1767     } else if (LessThan(s2.dimInWhat, s1.dimInWhat)) {
1768         return false;
1769     }
1770 
1771     return LessThan(s1.stateValues, s2.stateValues);
1772 }
1773 
backfillStringInDimension(const std::map<uint64_t,string> & str_map,DimensionsValue * dimension)1774 void backfillStringInDimension(const std::map<uint64_t, string>& str_map,
1775                                DimensionsValue* dimension) {
1776     if (dimension->has_value_str_hash()) {
1777         auto it = str_map.find((uint64_t)(dimension->value_str_hash()));
1778         if (it != str_map.end()) {
1779             dimension->clear_value_str_hash();
1780             dimension->set_value_str(it->second);
1781         } else {
1782             ALOGE("Can not find the string hash: %llu",
1783                 (unsigned long long)dimension->value_str_hash());
1784         }
1785     } else if (dimension->has_value_tuple()) {
1786         auto value_tuple = dimension->mutable_value_tuple();
1787         for (int i = 0; i < value_tuple->dimensions_value_size(); ++i) {
1788             backfillStringInDimension(str_map, value_tuple->mutable_dimensions_value(i));
1789         }
1790     }
1791 }
1792 
backfillStringInReport(ConfigMetricsReport * config_report)1793 void backfillStringInReport(ConfigMetricsReport *config_report) {
1794     std::map<uint64_t, string> str_map;
1795     for (const auto& str : config_report->strings()) {
1796         uint64_t hash = Hash64(str);
1797         if (str_map.find(hash) != str_map.end()) {
1798             ALOGE("String hash conflicts: %s %s", str.c_str(), str_map[hash].c_str());
1799         }
1800         str_map[hash] = str;
1801     }
1802     for (int i = 0; i < config_report->metrics_size(); ++i) {
1803         auto metric_report = config_report->mutable_metrics(i);
1804         if (metric_report->has_count_metrics()) {
1805             backfillStringInDimension(str_map, metric_report->mutable_count_metrics());
1806         } else if (metric_report->has_duration_metrics()) {
1807             backfillStringInDimension(str_map, metric_report->mutable_duration_metrics());
1808         } else if (metric_report->has_gauge_metrics()) {
1809             backfillStringInDimension(str_map, metric_report->mutable_gauge_metrics());
1810         } else if (metric_report->has_value_metrics()) {
1811             backfillStringInDimension(str_map, metric_report->mutable_value_metrics());
1812         } else if (metric_report->has_kll_metrics()) {
1813             backfillStringInDimension(str_map, metric_report->mutable_kll_metrics());
1814         }
1815     }
1816     // Backfill the package names.
1817     for (int i = 0 ; i < config_report->uid_map().snapshots_size(); ++i) {
1818         auto snapshot = config_report->mutable_uid_map()->mutable_snapshots(i);
1819         for (int j = 0 ; j < snapshot->package_info_size(); ++j) {
1820             auto package_info = snapshot->mutable_package_info(j);
1821             if (package_info->has_name_hash()) {
1822                 auto it = str_map.find((uint64_t)(package_info->name_hash()));
1823                 if (it != str_map.end()) {
1824                     package_info->clear_name_hash();
1825                     package_info->set_name(it->second);
1826                 } else {
1827                     ALOGE("Can not find the string package name hash: %llu",
1828                         (unsigned long long)package_info->name_hash());
1829                 }
1830 
1831             }
1832         }
1833     }
1834     // Backfill the app name in app changes.
1835     for (int i = 0 ; i < config_report->uid_map().changes_size(); ++i) {
1836         auto change = config_report->mutable_uid_map()->mutable_changes(i);
1837         if (change->has_app_hash()) {
1838             auto it = str_map.find((uint64_t)(change->app_hash()));
1839             if (it != str_map.end()) {
1840                 change->clear_app_hash();
1841                 change->set_app(it->second);
1842             } else {
1843                 ALOGE("Can not find the string change app name hash: %llu",
1844                     (unsigned long long)change->app_hash());
1845             }
1846         }
1847     }
1848 }
1849 
backfillStringInReport(ConfigMetricsReportList * config_report_list)1850 void backfillStringInReport(ConfigMetricsReportList *config_report_list) {
1851     for (int i = 0; i < config_report_list->reports_size(); ++i) {
1852         backfillStringInReport(config_report_list->mutable_reports(i));
1853     }
1854 }
1855 
backfillDimensionPath(const DimensionsValue & path,const google::protobuf::RepeatedPtrField<DimensionsValue> & leafValues,int * leafIndex,DimensionsValue * dimension)1856 bool backfillDimensionPath(const DimensionsValue& path,
1857                            const google::protobuf::RepeatedPtrField<DimensionsValue>& leafValues,
1858                            int* leafIndex, DimensionsValue* dimension) {
1859     dimension->set_field(path.field());
1860     if (path.has_value_tuple()) {
1861         for (int i = 0; i < path.value_tuple().dimensions_value_size(); ++i) {
1862             if (!backfillDimensionPath(path.value_tuple().dimensions_value(i), leafValues,
1863                                        leafIndex,
1864                                        dimension->mutable_value_tuple()->add_dimensions_value())) {
1865                 return false;
1866             }
1867         }
1868     } else {
1869         if (*leafIndex < 0 || *leafIndex >= leafValues.size()) {
1870             return false;
1871         }
1872         dimension->MergeFrom(leafValues.Get(*leafIndex));
1873         (*leafIndex)++;
1874     }
1875     return true;
1876 }
1877 
backfillDimensionPath(const DimensionsValue & path,const google::protobuf::RepeatedPtrField<DimensionsValue> & leafValues,DimensionsValue * dimension)1878 bool backfillDimensionPath(const DimensionsValue& path,
1879                            const google::protobuf::RepeatedPtrField<DimensionsValue>& leafValues,
1880                            DimensionsValue* dimension) {
1881     int leafIndex = 0;
1882     return backfillDimensionPath(path, leafValues, &leafIndex, dimension);
1883 }
1884 
backfillDimensionPath(StatsLogReport * report)1885 void backfillDimensionPath(StatsLogReport* report) {
1886     if (report->has_dimensions_path_in_what()) {
1887         auto whatPath = report->dimensions_path_in_what();
1888         if (report->has_count_metrics()) {
1889             backfillDimensionPath(whatPath, report->mutable_count_metrics());
1890         } else if (report->has_duration_metrics()) {
1891             backfillDimensionPath(whatPath, report->mutable_duration_metrics());
1892         } else if (report->has_gauge_metrics()) {
1893             backfillDimensionPath(whatPath, report->mutable_gauge_metrics());
1894         } else if (report->has_value_metrics()) {
1895             backfillDimensionPath(whatPath, report->mutable_value_metrics());
1896         } else if (report->has_kll_metrics()) {
1897             backfillDimensionPath(whatPath, report->mutable_kll_metrics());
1898         }
1899         report->clear_dimensions_path_in_what();
1900     }
1901 }
1902 
backfillDimensionPath(ConfigMetricsReport * config_report)1903 void backfillDimensionPath(ConfigMetricsReport* config_report) {
1904     for (int i = 0; i < config_report->metrics_size(); ++i) {
1905         backfillDimensionPath(config_report->mutable_metrics(i));
1906     }
1907 }
1908 
backfillDimensionPath(ConfigMetricsReportList * config_report_list)1909 void backfillDimensionPath(ConfigMetricsReportList* config_report_list) {
1910     for (int i = 0; i < config_report_list->reports_size(); ++i) {
1911         backfillDimensionPath(config_report_list->mutable_reports(i));
1912     }
1913 }
1914 
backfillStartEndTimestamp(StatsLogReport * report)1915 void backfillStartEndTimestamp(StatsLogReport *report) {
1916     const int64_t timeBaseNs = report->time_base_elapsed_nano_seconds();
1917     const int64_t bucketSizeNs = report->bucket_size_nano_seconds();
1918     if (report->has_count_metrics()) {
1919         backfillStartEndTimestampForMetrics(
1920             timeBaseNs, bucketSizeNs, report->mutable_count_metrics());
1921     } else if (report->has_duration_metrics()) {
1922         backfillStartEndTimestampForMetrics(
1923             timeBaseNs, bucketSizeNs, report->mutable_duration_metrics());
1924     } else if (report->has_gauge_metrics()) {
1925         backfillStartEndTimestampForMetrics(
1926             timeBaseNs, bucketSizeNs, report->mutable_gauge_metrics());
1927         if (report->gauge_metrics().skipped_size() > 0) {
1928             backfillStartEndTimestampForSkippedBuckets(
1929                 timeBaseNs, report->mutable_gauge_metrics());
1930         }
1931     } else if (report->has_value_metrics()) {
1932         backfillStartEndTimestampForMetrics(
1933             timeBaseNs, bucketSizeNs, report->mutable_value_metrics());
1934         if (report->value_metrics().skipped_size() > 0) {
1935             backfillStartEndTimestampForSkippedBuckets(
1936                 timeBaseNs, report->mutable_value_metrics());
1937         }
1938     } else if (report->has_kll_metrics()) {
1939         backfillStartEndTimestampForMetrics(timeBaseNs, bucketSizeNs,
1940                                             report->mutable_kll_metrics());
1941         if (report->kll_metrics().skipped_size() > 0) {
1942             backfillStartEndTimestampForSkippedBuckets(timeBaseNs, report->mutable_kll_metrics());
1943         }
1944     }
1945 }
1946 
backfillStartEndTimestamp(ConfigMetricsReport * config_report)1947 void backfillStartEndTimestamp(ConfigMetricsReport *config_report) {
1948     for (int j = 0; j < config_report->metrics_size(); ++j) {
1949         backfillStartEndTimestamp(config_report->mutable_metrics(j));
1950     }
1951 }
1952 
backfillStartEndTimestamp(ConfigMetricsReportList * config_report_list)1953 void backfillStartEndTimestamp(ConfigMetricsReportList *config_report_list) {
1954     for (int i = 0; i < config_report_list->reports_size(); ++i) {
1955         backfillStartEndTimestamp(config_report_list->mutable_reports(i));
1956     }
1957 }
1958 
backfillAggregatedAtoms(ConfigMetricsReportList * config_report_list)1959 void backfillAggregatedAtoms(ConfigMetricsReportList* config_report_list) {
1960     for (int i = 0; i < config_report_list->reports_size(); ++i) {
1961         backfillAggregatedAtoms(config_report_list->mutable_reports(i));
1962     }
1963 }
1964 
backfillAggregatedAtoms(ConfigMetricsReport * config_report)1965 void backfillAggregatedAtoms(ConfigMetricsReport* config_report) {
1966     for (int i = 0; i < config_report->metrics_size(); ++i) {
1967         backfillAggregatedAtoms(config_report->mutable_metrics(i));
1968     }
1969 }
1970 
backfillAggregatedAtoms(StatsLogReport * report)1971 void backfillAggregatedAtoms(StatsLogReport* report) {
1972     if (report->has_event_metrics()) {
1973         backfillAggregatedAtomsInEventMetric(report->mutable_event_metrics());
1974     }
1975     if (report->has_gauge_metrics()) {
1976         backfillAggregatedAtomsInGaugeMetric(report->mutable_gauge_metrics());
1977     }
1978 }
1979 
backfillAggregatedAtomsInEventMetric(StatsLogReport::EventMetricDataWrapper * wrapper)1980 void backfillAggregatedAtomsInEventMetric(StatsLogReport::EventMetricDataWrapper* wrapper) {
1981     std::vector<EventMetricData> metricData;
1982     for (int i = 0; i < wrapper->data_size(); ++i) {
1983         AggregatedAtomInfo* atomInfo = wrapper->mutable_data(i)->mutable_aggregated_atom_info();
1984         for (int j = 0; j < atomInfo->elapsed_timestamp_nanos_size(); j++) {
1985             EventMetricData data;
1986             *(data.mutable_atom()) = atomInfo->atom();
1987             data.set_elapsed_timestamp_nanos(atomInfo->elapsed_timestamp_nanos(j));
1988             metricData.push_back(data);
1989         }
1990     }
1991 
1992     if (metricData.size() == 0) {
1993         return;
1994     }
1995 
1996     sort(metricData.begin(), metricData.end(),
1997          [](const EventMetricData& lhs, const EventMetricData& rhs) {
1998              return lhs.elapsed_timestamp_nanos() < rhs.elapsed_timestamp_nanos();
1999          });
2000 
2001     wrapper->clear_data();
2002     for (int i = 0; i < metricData.size(); ++i) {
2003         *(wrapper->add_data()) = metricData[i];
2004     }
2005 }
2006 
backfillAggregatedAtomsInGaugeMetric(StatsLogReport::GaugeMetricDataWrapper * wrapper)2007 void backfillAggregatedAtomsInGaugeMetric(StatsLogReport::GaugeMetricDataWrapper* wrapper) {
2008     for (int i = 0; i < wrapper->data_size(); ++i) {
2009         for (int j = 0; j < wrapper->data(i).bucket_info_size(); ++j) {
2010             GaugeBucketInfo* bucketInfo = wrapper->mutable_data(i)->mutable_bucket_info(j);
2011             vector<pair<Atom, int64_t>> atomData = unnestGaugeAtomData(*bucketInfo);
2012 
2013             if (atomData.size() == 0) {
2014                 return;
2015             }
2016 
2017             bucketInfo->clear_aggregated_atom_info();
2018             ASSERT_EQ(bucketInfo->atom_size(), 0);
2019             ASSERT_EQ(bucketInfo->elapsed_timestamp_nanos_size(), 0);
2020 
2021             for (int k = 0; k < atomData.size(); ++k) {
2022                 *(bucketInfo->add_atom()) = atomData[k].first;
2023                 bucketInfo->add_elapsed_timestamp_nanos(atomData[k].second);
2024             }
2025         }
2026     }
2027 }
2028 
unnestGaugeAtomData(const GaugeBucketInfo & bucketInfo)2029 vector<pair<Atom, int64_t>> unnestGaugeAtomData(const GaugeBucketInfo& bucketInfo) {
2030     vector<pair<Atom, int64_t>> atomData;
2031     for (int k = 0; k < bucketInfo.aggregated_atom_info_size(); ++k) {
2032         const AggregatedAtomInfo& atomInfo = bucketInfo.aggregated_atom_info(k);
2033         for (int l = 0; l < atomInfo.elapsed_timestamp_nanos_size(); ++l) {
2034             atomData.push_back(make_pair(atomInfo.atom(), atomInfo.elapsed_timestamp_nanos(l)));
2035         }
2036     }
2037 
2038     sort(atomData.begin(), atomData.end(),
2039          [](const pair<Atom, int64_t>& lhs, const pair<Atom, int64_t>& rhs) {
2040              return lhs.second < rhs.second;
2041          });
2042 
2043     return atomData;
2044 }
2045 
sortReportsByElapsedTime(ConfigMetricsReportList * configReportList)2046 void sortReportsByElapsedTime(ConfigMetricsReportList* configReportList) {
2047     RepeatedPtrField<ConfigMetricsReport>* reports = configReportList->mutable_reports();
2048     sort(reports->pointer_begin(), reports->pointer_end(),
2049          [](const ConfigMetricsReport* lhs, const ConfigMetricsReport* rhs) {
2050              return lhs->current_report_elapsed_nanos() < rhs->current_report_elapsed_nanos();
2051          });
2052 }
2053 
onPullAtom(int atomTag,const shared_ptr<IPullAtomResultReceiver> & resultReceiver)2054 Status FakeSubsystemSleepCallback::onPullAtom(int atomTag,
2055         const shared_ptr<IPullAtomResultReceiver>& resultReceiver) {
2056     // Convert stats_events into StatsEventParcels.
2057     std::vector<StatsEventParcel> parcels;
2058     for (int i = 1; i < 3; i++) {
2059         AStatsEvent* event = AStatsEvent_obtain();
2060         AStatsEvent_setAtomId(event, atomTag);
2061         std::string subsystemName = "subsystem_name_";
2062         subsystemName = subsystemName + std::to_string(i);
2063         AStatsEvent_writeString(event, subsystemName.c_str());
2064         AStatsEvent_writeString(event, "subsystem_subname foo");
2065         AStatsEvent_writeInt64(event, /*count= */ i);
2066         AStatsEvent_writeInt64(event, /*time_millis= */ pullNum * pullNum * 100 + i);
2067         AStatsEvent_build(event);
2068         size_t size;
2069         uint8_t* buffer = AStatsEvent_getBuffer(event, &size);
2070 
2071         StatsEventParcel p;
2072         // vector.assign() creates a copy, but this is inevitable unless
2073         // stats_event.h/c uses a vector as opposed to a buffer.
2074         p.buffer.assign(buffer, buffer + size);
2075         parcels.push_back(std::move(p));
2076         AStatsEvent_release(event);
2077     }
2078     pullNum++;
2079     resultReceiver->pullFinished(atomTag, /*success=*/true, parcels);
2080     return Status::ok();
2081 }
2082 
writeFlag(const string & flagName,const string & flagValue)2083 void writeFlag(const string& flagName, const string& flagValue) {
2084     SetProperty(StringPrintf("persist.device_config.%s.%s", STATSD_NATIVE_NAMESPACE.c_str(),
2085                              flagName.c_str()),
2086                 flagValue);
2087 }
2088 
writeBootFlag(const string & flagName,const string & flagValue)2089 void writeBootFlag(const string& flagName, const string& flagValue) {
2090     SetProperty(StringPrintf("persist.device_config.%s.%s", STATSD_NATIVE_BOOT_NAMESPACE.c_str(),
2091                              flagName.c_str()),
2092                 flagValue);
2093 }
2094 
getPackageInfoSnapshot(const sp<UidMap> uidMap)2095 PackageInfoSnapshot getPackageInfoSnapshot(const sp<UidMap> uidMap) {
2096     ProtoOutputStream protoOutputStream;
2097     uidMap->writeUidMapSnapshot(/* timestamp */ 1, /* includeVersionStrings */ true,
2098                                 /* includeInstaller */ true, /* certificateHashSize */ UINT8_MAX,
2099                                 /* interestingUids */ {},
2100                                 /* installerIndices */ nullptr, /* str_set */ nullptr,
2101                                 &protoOutputStream);
2102 
2103     PackageInfoSnapshot packageInfoSnapshot;
2104     outputStreamToProto(&protoOutputStream, &packageInfoSnapshot);
2105     return packageInfoSnapshot;
2106 }
2107 
buildPackageInfo(const string & name,const int32_t uid,const int64_t version,const string & versionString,const optional<string> installer,const vector<uint8_t> & certHash,const bool deleted,const bool hashStrings,const optional<uint32_t> installerIndex)2108 PackageInfo buildPackageInfo(const string& name, const int32_t uid, const int64_t version,
2109                              const string& versionString, const optional<string> installer,
2110                              const vector<uint8_t>& certHash, const bool deleted,
2111                              const bool hashStrings, const optional<uint32_t> installerIndex) {
2112     PackageInfo packageInfo;
2113     packageInfo.set_version(version);
2114     packageInfo.set_uid(uid);
2115     packageInfo.set_deleted(deleted);
2116     if (!certHash.empty()) {
2117         packageInfo.set_truncated_certificate_hash(certHash.data(), certHash.size());
2118     }
2119     if (hashStrings) {
2120         packageInfo.set_name_hash(Hash64(name));
2121         packageInfo.set_version_string_hash(Hash64(versionString));
2122     } else {
2123         packageInfo.set_name(name);
2124         packageInfo.set_version_string(versionString);
2125     }
2126     if (installer) {
2127         if (installerIndex) {
2128             packageInfo.set_installer_index(*installerIndex);
2129         } else if (hashStrings) {
2130             packageInfo.set_installer_hash(Hash64(*installer));
2131         } else {
2132             packageInfo.set_installer(*installer);
2133         }
2134     }
2135     return packageInfo;
2136 }
2137 
buildPackageInfos(const vector<string> & names,const vector<int32_t> & uids,const vector<int64_t> & versions,const vector<string> & versionStrings,const vector<string> & installers,const vector<vector<uint8_t>> & certHashes,const vector<bool> & deleted,const vector<uint32_t> & installerIndices,const bool hashStrings)2138 vector<PackageInfo> buildPackageInfos(
2139         const vector<string>& names, const vector<int32_t>& uids, const vector<int64_t>& versions,
2140         const vector<string>& versionStrings, const vector<string>& installers,
2141         const vector<vector<uint8_t>>& certHashes, const vector<bool>& deleted,
2142         const vector<uint32_t>& installerIndices, const bool hashStrings) {
2143     vector<PackageInfo> packageInfos;
2144     for (int i = 0; i < uids.size(); i++) {
2145         const optional<uint32_t> installerIndex =
2146                 installerIndices.empty() ? nullopt : optional<uint32_t>(installerIndices[i]);
2147         const optional<string> installer =
2148                 installers.empty() ? nullopt : optional<string>(installers[i]);
2149         vector<uint8_t> certHash;
2150         if (!certHashes.empty()) {
2151             certHash = certHashes[i];
2152         }
2153         packageInfos.emplace_back(buildPackageInfo(names[i], uids[i], versions[i],
2154                                                    versionStrings[i], installer, certHash,
2155                                                    deleted[i], hashStrings, installerIndex));
2156     }
2157     return packageInfos;
2158 }
2159 
getPulledAtomStats(int32_t atom_id)2160 StatsdStatsReport_PulledAtomStats getPulledAtomStats(int32_t atom_id) {
2161     vector<uint8_t> statsBuffer;
2162     StatsdStats::getInstance().dumpStats(&statsBuffer, false /*reset stats*/);
2163     StatsdStatsReport statsReport;
2164     StatsdStatsReport_PulledAtomStats pulledAtomStats;
2165     if (!statsReport.ParseFromArray(&statsBuffer[0], statsBuffer.size())) {
2166         return pulledAtomStats;
2167     }
2168     if (statsReport.pulled_atom_stats_size() == 0) {
2169         return pulledAtomStats;
2170     }
2171     for (size_t i = 0; i < statsReport.pulled_atom_stats_size(); i++) {
2172         if (statsReport.pulled_atom_stats(i).atom_id() == atom_id) {
2173             return statsReport.pulled_atom_stats(i);
2174         }
2175     }
2176     return pulledAtomStats;
2177 }
2178 
createStatsEvent(AStatsEvent * statsEvent,uint8_t typeId,uint32_t atomId)2179 void createStatsEvent(AStatsEvent* statsEvent, uint8_t typeId, uint32_t atomId) {
2180     AStatsEvent_setAtomId(statsEvent, atomId);
2181     fillStatsEventWithSampleValue(statsEvent, typeId);
2182 }
2183 
fillStatsEventWithSampleValue(AStatsEvent * statsEvent,uint8_t typeId)2184 void fillStatsEventWithSampleValue(AStatsEvent* statsEvent, uint8_t typeId) {
2185     int int32Array[2] = {3, 6};
2186     uint32_t uids[] = {1001, 1002};
2187     const char* tags[] = {"tag1", "tag2"};
2188 
2189     switch (typeId) {
2190         case INT32_TYPE:
2191             AStatsEvent_writeInt32(statsEvent, 10);
2192             break;
2193         case INT64_TYPE:
2194             AStatsEvent_writeInt64(statsEvent, 1000L);
2195             break;
2196         case STRING_TYPE:
2197             AStatsEvent_writeString(statsEvent, "test");
2198             break;
2199         case LIST_TYPE:
2200             AStatsEvent_writeInt32Array(statsEvent, int32Array, 2);
2201             break;
2202         case FLOAT_TYPE:
2203             AStatsEvent_writeFloat(statsEvent, 1.3f);
2204             break;
2205         case BOOL_TYPE:
2206             AStatsEvent_writeBool(statsEvent, 1);
2207             break;
2208         case BYTE_ARRAY_TYPE:
2209             AStatsEvent_writeByteArray(statsEvent, (uint8_t*)"test", strlen("test"));
2210             break;
2211         case ATTRIBUTION_CHAIN_TYPE:
2212             AStatsEvent_writeAttributionChain(statsEvent, uids, tags, 2);
2213             break;
2214         default:
2215             break;
2216     }
2217 }
2218 
2219 }  // namespace statsd
2220 }  // namespace os
2221 }  // namespace android
2222