• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2020 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/proto/profiler_util.h"
18 
19 #include "perfetto/ext/base/optional.h"
20 #include "perfetto/ext/base/string_utils.h"
21 #include "src/trace_processor/storage/trace_storage.h"
22 
23 namespace perfetto {
24 namespace trace_processor {
25 namespace {
26 
PackageFromApp(base::StringView location)27 base::Optional<base::StringView> PackageFromApp(base::StringView location) {
28   location = location.substr(base::StringView("/data/app/").size());
29   size_t start = 0;
30   if (location.at(0) == '~') {
31     size_t slash = location.find('/');
32     if (slash == std::string::npos) {
33       return base::nullopt;
34     }
35     start = slash + 1;
36   }
37   size_t end = location.find('/', start + 1);
38   if (end == std::string::npos) {
39     return base::nullopt;
40   }
41   location = location.substr(start, end);
42   size_t minus = location.find('-');
43   if (minus == std::string::npos) {
44     return base::nullopt;
45   }
46   return location.substr(0, minus);
47 }
48 
49 }  // namespace
50 
PackageFromLocation(TraceStorage * storage,base::StringView location)51 base::Optional<std::string> PackageFromLocation(TraceStorage* storage,
52                                                 base::StringView location) {
53   // List of some hardcoded apps that do not follow the scheme used in
54   // PackageFromApp. Ask for yours to be added.
55   //
56   // TODO(b/153632336): Get rid of the hardcoded list of system apps.
57   base::StringView sysui(
58       "/system_ext/priv-app/SystemUIGoogle/SystemUIGoogle.apk");
59   if (location.size() >= sysui.size() &&
60       location.substr(0, sysui.size()) == sysui) {
61     return "com.android.systemui";
62   }
63 
64   base::StringView phonesky("/product/priv-app/Phonesky/Phonesky.apk");
65   if (location.size() >= phonesky.size() &&
66       location.substr(0, phonesky.size()) == phonesky) {
67     return "com.android.vending";
68   }
69 
70   base::StringView maps("/product/app/Maps/Maps.apk");
71   if (location.size() >= maps.size() &&
72       location.substr(0, maps.size()) == maps) {
73     return "com.google.android.apps.maps";
74   }
75 
76   base::StringView launcher(
77       "/system_ext/priv-app/NexusLauncherRelease/NexusLauncherRelease.apk");
78   if (location.size() >= launcher.size() &&
79       location.substr(0, launcher.size()) == launcher) {
80     return "com.google.android.apps.nexuslauncher";
81   }
82 
83   base::StringView photos("/product/app/Photos/Photos.apk");
84   if (location.size() >= photos.size() &&
85       location.substr(0, photos.size()) == photos) {
86     return "com.google.android.apps.photos";
87   }
88 
89   base::StringView wellbeing(
90       "/product/priv-app/WellbeingPrebuilt/WellbeingPrebuilt.apk");
91   if (location.size() >= wellbeing.size() &&
92       location.substr(0, wellbeing.size()) == wellbeing) {
93     return "com.google.android.apps.wellbeing";
94   }
95 
96   if (location.find("DevicePersonalizationPrebuilt") !=
97           base::StringView::npos ||
98       location.find("MatchMaker") != base::StringView::npos) {
99     return "com.google.android.as";
100   }
101 
102   base::StringView gm("/product/app/PrebuiltGmail/PrebuiltGmail.apk");
103   if (location.size() >= gm.size() && location.substr(0, gm.size()) == gm) {
104     return "com.google.android.gm";
105   }
106 
107   if (location.find("PrebuiltGmsCore") != std::string::npos) {
108     return "com.google.android.gms";
109   }
110 
111   base::StringView velvet("/product/priv-app/Velvet/Velvet.apk");
112   if (location.size() >= velvet.size() &&
113       location.substr(0, velvet.size()) == velvet) {
114     return "com.google.android.googlequicksearchbox";
115   }
116 
117   base::StringView inputmethod(
118       "/product/app/LatinIMEGooglePrebuilt/LatinIMEGooglePrebuilt.apk");
119   if (location.size() >= inputmethod.size() &&
120       location.substr(0, inputmethod.size()) == inputmethod) {
121     return "com.google.android.inputmethod.latin";
122   }
123 
124   base::StringView messaging("/product/app/PrebuiltBugle/PrebuiltBugle.apk");
125   if (location.size() >= messaging.size() &&
126       location.substr(0, messaging.size()) == messaging) {
127     return "com.google.android.apps.messaging";
128   }
129 
130   base::StringView data_app("/data/app/");
131   if (location.substr(0, data_app.size()) == data_app) {
132     auto package = PackageFromApp(location);
133     if (!package) {
134       PERFETTO_DLOG("Failed to parse %s", location.ToStdString().c_str());
135       storage->IncrementStats(stats::deobfuscate_location_parse_error);
136       return base::nullopt;
137     }
138     return package->ToStdString();
139   }
140   return base::nullopt;
141 }
142 
FullyQualifiedDeobfuscatedName(protos::pbzero::ObfuscatedClass::Decoder & cls,protos::pbzero::ObfuscatedMember::Decoder & member)143 std::string FullyQualifiedDeobfuscatedName(
144     protos::pbzero::ObfuscatedClass::Decoder& cls,
145     protos::pbzero::ObfuscatedMember::Decoder& member) {
146   std::string member_deobfuscated_name =
147       member.deobfuscated_name().ToStdString();
148   if (base::Contains(member_deobfuscated_name, '.')) {
149     // Fully qualified name.
150     return member_deobfuscated_name;
151   } else {
152     // Name relative to class.
153     return cls.deobfuscated_name().ToStdString() + "." +
154            member_deobfuscated_name;
155   }
156 }
157 
158 }  // namespace trace_processor
159 }  // namespace perfetto
160