1 /*
2  * Copyright (C) 2022 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 "src/trace_processor/importers/common/args_translation_table.h"
18 
19 #include <optional>
20 
21 #include "src/trace_processor/importers/common/deobfuscation_mapping_table.h"
22 #include "test/gtest_and_gmock.h"
23 
24 namespace perfetto {
25 namespace trace_processor {
26 namespace {
27 
TEST(ArgsTranslationTable,EmptyTableByDefault)28 TEST(ArgsTranslationTable, EmptyTableByDefault) {
29   TraceStorage storage;
30   ArgsTranslationTable table(&storage);
31   EXPECT_EQ(table.TranslateChromeHistogramHashForTesting(1), std::nullopt);
32   EXPECT_EQ(table.TranslateChromeUserEventHashForTesting(1), std::nullopt);
33 }
34 
TEST(ArgsTranslationTable,TranslatesHistogramHashes)35 TEST(ArgsTranslationTable, TranslatesHistogramHashes) {
36   TraceStorage storage;
37   ArgsTranslationTable table(&storage);
38   table.AddChromeHistogramTranslationRule(1, "hash1");
39   table.AddChromeHistogramTranslationRule(10, "hash2");
40   EXPECT_EQ(table.TranslateChromeHistogramHashForTesting(1),
41             std::optional<base::StringView>("hash1"));
42   EXPECT_EQ(table.TranslateChromeHistogramHashForTesting(10),
43             std::optional<base::StringView>("hash2"));
44   EXPECT_EQ(table.TranslateChromeHistogramHashForTesting(2), std::nullopt);
45 }
46 
TEST(ArgsTranslationTable,TranslatesUserEventHashes)47 TEST(ArgsTranslationTable, TranslatesUserEventHashes) {
48   TraceStorage storage;
49   ArgsTranslationTable table(&storage);
50   table.AddChromeUserEventTranslationRule(1, "action1");
51   table.AddChromeUserEventTranslationRule(10, "action2");
52   EXPECT_EQ(table.TranslateChromeUserEventHashForTesting(1),
53             std::optional<base::StringView>("action1"));
54   EXPECT_EQ(table.TranslateChromeUserEventHashForTesting(10),
55             std::optional<base::StringView>("action2"));
56   EXPECT_EQ(table.TranslateChromeUserEventHashForTesting(2), std::nullopt);
57 }
58 
TEST(ArgsTranslationTable,TranslatesPerformanceMarkSiteHashes)59 TEST(ArgsTranslationTable, TranslatesPerformanceMarkSiteHashes) {
60   TraceStorage storage;
61   ArgsTranslationTable table(&storage);
62   table.AddChromePerformanceMarkSiteTranslationRule(1, "hash1");
63   table.AddChromePerformanceMarkSiteTranslationRule(10, "hash2");
64   EXPECT_EQ(table.TranslateChromePerformanceMarkSiteHashForTesting(1),
65             std::optional<base::StringView>("hash1"));
66   EXPECT_EQ(table.TranslateChromePerformanceMarkSiteHashForTesting(10),
67             std::optional<base::StringView>("hash2"));
68   EXPECT_EQ(table.TranslateChromePerformanceMarkSiteHashForTesting(2),
69             std::nullopt);
70 }
71 
TEST(ArgsTranslationTable,TranslatesPerformanceMarkMarkHashes)72 TEST(ArgsTranslationTable, TranslatesPerformanceMarkMarkHashes) {
73   TraceStorage storage;
74   ArgsTranslationTable table(&storage);
75   table.AddChromePerformanceMarkMarkTranslationRule(1, "hash1");
76   table.AddChromePerformanceMarkMarkTranslationRule(10, "hash2");
77   EXPECT_EQ(table.TranslateChromePerformanceMarkMarkHashForTesting(1),
78             std::optional<base::StringView>("hash1"));
79   EXPECT_EQ(table.TranslateChromePerformanceMarkMarkHashForTesting(10),
80             std::optional<base::StringView>("hash2"));
81   EXPECT_EQ(table.TranslateChromePerformanceMarkMarkHashForTesting(2),
82             std::nullopt);
83 }
84 
TEST(ArgsTranslationTable,TranslatesStudyHashes)85 TEST(ArgsTranslationTable, TranslatesStudyHashes) {
86   TraceStorage storage;
87   ArgsTranslationTable table(&storage);
88   table.AddChromeStudyTranslationRule(1, "hash1");
89   table.AddChromeStudyTranslationRule(10, "hash2");
90   EXPECT_EQ(table.TranslateChromeStudyHashForTesting(1),
91             std::optional<base::StringView>("hash1"));
92   EXPECT_EQ(table.TranslateChromeStudyHashForTesting(10),
93             std::optional<base::StringView>("hash2"));
94   EXPECT_EQ(table.TranslateChromeStudyHashForTesting(2), std::nullopt);
95 }
96 
TEST(ArgsTranslationTable,TranslateClassName)97 TEST(ArgsTranslationTable, TranslateClassName) {
98   TraceStorage storage;
99   StringId xyz_id = storage.InternString("xyz");
100   StringId abc_id = storage.InternString("abc");
101   StringId class_x_id = storage.InternString("class_X");
102   DeobfuscationMappingTable deobfuscation_mapping;
103   deobfuscation_mapping.AddClassTranslation(
104       DeobfuscationMappingTable::PackageId{"app", 123}, xyz_id, class_x_id,
105       base::FlatHashMap<StringId, StringId>{});
106   ArgsTranslationTable table(&storage);
107   table.AddDeobfuscationMappingTable(std::move(deobfuscation_mapping));
108 
109   EXPECT_EQ(table.TranslateClassNameForTesting(xyz_id),
110             std::optional<StringId>(class_x_id));
111   EXPECT_EQ(table.TranslateClassNameForTesting(abc_id), std::nullopt);
112 }
113 
TEST(ArgsTranslationTable,NeedsTranslation)114 TEST(ArgsTranslationTable, NeedsTranslation) {
115   TraceStorage storage;
116   ArgsTranslationTable table(&storage);
117 
118   EXPECT_TRUE(table.NeedsTranslation(
119       storage.InternString("unused_flat_key"),
120       storage.InternString("chrome_histogram_sample.name_hash"),
121       Variadic::Type::kUint));
122   EXPECT_TRUE(table.NeedsTranslation(
123       storage.InternString("unused_flat_key"),
124       storage.InternString("chrome_user_event.action_hash"),
125       Variadic::Type::kUint));
126   EXPECT_TRUE(table.NeedsTranslation(
127       storage.InternString("unused_flat_key"),
128       storage.InternString("chrome_hashed_performance_mark.site_hash"),
129       Variadic::Type::kUint));
130   EXPECT_TRUE(table.NeedsTranslation(
131       storage.InternString("unused_flat_key"),
132       storage.InternString("chrome_hashed_performance_mark.mark_hash"),
133       Variadic::Type::kUint));
134 
135   // A real life case, where flat_key == key.
136   EXPECT_TRUE(table.NeedsTranslation(
137       storage.InternString("chrome_histogram_sample.name_hash"),
138       storage.InternString("chrome_histogram_sample.name_hash"),
139       Variadic::Type::kUint));
140   EXPECT_TRUE(table.NeedsTranslation(
141       storage.InternString("chrome_user_event.action_hash"),
142       storage.InternString("chrome_user_event.action_hash"),
143       Variadic::Type::kUint));
144   EXPECT_TRUE(table.NeedsTranslation(
145       storage.InternString("chrome_hashed_performance_mark.site_hash"),
146       storage.InternString("chrome_hashed_performance_mark.site_hash"),
147       Variadic::Type::kUint));
148   EXPECT_TRUE(table.NeedsTranslation(
149       storage.InternString("chrome_hashed_performance_mark.mark_hash"),
150       storage.InternString("chrome_hashed_performance_mark.mark_hash"),
151       Variadic::Type::kUint));
152 
153   // The key needs translation, but the arg type is wrong (not uint).
154   EXPECT_FALSE(table.NeedsTranslation(
155       storage.InternString("unused_flat_key"),
156       storage.InternString("chrome_histogram_sample.name_hash"),
157       Variadic::Type::kInt));
158   // The key does not require translation.
159   EXPECT_FALSE(table.NeedsTranslation(
160       storage.InternString("unused_flat_key"),
161       storage.InternString("chrome_histogram_sample.name"),
162       Variadic::Type::kUint));
163 
164   // The key needs translation by flat_key.
165   EXPECT_TRUE(table.NeedsTranslation(
166       storage.InternString("android_view_dump.activity.view.class_name"),
167       storage.InternString("android_view_dump.activity[0].view[0].class_name"),
168       Variadic::Type::kString));
169   // The key does not require translation because flat_key and key are swapped.
170   EXPECT_FALSE(table.NeedsTranslation(
171       storage.InternString("android_view_dump.activity[0].view[0].class_name"),
172       storage.InternString("android_view_dump.activity.view.class_name"),
173       Variadic::Type::kString));
174 }
175 
176 }  // namespace
177 }  // namespace trace_processor
178 }  // namespace perfetto
179