use of android.util.ArraySet in project android_frameworks_base by DirtyUnicorns.
the class ArrayMapTests method run.
public static void run() {
HashMap<ControlledHash, Integer> hashMap = new HashMap<ControlledHash, Integer>();
ArrayMap<ControlledHash, Integer> arrayMap = new ArrayMap<ControlledHash, Integer>();
HashSet<ControlledHash> hashSet = new HashSet<ControlledHash>();
ArraySet<ControlledHash> arraySet = new ArraySet<ControlledHash>();
for (int i = 0; i < OPS.length; i++) {
Integer oldHash;
Integer oldArray;
boolean hashChanged;
boolean arrayChanged;
ControlledHash key = KEYS[i] < 0 ? null : new ControlledHash(KEYS[i]);
switch(OPS[i]) {
case OP_ADD:
Log.i("test", "Adding key: " + KEYS[i]);
oldHash = hashMap.put(key, i);
oldArray = arrayMap.put(key, i);
hashChanged = hashSet.add(key);
arrayChanged = arraySet.add(key);
break;
case OP_REM:
Log.i("test", "Removing key: " + KEYS[i]);
oldHash = hashMap.remove(key);
oldArray = arrayMap.remove(key);
hashChanged = hashSet.remove(key);
arrayChanged = arraySet.remove(key);
break;
default:
Log.e("test", "Bad operation " + OPS[i] + " @ " + i);
return;
}
if (!compare(oldHash, oldArray)) {
Log.e("test", "Bad result: expected " + oldHash + ", got " + oldArray);
dump(hashMap, arrayMap);
return;
}
if (hashChanged != arrayChanged) {
Log.e("test", "Bad change: expected " + hashChanged + ", got " + arrayChanged);
dump(hashSet, arraySet);
return;
}
if (!validateArrayMap(arrayMap)) {
dump(hashMap, arrayMap);
return;
}
if (!compareMaps(hashMap, arrayMap)) {
dump(hashMap, arrayMap);
return;
}
if (!compareSets(hashSet, arraySet)) {
dump(hashSet, arraySet);
return;
}
}
arrayMap.put(new ControlledHash(50000), 100);
ControlledHash lookup = new ControlledHash(50000);
Iterator<ControlledHash> it = arrayMap.keySet().iterator();
while (it.hasNext()) {
if (it.next().equals(lookup)) {
it.remove();
}
}
if (arrayMap.containsKey(lookup)) {
Log.e("test", "Bad map iterator: didn't remove test key");
dump(hashMap, arrayMap);
}
arraySet.add(new ControlledHash(50000));
it = arraySet.iterator();
while (it.hasNext()) {
if (it.next().equals(lookup)) {
it.remove();
}
}
if (arraySet.contains(lookup)) {
Log.e("test", "Bad set iterator: didn't remove test key");
dump(hashSet, arraySet);
}
if (!equalsMapTest()) {
return;
}
if (!equalsSetTest()) {
return;
}
// map copy constructor test
ArrayMap newMap = new ArrayMap<Integer, String>();
for (int i = 0; i < 10; ++i) {
newMap.put(i, String.valueOf(i));
}
ArrayMap mapCopy = new ArrayMap(newMap);
if (!compare(mapCopy, newMap)) {
Log.e("test", "ArrayMap copy constructor failure: expected " + newMap + ", got " + mapCopy);
dump(newMap, mapCopy);
return;
}
// set copy constructor test
ArraySet newSet = new ArraySet<Integer>();
for (int i = 0; i < 10; ++i) {
newSet.add(i);
}
ArraySet setCopy = new ArraySet(newSet);
if (!compare(setCopy, newSet)) {
Log.e("test", "ArraySet copy constructor failure: expected " + newSet + ", got " + setCopy);
dump(newSet, setCopy);
return;
}
Log.e("test", "Test successful; printing final map.");
dump(hashMap, arrayMap);
Log.e("test", "Test successful; printing final set.");
dump(hashSet, arraySet);
}
use of android.util.ArraySet in project android_frameworks_base by DirtyUnicorns.
the class ShortcutParser method parseShortcutsOneFile.
private static List<ShortcutInfo> parseShortcutsOneFile(ShortcutService service, ActivityInfo activityInfo, String packageName, @UserIdInt int userId, List<ShortcutInfo> result) throws IOException, XmlPullParserException {
if (ShortcutService.DEBUG) {
Slog.d(TAG, String.format("Checking main activity %s", activityInfo.getComponentName()));
}
XmlResourceParser parser = null;
try {
parser = service.injectXmlMetaData(activityInfo, METADATA_KEY);
if (parser == null) {
return result;
}
final ComponentName activity = new ComponentName(packageName, activityInfo.name);
final AttributeSet attrs = Xml.asAttributeSet(parser);
int type;
int rank = 0;
final int maxShortcuts = service.getMaxActivityShortcuts();
int numShortcuts = 0;
// We instantiate ShortcutInfo at <shortcut>, but we add it to the list at </shortcut>,
// after parsing <intent>. We keep the current one in here.
ShortcutInfo currentShortcut = null;
Set<String> categories = null;
final ArrayList<Intent> intents = new ArrayList<>();
outer: while ((type = parser.next()) != XmlPullParser.END_DOCUMENT && (type != XmlPullParser.END_TAG || parser.getDepth() > 0)) {
final int depth = parser.getDepth();
final String tag = parser.getName();
// When a shortcut tag is closing, publish.
if ((type == XmlPullParser.END_TAG) && (depth == 2) && (TAG_SHORTCUT.equals(tag))) {
if (currentShortcut == null) {
// Shortcut was invalid.
continue;
}
final ShortcutInfo si = currentShortcut;
// Make sure to null out for the next iteration.
currentShortcut = null;
if (si.isEnabled()) {
if (intents.size() == 0) {
Log.e(TAG, "Shortcut " + si.getId() + " has no intent. Skipping it.");
continue;
}
} else {
// Just set the default intent to disabled shortcuts.
intents.clear();
intents.add(new Intent(Intent.ACTION_VIEW));
}
if (numShortcuts >= maxShortcuts) {
Log.e(TAG, "More than " + maxShortcuts + " shortcuts found for " + activityInfo.getComponentName() + ". Skipping the rest.");
return result;
}
// Same flag as what TaskStackBuilder adds.
intents.get(0).addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK | Intent.FLAG_ACTIVITY_TASK_ON_HOME);
try {
si.setIntents(intents.toArray(new Intent[intents.size()]));
} catch (RuntimeException e) {
// This shouldn't happen because intents in XML can't have complicated
// extras, but just in case Intent.parseIntent() supports such a thing one
// day.
Log.e(TAG, "Shortcut's extras contain un-persistable values. Skipping it.");
continue;
}
intents.clear();
if (categories != null) {
si.setCategories(categories);
categories = null;
}
if (result == null) {
result = new ArrayList<>();
}
result.add(si);
numShortcuts++;
rank++;
if (ShortcutService.DEBUG) {
Slog.d(TAG, "Shortcut added: " + si.toInsecureString());
}
continue;
}
// Otherwise, just look at start tags.
if (type != XmlPullParser.START_TAG) {
continue;
}
if (depth == 1 && TAG_SHORTCUTS.equals(tag)) {
// Root tag.
continue;
}
if (depth == 2 && TAG_SHORTCUT.equals(tag)) {
final ShortcutInfo si = parseShortcutAttributes(service, attrs, packageName, activity, userId, rank);
if (si == null) {
// Shortcut was invalid.
continue;
}
if (ShortcutService.DEBUG) {
Slog.d(TAG, "Shortcut found: " + si.toInsecureString());
}
if (result != null) {
for (int i = result.size() - 1; i >= 0; i--) {
if (si.getId().equals(result.get(i).getId())) {
Log.e(TAG, "Duplicate shortcut ID detected. Skipping it.");
continue outer;
}
}
}
currentShortcut = si;
categories = null;
continue;
}
if (depth == 3 && TAG_INTENT.equals(tag)) {
if ((currentShortcut == null) || !currentShortcut.isEnabled()) {
Log.e(TAG, "Ignoring excessive intent tag.");
continue;
}
final Intent intent = Intent.parseIntent(service.mContext.getResources(), parser, attrs);
if (TextUtils.isEmpty(intent.getAction())) {
Log.e(TAG, "Shortcut intent action must be provided. activity=" + activity);
// Invalidate the current shortcut.
currentShortcut = null;
continue;
}
intents.add(intent);
continue;
}
if (depth == 3 && TAG_CATEGORIES.equals(tag)) {
if ((currentShortcut == null) || (currentShortcut.getCategories() != null)) {
continue;
}
final String name = parseCategories(service, attrs);
if (TextUtils.isEmpty(name)) {
Log.e(TAG, "Empty category found. activity=" + activity);
continue;
}
if (categories == null) {
categories = new ArraySet<>();
}
categories.add(name);
continue;
}
Log.w(TAG, String.format("Invalid tag '%s' found at depth %d", tag, depth));
}
} finally {
if (parser != null) {
parser.close();
}
}
return result;
}
use of android.util.ArraySet in project android_frameworks_base by DirtyUnicorns.
the class ProcessStats method collectProcessesLocked.
public ArrayList<ProcessState> collectProcessesLocked(int[] screenStates, int[] memStates, int[] procStates, int[] sortProcStates, long now, String reqPackage, boolean activeOnly) {
final ArraySet<ProcessState> foundProcs = new ArraySet<ProcessState>();
final ArrayMap<String, SparseArray<SparseArray<PackageState>>> pkgMap = mPackages.getMap();
for (int ip = 0; ip < pkgMap.size(); ip++) {
final String pkgName = pkgMap.keyAt(ip);
final SparseArray<SparseArray<PackageState>> procs = pkgMap.valueAt(ip);
for (int iu = 0; iu < procs.size(); iu++) {
final SparseArray<PackageState> vpkgs = procs.valueAt(iu);
final int NVERS = vpkgs.size();
for (int iv = 0; iv < NVERS; iv++) {
final PackageState state = vpkgs.valueAt(iv);
final int NPROCS = state.mProcesses.size();
final boolean pkgMatch = reqPackage == null || reqPackage.equals(pkgName);
for (int iproc = 0; iproc < NPROCS; iproc++) {
final ProcessState proc = state.mProcesses.valueAt(iproc);
if (!pkgMatch && !reqPackage.equals(proc.getName())) {
continue;
}
if (activeOnly && !proc.isInUse()) {
continue;
}
foundProcs.add(proc.getCommonProcess());
}
}
}
}
ArrayList<ProcessState> outProcs = new ArrayList<ProcessState>(foundProcs.size());
for (int i = 0; i < foundProcs.size(); i++) {
ProcessState proc = foundProcs.valueAt(i);
if (proc.computeProcessTimeLocked(screenStates, memStates, procStates, now) > 0) {
outProcs.add(proc);
if (procStates != sortProcStates) {
proc.computeProcessTimeLocked(screenStates, memStates, sortProcStates, now);
}
}
}
Collections.sort(outProcs, ProcessState.COMPARATOR);
return outProcs;
}
use of android.util.ArraySet in project android_frameworks_base by DirtyUnicorns.
the class PackageHelper method resolveInstallVolume.
/**
* Given a requested {@link PackageInfo#installLocation} and calculated
* install size, pick the actual volume to install the app. Only considers
* internal and private volumes, and prefers to keep an existing package on
* its current volume.
*
* @return the {@link VolumeInfo#fsUuid} to install onto, or {@code null}
* for internal storage.
*/
public static String resolveInstallVolume(Context context, String packageName, int installLocation, long sizeBytes) throws IOException {
final boolean forceAllowOnExternal = Settings.Global.getInt(context.getContentResolver(), Settings.Global.FORCE_ALLOW_ON_EXTERNAL, 0) != 0;
// TODO: handle existing apps installed in ASEC; currently assumes
// they'll end up back on internal storage
ApplicationInfo existingInfo = null;
try {
existingInfo = context.getPackageManager().getApplicationInfo(packageName, PackageManager.GET_UNINSTALLED_PACKAGES);
} catch (NameNotFoundException ignored) {
}
final StorageManager storageManager = context.getSystemService(StorageManager.class);
final boolean fitsOnInternal = fitsOnInternal(context, sizeBytes);
final ArraySet<String> allCandidates = new ArraySet<>();
VolumeInfo bestCandidate = null;
long bestCandidateAvailBytes = Long.MIN_VALUE;
for (VolumeInfo vol : storageManager.getVolumes()) {
if (vol.type == VolumeInfo.TYPE_PRIVATE && vol.isMountedWritable()) {
final long availBytes = storageManager.getStorageBytesUntilLow(new File(vol.path));
if (availBytes >= sizeBytes) {
allCandidates.add(vol.fsUuid);
}
if (availBytes >= bestCandidateAvailBytes) {
bestCandidate = vol;
bestCandidateAvailBytes = availBytes;
}
}
}
// System apps always forced to internal storage
if (existingInfo != null && existingInfo.isSystemApp()) {
installLocation = PackageInfo.INSTALL_LOCATION_INTERNAL_ONLY;
}
// If app expresses strong desire for internal storage, honor it
if (!forceAllowOnExternal && installLocation == PackageInfo.INSTALL_LOCATION_INTERNAL_ONLY) {
if (existingInfo != null && !Objects.equals(existingInfo.volumeUuid, StorageManager.UUID_PRIVATE_INTERNAL)) {
throw new IOException("Cannot automatically move " + packageName + " from " + existingInfo.volumeUuid + " to internal storage");
}
if (fitsOnInternal) {
return StorageManager.UUID_PRIVATE_INTERNAL;
} else {
throw new IOException("Requested internal only, but not enough space");
}
}
// If app already exists somewhere, we must stay on that volume
if (existingInfo != null) {
if (Objects.equals(existingInfo.volumeUuid, StorageManager.UUID_PRIVATE_INTERNAL) && fitsOnInternal) {
return StorageManager.UUID_PRIVATE_INTERNAL;
} else if (allCandidates.contains(existingInfo.volumeUuid)) {
return existingInfo.volumeUuid;
} else {
throw new IOException("Not enough space on existing volume " + existingInfo.volumeUuid + " for " + packageName + " upgrade");
}
}
// volume with most space
if (bestCandidate != null) {
return bestCandidate.fsUuid;
} else if (fitsOnInternal) {
return StorageManager.UUID_PRIVATE_INTERNAL;
} else {
throw new IOException("No special requests, but no room anywhere");
}
}
use of android.util.ArraySet in project android_frameworks_base by DirtyUnicorns.
the class TaskStack method computeComponentsRemoved.
/**
* Computes the components of tasks in this stack that have been removed as a result of a change
* in the specified package.
*/
public ArraySet<ComponentName> computeComponentsRemoved(String packageName, int userId) {
// Identify all the tasks that should be removed as a result of the package being removed.
// Using a set to ensure that we callback once per unique component.
SystemServicesProxy ssp = Recents.getSystemServices();
ArraySet<ComponentName> existingComponents = new ArraySet<>();
ArraySet<ComponentName> removedComponents = new ArraySet<>();
ArrayList<Task.TaskKey> taskKeys = getTaskKeys();
int taskKeyCount = taskKeys.size();
for (int i = 0; i < taskKeyCount; i++) {
Task.TaskKey t = taskKeys.get(i);
// Skip if this doesn't apply to the current user
if (t.userId != userId)
continue;
ComponentName cn = t.getComponent();
if (cn.getPackageName().equals(packageName)) {
if (existingComponents.contains(cn)) {
// If we know that the component still exists in the package, then skip
continue;
}
if (ssp.getActivityInfo(cn, userId) != null) {
existingComponents.add(cn);
} else {
removedComponents.add(cn);
}
}
}
return removedComponents;
}
Aggregations