summaryrefslogtreecommitdiffstats
path: root/services/core/java/com/android/server/location/LocationBlacklist.java
diff options
context:
space:
mode:
Diffstat (limited to 'services/core/java/com/android/server/location/LocationBlacklist.java')
-rw-r--r--services/core/java/com/android/server/location/LocationBlacklist.java151
1 files changed, 151 insertions, 0 deletions
diff --git a/services/core/java/com/android/server/location/LocationBlacklist.java b/services/core/java/com/android/server/location/LocationBlacklist.java
new file mode 100644
index 0000000..6f22689
--- /dev/null
+++ b/services/core/java/com/android/server/location/LocationBlacklist.java
@@ -0,0 +1,151 @@
+/*
+ * Copyright (C) 2012 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+package com.android.server.location;
+
+import android.content.Context;
+import android.database.ContentObserver;
+import android.os.Handler;
+import android.os.UserHandle;
+import android.provider.Settings;
+import android.util.Log;
+import android.util.Slog;
+
+import com.android.server.LocationManagerService;
+
+import java.io.PrintWriter;
+import java.util.ArrayList;
+import java.util.Arrays;
+
+/**
+ * Allows applications to be blacklisted from location updates at run-time.
+ *
+ * This is a silent blacklist. Applications can still call Location Manager
+ * API's, but they just won't receive any locations.
+ */
+public final class LocationBlacklist extends ContentObserver {
+ private static final String TAG = "LocationBlacklist";
+ private static final boolean D = LocationManagerService.D;
+ private static final String BLACKLIST_CONFIG_NAME = "locationPackagePrefixBlacklist";
+ private static final String WHITELIST_CONFIG_NAME = "locationPackagePrefixWhitelist";
+
+ private final Context mContext;
+ private final Object mLock = new Object();
+
+ // all fields below synchronized on mLock
+ private String[] mWhitelist = new String[0];
+ private String[] mBlacklist = new String[0];
+
+ private int mCurrentUserId = UserHandle.USER_OWNER;
+
+ public LocationBlacklist(Context context, Handler handler) {
+ super(handler);
+ mContext = context;
+ }
+
+ public void init() {
+ mContext.getContentResolver().registerContentObserver(Settings.Secure.getUriFor(
+ BLACKLIST_CONFIG_NAME), false, this, UserHandle.USER_ALL);
+// mContext.getContentResolver().registerContentObserver(Settings.Secure.getUriFor(
+// WHITELIST_CONFIG_NAME), false, this, UserHandle.USER_ALL);
+ reloadBlacklist();
+ }
+
+ private void reloadBlacklistLocked() {
+ mWhitelist = getStringArrayLocked(WHITELIST_CONFIG_NAME);
+ if (D) Slog.d(TAG, "whitelist: " + Arrays.toString(mWhitelist));
+ mBlacklist = getStringArrayLocked(BLACKLIST_CONFIG_NAME);
+ if (D) Slog.d(TAG, "blacklist: " + Arrays.toString(mBlacklist));
+ }
+
+ private void reloadBlacklist() {
+ synchronized (mLock) {
+ reloadBlacklistLocked();
+ }
+ }
+
+ /**
+ * Return true if in blacklist
+ * (package name matches blacklist, and does not match whitelist)
+ */
+ public boolean isBlacklisted(String packageName) {
+ synchronized (mLock) {
+ for (String black : mBlacklist) {
+ if (packageName.startsWith(black)) {
+ if (inWhitelist(packageName)) {
+ continue;
+ } else {
+ if (D) Log.d(TAG, "dropping location (blacklisted): "
+ + packageName + " matches " + black);
+ return true;
+ }
+ }
+ }
+ }
+ return false;
+ }
+
+ /**
+ * Return true if any of packages are in whitelist
+ */
+ private boolean inWhitelist(String pkg) {
+ synchronized (mLock) {
+ for (String white : mWhitelist) {
+ if (pkg.startsWith(white)) return true;
+ }
+ }
+ return false;
+ }
+
+ @Override
+ public void onChange(boolean selfChange) {
+ reloadBlacklist();
+ }
+
+ public void switchUser(int userId) {
+ synchronized(mLock) {
+ mCurrentUserId = userId;
+ reloadBlacklistLocked();
+ }
+ }
+
+ private String[] getStringArrayLocked(String key) {
+ String flatString;
+ synchronized(mLock) {
+ flatString = Settings.Secure.getStringForUser(mContext.getContentResolver(), key,
+ mCurrentUserId);
+ }
+ if (flatString == null) {
+ return new String[0];
+ }
+ String[] splitStrings = flatString.split(",");
+ ArrayList<String> result = new ArrayList<String>();
+ for (String pkg : splitStrings) {
+ pkg = pkg.trim();
+ if (pkg.isEmpty()) {
+ continue;
+ }
+ result.add(pkg);
+ }
+ return result.toArray(new String[result.size()]);
+ }
+
+ public void dump(PrintWriter pw) {
+ pw.println("mWhitelist=" + Arrays.toString(mWhitelist) + " mBlacklist=" +
+ Arrays.toString(mBlacklist));
+ }
+}