Merge "READ_SMS allows getLine1Number() [1/3]" into mnc-dev
diff --git a/api/current.txt b/api/current.txt
index 68ecf96..e16294e 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -3341,6 +3341,7 @@
method public boolean isImmersive();
method public boolean isTaskRoot();
method public boolean isVoiceInteraction();
+ method public boolean isVoiceInteractionRoot();
method public final deprecated android.database.Cursor managedQuery(android.net.Uri, java.lang.String[], java.lang.String, java.lang.String[], java.lang.String);
method public boolean moveTaskToBack(boolean);
method public boolean navigateUpTo(android.content.Intent);
diff --git a/api/system-current.txt b/api/system-current.txt
index 2e0613a..a784378 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -3444,6 +3444,7 @@
method public boolean isImmersive();
method public boolean isTaskRoot();
method public boolean isVoiceInteraction();
+ method public boolean isVoiceInteractionRoot();
method public final deprecated android.database.Cursor managedQuery(android.net.Uri, java.lang.String[], java.lang.String, java.lang.String[], java.lang.String);
method public boolean moveTaskToBack(boolean);
method public boolean navigateUpTo(android.content.Intent);
diff --git a/core/java/android/app/Activity.java b/core/java/android/app/Activity.java
index bdea608..3c8af0d 100644
--- a/core/java/android/app/Activity.java
+++ b/core/java/android/app/Activity.java
@@ -1229,6 +1229,22 @@
}
/**
+ * Like {@link #isVoiceInteraction}, but only returns true if this is also the root
+ * of a voice interaction. That is, returns true if this activity was directly
+ * started by the voice interaction service as the initiation of a voice interaction.
+ * Otherwise, for example if it was started by another activity while under voice
+ * interaction, returns false.
+ */
+ public boolean isVoiceInteractionRoot() {
+ try {
+ return mVoiceInteractor != null
+ && ActivityManagerNative.getDefault().isRootVoiceInteraction(mToken);
+ } catch (RemoteException e) {
+ }
+ return false;
+ }
+
+ /**
* Retrieve the active {@link VoiceInteractor} that the user is going through to
* interact with this activity.
*/
diff --git a/core/java/android/app/ActivityManagerNative.java b/core/java/android/app/ActivityManagerNative.java
index b758a7a..e144c29 100644
--- a/core/java/android/app/ActivityManagerNative.java
+++ b/core/java/android/app/ActivityManagerNative.java
@@ -2582,6 +2582,15 @@
reply.writeInt(res ? 1 : 0);
return true;
}
+
+ case IS_ROOT_VOICE_INTERACTION_TRANSACTION: {
+ data.enforceInterface(IActivityManager.descriptor);
+ IBinder token = data.readStrongBinder();
+ boolean res = isRootVoiceInteraction(token);
+ reply.writeNoException();
+ reply.writeInt(res ? 1 : 0);
+ return true;
+ }
}
return super.onTransact(code, data, reply, flags);
@@ -5962,5 +5971,19 @@
return res != 0;
}
+ @Override
+ public boolean isRootVoiceInteraction(IBinder token) throws RemoteException {
+ Parcel data = Parcel.obtain();
+ Parcel reply = Parcel.obtain();
+ data.writeInterfaceToken(IActivityManager.descriptor);
+ data.writeStrongBinder(token);
+ mRemote.transact(IS_ROOT_VOICE_INTERACTION_TRANSACTION, data, reply, 0);
+ reply.readException();
+ int res = reply.readInt();
+ data.recycle();
+ reply.recycle();
+ return res != 0;
+ }
+
private IBinder mRemote;
}
diff --git a/core/java/android/app/ApplicationPackageManager.java b/core/java/android/app/ApplicationPackageManager.java
index dbe91f9..0adce5d 100644
--- a/core/java/android/app/ApplicationPackageManager.java
+++ b/core/java/android/app/ApplicationPackageManager.java
@@ -777,7 +777,9 @@
public List<ProviderInfo> queryContentProviders(String processName,
int uid, int flags) {
try {
- return mPM.queryContentProviders(processName, uid, flags);
+ ParceledListSlice<ProviderInfo> slice
+ = mPM.queryContentProviders(processName, uid, flags);
+ return slice != null ? slice.getList() : null;
} catch (RemoteException e) {
throw new RuntimeException("Package manager has died", e);
}
diff --git a/core/java/android/app/IActivityManager.java b/core/java/android/app/IActivityManager.java
index 9ebbb9b..90216af 100644
--- a/core/java/android/app/IActivityManager.java
+++ b/core/java/android/app/IActivityManager.java
@@ -515,6 +515,8 @@
public boolean setProcessMemoryTrimLevel(String process, int uid, int level)
throws RemoteException;
+ public boolean isRootVoiceInteraction(IBinder token) throws RemoteException;
+
/*
* Private non-Binder interfaces
*/
@@ -861,4 +863,5 @@
int IS_SCREEN_CAPTURE_ALLOWED_ON_CURRENT_ACTIVITY_TRANSACTION
= IBinder.FIRST_CALL_TRANSACTION+299;
int SHOW_ASSIST_FROM_ACTIVITY_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+300;
+ int IS_ROOT_VOICE_INTERACTION_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+301;
}
diff --git a/core/java/android/app/Instrumentation.java b/core/java/android/app/Instrumentation.java
index c2d901d..69b8b95 100644
--- a/core/java/android/app/Instrumentation.java
+++ b/core/java/android/app/Instrumentation.java
@@ -1810,9 +1810,14 @@
throw new SecurityException(
"Starting under voice control not allowed for: " + intent);
case ActivityManager.START_NOT_CURRENT_USER_ACTIVITY:
- throw new SecurityException(
- "Not allowed to start background user activity that shouldn't be"
- + " displayed for all users.");
+ // Fail silently for this case so we don't break current apps.
+ // TODO(b/22929608): Instead of failing silently or throwing an exception,
+ // we should properly position the activity in the stack (i.e. behind all current
+ // user activity/task) and not change the positioning of stacks.
+ Log.e(TAG,
+ "Not allowed to start background user activity that shouldn't be displayed"
+ + " for all users. Failing silently...");
+ break;
default:
throw new AndroidRuntimeException("Unknown error code "
+ res + " when starting " + intent);
diff --git a/core/java/android/content/Intent.java b/core/java/android/content/Intent.java
index aaaa745..ec443cd 100644
--- a/core/java/android/content/Intent.java
+++ b/core/java/android/content/Intent.java
@@ -1782,14 +1782,6 @@
@SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
public static final String ACTION_ALARM_CHANGED = "android.intent.action.ALARM_CHANGED";
/**
- * Sync State Changed Action: This is broadcast when the sync starts or stops or when one has
- * been failing for a long time. It is used by the SyncManager and the StatusBar service.
- * @hide
- */
- @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
- public static final String ACTION_SYNC_STATE_CHANGED
- = "android.intent.action.SYNC_STATE_CHANGED";
- /**
* Broadcast Action: This is broadcast once, after the system has finished
* booting. It can be used to perform application-specific initialization,
* such as installing alarms. You must hold the
diff --git a/core/java/android/content/pm/IPackageManager.aidl b/core/java/android/content/pm/IPackageManager.aidl
index 0336645..a5e9faf 100644
--- a/core/java/android/content/pm/IPackageManager.aidl
+++ b/core/java/android/content/pm/IPackageManager.aidl
@@ -203,7 +203,7 @@
void querySyncProviders(inout List<String> outNames,
inout List<ProviderInfo> outInfo);
- List<ProviderInfo> queryContentProviders(
+ ParceledListSlice queryContentProviders(
String processName, int uid, int flags);
InstrumentationInfo getInstrumentationInfo(
diff --git a/core/java/android/content/res/ResourcesKey.java b/core/java/android/content/res/ResourcesKey.java
index 9548d49..2620571 100644
--- a/core/java/android/content/res/ResourcesKey.java
+++ b/core/java/android/content/res/ResourcesKey.java
@@ -16,6 +16,8 @@
package android.content.res;
+import android.annotation.NonNull;
+
import java.util.Objects;
/** @hide */
@@ -25,27 +27,27 @@
private final int mHash;
public final int mDisplayId;
+ @NonNull
public final Configuration mOverrideConfiguration;
public ResourcesKey(String resDir, int displayId, Configuration overrideConfiguration,
float scale) {
mResDir = resDir;
mDisplayId = displayId;
- mOverrideConfiguration = overrideConfiguration;
+ mOverrideConfiguration = overrideConfiguration != null
+ ? overrideConfiguration : Configuration.EMPTY;
mScale = scale;
int hash = 17;
hash = 31 * hash + (mResDir == null ? 0 : mResDir.hashCode());
hash = 31 * hash + mDisplayId;
- hash = 31 * hash + (mOverrideConfiguration != null
- ? mOverrideConfiguration.hashCode() : 0);
+ hash = 31 * hash + mOverrideConfiguration.hashCode();
hash = 31 * hash + Float.floatToIntBits(mScale);
mHash = hash;
}
public boolean hasOverrideConfiguration() {
- return mOverrideConfiguration != null
- && !Configuration.EMPTY.equals(mOverrideConfiguration);
+ return !Configuration.EMPTY.equals(mOverrideConfiguration);
}
@Override
@@ -66,13 +68,8 @@
if (mDisplayId != peer.mDisplayId) {
return false;
}
- if (mOverrideConfiguration != peer.mOverrideConfiguration) {
- if (mOverrideConfiguration == null || peer.mOverrideConfiguration == null) {
- return false;
- }
- if (!mOverrideConfiguration.equals(peer.mOverrideConfiguration)) {
- return false;
- }
+ if (!mOverrideConfiguration.equals(peer.mOverrideConfiguration)) {
+ return false;
}
if (mScale != peer.mScale) {
return false;
diff --git a/core/java/android/hardware/usb/IUsbManager.aidl b/core/java/android/hardware/usb/IUsbManager.aidl
index 80c7b1a..6e4c9de 100644
--- a/core/java/android/hardware/usb/IUsbManager.aidl
+++ b/core/java/android/hardware/usb/IUsbManager.aidl
@@ -97,9 +97,6 @@
*/
void setUsbDataUnlocked(boolean unlock);
- /* Returns true iff sensitive user data is exposed on the USB connection. */
- boolean isUsbDataUnlocked();
-
/* Allow USB debugging from the attached host. If alwaysAllow is true, add the
* the public key to list of host keys that the user has approved.
*/
diff --git a/core/java/android/hardware/usb/UsbManager.java b/core/java/android/hardware/usb/UsbManager.java
index c88f213..3b3ee52 100644
--- a/core/java/android/hardware/usb/UsbManager.java
+++ b/core/java/android/hardware/usb/UsbManager.java
@@ -520,21 +520,6 @@
}
/**
- * Returns {@code true} iff access to sensitive USB data is currently allowed when
- * in device mode.
- *
- * {@hide}
- */
- public boolean isUsbDataUnlocked() {
- try {
- return mService.isUsbDataUnlocked();
- } catch (RemoteException e) {
- Log.e(TAG, "RemoteException in isUsbDataUnlocked", e);
- }
- return false;
- }
-
- /**
* Returns a list of physical USB ports on the device.
* <p>
* This list is guaranteed to contain all dual-role USB Type C ports but it might
diff --git a/core/java/android/net/ConnectivityManager.java b/core/java/android/net/ConnectivityManager.java
index abed1f0..605acb0 100644
--- a/core/java/android/net/ConnectivityManager.java
+++ b/core/java/android/net/ConnectivityManager.java
@@ -964,41 +964,6 @@
return 1;
}
- /**
- * Removes the NET_CAPABILITY_NOT_RESTRICTED capability from the given
- * NetworkCapabilities object if all the capabilities it provides are
- * typically provided by restricted networks.
- *
- * TODO: consider:
- * - Moving to NetworkCapabilities
- * - Renaming it to guessRestrictedCapability and make it set the
- * restricted capability bit in addition to clearing it.
- * @hide
- */
- public static void maybeMarkCapabilitiesRestricted(NetworkCapabilities nc) {
- for (int capability : nc.getCapabilities()) {
- switch (capability) {
- case NetworkCapabilities.NET_CAPABILITY_CBS:
- case NetworkCapabilities.NET_CAPABILITY_DUN:
- case NetworkCapabilities.NET_CAPABILITY_EIMS:
- case NetworkCapabilities.NET_CAPABILITY_FOTA:
- case NetworkCapabilities.NET_CAPABILITY_IA:
- case NetworkCapabilities.NET_CAPABILITY_IMS:
- case NetworkCapabilities.NET_CAPABILITY_RCS:
- case NetworkCapabilities.NET_CAPABILITY_XCAP:
- case NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED: //there by default
- continue;
- default:
- // At least one capability usually provided by unrestricted
- // networks. Conclude that this network is unrestricted.
- return;
- }
- }
- // All the capabilities are typically provided by restricted networks.
- // Conclude that this network is restricted.
- nc.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED);
- }
-
private NetworkCapabilities networkCapabilitiesForFeature(int networkType, String feature) {
if (networkType == TYPE_MOBILE) {
int cap = -1;
@@ -1021,14 +986,14 @@
}
NetworkCapabilities netCap = new NetworkCapabilities();
netCap.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR).addCapability(cap);
- maybeMarkCapabilitiesRestricted(netCap);
+ netCap.maybeMarkCapabilitiesRestricted();
return netCap;
} else if (networkType == TYPE_WIFI) {
if ("p2p".equals(feature)) {
NetworkCapabilities netCap = new NetworkCapabilities();
netCap.addTransportType(NetworkCapabilities.TRANSPORT_WIFI);
netCap.addCapability(NetworkCapabilities.NET_CAPABILITY_WIFI_P2P);
- maybeMarkCapabilitiesRestricted(netCap);
+ netCap.maybeMarkCapabilitiesRestricted();
return netCap;
}
}
diff --git a/core/java/android/net/NetworkCapabilities.java b/core/java/android/net/NetworkCapabilities.java
index 651fb35..29b063a 100644
--- a/core/java/android/net/NetworkCapabilities.java
+++ b/core/java/android/net/NetworkCapabilities.java
@@ -38,10 +38,7 @@
*/
public NetworkCapabilities() {
clearAll();
- mNetworkCapabilities =
- (1 << NET_CAPABILITY_NOT_RESTRICTED) |
- (1 << NET_CAPABILITY_TRUSTED) |
- (1 << NET_CAPABILITY_NOT_VPN);
+ mNetworkCapabilities = DEFAULT_CAPABILITIES;
}
public NetworkCapabilities(NetworkCapabilities nc) {
@@ -187,6 +184,28 @@
private static final int MAX_NET_CAPABILITY = NET_CAPABILITY_CAPTIVE_PORTAL;
/**
+ * Capabilities that are set by default when the object is constructed.
+ */
+ private static final long DEFAULT_CAPABILITIES =
+ (1 << NET_CAPABILITY_NOT_RESTRICTED) |
+ (1 << NET_CAPABILITY_TRUSTED) |
+ (1 << NET_CAPABILITY_NOT_VPN);
+
+ /**
+ * Capabilities that suggest that a network is restricted.
+ * {@see #maybeMarkCapabilitiesRestricted}.
+ */
+ private static final long RESTRICTED_CAPABILITIES =
+ (1 << NET_CAPABILITY_CBS) |
+ (1 << NET_CAPABILITY_DUN) |
+ (1 << NET_CAPABILITY_EIMS) |
+ (1 << NET_CAPABILITY_FOTA) |
+ (1 << NET_CAPABILITY_IA) |
+ (1 << NET_CAPABILITY_IMS) |
+ (1 << NET_CAPABILITY_RCS) |
+ (1 << NET_CAPABILITY_XCAP);
+
+ /**
* Adds the given capability to this {@code NetworkCapability} instance.
* Multiple capabilities may be applied sequentially. Note that when searching
* for a network to satisfy a request, all capabilities requested must be satisfied.
@@ -269,6 +288,22 @@
}
/**
+ * Removes the NET_CAPABILITY_NOT_RESTRICTED capability if all the capabilities it provides are
+ * typically provided by restricted networks.
+ *
+ * TODO: consider:
+ * - Renaming it to guessRestrictedCapability and make it set the
+ * restricted capability bit in addition to clearing it.
+ * @hide
+ */
+ public void maybeMarkCapabilitiesRestricted() {
+ // If all the capabilities are typically provided by restricted networks, conclude that this
+ // network is restricted.
+ if ((mNetworkCapabilities & ~(DEFAULT_CAPABILITIES | RESTRICTED_CAPABILITIES)) == 0)
+ removeCapability(NET_CAPABILITY_NOT_RESTRICTED);
+ }
+
+ /**
* Representing the transport type. Apps should generally not care about transport. A
* request for a fast internet connection could be satisfied by a number of different
* transports. If any are specified here it will be satisfied a Network that matches
diff --git a/core/java/android/net/NetworkRequest.java b/core/java/android/net/NetworkRequest.java
index e61594c..e184ec4 100644
--- a/core/java/android/net/NetworkRequest.java
+++ b/core/java/android/net/NetworkRequest.java
@@ -83,7 +83,13 @@
* Build {@link NetworkRequest} give the current set of capabilities.
*/
public NetworkRequest build() {
- return new NetworkRequest(mNetworkCapabilities, ConnectivityManager.TYPE_NONE,
+ // Make a copy of mNetworkCapabilities so we don't inadvertently remove NOT_RESTRICTED
+ // when later an unrestricted capability could be added to mNetworkCapabilities, in
+ // which case NOT_RESTRICTED should be returned to mNetworkCapabilities, which
+ // maybeMarkCapabilitiesRestricted() doesn't add back.
+ final NetworkCapabilities nc = new NetworkCapabilities(mNetworkCapabilities);
+ nc.maybeMarkCapabilitiesRestricted();
+ return new NetworkRequest(nc, ConnectivityManager.TYPE_NONE,
ConnectivityManager.REQUEST_ID_UNSET);
}
diff --git a/core/java/android/os/INetworkManagementService.aidl b/core/java/android/os/INetworkManagementService.aidl
index 8114155..cd84c8f 100644
--- a/core/java/android/os/INetworkManagementService.aidl
+++ b/core/java/android/os/INetworkManagementService.aidl
@@ -388,8 +388,10 @@
/**
* Setup a new physical network.
+ * @param permission null if no permissions required to access this network. PERMISSION_NETWORK
+ * or PERMISSION_SYSTEM to set respective permission.
*/
- void createPhysicalNetwork(int netId);
+ void createPhysicalNetwork(int netId, String permission);
/**
* Setup a new VPN.
@@ -416,6 +418,13 @@
void setDefaultNetId(int netId);
void clearDefaultNetId();
+ /**
+ * Set permission for a network.
+ * @param permission null to clear permissions. PERMISSION_NETWORK or PERMISSION_SYSTEM to set
+ * permission.
+ */
+ void setNetworkPermission(int netId, String permission);
+
void setPermission(String permission, in int[] uids);
void clearPermission(in int[] uids);
diff --git a/core/java/android/provider/CallLog.java b/core/java/android/provider/CallLog.java
index 23555d6..4f880b1 100644
--- a/core/java/android/provider/CallLog.java
+++ b/core/java/android/provider/CallLog.java
@@ -421,7 +421,7 @@
int presentation, int callType, int features, PhoneAccountHandle accountHandle,
long start, int duration, Long dataUsage) {
return addCall(ci, context, number, presentation, callType, features, accountHandle,
- start, duration, dataUsage, false);
+ start, duration, dataUsage, false, false);
}
@@ -450,8 +450,41 @@
* {@hide}
*/
public static Uri addCall(CallerInfo ci, Context context, String number,
+ int presentation, int callType, int features, PhoneAccountHandle accountHandle,
+ long start, int duration, Long dataUsage, boolean addForAllUsers) {
+ return addCall(ci, context, number, presentation, callType, features, accountHandle,
+ start, duration, dataUsage, addForAllUsers, false);
+ }
+
+ /**
+ * Adds a call to the call log.
+ *
+ * @param ci the CallerInfo object to get the target contact from. Can be null
+ * if the contact is unknown.
+ * @param context the context used to get the ContentResolver
+ * @param number the phone number to be added to the calls db
+ * @param presentation enum value from PhoneConstants.PRESENTATION_xxx, which
+ * is set by the network and denotes the number presenting rules for
+ * "allowed", "payphone", "restricted" or "unknown"
+ * @param callType enumerated values for "incoming", "outgoing", or "missed"
+ * @param features features of the call (e.g. Video).
+ * @param accountHandle The accountHandle object identifying the provider of the call
+ * @param start time stamp for the call in milliseconds
+ * @param duration call duration in seconds
+ * @param dataUsage data usage for the call in bytes, null if data usage was not tracked for
+ * the call.
+ * @param addForAllUsers If true, the call is added to the call log of all currently
+ * running users. The caller must have the MANAGE_USERS permission if this is true.
+ * @param is_read Flag to show if the missed call log has been read by the user or not.
+ * Used for call log restore of missed calls.
+ *
+ * @result The URI of the call log entry belonging to the user that made or received this
+ * call.
+ * {@hide}
+ */
+ public static Uri addCall(CallerInfo ci, Context context, String number,
int presentation, int callType, int features, PhoneAccountHandle accountHandle,
- long start, int duration, Long dataUsage, boolean addForAllUsers) {
+ long start, int duration, Long dataUsage, boolean addForAllUsers, boolean is_read) {
final ContentResolver resolver = context.getContentResolver();
int numberPresentation = PRESENTATION_ALLOWED;
@@ -516,7 +549,7 @@
values.put(NEW, Integer.valueOf(1));
if (callType == MISSED_TYPE) {
- values.put(IS_READ, Integer.valueOf(0));
+ values.put(IS_READ, Integer.valueOf(is_read ? 1 : 0));
}
if ((ci != null) && (ci.contactIdOrZero > 0)) {
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index a836cc5..6f98788 100644
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -8333,9 +8333,9 @@
return true;
case AppOpsManager.MODE_DEFAULT:
// this is the default operating mode after an app's installation
- if (!throwException) {
- return context.checkCallingOrSelfPermission(permissionName) ==
- PackageManager.PERMISSION_GRANTED;
+ if(context.checkCallingOrSelfPermission(permissionName) == PackageManager
+ .PERMISSION_GRANTED) {
+ return true;
}
default:
// this is for all other cases trickled down here...
diff --git a/core/java/android/speech/tts/TextToSpeechService.java b/core/java/android/speech/tts/TextToSpeechService.java
index fa015b2..c3aed75 100644
--- a/core/java/android/speech/tts/TextToSpeechService.java
+++ b/core/java/android/speech/tts/TextToSpeechService.java
@@ -40,6 +40,7 @@
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
+import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.MissingResourceException;
@@ -247,7 +248,7 @@
* @return A list of features supported for the given language.
*/
protected Set<String> onGetFeaturesForLanguage(String lang, String country, String variant) {
- return null;
+ return new HashSet<String>();
}
private int getExpectedLanguageAvailableStatus(Locale locale) {
diff --git a/core/java/android/view/ViewRootImpl.java b/core/java/android/view/ViewRootImpl.java
index 928fe93..6e93a30 100644
--- a/core/java/android/view/ViewRootImpl.java
+++ b/core/java/android/view/ViewRootImpl.java
@@ -3159,6 +3159,17 @@
return (theParent instanceof ViewGroup) && isViewDescendantOf((View) theParent, parent);
}
+ private static void forceLayout(View view) {
+ view.forceLayout();
+ if (view instanceof ViewGroup) {
+ ViewGroup group = (ViewGroup) view;
+ final int count = group.getChildCount();
+ for (int i = 0; i < count; i++) {
+ forceLayout(group.getChildAt(i));
+ }
+ }
+ }
+
private final static int MSG_INVALIDATE = 1;
private final static int MSG_INVALIDATE_RECT = 2;
private final static int MSG_DIE = 3;
@@ -3297,6 +3308,10 @@
mReportNextDraw = true;
}
+ if (mView != null) {
+ forceLayout(mView);
+ }
+
requestLayout();
}
break;
@@ -3311,6 +3326,9 @@
mWinFrame.top = t;
mWinFrame.bottom = t + h;
+ if (mView != null) {
+ forceLayout(mView);
+ }
requestLayout();
}
break;
diff --git a/core/java/com/android/internal/app/ChooserActivity.java b/core/java/com/android/internal/app/ChooserActivity.java
index 6af2e8b..d9faece 100644
--- a/core/java/com/android/internal/app/ChooserActivity.java
+++ b/core/java/com/android/internal/app/ChooserActivity.java
@@ -517,6 +517,7 @@
private final ResolveInfo mBackupResolveInfo;
private final ChooserTarget mChooserTarget;
private Drawable mBadgeIcon = null;
+ private CharSequence mBadgeContentDescription;
private Drawable mDisplayIcon;
private final Intent mFillInIntent;
private final int mFillInFlags;
@@ -532,7 +533,9 @@
if (ri != null) {
final ActivityInfo ai = ri.activityInfo;
if (ai != null && ai.applicationInfo != null) {
- mBadgeIcon = getPackageManager().getApplicationIcon(ai.applicationInfo);
+ final PackageManager pm = getPackageManager();
+ mBadgeIcon = pm.getApplicationIcon(ai.applicationInfo);
+ mBadgeContentDescription = pm.getApplicationLabel(ai.applicationInfo);
}
}
}
@@ -555,6 +558,7 @@
mBackupResolveInfo = other.mBackupResolveInfo;
mChooserTarget = other.mChooserTarget;
mBadgeIcon = other.mBadgeIcon;
+ mBadgeContentDescription = other.mBadgeContentDescription;
mDisplayIcon = other.mDisplayIcon;
mFillInIntent = fillInIntent;
mFillInFlags = flags;
@@ -647,6 +651,11 @@
}
@Override
+ public CharSequence getBadgeContentDescription() {
+ return mBadgeContentDescription;
+ }
+
+ @Override
public TargetInfo cloneFilledIn(Intent fillInIntent, int flags) {
return new ChooserTargetInfo(this, fillInIntent, flags);
}
diff --git a/core/java/com/android/internal/app/ResolverActivity.java b/core/java/com/android/internal/app/ResolverActivity.java
index 89599e0..7dd3bed 100644
--- a/core/java/com/android/internal/app/ResolverActivity.java
+++ b/core/java/com/android/internal/app/ResolverActivity.java
@@ -932,6 +932,11 @@
}
@Override
+ public CharSequence getBadgeContentDescription() {
+ return null;
+ }
+
+ @Override
public TargetInfo cloneFilledIn(Intent fillInIntent, int flags) {
return new DisplayResolveInfo(this, fillInIntent, flags);
}
@@ -1072,6 +1077,11 @@
public Drawable getBadgeIcon();
/**
+ * @return The content description for the badge icon
+ */
+ public CharSequence getBadgeContentDescription();
+
+ /**
* Clone this target with the given fill-in information.
*/
public TargetInfo cloneFilledIn(Intent fillInIntent, int flags);
@@ -1542,6 +1552,7 @@
final Drawable badge = info.getBadgeIcon();
if (badge != null) {
holder.badge.setImageDrawable(badge);
+ holder.badge.setContentDescription(info.getBadgeContentDescription());
holder.badge.setVisibility(View.VISIBLE);
} else {
holder.badge.setVisibility(View.GONE);
diff --git a/core/java/com/android/internal/os/BatteryStatsImpl.java b/core/java/com/android/internal/os/BatteryStatsImpl.java
index e7c58f4..6c7e298 100644
--- a/core/java/com/android/internal/os/BatteryStatsImpl.java
+++ b/core/java/com/android/internal/os/BatteryStatsImpl.java
@@ -7674,6 +7674,7 @@
final long totalTimeMs = txTimeMs + rxTimeMs + idleTimeMs;
long leftOverRxTimeMs = rxTimeMs;
+ long leftOverTxTimeMs = txTimeMs;
if (DEBUG_ENERGY) {
Slog.d(TAG, "------ BEGIN WiFi power blaming ------");
@@ -7705,6 +7706,10 @@
Slog.d(TAG, " !Estimated scan time > Actual rx time (" + totalScanTimeMs + " ms > "
+ rxTimeMs + " ms). Normalizing scan time.");
}
+ if (DEBUG_ENERGY && totalScanTimeMs > txTimeMs) {
+ Slog.d(TAG, " !Estimated scan time > Actual tx time (" + totalScanTimeMs + " ms > "
+ + txTimeMs + " ms). Normalizing scan time.");
+ }
// Actually assign and distribute power usage to apps.
for (int i = 0; i < uidStatsSize; i++) {
@@ -7716,23 +7721,34 @@
// Set the new mark so that next time we get new data since this point.
uid.mWifiScanTimer.setMark(elapsedRealtimeMs);
+ long scanRxTimeSinceMarkMs = scanTimeSinceMarkMs;
+ long scanTxTimeSinceMarkMs = scanTimeSinceMarkMs;
+
+ // Our total scan time is more than the reported Tx/Rx time.
+ // This is possible because the cost of a scan is approximate.
+ // Let's normalize the result so that we evenly blame each app
+ // scanning.
+ //
+ // This means that we may have apps that transmitted/received packets not be
+ // blamed for this, but this is fine as scans are relatively more expensive.
if (totalScanTimeMs > rxTimeMs) {
- // Our total scan time is more than the reported Rx time.
- // This is possible because the cost of a scan is approximate.
- // Let's normalize the result so that we evenly blame each app
- // scanning.
- //
- // This means that we may have apps that received packets not be blamed
- // for this, but this is fine as scans are relatively more expensive.
- scanTimeSinceMarkMs = (rxTimeMs * scanTimeSinceMarkMs) / totalScanTimeMs;
+ scanRxTimeSinceMarkMs = (rxTimeMs * scanRxTimeSinceMarkMs) /
+ totalScanTimeMs;
+ }
+ if (totalScanTimeMs > txTimeMs) {
+ scanTxTimeSinceMarkMs = (txTimeMs * scanTxTimeSinceMarkMs) /
+ totalScanTimeMs;
}
if (DEBUG_ENERGY) {
- Slog.d(TAG, " ScanTime for UID " + uid.getUid() + ": "
- + scanTimeSinceMarkMs + " ms)");
+ Slog.d(TAG, " ScanTime for UID " + uid.getUid() + ": Rx:"
+ + scanRxTimeSinceMarkMs + " ms Tx:"
+ + scanTxTimeSinceMarkMs + " ms)");
}
- uid.noteWifiControllerActivityLocked(CONTROLLER_RX_TIME, scanTimeSinceMarkMs);
- leftOverRxTimeMs -= scanTimeSinceMarkMs;
+ uid.noteWifiControllerActivityLocked(CONTROLLER_RX_TIME, scanRxTimeSinceMarkMs);
+ uid.noteWifiControllerActivityLocked(CONTROLLER_TX_TIME, scanTxTimeSinceMarkMs);
+ leftOverRxTimeMs -= scanRxTimeSinceMarkMs;
+ leftOverTxTimeMs -= scanTxTimeSinceMarkMs;
}
// Distribute evenly the power consumed while Idle to each app holding a WiFi
@@ -7755,12 +7771,14 @@
if (DEBUG_ENERGY) {
Slog.d(TAG, " New RxPower: " + leftOverRxTimeMs + " ms");
+ Slog.d(TAG, " New TxPower: " + leftOverTxTimeMs + " ms");
}
- // Distribute the Tx power appropriately between all apps that transmitted packets.
+ // Distribute the remaining Tx power appropriately between all apps that transmitted
+ // packets.
for (int i = 0; i < txPackets.size(); i++) {
final Uid uid = getUidStatsLocked(txPackets.keyAt(i));
- final long myTxTimeMs = (txPackets.valueAt(i) * txTimeMs) / totalTxPackets;
+ final long myTxTimeMs = (txPackets.valueAt(i) * leftOverTxTimeMs) / totalTxPackets;
if (DEBUG_ENERGY) {
Slog.d(TAG, " TxTime for UID " + uid.getUid() + ": " + myTxTimeMs + " ms");
}
@@ -7915,6 +7933,8 @@
return;
}
+ // Record whether we've seen a non-zero time (for debugging b/22716723).
+ boolean seenNonZeroTime = false;
for (Map.Entry<String, KernelWakelockStats.Entry> ent : wakelockStats.entrySet()) {
String name = ent.getKey();
KernelWakelockStats.Entry kws = ent.getValue();
@@ -7928,17 +7948,31 @@
kwlt.updateCurrentReportedCount(kws.mCount);
kwlt.updateCurrentReportedTotalTime(kws.mTotalTime);
kwlt.setUpdateVersion(kws.mVersion);
+
+ if (kws.mVersion != wakelockStats.kernelWakelockVersion)
+ seenNonZeroTime |= kws.mTotalTime > 0;
}
+ int numWakelocksSetStale = 0;
if (wakelockStats.size() != mKernelWakelockStats.size()) {
// Set timers to stale if they didn't appear in /proc/wakelocks this time.
for (Map.Entry<String, SamplingTimer> ent : mKernelWakelockStats.entrySet()) {
SamplingTimer st = ent.getValue();
if (st.getUpdateVersion() != wakelockStats.kernelWakelockVersion) {
st.setStale();
+ numWakelocksSetStale++;
}
}
}
+
+ if (!seenNonZeroTime) {
+ Slog.wtf(TAG, "All kernel wakelocks had time of zero");
+ }
+
+ if (numWakelocksSetStale == mKernelWakelockStats.size()) {
+ Slog.wtf(TAG, "All kernel wakelocks were set stale. new version=" +
+ wakelockStats.kernelWakelockVersion);
+ }
}
// We use an anonymous class to access these variables,
diff --git a/core/java/com/android/internal/os/KernelWakelockReader.java b/core/java/com/android/internal/os/KernelWakelockReader.java
index 0369c3f..6654ea5 100644
--- a/core/java/com/android/internal/os/KernelWakelockReader.java
+++ b/core/java/com/android/internal/os/KernelWakelockReader.java
@@ -75,6 +75,8 @@
is = new FileInputStream(sWakeupSourceFile);
wakeup_sources = true;
} catch (java.io.FileNotFoundException e2) {
+ Slog.wtf(TAG, "neither " + sWakelockFile + " nor " +
+ sWakeupSourceFile + " exists");
return null;
}
}
@@ -82,6 +84,7 @@
len = is.read(buffer);
is.close();
} catch (java.io.IOException e) {
+ Slog.wtf(TAG, "failed to read kernel wakelocks", e);
return null;
}
@@ -171,6 +174,13 @@
numUpdatedWlNames++;
}
}
+ } else if (!parsed) {
+ try {
+ Slog.wtf(TAG, "Failed to parse proc line: " +
+ new String(wlBuffer, startIndex, endIndex - startIndex));
+ } catch (Exception e) {
+ Slog.wtf(TAG, "Failed to parse proc line!");
+ }
}
startIndex = endIndex;
}
diff --git a/core/java/com/android/internal/widget/ResolverDrawerLayout.java b/core/java/com/android/internal/widget/ResolverDrawerLayout.java
index fc9a1a5..7679624 100644
--- a/core/java/com/android/internal/widget/ResolverDrawerLayout.java
+++ b/core/java/com/android/internal/widget/ResolverDrawerLayout.java
@@ -34,6 +34,7 @@
import android.view.ViewTreeObserver;
import android.view.accessibility.AccessibilityEvent;
import android.view.accessibility.AccessibilityNodeInfo;
+import android.view.accessibility.AccessibilityNodeInfo.AccessibilityAction;
import android.view.animation.AnimationUtils;
import android.widget.AbsListView;
import android.widget.OverScroller;
@@ -609,19 +610,37 @@
}
@Override
- public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info) {
- super.onInitializeAccessibilityNodeInfo(info);
+ public CharSequence getAccessibilityClassName() {
+ // Since we support scrolling, make this ViewGroup look like a
+ // ScrollView. This is kind of a hack until we have support for
+ // specifying auto-scroll behavior.
+ return android.widget.ScrollView.class.getName();
+ }
+
+ @Override
+ public void onInitializeAccessibilityNodeInfoInternal(AccessibilityNodeInfo info) {
+ super.onInitializeAccessibilityNodeInfoInternal(info);
+
if (isEnabled()) {
if (mCollapseOffset != 0) {
info.addAction(AccessibilityNodeInfo.ACTION_SCROLL_FORWARD);
info.setScrollable(true);
}
}
+
+ // This view should never get accessibility focus, but it's interactive
+ // via nested scrolling, so we can't hide it completely.
+ info.removeAction(AccessibilityAction.ACTION_ACCESSIBILITY_FOCUS);
}
@Override
- public boolean performAccessibilityAction(int action, Bundle arguments) {
- if (super.performAccessibilityAction(action, arguments)) {
+ public boolean performAccessibilityActionInternal(int action, Bundle arguments) {
+ if (action == AccessibilityAction.ACTION_ACCESSIBILITY_FOCUS.getId()) {
+ // This view should never get accessibility focus.
+ return false;
+ }
+
+ if (super.performAccessibilityActionInternal(action, arguments)) {
return true;
}
@@ -629,6 +648,7 @@
smoothScrollTo(0, 0);
return true;
}
+
return false;
}
diff --git a/core/jni/android/graphics/Bitmap.cpp b/core/jni/android/graphics/Bitmap.cpp
index 670d3c01..fbe3ece 100755
--- a/core/jni/android/graphics/Bitmap.cpp
+++ b/core/jni/android/graphics/Bitmap.cpp
@@ -218,7 +218,6 @@
}
const SkImageInfo& Bitmap::info() const {
- assertValid();
return mPixelRef->info();
}
diff --git a/core/res/res/values/colors_material.xml b/core/res/res/values/colors_material.xml
index 1cb39f0..7399fa9 100644
--- a/core/res/res/values/colors_material.xml
+++ b/core/res/res/values/colors_material.xml
@@ -41,9 +41,6 @@
<color name="switch_thumb_disabled_material_dark">#ff616161</color>
<color name="switch_thumb_disabled_material_light">#ffbdbdbd</color>
- <color name="link_text_material_light">@color/material_deep_teal_500</color>
- <color name="link_text_material_dark">@color/material_deep_teal_200</color>
-
<!-- Text & foreground colors -->
<eat-comment />
diff --git a/core/res/res/values/themes_material.xml b/core/res/res/values/themes_material.xml
index 9d3a7ef..e88a4fb 100644
--- a/core/res/res/values/themes_material.xml
+++ b/core/res/res/values/themes_material.xml
@@ -67,8 +67,8 @@
<item name="textColorHintInverse">@color/hint_foreground_material_light</item>
<item name="textColorHighlight">@color/highlighted_text_material</item>
<item name="textColorHighlightInverse">@color/highlighted_text_material</item>
- <item name="textColorLink">@color/link_text_material_dark</item>
- <item name="textColorLinkInverse">@color/link_text_material_light</item>
+ <item name="textColorLink">?attr/colorAccent</item>
+ <item name="textColorLinkInverse">?attr/colorAccent</item>
<item name="textColorSearchUrl">@color/search_url_text_material_dark</item>
<item name="textColorAlertDialogListItem">@color/primary_text_material_dark</item>
@@ -422,8 +422,8 @@
<item name="textColorHintInverse">@color/hint_foreground_material_dark</item>
<item name="textColorHighlight">@color/highlighted_text_material</item>
<item name="textColorHighlightInverse">@color/highlighted_text_material</item>
- <item name="textColorLink">@color/link_text_material_light</item>
- <item name="textColorLinkInverse">@color/link_text_material_dark</item>
+ <item name="textColorLink">?attr/colorAccent</item>
+ <item name="textColorLinkInverse">?attr/colorAccent</item>
<item name="textColorSearchUrl">@color/search_url_text_material_light</item>
<item name="textColorAlertDialogListItem">@color/primary_text_material_light</item>
@@ -793,8 +793,6 @@
<item name="textColorHintInverse">@color/hint_foreground_material_dark</item>
<item name="textColorHighlight">@color/highlighted_text_material</item>
<item name="textColorHighlightInverse">@color/highlighted_text_material</item>
- <item name="textColorLink">@color/link_text_material_light</item>
- <item name="textColorLinkInverse">@color/link_text_material_dark</item>
<item name="textColorSearchUrl">@color/search_url_text_material_light</item>
<item name="textColorAlertDialogListItem">@color/primary_text_material_light</item>
@@ -827,8 +825,6 @@
<item name="textColorHintInverse">@color/hint_foreground_material_light</item>
<item name="textColorHighlight">@color/highlighted_text_material</item>
<item name="textColorHighlightInverse">@color/highlighted_text_material</item>
- <item name="textColorLink">@color/link_text_material_dark</item>
- <item name="textColorLinkInverse">@color/link_text_material_light</item>
<item name="textColorSearchUrl">@color/search_url_text_material_dark</item>
<item name="textColorAlertDialogListItem">@color/primary_text_material_dark</item>
diff --git a/data/fonts/Android.mk b/data/fonts/Android.mk
index 3181017..39458f9 100644
--- a/data/fonts/Android.mk
+++ b/data/fonts/Android.mk
@@ -17,10 +17,13 @@
LOCAL_PATH := $(call my-dir)
-# Use full Noto Sans Japanese font on non-smaller footprints
+# Use full Noto Sans Japanese font on the normal footprints, but
+# exclude it from SMALLER and use a subset on the CONSTRAINED ones.
ifneq ($(SMALLER_FONT_FOOTPRINT),true)
+ifneq ($(CONSTRAINED_FONT_FOOTPRINT),true)
FONT_NOTOSANS_JP_FULL := true
endif
+endif
##########################################
# create symlink for given font
@@ -82,19 +85,32 @@
extra_font_files :=
################################
-# Include the DroidSansFallback subset on SMALLER_FONT_FOOTPRINT build
+# Include the DroidSansFallback subset on SMALLER_FONT_FOOTPRINT builds,
+# and the full font on CONSTRAINED_FONT_FOOTPRINT ones.
ifeq ($(SMALLER_FONT_FOOTPRINT),true)
+droidsans_fallback_src := DroidSansFallback.ttf
+build_droidsans_fallback := true
+endif # SMALLER_FONT_FOOTPRINT
+
+ifeq ($(CONSTRAINED_FONT_FOOTPRINT),true)
+droidsans_fallback_src := DroidSansFallbackFull.ttf
+build_droidsans_fallback := true
+endif # CONSTRAINED_FONT_FOOTPRINT
+
+ifeq ($(build_droidsans_fallback),true)
include $(CLEAR_VARS)
LOCAL_MODULE := DroidSansFallback.ttf
-LOCAL_SRC_FILES := $(LOCAL_MODULE)
+LOCAL_SRC_FILES := $(droidsans_fallback_src)
LOCAL_MODULE_CLASS := ETC
LOCAL_MODULE_TAGS := optional
LOCAL_MODULE_PATH := $(TARGET_OUT)/fonts
include $(BUILD_PREBUILT)
droidsans_fallback_src :=
-endif # SMALLER_FONT_FOOTPRINT
+endif # build_droidsans_fallback
+
+build_droidsans_fallback :=
################################
# Build the rest of font files as prebuilt.
diff --git a/graphics/java/android/graphics/Bitmap.java b/graphics/java/android/graphics/Bitmap.java
index 8ad7c12..3e4d93b 100644
--- a/graphics/java/android/graphics/Bitmap.java
+++ b/graphics/java/android/graphics/Bitmap.java
@@ -23,6 +23,7 @@
import android.os.Parcelable;
import android.os.Trace;
import android.util.DisplayMetrics;
+import android.util.Log;
import dalvik.system.VMRuntime;
@@ -33,6 +34,8 @@
import java.nio.ShortBuffer;
public final class Bitmap implements Parcelable {
+ private static final String TAG = "Bitmap";
+
/**
* Indicates that the bitmap was created for an unknown pixel density.
*
@@ -159,6 +162,9 @@
* @see #DENSITY_NONE
*/
public int getDensity() {
+ if (mRecycled) {
+ Log.w(TAG, "Called getDensity() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return mDensity;
}
@@ -330,7 +336,9 @@
* @return The current generation ID for this bitmap.
*/
public int getGenerationId() {
- if (mRecycled) return 0;
+ if (mRecycled) {
+ Log.w(TAG, "Called getGenerationId() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return nativeGenerationId(mFinalizer.mNativeBitmap);
}
@@ -1057,7 +1065,9 @@
* @see BitmapFactory.Options#inPremultiplied
*/
public final boolean isPremultiplied() {
- if (mRecycled) return false;
+ if (mRecycled) {
+ Log.w(TAG, "Called isPremultiplied() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return nativeIsPremultiplied(mFinalizer.mNativeBitmap);
}
@@ -1089,11 +1099,17 @@
/** Returns the bitmap's width */
public final int getWidth() {
+ if (mRecycled) {
+ Log.w(TAG, "Called getWidth() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return mWidth;
}
/** Returns the bitmap's height */
public final int getHeight() {
+ if (mRecycled) {
+ Log.w(TAG, "Called getHeight() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return mHeight;
}
@@ -1176,7 +1192,9 @@
* @return number of bytes between rows of the native bitmap pixels.
*/
public final int getRowBytes() {
- if (mRecycled) return 0;
+ if (mRecycled) {
+ Log.w(TAG, "Called getRowBytes() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return nativeRowBytes(mFinalizer.mNativeBitmap);
}
@@ -1220,7 +1238,9 @@
* that config, otherwise return null.
*/
public final Config getConfig() {
- if (mRecycled) return Config.ARGB_8888;
+ if (mRecycled) {
+ Log.w(TAG, "Called getConfig() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return Config.nativeToConfig(nativeConfig(mFinalizer.mNativeBitmap));
}
@@ -1233,7 +1253,9 @@
* it will return true by default.
*/
public final boolean hasAlpha() {
- if (mRecycled) return false;
+ if (mRecycled) {
+ Log.w(TAG, "Called hasAlpha() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return nativeHasAlpha(mFinalizer.mNativeBitmap);
}
@@ -1270,7 +1292,9 @@
* @see #setHasMipMap(boolean)
*/
public final boolean hasMipMap() {
- if (mRecycled) return false;
+ if (mRecycled) {
+ Log.w(TAG, "Called hasMipMap() on a recycle()'d bitmap! This is undefined behavior!");
+ }
return nativeHasMipMap(mFinalizer.mNativeBitmap);
}
diff --git a/libs/hwui/renderstate/RenderState.cpp b/libs/hwui/renderstate/RenderState.cpp
index 3ebd57b..1e39bfa 100644
--- a/libs/hwui/renderstate/RenderState.cpp
+++ b/libs/hwui/renderstate/RenderState.cpp
@@ -124,9 +124,15 @@
}
void RenderState::invokeFunctor(Functor* functor, DrawGlInfo::Mode mode, DrawGlInfo* info) {
- interruptForFunctorInvoke();
- (*functor)(mode, info);
- resumeFromFunctorInvoke();
+ if (mode == DrawGlInfo::kModeProcessNoContext) {
+ // If there's no context we don't need to interrupt as there's
+ // no gl state to save/restore
+ (*functor)(mode, info);
+ } else {
+ interruptForFunctorInvoke();
+ (*functor)(mode, info);
+ resumeFromFunctorInvoke();
+ }
}
void RenderState::interruptForFunctorInvoke() {
diff --git a/libs/hwui/renderthread/CanvasContext.cpp b/libs/hwui/renderthread/CanvasContext.cpp
index e472e93..6dfb6e8 100644
--- a/libs/hwui/renderthread/CanvasContext.cpp
+++ b/libs/hwui/renderthread/CanvasContext.cpp
@@ -229,10 +229,11 @@
SkRect dirty;
mDamageAccumulator.finish(&dirty);
- if (dirty.isEmpty() && Properties::skipEmptyFrames) {
- mCurrentFrameInfo->addFlag(FrameInfoFlags::SkippedFrame);
- return;
- }
+ // TODO: Re-enable after figuring out cause of b/22592975
+// if (dirty.isEmpty() && Properties::skipEmptyFrames) {
+// mCurrentFrameInfo->addFlag(FrameInfoFlags::SkippedFrame);
+// return;
+// }
mCurrentFrameInfo->markIssueDrawCommandsStart();
diff --git a/media/java/android/media/AudioSystem.java b/media/java/android/media/AudioSystem.java
index acdadd7..e99a37a 100644
--- a/media/java/android/media/AudioSystem.java
+++ b/media/java/android/media/AudioSystem.java
@@ -604,6 +604,10 @@
public static final int SYNC_EVENT_NONE = 0;
public static final int SYNC_EVENT_PRESENTATION_COMPLETE = 1;
+ /**
+ * @return command completion status, one of {@link #AUDIO_STATUS_OK},
+ * {@link #AUDIO_STATUS_ERROR} or {@link #AUDIO_STATUS_SERVER_DIED}
+ */
public static native int setDeviceConnectionState(int device, int state,
String device_address, String device_name);
public static native int getDeviceConnectionState(int device, String device_address);
diff --git a/media/java/android/media/Ringtone.java b/media/java/android/media/Ringtone.java
index 9e9d602..c2bcd93 100644
--- a/media/java/android/media/Ringtone.java
+++ b/media/java/android/media/Ringtone.java
@@ -52,7 +52,8 @@
MediaStore.Audio.Media.TITLE
};
/** Selection that limits query results to just audio files */
- private static final String MEDIA_SELECTION = MediaColumns.MIME_TYPE + " LIKE 'audio/%'";
+ private static final String MEDIA_SELECTION = MediaColumns.MIME_TYPE + " LIKE 'audio/%' OR "
+ + MediaColumns.MIME_TYPE + " IN ('application/ogg', 'application/x-flac')";
// keep references on active Ringtones until stopped or completion listener called.
private static final ArrayList<Ringtone> sActiveRingtones = new ArrayList<Ringtone>();
diff --git a/packages/Keyguard/src/com/android/keyguard/KeyguardAbsKeyInputView.java b/packages/Keyguard/src/com/android/keyguard/KeyguardAbsKeyInputView.java
index 0c6837f..8f792de 100644
--- a/packages/Keyguard/src/com/android/keyguard/KeyguardAbsKeyInputView.java
+++ b/packages/Keyguard/src/com/android/keyguard/KeyguardAbsKeyInputView.java
@@ -53,15 +53,18 @@
super(context, attrs);
}
+ @Override
public void setKeyguardCallback(KeyguardSecurityCallback callback) {
mCallback = callback;
}
+ @Override
public void setLockPatternUtils(LockPatternUtils utils) {
mLockPatternUtils = utils;
mEnableHaptics = mLockPatternUtils.isTactileFeedbackEnabled();
}
+ @Override
public void reset() {
// start fresh
resetPasswordText(false /* animate */);
@@ -95,6 +98,7 @@
}
}
+ @Override
public void onEmergencyButtonClickedWhenInCall() {
mCallback.reset();
}
@@ -115,11 +119,11 @@
mPendingLockCheck.cancel(false);
}
- if (entry.length() < MINIMUM_PASSWORD_LENGTH_BEFORE_REPORT) {
+ if (entry.length() <= MINIMUM_PASSWORD_LENGTH_BEFORE_REPORT) {
// to avoid accidental lockout, only count attempts that are long enough to be a
// real password. This may require some tweaking.
setPasswordEntryInputEnabled(true);
- onPasswordChecked(entry, false, 0);
+ onPasswordChecked(false /* matched */, 0, false /* not valid - too short */);
return;
}
@@ -132,24 +136,27 @@
public void onChecked(boolean matched, int timeoutMs) {
setPasswordEntryInputEnabled(true);
mPendingLockCheck = null;
- onPasswordChecked(entry, matched, timeoutMs);
+ onPasswordChecked(matched, timeoutMs, true /* isValidPassword */);
}
});
}
- private void onPasswordChecked(String entry, boolean matched, int timeoutMs) {
+ private void onPasswordChecked(boolean matched, int timeoutMs, boolean isValidPassword) {
if (matched) {
mCallback.reportUnlockAttempt(true, 0);
mCallback.dismiss(true);
} else {
- mCallback.reportUnlockAttempt(false, timeoutMs);
- int attempts = KeyguardUpdateMonitor.getInstance(mContext).getFailedUnlockAttempts();
- if (timeoutMs > 0) {
- long deadline = mLockPatternUtils.setLockoutAttemptDeadline(
- KeyguardUpdateMonitor.getCurrentUser(), timeoutMs);
- handleAttemptLockout(deadline);
+ if (isValidPassword) {
+ mCallback.reportUnlockAttempt(false, timeoutMs);
+ if (timeoutMs > 0) {
+ long deadline = mLockPatternUtils.setLockoutAttemptDeadline(
+ KeyguardUpdateMonitor.getCurrentUser(), timeoutMs);
+ handleAttemptLockout(deadline);
+ }
}
- mSecurityMessageDisplay.setMessage(getWrongPasswordStringId(), true);
+ if (timeoutMs == 0) {
+ mSecurityMessageDisplay.setMessage(getWrongPasswordStringId(), true);
+ }
}
resetPasswordText(true /* animate */);
}
diff --git a/packages/Keyguard/src/com/android/keyguard/KeyguardPatternView.java b/packages/Keyguard/src/com/android/keyguard/KeyguardPatternView.java
index b000e26..4bd1a2e 100644
--- a/packages/Keyguard/src/com/android/keyguard/KeyguardPatternView.java
+++ b/packages/Keyguard/src/com/android/keyguard/KeyguardPatternView.java
@@ -82,6 +82,7 @@
* Useful for clearing out the wrong pattern after a delay
*/
private Runnable mCancelPatternRunnable = new Runnable() {
+ @Override
public void run() {
mLockPatternView.clearPattern();
}
@@ -117,10 +118,12 @@
R.dimen.disappear_y_translation);
}
+ @Override
public void setKeyguardCallback(KeyguardSecurityCallback callback) {
mCallback = callback;
}
+ @Override
public void setLockPatternUtils(LockPatternUtils utils) {
mLockPatternUtils = utils;
}
@@ -153,6 +156,7 @@
}
}
+ @Override
public void onEmergencyButtonClickedWhenInCall() {
mCallback.reset();
}
@@ -174,6 +178,7 @@
return result;
}
+ @Override
public void reset() {
// reset lock pattern
mLockPatternView.enableInput();
@@ -207,18 +212,22 @@
private class UnlockPatternListener implements LockPatternView.OnPatternListener {
+ @Override
public void onPatternStart() {
mLockPatternView.removeCallbacks(mCancelPatternRunnable);
mSecurityMessageDisplay.setMessage("", false);
}
+ @Override
public void onPatternCleared() {
}
+ @Override
public void onPatternCellAdded(List<LockPatternView.Cell> pattern) {
mCallback.userActivity();
}
+ @Override
public void onPatternDetected(final List<LockPatternView.Cell> pattern) {
mLockPatternView.disableInput();
if (mPendingLockCheck != null) {
@@ -227,7 +236,7 @@
if (pattern.size() < LockPatternUtils.MIN_PATTERN_REGISTER_FAIL) {
mLockPatternView.enableInput();
- onPatternChecked(pattern, false, 0);
+ onPatternChecked(false, 0, false /* not valid - too short */);
return;
}
@@ -240,29 +249,30 @@
public void onChecked(boolean matched, int timeoutMs) {
mLockPatternView.enableInput();
mPendingLockCheck = null;
- onPatternChecked(pattern, matched, timeoutMs);
+ onPatternChecked(matched, timeoutMs, true);
}
});
+ if (pattern.size() > MIN_PATTERN_BEFORE_POKE_WAKELOCK) {
+ mCallback.userActivity();
+ }
}
- private void onPatternChecked(List<LockPatternView.Cell> pattern, boolean matched,
- int timeoutMs) {
+ private void onPatternChecked(boolean matched, int timeoutMs, boolean isValidPattern) {
if (matched) {
mCallback.reportUnlockAttempt(true, 0);
mLockPatternView.setDisplayMode(LockPatternView.DisplayMode.Correct);
mCallback.dismiss(true);
} else {
- if (pattern.size() > MIN_PATTERN_BEFORE_POKE_WAKELOCK) {
- mCallback.userActivity();
- }
mLockPatternView.setDisplayMode(LockPatternView.DisplayMode.Wrong);
- mCallback.reportUnlockAttempt(false, timeoutMs);
- int attempts = mKeyguardUpdateMonitor.getFailedUnlockAttempts();
- if (timeoutMs > 0) {
- long deadline = mLockPatternUtils.setLockoutAttemptDeadline(
- KeyguardUpdateMonitor.getCurrentUser(), timeoutMs);
- handleAttemptLockout(deadline);
- } else {
+ if (isValidPattern) {
+ mCallback.reportUnlockAttempt(false, timeoutMs);
+ if (timeoutMs > 0) {
+ long deadline = mLockPatternUtils.setLockoutAttemptDeadline(
+ KeyguardUpdateMonitor.getCurrentUser(), timeoutMs);
+ handleAttemptLockout(deadline);
+ }
+ }
+ if (timeoutMs == 0) {
mSecurityMessageDisplay.setMessage(R.string.kg_wrong_pattern, true);
mLockPatternView.postDelayed(mCancelPatternRunnable, PATTERN_CLEAR_TIMEOUT_MS);
}
diff --git a/packages/SettingsLib/src/com/android/settingslib/bluetooth/CachedBluetoothDevice.java b/packages/SettingsLib/src/com/android/settingslib/bluetooth/CachedBluetoothDevice.java
index 249eaa5..b0429ef 100644
--- a/packages/SettingsLib/src/com/android/settingslib/bluetooth/CachedBluetoothDevice.java
+++ b/packages/SettingsLib/src/com/android/settingslib/bluetooth/CachedBluetoothDevice.java
@@ -808,7 +808,7 @@
// The pairing dialog now warns of phone-book access for paired devices.
// No separate prompt is displayed after pairing.
if (getPhonebookPermissionChoice() == CachedBluetoothDevice.ACCESS_UNKNOWN) {
- setPhonebookPermissionChoice(CachedBluetoothDevice.ACCESS_REJECTED);
+ setPhonebookPermissionChoice(CachedBluetoothDevice.ACCESS_ALLOWED);
}
}
}
diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
index 3e9b122..73971ad 100644
--- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
+++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
@@ -42,6 +42,9 @@
import android.os.Bundle;
import android.os.DropBoxManager;
import android.os.Environment;
+import android.os.Handler;
+import android.os.Looper;
+import android.os.Message;
import android.os.ParcelFileDescriptor;
import android.os.Process;
import android.os.SystemProperties;
@@ -204,9 +207,6 @@
// We have to call in the user manager with no lock held,
private volatile UserManager mUserManager;
- // We have to call in the app ops manager with no lock held,
- private volatile AppOpsManager mAppOpsManager;
-
// We have to call in the package manager with no lock held,
private volatile PackageManager mPackageManager;
@@ -214,7 +214,6 @@
public boolean onCreate() {
synchronized (mLock) {
mUserManager = (UserManager) getContext().getSystemService(Context.USER_SERVICE);
- mAppOpsManager = (AppOpsManager) getContext().getSystemService(Context.APP_OPS_SERVICE);
mPackageManager = getContext().getPackageManager();
mSettingsRegistry = new SettingsRegistry();
}
@@ -532,7 +531,7 @@
} while (cursor.moveToNext());
}
- private static final String toDumpString(String s) {
+ private static String toDumpString(String s) {
if (s != null) {
return s;
}
@@ -1158,18 +1157,6 @@
getCallingPackage());
}
- private void sendNotify(Uri uri, int userId) {
- final long identity = Binder.clearCallingIdentity();
- try {
- getContext().getContentResolver().notifyChange(uri, null, true, userId);
- if (DEBUG) {
- Slog.v(LOG_TAG, "Notifying for " + userId + ": " + uri);
- }
- } finally {
- Binder.restoreCallingIdentity(identity);
- }
- }
-
private static void warnOrThrowForUndesiredSecureSettingsMutationForTargetSdk(
int targetSdkVersion, String name) {
// If the app targets Lollipop MR1 or older SDK we warn, otherwise crash.
@@ -1390,8 +1377,11 @@
private final BackupManager mBackupManager;
+ private final Handler mHandler;
+
public SettingsRegistry() {
mBackupManager = new BackupManager(getContext());
+ mHandler = new MyHandler(getContext().getMainLooper());
migrateAllLegacySettingsIfNeeded();
}
@@ -1733,7 +1723,7 @@
// Inform the backup manager about a data change
if (backedUpDataChanged) {
- mBackupManager.dataChanged();
+ mHandler.obtainMessage(MyHandler.MSG_NOTIFY_DATA_CHANGED).sendToTarget();
}
// Now send the notification through the content framework.
@@ -1741,7 +1731,9 @@
final int userId = getUserIdFromKey(key);
Uri uri = getNotificationUriFor(key, name);
- sendNotify(uri, userId);
+ mHandler.obtainMessage(MyHandler.MSG_NOTIFY_URI_CHANGED,
+ userId, 0, uri).sendToTarget();
+
if (isSecureSettingsKey(key)) {
maybeNotifyProfiles(userId, uri, name, sSecureCloneToManagedSettings);
} else if (isSystemSettingsKey(key)) {
@@ -1758,7 +1750,8 @@
UserInfo profile = profiles.get(i);
// the notification for userId has already been sent.
if (profile.id != userId) {
- sendNotify(uri, profile.id);
+ mHandler.obtainMessage(MyHandler.MSG_NOTIFY_URI_CHANGED,
+ profile.id, 0, uri).sendToTarget();
}
}
}
@@ -1834,6 +1827,33 @@
}
}
+ private final class MyHandler extends Handler {
+ private static final int MSG_NOTIFY_URI_CHANGED = 1;
+ private static final int MSG_NOTIFY_DATA_CHANGED = 2;
+
+ public MyHandler(Looper looper) {
+ super(looper);
+ }
+
+ @Override
+ public void handleMessage(Message msg) {
+ switch (msg.what) {
+ case MSG_NOTIFY_URI_CHANGED: {
+ final int userId = msg.arg1;
+ Uri uri = (Uri) msg.obj;
+ getContext().getContentResolver().notifyChange(uri, null, true, userId);
+ if (DEBUG) {
+ Slog.v(LOG_TAG, "Notifying for " + userId + ": " + uri);
+ }
+ } break;
+
+ case MSG_NOTIFY_DATA_CHANGED: {
+ mBackupManager.dataChanged();
+ } break;
+ }
+ }
+ }
+
private final class UpgradeController {
private static final int SETTINGS_VERSION = 122;
@@ -1963,9 +1983,11 @@
currentVersion = 120;
}
- // Before 121, we used a different string encoding logic. We just bump the version
- // here; SettingsState knows how to handle pre-version 120 files.
- currentVersion = 121;
+ if (currentVersion == 120) {
+ // Before 121, we used a different string encoding logic. We just bump the
+ // version here; SettingsState knows how to handle pre-version 120 files.
+ currentVersion = 121;
+ }
if (currentVersion == 121) {
// Version 122: allow OEMs to set a default payment component in resources.
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/FlashlightTile.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/FlashlightTile.java
index 5d746046..21cbef2 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/FlashlightTile.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/FlashlightTile.java
@@ -79,6 +79,8 @@
return;
}
state.value = value;
+ } else {
+ state.value = mFlashlightController.isEnabled();
}
final AnimationIcon icon = state.value ? mEnable : mDisable;
icon.setAllowAnimation(arg instanceof UserBoolean && ((UserBoolean) arg).userInitiated);
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/FlashlightController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/FlashlightController.java
index cd1914c..29a8f67 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/FlashlightController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/FlashlightController.java
@@ -93,6 +93,10 @@
}
}
+ public synchronized boolean isEnabled() {
+ return mFlashlightEnabled;
+ }
+
public synchronized boolean isAvailable() {
return mTorchAvailable;
}
diff --git a/services/core/java/com/android/server/BluetoothManagerService.java b/services/core/java/com/android/server/BluetoothManagerService.java
index 10a4cd1..50bd544 100644
--- a/services/core/java/com/android/server/BluetoothManagerService.java
+++ b/services/core/java/com/android/server/BluetoothManagerService.java
@@ -1506,6 +1506,7 @@
//Unbind
mContext.unbindService(mConnection);
}
+ mBluetoothGatt = null;
}
SystemClock.sleep(100);
@@ -1811,6 +1812,7 @@
//Unbind
mContext.unbindService(mConnection);
}
+ mBluetoothGatt = null;
}
mHandler.removeMessages(MESSAGE_BLUETOOTH_STATE_CHANGE);
diff --git a/services/core/java/com/android/server/ConnectivityService.java b/services/core/java/com/android/server/ConnectivityService.java
index 6a22f22..0802d30 100644
--- a/services/core/java/com/android/server/ConnectivityService.java
+++ b/services/core/java/com/android/server/ConnectivityService.java
@@ -4024,6 +4024,16 @@
}
if (!Objects.equals(nai.networkCapabilities, networkCapabilities)) {
final int oldScore = nai.getCurrentScore();
+ if (nai.networkCapabilities.hasCapability(NET_CAPABILITY_NOT_RESTRICTED) !=
+ networkCapabilities.hasCapability(NET_CAPABILITY_NOT_RESTRICTED)) {
+ try {
+ mNetd.setNetworkPermission(nai.network.netId,
+ networkCapabilities.hasCapability(NET_CAPABILITY_NOT_RESTRICTED) ?
+ null : NetworkManagementService.PERMISSION_SYSTEM);
+ } catch (RemoteException e) {
+ loge("Exception in setNetworkPermission: " + e);
+ }
+ }
synchronized (nai) {
nai.networkCapabilities = networkCapabilities;
}
@@ -4491,7 +4501,10 @@
(networkAgent.networkMisc == null ||
!networkAgent.networkMisc.allowBypass));
} else {
- mNetd.createPhysicalNetwork(networkAgent.network.netId);
+ mNetd.createPhysicalNetwork(networkAgent.network.netId,
+ networkAgent.networkCapabilities.hasCapability(
+ NET_CAPABILITY_NOT_RESTRICTED) ?
+ null : NetworkManagementService.PERMISSION_SYSTEM);
}
} catch (Exception e) {
loge("Error creating network " + networkAgent.network.netId + ": "
diff --git a/services/core/java/com/android/server/MountService.java b/services/core/java/com/android/server/MountService.java
index 6ab2fd7..53e8d14 100644
--- a/services/core/java/com/android/server/MountService.java
+++ b/services/core/java/com/android/server/MountService.java
@@ -559,6 +559,7 @@
private static final int H_FSTRIM = 4;
private static final int H_VOLUME_MOUNT = 5;
private static final int H_VOLUME_BROADCAST = 6;
+ private static final int H_INTERNAL_BROADCAST = 7;
class MountServiceHandler extends Handler {
public MountServiceHandler(Looper looper) {
@@ -655,6 +656,13 @@
}
break;
}
+ case H_INTERNAL_BROADCAST: {
+ // Internal broadcasts aimed at system components, not for
+ // third-party apps.
+ final Intent intent = (Intent) msg.obj;
+ mContext.sendBroadcastAsUser(intent, UserHandle.ALL,
+ android.Manifest.permission.WRITE_MEDIA_STORAGE);
+ }
}
}
}
@@ -1126,8 +1134,7 @@
intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
intent.putExtra(DiskInfo.EXTRA_DISK_ID, disk.id);
intent.putExtra(DiskInfo.EXTRA_VOLUME_COUNT, volumeCount);
- mContext.sendBroadcastAsUser(intent, UserHandle.ALL,
- android.Manifest.permission.WRITE_MEDIA_STORAGE);
+ mHandler.obtainMessage(H_INTERNAL_BROADCAST, intent).sendToTarget();
final CountDownLatch latch = mDiskScanLatches.remove(disk.id);
if (latch != null) {
@@ -1239,8 +1246,7 @@
intent.putExtra(VolumeInfo.EXTRA_VOLUME_STATE, newState);
intent.putExtra(VolumeRecord.EXTRA_FS_UUID, vol.fsUuid);
intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
- mContext.sendBroadcastAsUser(intent, UserHandle.ALL,
- android.Manifest.permission.WRITE_MEDIA_STORAGE);
+ mHandler.obtainMessage(H_INTERNAL_BROADCAST, intent).sendToTarget();
}
final String oldStateEnv = VolumeInfo.getEnvironmentForState(oldState);
diff --git a/services/core/java/com/android/server/NetworkManagementService.java b/services/core/java/com/android/server/NetworkManagementService.java
index 0e3134d..433f707 100644
--- a/services/core/java/com/android/server/NetworkManagementService.java
+++ b/services/core/java/com/android/server/NetworkManagementService.java
@@ -131,6 +131,19 @@
*/
public static final String LIMIT_GLOBAL_ALERT = "globalAlert";
+ /**
+ * String to pass to netd to indicate that a network is only accessible
+ * to apps that have the CHANGE_NETWORK_STATE permission.
+ */
+ public static final String PERMISSION_NETWORK = "NETWORK";
+
+ /**
+ * String to pass to netd to indicate that a network is only
+ * accessible to system apps and those with the CONNECTIVITY_INTERNAL
+ * permission.
+ */
+ public static final String PERMISSION_SYSTEM = "SYSTEM";
+
class NetdResponseCode {
/* Keep in sync with system/netd/server/ResponseCode.h */
public static final int InterfaceListResult = 110;
@@ -2329,11 +2342,15 @@
}
@Override
- public void createPhysicalNetwork(int netId) {
+ public void createPhysicalNetwork(int netId, String permission) {
mContext.enforceCallingOrSelfPermission(CONNECTIVITY_INTERNAL, TAG);
try {
- mConnector.execute("network", "create", netId);
+ if (permission != null) {
+ mConnector.execute("network", "create", netId, permission);
+ } else {
+ mConnector.execute("network", "create", netId);
+ }
} catch (NativeDaemonConnectorException e) {
throw e.rethrowAsParcelableException();
}
@@ -2425,6 +2442,22 @@
}
@Override
+ public void setNetworkPermission(int netId, String permission) {
+ mContext.enforceCallingOrSelfPermission(CONNECTIVITY_INTERNAL, TAG);
+
+ try {
+ if (permission != null) {
+ mConnector.execute("network", "permission", "network", "set", permission, netId);
+ } else {
+ mConnector.execute("network", "permission", "network", "clear", netId);
+ }
+ } catch (NativeDaemonConnectorException e) {
+ throw e.rethrowAsParcelableException();
+ }
+ }
+
+
+ @Override
public void setPermission(String permission, int[] uids) {
mContext.enforceCallingOrSelfPermission(CONNECTIVITY_INTERNAL, TAG);
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 783dea5..b8d32c3 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -6552,6 +6552,17 @@
}
@Override
+ public boolean isRootVoiceInteraction(IBinder token) {
+ synchronized(this) {
+ ActivityRecord r = ActivityRecord.isInStackLocked(token);
+ if (r == null) {
+ return false;
+ }
+ return r.rootVoiceInteraction;
+ }
+ }
+
+ @Override
public IIntentSender getIntentSender(int type,
String packageName, IBinder token, String resultWho,
int requestCode, Intent[] intents, String[] resolvedTypes,
@@ -9154,9 +9165,10 @@
private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) {
List<ProviderInfo> providers = null;
try {
- providers = AppGlobals.getPackageManager().
+ ParceledListSlice<ProviderInfo> slice = AppGlobals.getPackageManager().
queryContentProviders(app.processName, app.uid,
STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS);
+ providers = slice != null ? slice.getList() : null;
} catch (RemoteException ex) {
}
if (DEBUG_MU) Slog.v(TAG_MU,
diff --git a/services/core/java/com/android/server/am/ActivityRecord.java b/services/core/java/com/android/server/am/ActivityRecord.java
index 0957eb5..3de2009 100755
--- a/services/core/java/com/android/server/am/ActivityRecord.java
+++ b/services/core/java/com/android/server/am/ActivityRecord.java
@@ -107,6 +107,7 @@
boolean fullscreen; // covers the full screen?
final boolean noDisplay; // activity is not displayed?
final boolean componentSpecified; // did caller specifiy an explicit component?
+ final boolean rootVoiceInteraction; // was this the root activity of a voice interaction?
static final int APPLICATION_ACTIVITY_TYPE = 0;
static final int HOME_ACTIVITY_TYPE = 1;
@@ -207,6 +208,9 @@
pw.print(prefix); pw.print("stateNotNeeded="); pw.print(stateNotNeeded);
pw.print(" componentSpecified="); pw.print(componentSpecified);
pw.print(" mActivityType="); pw.println(mActivityType);
+ if (rootVoiceInteraction) {
+ pw.print(prefix); pw.print("rootVoiceInteraction="); pw.println(rootVoiceInteraction);
+ }
pw.print(prefix); pw.print("compat="); pw.print(compat);
pw.print(" labelRes=0x"); pw.print(Integer.toHexString(labelRes));
pw.print(" icon=0x"); pw.print(Integer.toHexString(icon));
@@ -432,7 +436,8 @@
int _launchedFromUid, String _launchedFromPackage, Intent _intent, String _resolvedType,
ActivityInfo aInfo, Configuration _configuration,
ActivityRecord _resultTo, String _resultWho, int _reqCode,
- boolean _componentSpecified, ActivityStackSupervisor supervisor,
+ boolean _componentSpecified, boolean _rootVoiceInteraction,
+ ActivityStackSupervisor supervisor,
ActivityContainer container, Bundle options) {
service = _service;
appToken = new Token(this, service);
@@ -444,6 +449,7 @@
shortComponentName = _intent.getComponent().flattenToShortString();
resolvedType = _resolvedType;
componentSpecified = _componentSpecified;
+ rootVoiceInteraction = _rootVoiceInteraction;
configuration = _configuration;
stackConfigOverride = (container != null)
? container.mStack.mOverrideConfig : Configuration.EMPTY;
@@ -1257,7 +1263,7 @@
}
final ActivityRecord r = new ActivityRecord(service, /*caller*/null, launchedFromUid,
launchedFromPackage, intent, resolvedType, aInfo, service.getConfiguration(),
- null, null, 0, componentSpecified, stackSupervisor, null, null);
+ null, null, 0, componentSpecified, false, stackSupervisor, null, null);
r.persistentState = persistentState;
r.taskDescription = taskDescription;
diff --git a/services/core/java/com/android/server/am/ActivityStackSupervisor.java b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
index 0be2f6f..71fd49b 100644
--- a/services/core/java/com/android/server/am/ActivityStackSupervisor.java
+++ b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
@@ -1506,6 +1506,7 @@
if ((launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) == 0
&& sourceRecord.info.applicationInfo.uid != aInfo.applicationInfo.uid) {
try {
+ intent.addCategory(Intent.CATEGORY_VOICE);
if (!AppGlobals.getPackageManager().activitySupportsIntent(
intent.getComponent(), intent, resolvedType)) {
err = ActivityManager.START_NOT_VOICE_COMPATIBLE;
@@ -1626,7 +1627,7 @@
ActivityRecord r = new ActivityRecord(mService, callerApp, callingUid, callingPackage,
intent, resolvedType, aInfo, mService.mConfiguration, resultRecord, resultWho,
- requestCode, componentSpecified, this, container, options);
+ requestCode, componentSpecified, voiceSession != null, this, container, options);
if (outActivity != null) {
outActivity[0] = r;
}
@@ -3721,19 +3722,19 @@
@Override
public void onDisplayAdded(int displayId) {
- Slog.v(TAG, "Display added displayId=" + displayId);
+ if (DEBUG_STACK) Slog.v(TAG, "Display added displayId=" + displayId);
mHandler.sendMessage(mHandler.obtainMessage(HANDLE_DISPLAY_ADDED, displayId, 0));
}
@Override
public void onDisplayRemoved(int displayId) {
- Slog.v(TAG, "Display removed displayId=" + displayId);
+ if (DEBUG_STACK) Slog.v(TAG, "Display removed displayId=" + displayId);
mHandler.sendMessage(mHandler.obtainMessage(HANDLE_DISPLAY_REMOVED, displayId, 0));
}
@Override
public void onDisplayChanged(int displayId) {
- Slog.v(TAG, "Display changed displayId=" + displayId);
+ if (DEBUG_STACK) Slog.v(TAG, "Display changed displayId=" + displayId);
mHandler.sendMessage(mHandler.obtainMessage(HANDLE_DISPLAY_CHANGED, displayId, 0));
}
diff --git a/services/core/java/com/android/server/am/BroadcastRecord.java b/services/core/java/com/android/server/am/BroadcastRecord.java
index a7e6471..1fbfd9f 100644
--- a/services/core/java/com/android/server/am/BroadcastRecord.java
+++ b/services/core/java/com/android/server/am/BroadcastRecord.java
@@ -240,8 +240,12 @@
}
didSomething = true;
receivers.remove(i);
+ if (i < nextReceiver) {
+ nextReceiver--;
+ }
}
}
+ nextReceiver = Math.min(nextReceiver, receivers.size());
return didSomething;
}
diff --git a/services/core/java/com/android/server/am/RecentTasks.java b/services/core/java/com/android/server/am/RecentTasks.java
index 6ee1650..b216114 100644
--- a/services/core/java/com/android/server/am/RecentTasks.java
+++ b/services/core/java/com/android/server/am/RecentTasks.java
@@ -435,7 +435,8 @@
*/
int trimForTaskLocked(TaskRecord task, boolean doTrim) {
int recentsCount = size();
- final boolean document = task.intent != null && task.intent.isDocument();
+ final Intent intent = task.intent;
+ final boolean document = intent != null && intent.isDocument();
int maxRecents = task.maxRecents - 1;
for (int i = 0; i < recentsCount; i++) {
final TaskRecord tr = get(i);
@@ -446,12 +447,13 @@
if (i > MAX_RECENT_BITMAPS) {
tr.freeLastThumbnail();
}
+ final Intent trIntent = tr.intent;
final boolean sameAffinity =
task.affinity != null && task.affinity.equals(tr.affinity);
- final boolean trIsDocument = tr.intent != null && tr.intent.isDocument();
+ final boolean sameIntent = (intent != null && intent.filterEquals(trIntent));
+ final boolean trIsDocument = trIntent != null && trIntent.isDocument();
final boolean bothDocuments = document && trIsDocument;
- if (!sameAffinity && !bothDocuments) {
- // Not the same affinity and not documents. Move along...
+ if (!sameAffinity && !sameIntent && !bothDocuments) {
continue;
}
diff --git a/services/core/java/com/android/server/audio/AudioService.java b/services/core/java/com/android/server/audio/AudioService.java
index 094cb57..a0ededf 100644
--- a/services/core/java/com/android/server/audio/AudioService.java
+++ b/services/core/java/com/android/server/audio/AudioService.java
@@ -4730,13 +4730,19 @@
Slog.i(TAG, "deviceSpec:" + deviceSpec + " is(already)Connected:" + isConnected);
}
if (connect && !isConnected) {
- AudioSystem.setDeviceConnectionState(device, AudioSystem.DEVICE_STATE_AVAILABLE,
- address, deviceName);
+ final int res = AudioSystem.setDeviceConnectionState(device,
+ AudioSystem.DEVICE_STATE_AVAILABLE, address, deviceName);
+ if (res != AudioSystem.AUDIO_STATUS_OK) {
+ Slog.e(TAG, "not connecting device 0x" + Integer.toHexString(device) +
+ " due to command error " + res );
+ return false;
+ }
mConnectedDevices.put(deviceKey, new DeviceListSpec(device, deviceName, address));
return true;
} else if (!connect && isConnected) {
- AudioSystem.setDeviceConnectionState(device, AudioSystem.DEVICE_STATE_UNAVAILABLE,
- address, deviceName);
+ AudioSystem.setDeviceConnectionState(device,
+ AudioSystem.DEVICE_STATE_UNAVAILABLE, address, deviceName);
+ // always remove even if disconnection failed
mConnectedDevices.remove(deviceKey);
return true;
}
@@ -4869,7 +4875,10 @@
boolean isUsb = ((device & ~AudioSystem.DEVICE_OUT_ALL_USB) == 0) ||
(((device & AudioSystem.DEVICE_BIT_IN) != 0) &&
((device & ~AudioSystem.DEVICE_IN_ALL_USB) == 0));
- handleDeviceConnection(state == 1, device, address, deviceName);
+ if (!handleDeviceConnection(state == 1, device, address, deviceName)) {
+ // change of connection state failed, bailout
+ return;
+ }
if (state != 0) {
if ((device == AudioSystem.DEVICE_OUT_WIRED_HEADSET) ||
(device == AudioSystem.DEVICE_OUT_WIRED_HEADPHONE) ||
diff --git a/services/core/java/com/android/server/content/SyncManager.java b/services/core/java/com/android/server/content/SyncManager.java
index 658f6f8..c998c2c 100644
--- a/services/core/java/com/android/server/content/SyncManager.java
+++ b/services/core/java/com/android/server/content/SyncManager.java
@@ -297,7 +297,6 @@
private final UserManager mUserManager;
private static final long SYNC_ALARM_TIMEOUT_MIN = 30 * 1000; // 30 seconds
- private static final long SYNC_ALARM_TIMEOUT_MAX = 2 * 60 * 60 * 1000; // two hours
private List<UserInfo> getAllUsers() {
return mUserManager.getUsers();
@@ -1478,9 +1477,9 @@
final long now = SystemClock.elapsedRealtime();
pw.print("now: "); pw.print(now);
pw.println(" (" + formatTime(System.currentTimeMillis()) + ")");
- pw.print("offset: "); pw.print(DateUtils.formatElapsedTime(mSyncRandomOffsetMillis/1000));
+ pw.print("offset: "); pw.print(DateUtils.formatElapsedTime(mSyncRandomOffsetMillis / 1000));
pw.println(" (HH:MM:SS)");
- pw.print("uptime: "); pw.print(DateUtils.formatElapsedTime(now/1000));
+ pw.print("uptime: "); pw.print(DateUtils.formatElapsedTime(now / 1000));
pw.println(" (HH:MM:SS)");
pw.print("time spent syncing: ");
pw.print(DateUtils.formatElapsedTime(
@@ -1497,11 +1496,6 @@
pw.println("no alarm is scheduled (there had better not be any pending syncs)");
}
- pw.print("notification info: ");
- final StringBuilder sb = new StringBuilder();
- mSyncHandler.mSyncNotificationInfo.toString(sb);
- pw.println(sb.toString());
-
pw.println();
pw.println("Active Syncs: " + mActiveSyncContexts.size());
final PackageManager pm = mContext.getPackageManager();
@@ -1514,8 +1508,8 @@
pw.println();
}
+ final StringBuilder sb = new StringBuilder();
synchronized (mSyncQueue) {
- sb.setLength(0);
mSyncQueue.dump(sb);
// Dump Pending Operations.
getSyncStorageEngine().dumpPendingOperations(sb);
@@ -2349,7 +2343,6 @@
}
} finally {
- manageSyncNotificationLocked();
manageSyncAlarmLocked(earliestFuturePollTime, nextPendingSyncTime);
mSyncTimeTracker.update();
mSyncManagerWakeLock.release();
@@ -3169,67 +3162,6 @@
throw new IllegalStateException("we are not in an error state, " + syncResult);
}
- private void manageSyncNotificationLocked() {
- boolean shouldCancel;
- boolean shouldInstall;
-
- if (mActiveSyncContexts.isEmpty()) {
- mSyncNotificationInfo.startTime = null;
-
- // we aren't syncing. if the notification is active then remember that we need
- // to cancel it and then clear out the info
- shouldCancel = mSyncNotificationInfo.isActive;
- shouldInstall = false;
- } else {
- // we are syncing
- final long now = SystemClock.elapsedRealtime();
- if (mSyncNotificationInfo.startTime == null) {
- mSyncNotificationInfo.startTime = now;
- }
-
- // there are three cases:
- // - the notification is up: do nothing
- // - the notification is not up but it isn't time yet: don't install
- // - the notification is not up and it is time: need to install
-
- if (mSyncNotificationInfo.isActive) {
- shouldInstall = shouldCancel = false;
- } else {
- // it isn't currently up, so there is nothing to cancel
- shouldCancel = false;
-
- final boolean timeToShowNotification =
- now > mSyncNotificationInfo.startTime + SYNC_NOTIFICATION_DELAY;
- if (timeToShowNotification) {
- shouldInstall = true;
- } else {
- // show the notification immediately if this is a manual sync
- shouldInstall = false;
- for (ActiveSyncContext activeSyncContext : mActiveSyncContexts) {
- final boolean manualSync = activeSyncContext.mSyncOperation.extras
- .getBoolean(ContentResolver.SYNC_EXTRAS_MANUAL, false);
- if (manualSync) {
- shouldInstall = true;
- break;
- }
- }
- }
- }
- }
-
- if (shouldCancel && !shouldInstall) {
- mNeedSyncActiveNotification = false;
- sendSyncStateIntent();
- mSyncNotificationInfo.isActive = false;
- }
-
- if (shouldInstall) {
- mNeedSyncActiveNotification = true;
- sendSyncStateIntent();
- mSyncNotificationInfo.isActive = true;
- }
- }
-
private void manageSyncAlarmLocked(long nextPeriodicEventElapsedTime,
long nextPendingEventElapsedTime) {
// in each of these cases the sync loop will be kicked, which will cause this
@@ -3238,13 +3170,6 @@
if (mStorageIsLow) return;
if (mDeviceIsIdle) return;
- // When the status bar notification should be raised
- final long notificationTime =
- (!mSyncHandler.mSyncNotificationInfo.isActive
- && mSyncHandler.mSyncNotificationInfo.startTime != null)
- ? mSyncHandler.mSyncNotificationInfo.startTime + SYNC_NOTIFICATION_DELAY
- : Long.MAX_VALUE;
-
// When we should consider canceling an active sync
long earliestTimeoutTime = Long.MAX_VALUE;
for (ActiveSyncContext currentSyncContext : mActiveSyncContexts) {
@@ -3260,24 +3185,14 @@
}
if (Log.isLoggable(TAG, Log.VERBOSE)) {
- Log.v(TAG, "manageSyncAlarm: notificationTime is " + notificationTime);
- }
-
- if (Log.isLoggable(TAG, Log.VERBOSE)) {
Log.v(TAG, "manageSyncAlarm: earliestTimeoutTime is " + earliestTimeoutTime);
- }
-
- if (Log.isLoggable(TAG, Log.VERBOSE)) {
Log.v(TAG, "manageSyncAlarm: nextPeriodicEventElapsedTime is "
+ nextPeriodicEventElapsedTime);
- }
- if (Log.isLoggable(TAG, Log.VERBOSE)) {
Log.v(TAG, "manageSyncAlarm: nextPendingEventElapsedTime is "
+ nextPendingEventElapsedTime);
}
- long alarmTime = Math.min(notificationTime, earliestTimeoutTime);
- alarmTime = Math.min(alarmTime, nextPeriodicEventElapsedTime);
+ long alarmTime = Math.min(earliestTimeoutTime, nextPeriodicEventElapsedTime);
alarmTime = Math.min(alarmTime, nextPendingEventElapsedTime);
// Bound the alarm time.
@@ -3288,24 +3203,16 @@
+ alarmTime + ", setting to " + (now + SYNC_ALARM_TIMEOUT_MIN));
}
alarmTime = now + SYNC_ALARM_TIMEOUT_MIN;
- } else if (alarmTime > now + SYNC_ALARM_TIMEOUT_MAX) {
- if (Log.isLoggable(TAG, Log.VERBOSE)) {
- Log.v(TAG, "manageSyncAlarm: the alarmTime is too large, "
- + alarmTime + ", setting to " + (now + SYNC_ALARM_TIMEOUT_MIN));
- }
- alarmTime = now + SYNC_ALARM_TIMEOUT_MAX;
}
- // determine if we need to set or cancel the alarm
+ // Determine if we need to set or cancel the alarm
boolean shouldSet = false;
boolean shouldCancel = false;
final boolean alarmIsActive = (mAlarmScheduleTime != null) && (now < mAlarmScheduleTime);
- final boolean needAlarm = alarmTime != Long.MAX_VALUE;
- if (needAlarm) {
- // Need the alarm if
- // - it's currently not set
- // - if the alarm is set in the past.
- if (!alarmIsActive || alarmTime < mAlarmScheduleTime) {
+
+ if (alarmTime != Long.MAX_VALUE) {
+ // Need the alarm if it isn't set or has changed.
+ if (!alarmIsActive || alarmTime != mAlarmScheduleTime) {
shouldSet = true;
}
} else {
@@ -3329,14 +3236,6 @@
}
}
- private void sendSyncStateIntent() {
- Intent syncStateIntent = new Intent(Intent.ACTION_SYNC_STATE_CHANGED);
- syncStateIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
- syncStateIntent.putExtra("active", mNeedSyncActiveNotification);
- syncStateIntent.putExtra("failing", false);
- mContext.sendBroadcastAsUser(syncStateIntent, UserHandle.OWNER);
- }
-
private void installHandleTooManyDeletesNotification(Account account, String authority,
long numDeletes, int userId) {
if (mNotificationMgr == null) return;
diff --git a/services/core/java/com/android/server/media/projection/MediaProjectionManagerService.java b/services/core/java/com/android/server/media/projection/MediaProjectionManagerService.java
index a029b0e..3ea4f2c 100644
--- a/services/core/java/com/android/server/media/projection/MediaProjectionManagerService.java
+++ b/services/core/java/com/android/server/media/projection/MediaProjectionManagerService.java
@@ -127,9 +127,7 @@
IBinder.DeathRecipient deathRecipient = new IBinder.DeathRecipient() {
@Override
public void binderDied() {
- synchronized (mLock) {
- removeCallback(callback);
- }
+ removeCallback(callback);
}
};
synchronized (mLock) {
@@ -344,6 +342,7 @@
public final String packageName;
public final UserHandle userHandle;
+ private IMediaProjectionCallback mCallback;
private IBinder mToken;
private IBinder.DeathRecipient mDeathEater;
private int mType;
@@ -406,7 +405,8 @@
throw new IllegalStateException(
"Cannot start already started MediaProjection");
}
- registerCallback(callback);
+ mCallback = callback;
+ registerCallback(mCallback);
try {
mToken = callback.asBinder();
mDeathEater = new IBinder.DeathRecipient() {
@@ -435,8 +435,11 @@
+ "pid=" + Binder.getCallingPid() + ")");
return;
}
- mToken.unlinkToDeath(mDeathEater, 0);
stopProjectionLocked(this);
+ mToken.unlinkToDeath(mDeathEater, 0);
+ mToken = null;
+ unregisterCallback(mCallback);
+ mCallback = null;
}
}
diff --git a/services/core/java/com/android/server/notification/NotificationManagerService.java b/services/core/java/com/android/server/notification/NotificationManagerService.java
index 7a6895f..9426b76 100644
--- a/services/core/java/com/android/server/notification/NotificationManagerService.java
+++ b/services/core/java/com/android/server/notification/NotificationManagerService.java
@@ -1842,7 +1842,7 @@
}
pw.println(':');
int N;
- final boolean zenOnly = filter != null && filter.zen;
+ final boolean zenOnly = filter.filtered && filter.zen;
if (!zenOnly) {
synchronized (mToastQueue) {
@@ -1864,13 +1864,13 @@
pw.println(" Notification List:");
for (int i=0; i<N; i++) {
final NotificationRecord nr = mNotificationList.get(i);
- if (filter != null && !filter.matches(nr.sbn)) continue;
+ if (filter.filtered && !filter.matches(nr.sbn)) continue;
nr.dump(pw, " ", getContext(), filter.redact);
}
pw.println(" ");
}
- if (filter == null) {
+ if (!filter.filtered) {
N = mLights.size();
if (N > 0) {
pw.println(" Lights List:");
@@ -1911,7 +1911,7 @@
mUsageStats.dump(pw, " ", filter);
}
- if (filter == null || zenOnly) {
+ if (!filter.filtered || zenOnly) {
pw.println("\n Zen Mode:");
pw.print(" mInterruptionFilter="); pw.println(mInterruptionFilter);
mZenModeHelper.dump(pw, " ");
diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java
index 26304ab..11e30b5 100644
--- a/services/core/java/com/android/server/pm/PackageManagerService.java
+++ b/services/core/java/com/android/server/pm/PackageManagerService.java
@@ -5435,7 +5435,7 @@
}
@Override
- public List<ProviderInfo> queryContentProviders(String processName,
+ public ParceledListSlice<ProviderInfo> queryContentProviders(String processName,
int uid, int flags) {
ArrayList<ProviderInfo> finalList = null;
// reader
@@ -5467,9 +5467,10 @@
if (finalList != null) {
Collections.sort(finalList, mProviderInitOrderSorter);
+ return new ParceledListSlice<ProviderInfo>(finalList);
}
- return finalList;
+ return null;
}
@Override
@@ -15813,16 +15814,27 @@
"Cannot move system application");
}
- if (Objects.equals(ps.volumeUuid, volumeUuid)) {
- throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR,
- "Package already moved to " + volumeUuid);
+ if (pkg.applicationInfo.isExternalAsec()) {
+ currentAsec = true;
+ currentVolumeUuid = StorageManager.UUID_PRIMARY_PHYSICAL;
+ } else if (pkg.applicationInfo.isForwardLocked()) {
+ currentAsec = true;
+ currentVolumeUuid = "forward_locked";
+ } else {
+ currentAsec = false;
+ currentVolumeUuid = ps.volumeUuid;
+
+ final File probe = new File(pkg.codePath);
+ final File probeOat = new File(probe, "oat");
+ if (!probe.isDirectory() || !probeOat.isDirectory()) {
+ throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR,
+ "Move only supported for modern cluster style installs");
+ }
}
- final File probe = new File(pkg.codePath);
- final File probeOat = new File(probe, "oat");
- if (!probe.isDirectory() || !probeOat.isDirectory()) {
+ if (Objects.equals(currentVolumeUuid, volumeUuid)) {
throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR,
- "Move only supported for modern cluster style installs");
+ "Package already moved to " + volumeUuid);
}
if (ps.frozen) {
@@ -15831,9 +15843,6 @@
}
ps.frozen = true;
- currentAsec = pkg.applicationInfo.isForwardLocked()
- || pkg.applicationInfo.isExternalAsec();
- currentVolumeUuid = ps.volumeUuid;
codeFile = new File(pkg.codePath);
installerPackageName = ps.installerPackageName;
packageAbiOverride = ps.cpuAbiOverrideString;
diff --git a/services/core/java/com/android/server/pm/Settings.java b/services/core/java/com/android/server/pm/Settings.java
index 736b153..82ffa47 100644
--- a/services/core/java/com/android/server/pm/Settings.java
+++ b/services/core/java/com/android/server/pm/Settings.java
@@ -613,6 +613,7 @@
p.sharedUser = origPackage.sharedUser;
p.appId = origPackage.appId;
p.origPackage = origPackage;
+ p.getPermissionsState().copyFrom(origPackage.getPermissionsState());
mRenamedPackages.put(name, origPackage.name);
name = origPackage.name;
// Update new package state.
@@ -812,6 +813,20 @@
p.sharedUser = sharedUser;
p.appId = sharedUser.userId;
}
+
+ // If the we know about this user id, we have to update it as it
+ // has to point to the same PackageSetting instance as the package.
+ Object userIdPs = getUserIdLPr(p.appId);
+ if (sharedUser == null) {
+ if (userIdPs != null && userIdPs != p) {
+ replaceUserIdLPw(p.appId, p);
+ }
+ } else {
+ if (userIdPs != null && userIdPs != sharedUser) {
+ replaceUserIdLPw(p.appId, sharedUser);
+ }
+ }
+
IntentFilterVerificationInfo ivi = mRestoredIntentFilterVerifications.get(name);
if (ivi != null) {
if (DEBUG_DOMAIN_VERIFICATION) {
diff --git a/services/tests/servicestests/src/com/android/server/ConnectivityServiceTest.java b/services/tests/servicestests/src/com/android/server/ConnectivityServiceTest.java
index 19d29f3..696f106 100644
--- a/services/tests/servicestests/src/com/android/server/ConnectivityServiceTest.java
+++ b/services/tests/servicestests/src/com/android/server/ConnectivityServiceTest.java
@@ -937,6 +937,19 @@
}
private void tryNetworkFactoryRequests(int capability) throws Exception {
+ // Verify NOT_RESTRICTED is set appropriately
+ final NetworkCapabilities nc = new NetworkRequest.Builder().addCapability(capability)
+ .build().networkCapabilities;
+ if (capability == NET_CAPABILITY_CBS || capability == NET_CAPABILITY_DUN ||
+ capability == NET_CAPABILITY_EIMS || capability == NET_CAPABILITY_FOTA ||
+ capability == NET_CAPABILITY_IA || capability == NET_CAPABILITY_IMS ||
+ capability == NET_CAPABILITY_RCS || capability == NET_CAPABILITY_XCAP ||
+ capability == NET_CAPABILITY_TRUSTED || capability == NET_CAPABILITY_NOT_VPN) {
+ assertFalse(nc.hasCapability(NET_CAPABILITY_NOT_RESTRICTED));
+ } else {
+ assertTrue(nc.hasCapability(NET_CAPABILITY_NOT_RESTRICTED));
+ }
+
NetworkCapabilities filter = new NetworkCapabilities();
filter.addCapability(capability);
final HandlerThread handlerThread = new HandlerThread("testNetworkFactoryRequests");
diff --git a/services/usb/java/com/android/server/usb/UsbDeviceManager.java b/services/usb/java/com/android/server/usb/UsbDeviceManager.java
index 1787b91..09e15a8 100644
--- a/services/usb/java/com/android/server/usb/UsbDeviceManager.java
+++ b/services/usb/java/com/android/server/usb/UsbDeviceManager.java
@@ -49,10 +49,8 @@
import com.android.server.FgThread;
import java.io.File;
-import java.io.FileDescriptor;
import java.io.FileNotFoundException;
import java.io.IOException;
-import java.io.PrintWriter;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
@@ -316,6 +314,9 @@
// Restore default functions.
mCurrentFunctions = SystemProperties.get(USB_CONFIG_PROPERTY,
UsbManager.USB_FUNCTION_NONE);
+ if (UsbManager.USB_FUNCTION_NONE.equals(mCurrentFunctions)) {
+ mCurrentFunctions = UsbManager.USB_FUNCTION_MTP;
+ }
mCurrentFunctionsApplied = mCurrentFunctions.equals(
SystemProperties.get(USB_STATE_PROPERTY));
mAdbEnabled = UsbManager.containsFunction(getDefaultFunctions(),
@@ -400,6 +401,14 @@
return waitForState(config);
}
+ private void setUsbDataUnlocked(boolean enable) {
+ if (DEBUG) Slog.d(TAG, "setUsbDataUnlocked: " + enable);
+ mUsbDataUnlocked = enable;
+ updateUsbNotification();
+ updateUsbStateBroadcast();
+ setEnabledFunctions(mCurrentFunctions, true);
+ }
+
private void setAdbEnabled(boolean enable) {
if (DEBUG) Slog.d(TAG, "setAdbEnabled: " + enable);
if (enable != mAdbEnabled) {
@@ -471,7 +480,6 @@
}
functions = applyAdbFunction(functions);
functions = applyOemOverrideFunction(functions);
- functions = applyUserRestrictions(functions);
if (!mCurrentFunctions.equals(functions) || !mCurrentFunctionsApplied
|| forceRestart) {
@@ -502,13 +510,9 @@
return functions;
}
- private String applyUserRestrictions(String functions) {
+ private boolean isUsbTransferAllowed() {
UserManager userManager = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
- if (userManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER)) {
- functions = UsbManager.removeFunction(functions, UsbManager.USB_FUNCTION_MTP);
- functions = UsbManager.removeFunction(functions, UsbManager.USB_FUNCTION_PTP);
- }
- return functions;
+ return !userManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER);
}
private void updateCurrentAccessory() {
@@ -555,7 +559,7 @@
| Intent.FLAG_RECEIVER_FOREGROUND);
intent.putExtra(UsbManager.USB_CONNECTED, mConnected);
intent.putExtra(UsbManager.USB_CONFIGURED, mConfigured);
- intent.putExtra(UsbManager.USB_DATA_UNLOCKED, mUsbDataUnlocked);
+ intent.putExtra(UsbManager.USB_DATA_UNLOCKED, isUsbTransferAllowed() && mUsbDataUnlocked);
if (mCurrentFunctions != null) {
String[] functions = mCurrentFunctions.split(",");
@@ -659,10 +663,7 @@
setEnabledFunctions(mCurrentFunctions, false);
break;
case MSG_SET_USB_DATA_UNLOCKED:
- mUsbDataUnlocked = (msg.arg1 == 1);
- updateUsbNotification();
- updateUsbStateBroadcast();
- setEnabledFunctions(mCurrentFunctions, true);
+ setUsbDataUnlocked(msg.arg1 == 1);
break;
case MSG_SYSTEM_READY:
updateUsbNotification();
@@ -807,8 +808,12 @@
}
private String getDefaultFunctions() {
- return SystemProperties.get(USB_PERSISTENT_CONFIG_PROPERTY,
- UsbManager.USB_FUNCTION_ADB);
+ String func = SystemProperties.get(USB_PERSISTENT_CONFIG_PROPERTY,
+ UsbManager.USB_FUNCTION_NONE);
+ if (UsbManager.USB_FUNCTION_NONE.equals(func)) {
+ func = UsbManager.USB_FUNCTION_MTP;
+ }
+ return func;
}
public void dump(IndentingPrintWriter pw) {
@@ -817,6 +822,7 @@
pw.println(" mCurrentFunctionsApplied: " + mCurrentFunctionsApplied);
pw.println(" mConnected: " + mConnected);
pw.println(" mConfigured: " + mConfigured);
+ pw.println(" mUsbDataUnlocked: " + mUsbDataUnlocked);
pw.println(" mCurrentAccessory: " + mCurrentAccessory);
try {
pw.println(" Kernel state: "
@@ -864,11 +870,6 @@
mHandler.sendMessage(MSG_SET_USB_DATA_UNLOCKED, unlocked);
}
- public boolean isUsbDataUnlocked() {
- if (DEBUG) Slog.d(TAG, "isUsbDataUnlocked() -> " + mHandler.mUsbDataUnlocked);
- return mHandler.mUsbDataUnlocked;
- }
-
private void readOemUsbOverrideConfig() {
String[] configList = mContext.getResources().getStringArray(
com.android.internal.R.array.config_oemUsbModeOverride);
diff --git a/services/usb/java/com/android/server/usb/UsbService.java b/services/usb/java/com/android/server/usb/UsbService.java
index f93a2ef..edd9201 100644
--- a/services/usb/java/com/android/server/usb/UsbService.java
+++ b/services/usb/java/com/android/server/usb/UsbService.java
@@ -322,23 +322,10 @@
@Override
public void setUsbDataUnlocked(boolean unlocked) {
mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USB, null);
- // If attempt to change USB function while file transfer is restricted, ensure that
- // usb data is always locked, and return.
- UserManager userManager = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
- if (userManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER)) {
- if (mDeviceManager != null) mDeviceManager.setUsbDataUnlocked(false);
- return;
- }
mDeviceManager.setUsbDataUnlocked(unlocked);
}
@Override
- public boolean isUsbDataUnlocked() {
- mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USB, null);
- return mDeviceManager.isUsbDataUnlocked();
- }
-
- @Override
public void allowUsbDebugging(boolean alwaysAllow, String publicKey) {
mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USB, null);
mDeviceManager.allowUsbDebugging(alwaysAllow, publicKey);
diff --git a/tests/VoiceInteraction/res/layout/test_interaction.xml b/tests/VoiceInteraction/res/layout/test_interaction.xml
index d1a7ad5..277117e 100644
--- a/tests/VoiceInteraction/res/layout/test_interaction.xml
+++ b/tests/VoiceInteraction/res/layout/test_interaction.xml
@@ -39,6 +39,19 @@
android:layout_marginTop="16dp"
android:orientation="horizontal">
+ <Button android:id="@+id/airplane"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/launchAirplane"
+ />
+
+ </LinearLayout>
+
+ <LinearLayout android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_marginTop="16dp"
+ android:orientation="horizontal">
+
<Button android:id="@+id/complete"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
diff --git a/tests/VoiceInteraction/res/values/strings.xml b/tests/VoiceInteraction/res/values/strings.xml
index 29ffe21..c665c23 100644
--- a/tests/VoiceInteraction/res/values/strings.xml
+++ b/tests/VoiceInteraction/res/values/strings.xml
@@ -21,6 +21,7 @@
<string name="tree">Tree</string>
<string name="text">Text</string>
<string name="asyncStructure">(Async structure goes here)</string>
+ <string name="launchAirplane">Launch airplane mode</string>
<string name="confirm">Confirm</string>
<string name="abort">Abort</string>
<string name="complete">Complete</string>
diff --git a/tests/VoiceInteraction/src/com/android/test/voiceinteraction/TestInteractionActivity.java b/tests/VoiceInteraction/src/com/android/test/voiceinteraction/TestInteractionActivity.java
index e10d89f..ada0e21 100644
--- a/tests/VoiceInteraction/src/com/android/test/voiceinteraction/TestInteractionActivity.java
+++ b/tests/VoiceInteraction/src/com/android/test/voiceinteraction/TestInteractionActivity.java
@@ -21,6 +21,7 @@
import android.content.ComponentName;
import android.content.Intent;
import android.os.Bundle;
+import android.provider.Settings;
import android.service.voice.VoiceInteractionService;
import android.util.Log;
import android.view.View;
@@ -39,6 +40,7 @@
VoiceInteractor mInteractor;
VoiceInteractor.Request mCurrentRequest = null;
TextView mLog;
+ Button mAirplaneButton;
Button mAbortButton;
Button mCompleteButton;
Button mCommandButton;
@@ -65,6 +67,8 @@
setContentView(R.layout.test_interaction);
mLog = (TextView)findViewById(R.id.log);
+ mAirplaneButton = (Button)findViewById(R.id.airplane);
+ mAirplaneButton.setOnClickListener(this);
mAbortButton = (Button)findViewById(R.id.abort);
mAbortButton.setOnClickListener(this);
mCompleteButton = (Button)findViewById(R.id.complete);
@@ -122,7 +126,12 @@
@Override
public void onClick(View v) {
- if (v == mAbortButton) {
+ if (v == mAirplaneButton) {
+ Intent intent = new Intent(Settings.ACTION_VOICE_CONTROL_AIRPLANE_MODE);
+ intent.addCategory(Intent.CATEGORY_VOICE);
+ intent.putExtra(Settings.EXTRA_AIRPLANE_MODE_ENABLED, true);
+ startActivity(intent);
+ } else if (v == mAbortButton) {
VoiceInteractor.AbortVoiceRequest req = new TestAbortVoice();
mInteractor.submitRequest(req, REQUEST_ABORT);
} else if (v == mCompleteButton) {
diff --git a/tools/layoutlib/bridge/src/android/graphics/Matrix_Delegate.java b/tools/layoutlib/bridge/src/android/graphics/Matrix_Delegate.java
index 1105c7b..a503e50 100644
--- a/tools/layoutlib/bridge/src/android/graphics/Matrix_Delegate.java
+++ b/tools/layoutlib/bridge/src/android/graphics/Matrix_Delegate.java
@@ -673,7 +673,7 @@
return;
}
- System.arraycopy(d.mValues, 0, d.mValues, 0, MATRIX_SIZE);
+ System.arraycopy(d.mValues, 0, values, 0, MATRIX_SIZE);
}
@LayoutlibDelegate
diff --git a/tools/layoutlib/bridge/src/android/graphics/Path_Delegate.java b/tools/layoutlib/bridge/src/android/graphics/Path_Delegate.java
index 34d0985..3c9a062 100644
--- a/tools/layoutlib/bridge/src/android/graphics/Path_Delegate.java
+++ b/tools/layoutlib/bridge/src/android/graphics/Path_Delegate.java
@@ -36,7 +36,6 @@
import java.awt.geom.Point2D;
import java.awt.geom.Rectangle2D;
import java.awt.geom.RoundRectangle2D;
-import java.util.ArrayList;
/**
* Delegate implementing the native methods of android.graphics.Path
@@ -504,13 +503,13 @@
switch (type) {
case PathIterator.SEG_MOVETO:
case PathIterator.SEG_LINETO:
- store(coords, tmp, 1, isFirstPoint);
+ store(tmp, coords, 1, isFirstPoint);
break;
case PathIterator.SEG_QUADTO:
- store(coords, tmp, 2, isFirstPoint);
+ store(tmp, coords, 2, isFirstPoint);
break;
case PathIterator.SEG_CUBICTO:
- store(coords, tmp, 3, isFirstPoint);
+ store(tmp, coords, 3, isFirstPoint);
break;
case PathIterator.SEG_CLOSE:
// No points returned.
@@ -528,14 +527,14 @@
private static void store(float[] src, float[] dst, int count, boolean isFirst) {
if (isFirst) {
- dst[0] = 0;
- dst[1] = src[0];
- dst[2] = src[1];
+ dst[0] = 0; // fraction
+ dst[1] = src[0]; // abscissa
+ dst[2] = src[1]; // ordinate
}
if (count > 1 || !isFirst) {
dst[3] = 1;
- dst[4] = src[2 * count];
- dst[5] = src[2 * count + 1];
+ dst[4] = src[2 * count - 2];
+ dst[5] = src[2 * count - 1];
}
}
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Layout.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Layout.java
index 8c7ea8a..c72c979 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Layout.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Layout.java
@@ -83,7 +83,7 @@
// Theme attributes used for configuring appearance of the system decor.
private static final String ATTR_WINDOW_FLOATING = "windowIsFloating";
private static final String ATTR_WINDOW_BACKGROUND = "windowBackground";
- private static final String ATTR_WINDOW_FULL_SCREEN = "windowFullScreen";
+ private static final String ATTR_WINDOW_FULL_SCREEN = "windowFullscreen";
private static final String ATTR_NAV_BAR_HEIGHT = "navigation_bar_height";
private static final String ATTR_NAV_BAR_WIDTH = "navigation_bar_width";
private static final String ATTR_STATUS_BAR_HEIGHT = "status_bar_height";
@@ -329,9 +329,12 @@
mWindowIsFloating = getBooleanThemeValue(mResources, ATTR_WINDOW_FLOATING, true, true);
findBackground();
- findStatusBar();
- findActionBar();
- findNavBar();
+
+ if (!mParams.isForceNoDecor()) {
+ findStatusBar();
+ findActionBar();
+ findNavBar();
+ }
}
private void findBackground() {
diff --git a/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/array_check.png b/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/array_check.png
index 9a13568..336f9d8 100644
--- a/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/array_check.png
+++ b/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/array_check.png
Binary files differ
diff --git a/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/expand_horz_layout.png b/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/expand_horz_layout.png
index 92eb3e1..0c16215 100644
--- a/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/expand_horz_layout.png
+++ b/tools/layoutlib/bridge/tests/res/testApp/MyApplication/golden/expand_horz_layout.png
Binary files differ
diff --git a/tools/layoutlib/bridge/tests/src/com/android/layoutlib/bridge/intensive/Main.java b/tools/layoutlib/bridge/tests/src/com/android/layoutlib/bridge/intensive/Main.java
index ee448ca..9ebeebd 100644
--- a/tools/layoutlib/bridge/tests/src/com/android/layoutlib/bridge/intensive/Main.java
+++ b/tools/layoutlib/bridge/tests/src/com/android/layoutlib/bridge/intensive/Main.java
@@ -329,8 +329,8 @@
.setNavigation(Navigation.NONAV);
SessionParams params = getSessionParams(parser, customConfigGenerator,
- layoutLibCallback, "Theme.Material.NoActionBar.Fullscreen", RenderingMode.V_SCROLL,
- 22);
+ layoutLibCallback, "Theme.Material.NoActionBar.Fullscreen", false,
+ RenderingMode.V_SCROLL, 22);
renderAndVerify(params, "expand_vert_layout.png");
@@ -342,8 +342,8 @@
parser = new LayoutPullParser(APP_TEST_RES + "/layout/" +
"expand_horz_layout.xml");
params = getSessionParams(parser, customConfigGenerator,
- layoutLibCallback, "Theme.Material.NoActionBar.Fullscreen", RenderingMode
- .H_SCROLL, 22);
+ layoutLibCallback, "Theme.Material.NoActionBar.Fullscreen", false,
+ RenderingMode.H_SCROLL, 22);
renderAndVerify(params, "expand_horz_layout.png");
}
@@ -390,7 +390,7 @@
// TODO: Set up action bar handler properly to test menu rendering.
// Create session params.
SessionParams params = getSessionParams(parser, ConfigGenerator.NEXUS_5,
- layoutLibCallback, "Theme.Material.Light.DarkActionBar", RenderingMode.NORMAL, 22);
+ layoutLibCallback, "AppTheme", true, RenderingMode.NORMAL, 22);
renderAndVerify(params, goldenFileName);
}
@@ -399,12 +399,12 @@
*/
private SessionParams getSessionParams(LayoutPullParser layoutParser,
ConfigGenerator configGenerator, LayoutLibTestCallback layoutLibCallback,
- String themeName, RenderingMode renderingMode, int targetSdk) {
+ String themeName, boolean isProjectTheme, RenderingMode renderingMode, int targetSdk) {
FolderConfiguration config = configGenerator.getFolderConfig();
ResourceResolver resourceResolver =
ResourceResolver.create(sProjectResources.getConfiguredResources(config),
sFrameworkRepo.getConfiguredResources(config),
- themeName, false);
+ themeName, isProjectTheme);
return new SessionParams(
layoutParser,
diff --git a/wifi/java/android/net/wifi/ScanResult.java b/wifi/java/android/net/wifi/ScanResult.java
index cc1e976..8a20012 100644
--- a/wifi/java/android/net/wifi/ScanResult.java
+++ b/wifi/java/android/net/wifi/ScanResult.java
@@ -363,11 +363,10 @@
}
/** {@hide} */
- public ScanResult(WifiSsid wifiSsid, String BSSID, String caps, int level, int frequency,
+ public ScanResult(String Ssid, String BSSID, String caps, int level, int frequency,
long tsf, int distCm, int distSdCm, int channelWidth, int centerFreq0, int centerFreq1,
boolean is80211McRTTResponder) {
- this.wifiSsid = wifiSsid;
- this.SSID = (wifiSsid != null) ? wifiSsid.toString() : WifiSsid.NONE;
+ this.SSID = Ssid;
this.BSSID = BSSID;
this.capabilities = caps;
this.level = level;
@@ -385,6 +384,15 @@
}
}
+ /** {@hide} */
+ public ScanResult(WifiSsid wifiSsid, String Ssid, String BSSID, String caps, int level,
+ int frequency, long tsf, int distCm, int distSdCm, int channelWidth,
+ int centerFreq0, int centerFreq1, boolean is80211McRTTResponder) {
+ this(Ssid, BSSID, caps,level, frequency, tsf, distCm, distSdCm, channelWidth, centerFreq0,
+ centerFreq1, is80211McRTTResponder);
+ this.wifiSsid = wifiSsid;
+ }
+
/** copy constructor {@hide} */
public ScanResult(ScanResult source) {
if (source != null) {
@@ -469,6 +477,7 @@
} else {
dest.writeInt(0);
}
+ dest.writeString(SSID);
dest.writeString(BSSID);
dest.writeString(capabilities);
dest.writeInt(level);
@@ -512,6 +521,7 @@
}
ScanResult sr = new ScanResult(
wifiSsid,
+ in.readString(), /* SSID */
in.readString(), /* BSSID */
in.readString(), /* capabilities */
in.readInt(), /* level */
diff --git a/wifi/java/android/net/wifi/WifiScanner.java b/wifi/java/android/net/wifi/WifiScanner.java
index a3dc077..a65f250 100644
--- a/wifi/java/android/net/wifi/WifiScanner.java
+++ b/wifi/java/android/net/wifi/WifiScanner.java
@@ -255,9 +255,7 @@
mResults = new ScanResult[s.mResults.length];
for (int i = 0; i < s.mResults.length; i++) {
ScanResult result = s.mResults[i];
- WifiSsid wifiSsid = WifiSsid.createFromAsciiEncoded(result.SSID);
ScanResult newResult = new ScanResult(result);
- newResult.wifiSsid = wifiSsid;
mResults[i] = newResult;
}
}