Merge "Don't mix UI and print job state" into nyc-dev
diff --git a/api/current.txt b/api/current.txt
index 4c069cd..936ca88 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -10101,27 +10101,22 @@
method public final long skip(long) throws java.io.IOException;
}
- public class ColorStateList extends android.content.res.ComplexColor implements android.os.Parcelable {
+ public class ColorStateList implements android.os.Parcelable {
ctor public ColorStateList(int[][], int[]);
method public static deprecated android.content.res.ColorStateList createFromXml(android.content.res.Resources, org.xmlpull.v1.XmlPullParser) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
method public static android.content.res.ColorStateList createFromXml(android.content.res.Resources, org.xmlpull.v1.XmlPullParser, android.content.res.Resources.Theme) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
method public int describeContents();
+ method public int getChangingConfigurations();
method public int getColorForState(int[], int);
method public int getDefaultColor();
method public boolean isOpaque();
+ method public boolean isStateful();
method public static android.content.res.ColorStateList valueOf(int);
method public android.content.res.ColorStateList withAlpha(int);
method public void writeToParcel(android.os.Parcel, int);
field public static final android.os.Parcelable.Creator<android.content.res.ColorStateList> CREATOR;
}
- public abstract class ComplexColor {
- ctor public ComplexColor();
- method public int getChangingConfigurations();
- method public abstract int getDefaultColor();
- method public boolean isStateful();
- }
-
public final class Configuration implements java.lang.Comparable android.os.Parcelable {
ctor public Configuration();
ctor public Configuration(android.content.res.Configuration);
@@ -10225,11 +10220,6 @@
field public int uiMode;
}
- public class GradientColor extends android.content.res.ComplexColor {
- method public static android.content.res.GradientColor createFromXml(android.content.res.Resources, android.content.res.XmlResourceParser, android.content.res.Resources.Theme) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
- method public int getDefaultColor();
- }
-
public class ObbInfo implements android.os.Parcelable {
method public int describeContents();
method public void writeToParcel(android.os.Parcel, int);
@@ -10289,7 +10279,6 @@
method public void getValue(java.lang.String, android.util.TypedValue, boolean) throws android.content.res.Resources.NotFoundException;
method public void getValueForDensity(int, int, android.util.TypedValue, boolean) throws android.content.res.Resources.NotFoundException;
method public android.content.res.XmlResourceParser getXml(int) throws android.content.res.Resources.NotFoundException;
- method public android.content.res.ComplexColor loadComplexColor(android.util.TypedValue, int, android.content.res.Resources.Theme);
method public final android.content.res.Resources.Theme newTheme();
method public android.content.res.TypedArray obtainAttributes(android.util.AttributeSet, int[]);
method public android.content.res.TypedArray obtainTypedArray(int) throws android.content.res.Resources.NotFoundException;
@@ -10325,7 +10314,6 @@
method public int getChangingConfigurations();
method public int getColor(int, int);
method public android.content.res.ColorStateList getColorStateList(int);
- method public android.content.res.ComplexColor getComplexColor(int);
method public float getDimension(int, float);
method public int getDimensionPixelOffset(int, int);
method public int getDimensionPixelSize(int, int);
@@ -36719,11 +36707,10 @@
method public void notifyConfigChanged(int);
method public deprecated void notifyConfigChangedForSubId(int);
field public static final java.lang.String ACTION_CARRIER_CONFIG_CHANGED = "android.telephony.action.CARRIER_CONFIG_CHANGED";
- field public static final java.lang.String BOOL_ALLOW_EMERGENCY_VIDEO_CALLS = "bool_allow_emergency_video_calls";
- field public static final java.lang.String BOOL_ALLOW_VIDEO_PAUSE = "bool_allow_video_pause";
field public static final java.lang.String KEY_ADDITIONAL_CALL_SETTING_BOOL = "additional_call_setting_bool";
field public static final java.lang.String KEY_ALLOW_ADDING_APNS_BOOL = "allow_adding_apns_bool";
field public static final java.lang.String KEY_ALLOW_EMERGENCY_NUMBERS_IN_CALL_LOG_BOOL = "allow_emergency_numbers_in_call_log_bool";
+ field public static final java.lang.String KEY_ALLOW_EMERGENCY_VIDEO_CALLS_BOOL = "allow_emergency_video_calls_bool";
field public static final java.lang.String KEY_ALLOW_LOCAL_DTMF_TONES_BOOL = "allow_local_dtmf_tones_bool";
field public static final java.lang.String KEY_ALLOW_NON_EMERGENCY_CALLS_IN_ECM_BOOL = "allow_non_emergency_calls_in_ecm_bool";
field public static final java.lang.String KEY_ALWAYS_SHOW_EMERGENCY_ALERT_ONOFF_BOOL = "always_show_emergency_alert_onoff_bool";
@@ -39766,8 +39753,10 @@
method public static final boolean addLinks(android.widget.TextView, int);
method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String);
method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String, android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
+ method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String, java.lang.String[], android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String);
method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String, android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
+ method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String, java.lang.String[], android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
field public static final int ALL = 15; // 0xf
field public static final int EMAIL_ADDRESSES = 2; // 0x2
field public static final int MAP_ADDRESSES = 8; // 0x8
diff --git a/api/system-current.txt b/api/system-current.txt
index 1ed7ac2..f8863e5 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -10499,27 +10499,22 @@
method public final long skip(long) throws java.io.IOException;
}
- public class ColorStateList extends android.content.res.ComplexColor implements android.os.Parcelable {
+ public class ColorStateList implements android.os.Parcelable {
ctor public ColorStateList(int[][], int[]);
method public static deprecated android.content.res.ColorStateList createFromXml(android.content.res.Resources, org.xmlpull.v1.XmlPullParser) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
method public static android.content.res.ColorStateList createFromXml(android.content.res.Resources, org.xmlpull.v1.XmlPullParser, android.content.res.Resources.Theme) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
method public int describeContents();
+ method public int getChangingConfigurations();
method public int getColorForState(int[], int);
method public int getDefaultColor();
method public boolean isOpaque();
+ method public boolean isStateful();
method public static android.content.res.ColorStateList valueOf(int);
method public android.content.res.ColorStateList withAlpha(int);
method public void writeToParcel(android.os.Parcel, int);
field public static final android.os.Parcelable.Creator<android.content.res.ColorStateList> CREATOR;
}
- public abstract class ComplexColor {
- ctor public ComplexColor();
- method public int getChangingConfigurations();
- method public abstract int getDefaultColor();
- method public boolean isStateful();
- }
-
public final class Configuration implements java.lang.Comparable android.os.Parcelable {
ctor public Configuration();
ctor public Configuration(android.content.res.Configuration);
@@ -10623,11 +10618,6 @@
field public int uiMode;
}
- public class GradientColor extends android.content.res.ComplexColor {
- method public static android.content.res.GradientColor createFromXml(android.content.res.Resources, android.content.res.XmlResourceParser, android.content.res.Resources.Theme) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
- method public int getDefaultColor();
- }
-
public class ObbInfo implements android.os.Parcelable {
method public int describeContents();
method public void writeToParcel(android.os.Parcel, int);
@@ -10687,7 +10677,6 @@
method public void getValue(java.lang.String, android.util.TypedValue, boolean) throws android.content.res.Resources.NotFoundException;
method public void getValueForDensity(int, int, android.util.TypedValue, boolean) throws android.content.res.Resources.NotFoundException;
method public android.content.res.XmlResourceParser getXml(int) throws android.content.res.Resources.NotFoundException;
- method public android.content.res.ComplexColor loadComplexColor(android.util.TypedValue, int, android.content.res.Resources.Theme);
method public final android.content.res.Resources.Theme newTheme();
method public android.content.res.TypedArray obtainAttributes(android.util.AttributeSet, int[]);
method public android.content.res.TypedArray obtainTypedArray(int) throws android.content.res.Resources.NotFoundException;
@@ -10723,7 +10712,6 @@
method public int getChangingConfigurations();
method public int getColor(int, int);
method public android.content.res.ColorStateList getColorStateList(int);
- method public android.content.res.ComplexColor getComplexColor(int);
method public float getDimension(int, float);
method public int getDimensionPixelOffset(int, int);
method public int getDimensionPixelSize(int, int);
@@ -39380,11 +39368,10 @@
method public deprecated void notifyConfigChangedForSubId(int);
method public void updateConfigForPhoneId(int, java.lang.String);
field public static final java.lang.String ACTION_CARRIER_CONFIG_CHANGED = "android.telephony.action.CARRIER_CONFIG_CHANGED";
- field public static final java.lang.String BOOL_ALLOW_EMERGENCY_VIDEO_CALLS = "bool_allow_emergency_video_calls";
- field public static final java.lang.String BOOL_ALLOW_VIDEO_PAUSE = "bool_allow_video_pause";
field public static final java.lang.String KEY_ADDITIONAL_CALL_SETTING_BOOL = "additional_call_setting_bool";
field public static final java.lang.String KEY_ALLOW_ADDING_APNS_BOOL = "allow_adding_apns_bool";
field public static final java.lang.String KEY_ALLOW_EMERGENCY_NUMBERS_IN_CALL_LOG_BOOL = "allow_emergency_numbers_in_call_log_bool";
+ field public static final java.lang.String KEY_ALLOW_EMERGENCY_VIDEO_CALLS_BOOL = "allow_emergency_video_calls_bool";
field public static final java.lang.String KEY_ALLOW_LOCAL_DTMF_TONES_BOOL = "allow_local_dtmf_tones_bool";
field public static final java.lang.String KEY_ALLOW_NON_EMERGENCY_CALLS_IN_ECM_BOOL = "allow_non_emergency_calls_in_ecm_bool";
field public static final java.lang.String KEY_ALWAYS_SHOW_EMERGENCY_ALERT_ONOFF_BOOL = "always_show_emergency_alert_onoff_bool";
@@ -42491,8 +42478,10 @@
method public static final boolean addLinks(android.widget.TextView, int);
method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String);
method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String, android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
+ method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String, java.lang.String[], android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String);
method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String, android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
+ method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String, java.lang.String[], android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
field public static final int ALL = 15; // 0xf
field public static final int EMAIL_ADDRESSES = 2; // 0x2
field public static final int MAP_ADDRESSES = 8; // 0x8
diff --git a/api/test-current.txt b/api/test-current.txt
index c0f551a..6327dc2 100644
--- a/api/test-current.txt
+++ b/api/test-current.txt
@@ -10111,27 +10111,22 @@
method public final long skip(long) throws java.io.IOException;
}
- public class ColorStateList extends android.content.res.ComplexColor implements android.os.Parcelable {
+ public class ColorStateList implements android.os.Parcelable {
ctor public ColorStateList(int[][], int[]);
method public static deprecated android.content.res.ColorStateList createFromXml(android.content.res.Resources, org.xmlpull.v1.XmlPullParser) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
method public static android.content.res.ColorStateList createFromXml(android.content.res.Resources, org.xmlpull.v1.XmlPullParser, android.content.res.Resources.Theme) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
method public int describeContents();
+ method public int getChangingConfigurations();
method public int getColorForState(int[], int);
method public int getDefaultColor();
method public boolean isOpaque();
+ method public boolean isStateful();
method public static android.content.res.ColorStateList valueOf(int);
method public android.content.res.ColorStateList withAlpha(int);
method public void writeToParcel(android.os.Parcel, int);
field public static final android.os.Parcelable.Creator<android.content.res.ColorStateList> CREATOR;
}
- public abstract class ComplexColor {
- ctor public ComplexColor();
- method public int getChangingConfigurations();
- method public abstract int getDefaultColor();
- method public boolean isStateful();
- }
-
public final class Configuration implements java.lang.Comparable android.os.Parcelable {
ctor public Configuration();
ctor public Configuration(android.content.res.Configuration);
@@ -10235,11 +10230,6 @@
field public int uiMode;
}
- public class GradientColor extends android.content.res.ComplexColor {
- method public static android.content.res.GradientColor createFromXml(android.content.res.Resources, android.content.res.XmlResourceParser, android.content.res.Resources.Theme) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
- method public int getDefaultColor();
- }
-
public class ObbInfo implements android.os.Parcelable {
method public int describeContents();
method public void writeToParcel(android.os.Parcel, int);
@@ -10299,7 +10289,6 @@
method public void getValue(java.lang.String, android.util.TypedValue, boolean) throws android.content.res.Resources.NotFoundException;
method public void getValueForDensity(int, int, android.util.TypedValue, boolean) throws android.content.res.Resources.NotFoundException;
method public android.content.res.XmlResourceParser getXml(int) throws android.content.res.Resources.NotFoundException;
- method public android.content.res.ComplexColor loadComplexColor(android.util.TypedValue, int, android.content.res.Resources.Theme);
method public final android.content.res.Resources.Theme newTheme();
method public android.content.res.TypedArray obtainAttributes(android.util.AttributeSet, int[]);
method public android.content.res.TypedArray obtainTypedArray(int) throws android.content.res.Resources.NotFoundException;
@@ -10335,7 +10324,6 @@
method public int getChangingConfigurations();
method public int getColor(int, int);
method public android.content.res.ColorStateList getColorStateList(int);
- method public android.content.res.ComplexColor getComplexColor(int);
method public float getDimension(int, float);
method public int getDimensionPixelOffset(int, int);
method public int getDimensionPixelSize(int, int);
@@ -36790,11 +36778,10 @@
method public void notifyConfigChanged(int);
method public deprecated void notifyConfigChangedForSubId(int);
field public static final java.lang.String ACTION_CARRIER_CONFIG_CHANGED = "android.telephony.action.CARRIER_CONFIG_CHANGED";
- field public static final java.lang.String BOOL_ALLOW_EMERGENCY_VIDEO_CALLS = "bool_allow_emergency_video_calls";
- field public static final java.lang.String BOOL_ALLOW_VIDEO_PAUSE = "bool_allow_video_pause";
field public static final java.lang.String KEY_ADDITIONAL_CALL_SETTING_BOOL = "additional_call_setting_bool";
field public static final java.lang.String KEY_ALLOW_ADDING_APNS_BOOL = "allow_adding_apns_bool";
field public static final java.lang.String KEY_ALLOW_EMERGENCY_NUMBERS_IN_CALL_LOG_BOOL = "allow_emergency_numbers_in_call_log_bool";
+ field public static final java.lang.String KEY_ALLOW_EMERGENCY_VIDEO_CALLS_BOOL = "allow_emergency_video_calls_bool";
field public static final java.lang.String KEY_ALLOW_LOCAL_DTMF_TONES_BOOL = "allow_local_dtmf_tones_bool";
field public static final java.lang.String KEY_ALLOW_NON_EMERGENCY_CALLS_IN_ECM_BOOL = "allow_non_emergency_calls_in_ecm_bool";
field public static final java.lang.String KEY_ALWAYS_SHOW_EMERGENCY_ALERT_ONOFF_BOOL = "always_show_emergency_alert_onoff_bool";
@@ -39839,8 +39826,10 @@
method public static final boolean addLinks(android.widget.TextView, int);
method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String);
method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String, android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
+ method public static final void addLinks(android.widget.TextView, java.util.regex.Pattern, java.lang.String, java.lang.String[], android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String);
method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String, android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
+ method public static final boolean addLinks(android.text.Spannable, java.util.regex.Pattern, java.lang.String, java.lang.String[], android.text.util.Linkify.MatchFilter, android.text.util.Linkify.TransformFilter);
field public static final int ALL = 15; // 0xf
field public static final int EMAIL_ADDRESSES = 2; // 0x2
field public static final int MAP_ADDRESSES = 8; // 0x8
diff --git a/cmds/am/src/com/android/commands/am/Am.java b/cmds/am/src/com/android/commands/am/Am.java
index e6c5768..86734b1 100644
--- a/cmds/am/src/com/android/commands/am/Am.java
+++ b/cmds/am/src/com/android/commands/am/Am.java
@@ -1814,7 +1814,7 @@
private void resizeStackUnchecked(int stackId, Rect bounds, int delayMs, boolean animate) {
try {
- mAm.resizeStack(stackId, bounds, false, false, animate);
+ mAm.resizeStack(stackId, bounds, false, false, animate, -1);
Thread.sleep(delayMs);
} catch (RemoteException e) {
showError("Error: resizing stack " + e);
diff --git a/core/java/android/accessibilityservice/AccessibilityService.java b/core/java/android/accessibilityservice/AccessibilityService.java
index ddc5b0c..bf823f8 100644
--- a/core/java/android/accessibilityservice/AccessibilityService.java
+++ b/core/java/android/accessibilityservice/AccessibilityService.java
@@ -406,7 +406,9 @@
/**
* Callback for {@link android.view.accessibility.AccessibilityEvent}s.
*
- * @param event An event.
+ * @param event The new event. This event is owned by the caller and cannot be used after
+ * this method returns. Services wishing to use the event after this method returns should
+ * make a copy.
*/
public abstract void onAccessibilityEvent(AccessibilityEvent event);
@@ -493,7 +495,9 @@
* functionality.
* <p>
*
- * @param event The event to be processed.
+ * @param event The event to be processed. This event is owned by the caller and cannot be used
+ * after this method returns. Services wishing to use the event after this method returns should
+ * make a copy.
* @return If true then the event will be consumed and not delivered to
* applications, otherwise it will be delivered as usual.
*/
diff --git a/core/java/android/app/ActivityManagerNative.java b/core/java/android/app/ActivityManagerNative.java
index 5f317b0..f5d7e7e 100644
--- a/core/java/android/app/ActivityManagerNative.java
+++ b/core/java/android/app/ActivityManagerNative.java
@@ -820,7 +820,9 @@
final boolean allowResizeInDockedMode = data.readInt() == 1;
final boolean preserveWindows = data.readInt() == 1;
final boolean animate = data.readInt() == 1;
- resizeStack(stackId, r, allowResizeInDockedMode, preserveWindows, animate);
+ final int animationDuration = data.readInt();
+ resizeStack(stackId,
+ r, allowResizeInDockedMode, preserveWindows, animate, animationDuration);
reply.writeNoException();
return true;
}
@@ -3889,7 +3891,8 @@
}
@Override
public void resizeStack(int stackId, Rect r, boolean allowResizeInDockedMode,
- boolean preserveWindows, boolean animate) throws RemoteException {
+ boolean preserveWindows, boolean animate, int animationDuration)
+ throws RemoteException {
Parcel data = Parcel.obtain();
Parcel reply = Parcel.obtain();
data.writeInterfaceToken(IActivityManager.descriptor);
@@ -3903,6 +3906,7 @@
data.writeInt(allowResizeInDockedMode ? 1 : 0);
data.writeInt(preserveWindows ? 1 : 0);
data.writeInt(animate ? 1 : 0);
+ data.writeInt(animationDuration);
mRemote.transact(RESIZE_STACK_TRANSACTION, data, reply, 0);
reply.readException();
data.recycle();
diff --git a/core/java/android/app/IActivityManager.java b/core/java/android/app/IActivityManager.java
index d0c21f5..639c207 100644
--- a/core/java/android/app/IActivityManager.java
+++ b/core/java/android/app/IActivityManager.java
@@ -148,8 +148,23 @@
public boolean moveTaskToDockedStack(int taskId, int createMode, boolean toTop, boolean animate,
Rect initialBounds) throws RemoteException;
public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) throws RemoteException;
+
+ /**
+ * Resizes the input stack id to the given bounds.
+ *
+ * @param stackId Id of the stack to resize.
+ * @param bounds Bounds to resize the stack to or {@code null} for fullscreen.
+ * @param allowResizeInDockedMode True if the resize should be allowed when the docked stack is
+ * active.
+ * @param preserveWindows True if the windows of activities contained in the stack should be
+ * preserved.
+ * @param animate True if the stack resize should be animated.
+ * @param animationDuration The duration of the resize animation in milliseconds or -1 if the
+ * default animation duration should be used.
+ * @throws RemoteException
+ */
public void resizeStack(int stackId, Rect bounds, boolean allowResizeInDockedMode,
- boolean preserveWindows, boolean animate) throws RemoteException;
+ boolean preserveWindows, boolean animate, int animationDuration) throws RemoteException;
/**
* Moves all tasks from the docked stack in the fullscreen stack and puts the top task of the
diff --git a/core/java/android/content/res/ComplexColor.java b/core/java/android/content/res/ComplexColor.java
index b297764..58c6fc5 100644
--- a/core/java/android/content/res/ComplexColor.java
+++ b/core/java/android/content/res/ComplexColor.java
@@ -23,6 +23,7 @@
/**
* Defines an abstract class for the complex color information, like
* {@link android.content.res.ColorStateList} or {@link android.content.res.GradientColor}
+ * @hide
*/
public abstract class ComplexColor {
private int mChangingConfigurations;
diff --git a/core/java/android/content/res/GradientColor.java b/core/java/android/content/res/GradientColor.java
index f29656a..c49c4b2 100644
--- a/core/java/android/content/res/GradientColor.java
+++ b/core/java/android/content/res/GradientColor.java
@@ -68,6 +68,7 @@
*
* Also note if any color "item" element is defined, then startColor, centerColor and endColor will
* be ignored.
+ * @hide
*/
public class GradientColor extends ComplexColor {
private static final String TAG = "GradientColor";
diff --git a/core/java/android/content/res/Resources.java b/core/java/android/content/res/Resources.java
index fb706fc..387fda7 100644
--- a/core/java/android/content/res/Resources.java
+++ b/core/java/android/content/res/Resources.java
@@ -999,6 +999,9 @@
return mResourcesImpl.loadColorStateList(this, value, id, theme);
}
+ /**
+ * @hide
+ */
@Nullable
public ComplexColor loadComplexColor(@NonNull TypedValue value, int id, @Nullable Theme theme) {
return mResourcesImpl.loadComplexColor(this, value, id, theme);
diff --git a/core/java/android/content/res/TypedArray.java b/core/java/android/content/res/TypedArray.java
index f6ac0ba..92134ee 100644
--- a/core/java/android/content/res/TypedArray.java
+++ b/core/java/android/content/res/TypedArray.java
@@ -475,6 +475,7 @@
* been recycled.
* @throws UnsupportedOperationException if the attribute is defined but is
* not an integer color, color state list or GradientColor.
+ * @hide
*/
@Nullable
public ComplexColor getComplexColor(@StyleableRes int index) {
diff --git a/core/java/android/net/NetworkTemplate.java b/core/java/android/net/NetworkTemplate.java
index 5761d66..d847cd0 100644
--- a/core/java/android/net/NetworkTemplate.java
+++ b/core/java/android/net/NetworkTemplate.java
@@ -250,6 +250,16 @@
}
}
+ public boolean isPersistable() {
+ switch (mMatchRule) {
+ case MATCH_MOBILE_WILDCARD:
+ case MATCH_WIFI_WILDCARD:
+ return false;
+ default:
+ return true;
+ }
+ }
+
public int getMatchRule() {
return mMatchRule;
}
diff --git a/core/java/android/text/util/Linkify.java b/core/java/android/text/util/Linkify.java
index bd376ea..ca037a2 100644
--- a/core/java/android/text/util/Linkify.java
+++ b/core/java/android/text/util/Linkify.java
@@ -16,6 +16,9 @@
package android.text.util;
+import android.annotation.IntDef;
+import android.annotation.NonNull;
+import android.annotation.Nullable;
import android.telephony.PhoneNumberUtils;
import android.text.method.LinkMovementMethod;
import android.text.method.MovementMethod;
@@ -29,6 +32,8 @@
import java.io.UnsupportedEncodingException;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Collections;
@@ -41,19 +46,21 @@
import com.android.i18n.phonenumbers.PhoneNumberUtil;
import com.android.i18n.phonenumbers.PhoneNumberUtil.Leniency;
+import libcore.util.EmptyArray;
+
/**
* Linkify take a piece of text and a regular expression and turns all of the
* regex matches in the text into clickable links. This is particularly
- * useful for matching things like email addresses, web urls, etc. and making
+ * useful for matching things like email addresses, web URLs, etc. and making
* them actionable.
*
- * Alone with the pattern that is to be matched, a url scheme prefix is also
+ * Alone with the pattern that is to be matched, a URL scheme prefix is also
* required. Any pattern match that does not begin with the supplied scheme
- * will have the scheme prepended to the matched text when the clickable url
- * is created. For instance, if you are matching web urls you would supply
- * the scheme <code>http://</code>. If the pattern matches example.com, which
- * does not have a url scheme prefix, the supplied scheme will be prepended to
- * create <code>http://example.com</code> when the clickable url link is
+ * will have the scheme prepended to the matched text when the clickable URL
+ * is created. For instance, if you are matching web URLs you would supply
+ * the scheme <code>http://</code>. If the pattern matches example.com, which
+ * does not have a URL scheme prefix, the supplied scheme will be prepended to
+ * create <code>http://example.com</code> when the clickable URL link is
* created.
*/
@@ -97,6 +104,11 @@
*/
private static final int PHONE_NUMBER_MINIMUM_DIGITS = 5;
+ /** @hide */
+ @IntDef(flag = true, value = { WEB_URLS, EMAIL_ADDRESSES, PHONE_NUMBERS, MAP_ADDRESSES, ALL })
+ @Retention(RetentionPolicy.SOURCE)
+ public @interface LinkifyMask {}
+
/**
* Filters out web URL matches that occur after an at-sign (@). This is
* to prevent turning the domain name in an email address into a web link.
@@ -152,10 +164,10 @@
* MatchFilter enables client code to have more control over
* what is allowed to match and become a link, and what is not.
*
- * For example: when matching web urls you would like things like
+ * For example: when matching web URLs you would like things like
* http://www.example.com to match, as well as just example.com itelf.
* However, you would not want to match against the domain in
- * support@example.com. So, when matching against a web url pattern you
+ * support@example.com. So, when matching against a web URL pattern you
* might also include a MatchFilter that disallows the match if it is
* immediately preceded by an at-sign (@).
*/
@@ -203,8 +215,13 @@
* If the mask is nonzero, it also removes any existing URLSpans
* attached to the Spannable, to avoid problems if you call it
* repeatedly on the same text.
+ *
+ * @param text Spannable whose text is to be marked-up with links
+ * @param mask Mask to define which kinds of links will be searched.
+ *
+ * @return True if at least one link is found and applied.
*/
- public static final boolean addLinks(Spannable text, int mask) {
+ public static final boolean addLinks(@NonNull Spannable text, @LinkifyMask int mask) {
if (mask == 0) {
return false;
}
@@ -255,8 +272,13 @@
* the link types indicated in the mask into clickable links. If matches
* are found the movement method for the TextView is set to
* LinkMovementMethod.
+ *
+ * @param text TextView whose text is to be marked-up with links
+ * @param mask Mask to define which kinds of links will be searched.
+ *
+ * @return True if at least one link is found and applied.
*/
- public static final boolean addLinks(TextView text, int mask) {
+ public static final boolean addLinks(@NonNull TextView text, @LinkifyMask int mask) {
if (mask == 0) {
return false;
}
@@ -284,7 +306,7 @@
}
}
- private static final void addLinkMovementMethod(TextView t) {
+ private static final void addLinkMovementMethod(@NonNull TextView t) {
MovementMethod m = t.getMovementMethod();
if ((m == null) || !(m instanceof LinkMovementMethod)) {
@@ -302,12 +324,12 @@
*
* @param text TextView whose text is to be marked-up with links
* @param pattern Regex pattern to be used for finding links
- * @param scheme Url scheme string (eg <code>http://</code> to be
- * prepended to the url of links that do not have
- * a scheme specified in the link text
+ * @param scheme URL scheme string (eg <code>http://</code>) to be
+ * prepended to the links that do not start with this scheme.
*/
- public static final void addLinks(TextView text, Pattern pattern, String scheme) {
- addLinks(text, pattern, scheme, null, null);
+ public static final void addLinks(@NonNull TextView text, @NonNull Pattern pattern,
+ @Nullable String scheme) {
+ addLinks(text, pattern, scheme, null, null, null);
}
/**
@@ -317,20 +339,45 @@
* to LinkMovementMethod.
*
* @param text TextView whose text is to be marked-up with links
- * @param p Regex pattern to be used for finding links
- * @param scheme Url scheme string (eg <code>http://</code> to be
- * prepended to the url of links that do not have
- * a scheme specified in the link text
+ * @param pattern Regex pattern to be used for finding links
+ * @param scheme URL scheme string (eg <code>http://</code>) to be
+ * prepended to the links that do not start with this scheme.
* @param matchFilter The filter that is used to allow the client code
* additional control over which pattern matches are
* to be converted into links.
*/
- public static final void addLinks(TextView text, Pattern p, String scheme,
- MatchFilter matchFilter, TransformFilter transformFilter) {
- SpannableString s = SpannableString.valueOf(text.getText());
+ public static final void addLinks(@NonNull TextView text, @NonNull Pattern pattern,
+ @Nullable String scheme, @Nullable MatchFilter matchFilter,
+ @Nullable TransformFilter transformFilter) {
+ addLinks(text, pattern, scheme, null, matchFilter, transformFilter);
+ }
- if (addLinks(s, p, scheme, matchFilter, transformFilter)) {
- text.setText(s);
+ /**
+ * Applies a regex to the text of a TextView turning the matches into
+ * links. If links are found then UrlSpans are applied to the link
+ * text match areas, and the movement method for the text is changed
+ * to LinkMovementMethod.
+ *
+ * @param text TextView whose text is to be marked-up with links.
+ * @param pattern Regex pattern to be used for finding links.
+ * @param defaultScheme The default scheme to be prepended to links if the link does not
+ * start with one of the <code>schemes</code> given.
+ * @param schemes Array of schemes (eg <code>http://</code>) to check if the link found
+ * contains a scheme. Passing a null or empty value means prepend defaultScheme
+ * to all links.
+ * @param matchFilter The filter that is used to allow the client code additional control
+ * over which pattern matches are to be converted into links.
+ * @param transformFilter Filter to allow the client code to update the link found.
+ */
+ public static final void addLinks(@NonNull TextView text, @NonNull Pattern pattern,
+ @Nullable String defaultScheme, @Nullable String[] schemes,
+ @Nullable MatchFilter matchFilter, @Nullable TransformFilter transformFilter) {
+ SpannableString spannable = SpannableString.valueOf(text.getText());
+
+ boolean linksAdded = addLinks(spannable, pattern, defaultScheme, schemes, matchFilter,
+ transformFilter);
+ if (linksAdded) {
+ text.setText(spannable);
addLinkMovementMethod(text);
}
}
@@ -339,37 +386,72 @@
* Applies a regex to a Spannable turning the matches into
* links.
*
- * @param text Spannable whose text is to be marked-up with
- * links
+ * @param text Spannable whose text is to be marked-up with links
* @param pattern Regex pattern to be used for finding links
- * @param scheme Url scheme string (eg <code>http://</code> to be
- * prepended to the url of links that do not have
- * a scheme specified in the link text
+ * @param scheme URL scheme string (eg <code>http://</code>) to be
+ * prepended to the links that do not start with this scheme.
*/
- public static final boolean addLinks(Spannable text, Pattern pattern, String scheme) {
- return addLinks(text, pattern, scheme, null, null);
+ public static final boolean addLinks(@NonNull Spannable text, @NonNull Pattern pattern,
+ @Nullable String scheme) {
+ return addLinks(text, pattern, scheme, null, null, null);
}
/**
- * Applies a regex to a Spannable turning the matches into
- * links.
+ * Applies a regex to a Spannable turning the matches into
+ * links.
*
- * @param s Spannable whose text is to be marked-up with
- * links
- * @param p Regex pattern to be used for finding links
- * @param scheme Url scheme string (eg <code>http://</code> to be
- * prepended to the url of links that do not have
- * a scheme specified in the link text
- * @param matchFilter The filter that is used to allow the client code
- * additional control over which pattern matches are
- * to be converted into links.
+ * @param spannable Spannable whose text is to be marked-up with links
+ * @param pattern Regex pattern to be used for finding links
+ * @param scheme URL scheme string (eg <code>http://</code>) to be
+ * prepended to the links that do not start with this scheme.
+ * @param matchFilter The filter that is used to allow the client code
+ * additional control over which pattern matches are
+ * to be converted into links.
+ * @param transformFilter Filter to allow the client code to update the link found.
+ *
+ * @return True if at least one link is found and applied.
*/
- public static final boolean addLinks(Spannable s, Pattern p,
- String scheme, MatchFilter matchFilter,
- TransformFilter transformFilter) {
+ public static final boolean addLinks(@NonNull Spannable spannable, @NonNull Pattern pattern,
+ @Nullable String scheme, @Nullable MatchFilter matchFilter,
+ @Nullable TransformFilter transformFilter) {
+ return addLinks(spannable, pattern, scheme, null, matchFilter,
+ transformFilter);
+ }
+
+ /**
+ * Applies a regex to a Spannable turning the matches into links.
+ *
+ * @param spannable Spannable whose text is to be marked-up with links.
+ * @param pattern Regex pattern to be used for finding links.
+ * @param defaultScheme The default scheme to be prepended to links if the link does not
+ * start with one of the <code>schemes</code> given.
+ * @param schemes Array of schemes (eg <code>http://</code>) to check if the link found
+ * contains a scheme. Passing a null or empty value means prepend defaultScheme
+ * to all links.
+ * @param matchFilter The filter that is used to allow the client code additional control
+ * over which pattern matches are to be converted into links.
+ * @param transformFilter Filter to allow the client code to update the link found.
+ *
+ * @return True if at least one link is found and applied.
+ */
+ public static final boolean addLinks(@NonNull Spannable spannable, @NonNull Pattern pattern,
+ @Nullable String defaultScheme, @Nullable String[] schemes,
+ @Nullable MatchFilter matchFilter, @Nullable TransformFilter transformFilter) {
+ final String[] schemesCopy;
+ if (defaultScheme == null) defaultScheme = "";
+ if (schemes == null || schemes.length < 1) {
+ schemes = EmptyArray.STRING;
+ }
+
+ schemesCopy = new String[schemes.length + 1];
+ schemesCopy[0] = defaultScheme.toLowerCase(Locale.ROOT);
+ for (int index = 0; index < schemes.length; index++) {
+ String scheme = schemes[index];
+ schemesCopy[index + 1] = (scheme == null) ? "" : scheme.toLowerCase(Locale.ROOT);
+ }
+
boolean hasMatches = false;
- String prefix = (scheme == null) ? "" : scheme.toLowerCase(Locale.ROOT);
- Matcher m = p.matcher(s);
+ Matcher m = pattern.matcher(spannable);
while (m.find()) {
int start = m.start();
@@ -377,14 +459,13 @@
boolean allowed = true;
if (matchFilter != null) {
- allowed = matchFilter.acceptMatch(s, start, end);
+ allowed = matchFilter.acceptMatch(spannable, start, end);
}
if (allowed) {
- String url = makeUrl(m.group(0), new String[] { prefix },
- m, transformFilter);
+ String url = makeUrl(m.group(0), schemesCopy, m, transformFilter);
- applyLink(url, start, end, s);
+ applyLink(url, start, end, spannable);
hasMatches = true;
}
}
@@ -398,22 +479,20 @@
text.setSpan(span, start, end, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
}
- private static final String makeUrl(String url, String[] prefixes,
- Matcher m, TransformFilter filter) {
+ private static final String makeUrl(@NonNull String url, @NonNull String[] prefixes,
+ Matcher matcher, @Nullable TransformFilter filter) {
if (filter != null) {
- url = filter.transformUrl(m, url);
+ url = filter.transformUrl(matcher, url);
}
boolean hasPrefix = false;
-
+
for (int i = 0; i < prefixes.length; i++) {
- if (url.regionMatches(true, 0, prefixes[i], 0,
- prefixes[i].length())) {
+ if (url.regionMatches(true, 0, prefixes[i], 0, prefixes[i].length())) {
hasPrefix = true;
// Fix capitalization if necessary
- if (!url.regionMatches(false, 0, prefixes[i], 0,
- prefixes[i].length())) {
+ if (!url.regionMatches(false, 0, prefixes[i], 0, prefixes[i].length())) {
url = prefixes[i] + url.substring(prefixes[i].length());
}
@@ -421,7 +500,7 @@
}
}
- if (!hasPrefix) {
+ if (!hasPrefix && prefixes.length > 0) {
url = prefixes[0] + url;
}
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index e5ab971..3586484 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -5020,8 +5020,8 @@
if (scrollabilityCache.scrollBar == null) {
scrollabilityCache.scrollBar = new ScrollBarDrawable();
- scrollabilityCache.scrollBar.setCallback(this);
scrollabilityCache.scrollBar.setState(getDrawableState());
+ scrollabilityCache.scrollBar.setCallback(this);
}
final boolean fadeScrollbars = a.getBoolean(R.styleable.View_fadeScrollbars, true);
@@ -13295,8 +13295,8 @@
if (scrollCache.scrollBar == null) {
scrollCache.scrollBar = new ScrollBarDrawable();
- scrollCache.scrollBar.setCallback(this);
scrollCache.scrollBar.setState(getDrawableState());
+ scrollCache.scrollBar.setCallback(this);
}
if (isHorizontalScrollBarEnabled() || isVerticalScrollBarEnabled()) {
@@ -18049,7 +18049,6 @@
// which requires the view set as the callback (us) to recognize the drawable as
// belonging to it as per verifyDrawable.
mBackground = background;
- background.setCallback(this);
if (background.isStateful()) {
background.setState(getDrawableState());
}
@@ -18059,6 +18058,9 @@
applyBackgroundTint();
+ // Set callback last, since the view may still be initializing.
+ background.setCallback(this);
+
if ((mPrivateFlags & PFLAG_SKIP_DRAW) != 0) {
mPrivateFlags &= ~PFLAG_SKIP_DRAW;
requestLayout = true;
@@ -18248,7 +18250,6 @@
if ((mPrivateFlags & PFLAG_SKIP_DRAW) != 0) {
mPrivateFlags &= ~PFLAG_SKIP_DRAW;
}
- foreground.setCallback(this);
foreground.setLayoutDirection(getLayoutDirection());
if (foreground.isStateful()) {
foreground.setState(getDrawableState());
@@ -18257,6 +18258,8 @@
if (isAttachedToWindow()) {
foreground.setVisible(getWindowVisibility() == VISIBLE && isShown(), false);
}
+ // Set callback last, since the view may still be initializing.
+ foreground.setCallback(this);
} else if ((mViewFlags & WILL_NOT_DRAW) != 0 && mBackground == null) {
mPrivateFlags |= PFLAG_SKIP_DRAW;
}
diff --git a/core/java/android/widget/ListPopupWindow.java b/core/java/android/widget/ListPopupWindow.java
index 36e0c77..6a10743 100644
--- a/core/java/android/widget/ListPopupWindow.java
+++ b/core/java/android/widget/ListPopupWindow.java
@@ -1183,28 +1183,28 @@
}
// getMaxAvailableHeight() subtracts the padding, so we put it back
- // to get the available height for the whole window
- int padding = 0;
- Drawable background = mPopup.getBackground();
+ // to get the available height for the whole window.
+ final int padding;
+ final Drawable background = mPopup.getBackground();
if (background != null) {
background.getPadding(mTempRect);
padding = mTempRect.top + mTempRect.bottom;
- // If we don't have an explicit vertical offset, determine one from the window
- // background so that content will line up.
+ // If we don't have an explicit vertical offset, determine one from
+ // the window background so that content will line up.
if (!mDropDownVerticalOffsetSet) {
mDropDownVerticalOffset = -mTempRect.top;
}
} else {
mTempRect.setEmpty();
+ padding = 0;
}
// Max height available on the screen for a popup.
- boolean ignoreBottomDecorations =
+ final boolean ignoreBottomDecorations =
mPopup.getInputMethodMode() == PopupWindow.INPUT_METHOD_NOT_NEEDED;
final int maxHeight = mPopup.getMaxAvailableHeight(
getAnchorView(), mDropDownVerticalOffset, ignoreBottomDecorations);
-
if (mDropDownAlwaysVisible || mDropDownHeight == ViewGroup.LayoutParams.MATCH_PARENT) {
return maxHeight + padding;
}
@@ -1213,25 +1213,30 @@
switch (mDropDownWidth) {
case ViewGroup.LayoutParams.WRAP_CONTENT:
childWidthSpec = MeasureSpec.makeMeasureSpec(
- mContext.getResources().getDisplayMetrics().widthPixels -
- (mTempRect.left + mTempRect.right),
+ mContext.getResources().getDisplayMetrics().widthPixels
+ - (mTempRect.left + mTempRect.right),
MeasureSpec.AT_MOST);
break;
case ViewGroup.LayoutParams.MATCH_PARENT:
childWidthSpec = MeasureSpec.makeMeasureSpec(
- mContext.getResources().getDisplayMetrics().widthPixels -
- (mTempRect.left + mTempRect.right),
+ mContext.getResources().getDisplayMetrics().widthPixels
+ - (mTempRect.left + mTempRect.right),
MeasureSpec.EXACTLY);
break;
default:
childWidthSpec = MeasureSpec.makeMeasureSpec(mDropDownWidth, MeasureSpec.EXACTLY);
break;
}
+
+ // Add padding only if the list has items in it, that way we don't show
+ // the popup if it is not needed.
final int listContent = mDropDownList.measureHeightOfChildren(childWidthSpec,
- 0, ListView.NO_POSITION, maxHeight - otherHeights, -1);
- // add padding only if the list has items in it, that way we don't show
- // the popup if it is not needed
- if (listContent > 0) otherHeights += padding;
+ 0, DropDownListView.NO_POSITION, maxHeight - otherHeights, -1);
+ if (listContent > 0) {
+ final int listPadding = mDropDownList.getPaddingTop()
+ + mDropDownList.getPaddingBottom();
+ otherHeights += padding + listPadding;
+ }
return listContent + otherHeights;
}
diff --git a/core/java/android/widget/RemoteViews.java b/core/java/android/widget/RemoteViews.java
index 063288e..8bd63df 100644
--- a/core/java/android/widget/RemoteViews.java
+++ b/core/java/android/widget/RemoteViews.java
@@ -60,6 +60,7 @@
import libcore.util.Objects;
import com.android.internal.R;
+import com.android.internal.util.Preconditions;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
@@ -1096,6 +1097,13 @@
memoryCounter.addBitmapMemory(mBitmaps.get(i));
}
}
+
+ @Override
+ protected BitmapCache clone() {
+ BitmapCache bitmapCache = new BitmapCache();
+ bitmapCache.mBitmaps.addAll(mBitmaps);
+ return bitmapCache;
+ }
}
private class BitmapReflectionAction extends Action {
@@ -2227,10 +2235,21 @@
public RemoteViews clone() {
+ Preconditions.checkState(mIsRoot, "RemoteView has been attached to another RemoteView. "
+ + "May only clone the root of a RemoteView hierarchy.");
+
Parcel p = Parcel.obtain();
+
+ // Do not parcel the Bitmap cache - doing so creates an expensive copy of all bitmaps.
+ // Instead pretend we're not owning the cache while parceling.
+ mIsRoot = false;
writeToParcel(p, 0);
p.setDataPosition(0);
- RemoteViews rv = new RemoteViews(p);
+ mIsRoot = true;
+
+ RemoteViews rv = new RemoteViews(p, mBitmapCache.clone());
+ rv.mIsRoot = true;
+
p.recycle();
return rv;
}
@@ -2240,7 +2259,7 @@
}
/**
- * Reutrns the layout id of the root layout associated with this RemoteViews. In the case
+ * Returns the layout id of the root layout associated with this RemoteViews. In the case
* that the RemoteViews has both a landscape and portrait root, this will return the layout
* id associated with the portrait layout.
*
diff --git a/core/tests/coretests/res/layout/remote_views_test.xml b/core/tests/coretests/res/layout/remote_views_test.xml
new file mode 100644
index 0000000..c5f7a47
--- /dev/null
+++ b/core/tests/coretests/res/layout/remote_views_test.xml
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2016 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:id="@+id/layout"
+ android:orientation="vertical">
+
+ <TextView android:id="@+id/text"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" />
+
+ <ImageView android:id="@+id/image"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" />
+
+</LinearLayout>
diff --git a/core/tests/coretests/src/android/view/RemoteViewsTest.java b/core/tests/coretests/src/android/view/RemoteViewsTest.java
new file mode 100644
index 0000000..9c4fd70
--- /dev/null
+++ b/core/tests/coretests/src/android/view/RemoteViewsTest.java
@@ -0,0 +1,127 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package android.view;
+
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+import org.junit.runner.RunWith;
+
+import android.content.Context;
+import android.graphics.Bitmap;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.support.test.InstrumentationRegistry;
+import android.support.test.filters.SmallTest;
+import android.support.test.runner.AndroidJUnit4;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.RemoteViews;
+import android.widget.TextView;
+
+import com.android.frameworks.coretests.R;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertSame;
+
+/**
+ * Tests for RemoteViews.
+ */
+@RunWith(AndroidJUnit4.class)
+@SmallTest
+public class RemoteViewsTest {
+
+ @Rule
+ public final ExpectedException exception = ExpectedException.none();
+
+ private Context mContext;
+ private String mPackage;
+ private LinearLayout mContainer;
+
+ @Before
+ public void setup() {
+ mContext = InstrumentationRegistry.getContext();
+ mPackage = mPackage;
+ mContainer = new LinearLayout(mContext);
+ }
+
+ @Test
+ public void clone_doesNotCopyBitmap() {
+ RemoteViews original = new RemoteViews(mPackage, R.layout.remote_views_test);
+ Bitmap bitmap = Bitmap.createBitmap(10, 10, Bitmap.Config.ARGB_8888);
+
+ original.setImageViewBitmap(R.id.image, bitmap);
+ RemoteViews clone = original.clone();
+ View inflated = clone.apply(mContext, mContainer);
+
+ Drawable drawable = ((ImageView) inflated.findViewById(R.id.image)).getDrawable();
+ assertSame(bitmap, ((BitmapDrawable)drawable).getBitmap());
+ }
+
+ @Test
+ public void clone_originalCanStillBeApplied() {
+ RemoteViews original = new RemoteViews(mPackage, R.layout.remote_views_test);
+
+ RemoteViews clone = original.clone();
+
+ clone.apply(mContext, mContainer);
+ }
+
+ @Test
+ public void clone_clones() {
+ RemoteViews original = new RemoteViews(mPackage, R.layout.remote_views_test);
+
+ RemoteViews clone = original.clone();
+ original.setTextViewText(R.id.text, "test");
+ View inflated = clone.apply(mContext, mContainer);
+
+ TextView textView = (TextView) inflated.findViewById(R.id.text);
+ assertEquals("", textView.getText());
+ }
+
+ @Test
+ public void clone_child_fails() {
+ RemoteViews original = new RemoteViews(mPackage, R.layout.remote_views_test);
+ RemoteViews child = new RemoteViews(mPackage, R.layout.remote_views_test);
+
+ original.addView(R.id.layout, child);
+
+ exception.expect(IllegalStateException.class);
+ RemoteViews clone = child.clone();
+ }
+
+ @Test
+ public void clone_repeatedly() {
+ RemoteViews original = new RemoteViews(mPackage, R.layout.remote_views_test);
+
+ original.clone();
+ original.clone();
+
+ original.apply(mContext, mContainer);
+ }
+
+ @Test
+ public void clone_chained() {
+ RemoteViews original = new RemoteViews(mPackage, R.layout.remote_views_test);
+
+ RemoteViews clone = original.clone().clone();
+
+ clone.apply(mContext, mContainer);
+ }
+
+}
diff --git a/graphics/java/android/graphics/drawable/VectorDrawable.java b/graphics/java/android/graphics/drawable/VectorDrawable.java
index bd069ff..e75fb98 100644
--- a/graphics/java/android/graphics/drawable/VectorDrawable.java
+++ b/graphics/java/android/graphics/drawable/VectorDrawable.java
@@ -53,8 +53,15 @@
import java.util.Stack;
/**
- * This lets you create a drawable based on an XML vector graphic. It can be
- * defined in an XML file with the <code><vector></code> element.
+ * This lets you create a drawable based on an XML vector graphic.
+ * <p/>
+ * <strong>Note:</strong> To optimize for the re-drawing performance, one bitmap cache is created
+ * for each VectorDrawable. Therefore, referring to the same VectorDrawable means sharing the same
+ * bitmap cache. If these references don't agree upon on the same size, the bitmap will be recreated
+ * and redrawn every time size is changed. In other words, if a VectorDrawable is used for
+ * different sizes, it is more efficient to create multiple VectorDrawables, one for each size.
+ * <p/>
+ * VectorDrawable can be defined in an XML file with the <code><vector></code> element.
* <p/>
* The vector drawable has the following elements:
* <p/>
diff --git a/libs/hwui/BakedOpState.cpp b/libs/hwui/BakedOpState.cpp
index 26653f7..85903654 100644
--- a/libs/hwui/BakedOpState.cpp
+++ b/libs/hwui/BakedOpState.cpp
@@ -82,6 +82,16 @@
}
}
+ResolvedRenderState::ResolvedRenderState(LinearAllocator& allocator, Snapshot& snapshot,
+ const Matrix4& localTransform, const ClipBase* localClip) {
+ transform.loadMultiply(*snapshot.transform, localTransform);
+ clipState = snapshot.mutateClipArea().serializeIntersectedClip(allocator,
+ localClip, *(snapshot.transform));
+ clippedBounds = clipState->rect;
+ clipSideFlags = OpClipSideFlags::Full;
+ localProjectionPathMask = nullptr;
+}
+
ResolvedRenderState::ResolvedRenderState(LinearAllocator& allocator, Snapshot& snapshot)
: transform(*snapshot.transform)
, clipState(snapshot.mutateClipArea().serializeClip(allocator))
diff --git a/libs/hwui/BakedOpState.h b/libs/hwui/BakedOpState.h
index ffe2901..4e3cb8a 100644
--- a/libs/hwui/BakedOpState.h
+++ b/libs/hwui/BakedOpState.h
@@ -55,6 +55,10 @@
ResolvedRenderState(LinearAllocator& allocator, Snapshot& snapshot,
const RecordedOp& recordedOp, bool expandForStroke);
+ // Constructor for unbounded ops *with* transform/clip
+ ResolvedRenderState(LinearAllocator& allocator, Snapshot& snapshot,
+ const Matrix4& localTransform, const ClipBase* localClip);
+
// Constructor for unbounded ops without transform/clip (namely shadows)
ResolvedRenderState(LinearAllocator& allocator, Snapshot& snapshot);
@@ -111,8 +115,14 @@
return bakedState;
}
+ static BakedOpState* tryConstructUnbounded(LinearAllocator& allocator,
+ Snapshot& snapshot, const RecordedOp& recordedOp) {
+ if (CC_UNLIKELY(snapshot.getRenderTargetClip().isEmpty())) return nullptr;
+ return allocator.create_trivial<BakedOpState>(allocator, snapshot, recordedOp);
+ }
+
enum class StrokeBehavior {
- // stroking is forced, regardless of style on paint
+ // stroking is forced, regardless of style on paint (such as for lines)
Forced,
// stroking is defined by style on paint
StyleDefined,
@@ -167,6 +177,13 @@
, roundRectClipState(snapshot.roundRectClipState)
, op(&recordedOp) {}
+ // TODO: fix this brittleness
+ BakedOpState(LinearAllocator& allocator, Snapshot& snapshot, const RecordedOp& recordedOp)
+ : computedState(allocator, snapshot, recordedOp.localMatrix, recordedOp.localClip)
+ , alpha(snapshot.alpha)
+ , roundRectClipState(snapshot.roundRectClipState)
+ , op(&recordedOp) {}
+
BakedOpState(LinearAllocator& allocator, Snapshot& snapshot, const ShadowOp* shadowOpPtr)
: computedState(allocator, snapshot)
, alpha(snapshot.alpha)
diff --git a/libs/hwui/FrameBuilder.cpp b/libs/hwui/FrameBuilder.cpp
index 50b21a4..fc39682 100644
--- a/libs/hwui/FrameBuilder.cpp
+++ b/libs/hwui/FrameBuilder.cpp
@@ -574,7 +574,7 @@
}
void FrameBuilder::deferFunctorOp(const FunctorOp& op) {
- BakedOpState* bakedState = tryBakeOpState(op);
+ BakedOpState* bakedState = tryBakeUnboundedOpState(op);
if (!bakedState) return; // quick rejected
currentLayer().deferUnmergeableOp(mAllocator, bakedState, OpBatchType::Functor);
}
@@ -663,7 +663,7 @@
}
void FrameBuilder::deferTextOnPathOp(const TextOnPathOp& op) {
- BakedOpState* bakedState = tryBakeOpState(op);
+ BakedOpState* bakedState = tryBakeUnboundedOpState(op);
if (!bakedState) return; // quick rejected
currentLayer().deferUnmergeableOp(mAllocator, bakedState, textBatchId(*(op.paint)));
}
diff --git a/libs/hwui/FrameBuilder.h b/libs/hwui/FrameBuilder.h
index f44306a..8a00d33 100644
--- a/libs/hwui/FrameBuilder.h
+++ b/libs/hwui/FrameBuilder.h
@@ -173,6 +173,10 @@
BakedOpState* tryBakeOpState(const RecordedOp& recordedOp) {
return BakedOpState::tryConstruct(mAllocator, *mCanvasState.writableSnapshot(), recordedOp);
}
+ BakedOpState* tryBakeUnboundedOpState(const RecordedOp& recordedOp) {
+ return BakedOpState::tryConstructUnbounded(mAllocator, *mCanvasState.writableSnapshot(), recordedOp);
+ }
+
// should always be surrounded by a save/restore pair, and not called if DisplayList is null
void deferNodePropsAndOps(RenderNode& node);
diff --git a/libs/hwui/RecordedOp.h b/libs/hwui/RecordedOp.h
index c37458d..96a57b6 100644
--- a/libs/hwui/RecordedOp.h
+++ b/libs/hwui/RecordedOp.h
@@ -257,8 +257,10 @@
};
struct FunctorOp : RecordedOp {
- FunctorOp(BASE_PARAMS_PAINTLESS, Functor* functor)
- : SUPER_PAINTLESS(FunctorOp)
+ // Note: undefined record-time bounds, since this op fills the clip
+ // TODO: explicitly define bounds
+ FunctorOp(const Matrix4& localMatrix, const ClipBase* localClip, Functor* functor)
+ : RecordedOp(RecordedOpId::FunctorOp, Rect(), localMatrix, localClip, nullptr)
, functor(functor) {}
Functor* functor;
};
@@ -385,9 +387,10 @@
};
struct TextOnPathOp : RecordedOp {
- TextOnPathOp(BASE_PARAMS, const glyph_t* glyphs, int glyphCount,
- const SkPath* path, float hOffset, float vOffset)
- : SUPER(TextOnPathOp)
+ // TODO: explicitly define bounds
+ TextOnPathOp(const Matrix4& localMatrix, const ClipBase* localClip, const SkPaint* paint,
+ const glyph_t* glyphs, int glyphCount, const SkPath* path, float hOffset, float vOffset)
+ : RecordedOp(RecordedOpId::TextOnPathOp, Rect(), localMatrix, localClip, paint)
, glyphs(glyphs)
, glyphCount(glyphCount)
, path(path)
diff --git a/libs/hwui/RecordingCanvas.cpp b/libs/hwui/RecordingCanvas.cpp
index 11eb825..1546baf 100644
--- a/libs/hwui/RecordingCanvas.cpp
+++ b/libs/hwui/RecordingCanvas.cpp
@@ -24,14 +24,6 @@
namespace android {
namespace uirenderer {
-#define MIL_PIX 1000000
-static Rect sUnreasonablyLargeBounds(-MIL_PIX, -MIL_PIX, MIL_PIX, MIL_PIX);
-
-static const Rect& getConservativeOpBounds(const ClipBase* clip) {
- // if op is clipped, that rect can be used, but otherwise just use a conservatively large rect
- return clip ? clip->rect : sUnreasonablyLargeBounds;
-}
-
RecordingCanvas::RecordingCanvas(size_t width, size_t height)
: mState(*this)
, mResourceCache(ResourceCache::getInstance()) {
@@ -249,12 +241,10 @@
}
void RecordingCanvas::drawPaint(const SkPaint& paint) {
- const ClipBase* clip = getRecordedClip();
- addOp(alloc().create_trivial<RectOp>(
- getConservativeOpBounds(clip),
- Matrix4::identity(),
- clip,
- refPaint(&paint)));
+ SkRect bounds;
+ if (getClipBounds(&bounds)) {
+ drawRect(bounds.fLeft, bounds.fTop, bounds.fRight, bounds.fBottom, paint);
+ }
}
static Rect calcBoundsOfPoints(const float* points, int floatCount) {
@@ -544,11 +534,9 @@
float hOffset, float vOffset, const SkPaint& paint) {
if (!glyphs || glyphCount <= 0 || PaintUtils::paintWillNotDrawText(paint)) return;
glyphs = refBuffer<glyph_t>(glyphs, glyphCount);
- auto clip = getRecordedClip();
addOp(alloc().create_trivial<TextOnPathOp>(
- getConservativeOpBounds(clip), // TODO: explicitly define bounds
*(mState.currentSnapshot()->transform),
- clip,
+ getRecordedClip(),
refPaint(&paint), glyphs, glyphCount, refPath(&path), hOffset, vOffset));
}
@@ -599,11 +587,9 @@
void RecordingCanvas::callDrawGLFunction(Functor* functor) {
mDisplayList->functors.push_back(functor);
- auto clip = getRecordedClip();
addOp(alloc().create_trivial<FunctorOp>(
- getConservativeOpBounds(clip),
*(mState.currentSnapshot()->transform),
- clip,
+ getRecordedClip(),
functor));
}
diff --git a/libs/hwui/tests/unit/RecordingCanvasTests.cpp b/libs/hwui/tests/unit/RecordingCanvasTests.cpp
index 5e613fd..e6d84c6 100644
--- a/libs/hwui/tests/unit/RecordingCanvasTests.cpp
+++ b/libs/hwui/tests/unit/RecordingCanvasTests.cpp
@@ -223,8 +223,7 @@
auto op = *(dl->getOps()[0]);
EXPECT_EQ(RecordedOpId::RectOp, op.opId);
EXPECT_EQ(nullptr, op.localClip);
- EXPECT_TRUE(op.unmappedBounds.contains(Rect(-1000, -1000, 1000, 1000)))
- << "no clip, unmappedBounds should resolve to be much larger than DL bounds";
+ EXPECT_TRUE(op.unmappedBounds.contains(Rect(200, 200))) << "Expect recording/clip bounds";
}
TEST(RecordingCanvas, backgroundAndImage) {
diff --git a/media/java/android/media/AudioDeviceCallback.java b/media/java/android/media/AudioDeviceCallback.java
index d9f0037..a5b1d24 100644
--- a/media/java/android/media/AudioDeviceCallback.java
+++ b/media/java/android/media/AudioDeviceCallback.java
@@ -19,7 +19,7 @@
/**
* AudioDeviceCallback defines the mechanism by which applications can receive notifications
* of audio device connection and disconnection events.
- * @see AudioManager#registerAudioDeviceCallback.
+ * @see AudioManager#registerAudioDeviceCallback(AudioDeviceCallback, android.os.Handler handler).
*/
public abstract class AudioDeviceCallback {
/**
diff --git a/media/java/android/media/AudioFormat.java b/media/java/android/media/AudioFormat.java
index abb6f4e..a4484e7 100644
--- a/media/java/android/media/AudioFormat.java
+++ b/media/java/android/media/AudioFormat.java
@@ -256,6 +256,11 @@
public static final int ENCODING_AAC_HE_V2 = 12;
/** Audio data format: compressed audio wrapped in PCM for HDMI
* or S/PDIF passthrough.
+ * IEC61937 uses a stereo stream of 16-bit samples as the wrapper.
+ * So the channel mask for the track must be {@link #CHANNEL_OUT_STEREO}.
+ * Data should be written to the stream in a short[] array.
+ * If the data is written in a byte[] array then there may be endian problems
+ * on some platforms when converting to short internally.
*/
public static final int ENCODING_IEC61937 = 13;
diff --git a/media/java/android/media/AudioTrack.java b/media/java/android/media/AudioTrack.java
index e1dab09..d9caf03 100644
--- a/media/java/android/media/AudioTrack.java
+++ b/media/java/android/media/AudioTrack.java
@@ -806,6 +806,15 @@
}
mSampleRate = sampleRateInHz;
+ // IEC61937 is based on stereo. We could coerce it to stereo.
+ // But the application needs to know the stream is stereo so that
+ // it is encoded and played correctly. So better to just reject it.
+ if (audioFormat == AudioFormat.ENCODING_IEC61937
+ && channelConfig != AudioFormat.CHANNEL_OUT_STEREO) {
+ throw new IllegalArgumentException(
+ "ENCODING_IEC61937 must be configured as CHANNEL_OUT_STEREO");
+ }
+
//--------------
// channel config
mChannelConfiguration = channelConfig;
diff --git a/media/java/android/media/MediaMetadata.java b/media/java/android/media/MediaMetadata.java
index 722605f..9ebf10f 100644
--- a/media/java/android/media/MediaMetadata.java
+++ b/media/java/android/media/MediaMetadata.java
@@ -365,7 +365,7 @@
}
private MediaMetadata(Parcel in) {
- mBundle = in.readBundle();
+ mBundle = Bundle.setDefusable(in.readBundle(), true);
}
/**
diff --git a/packages/Keyguard/res/values/strings.xml b/packages/Keyguard/res/values/strings.xml
index 746457f..61966b2 100644
--- a/packages/Keyguard/res/values/strings.xml
+++ b/packages/Keyguard/res/values/strings.xml
@@ -302,7 +302,7 @@
<string name="keyguard_carrier_default">No service.</string>
<!-- Content description of the switch input method button for accessibility (not shown on the screen). [CHAR LIMIT=NONE] -->
- <string name="accessibility_ime_switch_button" msgid="5032926134740456424">Switch input method button.</string>
+ <string name="accessibility_ime_switch_button" msgid="5032926134740456424">Switch input method</string>
<!-- Description of airplane mode -->
<string name="airplane_mode">Airplane mode</string>
diff --git a/packages/SystemUI/src/com/android/systemui/stackdivider/WindowManagerProxy.java b/packages/SystemUI/src/com/android/systemui/stackdivider/WindowManagerProxy.java
index e312fa2..ef32f7e 100644
--- a/packages/SystemUI/src/com/android/systemui/stackdivider/WindowManagerProxy.java
+++ b/packages/SystemUI/src/com/android/systemui/stackdivider/WindowManagerProxy.java
@@ -100,8 +100,8 @@
@Override
public void run() {
try {
- ActivityManagerNative.getDefault().resizeStack(DOCKED_STACK_ID, null, true, true,
- false);
+ ActivityManagerNative.getDefault().resizeStack(
+ DOCKED_STACK_ID, null, true, true, false, -1);
} catch (RemoteException e) {
Log.w(TAG, "Failed to resize stack: " + e);
}
diff --git a/packages/SystemUI/src/com/android/systemui/tv/pip/PipManager.java b/packages/SystemUI/src/com/android/systemui/tv/pip/PipManager.java
index ff7ea27..8db7534 100644
--- a/packages/SystemUI/src/com/android/systemui/tv/pip/PipManager.java
+++ b/packages/SystemUI/src/com/android/systemui/tv/pip/PipManager.java
@@ -385,7 +385,7 @@
break;
}
try {
- mActivityManager.resizeStack(PINNED_STACK_ID, mCurrentPipBounds, true, true, true);
+ mActivityManager.resizeStack(PINNED_STACK_ID, mCurrentPipBounds, true, true, true, -1);
} catch (RemoteException e) {
Log.e(TAG, "showPipMenu failed", e);
}
diff --git a/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java b/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
index 9ce81ed..c810e6c 100644
--- a/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
+++ b/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
@@ -4086,7 +4086,7 @@
}
public boolean isHandlingAccessibilityEvents() {
- return !mBoundServices.isEmpty() || !mBoundServices.isEmpty();
+ return !mBoundServices.isEmpty() || !mBindingServices.isEmpty();
}
public void onSwitchToAnotherUser() {
diff --git a/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java b/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
index 8febecc..215be4a 100644
--- a/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
+++ b/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
@@ -332,7 +332,12 @@
for (int i = N - 1; i >= 0; i--) {
Provider provider = installedProviders.get(i);
- ensureGroupStateLoadedLocked(provider.getUserId());
+ final int userId = provider.getUserId();
+ if (!mUserManager.isUserUnlocked(userId) ||
+ isProfileWithLockedParent(userId)) {
+ continue;
+ }
+ ensureGroupStateLoadedLocked(userId);
if (!removedProviders.contains(provider.id)) {
final boolean changed = updateProvidersForPackageLocked(
diff --git a/services/backup/java/com/android/server/backup/BackupManagerService.java b/services/backup/java/com/android/server/backup/BackupManagerService.java
index cd4d107d..b737ae2 100644
--- a/services/backup/java/com/android/server/backup/BackupManagerService.java
+++ b/services/backup/java/com/android/server/backup/BackupManagerService.java
@@ -2918,9 +2918,15 @@
mBackupRunning = false;
if (mStatus == BackupTransport.TRANSPORT_NOT_INITIALIZED) {
// Make sure we back up everything and perform the one-time init
- clearMetadata();
if (MORE_DEBUG) Slog.d(TAG, "Server requires init; rerunning");
addBackupTrace("init required; rerunning");
+ try {
+ mPendingInits.add(mTransport.transportDirName());
+ } catch (Exception e) {
+ Slog.w(TAG, "Failed to query transport name heading for init", e);
+ // swallow it and proceed; we don't rely on this
+ }
+ clearMetadata();
backupNow();
}
}
@@ -4451,13 +4457,21 @@
}
}
- // We still could fail in backup runner thread, getting result from there.
- int backupRunnerResult = backupRunner.getBackupResultBlocking();
- if (backupPackageStatus != BackupTransport.TRANSPORT_ERROR
- && backupRunnerResult != BackupTransport.TRANSPORT_OK) {
- // If there was an error in runner thread and
- // not TRANSPORT_ERROR here, overwrite it.
- backupPackageStatus = backupRunnerResult;
+ // TRANSPORT_ERROR here means that we've hit an error that the runner
+ // doesn't know about, so it's still moving data but we're pulling the
+ // rug out from under it. Don't ask for its result: we already know better
+ // and we'll hang if we block waiting for it, since it relies on us to
+ // read back the data it's writing into the engine. Just proceed with
+ // a graceful failure. The runner/engine mechanism will tear itself
+ // down cleanly when we close the pipes from this end.
+ if (backupPackageStatus != BackupTransport.TRANSPORT_ERROR) {
+ // We still could fail in backup runner thread, getting result from there.
+ int backupRunnerResult = backupRunner.getBackupResultBlocking();
+ if (backupRunnerResult != BackupTransport.TRANSPORT_OK) {
+ // If there was an error in runner thread and
+ // not TRANSPORT_ERROR here, overwrite it.
+ backupPackageStatus = backupRunnerResult;
+ }
}
if (MORE_DEBUG) {
diff --git a/services/core/java/com/android/server/MountService.java b/services/core/java/com/android/server/MountService.java
index 65a22b9..ccca5ba 100644
--- a/services/core/java/com/android/server/MountService.java
+++ b/services/core/java/com/android/server/MountService.java
@@ -1946,6 +1946,10 @@
throw new IllegalStateException(
"Emulation not available on device with native FBE");
}
+ if (mLockPatternUtils.isCredentialRequiredToDecrypt(false)) {
+ throw new IllegalStateException(
+ "Emulation requires disabling 'Secure start-up' in Settings > Security");
+ }
final long token = Binder.clearCallingIdentity();
try {
diff --git a/services/core/java/com/android/server/am/ActiveServices.java b/services/core/java/com/android/server/am/ActiveServices.java
index 63a0e87..f51fb6c 100755
--- a/services/core/java/com/android/server/am/ActiveServices.java
+++ b/services/core/java/com/android/server/am/ActiveServices.java
@@ -811,10 +811,8 @@
// Hacky kind of thing -- allow system stuff to tell us
// what they are, so we can report this elsewhere for
// others to know why certain services are running.
- try {
- clientIntent = service.getParcelableExtra(Intent.EXTRA_CLIENT_INTENT);
- } catch (RuntimeException e) {
- }
+ service.setDefusable(true);
+ clientIntent = service.getParcelableExtra(Intent.EXTRA_CLIENT_INTENT);
if (clientIntent != null) {
clientLabel = service.getIntExtra(Intent.EXTRA_CLIENT_LABEL, 0);
if (clientLabel != 0) {
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 5aac43d..c1ec71c 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -6923,6 +6923,7 @@
intents[i].setDefusable(true);
}
}
+ Bundle.setDefusable(bOptions, true);
final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0;
final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0;
@@ -9673,14 +9674,14 @@
@Override
public void resizeStack(int stackId, Rect bounds, boolean allowResizeInDockedMode,
- boolean preserveWindows, boolean animate) {
+ boolean preserveWindows, boolean animate, int animationDuration) {
enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()");
long ident = Binder.clearCallingIdentity();
try {
synchronized (this) {
if (animate) {
if (stackId == PINNED_STACK_ID) {
- mWindowManager.animateResizePinnedStack(bounds);
+ mWindowManager.animateResizePinnedStack(bounds, animationDuration);
} else {
throw new IllegalArgumentException("Stack: " + stackId
+ " doesn't support animated resize.");
diff --git a/services/core/java/com/android/server/am/ActivityStackSupervisor.java b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
index d364d85..7def1bd 100644
--- a/services/core/java/com/android/server/am/ActivityStackSupervisor.java
+++ b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
@@ -2408,7 +2408,7 @@
ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
resumeFocusedStackTopActivityLocked();
- mWindowManager.animateResizePinnedStack(bounds);
+ mWindowManager.animateResizePinnedStack(bounds, -1);
mService.notifyActivityPinnedLocked();
}
diff --git a/services/core/java/com/android/server/am/ActivityStarter.java b/services/core/java/com/android/server/am/ActivityStarter.java
index efa7420..af69c93 100644
--- a/services/core/java/com/android/server/am/ActivityStarter.java
+++ b/services/core/java/com/android/server/am/ActivityStarter.java
@@ -1483,7 +1483,8 @@
if (mLaunchBounds != null) {
final int stackId = mTargetStack.mStackId;
if (StackId.resizeStackWithLaunchBounds(stackId)) {
- mService.resizeStack(stackId, mLaunchBounds, true, !PRESERVE_WINDOWS, ANIMATE);
+ mService.resizeStack(
+ stackId, mLaunchBounds, true, !PRESERVE_WINDOWS, ANIMATE, -1);
} else {
mStartActivity.task.updateOverrideConfiguration(mLaunchBounds);
}
@@ -1571,7 +1572,7 @@
stackId = stack.mStackId;
}
if (StackId.resizeStackWithLaunchBounds(stackId)) {
- mService.resizeStack(stackId, mLaunchBounds, true, !PRESERVE_WINDOWS, ANIMATE);
+ mService.resizeStack(stackId, mLaunchBounds, true, !PRESERVE_WINDOWS, ANIMATE, -1);
}
}
mTargetStack = mInTask.stack;
diff --git a/services/core/java/com/android/server/am/PendingIntentRecord.java b/services/core/java/com/android/server/am/PendingIntentRecord.java
index 8039072..b8f45bc 100644
--- a/services/core/java/com/android/server/am/PendingIntentRecord.java
+++ b/services/core/java/com/android/server/am/PendingIntentRecord.java
@@ -208,7 +208,10 @@
String requiredPermission, IBinder resultTo, String resultWho, int requestCode,
int flagsMask, int flagsValues, Bundle options, IActivityContainer container)
throws TransactionTooLargeException {
- synchronized(owner) {
+ if (intent != null) intent.setDefusable(true);
+ if (options != null) options.setDefusable(true);
+
+ synchronized (owner) {
final ActivityContainer activityContainer = (ActivityContainer)container;
if (activityContainer != null && activityContainer.mParentActivity != null &&
activityContainer.mParentActivity.state
diff --git a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
index 0b4f7f0..49ae293 100644
--- a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
+++ b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
@@ -28,13 +28,12 @@
import static android.content.Intent.ACTION_USER_ADDED;
import static android.content.Intent.ACTION_USER_REMOVED;
import static android.content.Intent.EXTRA_UID;
-
import static android.net.ConnectivityManager.CONNECTIVITY_ACTION;
-import static android.net.ConnectivityManager.TYPE_MOBILE;
-import static android.net.ConnectivityManager.TYPE_WIMAX;
import static android.net.ConnectivityManager.RESTRICT_BACKGROUND_STATUS_DISABLED;
import static android.net.ConnectivityManager.RESTRICT_BACKGROUND_STATUS_ENABLED;
import static android.net.ConnectivityManager.RESTRICT_BACKGROUND_STATUS_WHITELISTED;
+import static android.net.ConnectivityManager.TYPE_MOBILE;
+import static android.net.ConnectivityManager.TYPE_WIMAX;
import static android.net.ConnectivityManager.isNetworkTypeMobile;
import static android.net.NetworkPolicy.CYCLE_NONE;
import static android.net.NetworkPolicy.LIMIT_DISABLED;
@@ -47,11 +46,9 @@
import static android.net.NetworkPolicyManager.FIREWALL_RULE_ALLOW;
import static android.net.NetworkPolicyManager.FIREWALL_RULE_DEFAULT;
import static android.net.NetworkPolicyManager.FIREWALL_RULE_DENY;
-import static android.net.NetworkPolicyManager.POLICY_ALLOW_BACKGROUND_BATTERY_SAVE;
import static android.net.NetworkPolicyManager.POLICY_NONE;
import static android.net.NetworkPolicyManager.POLICY_REJECT_METERED_BACKGROUND;
import static android.net.NetworkPolicyManager.RULE_ALLOW_ALL;
-import static android.net.NetworkPolicyManager.RULE_REJECT_ALL;
import static android.net.NetworkPolicyManager.RULE_REJECT_METERED;
import static android.net.NetworkPolicyManager.RULE_UNKNOWN;
import static android.net.NetworkPolicyManager.computeLastCycleBoundary;
@@ -80,6 +77,7 @@
import static com.android.internal.util.XmlUtils.writeLongAttribute;
import static com.android.server.NetworkManagementService.LIMIT_GLOBAL_ALERT;
import static com.android.server.net.NetworkStatsService.ACTION_NETWORK_STATS_UPDATED;
+
import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT;
import static org.xmlpull.v1.XmlPullParser.END_TAG;
import static org.xmlpull.v1.XmlPullParser.START_TAG;
@@ -130,12 +128,12 @@
import android.os.INetworkManagementService;
import android.os.IPowerManager;
import android.os.Message;
-import android.os.ResultReceiver;
import android.os.MessageQueue.IdleHandler;
import android.os.PowerManager;
import android.os.PowerManagerInternal;
import android.os.RemoteCallbackList;
import android.os.RemoteException;
+import android.os.ResultReceiver;
import android.os.ServiceManager;
import android.os.UserHandle;
import android.os.UserManager;
@@ -157,8 +155,6 @@
import android.util.TrustedTime;
import android.util.Xml;
-import libcore.io.IoUtils;
-
import com.android.internal.R;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.content.PackageMonitor;
@@ -169,6 +165,9 @@
import com.android.server.EventLogTags;
import com.android.server.LocalServices;
import com.android.server.SystemConfig;
+
+import libcore.io.IoUtils;
+
import com.google.android.collect.Lists;
import org.xmlpull.v1.XmlPullParser;
@@ -1446,9 +1445,11 @@
final NetworkTemplate template = new NetworkTemplate(networkTemplate,
subscriberId, networkId);
- mNetworkPolicy.put(template, new NetworkPolicy(template, cycleDay,
- cycleTimezone, warningBytes, limitBytes, lastWarningSnooze,
- lastLimitSnooze, metered, inferred));
+ if (template.isPersistable()) {
+ mNetworkPolicy.put(template, new NetworkPolicy(template, cycleDay,
+ cycleTimezone, warningBytes, limitBytes, lastWarningSnooze,
+ lastLimitSnooze, metered, inferred));
+ }
} else if (TAG_UID_POLICY.equals(tag)) {
final int uid = readIntAttribute(in, ATTR_UID);
@@ -1535,6 +1536,7 @@
for (int i = 0; i < mNetworkPolicy.size(); i++) {
final NetworkPolicy policy = mNetworkPolicy.valueAt(i);
final NetworkTemplate template = policy.template;
+ if (!template.isPersistable()) continue;
out.startTag(null, TAG_NETWORK_POLICY);
writeIntAttribute(out, ATTR_NETWORK_TEMPLATE, template.getMatchRule());
diff --git a/services/core/java/com/android/server/pm/UserManagerService.java b/services/core/java/com/android/server/pm/UserManagerService.java
index 5fd196b..a3622b5 100644
--- a/services/core/java/com/android/server/pm/UserManagerService.java
+++ b/services/core/java/com/android/server/pm/UserManagerService.java
@@ -387,6 +387,15 @@
synchronized (mRestrictionsLock) {
applyUserRestrictionsLR(UserHandle.USER_SYSTEM);
}
+
+ UserInfo currentGuestUser = findCurrentGuestUser();
+ if (currentGuestUser != null && !hasUserRestriction(
+ UserManager.DISALLOW_CONFIG_WIFI, currentGuestUser.id)) {
+ // If a guest user currently exists, apply the DISALLOW_CONFIG_WIFI option
+ // to it, in case this guest was created in a previous version where this
+ // user restriction was not a default guest restriction.
+ setUserRestriction(UserManager.DISALLOW_CONFIG_WIFI, true, currentGuestUser.id);
+ }
}
@Override
@@ -828,6 +837,7 @@
private void initDefaultGuestRestrictions() {
synchronized (mGuestRestrictions) {
if (mGuestRestrictions.isEmpty()) {
+ mGuestRestrictions.putBoolean(UserManager.DISALLOW_CONFIG_WIFI, true);
mGuestRestrictions.putBoolean(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES, true);
mGuestRestrictions.putBoolean(UserManager.DISALLOW_OUTGOING_CALLS, true);
mGuestRestrictions.putBoolean(UserManager.DISALLOW_SMS, true);
diff --git a/services/core/java/com/android/server/power/PowerManagerService.java b/services/core/java/com/android/server/power/PowerManagerService.java
index cbd77d4..ff5a0f9 100644
--- a/services/core/java/com/android/server/power/PowerManagerService.java
+++ b/services/core/java/com/android/server/power/PowerManagerService.java
@@ -71,6 +71,8 @@
import com.android.server.am.BatteryStatsService;
import com.android.server.lights.Light;
import com.android.server.lights.LightsManager;
+import com.android.server.vr.VrManagerInternal;
+import com.android.server.vr.VrStateListener;
import libcore.util.Objects;
import java.io.FileDescriptor;
@@ -158,6 +160,7 @@
// Power hints defined in hardware/libhardware/include/hardware/power.h.
private static final int POWER_HINT_LOW_POWER = 5;
private static final int POWER_HINT_SUSTAINED_PERFORMANCE = 6;
+ private static final int POWER_HINT_VR_MODE = 7;
// Power features defined in hardware/libhardware/include/hardware/power.h.
private static final int POWER_FEATURE_DOUBLE_TAP_TO_WAKE = 1;
@@ -654,6 +657,7 @@
resolver.registerContentObserver(Settings.Secure.getUriFor(
Secure.BRIGHTNESS_USE_TWILIGHT),
false, mSettingsObserver, UserHandle.USER_ALL);
+ getLocalService(VrManagerInternal.class).registerListener(mVrStateListener);
// Go.
readConfigurationLocked();
updateSettingsLocked();
@@ -3002,6 +3006,13 @@
}
}
+ private final VrStateListener mVrStateListener = new VrStateListener() {
+ @Override
+ public void onVrStateChanged(boolean enabled) {
+ powerHintInternal(POWER_HINT_VR_MODE, enabled ? 1 : 0);
+ }
+ };
+
/**
* Handler for asynchronous operations performed by the power manager.
*/
diff --git a/services/core/java/com/android/server/vr/VrManagerService.java b/services/core/java/com/android/server/vr/VrManagerService.java
index 0aa3052..6bf949c 100644
--- a/services/core/java/com/android/server/vr/VrManagerService.java
+++ b/services/core/java/com/android/server/vr/VrManagerService.java
@@ -158,7 +158,7 @@
@Override
public void onBootPhase(int phase) {
- if (phase == SystemService.PHASE_THIRD_PARTY_APPS_CAN_START) {
+ if (phase == SystemService.PHASE_SYSTEM_SERVICES_READY) {
synchronized (mLock) {
Looper looper = Looper.getMainLooper();
Handler handler = new Handler(looper);
diff --git a/services/core/java/com/android/server/wm/BoundsAnimationController.java b/services/core/java/com/android/server/wm/BoundsAnimationController.java
index 79d3d84..b7d6062 100644
--- a/services/core/java/com/android/server/wm/BoundsAnimationController.java
+++ b/services/core/java/com/android/server/wm/BoundsAnimationController.java
@@ -214,7 +214,7 @@
void getFullScreenBounds(Rect bounds);
}
- void animateBounds(final AnimateBoundsUser target, Rect from, Rect to) {
+ void animateBounds(final AnimateBoundsUser target, Rect from, Rect to, int animationDuration) {
boolean moveToFullscreen = false;
if (to == null) {
to = new Rect();
@@ -242,7 +242,8 @@
new BoundsAnimator(target, from, to, moveToFullscreen, replacing);
mRunningAnimations.put(target, animator);
animator.setFloatValues(0f, 1f);
- animator.setDuration(DEFAULT_APP_TRANSITION_DURATION * DEBUG_ANIMATION_SLOW_DOWN_FACTOR);
+ animator.setDuration((animationDuration != -1 ? animationDuration
+ : DEFAULT_APP_TRANSITION_DURATION) * DEBUG_ANIMATION_SLOW_DOWN_FACTOR);
animator.setInterpolator(new LinearInterpolator());
animator.start();
}
diff --git a/services/core/java/com/android/server/wm/TaskStack.java b/services/core/java/com/android/server/wm/TaskStack.java
index 60b2e4a..c667767 100644
--- a/services/core/java/com/android/server/wm/TaskStack.java
+++ b/services/core/java/com/android/server/wm/TaskStack.java
@@ -1089,7 +1089,7 @@
}
}
try {
- mService.mActivityManager.resizeStack(mStackId, bounds, false, true, false);
+ mService.mActivityManager.resizeStack(mStackId, bounds, false, true, false, -1);
} catch (RemoteException e) {
}
return true;
diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java
index 607a3e9..b84ed7b 100644
--- a/services/core/java/com/android/server/wm/WindowManagerService.java
+++ b/services/core/java/com/android/server/wm/WindowManagerService.java
@@ -8241,8 +8241,8 @@
break;
case RESIZE_STACK: {
try {
- mActivityManager.resizeStack(msg.arg1, (Rect) msg.obj, msg.arg2 == 1, false,
- false);
+ mActivityManager.resizeStack(
+ msg.arg1, (Rect) msg.obj, msg.arg2 == 1, false, false, -1);
} catch (RemoteException e) {
// This will not happen since we are in the same process.
}
@@ -10460,7 +10460,7 @@
}
}
- public void animateResizePinnedStack(final Rect bounds) {
+ public void animateResizePinnedStack(final Rect bounds, final int animationDuration) {
synchronized (mWindowMap) {
final TaskStack stack = mStackIdToStack.get(PINNED_STACK_ID);
if (stack == null) {
@@ -10472,7 +10472,8 @@
UiThread.getHandler().post(new Runnable() {
@Override
public void run() {
- mBoundsAnimationController.animateBounds(stack, originalBounds, bounds);
+ mBoundsAnimationController.animateBounds(
+ stack, originalBounds, bounds, animationDuration);
}
});
}
diff --git a/telecomm/java/android/telecom/ParcelableConnection.java b/telecomm/java/android/telecom/ParcelableConnection.java
index fe0a4d8..ce51c96 100644
--- a/telecomm/java/android/telecom/ParcelableConnection.java
+++ b/telecomm/java/android/telecom/ParcelableConnection.java
@@ -188,7 +188,7 @@
DisconnectCause disconnectCause = source.readParcelable(classLoader);
List<String> conferenceableConnectionIds = new ArrayList<>();
source.readStringList(conferenceableConnectionIds);
- Bundle extras = source.readBundle(classLoader);
+ Bundle extras = Bundle.setDefusable(source.readBundle(classLoader), true);
return new ParcelableConnection(
phoneAccount,
diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java
index 86518b5..c69a360 100644
--- a/telephony/java/android/telephony/CarrierConfigManager.java
+++ b/telephony/java/android/telephony/CarrierConfigManager.java
@@ -590,21 +590,8 @@
* When {@code true}, video calls to emergency numbers will be allowed. When {@code false},
* video calls to emergency numbers will be initiated as audio-only calls instead.
*/
- @SystemApi
- public static final String BOOL_ALLOW_EMERGENCY_VIDEO_CALLS =
- "bool_allow_emergency_video_calls";
-
- /**
- * Flag indicating whether the carrier supports video pause signaling. When {@code true}, the
- * carrier supports use of the {@link android.telecom.VideoProfile#STATE_PAUSED} video state
- * to pause transmission of video when the In-Call app is sent to the background.
- * When {@code false}, video pause signaling is not supported. {@code True} by default unless
- * a carrier configuration overrides the default.
- */
- @SystemApi
- public static final String BOOL_ALLOW_VIDEO_PAUSE =
- "bool_allow_video_pause";
-
+ public static final String KEY_ALLOW_EMERGENCY_VIDEO_CALLS_BOOL =
+ "allow_emergency_video_calls_bool";
/**
* Flag indicating whether the carrier supports RCS presence indication for video calls. When
@@ -617,7 +604,6 @@
* and can choose to hide or show the video calling icon based on whether a contact supports
* video.
*/
- @SystemApi
public static final String KEY_USE_RCS_PRESENCE_BOOL = "use_rcs_presence_bool";
/**
@@ -715,8 +701,7 @@
sDefaults.putBoolean(KEY_EDITABLE_ENHANCED_4G_LTE_BOOL, true);
sDefaults.putBoolean(KEY_HIDE_IMS_APN_BOOL, false);
sDefaults.putBoolean(KEY_HIDE_PREFERRED_NETWORK_TYPE_BOOL, false);
- sDefaults.putBoolean(BOOL_ALLOW_EMERGENCY_VIDEO_CALLS, false);
- sDefaults.putBoolean(BOOL_ALLOW_VIDEO_PAUSE, true);
+ sDefaults.putBoolean(KEY_ALLOW_EMERGENCY_VIDEO_CALLS_BOOL, false);
sDefaults.putBoolean(KEY_EDITABLE_WFC_MODE_BOOL, true);
// MMS defaults
diff --git a/telephony/java/com/android/internal/telephony/RILConstants.java b/telephony/java/com/android/internal/telephony/RILConstants.java
index 4f0e036..8aa0e34 100644
--- a/telephony/java/com/android/internal/telephony/RILConstants.java
+++ b/telephony/java/com/android/internal/telephony/RILConstants.java
@@ -81,8 +81,7 @@
int INTERNAL_ERR = 38; /* Hit unexpected vendor internal error scenario */
int SYSTEM_ERR = 39; /* Hit platform or system error */
int MODEM_ERR = 40; /* Hit unexpected modem error */
- int INVALID_STATE = 41; /* Can not process the request as vendor RIL is in
- invalid state. */
+ int INVALID_STATE = 41; /* Unexpected request for the current state */
int NO_RESOURCES = 42; /* Not sufficient resource to process the request */
int SIM_ERR = 43; /* Received error from SIM card */
int INVALID_ARGUMENTS = 44; /* Received invalid arguments in request */
@@ -103,6 +102,11 @@
int NO_SUCH_ENTRY = 59; /* No such entry present to perform the request */
int NETWORK_NOT_READY = 60; /* Network is not ready to perform the request */
int NOT_PROVISIONED = 61; /* Device doesnot have this value provisioned */
+ int NO_SUBSCRIPTION = 62; /* Device doesnot have subscription */
+ int NO_NETWORK_FOUND = 63; /* Network cannot be found */
+ int DEVICE_IN_USE = 64; /* Operation cannot be performed because the device
+ is currently in use */
+ int ABORTED = 65; /* Operation aborted */
// Below is list of OEM specific error codes which can by used by OEMs in case they don't want to
// reveal particular replacement for Generic failure
int OEM_ERROR_1 = 501;
diff --git a/tools/aapt/Bundle.h b/tools/aapt/Bundle.h
index c449550..ca06ac4 100644
--- a/tools/aapt/Bundle.h
+++ b/tools/aapt/Bundle.h
@@ -249,7 +249,7 @@
* above. SDK levels that have a non-numeric identifier are assumed
* to be newer than any SDK level that has a number designated.
*/
- bool isMinSdkAtLeast(int desired) {
+ bool isMinSdkAtLeast(int desired) const {
/* If the application specifies a minSdkVersion in the manifest
* then use that. Otherwise, check what the user specified on
* the command line. If neither, it's not available since
diff --git a/tools/aapt/Images.cpp b/tools/aapt/Images.cpp
index 40466bd..9939c18 100644
--- a/tools/aapt/Images.cpp
+++ b/tools/aapt/Images.cpp
@@ -1134,10 +1134,9 @@
}
}
-
static void write_png(const char* imageName,
png_structp write_ptr, png_infop write_info,
- image_info& imageInfo, int grayscaleTolerance)
+ image_info& imageInfo, const Bundle* bundle)
{
png_uint_32 width, height;
int color_type;
@@ -1174,9 +1173,26 @@
bool hasTransparency;
int paletteEntries, alphaPaletteEntries;
+ int grayscaleTolerance = bundle->getGrayscaleTolerance();
analyze_image(imageName, imageInfo, grayscaleTolerance, rgbPalette, alphaPalette,
&paletteEntries, &alphaPaletteEntries, &hasTransparency, &color_type, outRows);
+ // Legacy versions of aapt would always encode 9patch PNGs as RGBA. This had the unintended
+ // benefit of working around a bug decoding paletted images in Android 4.1.
+ // https://code.google.com/p/android/issues/detail?id=34619
+ //
+ // If SDK_JELLY_BEAN is supported, we need to avoid a paletted encoding in order to not expose
+ // this bug.
+ if (!bundle->isMinSdkAtLeast(SDK_JELLY_BEAN_MR1)) {
+ if (imageInfo.is9Patch && PNG_COLOR_TYPE_PALETTE == color_type) {
+ if (hasTransparency) {
+ color_type = PNG_COLOR_TYPE_RGB_ALPHA;
+ } else {
+ color_type = PNG_COLOR_TYPE_RGB;
+ }
+ }
+ }
+
if (kIsDebug) {
switch (color_type) {
case PNG_COLOR_TYPE_PALETTE:
@@ -1332,8 +1348,7 @@
return false;
}
- write_png(printableName.string(), write_ptr, write_info, *imageInfo,
- bundle->getGrayscaleTolerance());
+ write_png(printableName.string(), write_ptr, write_info, *imageInfo, bundle);
return true;
}
@@ -1543,8 +1558,7 @@
}
// Actually write out to the new png
- write_png(dest.string(), write_ptr, write_info, imageInfo,
- bundle->getGrayscaleTolerance());
+ write_png(dest.string(), write_ptr, write_info, imageInfo, bundle);
if (bundle->getVerbose()) {
// Find the size of our new file
diff --git a/wifi/java/android/net/wifi/WifiEnterpriseConfig.java b/wifi/java/android/net/wifi/WifiEnterpriseConfig.java
index 58e8761..9e15d60 100644
--- a/wifi/java/android/net/wifi/WifiEnterpriseConfig.java
+++ b/wifi/java/android/net/wifi/WifiEnterpriseConfig.java
@@ -1047,7 +1047,7 @@
StringBuffer sb = new StringBuffer();
for (String key : mFields.keySet()) {
// Don't display password in toString().
- String value = (key == PASSWORD_KEY) ? "<removed>" : mFields.get(key);
+ String value = PASSWORD_KEY.equals(key) ? "<removed>" : mFields.get(key);
sb.append(key).append(" ").append(value).append("\n");
}
return sb.toString();