• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include "statsd.h"
18 
19 #include "arch/instruction_set.h"
20 #include "base/compiler_filter.h"
21 #include "base/metrics/metrics.h"
22 #include "gc/collector/mark_compact.h"
23 #include "gc/heap.h"
24 #include "gc/space/image_space.h"
25 #include "runtime.h"
26 #include "statslog_art.h"
27 
28 #pragma clang diagnostic push
29 #pragma clang diagnostic error "-Wconversion"
30 
31 namespace art HIDDEN {
32 namespace metrics {
33 
34 namespace {
35 
36 // EncodeDatumId returns a std::optional that provides a enum value from atoms.proto if the datum is
37 // one that we support logging to statsd. The list of datums that ART collects is a superset of what
38 // we report to statsd. Therefore, we only have mappings for the DatumIds that statsd recognizes.
39 // Also it must be noted that histograms are not handled yet by statsd yet.
40 //
41 // Other code can use whether the result of this function has a value to decide whether to report
42 // the atom to statsd.
43 //
44 // To report additional measurements to statsd, first add an entry in atoms.proto and then add an
45 // entry to this function as well.
EncodeDatumId(DatumId datum_id)46 constexpr std::optional<int32_t> EncodeDatumId(DatumId datum_id) {
47   switch (datum_id) {
48     case DatumId::kClassVerificationTotalTime:
49       return std::make_optional(
50           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_CLASS_VERIFICATION_TIME_COUNTER_MICROS);
51     case DatumId::kClassVerificationTotalTimeDelta:
52       return std::make_optional(
53           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_CLASS_VERIFICATION_TIME_MICROS);
54     case DatumId::kJitMethodCompileTotalTime:
55       return std::make_optional(
56           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_JIT_METHOD_COMPILE_TIME_MICROS);
57     case DatumId::kJitMethodCompileTotalTimeDelta:
58       return std::make_optional(
59           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_JIT_METHOD_COMPILE_TIME_MICROS);
60     case DatumId::kClassLoadingTotalTime:
61       return std::make_optional(
62           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_CLASS_LOADING_TIME_COUNTER_MICROS);
63     case DatumId::kClassLoadingTotalTimeDelta:
64       return std::make_optional(
65           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_CLASS_LOADING_TIME_MICROS);
66     case DatumId::kClassVerificationCount:
67       return std::make_optional(
68           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_CLASS_VERIFICATION_COUNT);
69     case DatumId::kClassVerificationCountDelta:
70       return std::make_optional(
71           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_CLASS_VERIFICATION_COUNT);
72     case DatumId::kWorldStopTimeDuringGCAvg:
73       return std::make_optional(
74           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_WORLD_STOP_TIME_AVG_MICROS);
75     case DatumId::kYoungGcCount:
76       return std::make_optional(
77           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_COUNT);
78     case DatumId::kYoungGcCountDelta:
79       return std::make_optional(
80           statsd::
81               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_YOUNG_GENERATION_COLLECTION_COUNT);
82     case DatumId::kFullGcCount:
83       return std::make_optional(
84           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_COUNT);
85     case DatumId::kFullGcCountDelta:
86       return std::make_optional(
87           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_FULL_HEAP_COLLECTION_COUNT);
88     case DatumId::kTotalBytesAllocated:
89       return std::make_optional(
90           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_TOTAL_BYTES_ALLOCATED);
91     case DatumId::kTotalBytesAllocatedDelta:
92       return std::make_optional(
93           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_TOTAL_BYTES_ALLOCATED);
94     case DatumId::kYoungGcCollectionTime:
95       return std::make_optional(
96           statsd::
97               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_TIME_HISTO_MILLIS);
98     case DatumId::kFullGcCollectionTime:
99       return std::make_optional(
100           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_TIME_HISTO_MILLIS);
101     case DatumId::kYoungGcThroughput:
102       return std::make_optional(
103           statsd::
104               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_THROUGHPUT_HISTO_MB_PER_SEC);
105     case DatumId::kFullGcThroughput:
106       return std::make_optional(
107           statsd::
108               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_THROUGHPUT_HISTO_MB_PER_SEC);
109     case DatumId::kJitMethodCompileCount:
110       return std::make_optional(
111           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_JIT_METHOD_COMPILE_COUNT);
112     case DatumId::kJitMethodCompileCountDelta:
113       return std::make_optional(
114           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_JIT_METHOD_COMPILE_COUNT);
115     case DatumId::kYoungGcTracingThroughput:
116       return std::make_optional(
117           statsd::
118               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_TRACING_THROUGHPUT_HISTO_MB_PER_SEC);
119     case DatumId::kFullGcTracingThroughput:
120       return std::make_optional(
121           statsd::
122               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_TRACING_THROUGHPUT_HISTO_MB_PER_SEC);
123     case DatumId::kTotalGcCollectionTime:
124       return std::make_optional(
125           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_TOTAL_COLLECTION_TIME_MS);
126     case DatumId::kTotalGcCollectionTimeDelta:
127       return std::make_optional(
128           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_TOTAL_COLLECTION_TIME_MS);
129     case DatumId::kYoungGcThroughputAvg:
130       return std::make_optional(
131           statsd::
132               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_THROUGHPUT_AVG_MB_PER_SEC);
133     case DatumId::kFullGcThroughputAvg:
134       return std::make_optional(
135           statsd::
136               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_THROUGHPUT_AVG_MB_PER_SEC);
137     case DatumId::kYoungGcTracingThroughputAvg:
138       return std::make_optional(
139           statsd::
140               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_TRACING_THROUGHPUT_AVG_MB_PER_SEC);
141     case DatumId::kFullGcTracingThroughputAvg:
142       return std::make_optional(
143           statsd::
144               ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_TRACING_THROUGHPUT_AVG_MB_PER_SEC);
145     case DatumId::kGcWorldStopTime:
146       return std::make_optional(statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_WORLD_STOP_TIME_US);
147     case DatumId::kGcWorldStopTimeDelta:
148       return std::make_optional(
149           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_WORLD_STOP_TIME_US);
150     case DatumId::kGcWorldStopCount:
151       return std::make_optional(statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_WORLD_STOP_COUNT);
152     case DatumId::kGcWorldStopCountDelta:
153       return std::make_optional(
154           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_WORLD_STOP_COUNT);
155     case DatumId::kYoungGcScannedBytes:
156       return std::make_optional(
157           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_SCANNED_BYTES);
158     case DatumId::kYoungGcScannedBytesDelta:
159       return std::make_optional(
160           statsd::
161               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_YOUNG_GENERATION_COLLECTION_SCANNED_BYTES);
162     case DatumId::kYoungGcFreedBytes:
163       return std::make_optional(
164           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_FREED_BYTES);
165     case DatumId::kYoungGcFreedBytesDelta:
166       return std::make_optional(
167           statsd::
168               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_YOUNG_GENERATION_COLLECTION_FREED_BYTES);
169     case DatumId::kYoungGcDuration:
170       return std::make_optional(
171           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_YOUNG_GENERATION_COLLECTION_DURATION_MS);
172     case DatumId::kYoungGcDurationDelta:
173       return std::make_optional(
174           statsd::
175               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_YOUNG_GENERATION_COLLECTION_DURATION_MS);
176     case DatumId::kFullGcScannedBytes:
177       return std::make_optional(
178           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_SCANNED_BYTES);
179     case DatumId::kFullGcScannedBytesDelta:
180       return std::make_optional(
181           statsd::
182               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_FULL_HEAP_COLLECTION_SCANNED_BYTES);
183     case DatumId::kFullGcFreedBytes:
184       return std::make_optional(
185           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_FREED_BYTES);
186     case DatumId::kFullGcFreedBytesDelta:
187       return std::make_optional(
188           statsd::
189               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_FULL_HEAP_COLLECTION_FREED_BYTES);
190     case DatumId::kFullGcDuration:
191       return std::make_optional(
192           statsd::ART_DATUM_REPORTED__KIND__ART_DATUM_GC_FULL_HEAP_COLLECTION_DURATION_MS);
193     case DatumId::kFullGcDurationDelta:
194       return std::make_optional(
195           statsd::
196               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_FULL_HEAP_COLLECTION_DURATION_MS);
197     case DatumId::kTimeElapsedDelta:
198       return std::make_optional(
199           statsd::ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_TIME_ELAPSED_MS);
200     case DatumId::kAppSlowPathDuringYoungGcDurationDelta:
201       return std::make_optional(
202           statsd::
203               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_APP_SLOW_PATH_DURING_YOUNG_GENERATION_COLLECTION_DURATION_MILLIS);
204     case DatumId::kAppSlowPathDuringFullGcDurationDelta:
205       return std::make_optional(
206           statsd::
207               ART_DATUM_DELTA_REPORTED__KIND__ART_DATUM_DELTA_GC_APP_SLOW_PATH_DURING_FULL_HEAP_COLLECTION_DURATION_MILLIS);
208   }
209 }
210 
EncodeCompileFilter(CompilerFilterReporting filter)211 constexpr int32_t EncodeCompileFilter(CompilerFilterReporting filter) {
212   switch (filter) {
213     case CompilerFilterReporting::kAssumeVerified:
214       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_ASSUMED_VERIFIED;
215     case CompilerFilterReporting::kExtract:
216       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_EXTRACT;
217     case CompilerFilterReporting::kVerify:
218       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_VERIFY;
219     case CompilerFilterReporting::kSpaceProfile:
220       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_SPACE_PROFILE;
221     case CompilerFilterReporting::kSpace:
222       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_SPACE;
223     case CompilerFilterReporting::kSpeedProfile:
224       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_SPEED_PROFILE;
225     case CompilerFilterReporting::kSpeed:
226       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_SPEED;
227     case CompilerFilterReporting::kEverythingProfile:
228       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_EVERYTHING_PROFILE;
229     case CompilerFilterReporting::kEverything:
230       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_EVERYTHING;
231     case CompilerFilterReporting::kError:
232       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_ERROR;
233     case CompilerFilterReporting::kUnknown:
234       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_UNKNOWN;
235     case CompilerFilterReporting::kRunFromApk:
236       return statsd::ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_FAKE_RUN_FROM_APK;
237     case CompilerFilterReporting::kRunFromApkFallback:
238       return statsd::
239           ART_DATUM_REPORTED__COMPILE_FILTER__ART_COMPILATION_FILTER_FAKE_RUN_FROM_APK_FALLBACK;
240   }
241 }
242 
EncodeCompilationReason(CompilationReason reason)243 constexpr int32_t EncodeCompilationReason(CompilationReason reason) {
244   switch (reason) {
245     case CompilationReason::kUnknown:
246       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_UNKNOWN;
247     case CompilationReason::kABOTA:
248       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_AB_OTA;
249     case CompilationReason::kBgDexopt:
250       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_BG_DEXOPT;
251     case CompilationReason::kError:
252       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_ERROR;
253     case CompilationReason::kFirstBoot:
254       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_FIRST_BOOT;
255     case CompilationReason::kInactive:
256       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INACTIVE;
257     case CompilationReason::kInstall:
258       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL;
259     case CompilationReason::kInstallWithDexMetadata:
260       return statsd::
261           ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL_WITH_DEX_METADATA;
262     case CompilationReason::kShared:
263       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_SHARED;
264     case CompilationReason::kPostBoot:
265       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_POST_BOOT;
266     case CompilationReason::kInstallBulk:
267       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL_BULK;
268     case CompilationReason::kInstallBulkSecondary:
269       return statsd::
270           ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL_BULK_SECONDARY;
271     case CompilationReason::kInstallBulkDowngraded:
272       return statsd::
273           ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL_BULK_DOWNGRADED;
274     case CompilationReason::kInstallBulkSecondaryDowngraded:
275       return statsd::
276           ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL_BULK_SECONDARY_DOWNGRADED;
277     case CompilationReason::kBootAfterOTA:
278       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_BOOT_AFTER_OTA;
279     case CompilationReason::kInstallFast:
280       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_INSTALL_FAST;
281     case CompilationReason::kPrebuilt:
282       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_PREBUILT;
283     case CompilationReason::kCmdLine:
284       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_CMDLINE;
285     case CompilationReason::kVdex:
286       return statsd::ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_VDEX;
287     case CompilationReason::kBootAfterMainlineUpdate:
288       return statsd::
289           ART_DATUM_REPORTED__COMPILATION_REASON__ART_COMPILATION_REASON_BOOT_AFTER_MAINLINE_UPDATE;
290   }
291 }
292 
EncodeInstructionSet(InstructionSet isa)293 constexpr int32_t EncodeInstructionSet(InstructionSet isa) {
294   switch (isa) {
295     case InstructionSet::kArm:
296       // Fall-through.
297     case InstructionSet::kThumb2:
298       return statsd::ART_DATUM_REPORTED__ISA__ART_ISA_ARM;
299     case InstructionSet::kArm64:
300       return statsd::ART_DATUM_REPORTED__ISA__ART_ISA_ARM64;
301     case InstructionSet::kRiscv64:
302       return statsd::ART_DATUM_REPORTED__ISA__ART_ISA_RISCV64;
303     case InstructionSet::kX86:
304       return statsd::ART_DATUM_REPORTED__ISA__ART_ISA_X86;
305     case InstructionSet::kX86_64:
306       return statsd::ART_DATUM_REPORTED__ISA__ART_ISA_X86_64;
307     case InstructionSet::kNone:
308       return statsd::ART_DATUM_REPORTED__ISA__ART_ISA_UNKNOWN;
309   }
310 }
311 
EncodeGcCollectorType(gc::CollectorType collector_type)312 constexpr int32_t EncodeGcCollectorType(gc::CollectorType collector_type) {
313   switch (collector_type) {
314     case gc::CollectorType::kCollectorTypeMS:
315       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_MARK_SWEEP;
316     case gc::CollectorType::kCollectorTypeCMS:
317       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_CONCURRENT_MARK_SWEEP;
318     case gc::CollectorType::kCollectorTypeCMC:
319       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_CONCURRENT_MARK_COMPACT;
320     case gc::CollectorType::kCollectorTypeCMCBackground:
321       return statsd::
322           ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_CONCURRENT_MARK_COMPACT_BACKGROUND;
323     case gc::CollectorType::kCollectorTypeSS:
324       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_SEMI_SPACE;
325     case gc::kCollectorTypeCC:
326       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_CONCURRENT_COPYING;
327     case gc::kCollectorTypeCCBackground:
328       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_CONCURRENT_COPYING_BACKGROUND;
329     case gc::kCollectorTypeNone:
330     case gc::kCollectorTypeInstrumentation:
331     case gc::kCollectorTypeAddRemoveAppImageSpace:
332     case gc::kCollectorTypeDebugger:
333     case gc::kCollectorTypeHomogeneousSpaceCompact:
334     case gc::kCollectorTypeClassLinker:
335     case gc::kCollectorTypeJitCodeCache:
336     case gc::kCollectorTypeHprof:
337     case gc::kCollectorTypeAddRemoveSystemWeakHolder:
338     case gc::kCollectorTypeGetObjectsAllocated:
339     case gc::kCollectorTypeCriticalSection:
340     case gc::kCollectorTypeHeapTrim:
341       return statsd::ART_DATUM_REPORTED__GC__ART_GC_COLLECTOR_TYPE_UNKNOWN;
342   }
343 }
344 
EncodeUffdMinorFaultSupport()345 int32_t EncodeUffdMinorFaultSupport() {
346   auto [uffd_supported, minor_fault_supported] = gc::collector::MarkCompact::GetUffdAndMinorFault();
347 
348   if (uffd_supported) {
349     if (minor_fault_supported) {
350       return statsd::ART_DATUM_REPORTED__UFFD_SUPPORT__ART_UFFD_SUPPORT_MINOR_FAULT_MODE_SUPPORTED;
351     } else {
352       return statsd::
353           ART_DATUM_REPORTED__UFFD_SUPPORT__ART_UFFD_SUPPORT_MINOR_FAULT_MODE_NOT_SUPPORTED;
354     }
355   } else {
356     return statsd::ART_DATUM_REPORTED__UFFD_SUPPORT__ART_UFFD_SUPPORT_UFFD_NOT_SUPPORTED;
357   }
358 }
359 
360 class StatsdBackend : public MetricsBackend {
361  public:
BeginOrUpdateSession(const SessionData & session_data)362   void BeginOrUpdateSession(const SessionData& session_data) override {
363     session_data_ = session_data;
364   }
365 
366  protected:
BeginReport(uint64_t timestamp_since_start_ms)367   void BeginReport(uint64_t timestamp_since_start_ms) override {
368     current_timestamp_ = static_cast<int64_t>(timestamp_since_start_ms);
369   }
370 
ReportCounter(DatumId counter_type,uint64_t value)371   void ReportCounter(DatumId counter_type, uint64_t value) override {
372     std::optional<int32_t> datum_id = EncodeDatumId(counter_type);
373     if (!datum_id.has_value()) {
374       return;
375     }
376 
377     int32_t atom;
378     switch (counter_type) {
379 #define EVENT_METRIC_CASE(name, ...) case DatumId::k##name:
380       ART_EVENT_METRICS(EVENT_METRIC_CASE)
381 #undef EVENT_METRIC_CASE
382       atom = statsd::ART_DATUM_REPORTED;
383       break;
384 
385 #define VALUE_METRIC_CASE(name, type, ...) case DatumId::k##name:
386       ART_VALUE_METRICS(VALUE_METRIC_CASE)
387 #undef VALUE_METRIC_CASE
388       atom = statsd::ART_DATUM_DELTA_REPORTED;
389       break;
390     }
391 
392     statsd::stats_write(
393         atom,
394         session_data_.session_id,
395         session_data_.uid,
396         EncodeCompileFilter(session_data_.compiler_filter),
397         EncodeCompilationReason(session_data_.compilation_reason),
398         current_timestamp_,
399         0,  // deprecated - was ArtThreadType
400         datum_id.value(),
401         static_cast<int64_t>(value),
402         0,  // deprecated - was ArtDexMetadataType
403         0,  // deprecated - was ArtApkType
404         EncodeInstructionSet(kRuntimeISA),
405         EncodeGcCollectorType(Runtime::Current()->GetHeap()->GetForegroundCollectorType()),
406         EncodeUffdMinorFaultSupport());
407   }
408 
ReportHistogram(DatumId,int64_t,int64_t,const std::vector<uint32_t> &)409   void ReportHistogram(DatumId /*histogram_type*/,
410                        int64_t /*low_value*/,
411                        int64_t /*high_value*/,
412                        const std::vector<uint32_t>& /*buckets*/) override {
413     // TODO: implement this once ArtDatumReported in atoms.proto supports histograms.
414     LOG_STREAM(DEBUG) << "Attempting to write histogram to statsd. This is not supported yet.";
415   }
416 
EndReport()417   void EndReport() override {}
418 
419  private:
420   SessionData session_data_;
421   // The timestamp provided to the last call to BeginReport
422   int64_t current_timestamp_;
423 };
424 
425 }  // namespace
426 
CreateStatsdBackend()427 std::unique_ptr<MetricsBackend> CreateStatsdBackend() { return std::make_unique<StatsdBackend>(); }
428 
DeviceStatusCallback(int32_t atom_tag,AStatsEventList * data,void * cookie)429 AStatsManager_PullAtomCallbackReturn DeviceStatusCallback(int32_t atom_tag,
430                                                           AStatsEventList* data,
431                                                           [[maybe_unused]] void* cookie) {
432   if (atom_tag == statsd::ART_DEVICE_STATUS) {
433     Runtime* runtime = Runtime::Current();
434     int32_t boot_image_status;
435     if (runtime->GetHeap()->HasBootImageSpace() && !runtime->HasImageWithProfile()) {
436       boot_image_status = statsd::ART_DEVICE_DATUM_REPORTED__BOOT_IMAGE_STATUS__STATUS_FULL;
437     } else if (runtime->GetHeap()->HasBootImageSpace() &&
438                runtime->GetHeap()->GetBootImageSpaces()[0]->GetProfileFiles().empty()) {
439       boot_image_status = statsd::ART_DEVICE_DATUM_REPORTED__BOOT_IMAGE_STATUS__STATUS_MINIMAL;
440     } else {
441       boot_image_status = statsd::ART_DEVICE_DATUM_REPORTED__BOOT_IMAGE_STATUS__STATUS_NONE;
442     }
443     statsd::addAStatsEvent(data, atom_tag, boot_image_status);
444     return AStatsManager_PULL_SUCCESS;
445   }
446 
447   return AStatsManager_PULL_SKIP;
448 }
449 
SetupCallbackForDeviceStatus()450 void SetupCallbackForDeviceStatus() {
451   AStatsManager_setPullAtomCallback(
452       statsd::ART_DEVICE_STATUS, /*metadata=*/nullptr, DeviceStatusCallback, /*cookie=*/nullptr);
453 }
454 
ReportDeviceMetrics()455 void ReportDeviceMetrics() {
456   Runtime* runtime = Runtime::Current();
457   int32_t boot_image_status;
458   if (runtime->GetHeap()->HasBootImageSpace() && !runtime->HasImageWithProfile()) {
459     boot_image_status = statsd::ART_DEVICE_DATUM_REPORTED__BOOT_IMAGE_STATUS__STATUS_FULL;
460   } else if (runtime->GetHeap()->HasBootImageSpace() &&
461              runtime->GetHeap()->GetBootImageSpaces()[0]->GetProfileFiles().empty()) {
462     boot_image_status = statsd::ART_DEVICE_DATUM_REPORTED__BOOT_IMAGE_STATUS__STATUS_MINIMAL;
463   } else {
464     boot_image_status = statsd::ART_DEVICE_DATUM_REPORTED__BOOT_IMAGE_STATUS__STATUS_NONE;
465   }
466   statsd::stats_write(statsd::ART_DEVICE_DATUM_REPORTED, boot_image_status);
467 }
468 
469 }  // namespace metrics
470 }  // namespace art
471 
472 #pragma clang diagnostic pop  // -Wconversion
473