• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2011 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 package com.android.settings.net;
18 
19 import android.content.Context;
20 import android.content.pm.ApplicationInfo;
21 import android.content.pm.PackageInfo;
22 import android.content.pm.PackageManager;
23 import android.content.pm.PackageManager.NameNotFoundException;
24 import android.content.pm.UserInfo;
25 import android.content.res.Resources;
26 import android.graphics.drawable.Drawable;
27 import android.net.ConnectivityManager;
28 import android.net.TrafficStats;
29 import android.os.UserManager;
30 import android.text.TextUtils;
31 import android.util.SparseArray;
32 
33 import com.android.settings.R;
34 import com.android.settings.Utils;
35 import com.android.settings.users.UserUtils;
36 
37 /**
38  * Return details about a specific UID, handling special cases like
39  * {@link TrafficStats#UID_TETHERING} and {@link UserInfo}.
40  */
41 public class UidDetailProvider {
42     private final Context mContext;
43     private final SparseArray<UidDetail> mUidDetailCache;
44 
buildKeyForUser(int userHandle)45     public static int buildKeyForUser(int userHandle) {
46         return -(2000 + userHandle);
47     }
48 
UidDetailProvider(Context context)49     public UidDetailProvider(Context context) {
50         mContext = context.getApplicationContext();
51         mUidDetailCache = new SparseArray<UidDetail>();
52     }
53 
clearCache()54     public void clearCache() {
55         synchronized (mUidDetailCache) {
56             mUidDetailCache.clear();
57         }
58     }
59 
60     /**
61      * Resolve best descriptive label for the given UID.
62      */
getUidDetail(int uid, boolean blocking)63     public UidDetail getUidDetail(int uid, boolean blocking) {
64         UidDetail detail;
65 
66         synchronized (mUidDetailCache) {
67             detail = mUidDetailCache.get(uid);
68         }
69 
70         if (detail != null) {
71             return detail;
72         } else if (!blocking) {
73             return null;
74         }
75 
76         detail = buildUidDetail(uid);
77 
78         synchronized (mUidDetailCache) {
79             mUidDetailCache.put(uid, detail);
80         }
81 
82         return detail;
83     }
84 
85     /**
86      * Build {@link UidDetail} object, blocking until all {@link Drawable}
87      * lookup is finished.
88      */
buildUidDetail(int uid)89     private UidDetail buildUidDetail(int uid) {
90         final Resources res = mContext.getResources();
91         final PackageManager pm = mContext.getPackageManager();
92 
93         final UidDetail detail = new UidDetail();
94         detail.label = pm.getNameForUid(uid);
95         detail.icon = pm.getDefaultActivityIcon();
96 
97         // handle special case labels
98         switch (uid) {
99             case android.os.Process.SYSTEM_UID:
100                 detail.label = res.getString(R.string.process_kernel_label);
101                 detail.icon = pm.getDefaultActivityIcon();
102                 return detail;
103             case TrafficStats.UID_REMOVED:
104                 detail.label = res.getString(UserManager.supportsMultipleUsers()
105                         ? R.string.data_usage_uninstalled_apps_users
106                         : R.string.data_usage_uninstalled_apps);
107                 detail.icon = pm.getDefaultActivityIcon();
108                 return detail;
109             case TrafficStats.UID_TETHERING:
110                 final ConnectivityManager cm = (ConnectivityManager) mContext.getSystemService(
111                         Context.CONNECTIVITY_SERVICE);
112                 detail.label = res.getString(Utils.getTetheringLabel(cm));
113                 detail.icon = pm.getDefaultActivityIcon();
114                 return detail;
115         }
116 
117         // Handle keys that are actually user handles
118         if (uid <= -2000) {
119             final int userHandle = (-uid) - 2000;
120             final UserManager um = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
121             final UserInfo info = um.getUserInfo(userHandle);
122             if (info != null) {
123                 detail.label = res.getString(R.string.running_process_item_user_label, info.name);
124                 detail.icon = UserUtils.getUserIcon(um, info, res);
125                 return detail;
126             }
127         }
128 
129         // otherwise fall back to using packagemanager labels
130         final String[] packageNames = pm.getPackagesForUid(uid);
131         final int length = packageNames != null ? packageNames.length : 0;
132         try {
133             if (length == 1) {
134                 final ApplicationInfo info = pm.getApplicationInfo(packageNames[0], 0);
135                 detail.label = info.loadLabel(pm).toString();
136                 detail.icon = info.loadIcon(pm);
137             } else if (length > 1) {
138                 detail.detailLabels = new CharSequence[length];
139                 for (int i = 0; i < length; i++) {
140                     final String packageName = packageNames[i];
141                     final PackageInfo packageInfo = pm.getPackageInfo(packageName, 0);
142                     final ApplicationInfo appInfo = pm.getApplicationInfo(packageName, 0);
143 
144                     detail.detailLabels[i] = appInfo.loadLabel(pm).toString();
145                     if (packageInfo.sharedUserLabel != 0) {
146                         detail.label = pm.getText(packageName, packageInfo.sharedUserLabel,
147                                 packageInfo.applicationInfo).toString();
148                         detail.icon = appInfo.loadIcon(pm);
149                     }
150                 }
151             }
152         } catch (NameNotFoundException e) {
153         }
154 
155         if (TextUtils.isEmpty(detail.label)) {
156             detail.label = Integer.toString(uid);
157         }
158 
159         return detail;
160     }
161 }
162