diff options
Diffstat (limited to 'src/trace_processor/importers/proto/heap_graph_tracker_unittest.cc')
-rw-r--r-- | src/trace_processor/importers/proto/heap_graph_tracker_unittest.cc | 181 |
1 files changed, 164 insertions, 17 deletions
diff --git a/src/trace_processor/importers/proto/heap_graph_tracker_unittest.cc b/src/trace_processor/importers/proto/heap_graph_tracker_unittest.cc index 26b0ca59e..71714876e 100644 --- a/src/trace_processor/importers/proto/heap_graph_tracker_unittest.cc +++ b/src/trace_processor/importers/proto/heap_graph_tracker_unittest.cc @@ -16,9 +16,9 @@ #include "src/trace_processor/importers/proto/heap_graph_tracker.h" -#include "src/trace_processor/importers/proto/profiler_util.h" - #include "perfetto/base/logging.h" +#include "src/trace_processor/importers/common/process_tracker.h" +#include "src/trace_processor/importers/proto/profiler_util.h" #include "test/gtest_and_gmock.h" namespace perfetto { @@ -28,22 +28,167 @@ namespace { using ::testing::UnorderedElementsAre; TEST(HeapGraphTrackerTest, PackageFromLocationApp) { - TraceStorage storage; - EXPECT_EQ( - PackageFromLocation(&storage, - "/data/app/~~ASDFGH1234QWerT==/" - "com.twitter.android-MNBVCX7890SDTst6==/test.apk"), - "com.twitter.android"); - EXPECT_EQ(PackageFromLocation( - &storage, - "/data/app/com.google.android.webview-6XfQhnaSkFwGK0sYL9is0G==/" - "base.apk"), - "com.google.android.webview"); - EXPECT_EQ(PackageFromLocation(&storage, - "/data/app/" - "com.google.android.apps.wellbeing-" - "qfQCaB4uJ7P0OPpZQqOu0Q==/oat/arm64/base.odex"), + std::unique_ptr<TraceStorage> storage(new TraceStorage()); + + const char data_app_path[] = + "/data/app/org.perfetto.test-6XfQhnaSkFwGK0sYL9is0G==/base.apk"; + EXPECT_EQ(PackageFromLocation(storage.get(), data_app_path), + "org.perfetto.test"); + + const char with_extra_dir[] = + "/data/app/~~ASDFGH1234QWerT==/" + "com.perfetto.test-MNBVCX7890SDTst6==/test.apk"; + EXPECT_EQ(PackageFromLocation(storage.get(), with_extra_dir), + "com.perfetto.test"); + + const char odex[] = + "/data/app/com.google.android.apps.wellbeing-" + "qfQCaB4uJ7P0OPpZQqOu0Q==/oat/arm64/base.odex"; + EXPECT_EQ(PackageFromLocation(storage.get(), odex), "com.google.android.apps.wellbeing"); + + const char inmem_dex[] = + "[anon:dalvik-classes.dex extracted in memory from " + "/data/app/~~uUgHYtbjPNr2VFa3byIF4Q==/" + "com.perfetto.example-aC94wTfXRC60l2HJU5YvjQ==/base.apk]"; + EXPECT_EQ(PackageFromLocation(storage.get(), inmem_dex), + "com.perfetto.example"); +} + +TEST(HeapGraphTrackerTest, PopulateNativeSize) { + constexpr uint64_t kSeqId = 1; + constexpr UniquePid kPid = 1; + constexpr int64_t kTimestamp = 1; + + TraceProcessorContext context; + context.storage.reset(new TraceStorage()); + context.process_tracker.reset(new ProcessTracker(&context)); + context.process_tracker->GetOrCreateProcess(kPid); + + HeapGraphTracker tracker(&context); + + StringPool::Id normal_kind = context.storage->InternString("KIND_NORMAL"); + + constexpr uint64_t kLocation = 0; + tracker.AddInternedLocationName(kSeqId, kLocation, + context.storage->InternString("location")); + + enum Fields : uint64_t { kReferent = 1, kThunk, kThis0, kNext }; + + tracker.AddInternedFieldName(kSeqId, kReferent, + "java.lang.ref.Reference.referent"); + tracker.AddInternedFieldName(kSeqId, kThunk, "sun.misc.Cleaner.thunk"); + tracker.AddInternedFieldName( + kSeqId, kThis0, + "libcore.util.NativeAllocationRegistry$CleanerThunk.this$0"); + tracker.AddInternedFieldName(kSeqId, kNext, "sun.misc.Cleaner.next"); + + enum Types : uint64_t { + kTypeBitmap = 1, + kTypeCleaner, + kTypeCleanerThunk, + kTypeNativeAllocationRegistry, + }; + + tracker.AddInternedType( + kSeqId, kTypeBitmap, + context.storage->InternString("android.graphics.Bitmap"), kLocation, + /*object_size=*/0, + /*reference_field_name_ids=*/{}, /*superclass_id=*/0, + /*classloader_id=*/0, /*no_reference_fields=*/false, + /*kind=*/normal_kind); + + tracker.AddInternedType( + kSeqId, kTypeCleaner, context.storage->InternString("sun.misc.Cleaner"), + kLocation, /*object_size=*/0, + /*reference_field_name_ids=*/{kReferent, kThunk, kNext}, /*superclass_id=*/0, + /*classloader_id=*/0, /*no_reference_fields=*/false, + /*kind=*/normal_kind); + + tracker.AddInternedType( + kSeqId, kTypeCleanerThunk, + context.storage->InternString( + "libcore.util.NativeAllocationRegistry$CleanerThunk"), + kLocation, /*object_size=*/0, + /*reference_field_name_ids=*/{kThis0}, /*superclass_id=*/0, + /*classloader_id=*/0, /*no_reference_fields=*/false, + /*kind=*/normal_kind); + + tracker.AddInternedType( + kSeqId, kTypeNativeAllocationRegistry, + context.storage->InternString("libcore.util.NativeAllocationRegistry"), + kLocation, /*object_size=*/0, + /*reference_field_name_ids=*/{}, /*superclass_id=*/0, + /*classloader_id=*/0, /*no_reference_fields=*/false, + /*kind=*/normal_kind); + + enum Objects : uint64_t { + kObjBitmap = 1, + kObjCleaner, + kObjThunk, + kObjNativeAllocationRegistry, + }; + + { + HeapGraphTracker::SourceObject obj; + obj.object_id = kObjBitmap; + obj.type_id = kTypeBitmap; + + tracker.AddObject(kSeqId, kPid, kTimestamp, std::move(obj)); + } + + { + HeapGraphTracker::SourceObject obj; + obj.object_id = kObjCleaner; + obj.type_id = kTypeCleaner; + obj.referred_objects = {kObjBitmap, kObjThunk, 0}; + + tracker.AddObject(kSeqId, kPid, kTimestamp, std::move(obj)); + } + + { + HeapGraphTracker::SourceObject obj; + obj.object_id = kObjThunk; + obj.type_id = kTypeCleanerThunk; + obj.referred_objects = {kObjNativeAllocationRegistry}; + + tracker.AddObject(kSeqId, kPid, kTimestamp, std::move(obj)); + } + + { + HeapGraphTracker::SourceObject obj; + obj.object_id = kObjNativeAllocationRegistry; + obj.type_id = kTypeNativeAllocationRegistry; + + // NativeAllocationRegistry.size least significant bit is used to encode the + // source of the allocation (1: malloc, 0: other). + obj.native_allocation_registry_size = 24242 | 1; + + tracker.AddObject(kSeqId, kPid, kTimestamp, std::move(obj)); + } + + tracker.FinalizeProfile(kSeqId); + + const auto& objs_table = context.storage->heap_graph_object_table(); + const auto& class_table = context.storage->heap_graph_class_table(); + size_t count_bitmaps = 0; + for (uint32_t obj_row = 0; obj_row < objs_table.row_count(); ++obj_row) { + base::Optional<uint32_t> class_row = + class_table.id().IndexOf(objs_table.type_id()[obj_row]); + ASSERT_TRUE(class_row.has_value()); + if (context.storage->string_pool().Get(class_table.name()[*class_row]) == + "android.graphics.Bitmap") { + EXPECT_EQ(objs_table.native_size()[obj_row], 24242); + count_bitmaps++; + } else { + EXPECT_EQ(objs_table.native_size()[obj_row], 0) + << context.storage->string_pool() + .Get(class_table.name()[*class_row]) + .c_str() + << " has non zero native_size"; + } + } + EXPECT_EQ(count_bitmaps, 1u); } TEST(HeapGraphTrackerTest, BuildFlamegraph) { @@ -59,6 +204,8 @@ TEST(HeapGraphTrackerTest, BuildFlamegraph) { TraceProcessorContext context; context.storage.reset(new TraceStorage()); + context.process_tracker.reset(new ProcessTracker(&context)); + context.process_tracker->GetOrCreateProcess(kPid); HeapGraphTracker tracker(&context); |