diff options
author | Amit Pundir <amit.pundir@linaro.org> | 2013-09-12 01:41:54 +0530 |
---|---|---|
committer | Amit Pundir <amit.pundir@linaro.org> | 2013-09-12 01:41:54 +0530 |
commit | 24e70286545561e19d60f250dffff304eda74686 (patch) | |
tree | 70f2e7089ddd52d63ae2a8c5b421c52757900ab0 | |
parent | 161d8a6ad7edcfda770feca26c572da6d2ad8ff2 (diff) | |
parent | 36ebb70df6f2e7c62adc9bd8372293a2194d6516 (diff) | |
download | base-24e70286545561e19d60f250dffff304eda74686.tar.gz |
Merge android-4.3_r2.2:
Android 4.3 release 2.2
# gpg: directory `/home/pundiramit/.gnupg' created
# gpg: new configuration file `/home/pundiramit/.gnupg/gpg.conf' created
# gpg: WARNING: options in `/home/pundiramit/.gnupg/gpg.conf' are not yet active during this run
# gpg: keyring `/home/pundiramit/.gnupg/pubring.gpg' created
# gpg: Signature made Wednesday 21 August 2013 03:35:49 AM IST using DSA key ID 9AB10E78
# gpg: Can't check signature: public key not found
* tag 'android-4.3_r2.2':
Use hostname verifier directly instead of instance DO NOT MERGE
Fix issue #10226007: Reset apps restores most of the changed settings...
Add new app ops method to reset all op modes.
Revert "Add version identifier to app ops."
Add version identifier to app ops.
Allow the user to block notifications for foreground services.
(DO NOT MERGE) Fix pub issue #58043: Copy crash in Android 4.3...
7 files changed, 138 insertions, 40 deletions
diff --git a/core/java/android/app/ActivityManager.java b/core/java/android/app/ActivityManager.java index 443cb65ff36a..944da9eb6f9c 100644 --- a/core/java/android/app/ActivityManager.java +++ b/core/java/android/app/ActivityManager.java @@ -16,6 +16,7 @@ package android.app; +import android.R; import com.android.internal.app.IUsageStats; import com.android.internal.os.PkgUsageStats; import com.android.internal.util.MemInfoReader; @@ -369,9 +370,9 @@ public class ActivityManager { // Really brain dead right now -- just take this from the configured // vm heap size, and assume it is in megabytes and thus ends with "m". String vmHeapSize = SystemProperties.get("dalvik.vm.heapsize", "16m"); - return Integer.parseInt(vmHeapSize.substring(0, vmHeapSize.length()-1)); + return Integer.parseInt(vmHeapSize.substring(0, vmHeapSize.length() - 1)); } - + /** * Used by persistent processes to determine if they are running on a * higher-end device so should be okay using hardware drawing acceleration diff --git a/core/java/android/app/AppOpsManager.java b/core/java/android/app/AppOpsManager.java index c9776f17fc9a..4fcb18a84b4f 100644 --- a/core/java/android/app/AppOpsManager.java +++ b/core/java/android/app/AppOpsManager.java @@ -422,6 +422,14 @@ public class AppOpsManager { } } + /** @hide */ + public void resetAllModes() { + try { + mService.resetAllModes(); + } catch (RemoteException e) { + } + } + public void startWatchingMode(int op, String packageName, final Callback callback) { synchronized (mModeWatchers) { IAppOpsCallback cb = mModeWatchers.get(callback); diff --git a/core/java/android/net/SSLCertificateSocketFactory.java b/core/java/android/net/SSLCertificateSocketFactory.java index 2a2f7cf81f84..0fe5cc415c6a 100644 --- a/core/java/android/net/SSLCertificateSocketFactory.java +++ b/core/java/android/net/SSLCertificateSocketFactory.java @@ -81,9 +81,6 @@ public class SSLCertificateSocketFactory extends SSLSocketFactory { } }; - private static final HostnameVerifier HOSTNAME_VERIFIER = - HttpsURLConnection.getDefaultHostnameVerifier(); - private SSLSocketFactory mInsecureFactory = null; private SSLSocketFactory mSecureFactory = null; private TrustManager[] mTrustManagers = null; @@ -195,7 +192,7 @@ public class SSLCertificateSocketFactory extends SSLSocketFactory { if (session == null) { throw new SSLException("Cannot verify SSL socket without session"); } - if (!HOSTNAME_VERIFIER.verify(hostname, session)) { + if (!HttpsURLConnection.getDefaultHostnameVerifier().verify(hostname, session)) { throw new SSLPeerUnverifiedException("Cannot verify hostname: " + hostname); } } diff --git a/core/java/com/android/internal/app/IAppOpsService.aidl b/core/java/com/android/internal/app/IAppOpsService.aidl index a9da86376153..cfd9cc7cb071 100644 --- a/core/java/com/android/internal/app/IAppOpsService.aidl +++ b/core/java/com/android/internal/app/IAppOpsService.aidl @@ -33,4 +33,5 @@ interface IAppOpsService { List<AppOpsManager.PackageOps> getPackagesForOps(in int[] ops); List<AppOpsManager.PackageOps> getOpsForPackage(int uid, String packageName, in int[] ops); void setMode(int code, int uid, String packageName, int mode); + void resetAllModes(); } diff --git a/services/java/com/android/server/AppOpsService.java b/services/java/com/android/server/AppOpsService.java index a402642bc0de..a55fddcd7ed8 100644 --- a/services/java/com/android/server/AppOpsService.java +++ b/services/java/com/android/server/AppOpsService.java @@ -27,6 +27,7 @@ import java.util.ArrayList; import java.util.HashMap; import java.util.Iterator; import java.util.List; +import java.util.Map; import android.app.AppOpsManager; import android.content.Context; @@ -42,6 +43,7 @@ import android.os.ServiceManager; import android.os.UserHandle; import android.util.AtomicFile; import android.util.Log; +import android.util.Pair; import android.util.Slog; import android.util.SparseArray; import android.util.TimeUtils; @@ -288,6 +290,24 @@ public class AppOpsService extends IAppOpsService.Stub { } } + private void pruneOp(Op op, int uid, String packageName) { + if (op.time == 0 && op.rejectTime == 0) { + Ops ops = getOpsLocked(uid, packageName, false); + if (ops != null) { + ops.remove(op.op); + if (ops.size() <= 0) { + HashMap<String, Ops> pkgOps = mUidOps.get(uid); + if (pkgOps != null) { + pkgOps.remove(ops.packageName); + if (pkgOps.size() <= 0) { + mUidOps.remove(uid); + } + } + } + } + } + } + @Override public void setMode(int code, int uid, String packageName, int mode) { verifyIncomingUid(uid); @@ -316,21 +336,7 @@ public class AppOpsService extends IAppOpsService.Stub { if (mode == AppOpsManager.MODE_ALLOWED) { // If going into the default mode, prune this op // if there is nothing else interesting in it. - if (op.time == 0 && op.rejectTime == 0) { - Ops ops = getOpsLocked(uid, packageName, false); - if (ops != null) { - ops.remove(op.op); - if (ops.size() <= 0) { - HashMap<String, Ops> pkgOps = mUidOps.get(uid); - if (pkgOps != null) { - pkgOps.remove(ops.packageName); - if (pkgOps.size() <= 0) { - mUidOps.remove(uid); - } - } - } - } - } + pruneOp(op, uid, packageName); } scheduleWriteNowLocked(); } @@ -346,6 +352,82 @@ public class AppOpsService extends IAppOpsService.Stub { } } + private static HashMap<Callback, ArrayList<Pair<String, Integer>>> addCallbacks( + HashMap<Callback, ArrayList<Pair<String, Integer>>> callbacks, + String packageName, int op, ArrayList<Callback> cbs) { + if (cbs == null) { + return callbacks; + } + if (callbacks == null) { + callbacks = new HashMap<Callback, ArrayList<Pair<String, Integer>>>(); + } + for (int i=0; i<cbs.size(); i++) { + Callback cb = cbs.get(i); + ArrayList<Pair<String, Integer>> reports = callbacks.get(cb); + if (reports == null) { + reports = new ArrayList<Pair<String, Integer>>(); + callbacks.put(cb, reports); + } + reports.add(new Pair<String, Integer>(packageName, op)); + } + return callbacks; + } + + @Override + public void resetAllModes() { + mContext.enforcePermission(android.Manifest.permission.UPDATE_APP_OPS_STATS, + Binder.getCallingPid(), Binder.getCallingUid(), null); + HashMap<Callback, ArrayList<Pair<String, Integer>>> callbacks = null; + synchronized (this) { + boolean changed = false; + for (int i=mUidOps.size()-1; i>=0; i--) { + HashMap<String, Ops> packages = mUidOps.valueAt(i); + Iterator<Map.Entry<String, Ops>> it = packages.entrySet().iterator(); + while (it.hasNext()) { + Map.Entry<String, Ops> ent = it.next(); + String packageName = ent.getKey(); + Ops pkgOps = ent.getValue(); + for (int j=pkgOps.size()-1; j>=0; j--) { + Op curOp = pkgOps.valueAt(j); + if (curOp.mode != AppOpsManager.MODE_ALLOWED) { + curOp.mode = AppOpsManager.MODE_ALLOWED; + changed = true; + callbacks = addCallbacks(callbacks, packageName, curOp.op, + mOpModeWatchers.get(curOp.op)); + callbacks = addCallbacks(callbacks, packageName, curOp.op, + mPackageModeWatchers.get(packageName)); + if (curOp.time == 0 && curOp.rejectTime == 0) { + pkgOps.removeAt(j); + } + } + } + if (pkgOps.size() == 0) { + it.remove(); + } + } + if (packages.size() == 0) { + mUidOps.removeAt(i); + } + } + if (changed) { + scheduleWriteNowLocked(); + } + } + if (callbacks != null) { + for (Map.Entry<Callback, ArrayList<Pair<String, Integer>>> ent : callbacks.entrySet()) { + Callback cb = ent.getKey(); + ArrayList<Pair<String, Integer>> reports = ent.getValue(); + for (int i=0; i<reports.size(); i++) { + Pair<String, Integer> rep = reports.get(i); + try { + cb.mCallback.opChanged(rep.second, rep.first); + } catch (RemoteException e) { + } + } + } + } + } + @Override public void startWatchingMode(int op, String packageName, IAppOpsCallback callback) { synchronized (this) { diff --git a/services/java/com/android/server/ClipboardService.java b/services/java/com/android/server/ClipboardService.java index 058857ddb605..0bf03b5ff453 100644 --- a/services/java/com/android/server/ClipboardService.java +++ b/services/java/com/android/server/ClipboardService.java @@ -154,31 +154,36 @@ public class ClipboardService extends IClipboard.Stub { if (clip != null && clip.getItemCount() <= 0) { throw new IllegalArgumentException("No items"); } - if (mAppOps.noteOp(AppOpsManager.OP_WRITE_CLIPBOARD, Binder.getCallingUid(), + final int callingUid = Binder.getCallingUid(); + if (mAppOps.noteOp(AppOpsManager.OP_WRITE_CLIPBOARD, callingUid, callingPackage) != AppOpsManager.MODE_ALLOWED) { return; } - checkDataOwnerLocked(clip, Binder.getCallingUid()); + checkDataOwnerLocked(clip, callingUid); clearActiveOwnersLocked(); PerUserClipboard clipboard = getClipboard(); clipboard.primaryClip = clip; + final long ident = Binder.clearCallingIdentity(); final int n = clipboard.primaryClipListeners.beginBroadcast(); - for (int i = 0; i < n; i++) { - try { - ListenerInfo li = (ListenerInfo) - clipboard.primaryClipListeners.getBroadcastCookie(i); - if (mAppOps.checkOpNoThrow(AppOpsManager.OP_READ_CLIPBOARD, li.mUid, - li.mPackageName) == AppOpsManager.MODE_ALLOWED) { - clipboard.primaryClipListeners.getBroadcastItem(i) - .dispatchPrimaryClipChanged(); + try { + for (int i = 0; i < n; i++) { + try { + ListenerInfo li = (ListenerInfo) + clipboard.primaryClipListeners.getBroadcastCookie(i); + if (mAppOps.checkOpNoThrow(AppOpsManager.OP_READ_CLIPBOARD, li.mUid, + li.mPackageName) == AppOpsManager.MODE_ALLOWED) { + clipboard.primaryClipListeners.getBroadcastItem(i) + .dispatchPrimaryClipChanged(); + } + } catch (RemoteException e) { + // The RemoteCallbackList will take care of removing + // the dead object for us. } - } catch (RemoteException e) { - - // The RemoteCallbackList will take care of removing - // the dead object for us. } + } finally { + clipboard.primaryClipListeners.finishBroadcast(); + Binder.restoreCallingIdentity(ident); } - clipboard.primaryClipListeners.finishBroadcast(); } } diff --git a/services/java/com/android/server/NotificationManagerService.java b/services/java/com/android/server/NotificationManagerService.java index 29aaeaf33f4f..29780c06e8e5 100644 --- a/services/java/com/android/server/NotificationManagerService.java +++ b/services/java/com/android/server/NotificationManagerService.java @@ -1606,7 +1606,7 @@ public class NotificationManagerService extends INotificationManager.Stub Slog.v(TAG, "enqueueNotificationInternal: pkg=" + pkg + " id=" + id + " notification=" + notification); } checkCallerIsSystemOrSameApp(pkg); - final boolean isSystemNotification = isCallerSystem() || ("android".equals(pkg)); + final boolean isSystemNotification = isUidSystem(callingUid) || ("android".equals(pkg)); userId = ActivityManager.handleIncomingUser(callingPid, callingUid, userId, true, false, "enqueueNotification", pkg); @@ -2084,14 +2084,18 @@ public class NotificationManagerService extends INotificationManager.Stub cancelAllNotificationsInt(pkg, 0, Notification.FLAG_FOREGROUND_SERVICE, true, userId); } - // Return true if the caller is a system or phone UID and therefore should not have + // Return true if the UID is a system or phone UID and therefore should not have // any notifications or toasts blocked. - boolean isCallerSystem() { - final int uid = Binder.getCallingUid(); + boolean isUidSystem(int uid) { final int appid = UserHandle.getAppId(uid); return (appid == Process.SYSTEM_UID || appid == Process.PHONE_UID || uid == 0); } + // same as isUidSystem(int, int) for the Binder caller's UID. + boolean isCallerSystem() { + return isUidSystem(Binder.getCallingUid()); + } + void checkCallerIsSystem() { if (isCallerSystem()) { return; |