Merge "Have Recents focus second task when launched, if 2 or more tasks are available" into nyc-dev
diff --git a/api/current.txt b/api/current.txt
index 1c4f85b..1c77142 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -3578,6 +3578,7 @@
     method public final deprecated void removeDialog(int);
     method public void reportFullyDrawn();
     method public android.view.DropPermissions requestDropPermissions(android.view.DragEvent);
+    method public final void requestKeyboardShortcutsHelper();
     method public final void requestPermissions(java.lang.String[], int);
     method public boolean requestVisibleBehind(boolean);
     method public final boolean requestWindowFeature(int);
@@ -5030,13 +5031,13 @@
     method public android.app.Notification.Action.Builder extend(android.app.Notification.Action.Builder);
     method public java.lang.CharSequence getCancelLabel();
     method public java.lang.CharSequence getConfirmLabel();
-    method public boolean getHintContentIntentLaunchesActivity();
+    method public boolean getHintLaunchesActivity();
     method public java.lang.CharSequence getInProgressLabel();
     method public boolean isAvailableOffline();
     method public android.app.Notification.Action.WearableExtender setAvailableOffline(boolean);
     method public android.app.Notification.Action.WearableExtender setCancelLabel(java.lang.CharSequence);
     method public android.app.Notification.Action.WearableExtender setConfirmLabel(java.lang.CharSequence);
-    method public android.app.Notification.Action.WearableExtender setHintContentIntentLaunchesActivity(boolean);
+    method public android.app.Notification.Action.WearableExtender setHintLaunchesActivity(boolean);
     method public android.app.Notification.Action.WearableExtender setInProgressLabel(java.lang.CharSequence);
   }
 
@@ -8685,6 +8686,7 @@
     field public static final java.lang.String EXTRA_CHANGED_PACKAGE_LIST = "android.intent.extra.changed_package_list";
     field public static final java.lang.String EXTRA_CHANGED_UID_LIST = "android.intent.extra.changed_uid_list";
     field public static final java.lang.String EXTRA_CHOOSER_REFINEMENT_INTENT_SENDER = "android.intent.extra.CHOOSER_REFINEMENT_INTENT_SENDER";
+    field public static final java.lang.String EXTRA_CHOOSER_TARGETS = "android.intent.extra.CHOOSER_TARGETS";
     field public static final java.lang.String EXTRA_CHOSEN_COMPONENT = "android.intent.extra.CHOSEN_COMPONENT";
     field public static final java.lang.String EXTRA_CHOSEN_COMPONENT_INTENT_SENDER = "android.intent.extra.CHOSEN_COMPONENT_INTENT_SENDER";
     field public static final java.lang.String EXTRA_DATA_REMOVED = "android.intent.extra.DATA_REMOVED";
@@ -8696,6 +8698,7 @@
     field public static final int EXTRA_DOCK_STATE_UNDOCKED = 0; // 0x0
     field public static final java.lang.String EXTRA_DONT_KILL_APP = "android.intent.extra.DONT_KILL_APP";
     field public static final java.lang.String EXTRA_EMAIL = "android.intent.extra.EMAIL";
+    field public static final java.lang.String EXTRA_EXCLUDE_COMPONENTS = "android.intent.extra.EXCLUDE_COMPONENTS";
     field public static final java.lang.String EXTRA_HTML_TEXT = "android.intent.extra.HTML_TEXT";
     field public static final java.lang.String EXTRA_INDEX = "android.intent.extra.INDEX";
     field public static final java.lang.String EXTRA_INITIAL_INTENTS = "android.intent.extra.INITIAL_INTENTS";
@@ -9494,10 +9497,8 @@
 
   public class LauncherApps {
     method public java.util.List<android.content.pm.LauncherActivityInfo> getActivityList(java.lang.String, android.os.UserHandle);
-    method public android.content.pm.ApplicationInfo getApplicationInfo(java.lang.String, int, android.os.UserHandle);
-    method public android.os.ParcelFileDescriptor getShortcutIconFd(android.content.pm.ShortcutInfo, android.os.UserHandle);
-    method public int getShortcutIconResId(android.content.pm.ShortcutInfo, android.os.UserHandle);
-    method public java.util.List<android.content.pm.ShortcutInfo> getShortcutInfo(java.lang.String, java.util.List<java.lang.String>, android.os.UserHandle);
+    method public android.os.ParcelFileDescriptor getShortcutIconFd(android.content.pm.ShortcutInfo);
+    method public android.os.ParcelFileDescriptor getShortcutIconFd(java.lang.String, java.lang.String, android.os.UserHandle);
     method public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(android.content.pm.LauncherApps.ShortcutQuery, android.os.UserHandle);
     method public boolean hasShortcutHostPermission();
     method public boolean isActivityEnabled(android.content.ComponentName, android.os.UserHandle);
@@ -9509,6 +9510,7 @@
     method public void startAppDetailsActivity(android.content.ComponentName, android.os.UserHandle, android.graphics.Rect, android.os.Bundle);
     method public void startMainActivity(android.content.ComponentName, android.os.UserHandle, android.graphics.Rect, android.os.Bundle);
     method public boolean startShortcut(java.lang.String, java.lang.String, android.graphics.Rect, android.os.Bundle, android.os.UserHandle);
+    method public boolean startShortcut(android.content.pm.ShortcutInfo, android.graphics.Rect, android.os.Bundle);
     method public void unregisterCallback(android.content.pm.LauncherApps.Callback);
   }
 
@@ -9530,6 +9532,7 @@
     method public void setChangedSince(long);
     method public void setPackage(java.lang.String);
     method public void setQueryFlags(int);
+    method public void setShortcutIds(java.util.List<java.lang.String>);
     field public static final int FLAG_GET_DYNAMIC = 1; // 0x1
     field public static final int FLAG_GET_KEY_FIELDS_ONLY = 4; // 0x4
     field public static final int FLAG_GET_PINNED = 2; // 0x2
@@ -10036,13 +10039,16 @@
   public final class ShortcutInfo implements android.os.Parcelable {
     method public int describeContents();
     method public android.content.ComponentName getActivityComponent();
+    method public java.util.List<java.lang.String> getCategories();
     method public android.os.PersistableBundle getExtras();
+    method public int getIconResourceId();
     method public java.lang.String getId();
     method public android.content.Intent getIntent();
     method public long getLastChangedTimestamp();
     method public java.lang.String getPackageName();
     method public java.lang.String getText();
     method public java.lang.String getTitle();
+    method public android.os.UserHandle getUserHandle();
     method public int getWeight();
     method public boolean hasIconFile();
     method public boolean hasIconResource();
@@ -10059,12 +10065,14 @@
     field public static final int FLAG_HAS_ICON_RES = 4; // 0x4
     field public static final int FLAG_KEY_FIELDS_ONLY = 16; // 0x10
     field public static final int FLAG_PINNED = 2; // 0x2
+    field public static final java.lang.String SHORTCUT_CATEGORY_CONVERSATION = "android.shortcut.conversation";
   }
 
   public static class ShortcutInfo.Builder {
     ctor public ShortcutInfo.Builder(android.content.Context);
     method public android.content.pm.ShortcutInfo build();
     method public android.content.pm.ShortcutInfo.Builder setActivityComponent(android.content.ComponentName);
+    method public android.content.pm.ShortcutInfo.Builder setCategories(java.util.List<java.lang.String>);
     method public android.content.pm.ShortcutInfo.Builder setExtras(android.os.PersistableBundle);
     method public android.content.pm.ShortcutInfo.Builder setIcon(android.graphics.drawable.Icon);
     method public android.content.pm.ShortcutInfo.Builder setId(java.lang.String);
@@ -10075,15 +10083,15 @@
   }
 
   public class ShortcutManager {
-    method public boolean addDynamicShortcut(android.content.pm.ShortcutInfo);
-    method public void deleteAllDynamicShortcuts();
-    method public void deleteDynamicShortcut(java.lang.String);
+    method public boolean addDynamicShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
     method public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts();
     method public int getIconMaxDimensions();
     method public int getMaxDynamicShortcutCount();
     method public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts();
     method public long getRateLimitResetTime();
     method public int getRemainingCallCount();
+    method public void removeAllDynamicShortcuts();
+    method public void removeDynamicShortcuts(java.util.List<java.lang.String>);
     method public boolean setDynamicShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
     method public boolean updateShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
   }
@@ -13923,11 +13931,11 @@
     method public abstract void close();
     method public abstract android.hardware.camera2.CaptureRequest.Builder createCaptureRequest(int) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
-    method public abstract void createCaptureSessionByOutputConfiguration(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
+    method public abstract void createCaptureSessionByOutputConfigurations(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createConstrainedHighSpeedCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract android.hardware.camera2.CaptureRequest.Builder createReprocessCaptureRequest(android.hardware.camera2.TotalCaptureResult) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createReprocessableCaptureSession(android.hardware.camera2.params.InputConfiguration, java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
-    method public abstract void createReprocessableCaptureSessionWithConfigurations(android.hardware.camera2.params.InputConfiguration, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
+    method public abstract void createReprocessableCaptureSessionByConfigurations(android.hardware.camera2.params.InputConfiguration, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract java.lang.String getId();
     field public static final int TEMPLATE_MANUAL = 6; // 0x6
     field public static final int TEMPLATE_PREVIEW = 1; // 0x1
@@ -19850,8 +19858,8 @@
 
   public class AudioRecord implements android.media.AudioRouting {
     ctor public AudioRecord(int, int, int, int, int) throws java.lang.IllegalArgumentException;
+    method public void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public deprecated void addOnRoutingChangedListener(android.media.AudioRecord.OnRoutingChangedListener, android.os.Handler);
-    method public void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public int getAudioFormat();
     method public int getAudioSessionId();
     method public int getAudioSource();
@@ -19876,8 +19884,8 @@
     method public int read(java.nio.ByteBuffer, int);
     method public int read(java.nio.ByteBuffer, int, int);
     method public void release();
+    method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public deprecated void removeOnRoutingChangedListener(android.media.AudioRecord.OnRoutingChangedListener);
-    method public void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public int setNotificationMarkerPosition(int);
     method public int setPositionNotificationPeriod(int);
     method public boolean setPreferredDevice(android.media.AudioDeviceInfo);
@@ -19911,8 +19919,9 @@
     method public abstract void onPeriodicNotification(android.media.AudioRecord);
   }
 
-  public static abstract interface AudioRecord.OnRoutingChangedListener {
+  public static abstract deprecated interface AudioRecord.OnRoutingChangedListener implements android.media.AudioRouting.OnRoutingChangedListener {
     method public abstract void onRoutingChanged(android.media.AudioRecord);
+    method public default void onRoutingChanged(android.media.AudioRouting);
   }
 
   public final class AudioRecordingConfiguration implements android.os.Parcelable {
@@ -19927,10 +19936,10 @@
   }
 
   public abstract interface AudioRouting {
-    method public abstract void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
+    method public abstract void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public abstract android.media.AudioDeviceInfo getPreferredDevice();
     method public abstract android.media.AudioDeviceInfo getRoutedDevice();
-    method public abstract void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
+    method public abstract void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public abstract boolean setPreferredDevice(android.media.AudioDeviceInfo);
   }
 
@@ -19950,8 +19959,8 @@
     ctor public AudioTrack(int, int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioTrack(int, int, int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioTrack(android.media.AudioAttributes, android.media.AudioFormat, int, int, int) throws java.lang.IllegalArgumentException;
+    method public void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public deprecated void addOnRoutingChangedListener(android.media.AudioTrack.OnRoutingChangedListener, android.os.Handler);
-    method public void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public int attachAuxEffect(int);
     method public void flush();
     method public int getAudioFormat();
@@ -19983,8 +19992,8 @@
     method public void play() throws java.lang.IllegalStateException;
     method public void release();
     method public int reloadStaticData();
+    method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public deprecated void removeOnRoutingChangedListener(android.media.AudioTrack.OnRoutingChangedListener);
-    method public void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public int setAuxEffectSendLevel(float);
     method public int setBufferSizeInFrames(int);
     method public int setLoopPoints(int, int, int);
@@ -20038,8 +20047,9 @@
     method public abstract void onPeriodicNotification(android.media.AudioTrack);
   }
 
-  public static abstract deprecated interface AudioTrack.OnRoutingChangedListener {
-    method public abstract deprecated void onRoutingChanged(android.media.AudioTrack);
+  public static abstract deprecated interface AudioTrack.OnRoutingChangedListener implements android.media.AudioRouting.OnRoutingChangedListener {
+    method public abstract void onRoutingChanged(android.media.AudioTrack);
+    method public default void onRoutingChanged(android.media.AudioRouting);
   }
 
   public class CamcorderProfile {
@@ -20715,10 +20725,12 @@
     field public static final int VP9Level6 = 1024; // 0x400
     field public static final int VP9Level61 = 2048; // 0x800
     field public static final int VP9Level62 = 4096; // 0x1000
-    field public static final int VP9Profile0 = 0; // 0x0
-    field public static final int VP9Profile1 = 1; // 0x1
-    field public static final int VP9Profile2 = 2; // 0x2
-    field public static final int VP9Profile3 = 3; // 0x3
+    field public static final int VP9Profile0 = 1; // 0x1
+    field public static final int VP9Profile1 = 2; // 0x2
+    field public static final int VP9Profile2 = 4; // 0x4
+    field public static final int VP9Profile2HDR = 4096; // 0x1000
+    field public static final int VP9Profile3 = 8; // 0x8
+    field public static final int VP9Profile3HDR = 8192; // 0x2000
     field public int level;
     field public int profile;
   }
@@ -29573,6 +29585,7 @@
   public class StorageManager {
     method public java.lang.String getMountedObbPath(java.lang.String);
     method public android.os.storage.StorageVolume getPrimaryStorageVolume();
+    method public android.os.storage.StorageVolume getStorageVolume(java.io.File);
     method public java.util.List<android.os.storage.StorageVolume> getStorageVolumes();
     method public boolean isEncrypted(java.io.File);
     method public boolean isObbMounted(java.lang.String);
@@ -34723,7 +34736,9 @@
     method public static void requestRebind(android.content.ComponentName) throws android.os.RemoteException;
     method public final void requestUnbind() throws android.os.RemoteException;
     method public final void setNotificationsShown(java.lang.String[]);
+    field public static final int HINT_HOST_DISABLE_CALL_EFFECTS = 4; // 0x4
     field public static final int HINT_HOST_DISABLE_EFFECTS = 1; // 0x1
+    field public static final int HINT_HOST_DISABLE_NOTIFICATION_EFFECTS = 2; // 0x2
     field public static final int INTERRUPTION_FILTER_ALARMS = 4; // 0x4
     field public static final int INTERRUPTION_FILTER_ALL = 1; // 0x1
     field public static final int INTERRUPTION_FILTER_NONE = 3; // 0x3
@@ -34739,6 +34754,7 @@
     method public int getImportance();
     method public java.lang.CharSequence getImportanceExplanation();
     method public java.lang.String getKey();
+    method public java.lang.String getOverrideGroupKey();
     method public int getRank();
     method public int getSuppressedVisualEffects();
     method public boolean isAmbient();
@@ -34769,13 +34785,16 @@
     method public int getId();
     method public java.lang.String getKey();
     method public android.app.Notification getNotification();
+    method public java.lang.String getOverrideGroupKey();
     method public java.lang.String getPackageName();
     method public long getPostTime();
     method public java.lang.String getTag();
     method public android.os.UserHandle getUser();
     method public deprecated int getUserId();
     method public boolean isClearable();
+    method public boolean isGroup();
     method public boolean isOngoing();
+    method public void setOverrideGroupKey(java.lang.String);
     method public void writeToParcel(android.os.Parcel, int);
     field public static final android.os.Parcelable.Creator<android.service.notification.StatusBarNotification> CREATOR;
   }
@@ -34811,7 +34830,7 @@
     method public void onClick();
     method public void onStartListening();
     method public void onStopListening();
-    method public int onTileAdded();
+    method public void onTileAdded();
     method public void onTileRemoved();
     method public static final void requestListeningState(android.content.Context, android.content.ComponentName);
     method public final void showDialog(android.app.Dialog);
@@ -34819,8 +34838,7 @@
     method public final void unlockAndRun(java.lang.Runnable);
     field public static final java.lang.String ACTION_QS_TILE = "android.service.quicksettings.action.QS_TILE";
     field public static final java.lang.String ACTION_QS_TILE_PREFERENCES = "android.service.quicksettings.action.QS_TILE_PREFERENCES";
-    field public static final int TILE_MODE_ACTIVE = 2; // 0x2
-    field public static final int TILE_MODE_PASSIVE = 1; // 0x1
+    field public static final java.lang.String META_DATA_ACTIVE_TILE = "android.service.quicksettings.ACTIVE_TILE";
   }
 
 }
@@ -49045,6 +49063,7 @@
     ctor public BufferedReader(java.io.Reader, int);
     ctor public BufferedReader(java.io.Reader);
     method public void close() throws java.io.IOException;
+    method public java.util.stream.Stream<java.lang.String> lines();
     method public int read(char[], int, int) throws java.io.IOException;
     method public java.lang.String readLine() throws java.io.IOException;
   }
@@ -49915,6 +49934,11 @@
     ctor public UTFDataFormatException(java.lang.String);
   }
 
+  public class UncheckedIOException extends java.lang.RuntimeException {
+    ctor public UncheckedIOException(java.lang.String, java.io.IOException);
+    ctor public UncheckedIOException(java.io.IOException);
+  }
+
   public class UnsupportedEncodingException extends java.io.IOException {
     ctor public UnsupportedEncodingException();
     ctor public UnsupportedEncodingException(java.lang.String);
@@ -51977,7 +52001,6 @@
   public final class Method extends java.lang.reflect.AccessibleObject implements java.lang.reflect.GenericDeclaration java.lang.reflect.Member {
     method public boolean equals(java.lang.Object);
     method public A getAnnotation(java.lang.Class<A>);
-    method public java.lang.annotation.Annotation[] getDeclaredAnnotations();
     method public java.lang.Class<?> getDeclaringClass();
     method public java.lang.Object getDefaultValue();
     method public java.lang.Class<?>[] getExceptionTypes();
@@ -51991,7 +52014,6 @@
     method public java.lang.Class<?> getReturnType();
     method public java.lang.reflect.TypeVariable<java.lang.reflect.Method>[] getTypeParameters();
     method public java.lang.Object invoke(java.lang.Object, java.lang.Object...) throws java.lang.IllegalAccessException, java.lang.IllegalArgumentException, java.lang.reflect.InvocationTargetException;
-    method public boolean isAnnotationPresent(java.lang.Class<? extends java.lang.annotation.Annotation>);
     method public boolean isBridge();
     method public boolean isDefault();
     method public boolean isSynthetic();
@@ -57573,6 +57595,7 @@
     method public void set(int, int);
     method public void set(int, int, boolean);
     method public int size();
+    method public java.util.stream.IntStream stream();
     method public byte[] toByteArray();
     method public long[] toLongArray();
     method public static java.util.BitSet valueOf(long[]);
@@ -58028,6 +58051,7 @@
     method public java.util.Set<java.util.Map.Entry<K, V>> entrySet();
     method public void forEach(java.util.function.BiConsumer<? super K, ? super V>);
     method public boolean replace(K, V, V);
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
   }
 
   public class HashSet extends java.util.AbstractSet implements java.lang.Cloneable java.io.Serializable java.util.Set {
@@ -58071,6 +58095,7 @@
     method public synchronized boolean remove(java.lang.Object, java.lang.Object);
     method public synchronized boolean replace(K, V, V);
     method public synchronized V replace(K, V);
+    method public synchronized void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
     method public synchronized int size();
     method public java.util.Collection<V> values();
   }
@@ -58611,6 +58636,18 @@
   public class Random implements java.io.Serializable {
     ctor public Random();
     ctor public Random(long);
+    method public java.util.stream.DoubleStream doubles(long);
+    method public java.util.stream.DoubleStream doubles();
+    method public java.util.stream.DoubleStream doubles(long, double, double);
+    method public java.util.stream.DoubleStream doubles(double, double);
+    method public java.util.stream.IntStream ints(long);
+    method public java.util.stream.IntStream ints();
+    method public java.util.stream.IntStream ints(long, int, int);
+    method public java.util.stream.IntStream ints(int, int);
+    method public java.util.stream.LongStream longs(long);
+    method public java.util.stream.LongStream longs();
+    method public java.util.stream.LongStream longs(long, long, long);
+    method public java.util.stream.LongStream longs(long, long);
     method protected int next(int);
     method public boolean nextBoolean();
     method public void nextBytes(byte[]);
@@ -59052,6 +59089,7 @@
     method public java.util.NavigableSet<K> navigableKeySet();
     method public java.util.Map.Entry<K, V> pollFirstEntry();
     method public java.util.Map.Entry<K, V> pollLastEntry();
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
     method public java.util.NavigableMap<K, V> subMap(K, boolean, K, boolean);
     method public java.util.SortedMap<K, V> subMap(K, K);
     method public java.util.NavigableMap<K, V> tailMap(K, boolean);
@@ -59153,6 +59191,7 @@
     ctor public WeakHashMap(java.util.Map<? extends K, ? extends V>);
     method public java.util.Set<java.util.Map.Entry<K, V>> entrySet();
     method public void forEach(java.util.function.BiConsumer<? super K, ? super V>);
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
   }
 
 }
@@ -60126,18 +60165,6 @@
 
   public class ThreadLocalRandom extends java.util.Random {
     method public static java.util.concurrent.ThreadLocalRandom current();
-    method public java.util.stream.DoubleStream doubles(long);
-    method public java.util.stream.DoubleStream doubles();
-    method public java.util.stream.DoubleStream doubles(long, double, double);
-    method public java.util.stream.DoubleStream doubles(double, double);
-    method public java.util.stream.IntStream ints(long);
-    method public java.util.stream.IntStream ints();
-    method public java.util.stream.IntStream ints(long, int, int);
-    method public java.util.stream.IntStream ints(int, int);
-    method public java.util.stream.LongStream longs(long);
-    method public java.util.stream.LongStream longs();
-    method public java.util.stream.LongStream longs(long, long, long);
-    method public java.util.stream.LongStream longs(long, long);
     method public double nextDouble(double);
     method public double nextDouble(double, double);
     method public int nextInt(int, int);
@@ -61510,6 +61537,7 @@
   }
 
   public final class Pattern implements java.io.Serializable {
+    method public java.util.function.Predicate<java.lang.String> asPredicate();
     method public static java.util.regex.Pattern compile(java.lang.String);
     method public static java.util.regex.Pattern compile(java.lang.String, int) throws java.util.regex.PatternSyntaxException;
     method public int flags();
@@ -61519,6 +61547,7 @@
     method public static java.lang.String quote(java.lang.String);
     method public java.lang.String[] split(java.lang.CharSequence, int);
     method public java.lang.String[] split(java.lang.CharSequence);
+    method public java.util.stream.Stream<java.lang.String> splitAsStream(java.lang.CharSequence);
     field public static final int CANON_EQ = 128; // 0x80
     field public static final int CASE_INSENSITIVE = 2; // 0x2
     field public static final int COMMENTS = 4; // 0x4
diff --git a/api/system-current.txt b/api/system-current.txt
index 039b9ad..ee3e6d3 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -3696,6 +3696,7 @@
     method public final deprecated void removeDialog(int);
     method public void reportFullyDrawn();
     method public android.view.DropPermissions requestDropPermissions(android.view.DragEvent);
+    method public final void requestKeyboardShortcutsHelper();
     method public final void requestPermissions(java.lang.String[], int);
     method public boolean requestVisibleBehind(boolean);
     method public final boolean requestWindowFeature(int);
@@ -5076,6 +5077,7 @@
     field public static final java.lang.String EXTRA_THREAD_TITLE = "android.threadTitle";
     field public static final java.lang.String EXTRA_TITLE = "android.title";
     field public static final java.lang.String EXTRA_TITLE_BIG = "android.title.big";
+    field public static final int FLAG_AUTOGROUP_SUMMARY = 1024; // 0x400
     field public static final int FLAG_AUTO_CANCEL = 16; // 0x10
     field public static final int FLAG_FOREGROUND_SERVICE = 64; // 0x40
     field public static final int FLAG_GROUP_SUMMARY = 512; // 0x200
@@ -5163,13 +5165,13 @@
     method public android.app.Notification.Action.Builder extend(android.app.Notification.Action.Builder);
     method public java.lang.CharSequence getCancelLabel();
     method public java.lang.CharSequence getConfirmLabel();
-    method public boolean getHintContentIntentLaunchesActivity();
+    method public boolean getHintLaunchesActivity();
     method public java.lang.CharSequence getInProgressLabel();
     method public boolean isAvailableOffline();
     method public android.app.Notification.Action.WearableExtender setAvailableOffline(boolean);
     method public android.app.Notification.Action.WearableExtender setCancelLabel(java.lang.CharSequence);
     method public android.app.Notification.Action.WearableExtender setConfirmLabel(java.lang.CharSequence);
-    method public android.app.Notification.Action.WearableExtender setHintContentIntentLaunchesActivity(boolean);
+    method public android.app.Notification.Action.WearableExtender setHintLaunchesActivity(boolean);
     method public android.app.Notification.Action.WearableExtender setInProgressLabel(java.lang.CharSequence);
   }
 
@@ -9004,6 +9006,7 @@
     field public static final java.lang.String EXTRA_CHANGED_PACKAGE_LIST = "android.intent.extra.changed_package_list";
     field public static final java.lang.String EXTRA_CHANGED_UID_LIST = "android.intent.extra.changed_uid_list";
     field public static final java.lang.String EXTRA_CHOOSER_REFINEMENT_INTENT_SENDER = "android.intent.extra.CHOOSER_REFINEMENT_INTENT_SENDER";
+    field public static final java.lang.String EXTRA_CHOOSER_TARGETS = "android.intent.extra.CHOOSER_TARGETS";
     field public static final java.lang.String EXTRA_CHOSEN_COMPONENT = "android.intent.extra.CHOSEN_COMPONENT";
     field public static final java.lang.String EXTRA_CHOSEN_COMPONENT_INTENT_SENDER = "android.intent.extra.CHOSEN_COMPONENT_INTENT_SENDER";
     field public static final java.lang.String EXTRA_DATA_REMOVED = "android.intent.extra.DATA_REMOVED";
@@ -9017,6 +9020,7 @@
     field public static final java.lang.String EXTRA_EMAIL = "android.intent.extra.EMAIL";
     field public static final java.lang.String EXTRA_EPHEMERAL_FAILURE = "android.intent.extra.EPHEMERAL_FAILURE";
     field public static final java.lang.String EXTRA_EPHEMERAL_SUCCESS = "android.intent.extra.EPHEMERAL_SUCCESS";
+    field public static final java.lang.String EXTRA_EXCLUDE_COMPONENTS = "android.intent.extra.EXCLUDE_COMPONENTS";
     field public static final java.lang.String EXTRA_HTML_TEXT = "android.intent.extra.HTML_TEXT";
     field public static final java.lang.String EXTRA_INDEX = "android.intent.extra.INDEX";
     field public static final java.lang.String EXTRA_INITIAL_INTENTS = "android.intent.extra.INITIAL_INTENTS";
@@ -9831,10 +9835,8 @@
 
   public class LauncherApps {
     method public java.util.List<android.content.pm.LauncherActivityInfo> getActivityList(java.lang.String, android.os.UserHandle);
-    method public android.content.pm.ApplicationInfo getApplicationInfo(java.lang.String, int, android.os.UserHandle);
-    method public android.os.ParcelFileDescriptor getShortcutIconFd(android.content.pm.ShortcutInfo, android.os.UserHandle);
-    method public int getShortcutIconResId(android.content.pm.ShortcutInfo, android.os.UserHandle);
-    method public java.util.List<android.content.pm.ShortcutInfo> getShortcutInfo(java.lang.String, java.util.List<java.lang.String>, android.os.UserHandle);
+    method public android.os.ParcelFileDescriptor getShortcutIconFd(android.content.pm.ShortcutInfo);
+    method public android.os.ParcelFileDescriptor getShortcutIconFd(java.lang.String, java.lang.String, android.os.UserHandle);
     method public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(android.content.pm.LauncherApps.ShortcutQuery, android.os.UserHandle);
     method public boolean hasShortcutHostPermission();
     method public boolean isActivityEnabled(android.content.ComponentName, android.os.UserHandle);
@@ -9846,6 +9848,7 @@
     method public void startAppDetailsActivity(android.content.ComponentName, android.os.UserHandle, android.graphics.Rect, android.os.Bundle);
     method public void startMainActivity(android.content.ComponentName, android.os.UserHandle, android.graphics.Rect, android.os.Bundle);
     method public boolean startShortcut(java.lang.String, java.lang.String, android.graphics.Rect, android.os.Bundle, android.os.UserHandle);
+    method public boolean startShortcut(android.content.pm.ShortcutInfo, android.graphics.Rect, android.os.Bundle);
     method public void unregisterCallback(android.content.pm.LauncherApps.Callback);
   }
 
@@ -9867,6 +9870,7 @@
     method public void setChangedSince(long);
     method public void setPackage(java.lang.String);
     method public void setQueryFlags(int);
+    method public void setShortcutIds(java.util.List<java.lang.String>);
     field public static final int FLAG_GET_DYNAMIC = 1; // 0x1
     field public static final int FLAG_GET_KEY_FIELDS_ONLY = 4; // 0x4
     field public static final int FLAG_GET_PINNED = 2; // 0x2
@@ -10435,13 +10439,16 @@
   public final class ShortcutInfo implements android.os.Parcelable {
     method public int describeContents();
     method public android.content.ComponentName getActivityComponent();
+    method public java.util.List<java.lang.String> getCategories();
     method public android.os.PersistableBundle getExtras();
+    method public int getIconResourceId();
     method public java.lang.String getId();
     method public android.content.Intent getIntent();
     method public long getLastChangedTimestamp();
     method public java.lang.String getPackageName();
     method public java.lang.String getText();
     method public java.lang.String getTitle();
+    method public android.os.UserHandle getUserHandle();
     method public int getWeight();
     method public boolean hasIconFile();
     method public boolean hasIconResource();
@@ -10458,12 +10465,14 @@
     field public static final int FLAG_HAS_ICON_RES = 4; // 0x4
     field public static final int FLAG_KEY_FIELDS_ONLY = 16; // 0x10
     field public static final int FLAG_PINNED = 2; // 0x2
+    field public static final java.lang.String SHORTCUT_CATEGORY_CONVERSATION = "android.shortcut.conversation";
   }
 
   public static class ShortcutInfo.Builder {
     ctor public ShortcutInfo.Builder(android.content.Context);
     method public android.content.pm.ShortcutInfo build();
     method public android.content.pm.ShortcutInfo.Builder setActivityComponent(android.content.ComponentName);
+    method public android.content.pm.ShortcutInfo.Builder setCategories(java.util.List<java.lang.String>);
     method public android.content.pm.ShortcutInfo.Builder setExtras(android.os.PersistableBundle);
     method public android.content.pm.ShortcutInfo.Builder setIcon(android.graphics.drawable.Icon);
     method public android.content.pm.ShortcutInfo.Builder setId(java.lang.String);
@@ -10474,15 +10483,15 @@
   }
 
   public class ShortcutManager {
-    method public boolean addDynamicShortcut(android.content.pm.ShortcutInfo);
-    method public void deleteAllDynamicShortcuts();
-    method public void deleteDynamicShortcut(java.lang.String);
+    method public boolean addDynamicShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
     method public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts();
     method public int getIconMaxDimensions();
     method public int getMaxDynamicShortcutCount();
     method public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts();
     method public long getRateLimitResetTime();
     method public int getRemainingCallCount();
+    method public void removeAllDynamicShortcuts();
+    method public void removeDynamicShortcuts(java.util.List<java.lang.String>);
     method public boolean setDynamicShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
     method public boolean updateShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
   }
@@ -14330,11 +14339,11 @@
     method public abstract void close();
     method public abstract android.hardware.camera2.CaptureRequest.Builder createCaptureRequest(int) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
-    method public abstract void createCaptureSessionByOutputConfiguration(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
+    method public abstract void createCaptureSessionByOutputConfigurations(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createConstrainedHighSpeedCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract android.hardware.camera2.CaptureRequest.Builder createReprocessCaptureRequest(android.hardware.camera2.TotalCaptureResult) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createReprocessableCaptureSession(android.hardware.camera2.params.InputConfiguration, java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
-    method public abstract void createReprocessableCaptureSessionWithConfigurations(android.hardware.camera2.params.InputConfiguration, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
+    method public abstract void createReprocessableCaptureSessionByConfigurations(android.hardware.camera2.params.InputConfiguration, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract java.lang.String getId();
     field public static final int TEMPLATE_MANUAL = 6; // 0x6
     field public static final int TEMPLATE_PREVIEW = 1; // 0x1
@@ -15487,6 +15496,7 @@
 
   public class NanoApp {
     ctor public NanoApp();
+    ctor public NanoApp(int, byte[]);
     method public int describeContents();
     method public byte[] getAppBinary();
     method public int getAppId();
@@ -21327,8 +21337,8 @@
   public class AudioRecord implements android.media.AudioRouting {
     ctor public AudioRecord(int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioRecord(android.media.AudioAttributes, android.media.AudioFormat, int, int) throws java.lang.IllegalArgumentException;
+    method public void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public deprecated void addOnRoutingChangedListener(android.media.AudioRecord.OnRoutingChangedListener, android.os.Handler);
-    method public void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public int getAudioFormat();
     method public int getAudioSessionId();
     method public int getAudioSource();
@@ -21353,8 +21363,8 @@
     method public int read(java.nio.ByteBuffer, int);
     method public int read(java.nio.ByteBuffer, int, int);
     method public void release();
+    method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public deprecated void removeOnRoutingChangedListener(android.media.AudioRecord.OnRoutingChangedListener);
-    method public void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public int setNotificationMarkerPosition(int);
     method public int setPositionNotificationPeriod(int);
     method public boolean setPreferredDevice(android.media.AudioDeviceInfo);
@@ -21390,8 +21400,9 @@
     method public abstract void onPeriodicNotification(android.media.AudioRecord);
   }
 
-  public static abstract interface AudioRecord.OnRoutingChangedListener {
+  public static abstract deprecated interface AudioRecord.OnRoutingChangedListener implements android.media.AudioRouting.OnRoutingChangedListener {
     method public abstract void onRoutingChanged(android.media.AudioRecord);
+    method public default void onRoutingChanged(android.media.AudioRouting);
   }
 
   public final class AudioRecordingConfiguration implements android.os.Parcelable {
@@ -21406,10 +21417,10 @@
   }
 
   public abstract interface AudioRouting {
-    method public abstract void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
+    method public abstract void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public abstract android.media.AudioDeviceInfo getPreferredDevice();
     method public abstract android.media.AudioDeviceInfo getRoutedDevice();
-    method public abstract void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
+    method public abstract void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public abstract boolean setPreferredDevice(android.media.AudioDeviceInfo);
   }
 
@@ -21429,8 +21440,8 @@
     ctor public AudioTrack(int, int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioTrack(int, int, int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioTrack(android.media.AudioAttributes, android.media.AudioFormat, int, int, int) throws java.lang.IllegalArgumentException;
+    method public void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public deprecated void addOnRoutingChangedListener(android.media.AudioTrack.OnRoutingChangedListener, android.os.Handler);
-    method public void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public int attachAuxEffect(int);
     method public void flush();
     method public int getAudioFormat();
@@ -21462,8 +21473,8 @@
     method public void play() throws java.lang.IllegalStateException;
     method public void release();
     method public int reloadStaticData();
+    method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public deprecated void removeOnRoutingChangedListener(android.media.AudioTrack.OnRoutingChangedListener);
-    method public void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public int setAuxEffectSendLevel(float);
     method public int setBufferSizeInFrames(int);
     method public int setLoopPoints(int, int, int);
@@ -21517,8 +21528,9 @@
     method public abstract void onPeriodicNotification(android.media.AudioTrack);
   }
 
-  public static abstract deprecated interface AudioTrack.OnRoutingChangedListener {
-    method public abstract deprecated void onRoutingChanged(android.media.AudioTrack);
+  public static abstract deprecated interface AudioTrack.OnRoutingChangedListener implements android.media.AudioRouting.OnRoutingChangedListener {
+    method public abstract void onRoutingChanged(android.media.AudioTrack);
+    method public default void onRoutingChanged(android.media.AudioRouting);
   }
 
   public class CamcorderProfile {
@@ -22194,10 +22206,12 @@
     field public static final int VP9Level6 = 1024; // 0x400
     field public static final int VP9Level61 = 2048; // 0x800
     field public static final int VP9Level62 = 4096; // 0x1000
-    field public static final int VP9Profile0 = 0; // 0x0
-    field public static final int VP9Profile1 = 1; // 0x1
-    field public static final int VP9Profile2 = 2; // 0x2
-    field public static final int VP9Profile3 = 3; // 0x3
+    field public static final int VP9Profile0 = 1; // 0x1
+    field public static final int VP9Profile1 = 2; // 0x2
+    field public static final int VP9Profile2 = 4; // 0x4
+    field public static final int VP9Profile2HDR = 4096; // 0x1000
+    field public static final int VP9Profile3 = 8; // 0x8
+    field public static final int VP9Profile3HDR = 8192; // 0x2000
     field public int level;
     field public int profile;
   }
@@ -31877,6 +31891,7 @@
   public class StorageManager {
     method public java.lang.String getMountedObbPath(java.lang.String);
     method public android.os.storage.StorageVolume getPrimaryStorageVolume();
+    method public android.os.storage.StorageVolume getStorageVolume(java.io.File);
     method public java.util.List<android.os.storage.StorageVolume> getStorageVolumes();
     method public boolean isEncrypted(java.io.File);
     method public boolean isObbMounted(java.lang.String);
@@ -37117,6 +37132,22 @@
 
 package android.service.notification {
 
+  public final class Adjustment implements android.os.Parcelable {
+    ctor public Adjustment(java.lang.String, java.lang.String, int, android.os.Bundle, java.lang.CharSequence, android.net.Uri);
+    ctor protected Adjustment(android.os.Parcel);
+    method public int describeContents();
+    method public java.lang.CharSequence getExplanation();
+    method public int getImportance();
+    method public java.lang.String getKey();
+    method public java.lang.String getPackage();
+    method public android.net.Uri getReference();
+    method public android.os.Bundle getSignals();
+    method public void writeToParcel(android.os.Parcel, int);
+    field public static final android.os.Parcelable.Creator<android.service.notification.Adjustment> CREATOR;
+    field public static final java.lang.String GROUP_KEY_OVERRIDE_KEY = "group_key_override";
+    field public static final java.lang.String NEEDS_AUTOGROUPING_KEY = "autogroup_needed";
+  }
+
   public class Condition implements android.os.Parcelable {
     ctor public Condition(android.net.Uri, java.lang.String, int);
     ctor public Condition(android.net.Uri, java.lang.String, java.lang.String, java.lang.String, int, int, int);
@@ -37192,7 +37223,9 @@
     method public final void setNotificationsShown(java.lang.String[]);
     method public final void setOnNotificationPostedTrim(int);
     method public void unregisterAsSystemService() throws android.os.RemoteException;
+    field public static final int HINT_HOST_DISABLE_CALL_EFFECTS = 4; // 0x4
     field public static final int HINT_HOST_DISABLE_EFFECTS = 1; // 0x1
+    field public static final int HINT_HOST_DISABLE_NOTIFICATION_EFFECTS = 2; // 0x2
     field public static final int INTERRUPTION_FILTER_ALARMS = 4; // 0x4
     field public static final int INTERRUPTION_FILTER_ALL = 1; // 0x1
     field public static final int INTERRUPTION_FILTER_NONE = 3; // 0x3
@@ -37210,6 +37243,7 @@
     method public int getImportance();
     method public java.lang.CharSequence getImportanceExplanation();
     method public java.lang.String getKey();
+    method public java.lang.String getOverrideGroupKey();
     method public int getRank();
     method public int getSuppressedVisualEffects();
     method public boolean isAmbient();
@@ -37233,11 +37267,12 @@
 
   public abstract class NotificationRankerService extends android.service.notification.NotificationListenerService {
     ctor public NotificationRankerService();
-    method public final void adjustImportance(java.lang.String, android.service.notification.NotificationRankerService.Adjustment);
+    method public final void adjustNotification(android.service.notification.Adjustment);
+    method public final void adjustNotifications(java.util.List<android.service.notification.Adjustment>);
     method public final android.os.IBinder onBind(android.content.Intent);
     method public void onNotificationActionClick(java.lang.String, long, int);
     method public void onNotificationClick(java.lang.String, long);
-    method public abstract android.service.notification.NotificationRankerService.Adjustment onNotificationEnqueued(android.service.notification.StatusBarNotification, int, boolean);
+    method public abstract android.service.notification.Adjustment onNotificationEnqueued(android.service.notification.StatusBarNotification, int, boolean);
     method public void onNotificationRemoved(java.lang.String, long, int);
     method public void onNotificationVisibilityChanged(java.lang.String, long, boolean);
     field public static final int REASON_APP_CANCEL = 8; // 0x8
@@ -37254,14 +37289,11 @@
     field public static final int REASON_PACKAGE_CHANGED = 5; // 0x5
     field public static final int REASON_PACKAGE_SUSPENDED = 14; // 0xe
     field public static final int REASON_PROFILE_TURNED_OFF = 15; // 0xf
+    field public static final int REASON_UNAUTOBUNDLED = 16; // 0x10
     field public static final int REASON_USER_STOPPED = 6; // 0x6
     field public static final java.lang.String SERVICE_INTERFACE = "android.service.notification.NotificationRankerService";
   }
 
-  public class NotificationRankerService.Adjustment {
-    ctor public NotificationRankerService.Adjustment(int, java.lang.CharSequence, android.net.Uri);
-  }
-
   public class StatusBarNotification implements android.os.Parcelable {
     ctor public StatusBarNotification(java.lang.String, java.lang.String, int, java.lang.String, int, int, int, android.app.Notification, android.os.UserHandle, long);
     ctor public StatusBarNotification(android.os.Parcel);
@@ -37271,13 +37303,16 @@
     method public int getId();
     method public java.lang.String getKey();
     method public android.app.Notification getNotification();
+    method public java.lang.String getOverrideGroupKey();
     method public java.lang.String getPackageName();
     method public long getPostTime();
     method public java.lang.String getTag();
     method public android.os.UserHandle getUser();
     method public deprecated int getUserId();
     method public boolean isClearable();
+    method public boolean isGroup();
     method public boolean isOngoing();
+    method public void setOverrideGroupKey(java.lang.String);
     method public void writeToParcel(android.os.Parcel, int);
     field public static final android.os.Parcelable.Creator<android.service.notification.StatusBarNotification> CREATOR;
   }
@@ -37346,7 +37381,7 @@
     method public void onClick();
     method public void onStartListening();
     method public void onStopListening();
-    method public int onTileAdded();
+    method public void onTileAdded();
     method public void onTileRemoved();
     method public static final void requestListeningState(android.content.Context, android.content.ComponentName);
     method public final void setStatusIcon(android.graphics.drawable.Icon, java.lang.String);
@@ -37355,8 +37390,7 @@
     method public final void unlockAndRun(java.lang.Runnable);
     field public static final java.lang.String ACTION_QS_TILE = "android.service.quicksettings.action.QS_TILE";
     field public static final java.lang.String ACTION_QS_TILE_PREFERENCES = "android.service.quicksettings.action.QS_TILE_PREFERENCES";
-    field public static final int TILE_MODE_ACTIVE = 2; // 0x2
-    field public static final int TILE_MODE_PASSIVE = 1; // 0x1
+    field public static final java.lang.String META_DATA_ACTIVE_TILE = "android.service.quicksettings.ACTIVE_TILE";
   }
 
 }
@@ -52142,6 +52176,7 @@
     ctor public BufferedReader(java.io.Reader, int);
     ctor public BufferedReader(java.io.Reader);
     method public void close() throws java.io.IOException;
+    method public java.util.stream.Stream<java.lang.String> lines();
     method public int read(char[], int, int) throws java.io.IOException;
     method public java.lang.String readLine() throws java.io.IOException;
   }
@@ -53012,6 +53047,11 @@
     ctor public UTFDataFormatException(java.lang.String);
   }
 
+  public class UncheckedIOException extends java.lang.RuntimeException {
+    ctor public UncheckedIOException(java.lang.String, java.io.IOException);
+    ctor public UncheckedIOException(java.io.IOException);
+  }
+
   public class UnsupportedEncodingException extends java.io.IOException {
     ctor public UnsupportedEncodingException();
     ctor public UnsupportedEncodingException(java.lang.String);
@@ -55074,7 +55114,6 @@
   public final class Method extends java.lang.reflect.AccessibleObject implements java.lang.reflect.GenericDeclaration java.lang.reflect.Member {
     method public boolean equals(java.lang.Object);
     method public A getAnnotation(java.lang.Class<A>);
-    method public java.lang.annotation.Annotation[] getDeclaredAnnotations();
     method public java.lang.Class<?> getDeclaringClass();
     method public java.lang.Object getDefaultValue();
     method public java.lang.Class<?>[] getExceptionTypes();
@@ -55088,7 +55127,6 @@
     method public java.lang.Class<?> getReturnType();
     method public java.lang.reflect.TypeVariable<java.lang.reflect.Method>[] getTypeParameters();
     method public java.lang.Object invoke(java.lang.Object, java.lang.Object...) throws java.lang.IllegalAccessException, java.lang.IllegalArgumentException, java.lang.reflect.InvocationTargetException;
-    method public boolean isAnnotationPresent(java.lang.Class<? extends java.lang.annotation.Annotation>);
     method public boolean isBridge();
     method public boolean isDefault();
     method public boolean isSynthetic();
@@ -60670,6 +60708,7 @@
     method public void set(int, int);
     method public void set(int, int, boolean);
     method public int size();
+    method public java.util.stream.IntStream stream();
     method public byte[] toByteArray();
     method public long[] toLongArray();
     method public static java.util.BitSet valueOf(long[]);
@@ -61125,6 +61164,7 @@
     method public java.util.Set<java.util.Map.Entry<K, V>> entrySet();
     method public void forEach(java.util.function.BiConsumer<? super K, ? super V>);
     method public boolean replace(K, V, V);
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
   }
 
   public class HashSet extends java.util.AbstractSet implements java.lang.Cloneable java.io.Serializable java.util.Set {
@@ -61168,6 +61208,7 @@
     method public synchronized boolean remove(java.lang.Object, java.lang.Object);
     method public synchronized boolean replace(K, V, V);
     method public synchronized V replace(K, V);
+    method public synchronized void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
     method public synchronized int size();
     method public java.util.Collection<V> values();
   }
@@ -61708,6 +61749,18 @@
   public class Random implements java.io.Serializable {
     ctor public Random();
     ctor public Random(long);
+    method public java.util.stream.DoubleStream doubles(long);
+    method public java.util.stream.DoubleStream doubles();
+    method public java.util.stream.DoubleStream doubles(long, double, double);
+    method public java.util.stream.DoubleStream doubles(double, double);
+    method public java.util.stream.IntStream ints(long);
+    method public java.util.stream.IntStream ints();
+    method public java.util.stream.IntStream ints(long, int, int);
+    method public java.util.stream.IntStream ints(int, int);
+    method public java.util.stream.LongStream longs(long);
+    method public java.util.stream.LongStream longs();
+    method public java.util.stream.LongStream longs(long, long, long);
+    method public java.util.stream.LongStream longs(long, long);
     method protected int next(int);
     method public boolean nextBoolean();
     method public void nextBytes(byte[]);
@@ -62149,6 +62202,7 @@
     method public java.util.NavigableSet<K> navigableKeySet();
     method public java.util.Map.Entry<K, V> pollFirstEntry();
     method public java.util.Map.Entry<K, V> pollLastEntry();
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
     method public java.util.NavigableMap<K, V> subMap(K, boolean, K, boolean);
     method public java.util.SortedMap<K, V> subMap(K, K);
     method public java.util.NavigableMap<K, V> tailMap(K, boolean);
@@ -62250,6 +62304,7 @@
     ctor public WeakHashMap(java.util.Map<? extends K, ? extends V>);
     method public java.util.Set<java.util.Map.Entry<K, V>> entrySet();
     method public void forEach(java.util.function.BiConsumer<? super K, ? super V>);
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
   }
 
 }
@@ -63223,18 +63278,6 @@
 
   public class ThreadLocalRandom extends java.util.Random {
     method public static java.util.concurrent.ThreadLocalRandom current();
-    method public java.util.stream.DoubleStream doubles(long);
-    method public java.util.stream.DoubleStream doubles();
-    method public java.util.stream.DoubleStream doubles(long, double, double);
-    method public java.util.stream.DoubleStream doubles(double, double);
-    method public java.util.stream.IntStream ints(long);
-    method public java.util.stream.IntStream ints();
-    method public java.util.stream.IntStream ints(long, int, int);
-    method public java.util.stream.IntStream ints(int, int);
-    method public java.util.stream.LongStream longs(long);
-    method public java.util.stream.LongStream longs();
-    method public java.util.stream.LongStream longs(long, long, long);
-    method public java.util.stream.LongStream longs(long, long);
     method public double nextDouble(double);
     method public double nextDouble(double, double);
     method public int nextInt(int, int);
@@ -64607,6 +64650,7 @@
   }
 
   public final class Pattern implements java.io.Serializable {
+    method public java.util.function.Predicate<java.lang.String> asPredicate();
     method public static java.util.regex.Pattern compile(java.lang.String);
     method public static java.util.regex.Pattern compile(java.lang.String, int) throws java.util.regex.PatternSyntaxException;
     method public int flags();
@@ -64616,6 +64660,7 @@
     method public static java.lang.String quote(java.lang.String);
     method public java.lang.String[] split(java.lang.CharSequence, int);
     method public java.lang.String[] split(java.lang.CharSequence);
+    method public java.util.stream.Stream<java.lang.String> splitAsStream(java.lang.CharSequence);
     field public static final int CANON_EQ = 128; // 0x80
     field public static final int CASE_INSENSITIVE = 2; // 0x2
     field public static final int COMMENTS = 4; // 0x4
diff --git a/api/test-current.txt b/api/test-current.txt
index 3febda1..fd34f10 100644
--- a/api/test-current.txt
+++ b/api/test-current.txt
@@ -3578,6 +3578,7 @@
     method public final deprecated void removeDialog(int);
     method public void reportFullyDrawn();
     method public android.view.DropPermissions requestDropPermissions(android.view.DragEvent);
+    method public final void requestKeyboardShortcutsHelper();
     method public final void requestPermissions(java.lang.String[], int);
     method public boolean requestVisibleBehind(boolean);
     method public final boolean requestWindowFeature(int);
@@ -5030,13 +5031,13 @@
     method public android.app.Notification.Action.Builder extend(android.app.Notification.Action.Builder);
     method public java.lang.CharSequence getCancelLabel();
     method public java.lang.CharSequence getConfirmLabel();
-    method public boolean getHintContentIntentLaunchesActivity();
+    method public boolean getHintLaunchesActivity();
     method public java.lang.CharSequence getInProgressLabel();
     method public boolean isAvailableOffline();
     method public android.app.Notification.Action.WearableExtender setAvailableOffline(boolean);
     method public android.app.Notification.Action.WearableExtender setCancelLabel(java.lang.CharSequence);
     method public android.app.Notification.Action.WearableExtender setConfirmLabel(java.lang.CharSequence);
-    method public android.app.Notification.Action.WearableExtender setHintContentIntentLaunchesActivity(boolean);
+    method public android.app.Notification.Action.WearableExtender setHintLaunchesActivity(boolean);
     method public android.app.Notification.Action.WearableExtender setInProgressLabel(java.lang.CharSequence);
   }
 
@@ -8692,6 +8693,7 @@
     field public static final java.lang.String EXTRA_CHANGED_PACKAGE_LIST = "android.intent.extra.changed_package_list";
     field public static final java.lang.String EXTRA_CHANGED_UID_LIST = "android.intent.extra.changed_uid_list";
     field public static final java.lang.String EXTRA_CHOOSER_REFINEMENT_INTENT_SENDER = "android.intent.extra.CHOOSER_REFINEMENT_INTENT_SENDER";
+    field public static final java.lang.String EXTRA_CHOOSER_TARGETS = "android.intent.extra.CHOOSER_TARGETS";
     field public static final java.lang.String EXTRA_CHOSEN_COMPONENT = "android.intent.extra.CHOSEN_COMPONENT";
     field public static final java.lang.String EXTRA_CHOSEN_COMPONENT_INTENT_SENDER = "android.intent.extra.CHOSEN_COMPONENT_INTENT_SENDER";
     field public static final java.lang.String EXTRA_DATA_REMOVED = "android.intent.extra.DATA_REMOVED";
@@ -8703,6 +8705,7 @@
     field public static final int EXTRA_DOCK_STATE_UNDOCKED = 0; // 0x0
     field public static final java.lang.String EXTRA_DONT_KILL_APP = "android.intent.extra.DONT_KILL_APP";
     field public static final java.lang.String EXTRA_EMAIL = "android.intent.extra.EMAIL";
+    field public static final java.lang.String EXTRA_EXCLUDE_COMPONENTS = "android.intent.extra.EXCLUDE_COMPONENTS";
     field public static final java.lang.String EXTRA_HTML_TEXT = "android.intent.extra.HTML_TEXT";
     field public static final java.lang.String EXTRA_INDEX = "android.intent.extra.INDEX";
     field public static final java.lang.String EXTRA_INITIAL_INTENTS = "android.intent.extra.INITIAL_INTENTS";
@@ -9502,11 +9505,10 @@
   }
 
   public class LauncherApps {
+    ctor public LauncherApps(android.content.Context);
     method public java.util.List<android.content.pm.LauncherActivityInfo> getActivityList(java.lang.String, android.os.UserHandle);
-    method public android.content.pm.ApplicationInfo getApplicationInfo(java.lang.String, int, android.os.UserHandle);
-    method public android.os.ParcelFileDescriptor getShortcutIconFd(android.content.pm.ShortcutInfo, android.os.UserHandle);
-    method public int getShortcutIconResId(android.content.pm.ShortcutInfo, android.os.UserHandle);
-    method public java.util.List<android.content.pm.ShortcutInfo> getShortcutInfo(java.lang.String, java.util.List<java.lang.String>, android.os.UserHandle);
+    method public android.os.ParcelFileDescriptor getShortcutIconFd(android.content.pm.ShortcutInfo);
+    method public android.os.ParcelFileDescriptor getShortcutIconFd(java.lang.String, java.lang.String, android.os.UserHandle);
     method public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(android.content.pm.LauncherApps.ShortcutQuery, android.os.UserHandle);
     method public boolean hasShortcutHostPermission();
     method public boolean isActivityEnabled(android.content.ComponentName, android.os.UserHandle);
@@ -9518,6 +9520,7 @@
     method public void startAppDetailsActivity(android.content.ComponentName, android.os.UserHandle, android.graphics.Rect, android.os.Bundle);
     method public void startMainActivity(android.content.ComponentName, android.os.UserHandle, android.graphics.Rect, android.os.Bundle);
     method public boolean startShortcut(java.lang.String, java.lang.String, android.graphics.Rect, android.os.Bundle, android.os.UserHandle);
+    method public boolean startShortcut(android.content.pm.ShortcutInfo, android.graphics.Rect, android.os.Bundle);
     method public void unregisterCallback(android.content.pm.LauncherApps.Callback);
   }
 
@@ -9539,6 +9542,7 @@
     method public void setChangedSince(long);
     method public void setPackage(java.lang.String);
     method public void setQueryFlags(int);
+    method public void setShortcutIds(java.util.List<java.lang.String>);
     field public static final int FLAG_GET_DYNAMIC = 1; // 0x1
     field public static final int FLAG_GET_KEY_FIELDS_ONLY = 4; // 0x4
     field public static final int FLAG_GET_PINNED = 2; // 0x2
@@ -10046,13 +10050,16 @@
   public final class ShortcutInfo implements android.os.Parcelable {
     method public int describeContents();
     method public android.content.ComponentName getActivityComponent();
+    method public java.util.List<java.lang.String> getCategories();
     method public android.os.PersistableBundle getExtras();
+    method public int getIconResourceId();
     method public java.lang.String getId();
     method public android.content.Intent getIntent();
     method public long getLastChangedTimestamp();
     method public java.lang.String getPackageName();
     method public java.lang.String getText();
     method public java.lang.String getTitle();
+    method public android.os.UserHandle getUserHandle();
     method public int getWeight();
     method public boolean hasIconFile();
     method public boolean hasIconResource();
@@ -10069,12 +10076,14 @@
     field public static final int FLAG_HAS_ICON_RES = 4; // 0x4
     field public static final int FLAG_KEY_FIELDS_ONLY = 16; // 0x10
     field public static final int FLAG_PINNED = 2; // 0x2
+    field public static final java.lang.String SHORTCUT_CATEGORY_CONVERSATION = "android.shortcut.conversation";
   }
 
   public static class ShortcutInfo.Builder {
     ctor public ShortcutInfo.Builder(android.content.Context);
     method public android.content.pm.ShortcutInfo build();
     method public android.content.pm.ShortcutInfo.Builder setActivityComponent(android.content.ComponentName);
+    method public android.content.pm.ShortcutInfo.Builder setCategories(java.util.List<java.lang.String>);
     method public android.content.pm.ShortcutInfo.Builder setExtras(android.os.PersistableBundle);
     method public android.content.pm.ShortcutInfo.Builder setIcon(android.graphics.drawable.Icon);
     method public android.content.pm.ShortcutInfo.Builder setId(java.lang.String);
@@ -10085,15 +10094,16 @@
   }
 
   public class ShortcutManager {
-    method public boolean addDynamicShortcut(android.content.pm.ShortcutInfo);
-    method public void deleteAllDynamicShortcuts();
-    method public void deleteDynamicShortcut(java.lang.String);
+    ctor public ShortcutManager(android.content.Context);
+    method public boolean addDynamicShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
     method public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts();
     method public int getIconMaxDimensions();
     method public int getMaxDynamicShortcutCount();
     method public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts();
     method public long getRateLimitResetTime();
     method public int getRemainingCallCount();
+    method public void removeAllDynamicShortcuts();
+    method public void removeDynamicShortcuts(java.util.List<java.lang.String>);
     method public boolean setDynamicShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
     method public boolean updateShortcuts(java.util.List<android.content.pm.ShortcutInfo>);
   }
@@ -13933,11 +13943,11 @@
     method public abstract void close();
     method public abstract android.hardware.camera2.CaptureRequest.Builder createCaptureRequest(int) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
-    method public abstract void createCaptureSessionByOutputConfiguration(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
+    method public abstract void createCaptureSessionByOutputConfigurations(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createConstrainedHighSpeedCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract android.hardware.camera2.CaptureRequest.Builder createReprocessCaptureRequest(android.hardware.camera2.TotalCaptureResult) throws android.hardware.camera2.CameraAccessException;
     method public abstract void createReprocessableCaptureSession(android.hardware.camera2.params.InputConfiguration, java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
-    method public abstract void createReprocessableCaptureSessionWithConfigurations(android.hardware.camera2.params.InputConfiguration, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
+    method public abstract void createReprocessableCaptureSessionByConfigurations(android.hardware.camera2.params.InputConfiguration, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException;
     method public abstract java.lang.String getId();
     field public static final int TEMPLATE_MANUAL = 6; // 0x6
     field public static final int TEMPLATE_PREVIEW = 1; // 0x1
@@ -19916,8 +19926,8 @@
 
   public class AudioRecord implements android.media.AudioRouting {
     ctor public AudioRecord(int, int, int, int, int) throws java.lang.IllegalArgumentException;
+    method public void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public deprecated void addOnRoutingChangedListener(android.media.AudioRecord.OnRoutingChangedListener, android.os.Handler);
-    method public void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public int getAudioFormat();
     method public int getAudioSessionId();
     method public int getAudioSource();
@@ -19942,8 +19952,8 @@
     method public int read(java.nio.ByteBuffer, int);
     method public int read(java.nio.ByteBuffer, int, int);
     method public void release();
+    method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public deprecated void removeOnRoutingChangedListener(android.media.AudioRecord.OnRoutingChangedListener);
-    method public void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public int setNotificationMarkerPosition(int);
     method public int setPositionNotificationPeriod(int);
     method public boolean setPreferredDevice(android.media.AudioDeviceInfo);
@@ -19977,8 +19987,9 @@
     method public abstract void onPeriodicNotification(android.media.AudioRecord);
   }
 
-  public static abstract interface AudioRecord.OnRoutingChangedListener {
+  public static abstract deprecated interface AudioRecord.OnRoutingChangedListener implements android.media.AudioRouting.OnRoutingChangedListener {
     method public abstract void onRoutingChanged(android.media.AudioRecord);
+    method public default void onRoutingChanged(android.media.AudioRouting);
   }
 
   public final class AudioRecordingConfiguration implements android.os.Parcelable {
@@ -19993,10 +20004,10 @@
   }
 
   public abstract interface AudioRouting {
-    method public abstract void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
+    method public abstract void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public abstract android.media.AudioDeviceInfo getPreferredDevice();
     method public abstract android.media.AudioDeviceInfo getRoutedDevice();
-    method public abstract void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
+    method public abstract void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public abstract boolean setPreferredDevice(android.media.AudioDeviceInfo);
   }
 
@@ -20016,8 +20027,8 @@
     ctor public AudioTrack(int, int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioTrack(int, int, int, int, int, int, int) throws java.lang.IllegalArgumentException;
     ctor public AudioTrack(android.media.AudioAttributes, android.media.AudioFormat, int, int, int) throws java.lang.IllegalArgumentException;
+    method public void addOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public deprecated void addOnRoutingChangedListener(android.media.AudioTrack.OnRoutingChangedListener, android.os.Handler);
-    method public void addOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener, android.os.Handler);
     method public int attachAuxEffect(int);
     method public void flush();
     method public int getAudioFormat();
@@ -20049,8 +20060,8 @@
     method public void play() throws java.lang.IllegalStateException;
     method public void release();
     method public int reloadStaticData();
+    method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public deprecated void removeOnRoutingChangedListener(android.media.AudioTrack.OnRoutingChangedListener);
-    method public void removeOnRoutingListener(android.media.AudioRouting.OnRoutingChangedListener);
     method public int setAuxEffectSendLevel(float);
     method public int setBufferSizeInFrames(int);
     method public int setLoopPoints(int, int, int);
@@ -20104,8 +20115,9 @@
     method public abstract void onPeriodicNotification(android.media.AudioTrack);
   }
 
-  public static abstract deprecated interface AudioTrack.OnRoutingChangedListener {
-    method public abstract deprecated void onRoutingChanged(android.media.AudioTrack);
+  public static abstract deprecated interface AudioTrack.OnRoutingChangedListener implements android.media.AudioRouting.OnRoutingChangedListener {
+    method public abstract void onRoutingChanged(android.media.AudioTrack);
+    method public default void onRoutingChanged(android.media.AudioRouting);
   }
 
   public class CamcorderProfile {
@@ -20781,10 +20793,12 @@
     field public static final int VP9Level6 = 1024; // 0x400
     field public static final int VP9Level61 = 2048; // 0x800
     field public static final int VP9Level62 = 4096; // 0x1000
-    field public static final int VP9Profile0 = 0; // 0x0
-    field public static final int VP9Profile1 = 1; // 0x1
-    field public static final int VP9Profile2 = 2; // 0x2
-    field public static final int VP9Profile3 = 3; // 0x3
+    field public static final int VP9Profile0 = 1; // 0x1
+    field public static final int VP9Profile1 = 2; // 0x2
+    field public static final int VP9Profile2 = 4; // 0x4
+    field public static final int VP9Profile2HDR = 4096; // 0x1000
+    field public static final int VP9Profile3 = 8; // 0x8
+    field public static final int VP9Profile3HDR = 8192; // 0x2000
     field public int level;
     field public int profile;
   }
@@ -29640,6 +29654,7 @@
   public class StorageManager {
     method public java.lang.String getMountedObbPath(java.lang.String);
     method public android.os.storage.StorageVolume getPrimaryStorageVolume();
+    method public android.os.storage.StorageVolume getStorageVolume(java.io.File);
     method public java.util.List<android.os.storage.StorageVolume> getStorageVolumes();
     method public boolean isEncrypted(java.io.File);
     method public boolean isObbMounted(java.lang.String);
@@ -34796,7 +34811,9 @@
     method public static void requestRebind(android.content.ComponentName) throws android.os.RemoteException;
     method public final void requestUnbind() throws android.os.RemoteException;
     method public final void setNotificationsShown(java.lang.String[]);
+    field public static final int HINT_HOST_DISABLE_CALL_EFFECTS = 4; // 0x4
     field public static final int HINT_HOST_DISABLE_EFFECTS = 1; // 0x1
+    field public static final int HINT_HOST_DISABLE_NOTIFICATION_EFFECTS = 2; // 0x2
     field public static final int INTERRUPTION_FILTER_ALARMS = 4; // 0x4
     field public static final int INTERRUPTION_FILTER_ALL = 1; // 0x1
     field public static final int INTERRUPTION_FILTER_NONE = 3; // 0x3
@@ -34812,6 +34829,7 @@
     method public int getImportance();
     method public java.lang.CharSequence getImportanceExplanation();
     method public java.lang.String getKey();
+    method public java.lang.String getOverrideGroupKey();
     method public int getRank();
     method public int getSuppressedVisualEffects();
     method public boolean isAmbient();
@@ -34842,13 +34860,16 @@
     method public int getId();
     method public java.lang.String getKey();
     method public android.app.Notification getNotification();
+    method public java.lang.String getOverrideGroupKey();
     method public java.lang.String getPackageName();
     method public long getPostTime();
     method public java.lang.String getTag();
     method public android.os.UserHandle getUser();
     method public deprecated int getUserId();
     method public boolean isClearable();
+    method public boolean isGroup();
     method public boolean isOngoing();
+    method public void setOverrideGroupKey(java.lang.String);
     method public void writeToParcel(android.os.Parcel, int);
     field public static final android.os.Parcelable.Creator<android.service.notification.StatusBarNotification> CREATOR;
   }
@@ -34884,7 +34905,7 @@
     method public void onClick();
     method public void onStartListening();
     method public void onStopListening();
-    method public int onTileAdded();
+    method public void onTileAdded();
     method public void onTileRemoved();
     method public static final void requestListeningState(android.content.Context, android.content.ComponentName);
     method public final void showDialog(android.app.Dialog);
@@ -34892,8 +34913,7 @@
     method public final void unlockAndRun(java.lang.Runnable);
     field public static final java.lang.String ACTION_QS_TILE = "android.service.quicksettings.action.QS_TILE";
     field public static final java.lang.String ACTION_QS_TILE_PREFERENCES = "android.service.quicksettings.action.QS_TILE_PREFERENCES";
-    field public static final int TILE_MODE_ACTIVE = 2; // 0x2
-    field public static final int TILE_MODE_PASSIVE = 1; // 0x1
+    field public static final java.lang.String META_DATA_ACTIVE_TILE = "android.service.quicksettings.ACTIVE_TILE";
   }
 
 }
@@ -49121,6 +49141,7 @@
     ctor public BufferedReader(java.io.Reader, int);
     ctor public BufferedReader(java.io.Reader);
     method public void close() throws java.io.IOException;
+    method public java.util.stream.Stream<java.lang.String> lines();
     method public int read(char[], int, int) throws java.io.IOException;
     method public java.lang.String readLine() throws java.io.IOException;
   }
@@ -49991,6 +50012,11 @@
     ctor public UTFDataFormatException(java.lang.String);
   }
 
+  public class UncheckedIOException extends java.lang.RuntimeException {
+    ctor public UncheckedIOException(java.lang.String, java.io.IOException);
+    ctor public UncheckedIOException(java.io.IOException);
+  }
+
   public class UnsupportedEncodingException extends java.io.IOException {
     ctor public UnsupportedEncodingException();
     ctor public UnsupportedEncodingException(java.lang.String);
@@ -52053,7 +52079,6 @@
   public final class Method extends java.lang.reflect.AccessibleObject implements java.lang.reflect.GenericDeclaration java.lang.reflect.Member {
     method public boolean equals(java.lang.Object);
     method public A getAnnotation(java.lang.Class<A>);
-    method public java.lang.annotation.Annotation[] getDeclaredAnnotations();
     method public java.lang.Class<?> getDeclaringClass();
     method public java.lang.Object getDefaultValue();
     method public java.lang.Class<?>[] getExceptionTypes();
@@ -52067,7 +52092,6 @@
     method public java.lang.Class<?> getReturnType();
     method public java.lang.reflect.TypeVariable<java.lang.reflect.Method>[] getTypeParameters();
     method public java.lang.Object invoke(java.lang.Object, java.lang.Object...) throws java.lang.IllegalAccessException, java.lang.IllegalArgumentException, java.lang.reflect.InvocationTargetException;
-    method public boolean isAnnotationPresent(java.lang.Class<? extends java.lang.annotation.Annotation>);
     method public boolean isBridge();
     method public boolean isDefault();
     method public boolean isSynthetic();
@@ -57649,6 +57673,7 @@
     method public void set(int, int);
     method public void set(int, int, boolean);
     method public int size();
+    method public java.util.stream.IntStream stream();
     method public byte[] toByteArray();
     method public long[] toLongArray();
     method public static java.util.BitSet valueOf(long[]);
@@ -58104,6 +58129,7 @@
     method public java.util.Set<java.util.Map.Entry<K, V>> entrySet();
     method public void forEach(java.util.function.BiConsumer<? super K, ? super V>);
     method public boolean replace(K, V, V);
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
   }
 
   public class HashSet extends java.util.AbstractSet implements java.lang.Cloneable java.io.Serializable java.util.Set {
@@ -58147,6 +58173,7 @@
     method public synchronized boolean remove(java.lang.Object, java.lang.Object);
     method public synchronized boolean replace(K, V, V);
     method public synchronized V replace(K, V);
+    method public synchronized void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
     method public synchronized int size();
     method public java.util.Collection<V> values();
   }
@@ -58687,6 +58714,18 @@
   public class Random implements java.io.Serializable {
     ctor public Random();
     ctor public Random(long);
+    method public java.util.stream.DoubleStream doubles(long);
+    method public java.util.stream.DoubleStream doubles();
+    method public java.util.stream.DoubleStream doubles(long, double, double);
+    method public java.util.stream.DoubleStream doubles(double, double);
+    method public java.util.stream.IntStream ints(long);
+    method public java.util.stream.IntStream ints();
+    method public java.util.stream.IntStream ints(long, int, int);
+    method public java.util.stream.IntStream ints(int, int);
+    method public java.util.stream.LongStream longs(long);
+    method public java.util.stream.LongStream longs();
+    method public java.util.stream.LongStream longs(long, long, long);
+    method public java.util.stream.LongStream longs(long, long);
     method protected int next(int);
     method public boolean nextBoolean();
     method public void nextBytes(byte[]);
@@ -59128,6 +59167,7 @@
     method public java.util.NavigableSet<K> navigableKeySet();
     method public java.util.Map.Entry<K, V> pollFirstEntry();
     method public java.util.Map.Entry<K, V> pollLastEntry();
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
     method public java.util.NavigableMap<K, V> subMap(K, boolean, K, boolean);
     method public java.util.SortedMap<K, V> subMap(K, K);
     method public java.util.NavigableMap<K, V> tailMap(K, boolean);
@@ -59229,6 +59269,7 @@
     ctor public WeakHashMap(java.util.Map<? extends K, ? extends V>);
     method public java.util.Set<java.util.Map.Entry<K, V>> entrySet();
     method public void forEach(java.util.function.BiConsumer<? super K, ? super V>);
+    method public void replaceAll(java.util.function.BiFunction<? super K, ? super V, ? extends V>);
   }
 
 }
@@ -60202,18 +60243,6 @@
 
   public class ThreadLocalRandom extends java.util.Random {
     method public static java.util.concurrent.ThreadLocalRandom current();
-    method public java.util.stream.DoubleStream doubles(long);
-    method public java.util.stream.DoubleStream doubles();
-    method public java.util.stream.DoubleStream doubles(long, double, double);
-    method public java.util.stream.DoubleStream doubles(double, double);
-    method public java.util.stream.IntStream ints(long);
-    method public java.util.stream.IntStream ints();
-    method public java.util.stream.IntStream ints(long, int, int);
-    method public java.util.stream.IntStream ints(int, int);
-    method public java.util.stream.LongStream longs(long);
-    method public java.util.stream.LongStream longs();
-    method public java.util.stream.LongStream longs(long, long, long);
-    method public java.util.stream.LongStream longs(long, long);
     method public double nextDouble(double);
     method public double nextDouble(double, double);
     method public int nextInt(int, int);
@@ -61586,6 +61615,7 @@
   }
 
   public final class Pattern implements java.io.Serializable {
+    method public java.util.function.Predicate<java.lang.String> asPredicate();
     method public static java.util.regex.Pattern compile(java.lang.String);
     method public static java.util.regex.Pattern compile(java.lang.String, int) throws java.util.regex.PatternSyntaxException;
     method public int flags();
@@ -61595,6 +61625,7 @@
     method public static java.lang.String quote(java.lang.String);
     method public java.lang.String[] split(java.lang.CharSequence, int);
     method public java.lang.String[] split(java.lang.CharSequence);
+    method public java.util.stream.Stream<java.lang.String> splitAsStream(java.lang.CharSequence);
     field public static final int CANON_EQ = 128; // 0x80
     field public static final int CASE_INSENSITIVE = 2; // 0x2
     field public static final int COMMENTS = 4; // 0x4
diff --git a/core/java/android/app/Activity.java b/core/java/android/app/Activity.java
index 0410a6e..7652766 100644
--- a/core/java/android/app/Activity.java
+++ b/core/java/android/app/Activity.java
@@ -1343,20 +1343,21 @@
      * {@link #getVoiceInteractor()}.
      */
     public void onLocalVoiceInteractionStarted() {
-        Log.i(TAG, "onLocalVoiceInteractionStarted! " + getVoiceInteractor());
     }
 
     /**
-     * Callback to indicate that the local voice interaction has stopped for some
-     * reason.
+     * Callback to indicate that the local voice interaction has stopped either
+     * because it was requested through a call to {@link #stopLocalVoiceInteraction()}
+     * or because it was canceled by the user. The previously acquired {@link VoiceInteractor}
+     * is no longer valid after this.
      */
     public void onLocalVoiceInteractionStopped() {
-        Log.i(TAG, "onLocalVoiceInteractionStopped :( " + getVoiceInteractor());
     }
 
     /**
      * Request to terminate the current voice interaction that was previously started
-     * using {@link #startLocalVoiceInteraction(Bundle)}.
+     * using {@link #startLocalVoiceInteraction(Bundle)}. When the interaction is
+     * terminated, {@link #onLocalVoiceInteractionStopped()} will be called.
      */
     public void stopLocalVoiceInteraction() {
         try {
@@ -1675,6 +1676,17 @@
     public void onProvideAssistContent(AssistContent outContent) {
     }
 
+    /**
+     * Request the Keyboard Shortcuts screen to show up. If it succeeds, this will trigger
+     * {@link #onProvideKeyboardShortcuts} to retrieve the shortcuts for the foreground activity.
+     */
+    public final void requestKeyboardShortcutsHelper() {
+        Intent intent = new Intent(Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS);
+        intent.setComponent(new ComponentName("com.android.systemui",
+                "com.android.systemui.statusbar.KeyboardShortcutsReceiver"));
+        sendBroadcast(intent);
+    }
+
     @Override
     public void onProvideKeyboardShortcuts(
             List<KeyboardShortcutGroup> data, Menu menu, int deviceId) {
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index 96e1eaa..36e962e 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -4727,8 +4727,16 @@
         if (callbacks != null) {
             final int N = callbacks.size();
             for (int i=0; i<N; i++) {
-                performConfigurationChanged(callbacks.get(i), null, config, null,
-                        REPORT_TO_ACTIVITY);
+                ComponentCallbacks2 cb = callbacks.get(i);
+                if (cb instanceof Activity) {
+                    // If callback is an Activity - call corresponding method to consider override
+                    // config and avoid onConfigurationChanged if it hasn't changed.
+                    Activity a = (Activity) cb;
+                    performConfigurationChangedForActivity(mActivities.get(a.getActivityToken()),
+                            config, REPORT_TO_ACTIVITY);
+                } else {
+                    performConfigurationChanged(cb, null, config, null, REPORT_TO_ACTIVITY);
+                }
             }
         }
     }
diff --git a/core/java/android/app/INotificationManager.aidl b/core/java/android/app/INotificationManager.aidl
index 7a69c62..ee80ec3 100644
--- a/core/java/android/app/INotificationManager.aidl
+++ b/core/java/android/app/INotificationManager.aidl
@@ -25,6 +25,7 @@
 import android.content.pm.ParceledListSlice;
 import android.net.Uri;
 import android.os.Bundle;
+import android.service.notification.Adjustment;
 import android.service.notification.Condition;
 import android.service.notification.IConditionListener;
 import android.service.notification.IConditionProvider;
@@ -80,7 +81,8 @@
     void setOnNotificationPostedTrimFromListener(in INotificationListener token, int trim);
     void setInterruptionFilter(String pkg, int interruptionFilter);
 
-    void setImportanceFromRankerService(in INotificationListener token, String key, int importance, CharSequence explanation);
+    void applyAdjustmentFromRankerService(in INotificationListener token, in Adjustment adjustment);
+    void applyAdjustmentsFromRankerService(in INotificationListener token, in List<Adjustment> adjustments);
 
     ComponentName getEffectsSuppressor();
     boolean matchesCallFilter(in Bundle extras);
diff --git a/core/java/android/app/ITaskStackListener.aidl b/core/java/android/app/ITaskStackListener.aidl
index fa67529..496ca6f 100644
--- a/core/java/android/app/ITaskStackListener.aidl
+++ b/core/java/android/app/ITaskStackListener.aidl
@@ -40,4 +40,9 @@
      * Called when we launched an activity that we forced to be resizable.
      */
     void onActivityForcedResizable(String packageName, int taskId);
+
+    /**
+     * Callen when we launched an activity that is dismissed the docked stack.
+     */
+    void onActivityDismissingDockedStack();
 }
diff --git a/core/java/android/app/LoaderManager.java b/core/java/android/app/LoaderManager.java
index f0e35c9..f203f46 100644
--- a/core/java/android/app/LoaderManager.java
+++ b/core/java/android/app/LoaderManager.java
@@ -318,7 +318,7 @@
             if (mStarted) {
                 if (mReportNextStart) {
                     mReportNextStart = false;
-                    if (mHaveData) {
+                    if (mHaveData && !mRetaining) {
                         callOnLoadFinished(mLoader, mData);
                     }
                 }
diff --git a/core/java/android/app/Notification.java b/core/java/android/app/Notification.java
index faefc9d..520acf5 100644
--- a/core/java/android/app/Notification.java
+++ b/core/java/android/app/Notification.java
@@ -21,6 +21,7 @@
 import android.annotation.IntDef;
 import android.annotation.SdkConstant;
 import android.annotation.SdkConstant.SdkConstantType;
+import android.annotation.SystemApi;
 import android.content.Context;
 import android.content.Intent;
 import android.content.pm.ApplicationInfo;
@@ -28,6 +29,7 @@
 import android.content.res.ColorStateList;
 import android.graphics.Bitmap;
 import android.graphics.Canvas;
+import android.graphics.Color;
 import android.graphics.PorterDuff;
 import android.graphics.drawable.Drawable;
 import android.graphics.drawable.Icon;
@@ -42,6 +44,7 @@
 import android.os.Parcelable;
 import android.os.SystemClock;
 import android.os.UserHandle;
+import android.text.BidiFormatter;
 import android.text.SpannableStringBuilder;
 import android.text.Spanned;
 import android.text.TextUtils;
@@ -496,6 +499,15 @@
      */
     public static final int FLAG_GROUP_SUMMARY      = 0x00000200;
 
+    /**
+     * Bit to be bitswise-ored into the {@link #flags} field that should be
+     * set if this notification is the group summary for an auto-group of notifications.
+     *
+     * @hide
+     */
+    @SystemApi
+    public static final int FLAG_AUTOGROUP_SUMMARY  = 0x00000400;
+
     public int flags;
 
     /** @hide */
@@ -578,8 +590,8 @@
     private static final int COLOR_INVALID = 1;
 
     /**
-     * Sphere of visibility of this notification, which affects how and when the SystemUI reveals 
-     * the notification's presence and contents in untrusted situations (namely, on the secure 
+     * Sphere of visibility of this notification, which affects how and when the SystemUI reveals
+     * the notification's presence and contents in untrusted situations (namely, on the secure
      * lockscreen).
      *
      * The default level, {@link #VISIBILITY_PRIVATE}, behaves exactly as notifications have always
@@ -1409,7 +1421,7 @@
              * an activity and transitions should be generated, false otherwise.
              * @return this object for method chaining
              */
-            public WearableExtender setHintContentIntentLaunchesActivity(
+            public WearableExtender setHintLaunchesActivity(
                     boolean hintLaunchesActivity) {
                 setFlag(FLAG_HINT_LAUNCHES_ACTIVITY, hintLaunchesActivity);
                 return this;
@@ -1422,7 +1434,7 @@
              * should be generated, false otherwise. The default value is {@code false} if this was
              * never set.
              */
-            public boolean getHintContentIntentLaunchesActivity() {
+            public boolean getHintLaunchesActivity() {
                 return (mFlags & FLAG_HINT_LAUNCHES_ACTIVITY) != 0;
             }
         }
@@ -1945,13 +1957,16 @@
      * @hide
      */
     public static void addFieldsFromContext(Context context, Notification notification) {
-        if (notification.extras.getParcelable(EXTRA_BUILDER_APPLICATION_INFO) == null) {
-            notification.extras.putParcelable(EXTRA_BUILDER_APPLICATION_INFO,
-                    context.getApplicationInfo());
-        }
-        if (!notification.extras.containsKey(EXTRA_ORIGINATING_USERID)) {
-            notification.extras.putInt(EXTRA_ORIGINATING_USERID, context.getUserId());
-        }
+        addFieldsFromContext(context.getApplicationInfo(), context.getUserId(), notification);
+    }
+
+    /**
+     * @hide
+     */
+    public static void addFieldsFromContext(ApplicationInfo ai, int userId,
+            Notification notification) {
+        notification.extras.putParcelable(EXTRA_BUILDER_APPLICATION_INFO, ai);
+        notification.extras.putInt(EXTRA_ORIGINATING_USERID, userId);
     }
 
     @Override
@@ -2214,7 +2229,8 @@
                         Log.d(TAG, "Unknown style class: " + templateClass);
                     } else {
                         try {
-                            final Constructor<? extends Style> ctor = styleClass.getConstructor();
+                            final Constructor<? extends Style> ctor =
+                                    styleClass.getDeclaredConstructor();
                             ctor.setAccessible(true);
                             final Style style = ctor.newInstance();
                             style.restoreFromExtras(mN.extras);
@@ -3020,12 +3036,13 @@
         /**
          * @hide
          */
-        public void setFlag(int mask, boolean value) {
+        public Builder setFlag(int mask, boolean value) {
             if (value) {
                 mN.flags |= mask;
             } else {
                 mN.flags &= ~mask;
             }
+            return this;
         }
 
         /**
@@ -3112,6 +3129,18 @@
          * @param hasProgress whether the progress bar should be shown and set
          */
         private RemoteViews applyStandardTemplate(int resId, boolean hasProgress) {
+            final Bundle ex = mN.extras;
+
+            CharSequence title = processLegacyText(ex.getCharSequence(EXTRA_TITLE));
+            CharSequence text = processLegacyText(ex.getCharSequence(EXTRA_TEXT));
+            return applyStandardTemplate(resId, hasProgress, title, text);
+        }
+
+        /**
+         * @param hasProgress whether the progress bar should be shown and set
+         */
+        private RemoteViews applyStandardTemplate(int resId, boolean hasProgress,
+                CharSequence title, CharSequence text) {
             RemoteViews contentView = new BuilderRemoteViews(mContext.getApplicationInfo(), resId);
 
             resetStandardTemplate(contentView);
@@ -3120,17 +3149,15 @@
 
             bindNotificationHeader(contentView);
             bindLargeIcon(contentView);
-            if (ex.getCharSequence(EXTRA_TITLE) != null) {
+            if (title != null) {
                 contentView.setViewVisibility(R.id.title, View.VISIBLE);
-                contentView.setTextViewText(R.id.title,
-                        processLegacyText(ex.getCharSequence(EXTRA_TITLE)));
+                contentView.setTextViewText(R.id.title, title);
             }
             boolean showProgress = handleProgressBar(hasProgress, contentView, ex);
-            if (ex.getCharSequence(EXTRA_TEXT) != null) {
+            if (text != null) {
                 int textId = showProgress ? com.android.internal.R.id.text_line_1
                         : com.android.internal.R.id.text;
-                contentView.setTextViewText(textId, processLegacyText(
-                        ex.getCharSequence(EXTRA_TEXT)));
+                contentView.setTextViewText(textId, text);
                 contentView.setViewVisibility(textId, View.VISIBLE);
             }
 
@@ -3735,6 +3762,10 @@
             return R.layout.notification_template_material_inbox;
         }
 
+        private int getMessagingLayoutResource() {
+            return R.layout.notification_template_material_messaging;
+        }
+
         private int getActionLayoutResource() {
             return R.layout.notification_material_action;
         }
@@ -4361,13 +4392,100 @@
         /**
          * @hide
          */
-        public RemoteViews makeBigContentView() {
-            // TODO handset to write implementation
-            RemoteViews contentView = getStandardView(mBuilder.getBigTextLayoutResource());
+        @Override
+        public RemoteViews makeContentView() {
+            Message m = findLatestIncomingMessage();
+            CharSequence title = mConversationTitle != null
+                    ? mConversationTitle
+                    : (m == null) ? null : m.mSender;
+            CharSequence text = (m == null)
+                    ? null
+                    : mConversationTitle != null ? makeMessageLine(m) : m.mText;
 
+            return mBuilder.applyStandardTemplate(mBuilder.getBaseLayoutResource(),
+                    false /* hasProgress */,
+                    title,
+                    text);
+        }
+
+        private Message findLatestIncomingMessage() {
+            for (int i = mMessages.size() - 1; i >= 0; i--) {
+                Message m = mMessages.get(i);
+                // Incoming messages have a non-empty sender.
+                if (!TextUtils.isEmpty(m.mSender)) {
+                    return m;
+                }
+            }
+            return null;
+        }
+
+        /**
+         * @hide
+         */
+        @Override
+        public RemoteViews makeBigContentView() {
+            CharSequence title = !TextUtils.isEmpty(super.mBigContentTitle)
+                    ? super.mBigContentTitle
+                    : mConversationTitle;
+            boolean hasTitle = !TextUtils.isEmpty(title);
+
+            RemoteViews contentView = mBuilder.applyStandardTemplate(
+                    mBuilder.getMessagingLayoutResource(),
+                    false /* hasProgress */,
+                    title,
+                    null /* text */);
+
+            int[] rowIds = {R.id.inbox_text0, R.id.inbox_text1, R.id.inbox_text2, R.id.inbox_text3,
+                    R.id.inbox_text4, R.id.inbox_text5, R.id.inbox_text6};
+
+            // Make sure all rows are gone in case we reuse a view.
+            for (int rowId : rowIds) {
+                contentView.setViewVisibility(rowId, View.GONE);
+            }
+
+            int i=0;
+            int titlePadding = mBuilder.mContext.getResources().getDimensionPixelSize(
+                    R.dimen.notification_messaging_spacing);
+            contentView.setViewLayoutMarginBottom(R.id.line1, hasTitle ? titlePadding : 0);
+            contentView.setInt(R.id.notification_messaging, "setNumIndentLines",
+                    mBuilder.mN.mLargeIcon == null ? 0 : (hasTitle ? 1 : 2));
+
+            int firstMessage = Math.max(0, mMessages.size() - rowIds.length);
+            while (firstMessage + i < mMessages.size() && i < rowIds.length) {
+                Message m = mMessages.get(firstMessage + i);
+                int rowId = rowIds[i];
+
+                contentView.setViewVisibility(rowId, View.VISIBLE);
+                contentView.setTextViewText(rowId, makeMessageLine(m));
+
+                i++;
+            }
             return contentView;
         }
 
+        private CharSequence makeMessageLine(Message m) {
+            BidiFormatter bidi = BidiFormatter.getInstance();
+            SpannableStringBuilder sb = new SpannableStringBuilder();
+            if (TextUtils.isEmpty(m.mSender)) {
+                CharSequence replyName = mUserDisplayName == null ? "" : mUserDisplayName;
+                sb.append(bidi.unicodeWrap(replyName),
+                        makeFontColorSpan(mBuilder.resolveContrastColor()),
+                        0 /* flags */);
+            } else {
+                sb.append(bidi.unicodeWrap(m.mSender),
+                        makeFontColorSpan(Color.BLACK),
+                        0 /* flags */);
+            }
+            CharSequence text = m.mText == null ? "" : m.mText;
+            sb.append("  ").append(bidi.unicodeWrap(text));
+            return sb;
+        }
+
+        private static TextAppearanceSpan makeFontColorSpan(int color) {
+            return new TextAppearanceSpan(null, 0, 0,
+                    ColorStateList.valueOf(color), null);
+        }
+
         public static final class Message implements Parcelable {
 
             private final CharSequence mText;
diff --git a/core/java/android/app/SystemServiceRegistry.java b/core/java/android/app/SystemServiceRegistry.java
index bdc4404..d5d4ca7 100644
--- a/core/java/android/app/SystemServiceRegistry.java
+++ b/core/java/android/app/SystemServiceRegistry.java
@@ -589,9 +589,7 @@
                 new CachedServiceFetcher<LauncherApps>() {
             @Override
             public LauncherApps createService(ContextImpl ctx) {
-                IBinder b = ServiceManager.getService(Context.LAUNCHER_APPS_SERVICE);
-                ILauncherApps service = ILauncherApps.Stub.asInterface(b);
-                return new LauncherApps(ctx, service);
+                return new LauncherApps(ctx);
             }});
 
         registerService(Context.RESTRICTIONS_SERVICE, RestrictionsManager.class,
@@ -758,8 +756,7 @@
                 new CachedServiceFetcher<ShortcutManager>() {
             @Override
             public ShortcutManager createService(ContextImpl ctx) {
-                IBinder b = ServiceManager.getService(Context.SHORTCUT_SERVICE);
-                return new ShortcutManager(ctx, IShortcutService.Stub.asInterface(b));
+                return new ShortcutManager(ctx);
             }});
 
         registerService(Context.SYSTEM_HEALTH_SERVICE, SystemHealthManager.class,
diff --git a/core/java/android/app/job/JobInfo.java b/core/java/android/app/job/JobInfo.java
index 828ac38..9b4f43a 100644
--- a/core/java/android/app/job/JobInfo.java
+++ b/core/java/android/app/job/JobInfo.java
@@ -254,7 +254,8 @@
     }
 
     /**
-     * Flex time for this job. Only valid if this is a periodic job.
+     * Flex time for this job. Only valid if this is a periodic job.  The job can
+     * execute at any time in a window of flex length at the end of the period.
      */
     public long getFlexMillis() {
         long interval = getIntervalMillis();
diff --git a/core/java/android/app/job/JobService.java b/core/java/android/app/job/JobService.java
index 95a8ccf..77307b7 100644
--- a/core/java/android/app/job/JobService.java
+++ b/core/java/android/app/job/JobService.java
@@ -27,6 +27,8 @@
 
 import com.android.internal.annotations.GuardedBy;
 
+import java.lang.ref.WeakReference;
+
 /**
  * <p>Entry point for the callback from the {@link android.app.job.JobScheduler}.</p>
  * <p>This is the base class that handles asynchronous requests that were previously scheduled. You
@@ -62,15 +64,15 @@
      * Identifier for a message that will result in a call to
      * {@link #onStartJob(android.app.job.JobParameters)}.
      */
-    private final int MSG_EXECUTE_JOB = 0;
+    private static final int MSG_EXECUTE_JOB = 0;
     /**
      * Message that will result in a call to {@link #onStopJob(android.app.job.JobParameters)}.
      */
-    private final int MSG_STOP_JOB = 1;
+    private static final int MSG_STOP_JOB = 1;
     /**
      * Message that the client has completed execution of this job.
      */
-    private final int MSG_JOB_FINISHED = 2;
+    private static final int MSG_JOB_FINISHED = 2;
 
     /** Lock object for {@link #mHandler}. */
     private final Object mHandlerLock = new Object();
@@ -82,21 +84,36 @@
     @GuardedBy("mHandlerLock")
     JobHandler mHandler;
 
-    /** Binder for this service. */
-    IJobService mBinder = new IJobService.Stub() {
-        @Override
-        public void startJob(JobParameters jobParams) {
-            ensureHandler();
-            Message m = Message.obtain(mHandler, MSG_EXECUTE_JOB, jobParams);
-            m.sendToTarget();
+    static final class JobInterface extends IJobService.Stub {
+        final WeakReference<JobService> mService;
+
+        JobInterface(JobService service) {
+            mService = new WeakReference<>(service);
         }
+
         @Override
-        public void stopJob(JobParameters jobParams) {
-            ensureHandler();
-            Message m = Message.obtain(mHandler, MSG_STOP_JOB, jobParams);
-            m.sendToTarget();
+        public void startJob(JobParameters jobParams) throws RemoteException {
+            JobService service = mService.get();
+            if (service != null) {
+                service.ensureHandler();
+                Message m = Message.obtain(service.mHandler, MSG_EXECUTE_JOB, jobParams);
+                m.sendToTarget();
+            }
         }
-    };
+
+        @Override
+        public void stopJob(JobParameters jobParams) throws RemoteException {
+            JobService service = mService.get();
+            if (service != null) {
+                service.ensureHandler();
+                Message m = Message.obtain(service.mHandler, MSG_STOP_JOB, jobParams);
+                m.sendToTarget();
+            }
+
+        }
+    }
+
+    IJobService mBinder;
 
     /** @hide */
     void ensureHandler() {
@@ -194,6 +211,9 @@
 
     /** @hide */
     public final IBinder onBind(Intent intent) {
+        if (mBinder == null) {
+            mBinder = new JobInterface(this);
+        }
         return mBinder.asBinder();
     }
 
diff --git a/core/java/android/content/Intent.java b/core/java/android/content/Intent.java
index 30f2c94..7e67e8d 100644
--- a/core/java/android/content/Intent.java
+++ b/core/java/android/content/Intent.java
@@ -1404,6 +1404,16 @@
     public static final String ACTION_UPGRADE_SETUP = "android.intent.action.UPGRADE_SETUP";
 
     /**
+     * Activity Action: Start the Keyboard Shortcuts Helper screen.
+     * <p>Input: Nothing.
+     * <p>Output: Nothing.
+     * @hide
+     */
+    @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
+    public static final String ACTION_SHOW_KEYBOARD_SHORTCUTS =
+            "android.intent.action.SHOW_KEYBOARD_SHORTCUTS";
+
+    /**
      * Activity Action: Show settings for managing network data usage of a
      * specific application. Applications should define an activity that offers
      * options to control data usage.
@@ -3730,6 +3740,31 @@
     public static final String EXTRA_ALTERNATE_INTENTS = "android.intent.extra.ALTERNATE_INTENTS";
 
     /**
+     * A {@link ComponentName ComponentName[]} describing components that should be filtered out
+     * and omitted from a list of components presented to the user.
+     *
+     * <p>When used with {@link #ACTION_CHOOSER}, the chooser will omit any of the components
+     * in this array if it otherwise would have shown them. Useful for omitting specific targets
+     * from your own package or other apps from your organization if the idea of sending to those
+     * targets would be redundant with other app functionality. Filtered components will not
+     * be able to present targets from an associated <code>ChooserTargetService</code>.</p>
+     */
+    public static final String EXTRA_EXCLUDE_COMPONENTS
+            = "android.intent.extra.EXCLUDE_COMPONENTS";
+
+    /**
+     * A {@link android.service.chooser.ChooserTarget ChooserTarget[]} for {@link #ACTION_CHOOSER}
+     * describing additional high-priority deep-link targets for the chooser to present to the user.
+     *
+     * <p>Targets provided in this way will be presented inline with all other targets provided
+     * by services from other apps. They will be prioritized before other service targets, but
+     * after those targets provided by sources that the user has manually pinned to the front.</p>
+     *
+     * @see #ACTION_CHOOSER
+     */
+    public static final String EXTRA_CHOOSER_TARGETS = "android.intent.extra.CHOOSER_TARGETS";
+
+    /**
      * An {@link IntentSender} for an Activity that will be invoked when the user makes a selection
      * from the chooser activity presented by {@link #ACTION_CHOOSER}.
      *
diff --git a/core/java/android/content/pm/ApplicationInfo.java b/core/java/android/content/pm/ApplicationInfo.java
index 104feb5..585d2a3 100644
--- a/core/java/android/content/pm/ApplicationInfo.java
+++ b/core/java/android/content/pm/ApplicationInfo.java
@@ -366,6 +366,9 @@
      *
      * <p>NOTE: {@code WebView} does not honor this flag.
      *
+     * <p>This flag is ignored on Android N and above if an Android Network Security Config is
+     * present.
+     *
      * <p>This flag comes from
      * {@link android.R.styleable#AndroidManifestApplication_usesCleartextTraffic
      * android:usesCleartextTraffic} of the &lt;application&gt; tag.
diff --git a/core/java/android/content/pm/ILauncherApps.aidl b/core/java/android/content/pm/ILauncherApps.aidl
index 6b3d4f1..430c7e7 100644
--- a/core/java/android/content/pm/ILauncherApps.aidl
+++ b/core/java/android/content/pm/ILauncherApps.aidl
@@ -18,6 +18,7 @@
 
 import android.content.ComponentName;
 import android.content.Intent;
+import android.content.pm.ActivityInfo;
 import android.content.pm.ApplicationInfo;
 import android.content.pm.IOnAppsChangedListener;
 import android.content.pm.ParceledListSlice;
@@ -37,7 +38,7 @@
     void addOnAppsChangedListener(String callingPackage, in IOnAppsChangedListener listener);
     void removeOnAppsChangedListener(in IOnAppsChangedListener listener);
     ParceledListSlice getLauncherActivities(String packageName, in UserHandle user);
-    ResolveInfo resolveActivity(in Intent intent, in UserHandle user);
+    ActivityInfo resolveActivity(in ComponentName component, in UserHandle user);
     void startActivityAsUser(in ComponentName component, in Rect sourceBounds,
             in Bundle opts, in UserHandle user);
     void showAppDetailsAsUser(in ComponentName component, in Rect sourceBounds,
@@ -47,17 +48,16 @@
     ApplicationInfo getApplicationInfo(String packageName, int flags, in UserHandle user);
 
     ParceledListSlice getShortcuts(String callingPackage, long changedSince, String packageName,
-            in ComponentName componentName, int flags, in UserHandle user);
-    ParceledListSlice getShortcutInfo(String callingPackage, String packageName, in List<String> ids,
-            in UserHandle user);
+            in List shortcutIds, in ComponentName componentName, int flags, in UserHandle user);
     void pinShortcuts(String callingPackage, String packageName, in List<String> shortcutIds,
             in UserHandle user);
     boolean startShortcut(String callingPackage, String packageName, String id,
-            in Rect sourceBounds, in Bundle startActivityOptions, in UserHandle user);
+            in Rect sourceBounds, in Bundle startActivityOptions, int userId);
 
-    int getShortcutIconResId(String callingPackage, in ShortcutInfo shortcut, in UserHandle user);
-    ParcelFileDescriptor getShortcutIconFd(String callingPackage, in ShortcutInfo shortcut,
-            in UserHandle user);
+    int getShortcutIconResId(String callingPackage, String packageName, String id,
+            int userId);
+    ParcelFileDescriptor getShortcutIconFd(String callingPackage, String packageName, String id,
+            int userId);
 
     boolean hasShortcutHostPermission(String callingPackage);
 }
diff --git a/core/java/android/content/pm/IShortcutService.aidl b/core/java/android/content/pm/IShortcutService.aidl
index 31d377b..9c90346 100644
--- a/core/java/android/content/pm/IShortcutService.aidl
+++ b/core/java/android/content/pm/IShortcutService.aidl
@@ -28,11 +28,12 @@
 
     ParceledListSlice getDynamicShortcuts(String packageName, int userId);
 
-    boolean addDynamicShortcut(String packageName, in ShortcutInfo shortcutInfo, int userId);
+    boolean addDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList,
+            int userId);
 
-    void deleteDynamicShortcut(String packageName, in String shortcutId, int userId);
+    void removeDynamicShortcuts(String packageName, in List shortcutIds, int userId);
 
-    void deleteAllDynamicShortcuts(String packageName, int userId);
+    void removeAllDynamicShortcuts(String packageName, int userId);
 
     ParceledListSlice getPinnedShortcuts(String packageName, int userId);
 
diff --git a/core/java/android/content/pm/LauncherActivityInfo.java b/core/java/android/content/pm/LauncherActivityInfo.java
index 40e1a9f..2beca7b 100644
--- a/core/java/android/content/pm/LauncherActivityInfo.java
+++ b/core/java/android/content/pm/LauncherActivityInfo.java
@@ -39,7 +39,6 @@
 
     private ActivityInfo mActivityInfo;
     private ComponentName mComponentName;
-    private ResolveInfo mResolveInfo;
     private UserHandle mUser;
 
     /**
@@ -49,11 +48,10 @@
      * @param info ResolveInfo from which to create the LauncherActivityInfo.
      * @param user The UserHandle of the profile to which this activity belongs.
      */
-    LauncherActivityInfo(Context context, ResolveInfo info, UserHandle user) {
+    LauncherActivityInfo(Context context, ActivityInfo info, UserHandle user) {
         this(context);
-        mResolveInfo = info;
-        mActivityInfo = info.activityInfo;
-        mComponentName = LauncherApps.getComponentName(info);
+        mActivityInfo = info;
+        mComponentName =  new ComponentName(info.packageName, info.name);
         mUser = user;
     }
 
@@ -91,7 +89,7 @@
      * @return The label for the activity.
      */
     public CharSequence getLabel() {
-        return mResolveInfo.loadLabel(mPm);
+        return mActivityInfo.loadLabel(mPm);
     }
 
     /**
@@ -103,7 +101,7 @@
      * @return The drawable associated with the activity.
      */
     public Drawable getIcon(int density) {
-        final int iconRes = mResolveInfo.getIconResourceInternal();
+        final int iconRes = mActivityInfo.getIconResource();
         Drawable icon = null;
         // Get the preferred density icon from the app's resources
         if (density != 0 && iconRes != 0) {
@@ -116,7 +114,7 @@
         }
         // Get the default density icon
         if (icon == null) {
-            icon = mResolveInfo.loadIcon(mPm);
+            icon = mActivityInfo.loadIcon(mPm);
         }
         return icon;
     }
diff --git a/core/java/android/content/pm/LauncherApps.java b/core/java/android/content/pm/LauncherApps.java
index d865f34..824722d 100644
--- a/core/java/android/content/pm/LauncherApps.java
+++ b/core/java/android/content/pm/LauncherApps.java
@@ -19,6 +19,7 @@
 import android.annotation.IntDef;
 import android.annotation.NonNull;
 import android.annotation.Nullable;
+import android.annotation.TestApi;
 import android.content.ComponentName;
 import android.content.Context;
 import android.content.Intent;
@@ -30,6 +31,7 @@
 import android.os.Message;
 import android.os.ParcelFileDescriptor;
 import android.os.RemoteException;
+import android.os.ServiceManager;
 import android.os.UserHandle;
 import android.os.UserManager;
 import android.util.Log;
@@ -37,6 +39,7 @@
 import java.lang.annotation.Retention;
 import java.lang.annotation.RetentionPolicy;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collections;
 import java.util.List;
 
@@ -205,6 +208,9 @@
         String mPackage;
 
         @Nullable
+        List<String> mShortcutIds;
+
+        @Nullable
         ComponentName mActivity;
 
         @QueryFlags
@@ -229,6 +235,14 @@
         }
 
         /**
+         * If non-null, return only the specified shortcuts by ID.  When setting this field,
+         * a packange name must also be set with {@link #setPackage}.
+         */
+        public void setShortcutIds(@Nullable List<String> shortcutIds) {
+            mShortcutIds = shortcutIds;
+        }
+
+        /**
          * If non-null, returns only shortcuts associated with the activity.
          */
         public void setActivity(@Nullable ComponentName activity) {
@@ -250,6 +264,13 @@
         mPm = context.getPackageManager();
     }
 
+    /** @hide */
+    @TestApi
+    public LauncherApps(Context context) {
+        this(context, ILauncherApps.Stub.asInterface(
+                ServiceManager.getService(Context.LAUNCHER_APPS_SERVICE)));
+    }
+
     /**
      * Retrieves a list of launchable activities that match {@link Intent#ACTION_MAIN} and
      * {@link Intent#CATEGORY_LAUNCHER}, for a specified user.
@@ -271,7 +292,7 @@
         }
         ArrayList<LauncherActivityInfo> lais = new ArrayList<LauncherActivityInfo>();
         for (ResolveInfo ri : activities.getList()) {
-            LauncherActivityInfo lai = new LauncherActivityInfo(mContext, ri, user);
+            LauncherActivityInfo lai = new LauncherActivityInfo(mContext, ri.activityInfo, user);
             if (DEBUG) {
                 Log.v(TAG, "Returning activity for profile " + user + " : "
                         + lai.getComponentName());
@@ -281,10 +302,6 @@
         return lais;
     }
 
-    static ComponentName getComponentName(ResolveInfo ri) {
-        return new ComponentName(ri.activityInfo.packageName, ri.activityInfo.name);
-    }
-
     /**
      * Returns the activity info for a given intent and user handle, if it resolves. Otherwise it
      * returns null.
@@ -295,9 +312,9 @@
      */
     public LauncherActivityInfo resolveActivity(Intent intent, UserHandle user) {
         try {
-            ResolveInfo ri = mService.resolveActivity(intent, user);
-            if (ri != null) {
-                LauncherActivityInfo info = new LauncherActivityInfo(mContext, ri, user);
+            ActivityInfo ai = mService.resolveActivity(intent.getComponent(), user);
+            if (ai != null) {
+                LauncherActivityInfo info = new LauncherActivityInfo(mContext, ai, user);
                 return info;
             }
         } catch (RemoteException re) {
@@ -369,6 +386,7 @@
      *
      * @return An {@link ApplicationInfo} containing information about the package or
      *         null of the package isn't found.
+     * @hide
      */
     public ApplicationInfo getApplicationInfo(String packageName, @ApplicationInfoFlags int flags,
             UserHandle user) {
@@ -429,7 +447,8 @@
             @NonNull UserHandle user) {
         try {
             return mService.getShortcuts(mContext.getPackageName(),
-                    query.mChangedSince, query.mPackage, query.mActivity, query.mQueryFlags, user)
+                    query.mChangedSince, query.mPackage, query.mShortcutIds, query.mActivity,
+                    query.mQueryFlags, user)
                     .getList();
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
@@ -437,29 +456,18 @@
     }
 
     /**
-     * Returns {@link ShortcutInfo}s with the given IDs from a package.
-     *
-     * <p>Callers must be allowed to access the shortcut information, as defined in {@link
-     * #hasShortcutHostPermission()}.
-     *
-     * @param packageName The target package.
-     * @param ids IDs of the shortcuts to retrieve.
-     * @param user The UserHandle of the profile.
-     *
-     * @return list of {@link ShortcutInfo} associated with the package.
+     * @hide // No longer used.  Use getShortcuts() instead.  Kept for unit tests.
      */
     @Nullable
     public List<ShortcutInfo> getShortcutInfo(@NonNull String packageName,
             @NonNull List<String> ids, @NonNull UserHandle user) {
-        try {
-            return mService.getShortcutInfo(mContext.getPackageName(), packageName, ids, user)
-                    .getList();
-        } catch (RemoteException e) {
-            throw e.rethrowFromSystemServer();
-        }
+        final ShortcutQuery q = new ShortcutQuery();
+        q.setPackage(packageName);
+        q.setShortcutIds(ids);
+        q.setQueryFlags(ShortcutQuery.FLAG_GET_DYNAMIC | ShortcutQuery.FLAG_GET_PINNED);
+        return getShortcuts(q, user);
     }
 
-
     /**
      * Pin shortcuts on a package.
      *
@@ -483,21 +491,24 @@
     }
 
     /**
-     * Return the icon resource ID, if {@code shortcut} has one
-     * (i.e. when {@link ShortcutInfo#hasIconResource()} returns {@code true}).
-     *
-     * <p>Callers must be allowed to access the shortcut information, as defined in {@link
-     * #hasShortcutHostPermission()}.
-     *
-     * @param shortcut The target shortcut.
-     * @param user The UserHandle of the profile.
+     * @hide kept for testing.
      */
-    public int getShortcutIconResId(@NonNull ShortcutInfo shortcut, @NonNull UserHandle user) {
-        try {
-            return mService.getShortcutIconResId(mContext.getPackageName(), shortcut, user);
-        } catch (RemoteException e) {
-            throw e.rethrowFromSystemServer();
-        }
+    public int getShortcutIconResId(@NonNull ShortcutInfo shortcut) {
+        return shortcut.getIconResourceId();
+    }
+
+    /**
+     * @hide kept for testing.
+     */
+    public int getShortcutIconResId(@NonNull String packageName, @NonNull String shortcutId,
+            @NonNull UserHandle user) {
+        final ShortcutQuery q = new ShortcutQuery();
+        q.setPackage(packageName);
+        q.setShortcutIds(Arrays.asList(shortcutId));
+        q.setQueryFlags(ShortcutQuery.FLAG_GET_DYNAMIC | ShortcutQuery.FLAG_GET_PINNED);
+        final List<ShortcutInfo> shortcuts = getShortcuts(q, user);
+
+        return shortcuts.size() > 0 ? shortcuts.get(0).getIconResourceId() : 0;
     }
 
     /**
@@ -508,12 +519,34 @@
      * #hasShortcutHostPermission()}.
      *
      * @param shortcut The target shortcut.
+     */
+    public ParcelFileDescriptor getShortcutIconFd(
+            @NonNull ShortcutInfo shortcut) {
+        return getShortcutIconFd(shortcut.getPackageName(), shortcut.getId(),
+                shortcut.getUserId());
+    }
+
+    /**
+     * Return the icon as {@link ParcelFileDescriptor}, when it's stored as a file
+     * (i.e. when {@link ShortcutInfo#hasIconFile()} returns {@code true}).
+     *
+     * <p>Callers must be allowed to access the shortcut information, as defined in {@link
+     * #hasShortcutHostPermission()}.
+     *
+     * @param packageName The target package name.
+     * @param shortcutId The ID of the shortcut to lad rom.
      * @param user The UserHandle of the profile.
      */
     public ParcelFileDescriptor getShortcutIconFd(
-            @NonNull ShortcutInfo shortcut, @NonNull UserHandle user) {
+            @NonNull String packageName, @NonNull String shortcutId, @NonNull UserHandle user) {
+        return getShortcutIconFd(packageName, shortcutId, user.getIdentifier());
+    }
+
+    private ParcelFileDescriptor getShortcutIconFd(
+            @NonNull String packageName, @NonNull String shortcutId, int userId) {
         try {
-            return mService.getShortcutIconFd(mContext.getPackageName(), shortcut, user);
+            return mService.getShortcutIconFd(mContext.getPackageName(),
+                    packageName, shortcutId, userId);
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
         }
@@ -536,9 +569,35 @@
     public boolean startShortcut(@NonNull String packageName, @NonNull String shortcutId,
             @Nullable Rect sourceBounds, @Nullable Bundle startActivityOptions,
             @NonNull UserHandle user) {
+        return startShortcut(packageName, shortcutId, sourceBounds, startActivityOptions,
+                user.getIdentifier());
+    }
+
+    /**
+     * Launches a shortcut.
+     *
+     * <p>Callers must be allowed to access the shortcut information, as defined in {@link
+     * #hasShortcutHostPermission()}.
+     *
+     * @param shortcut The target shortcut.
+     * @param sourceBounds The Rect containing the source bounds of the clicked icon.
+     * @param startActivityOptions Options to pass to startActivity.
+     * @return {@code false} when the shortcut is no longer valid (e.g. the creator application
+     *   has been uninstalled). {@code true} when the shortcut is still valid.
+     */
+    public boolean startShortcut(@NonNull ShortcutInfo shortcut,
+            @Nullable Rect sourceBounds, @Nullable Bundle startActivityOptions) {
+        return startShortcut(shortcut.getPackageName(), shortcut.getId(),
+                sourceBounds, startActivityOptions,
+                shortcut.getUserId());
+    }
+
+    private boolean startShortcut(@NonNull String packageName, @NonNull String shortcutId,
+            @Nullable Rect sourceBounds, @Nullable Bundle startActivityOptions,
+            int userId) {
         try {
             return mService.startShortcut(mContext.getPackageName(), packageName, shortcutId,
-                    sourceBounds, startActivityOptions, user);
+                    sourceBounds, startActivityOptions, userId);
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
         }
diff --git a/core/java/android/content/pm/PackageUserState.java b/core/java/android/content/pm/PackageUserState.java
index e85311d..8236f55 100644
--- a/core/java/android/content/pm/PackageUserState.java
+++ b/core/java/android/content/pm/PackageUserState.java
@@ -36,22 +36,21 @@
  * @hide
  */
 public class PackageUserState {
+    public long ceDataInode;
+    public boolean installed;
     public boolean stopped;
     public boolean notLaunched;
-    public boolean installed;
     public boolean hidden; // Is the app restricted by owner / admin
     public boolean suspended;
-    public int enabled;
     public boolean blockUninstall;
-
+    public int enabled;
     public String lastDisableAppCaller;
+    public int domainVerificationStatus;
+    public int appLinkGeneration;
 
     public ArraySet<String> disabledComponents;
     public ArraySet<String> enabledComponents;
 
-    public int domainVerificationStatus;
-    public int appLinkGeneration;
-
     public PackageUserState() {
         installed = true;
         hidden = false;
@@ -62,18 +61,19 @@
     }
 
     public PackageUserState(PackageUserState o) {
+        ceDataInode = o.ceDataInode;
         installed = o.installed;
         stopped = o.stopped;
         notLaunched = o.notLaunched;
-        enabled = o.enabled;
         hidden = o.hidden;
         suspended = o.suspended;
-        lastDisableAppCaller = o.lastDisableAppCaller;
-        disabledComponents = ArrayUtils.cloneOrNull(o.disabledComponents);
-        enabledComponents = ArrayUtils.cloneOrNull(o.enabledComponents);
         blockUninstall = o.blockUninstall;
+        enabled = o.enabled;
+        lastDisableAppCaller = o.lastDisableAppCaller;
         domainVerificationStatus = o.domainVerificationStatus;
         appLinkGeneration = o.appLinkGeneration;
+        disabledComponents = ArrayUtils.cloneOrNull(o.disabledComponents);
+        enabledComponents = ArrayUtils.cloneOrNull(o.enabledComponents);
     }
 
     /**
diff --git a/core/java/android/content/pm/ShortcutInfo.java b/core/java/android/content/pm/ShortcutInfo.java
index 1812575a..a900015 100644
--- a/core/java/android/content/pm/ShortcutInfo.java
+++ b/core/java/android/content/pm/ShortcutInfo.java
@@ -18,6 +18,7 @@
 import android.annotation.IntDef;
 import android.annotation.NonNull;
 import android.annotation.Nullable;
+import android.annotation.UserIdInt;
 import android.content.ComponentName;
 import android.content.ContentResolver;
 import android.content.Context;
@@ -33,6 +34,8 @@
 
 import java.lang.annotation.Retention;
 import java.lang.annotation.RetentionPolicy;
+import java.util.ArrayList;
+import java.util.List;
 
 // TODO Enhance javadoc
 /**
@@ -106,6 +109,11 @@
     @Retention(RetentionPolicy.SOURCE)
     public @interface CloneFlags {}
 
+    /**
+     * Shortcut category for
+     */
+    public static final String SHORTCUT_CATEGORY_CONVERSATION = "android.shortcut.conversation";
+
     private final String mId;
 
     @NonNull
@@ -123,6 +131,9 @@
     @Nullable
     private String mText;
 
+    @NonNull
+    private List<String> mCategories;
+
     /**
      * Intent *with extras removed*.
      */
@@ -153,7 +164,11 @@
     @Nullable
     private String mBitmapPath;
 
+    private final int mUserId;
+
     private ShortcutInfo(Builder b) {
+        mUserId = b.mContext.getUserId();
+
         mId = Preconditions.checkStringNotEmpty(b.mId, "Shortcut ID must be provided");
 
         // Note we can't do other null checks here because SM.updateShortcuts() takes partial
@@ -163,6 +178,7 @@
         mIcon = b.mIcon;
         mTitle = b.mTitle;
         mText = b.mText;
+        mCategories = clone(b.mCategories);
         mIntent = b.mIntent;
         if (mIntent != null) {
             final Bundle intentExtras = mIntent.getExtras();
@@ -176,6 +192,10 @@
         updateTimestamp();
     }
 
+    private <T> ArrayList<T> clone(List<T> source) {
+        return (source == null) ? null : new ArrayList<>(source);
+    }
+
     /**
      * Throws if any of the mandatory fields is not set.
      *
@@ -191,22 +211,26 @@
      * Copy constructor.
      */
     private ShortcutInfo(ShortcutInfo source, @CloneFlags int cloneFlags) {
+        mUserId = source.mUserId;
         mId = source.mId;
         mPackageName = source.mPackageName;
         mFlags = source.mFlags;
         mLastChangedTimestamp = source.mLastChangedTimestamp;
 
+        // Just always keep it since it's cheep.
+        mIconResourceId = source.mIconResourceId;
+
         if ((cloneFlags & CLONE_REMOVE_NON_KEY_INFO) == 0) {
             mActivityComponent = source.mActivityComponent;
 
             if ((cloneFlags & CLONE_REMOVE_ICON) == 0) {
                 mIcon = source.mIcon;
                 mBitmapPath = source.mBitmapPath;
-                mIconResourceId = source.mIconResourceId;
             }
 
             mTitle = source.mTitle;
             mText = source.mText;
+            mCategories = clone(source.mCategories);
             if ((cloneFlags & CLONE_REMOVE_INTENT) == 0) {
                 mIntent = source.mIntent;
                 mIntentPersistableExtras = source.mIntentPersistableExtras;
@@ -238,6 +262,7 @@
      * @hide
      */
     public void copyNonNullFieldsFrom(ShortcutInfo source) {
+        Preconditions.checkState(mUserId == source.mUserId, "Owner User ID must match");
         Preconditions.checkState(mId.equals(source.mId), "ID must match");
         Preconditions.checkState(mPackageName.equals(source.mPackageName),
                 "Package name must match");
@@ -255,6 +280,9 @@
         if (source.mText != null) {
             mText = source.mText;
         }
+        if (source.mCategories != null) {
+            mCategories = clone(source.mCategories);
+        }
         if (source.mIntent != null) {
             mIntent = source.mIntent;
             mIntentPersistableExtras = source.mIntentPersistableExtras;
@@ -318,6 +346,8 @@
 
         private String mText;
 
+        private List<String> mCategories;
+
         private Intent mIntent;
 
         private int mWeight;
@@ -362,8 +392,9 @@
          *
          * <p>For performance reasons, icons will <b>NOT</b> be available on instances
          * returned by {@link ShortcutManager} or {@link LauncherApps}.  Launcher applications
-         * need to use {@link LauncherApps#getShortcutIconFd(ShortcutInfo, UserHandle)}
-         * and {@link LauncherApps#getShortcutIconResId(ShortcutInfo, UserHandle)}.
+         * can use {@link ShortcutInfo#getIconResourceId()} if {@link #hasIconResource()} is true.
+         * Otherwise, if {@link #hasIconFile()} is true, use
+         * {@link LauncherApps#getShortcutIconFd} to load the image.
          */
         @NonNull
         public Builder setIcon(Icon icon) {
@@ -396,6 +427,18 @@
         }
 
         /**
+         * Sets categories for a shortcut.  Launcher applications may use this information to
+         * categorise shortcuts.
+         *
+         * @see #SHORTCUT_CATEGORY_CONVERSATION
+         */
+        @NonNull
+        public Builder setCategories(List<String> categories) {
+            mCategories = categories;
+            return this;
+        }
+
+        /**
          * Sets the intent of a shortcut.  This is a mandatory field.  The extras must only contain
          * persistable information.  (See {@link PersistableBundle}).
          */
@@ -493,6 +536,14 @@
     }
 
     /**
+     * Return the categories.
+     */
+    @Nullable
+    public List<String> getCategories() {
+        return mCategories;
+    }
+
+    /**
      * Return the intent.
      *
      * <p>All shortcuts must have an intent, but this method will return null when
@@ -544,6 +595,18 @@
         return mExtras;
     }
 
+    /** @hide */
+    public int getUserId() {
+        return mUserId;
+    }
+
+    /**
+     * {@link UserHandle} on which the publisher created shortcuts.
+     */
+    public UserHandle getUserHandle() {
+        return UserHandle.of(mUserId);
+    }
+
     /**
      * Last time when any of the fields was updated.
      */
@@ -590,7 +653,7 @@
     /**
      * Return whether a shortcut's icon is a resource in the owning package.
      *
-     * @see LauncherApps#getShortcutIconResId(ShortcutInfo, UserHandle)
+     * @see LauncherApps#getShortcutIconResId(ShortcutInfo)
      */
     public boolean hasIconResource() {
         return hasFlags(FLAG_HAS_ICON_RES);
@@ -599,7 +662,7 @@
     /**
      * Return whether a shortcut's icon is stored as a file.
      *
-     * @see LauncherApps#getShortcutIconFd(ShortcutInfo, UserHandle)
+     * @see LauncherApps#getShortcutIconFd(ShortcutInfo)
      */
     public boolean hasIconFile() {
         return hasFlags(FLAG_HAS_ICON_FILE);
@@ -643,7 +706,9 @@
         mIconResourceId = iconResourceId;
     }
 
-    /** @hide */
+    /**
+     * Get the resource ID for the icon, valid only when {@link #hasIconResource()} } is true.
+     */
     public int getIconResourceId() {
         return mIconResourceId;
     }
@@ -661,12 +726,15 @@
     private ShortcutInfo(Parcel source) {
         final ClassLoader cl = getClass().getClassLoader();
 
+        mUserId = source.readInt();
         mId = source.readString();
         mPackageName = source.readString();
         mActivityComponent = source.readParcelable(cl);
         mIcon = source.readParcelable(cl);
         mTitle = source.readString();
         mText = source.readString();
+        mCategories = new ArrayList<>();
+        source.readStringList(mCategories);
         mIntent = source.readParcelable(cl);
         mIntentPersistableExtras = source.readParcelable(cl);
         mWeight = source.readInt();
@@ -679,12 +747,14 @@
 
     @Override
     public void writeToParcel(Parcel dest, int flags) {
+        dest.writeInt(mUserId);
         dest.writeString(mId);
         dest.writeString(mPackageName);
         dest.writeParcelable(mActivityComponent, flags);
         dest.writeParcelable(mIcon, flags);
         dest.writeString(mTitle);
         dest.writeString(mText);
+        dest.writeStringList(mCategories);
         dest.writeParcelable(mIntent, flags);
         dest.writeParcelable(mIntentPersistableExtras, flags);
         dest.writeInt(mWeight);
@@ -749,6 +819,9 @@
         sb.append(", text=");
         sb.append(secure ? "***" : mText);
 
+        sb.append(", categories=");
+        sb.append(mCategories);
+
         sb.append(", icon=");
         sb.append(mIcon);
 
@@ -784,17 +857,20 @@
     }
 
     /** @hide */
-    public ShortcutInfo(String id, String packageName, ComponentName activityComponent,
-            Icon icon, String title, String text, Intent intent,
+    public ShortcutInfo(
+            @UserIdInt int userId, String id, String packageName, ComponentName activityComponent,
+            Icon icon, String title, String text, List<String> categories, Intent intent,
             PersistableBundle intentPersistableExtras,
             int weight, PersistableBundle extras, long lastChangedTimestamp,
             int flags, int iconResId, String bitmapPath) {
+        mUserId = userId;
         mId = id;
         mPackageName = packageName;
         mActivityComponent = activityComponent;
         mIcon = icon;
         mTitle = title;
         mText = text;
+        mCategories = clone(categories);
         mIntent = intent;
         mIntentPersistableExtras = intentPersistableExtras;
         mWeight = weight;
diff --git a/core/java/android/content/pm/ShortcutManager.java b/core/java/android/content/pm/ShortcutManager.java
index e4a98b5..75803d3 100644
--- a/core/java/android/content/pm/ShortcutManager.java
+++ b/core/java/android/content/pm/ShortcutManager.java
@@ -16,8 +16,11 @@
 package android.content.pm;
 
 import android.annotation.NonNull;
+import android.annotation.TestApi;
 import android.content.Context;
+import android.os.IBinder;
 import android.os.RemoteException;
+import android.os.ServiceManager;
 import android.os.UserHandle;
 
 import com.android.internal.annotations.VisibleForTesting;
@@ -31,11 +34,11 @@
  * <h3>Dynamic shortcuts and pinned shortcuts</h3>
  *
  * An application can publish shortcuts with {@link #setDynamicShortcuts(List)} and
- * {@link #addDynamicShortcut(ShortcutInfo)}.  There can be at most
+ * {@link #addDynamicShortcuts(List)}.  There can be at most
  * {@link #getMaxDynamicShortcutCount()} number of dynamic shortcuts at a time from the same
  * application.
- * A dynamic shortcut can be deleted with {@link #deleteDynamicShortcut(String)}, and apps
- * can also use {@link #deleteAllDynamicShortcuts()} to delete all dynamic shortcuts.
+ * A dynamic shortcut can be deleted with {@link #removeDynamicShortcuts(List)}, and apps
+ * can also use {@link #removeAllDynamicShortcuts()} to delete all dynamic shortcuts.
  *
  * <p>The shortcuts that are currently published by the above APIs are called "dynamic", because
  * they can be removed by the creator application at any time.  The user may "pin" dynamic shortcuts
@@ -58,11 +61,11 @@
  *
  * <h3>Rate limiting</h3>
  *
- * Calls to {@link #setDynamicShortcuts(List)}, {@link #addDynamicShortcut(ShortcutInfo)},
+ * Calls to {@link #setDynamicShortcuts(List)}, {@link #addDynamicShortcuts(List)},
  * and {@link #updateShortcuts(List)} will be
  * rate-limited.  An application can call these methods at most
  * {@link #getRemainingCallCount()} times until the rate-limiting counter is reset,
- * which happens at a certain time every day.
+ * which happens every hour.
  *
  * <p>An application can use {@link #getRateLimitResetTime()} to get the next reset time.
  *
@@ -97,6 +100,15 @@
     }
 
     /**
+     * @hide
+     */
+    @TestApi
+    public ShortcutManager(Context context) {
+        this(context, IShortcutService.Stub.asInterface(
+                ServiceManager.getService(Context.SHORTCUT_SERVICE)));
+    }
+
+    /**
      * Publish a list of shortcuts.  All existing dynamic shortcuts from the caller application
      * will be replaced.
      *
@@ -141,10 +153,10 @@
      * @throws IllegalArgumentException if the caller application has already published the
      * max number of dynamic shortcuts.
      */
-    public boolean addDynamicShortcut(@NonNull ShortcutInfo shortcutInfo) {
+    public boolean addDynamicShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) {
         try {
-            return mService.addDynamicShortcut(
-                    mContext.getPackageName(), shortcutInfo, injectMyUserId());
+            return mService.addDynamicShortcuts(mContext.getPackageName(),
+                    new ParceledListSlice(shortcutInfoList), injectMyUserId());
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
         }
@@ -153,9 +165,10 @@
     /**
      * Delete a single dynamic shortcut by ID.
      */
-    public void deleteDynamicShortcut(@NonNull String shortcutId) {
+    public void removeDynamicShortcuts(@NonNull List<String> shortcutIds) {
         try {
-            mService.deleteDynamicShortcut(mContext.getPackageName(), shortcutId, injectMyUserId());
+            mService.removeDynamicShortcuts(mContext.getPackageName(), shortcutIds,
+                    injectMyUserId());
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
         }
@@ -164,9 +177,9 @@
     /**
      * Delete all dynamic shortcuts from the caller application.
      */
-    public void deleteAllDynamicShortcuts() {
+    public void removeAllDynamicShortcuts() {
         try {
-            mService.deleteAllDynamicShortcuts(mContext.getPackageName(), injectMyUserId());
+            mService.removeAllDynamicShortcuts(mContext.getPackageName(), injectMyUserId());
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
         }
diff --git a/core/java/android/content/pm/ShortcutServiceInternal.java b/core/java/android/content/pm/ShortcutServiceInternal.java
index d57f2e6e..dc3d317 100644
--- a/core/java/android/content/pm/ShortcutServiceInternal.java
+++ b/core/java/android/content/pm/ShortcutServiceInternal.java
@@ -42,15 +42,10 @@
     public abstract List<ShortcutInfo>
             getShortcuts(int launcherUserId,
             @NonNull String callingPackage, long changedSince,
-            @Nullable String packageName, @Nullable ComponentName componentName,
-            @ShortcutQuery.QueryFlags int flags,
+            @Nullable String packageName, @Nullable List<String> shortcutIds,
+            @Nullable ComponentName componentName, @ShortcutQuery.QueryFlags int flags,
             int userId);
 
-    public abstract List<ShortcutInfo>
-            getShortcutInfo(int launcherUserId, @NonNull String callingPackage,
-            @NonNull String packageName, @Nullable List<String> ids, int userId);
-
-
     public abstract boolean
             isPinnedByCaller(int launcherUserId, @NonNull String callingPackage,
             @NonNull String packageName, @NonNull String id, int userId);
@@ -65,11 +60,11 @@
     public abstract void addListener(@NonNull ShortcutChangeListener listener);
 
     public abstract int getShortcutIconResId(int launcherUserId, @NonNull String callingPackage,
-            @NonNull ShortcutInfo shortcut, int userId);
+            @NonNull String packageName, @NonNull String shortcutId, int userId);
 
     public abstract ParcelFileDescriptor getShortcutIconFd(int launcherUserId,
             @NonNull String callingPackage,
-            @NonNull ShortcutInfo shortcut, int userId);
+            @NonNull String packageName, @NonNull String shortcutId, int userId);
 
     public abstract boolean hasShortcutHostPermission(int launcherUserId,
             @NonNull String callingPackage);
diff --git a/core/java/android/hardware/camera2/CameraDevice.java b/core/java/android/hardware/camera2/CameraDevice.java
index 6aacc9c..c54d1e1 100644
--- a/core/java/android/hardware/camera2/CameraDevice.java
+++ b/core/java/android/hardware/camera2/CameraDevice.java
@@ -438,7 +438,7 @@
      * @see #createCaptureSession
      * @see OutputConfiguration
      */
-    public abstract void createCaptureSessionByOutputConfiguration(
+    public abstract void createCaptureSessionByOutputConfigurations(
             List<OutputConfiguration> outputConfigurations,
             CameraCaptureSession.StateCallback callback, Handler handler)
             throws CameraAccessException;
@@ -627,7 +627,7 @@
      * @see OutputConfiguration
      *
      */
-    public abstract void createReprocessableCaptureSessionWithConfigurations(
+    public abstract void createReprocessableCaptureSessionByConfigurations(
             @NonNull InputConfiguration inputConfig,
             @NonNull List<OutputConfiguration> outputs,
             @NonNull CameraCaptureSession.StateCallback callback,
diff --git a/core/java/android/hardware/camera2/impl/CameraDeviceImpl.java b/core/java/android/hardware/camera2/impl/CameraDeviceImpl.java
index d2e820e..18a155d 100644
--- a/core/java/android/hardware/camera2/impl/CameraDeviceImpl.java
+++ b/core/java/android/hardware/camera2/impl/CameraDeviceImpl.java
@@ -493,7 +493,7 @@
     }
 
     @Override
-    public void createCaptureSessionByOutputConfiguration(
+    public void createCaptureSessionByOutputConfigurations(
             List<OutputConfiguration> outputConfigurations,
             CameraCaptureSession.StateCallback callback, Handler handler)
             throws CameraAccessException {
@@ -532,7 +532,7 @@
     }
 
     @Override
-    public void createReprocessableCaptureSessionWithConfigurations(InputConfiguration inputConfig,
+    public void createReprocessableCaptureSessionByConfigurations(InputConfiguration inputConfig,
             List<OutputConfiguration> outputs,
             android.hardware.camera2.CameraCaptureSession.StateCallback callback, Handler handler)
                     throws CameraAccessException {
diff --git a/core/java/android/hardware/location/NanoApp.java b/core/java/android/hardware/location/NanoApp.java
index c8f3439..03ac4a2 100644
--- a/core/java/android/hardware/location/NanoApp.java
+++ b/core/java/android/hardware/location/NanoApp.java
@@ -18,6 +18,7 @@
 import android.annotation.SystemApi;
 import android.os.Parcel;
 import android.os.Parcelable;
+import android.util.Log;
 
 /** A class describing nano apps.
  * A nano app is a piece of executable code that can be
@@ -31,10 +32,15 @@
  */
 @SystemApi
 public class NanoApp {
+    private final String TAG = "NanoApp";
+
+    private final String UNKNOWN = "Unknown";
+
     private String mPublisher;
     private String mName;
 
     private int mAppId;
+    private boolean mAppIdSet;
     private int mAppVersion;
 
     private int mNeededReadMemBytes;
@@ -45,7 +51,48 @@
     private int[] mOutputEvents;
     private byte[] mAppBinary;
 
+    /**
+     * If this version of the constructor is used, the methods
+     * {@link #setAppBinary(byte[])} and {@link #setAppId(int)} must be called
+     * prior to passing this object to any managers.
+     *
+     * @see #NanoApp(int, byte[])
+     */
     public NanoApp() {
+        this(0, null);
+        mAppIdSet = false;
+    }
+
+    /**
+     * Initialize a NanoApp with the given id and binary.
+     *
+     * While this sets defaults for other fields, users will want to provide
+     * other values for those fields in most cases.
+     *
+     * @see #setPublisher(String)
+     * @see #setName(String)
+     * @see #setAppVersion(int)
+     * @see #setNeededReadMemBytes(int)
+     * @see #setNeededWriteMemBytes(int)
+     * @see #setNeededExecMemBytes(int)
+     * @see #setNeededSensors(int[])
+     * @see #setOutputEvents(int[])
+     */
+    public NanoApp(int appId, byte[] appBinary) {
+        mPublisher = UNKNOWN;
+        mName = UNKNOWN;
+
+        mAppId = appId;
+        mAppIdSet = true;
+        mAppVersion = 0;
+
+        mNeededReadMemBytes = 0;
+        mNeededWriteMemBytes = 0;
+        mNeededExecMemBytes = 0;
+
+        mNeededSensors = new int[0];
+        mOutputEvents = new int[0];
+        mAppBinary = appBinary;
     }
 
     /**
@@ -73,6 +120,7 @@
      */
     public void setAppId(int appId) {
         mAppId = appId;
+        mAppIdSet = true;
     }
 
     /**
@@ -144,7 +192,7 @@
      * @return publisher name
      */
     public String getPublisher() {
-      return mPublisher;
+        return mPublisher;
     }
 
     /**
@@ -153,7 +201,7 @@
      * @return app name
      */
     public String getName() {
-    return mName;
+        return mName;
     }
 
     /**
@@ -162,7 +210,7 @@
      * @return identifier for this app
      */
     public int getAppId() {
-      return mAppId;
+        return mAppId;
     }
 
     /**
@@ -171,7 +219,7 @@
      * @return app version
      */
     public int getAppVersion() {
-      return mAppVersion;
+        return mAppVersion;
     }
 
     /**
@@ -180,7 +228,7 @@
      * @return readable memory needed in bytes
      */
     public int getNeededReadMemBytes() {
-      return mNeededReadMemBytes;
+        return mNeededReadMemBytes;
     }
 
     /**
@@ -189,7 +237,7 @@
      * @return writable memory needed in bytes
      */
     public int getNeededWriteMemBytes() {
-      return mNeededWriteMemBytes;
+        return mNeededWriteMemBytes;
     }
 
     /**
@@ -198,7 +246,7 @@
      * @return executable memory needed in bytes
      */
     public int getNeededExecMemBytes() {
-      return mNeededExecMemBytes;
+        return mNeededExecMemBytes;
     }
 
     /**
@@ -207,7 +255,7 @@
      * @return sensors needed
      */
     public int[] getNeededSensors() {
-      return mNeededSensors;
+        return mNeededSensors;
     }
 
     /**
@@ -216,7 +264,7 @@
      * @return generated events
      */
     public int[] getOutputEvents() {
-      return mOutputEvents;
+        return mOutputEvents;
     }
 
     /**
@@ -225,7 +273,7 @@
      * @return app binary
      */
     public byte[] getAppBinary() {
-      return mAppBinary;
+        return mAppBinary;
     }
 
     private NanoApp(Parcel in) {
@@ -256,6 +304,13 @@
     }
 
     public void writeToParcel(Parcel out, int flags) {
+        if (mAppBinary == null) {
+            throw new IllegalStateException("Must set non-null AppBinary for nanoapp " + mName);
+        }
+        if (!mAppIdSet) {
+            throw new IllegalStateException("Must set AppId for nanoapp " + mName);
+        }
+
         out.writeString(mPublisher);
         out.writeString(mName);
         out.writeInt(mAppId);
diff --git a/core/java/android/hardware/soundtrigger/KeyphraseEnrollmentInfo.java b/core/java/android/hardware/soundtrigger/KeyphraseEnrollmentInfo.java
index cc018e9..458c584 100644
--- a/core/java/android/hardware/soundtrigger/KeyphraseEnrollmentInfo.java
+++ b/core/java/android/hardware/soundtrigger/KeyphraseEnrollmentInfo.java
@@ -35,9 +35,11 @@
 import org.xmlpull.v1.XmlPullParserException;
 
 import java.io.IOException;
-import java.util.Arrays;
+import java.util.HashMap;
+import java.util.LinkedList;
 import java.util.List;
 import java.util.Locale;
+import java.util.Map;
 
 /**
  * Enrollment information about the different available keyphrases.
@@ -82,8 +84,16 @@
     public static final String EXTRA_VOICE_KEYPHRASE_LOCALE =
             "com.android.intent.extra.VOICE_KEYPHRASE_LOCALE";
 
-    private KeyphraseMetadata[] mKeyphrases;
-    private String mEnrollmentPackage;
+    /**
+     * List of available keyphrases.
+     */
+    final private KeyphraseMetadata[] mKeyphrases;
+
+    /**
+     * Map between KeyphraseMetadata and the package name of the enrollment app that provides it.
+     */
+    final private Map<KeyphraseMetadata, String> mKeyphrasePackageMap;
+
     private String mParseError;
 
     public KeyphraseEnrollmentInfo(PackageManager pm) {
@@ -94,15 +104,17 @@
                 new Intent(ACTION_MANAGE_VOICE_KEYPHRASES), PackageManager.MATCH_DEFAULT_ONLY);
         if (ris == null || ris.isEmpty()) {
             // No application capable of enrolling for voice keyphrases is present.
-            mParseError = "No enrollment application found";
+            mParseError = "No enrollment applications found";
+            mKeyphrasePackageMap = null;
+            mKeyphrases = null;
             return;
         }
 
-        boolean found = false;
-        ApplicationInfo ai = null;
+        List<String> parseErrors = new LinkedList<String>();
+        mKeyphrasePackageMap = new HashMap<KeyphraseMetadata, String>();
         for (ResolveInfo ri : ris) {
             try {
-                ai = pm.getApplicationInfo(
+                ApplicationInfo ai = pm.getApplicationInfo(
                         ri.activityInfo.packageName, PackageManager.GET_META_DATA);
                 if ((ai.privateFlags & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED) == 0) {
                     // The application isn't privileged (/system/priv-app).
@@ -116,27 +128,45 @@
                     Slog.w(TAG, ai.packageName + " does not require MANAGE_VOICE_KEYPHRASES");
                     continue;
                 }
-                mEnrollmentPackage = ai.packageName;
-                found = true;
-                break;
+
+                mKeyphrasePackageMap.put(
+                        getKeyphraseMetadataFromApplicationInfo(pm, ai, parseErrors),
+                        ai.packageName);
             } catch (PackageManager.NameNotFoundException e) {
-                Slog.w(TAG, "error parsing voice enrollment meta-data", e);
+                String error = "error parsing voice enrollment meta-data for "
+                        + ri.activityInfo.packageName;
+                parseErrors.add(error + ": " + e);
+                Slog.w(TAG, error, e);
             }
         }
 
-        if (!found) {
+        if (mKeyphrasePackageMap.isEmpty()) {
+            String error = "No suitable enrollment application found";
+            parseErrors.add(error);
+            Slog.w(TAG, error);
             mKeyphrases = null;
-            mParseError = "No suitable enrollment application found";
-            return;
+        } else {
+            mKeyphrases = mKeyphrasePackageMap.keySet().toArray(
+                    new KeyphraseMetadata[mKeyphrasePackageMap.size()]);
         }
 
+        if (!parseErrors.isEmpty()) {
+            mParseError = TextUtils.join("\n", parseErrors);
+        }
+    }
+
+    private KeyphraseMetadata getKeyphraseMetadataFromApplicationInfo(PackageManager pm,
+            ApplicationInfo ai, List<String> parseErrors) {
         XmlResourceParser parser = null;
+        String packageName = ai.packageName;
+        KeyphraseMetadata keyphraseMetadata = null;
         try {
             parser = ai.loadXmlMetaData(pm, VOICE_KEYPHRASE_META_DATA);
             if (parser == null) {
-                mParseError = "No " + VOICE_KEYPHRASE_META_DATA + " meta-data for "
-                        + ai.packageName;
-                return;
+                String error = "No " + VOICE_KEYPHRASE_META_DATA + " meta-data for " + packageName;
+                parseErrors.add(error);
+                Slog.w(TAG, error);
+                return null;
             }
 
             Resources res = pm.getResourcesForApplication(ai);
@@ -149,48 +179,55 @@
 
             String nodeName = parser.getName();
             if (!"voice-enrollment-application".equals(nodeName)) {
-                mParseError = "Meta-data does not start with voice-enrollment-application tag";
-                return;
+                String error = "Meta-data does not start with voice-enrollment-application tag for "
+                        + packageName;
+                parseErrors.add(error);
+                Slog.w(TAG, error);
+                return null;
             }
 
             TypedArray array = res.obtainAttributes(attrs,
                     com.android.internal.R.styleable.VoiceEnrollmentApplication);
-            initializeKeyphrasesFromTypedArray(array);
+            keyphraseMetadata = getKeyphraseFromTypedArray(array, packageName, parseErrors);
             array.recycle();
         } catch (XmlPullParserException e) {
-            mParseError = "Error parsing keyphrase enrollment meta-data: " + e;
-            Slog.w(TAG, "error parsing keyphrase enrollment meta-data", e);
-            return;
+            String error = "Error parsing keyphrase enrollment meta-data for " + packageName;
+            parseErrors.add(error + ": " + e);
+            Slog.w(TAG, error, e);
         } catch (IOException e) {
-            mParseError = "Error parsing keyphrase enrollment meta-data: " + e;
-            Slog.w(TAG, "error parsing keyphrase enrollment meta-data", e);
-            return;
+            String error = "Error parsing keyphrase enrollment meta-data for " + packageName;
+            parseErrors.add(error + ": " + e);
+            Slog.w(TAG, error, e);
         } catch (PackageManager.NameNotFoundException e) {
-            mParseError = "Error parsing keyphrase enrollment meta-data: " + e;
-            Slog.w(TAG, "error parsing keyphrase enrollment meta-data", e);
-            return;
+            String error = "Error parsing keyphrase enrollment meta-data for " + packageName;
+            parseErrors.add(error + ": " + e);
+            Slog.w(TAG, error, e);
         } finally {
             if (parser != null) parser.close();
         }
+        return keyphraseMetadata;
     }
 
-    private void initializeKeyphrasesFromTypedArray(TypedArray array) {
+    private KeyphraseMetadata getKeyphraseFromTypedArray(TypedArray array, String packageName,
+            List<String> parseErrors) {
         // Get the keyphrase ID.
         int searchKeyphraseId = array.getInt(
                 com.android.internal.R.styleable.VoiceEnrollmentApplication_searchKeyphraseId, -1);
         if (searchKeyphraseId <= 0) {
-            mParseError = "No valid searchKeyphraseId specified in meta-data";
-            Slog.w(TAG, mParseError);
-            return;
+            String error = "No valid searchKeyphraseId specified in meta-data for " + packageName;
+            parseErrors.add(error);
+            Slog.w(TAG, error);
+            return null;
         }
 
         // Get the keyphrase text.
         String searchKeyphrase = array.getString(
                 com.android.internal.R.styleable.VoiceEnrollmentApplication_searchKeyphrase);
         if (searchKeyphrase == null) {
-            mParseError = "No valid searchKeyphrase specified in meta-data";
-            Slog.w(TAG, mParseError);
-            return;
+            String error = "No valid searchKeyphrase specified in meta-data for " + packageName;
+            parseErrors.add(error);
+            Slog.w(TAG, error);
+            return null;
         }
 
         // Get the supported locales.
@@ -198,9 +235,11 @@
                 com.android.internal.R.styleable
                         .VoiceEnrollmentApplication_searchKeyphraseSupportedLocales);
         if (searchKeyphraseSupportedLocales == null) {
-            mParseError = "No valid searchKeyphraseSupportedLocales specified in meta-data";
-            Slog.w(TAG, mParseError);
-            return;
+            String error = "No valid searchKeyphraseSupportedLocales specified in meta-data for "
+                    + packageName;
+            parseErrors.add(error);
+            Slog.w(TAG, error);
+            return null;
         }
         ArraySet<Locale> locales = new ArraySet<>();
         // Try adding locales if the locale string is non-empty.
@@ -214,9 +253,11 @@
                 // We catch a generic exception here because we don't want the system service
                 // to be affected by a malformed metadata because invalid locales were specified
                 // by the system application.
-                mParseError = "Error reading searchKeyphraseSupportedLocales from meta-data";
-                Slog.w(TAG, mParseError, ex);
-                return;
+                String error = "Error reading searchKeyphraseSupportedLocales from meta-data for "
+                        + packageName;
+                parseErrors.add(error);
+                Slog.w(TAG, error);
+                return null;
             }
         }
 
@@ -224,13 +265,13 @@
         int recognitionModes = array.getInt(com.android.internal.R.styleable
                 .VoiceEnrollmentApplication_searchKeyphraseRecognitionFlags, -1);
         if (recognitionModes < 0) {
-            mParseError = "No valid searchKeyphraseRecognitionFlags specified in meta-data";
-            Slog.w(TAG, mParseError);
-            return;
+            String error = "No valid searchKeyphraseRecognitionFlags specified in meta-data for "
+                    + packageName;
+            parseErrors.add(error);
+            Slog.w(TAG, error);
+            return null;
         }
-        mKeyphrases = new KeyphraseMetadata[1];
-        mKeyphrases[0] = new KeyphraseMetadata(searchKeyphraseId, searchKeyphrase, locales,
-                recognitionModes);
+        return new KeyphraseMetadata(searchKeyphraseId, searchKeyphrase, locales, recognitionModes);
     }
 
     public String getParseError() {
@@ -259,14 +300,15 @@
      *         given keyphrase/locale combination isn't possible.
      */
     public Intent getManageKeyphraseIntent(int action, String keyphrase, Locale locale) {
-        if (mEnrollmentPackage == null || mEnrollmentPackage.isEmpty()) {
+        if (mKeyphrasePackageMap == null || mKeyphrasePackageMap.isEmpty()) {
             Slog.w(TAG, "No enrollment application exists");
             return null;
         }
 
-        if (getKeyphraseMetadata(keyphrase, locale) != null) {
+        KeyphraseMetadata keyphraseMetadata = getKeyphraseMetadata(keyphrase, locale);
+        if (keyphraseMetadata != null) {
             Intent intent = new Intent(ACTION_MANAGE_VOICE_KEYPHRASES)
-                    .setPackage(mEnrollmentPackage)
+                    .setPackage(mKeyphrasePackageMap.get(keyphraseMetadata))
                     .putExtra(EXTRA_VOICE_KEYPHRASE_HINT_TEXT, keyphrase)
                     .putExtra(EXTRA_VOICE_KEYPHRASE_LOCALE, locale.toLanguageTag())
                     .putExtra(EXTRA_VOICE_KEYPHRASE_ACTION, action);
@@ -298,14 +340,13 @@
                 return keyphraseMetadata;
             }
         }
-        Slog.w(TAG, "Enrollment application doesn't support the given keyphrase/locale");
+        Slog.w(TAG, "No Enrollment application supports the given keyphrase/locale");
         return null;
     }
 
     @Override
     public String toString() {
-        return "KeyphraseEnrollmentInfo [Keyphrases=" + Arrays.toString(mKeyphrases)
-                + ", EnrollmentPackage=" + mEnrollmentPackage + ", ParseError=" + mParseError
-                + "]";
+        return "KeyphraseEnrollmentInfo [Keyphrases=" + mKeyphrasePackageMap.toString()
+                + ", ParseError=" + mParseError + "]";
     }
 }
diff --git a/core/java/android/inputmethodservice/CompactExtractEditLayout.java b/core/java/android/inputmethodservice/CompactExtractEditLayout.java
new file mode 100644
index 0000000..35c54b2
--- /dev/null
+++ b/core/java/android/inputmethodservice/CompactExtractEditLayout.java
@@ -0,0 +1,118 @@
+/*
+ * 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.inputmethodservice;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.annotation.FractionRes;
+import android.util.AttributeSet;
+import android.util.DisplayMetrics;
+import android.view.Gravity;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.LinearLayout;
+
+/**
+ * A special purpose layout for the editor extract view for tiny (sub 250dp) screens.
+ * The layout is based on sizes proportional to screen pixel size to provide for the
+ * best layout fidelity on varying pixel sizes and densities.
+ *
+ * @hide
+ */
+public class CompactExtractEditLayout extends LinearLayout {
+    private View mInputExtractEditText;
+    private View mInputExtractAccessories;
+    private View mInputExtractAction;
+    private boolean mPerformLayoutChanges;
+
+    public CompactExtractEditLayout(Context context) {
+        super(context);
+    }
+
+    public CompactExtractEditLayout(Context context, AttributeSet attrs) {
+        super(context, attrs);
+    }
+
+    public CompactExtractEditLayout(Context context, AttributeSet attrs, int defStyleAttr) {
+        super(context, attrs, defStyleAttr);
+    }
+
+    @Override
+    protected void onFinishInflate() {
+        super.onFinishInflate();
+        mInputExtractEditText = findViewById(com.android.internal.R.id.inputExtractEditText);
+        mInputExtractAccessories = findViewById(com.android.internal.R.id.inputExtractAccessories);
+        mInputExtractAction = findViewById(com.android.internal.R.id.inputExtractAction);
+
+        if (mInputExtractEditText != null && mInputExtractAccessories != null
+                && mInputExtractAction != null) {
+            mPerformLayoutChanges = true;
+        }
+    }
+
+    private int applyFractionInt(@FractionRes int fraction, int whole) {
+        return Math.round(getResources().getFraction(fraction, whole, whole));
+    }
+
+    private static void setLayoutHeight(View v, int px) {
+        ViewGroup.LayoutParams lp = v.getLayoutParams();
+        lp.height = px;
+        v.setLayoutParams(lp);
+    }
+
+    private static void setLayoutMarginBottom(View v, int px) {
+        ViewGroup.MarginLayoutParams lp = (MarginLayoutParams) v.getLayoutParams();
+        lp.bottomMargin = px;
+        v.setLayoutParams(lp);
+    }
+
+    private void applyProportionalLayout(int screenWidthPx, int screenHeightPx) {
+        if (getResources().getConfiguration().isScreenRound()) {
+            setGravity(Gravity.BOTTOM);
+        }
+        setLayoutHeight(this, applyFractionInt(
+                com.android.internal.R.fraction.input_extract_layout_height, screenHeightPx));
+
+        setPadding(
+                applyFractionInt(com.android.internal.R.fraction.input_extract_layout_padding_left,
+                        screenWidthPx),
+                0,
+                applyFractionInt(com.android.internal.R.fraction.input_extract_layout_padding_right,
+                        screenWidthPx),
+                0);
+
+        setLayoutMarginBottom(mInputExtractEditText,
+                applyFractionInt(com.android.internal.R.fraction.input_extract_text_margin_bottom,
+                        screenHeightPx));
+
+        setLayoutMarginBottom(mInputExtractAccessories,
+                applyFractionInt(com.android.internal.R.fraction.input_extract_action_margin_bottom,
+                        screenHeightPx));
+    }
+
+    @Override
+    protected void onAttachedToWindow() {
+        super.onAttachedToWindow();
+        if (mPerformLayoutChanges) {
+            Resources res = getResources();
+            DisplayMetrics dm = res.getDisplayMetrics();
+            int heightPixels = dm.heightPixels;
+            int widthPixels = dm.widthPixels;
+            applyProportionalLayout(widthPixels, heightPixels);
+        }
+    }
+}
diff --git a/core/java/android/inputmethodservice/InputMethodService.java b/core/java/android/inputmethodservice/InputMethodService.java
index cc201bc..085b97c 100644
--- a/core/java/android/inputmethodservice/InputMethodService.java
+++ b/core/java/android/inputmethodservice/InputMethodService.java
@@ -68,9 +68,10 @@
 import android.view.inputmethod.InputMethod;
 import android.view.inputmethod.InputMethodManager;
 import android.view.inputmethod.InputMethodSubtype;
-import android.widget.Button;
 import android.widget.FrameLayout;
+import android.widget.ImageButton;
 import android.widget.LinearLayout;
+import android.widget.TextView;
 
 import java.io.FileDescriptor;
 import java.io.PrintWriter;
@@ -302,7 +303,7 @@
     boolean mExtractViewHidden;
     ExtractEditText mExtractEditText;
     ViewGroup mExtractAccessories;
-    Button mExtractAction;
+    View mExtractAction;
     ExtractedText mExtractedText;
     int mExtractedToken;
     
@@ -1344,7 +1345,7 @@
             mExtractEditText = (ExtractEditText)view.findViewById(
                     com.android.internal.R.id.inputExtractEditText);
             mExtractEditText.setIME(this);
-            mExtractAction = (Button)view.findViewById(
+            mExtractAction = view.findViewById(
                     com.android.internal.R.id.inputExtractAction);
             if (mExtractAction != null) {
                 mExtractAccessories = (ViewGroup)view.findViewById(
@@ -2408,7 +2409,35 @@
                 return getText(com.android.internal.R.string.ime_action_default);
         }
     }
-    
+
+    /**
+     * Return a drawable resource id that can be used as a button icon for the given
+     * {@link EditorInfo#imeOptions EditorInfo.imeOptions}.
+     *
+     * @param imeOptions The value from @link EditorInfo#imeOptions EditorInfo.imeOptions}.
+     *
+     * @return Returns a drawable resource id to use.
+     */
+    @DrawableRes
+    private int getIconForImeAction(int imeOptions) {
+        switch (imeOptions&EditorInfo.IME_MASK_ACTION) {
+            case EditorInfo.IME_ACTION_GO:
+                return com.android.internal.R.drawable.ic_input_extract_action_go;
+            case EditorInfo.IME_ACTION_SEARCH:
+                return com.android.internal.R.drawable.ic_input_extract_action_search;
+            case EditorInfo.IME_ACTION_SEND:
+                return com.android.internal.R.drawable.ic_input_extract_action_send;
+            case EditorInfo.IME_ACTION_NEXT:
+                return com.android.internal.R.drawable.ic_input_extract_action_next;
+            case EditorInfo.IME_ACTION_DONE:
+                return com.android.internal.R.drawable.ic_input_extract_action_done;
+            case EditorInfo.IME_ACTION_PREVIOUS:
+                return com.android.internal.R.drawable.ic_input_extract_action_previous;
+            default:
+                return com.android.internal.R.drawable.ic_input_extract_action_return;
+        }
+    }
+
     /**
      * Called when the fullscreen-mode extracting editor info has changed,
      * to determine whether the extracting (extract text and candidates) portion
@@ -2459,10 +2488,20 @@
         if (hasAction) {
             mExtractAccessories.setVisibility(View.VISIBLE);
             if (mExtractAction != null) {
-                if (ei.actionLabel != null) {
-                    mExtractAction.setText(ei.actionLabel);
+                if (mExtractAction instanceof ImageButton) {
+                    ((ImageButton) mExtractAction)
+                            .setImageResource(getIconForImeAction(ei.imeOptions));
+                    if (ei.actionLabel != null) {
+                        mExtractAction.setContentDescription(ei.actionLabel);
+                    } else {
+                        mExtractAction.setContentDescription(getTextForImeAction(ei.imeOptions));
+                    }
                 } else {
-                    mExtractAction.setText(getTextForImeAction(ei.imeOptions));
+                    if (ei.actionLabel != null) {
+                        ((TextView) mExtractAction).setText(ei.actionLabel);
+                    } else {
+                        ((TextView) mExtractAction).setText(getTextForImeAction(ei.imeOptions));
+                    }
                 }
                 mExtractAction.setOnClickListener(mActionClickListener);
             }
diff --git a/core/java/android/net/NetworkIdentity.java b/core/java/android/net/NetworkIdentity.java
index a9de23e..9cd563e 100644
--- a/core/java/android/net/NetworkIdentity.java
+++ b/core/java/android/net/NetworkIdentity.java
@@ -55,19 +55,22 @@
     final String mSubscriberId;
     final String mNetworkId;
     final boolean mRoaming;
+    final boolean mMetered;
 
     public NetworkIdentity(
-            int type, int subType, String subscriberId, String networkId, boolean roaming) {
+            int type, int subType, String subscriberId, String networkId, boolean roaming,
+            boolean metered) {
         mType = type;
         mSubType = COMBINE_SUBTYPE_ENABLED ? SUBTYPE_COMBINED : subType;
         mSubscriberId = subscriberId;
         mNetworkId = networkId;
         mRoaming = roaming;
+        mMetered = metered;
     }
 
     @Override
     public int hashCode() {
-        return Objects.hash(mType, mSubType, mSubscriberId, mNetworkId, mRoaming);
+        return Objects.hash(mType, mSubType, mSubscriberId, mNetworkId, mRoaming, mMetered);
     }
 
     @Override
@@ -76,7 +79,8 @@
             final NetworkIdentity ident = (NetworkIdentity) obj;
             return mType == ident.mType && mSubType == ident.mSubType && mRoaming == ident.mRoaming
                     && Objects.equals(mSubscriberId, ident.mSubscriberId)
-                    && Objects.equals(mNetworkId, ident.mNetworkId);
+                    && Objects.equals(mNetworkId, ident.mNetworkId)
+                    && mMetered == ident.mMetered;
         }
         return false;
     }
@@ -102,6 +106,7 @@
         if (mRoaming) {
             builder.append(", ROAMING");
         }
+        builder.append(", metered=").append(mMetered);
         return builder.append("}").toString();
     }
 
@@ -125,6 +130,10 @@
         return mRoaming;
     }
 
+    public boolean getMetered() {
+        return mMetered;
+    }
+
     /**
      * Scrub given IMSI on production builds.
      */
@@ -162,6 +171,7 @@
         String subscriberId = null;
         String networkId = null;
         boolean roaming = false;
+        boolean metered = false;
 
         if (isNetworkTypeMobile(type)) {
             if (state.subscriberId == null) {
@@ -171,6 +181,9 @@
             subscriberId = state.subscriberId;
             roaming = state.networkInfo.isRoaming();
 
+            metered = !state.networkCapabilities.hasCapability(
+                    NetworkCapabilities.NET_CAPABILITY_NOT_METERED);
+
         } else if (type == TYPE_WIFI) {
             if (state.networkId != null) {
                 networkId = state.networkId;
@@ -182,7 +195,7 @@
             }
         }
 
-        return new NetworkIdentity(type, subType, subscriberId, networkId, roaming);
+        return new NetworkIdentity(type, subType, subscriberId, networkId, roaming, metered);
     }
 
     @Override
@@ -200,6 +213,9 @@
         if (res == 0) {
             res = Boolean.compare(mRoaming, another.mRoaming);
         }
+        if (res == 0) {
+            res = Boolean.compare(mMetered, another.mMetered);
+        }
         return res;
     }
 }
diff --git a/core/java/android/net/NetworkTemplate.java b/core/java/android/net/NetworkTemplate.java
index b32b2cc..caf7982 100644
--- a/core/java/android/net/NetworkTemplate.java
+++ b/core/java/android/net/NetworkTemplate.java
@@ -19,6 +19,7 @@
 import static android.net.ConnectivityManager.TYPE_BLUETOOTH;
 import static android.net.ConnectivityManager.TYPE_ETHERNET;
 import static android.net.ConnectivityManager.TYPE_PROXY;
+import static android.net.ConnectivityManager.TYPE_MOBILE;
 import static android.net.ConnectivityManager.TYPE_WIFI;
 import static android.net.ConnectivityManager.TYPE_WIFI_P2P;
 import static android.net.ConnectivityManager.TYPE_WIMAX;
@@ -30,9 +31,6 @@
 import static android.telephony.TelephonyManager.NETWORK_CLASS_UNKNOWN;
 import static android.telephony.TelephonyManager.getNetworkClass;
 
-import static com.android.internal.util.ArrayUtils.contains;
-
-import android.content.res.Resources;
 import android.os.Parcel;
 import android.os.Parcelable;
 import android.util.BackupUtils;
@@ -71,16 +69,6 @@
     public static final int MATCH_BLUETOOTH = 8;
     public static final int MATCH_PROXY = 9;
 
-    /**
-     * Set of {@link NetworkInfo#getType()} that reflect data usage.
-     */
-    private static final int[] DATA_USAGE_NETWORK_TYPES;
-
-    static {
-        DATA_USAGE_NETWORK_TYPES = Resources.getSystem().getIntArray(
-                com.android.internal.R.array.config_data_usage_network_types);
-    }
-
     private static boolean sForceAllNetworkTypes = false;
 
     @VisibleForTesting
@@ -318,9 +306,8 @@
             // TODO: consider matching against WiMAX subscriber identity
             return true;
         } else {
-            final boolean matchesType = (sForceAllNetworkTypes
-                    || contains(DATA_USAGE_NETWORK_TYPES, ident.mType));
-            return matchesType && !ArrayUtils.isEmpty(mMatchSubscriberIds)
+            return (sForceAllNetworkTypes || (ident.mType == TYPE_MOBILE && ident.mMetered))
+                    && !ArrayUtils.isEmpty(mMatchSubscriberIds)
                     && ArrayUtils.contains(mMatchSubscriberIds, ident.mSubscriberId);
         }
     }
@@ -389,7 +376,7 @@
         if (ident.mType == TYPE_WIMAX) {
             return true;
         } else {
-            return sForceAllNetworkTypes || contains(DATA_USAGE_NETWORK_TYPES, ident.mType);
+            return sForceAllNetworkTypes || (ident.mType == TYPE_MOBILE && ident.mMetered);
         }
     }
 
diff --git a/core/java/android/net/http/X509TrustManagerExtensions.java b/core/java/android/net/http/X509TrustManagerExtensions.java
index 6729347..87a0b70 100644
--- a/core/java/android/net/http/X509TrustManagerExtensions.java
+++ b/core/java/android/net/http/X509TrustManagerExtensions.java
@@ -44,6 +44,7 @@
     private final X509TrustManager mTrustManager;
     private final Method mCheckServerTrusted;
     private final Method mIsUserAddedCertificate;
+    private final Method mIsSameTrustConfiguration;
 
     /**
      * Constructs a new X509TrustManagerExtensions wrapper.
@@ -57,6 +58,7 @@
             mTrustManager = null;
             mCheckServerTrusted = null;
             mIsUserAddedCertificate = null;
+            mIsSameTrustConfiguration = null;
             return;
         }
         // Use duck typing if possible.
@@ -80,6 +82,15 @@
             throw new IllegalArgumentException(
                     "Required method isUserAddedCertificate(X509Certificate) missing");
         }
+        // Get the option isSameTrustConfiguration method.
+        Method isSameTrustConfiguration = null;
+        try {
+            isSameTrustConfiguration = tm.getClass().getMethod("isSameTrustConfiguration",
+                    String.class,
+                    String.class);
+        } catch (ReflectiveOperationException ignored) {
+        }
+        mIsSameTrustConfiguration = isSameTrustConfiguration;
     }
 
     /**
@@ -150,6 +161,19 @@
      */
     @SystemApi
     public boolean isSameTrustConfiguration(String hostname1, String hostname2) {
-        return true;
+        if (mIsSameTrustConfiguration == null) {
+            return true;
+        }
+        try {
+            return (Boolean) mIsSameTrustConfiguration.invoke(mTrustManager, hostname1, hostname2);
+        } catch (IllegalAccessException e) {
+            throw new RuntimeException("Failed to call isSameTrustConfiguration", e);
+        } catch (InvocationTargetException e) {
+            if (e.getCause() instanceof RuntimeException) {
+                throw (RuntimeException) e.getCause();
+            } else {
+                throw new RuntimeException("isSameTrustConfiguration failed", e.getCause());
+            }
+        }
     }
 }
diff --git a/core/java/android/os/BatteryManager.java b/core/java/android/os/BatteryManager.java
index e40ebf7..d39968a 100644
--- a/core/java/android/os/BatteryManager.java
+++ b/core/java/android/os/BatteryManager.java
@@ -115,6 +115,13 @@
      */
     public static final String EXTRA_MAX_CHARGING_VOLTAGE = "max_charging_voltage";
 
+    /**
+     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
+     * integer containing the charge counter present in the battery.
+     * {@hide}
+     */
+     public static final String EXTRA_CHARGE_COUNTER = "charge_counter";
+
     // values for "status" field in the ACTION_BATTERY_CHANGED Intent
     public static final int BATTERY_STATUS_UNKNOWN = 1;
     public static final int BATTERY_STATUS_CHARGING = 2;
diff --git a/core/java/android/os/BatteryProperties.java b/core/java/android/os/BatteryProperties.java
index c3e0f24..b509d76 100644
--- a/core/java/android/os/BatteryProperties.java
+++ b/core/java/android/os/BatteryProperties.java
@@ -30,6 +30,7 @@
     public int batteryLevel;
     public int batteryVoltage;
     public int batteryTemperature;
+    public int batteryChargeCounter;
     public String batteryTechnology;
 
     public BatteryProperties() {
@@ -47,6 +48,7 @@
         batteryLevel = other.batteryLevel;
         batteryVoltage = other.batteryVoltage;
         batteryTemperature = other.batteryTemperature;
+        batteryChargeCounter = other.batteryChargeCounter;
         batteryTechnology = other.batteryTechnology;
     }
 
@@ -67,6 +69,7 @@
         batteryLevel = p.readInt();
         batteryVoltage = p.readInt();
         batteryTemperature = p.readInt();
+        batteryChargeCounter = p.readInt();
         batteryTechnology = p.readString();
     }
 
@@ -82,6 +85,7 @@
         p.writeInt(batteryLevel);
         p.writeInt(batteryVoltage);
         p.writeInt(batteryTemperature);
+        p.writeInt(batteryChargeCounter);
         p.writeString(batteryTechnology);
     }
 
diff --git a/core/java/android/os/BatteryStats.java b/core/java/android/os/BatteryStats.java
index c452837..773e7dd 100644
--- a/core/java/android/os/BatteryStats.java
+++ b/core/java/android/os/BatteryStats.java
@@ -3094,14 +3094,8 @@
             dumpControllerActivityLine(pw, uid, category, WIFI_CONTROLLER_DATA,
                     u.getWifiControllerActivity(), which);
 
-            // Dump Bluetooth scan data, per UID.
-            final long bleScanTimeUs = u.getBluetoothScanTimer().getTotalTimeLocked(
+            dumpTimer(pw, uid, category, BLUETOOTH_MISC_DATA, u.getBluetoothScanTimer(),
                     rawRealtime, which);
-            final int bleScanCount = u.getBluetoothScanTimer().getCountLocked(which);
-            if (bleScanTimeUs != 0 || bleScanCount != 0) {
-                dumpLine(pw, uid, category, BLUETOOTH_MISC_DATA,
-                        bleScanTimeUs / 1000, bleScanCount);
-            }
 
             dumpControllerActivityLine(pw, uid, category, BLUETOOTH_CONTROLLER_DATA,
                     u.getBluetoothControllerActivity(), which);
diff --git a/core/java/android/os/IUserManager.aidl b/core/java/android/os/IUserManager.aidl
index c38bf3c..67d3959 100644
--- a/core/java/android/os/IUserManager.aidl
+++ b/core/java/android/os/IUserManager.aidl
@@ -45,6 +45,7 @@
     UserInfo getPrimaryUser();
     List<UserInfo> getUsers(boolean excludeDying);
     List<UserInfo> getProfiles(int userHandle, boolean enabledOnly);
+    int[] getProfileIds(int userId, boolean enabledOnly);
     boolean canAddMoreManagedProfiles(int userHandle, boolean allowedToRemoveOne);
     UserInfo getProfileParent(int userHandle);
     boolean isSameProfileGroup(int userHandle, int otherUserHandle);
diff --git a/core/java/android/os/UserManager.java b/core/java/android/os/UserManager.java
index 707d5f5..d5b3b35 100644
--- a/core/java/android/os/UserManager.java
+++ b/core/java/android/os/UserManager.java
@@ -1590,18 +1590,46 @@
      * @return A non-empty list of UserHandles associated with the calling user.
      */
     public List<UserHandle> getUserProfiles() {
-        ArrayList<UserHandle> profiles = new ArrayList<UserHandle>();
-        List<UserInfo> users;
+        int[] userIds = getProfileIds(UserHandle.myUserId(), true /* enabledOnly */);
+        List<UserHandle> result = new ArrayList<>(userIds.length);
+        for (int userId : userIds) {
+            result.add(UserHandle.of(userId));
+        }
+        return result;
+    }
+
+    /**
+     * Returns a list of ids for profiles associated with the specified user including the user
+     * itself.
+     *
+     * @param userId      id of the user to return profiles for
+     * @param enabledOnly whether return only {@link UserInfo#isEnabled() enabled} profiles
+     * @return A non-empty list of ids of profiles associated with the specified user.
+     *
+     * @hide
+     */
+    public int[] getProfileIds(@UserIdInt int userId, boolean enabledOnly) {
         try {
-            users = mService.getProfiles(UserHandle.myUserId(), true /* enabledOnly */);
+            return mService.getProfileIds(userId, enabledOnly);
         } catch (RemoteException re) {
             throw re.rethrowFromSystemServer();
         }
-        for (UserInfo info : users) {
-            UserHandle userHandle = new UserHandle(info.id);
-            profiles.add(userHandle);
-        }
-        return profiles;
+    }
+
+    /**
+     * @see #getProfileIds(int, boolean)
+     * @hide
+     */
+    public int[] getProfileIdsWithDisabled(@UserIdInt int userId) {
+        return getProfileIds(userId, false /* enabledOnly */);
+    }
+
+    /**
+     * @see #getProfileIds(int, boolean)
+     * @hide
+     */
+    public int[] getEnabledProfileIds(@UserIdInt int userId) {
+        return getProfileIds(userId, true /* enabledOnly */);
     }
 
     /**
diff --git a/core/java/android/os/storage/StorageManager.java b/core/java/android/os/storage/StorageManager.java
index ece1228..da215c6 100644
--- a/core/java/android/os/storage/StorageManager.java
+++ b/core/java/android/os/storage/StorageManager.java
@@ -824,7 +824,9 @@
         }
     }
 
-    /** {@hide} */
+    /**
+     * Return the {@link StorageVolume} that contains the given file, or {@code null} if none.
+     */
     public @Nullable StorageVolume getStorageVolume(File file) {
         return getStorageVolume(getVolumeList(), file);
     }
@@ -836,9 +838,13 @@
 
     /** {@hide} */
     private static @Nullable StorageVolume getStorageVolume(StorageVolume[] volumes, File file) {
+        if (file == null) {
+            return null;
+        }
         try {
             file = file.getCanonicalFile();
         } catch (IOException ignored) {
+            Slog.d(TAG, "Could not get canonical path for " + file);
             return null;
         }
         for (StorageVolume volume : volumes) {
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index 2a3c3fe..db5b07a 100755
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -1581,6 +1581,8 @@
     public static final class System extends NameValueTable {
         public static final String SYS_PROP_SETTING_VERSION = "sys.settings_system_version";
 
+        private static final float DEFAULT_FONT_SCALE = 1.0f;
+
         /** @hide */
         public static interface Validator {
             public boolean validate(String value);
@@ -2089,9 +2091,9 @@
         public static void getConfigurationForUser(ContentResolver cr, Configuration outConfig,
                 int userHandle) {
             outConfig.fontScale = Settings.System.getFloatForUser(
-                cr, FONT_SCALE, outConfig.fontScale, userHandle);
+                    cr, FONT_SCALE, DEFAULT_FONT_SCALE, userHandle);
             if (outConfig.fontScale < 0) {
-                outConfig.fontScale = 1;
+                outConfig.fontScale = DEFAULT_FONT_SCALE;
             }
             outConfig.setLocales(LocaleList.forLanguageTags(
                     Settings.System.getStringForUser(cr, SYSTEM_LOCALES, userHandle)));
@@ -6666,6 +6668,17 @@
        public static final String DEVICE_PROVISIONED = "device_provisioned";
 
        /**
+        * Whether mobile data should be allowed while the device is being provisioned.
+        * This allows the provisioning process to turn off mobile data before the user
+        * has an opportunity to set things up, preventing other processes from burning
+        * precious bytes before wifi is setup.
+        * (0 = false, 1 = true)
+        * @hide
+        */
+       public static final String DEVICE_PROVISIONING_MOBILE_DATA_ENABLED =
+               "device_provisioning_mobile_data";
+
+       /**
         * The saved value for WindowManagerService.setForcedDisplaySize().
         * Two integers separated by a comma.  If unset, then use the real display size.
         * @hide
@@ -7782,13 +7795,13 @@
          * ShortcutManager specific settings.
          * This is encoded as a key=value list, separated by commas. Ex:
          *
-         * "reset_interval_sec=86400,max_daily_updates=5"
+         * "reset_interval_sec=86400,max_updates_per_interval=1"
          *
          * The following keys are supported:
          *
          * <pre>
          * reset_interval_sec              (long)
-         * max_daily_updates               (int)
+         * max_updates_per_interval        (int)
          * max_icon_dimension_dp           (int, DP)
          * max_icon_dimension_dp_lowram    (int, DP)
          * max_shortcuts                   (int)
diff --git a/core/java/android/security/net/config/RootTrustManager.java b/core/java/android/security/net/config/RootTrustManager.java
index 19f6887..859e022 100644
--- a/core/java/android/security/net/config/RootTrustManager.java
+++ b/core/java/android/security/net/config/RootTrustManager.java
@@ -148,4 +148,15 @@
         NetworkSecurityConfig config = mConfig.getConfigForHostname("");
         return config.getTrustManager().getAcceptedIssuers();
     }
+
+    /**
+     * Returns {@code true} if this trust manager uses the same trust configuration for the provided
+     * hostnames.
+     *
+     * <p>This is required by android.net.http.X509TrustManagerExtensions.
+     */
+    public boolean isSameTrustConfiguration(String hostname1, String hostname2) {
+        return mConfig.getConfigForHostname(hostname1)
+                .equals(mConfig.getConfigForHostname(hostname2));
+    }
 }
diff --git a/core/java/android/service/notification/Adjustment.aidl b/core/java/android/service/notification/Adjustment.aidl
new file mode 100644
index 0000000..8bd814a
--- /dev/null
+++ b/core/java/android/service/notification/Adjustment.aidl
@@ -0,0 +1,19 @@
+/*
+ * 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.service.notification;
+
+parcelable Adjustment;
\ No newline at end of file
diff --git a/core/java/android/service/notification/Adjustment.java b/core/java/android/service/notification/Adjustment.java
new file mode 100644
index 0000000..2e4f48d
--- /dev/null
+++ b/core/java/android/service/notification/Adjustment.java
@@ -0,0 +1,150 @@
+/*
+ * 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.service.notification;
+
+import android.annotation.SystemApi;
+import android.net.Uri;
+import android.os.Bundle;
+import android.os.Parcel;
+import android.os.Parcelable;
+
+/**
+ * Ranking updates from the Ranker.
+ *
+ * @hide
+ */
+@SystemApi
+public final class Adjustment implements Parcelable {
+    private final String mPackage;
+    private final String mKey;
+    private final int mImportance;
+    private final CharSequence mExplanation;
+    private final Uri mReference;
+    private final Bundle mSignals;
+
+    public static final String GROUP_KEY_OVERRIDE_KEY = "group_key_override";
+    public static final String NEEDS_AUTOGROUPING_KEY = "autogroup_needed";
+
+    /**
+     * Create a notification adjustment.
+     *
+     * @param pkg The package of the notification.
+     * @param key The notification key.
+     * @param importance The recommended importance of the notification.
+     * @param signals A bundle of signals that should inform notification grouping and ordering.
+     * @param explanation A human-readable justification for the adjustment.
+     * @param reference A reference to an external object that augments the
+     *                  explanation, such as a
+     *                  {@link android.provider.ContactsContract.Contacts#CONTENT_LOOKUP_URI},
+     *                  or null.
+     */
+    public Adjustment(String pkg, String key, int importance, Bundle signals,
+            CharSequence explanation, Uri reference) {
+        mPackage = pkg;
+        mKey = key;
+        mImportance = importance;
+        mSignals = signals;
+        mExplanation = explanation;
+        mReference = reference;
+    }
+
+    protected Adjustment(Parcel in) {
+        if (in.readInt() == 1) {
+            mPackage = in.readString();
+        } else {
+            mPackage = null;
+        }
+        if (in.readInt() == 1) {
+            mKey = in.readString();
+        } else {
+            mKey = null;
+        }
+        mImportance = in.readInt();
+        if (in.readInt() == 1) {
+            mExplanation = in.readCharSequence();
+        } else {
+            mExplanation = null;
+        }
+        mReference = in.readParcelable(Uri.class.getClassLoader());
+        mSignals = in.readBundle();
+    }
+
+    public static final Creator<Adjustment> CREATOR = new Creator<Adjustment>() {
+        @Override
+        public Adjustment createFromParcel(Parcel in) {
+            return new Adjustment(in);
+        }
+
+        @Override
+        public Adjustment[] newArray(int size) {
+            return new Adjustment[size];
+        }
+    };
+
+    public String getPackage() {
+        return mPackage;
+    }
+
+    public String getKey() {
+        return mKey;
+    }
+
+    public int getImportance() {
+        return mImportance;
+    }
+
+    public CharSequence getExplanation() {
+        return mExplanation;
+    }
+
+    public Uri getReference() {
+        return mReference;
+    }
+
+    public Bundle getSignals() {
+        return mSignals;
+    }
+
+    @Override
+    public int describeContents() {
+        return 0;
+    }
+
+    @Override
+    public void writeToParcel(Parcel dest, int flags) {
+        if (mPackage != null) {
+            dest.writeInt(1);
+            dest.writeString(mPackage);
+        } else {
+            dest.writeInt(0);
+        }
+        if (mKey != null) {
+            dest.writeInt(1);
+            dest.writeString(mKey);
+        } else {
+            dest.writeInt(0);
+        }
+        dest.writeInt(mImportance);
+        if (mExplanation != null) {
+            dest.writeInt(1);
+            dest.writeCharSequence(mExplanation);
+        } else {
+            dest.writeInt(0);
+        }
+        dest.writeParcelable(mReference, flags);
+        dest.writeBundle(mSignals);
+    }
+}
diff --git a/core/java/android/service/notification/NotificationListenerService.java b/core/java/android/service/notification/NotificationListenerService.java
index 7325aef..e708b0a 100644
--- a/core/java/android/service/notification/NotificationListenerService.java
+++ b/core/java/android/service/notification/NotificationListenerService.java
@@ -123,6 +123,16 @@
      * This does not change the interruption filter, only the effects. **/
     public static final int HINT_HOST_DISABLE_EFFECTS = 1;
 
+    /** {@link #getCurrentListenerHints() Listener hints} constant - the primary device UI
+     * should disable notification sound, but not phone calls.
+     * This does not change the interruption filter, only the effects. **/
+    public static final int HINT_HOST_DISABLE_NOTIFICATION_EFFECTS = 1 << 1;
+
+    /** {@link #getCurrentListenerHints() Listener hints} constant - the primary device UI
+     * should disable phone call sounds, buyt not notification sound.
+     * This does not change the interruption filter, only the effects. **/
+    public static final int HINT_HOST_DISABLE_CALL_EFFECTS = 1 << 2;
+
     /**
      * Whether notification suppressed by DND should not interruption visually when the screen is
      * off.
@@ -1052,6 +1062,8 @@
         private int mSuppressedVisualEffects;
         private @Importance int mImportance;
         private CharSequence mImportanceExplanation;
+        // System specified group key.
+        private String mOverrideGroupKey;
 
         public Ranking() {}
 
@@ -1130,9 +1142,17 @@
             return mImportanceExplanation;
         }
 
+        /**
+         * If the system has overriden the group key, then this will be non-null, and this
+         * key should be used to bundle notifications.
+         */
+        public String getOverrideGroupKey() {
+            return mOverrideGroupKey;
+        }
+
         private void populate(String key, int rank, boolean matchesInterruptionFilter,
                 int visibilityOverride, int suppressedVisualEffects, int importance,
-                CharSequence explanation) {
+                CharSequence explanation, String overrideGroupKey) {
             mKey = key;
             mRank = rank;
             mIsAmbient = importance < IMPORTANCE_LOW;
@@ -1141,6 +1161,7 @@
             mSuppressedVisualEffects = suppressedVisualEffects;
             mImportance = importance;
             mImportanceExplanation = explanation;
+            mOverrideGroupKey = overrideGroupKey;
         }
 
         /**
@@ -1184,6 +1205,7 @@
         private ArrayMap<String, Integer> mSuppressedVisualEffects;
         private ArrayMap<String, Integer> mImportance;
         private ArrayMap<String, String> mImportanceExplanation;
+        private ArrayMap<String, String> mOverrideGroupKeys;
 
         private RankingMap(NotificationRankingUpdate rankingUpdate) {
             mRankingUpdate = rankingUpdate;
@@ -1210,7 +1232,7 @@
             int rank = getRank(key);
             outRanking.populate(key, rank, !isIntercepted(key),
                     getVisibilityOverride(key), getSuppressedVisualEffects(key),
-                    getImportance(key), getImportanceExplanation(key));
+                    getImportance(key), getImportanceExplanation(key), getOverrideGroupKey(key));
             return rank >= 0;
         }
 
@@ -1281,6 +1303,15 @@
             return mImportanceExplanation.get(key);
         }
 
+        private String getOverrideGroupKey(String key) {
+            synchronized (this) {
+                if (mOverrideGroupKeys == null) {
+                    buildOverrideGroupKeys();
+                }
+            }
+            return mOverrideGroupKeys.get(key);
+        }
+
         // Locked by 'this'
         private void buildRanksLocked() {
             String[] orderedKeys = mRankingUpdate.getOrderedKeys();
@@ -1335,6 +1366,15 @@
             }
         }
 
+        // Locked by 'this'
+        private void buildOverrideGroupKeys() {
+            Bundle overrideGroupKeys = mRankingUpdate.getOverrideGroupKeys();
+            mOverrideGroupKeys = new ArrayMap<>(overrideGroupKeys.size());
+            for (String key: overrideGroupKeys.keySet()) {
+                mOverrideGroupKeys.put(key, overrideGroupKeys.getString(key));
+            }
+        }
+
         // ----------- Parcelable
 
         @Override
diff --git a/core/java/android/service/notification/NotificationRankerService.java b/core/java/android/service/notification/NotificationRankerService.java
index 47fdac6..ee5361a 100644
--- a/core/java/android/service/notification/NotificationRankerService.java
+++ b/core/java/android/service/notification/NotificationRankerService.java
@@ -22,14 +22,19 @@
 import android.content.Context;
 import android.content.Intent;
 import android.net.Uri;
+import android.os.Bundle;
 import android.os.Handler;
 import android.os.IBinder;
 import android.os.Looper;
 import android.os.Message;
+import android.os.Parcel;
+import android.os.Parcelable;
 import android.os.RemoteException;
 import android.util.Log;
 import com.android.internal.os.SomeArgs;
 
+import java.util.List;
+
 /**
  * A service that helps the user manage notifications. This class is only used to
  * extend the framework service and may not be implemented by non-framework components.
@@ -91,27 +96,8 @@
     /** Notification was canceled by the owning managed profile being turned off. */
     public static final int REASON_PROFILE_TURNED_OFF = 15;
 
-    public class Adjustment {
-        int mImportance;
-        CharSequence mExplanation;
-        Uri mReference;
-
-        /**
-         * Create a notification importance adjustment.
-         *
-         * @param importance The final importance of the notification.
-         * @param explanation A human-readable justification for the adjustment.
-         * @param reference A reference to an external object that augments the
-         *                  explanation, such as a
-         *                  {@link android.provider.ContactsContract.Contacts#CONTENT_LOOKUP_URI},
-         *                  or null.
-         */
-        public Adjustment(int importance, CharSequence explanation, Uri reference) {
-            mImportance = importance;
-            mExplanation = explanation;
-            mReference = reference;
-        }
-    }
+    /** Autobundled summary notification was canceled because its group was unbundled */
+    public static final int REASON_UNAUTOBUNDLED = 16;
 
     private Handler mHandler;
 
@@ -200,18 +186,32 @@
     }
 
     /**
-     * Change the importance of an existing notification.  N.B. this won’t cause
+     * Updates a notification.  N.B. this won’t cause
      * an existing notification to alert, but might allow a future update to
      * this notification to alert.
      *
-     * @param key the notification key
-     * @param adjustment the new importance with an explanation
+     * @param adjustment the adjustment with an explanation
      */
-    public final void adjustImportance(String key, Adjustment adjustment) {
+    public final void adjustNotification(Adjustment adjustment) {
         if (!isBound()) return;
         try {
-            getNotificationInterface().setImportanceFromRankerService(mWrapper, key,
-                    adjustment.mImportance, adjustment.mExplanation);
+            getNotificationInterface().applyAdjustmentFromRankerService(mWrapper, adjustment);
+        } catch (android.os.RemoteException ex) {
+            Log.v(TAG, "Unable to contact notification manager", ex);
+        }
+    }
+
+    /**
+     * Updates existing notifications. Re-ranking won't occur until all adjustments are applied.
+     * N.B. this won’t cause an existing notification to alert, but might allow a future update to
+     * these notifications to alert.
+     *
+     * @param adjustments a list of adjustments with explanations
+     */
+    public final void adjustNotifications(List<Adjustment> adjustments) {
+        if (!isBound()) return;
+        try {
+            getNotificationInterface().applyAdjustmentsFromRankerService(mWrapper, adjustments);
         } catch (android.os.RemoteException ex) {
             Log.v(TAG, "Unable to contact notification manager", ex);
         }
@@ -299,7 +299,7 @@
                     args.recycle();
                     Adjustment adjustment = onNotificationEnqueued(sbn, importance, user);
                     if (adjustment != null) {
-                        adjustImportance(sbn.getKey(), adjustment);
+                        adjustNotification(adjustment);
                     }
                 } break;
 
diff --git a/core/java/android/service/notification/NotificationRankingUpdate.java b/core/java/android/service/notification/NotificationRankingUpdate.java
index 79f6fc4..788b5c0 100644
--- a/core/java/android/service/notification/NotificationRankingUpdate.java
+++ b/core/java/android/service/notification/NotificationRankingUpdate.java
@@ -30,16 +30,18 @@
     private final Bundle mSuppressedVisualEffects;
     private final int[] mImportance;
     private final Bundle mImportanceExplanation;
+    private final Bundle mOverrideGroupKeys;
 
     public NotificationRankingUpdate(String[] keys, String[] interceptedKeys,
             Bundle visibilityOverrides, Bundle suppressedVisualEffects,
-            int[] importance, Bundle explanation) {
+            int[] importance, Bundle explanation, Bundle overrideGroupKeys) {
         mKeys = keys;
         mInterceptedKeys = interceptedKeys;
         mVisibilityOverrides = visibilityOverrides;
         mSuppressedVisualEffects = suppressedVisualEffects;
         mImportance = importance;
         mImportanceExplanation = explanation;
+        mOverrideGroupKeys = overrideGroupKeys;
     }
 
     public NotificationRankingUpdate(Parcel in) {
@@ -50,6 +52,7 @@
         mImportance = new int[mKeys.length];
         in.readIntArray(mImportance);
         mImportanceExplanation = in.readBundle();
+        mOverrideGroupKeys = in.readBundle();
     }
 
     @Override
@@ -65,6 +68,7 @@
         out.writeBundle(mSuppressedVisualEffects);
         out.writeIntArray(mImportance);
         out.writeBundle(mImportanceExplanation);
+        out.writeBundle(mOverrideGroupKeys);
     }
 
     public static final Parcelable.Creator<NotificationRankingUpdate> CREATOR
@@ -101,4 +105,8 @@
     public Bundle getImportanceExplanation() {
         return mImportanceExplanation;
     }
+
+    public Bundle getOverrideGroupKeys() {
+        return mOverrideGroupKeys;
+    }
 }
diff --git a/core/java/android/service/notification/StatusBarNotification.java b/core/java/android/service/notification/StatusBarNotification.java
index 198e43d..0221b66 100644
--- a/core/java/android/service/notification/StatusBarNotification.java
+++ b/core/java/android/service/notification/StatusBarNotification.java
@@ -33,7 +33,8 @@
     private final int id;
     private final String tag;
     private final String key;
-    private final String groupKey;
+    private String groupKey;
+    private String overrideGroupKey;
 
     private final int uid;
     private final String opPkg;
@@ -51,6 +52,27 @@
                 System.currentTimeMillis());
     }
 
+    /** @hide */
+    public StatusBarNotification(String pkg, String opPkg, int id, String tag, int uid,
+            int initialPid, Notification notification, UserHandle user, String overrideGroupKey,
+            long postTime) {
+        if (pkg == null) throw new NullPointerException();
+        if (notification == null) throw new NullPointerException();
+
+        this.pkg = pkg;
+        this.opPkg = opPkg;
+        this.id = id;
+        this.tag = tag;
+        this.uid = uid;
+        this.initialPid = initialPid;
+        this.notification = notification;
+        this.user = user;
+        this.postTime = postTime;
+        this.overrideGroupKey = overrideGroupKey;
+        this.key = key();
+        this.groupKey = groupKey();
+    }
+
     public StatusBarNotification(String pkg, String opPkg, int id, String tag, int uid,
             int initialPid, int score, Notification notification, UserHandle user,
             long postTime) {
@@ -84,15 +106,27 @@
         this.notification = new Notification(in);
         this.user = UserHandle.readFromParcel(in);
         this.postTime = in.readLong();
+        if (in.readInt() != 0) {
+            this.overrideGroupKey = in.readString();
+        } else {
+            this.overrideGroupKey = null;
+        }
         this.key = key();
         this.groupKey = groupKey();
     }
 
     private String key() {
-        return user.getIdentifier() + "|" + pkg + "|" + id + "|" + tag + "|" + uid;
+        String sbnKey = user.getIdentifier() + "|" + pkg + "|" + id + "|" + tag + "|" + uid;
+        if (overrideGroupKey != null && getNotification().isGroupSummary()) {
+            sbnKey = sbnKey + "|" + overrideGroupKey;
+        }
+        return sbnKey;
     }
 
     private String groupKey() {
+        if (overrideGroupKey != null) {
+            return user.getIdentifier() + "|" + pkg + "|" + "g:" + overrideGroupKey;
+        }
         final String group = getNotification().getGroup();
         final String sortKey = getNotification().getSortKey();
         if (group == null && sortKey == null) {
@@ -105,6 +139,17 @@
                         : "g:" + group);
     }
 
+    /**
+     * Returns true if this notification is part of a group.
+     */
+    public boolean isGroup() {
+        if (overrideGroupKey != null || getNotification().getGroup() != null
+                || getNotification().getSortKey() != null) {
+            return true;
+        }
+        return false;
+    }
+
     public void writeToParcel(Parcel out, int flags) {
         out.writeString(this.pkg);
         out.writeString(this.opPkg);
@@ -121,6 +166,12 @@
         user.writeToParcel(out, flags);
 
         out.writeLong(this.postTime);
+        if (this.overrideGroupKey != null) {
+            out.writeInt(1);
+            out.writeString(this.overrideGroupKey);
+        } else {
+            out.writeInt(0);
+        }
     }
 
     public int describeContents() {
@@ -149,22 +200,22 @@
         this.notification.cloneInto(no, false); // light copy
         return new StatusBarNotification(this.pkg, this.opPkg,
                 this.id, this.tag, this.uid, this.initialPid,
-                0, no, this.user, this.postTime);
+                no, this.user, this.overrideGroupKey, this.postTime);
     }
 
     @Override
     public StatusBarNotification clone() {
         return new StatusBarNotification(this.pkg, this.opPkg,
                 this.id, this.tag, this.uid, this.initialPid,
-                0, this.notification.clone(), this.user, this.postTime);
+                this.notification.clone(), this.user, this.overrideGroupKey, this.postTime);
     }
 
     @Override
     public String toString() {
         return String.format(
-                "StatusBarNotification(pkg=%s user=%s id=%d tag=%s score=%d key=%s: %s)",
+                "StatusBarNotification(pkg=%s user=%s id=%d tag=%s key=%s: %s)",
                 this.pkg, this.user, this.id, this.tag,
-                0, this.key, this.notification);
+                this.key, this.notification);
     }
 
     /** Convenience method to check the notification's flags for
@@ -258,6 +309,21 @@
     }
 
     /**
+     * Sets the override group key.
+     */
+    public void setOverrideGroupKey(String overrideGroupKey) {
+        this.overrideGroupKey = overrideGroupKey;
+        groupKey = groupKey();
+    }
+
+    /**
+     * Returns the override group key.
+     */
+    public String getOverrideGroupKey() {
+        return overrideGroupKey;
+    }
+
+    /**
      * @hide
      */
     public Context getPackageContext(Context context) {
diff --git a/core/java/android/service/quicksettings/IQSService.aidl b/core/java/android/service/quicksettings/IQSService.aidl
index 5434e2e..747f185 100644
--- a/core/java/android/service/quicksettings/IQSService.aidl
+++ b/core/java/android/service/quicksettings/IQSService.aidl
@@ -28,7 +28,6 @@
             String contentDescription);
     void onShowDialog(in Tile tile);
     void onStartActivity(in Tile tile);
-    void setTileMode(in ComponentName component, int mode);
     boolean isLocked();
     boolean isSecure();
     void startUnlockAndRun(in Tile tile);
diff --git a/core/java/android/service/quicksettings/TileService.java b/core/java/android/service/quicksettings/TileService.java
index 553d539..4e9a075 100644
--- a/core/java/android/service/quicksettings/TileService.java
+++ b/core/java/android/service/quicksettings/TileService.java
@@ -89,28 +89,24 @@
     public static final String ACTION_QS_TILE = "android.service.quicksettings.action.QS_TILE";
 
     /**
-     * The tile mode hasn't been set yet.
-     * @hide
-     */
-    public static final int TILE_MODE_UNSET = 0;
-
-    /**
-     * Constant to be returned by {@link #onTileAdded}.
-     * <p>
-     * Passive mode is the default mode for tiles.  The System will tell the tile
-     * when it is most important to update by putting it in the listening state.
-     */
-    public static final int TILE_MODE_PASSIVE = 1;
-
-    /**
-     * Constant to be returned by {@link #onTileAdded}.
+     * Meta-data for tile definition to set a tile into active mode.
      * <p>
      * Active mode is for tiles which already listen and keep track of their state in their
      * own process.  These tiles may request to send an update to the System while their process
      * is alive using {@link #requestListeningState}.  The System will only bind these tiles
      * on its own when a click needs to occur.
+     *
+     * To make a TileService an active tile, set this meta-data to true on the TileService's
+     * manifest declaration.
+     * <pre class="prettyprint">
+     * {@literal
+     * <meta-data android:name="android.service.quicksettings.ACTIVE_TILE"
+     *      android:value="true" />
+     * }
+     * </pre>
      */
-    public static final int TILE_MODE_ACTIVE = 2;
+    public static final String META_DATA_ACTIVE_TILE
+            = "android.service.quicksettings.ACTIVE_TILE";
 
     /**
      * Used to notify SysUI that Listening has be requested.
@@ -147,12 +143,8 @@
      * Note that this is not guaranteed to be called between {@link #onCreate()}
      * and {@link #onStartListening()}, it will only be called when the tile is added
      * and not on subsequent binds.
-     *
-     * @see #TILE_MODE_PASSIVE
-     * @see #TILE_MODE_ACTIVE
      */
-    public int onTileAdded() {
-        return TILE_MODE_PASSIVE;
+    public void onTileAdded() {
     }
 
     /**
@@ -386,15 +378,7 @@
                     }
                     break;
                 case MSG_TILE_ADDED:
-                    int mode = TileService.this.onTileAdded();
-                    if (mService == null) {
-                        return;
-                    }
-                    try {
-                        mService.setTileMode(new ComponentName(TileService.this,
-                                TileService.this.getClass()), mode);
-                    } catch (RemoteException e) {
-                    }
+                    TileService.this.onTileAdded();
                     break;
                 case MSG_TILE_REMOVED:
                     if (mListening) {
@@ -431,8 +415,8 @@
     /**
      * Requests that a tile be put in the listening state so it can send an update.
      *
-     * This method is only applicable to tiles that return {@link #TILE_MODE_ACTIVE} from
-     * {@link #onTileAdded()}, and will do nothing otherwise.
+     * This method is only applicable to tiles that have {@link #META_DATA_ACTIVE_TILE} defined
+     * as true on their TileService Manifest declaration, and will do nothing otherwise.
      */
     public static final void requestListeningState(Context context, ComponentName component) {
         Intent intent = new Intent(ACTION_REQUEST_LISTENING);
diff --git a/core/java/android/util/PathParser.java b/core/java/android/util/PathParser.java
index 29a72fd..f1c8c7d 100644
--- a/core/java/android/util/PathParser.java
+++ b/core/java/android/util/PathParser.java
@@ -31,12 +31,7 @@
             throw new IllegalArgumentException("Path string can not be null.");
         }
         Path path = new Path();
-        boolean hasValidPathData = nParseStringForPath(path.mNativePath, pathString,
-                pathString.length());
-        if (!hasValidPathData) {
-            throw new IllegalArgumentException("Path string: " + pathString +
-                    " does not contain valid path data");
-        }
+        nParseStringForPath(path.mNativePath, pathString, pathString.length());
         return path;
     }
 
@@ -104,7 +99,6 @@
             }
             super.finalize();
         }
-
     }
 
     /**
@@ -123,7 +117,7 @@
     }
 
     // Native functions are defined below.
-    private static native boolean nParseStringForPath(long pathPtr, String pathString,
+    private static native void nParseStringForPath(long pathPtr, String pathString,
             int stringLength);
     private static native void nCreatePathFromPathData(long outPathPtr, long pathData);
     private static native long nCreateEmptyPathData();
diff --git a/core/java/android/util/Patterns.java b/core/java/android/util/Patterns.java
index 9ed4850..0a452db 100644
--- a/core/java/android/util/Patterns.java
+++ b/core/java/android/util/Patterns.java
@@ -251,9 +251,9 @@
             + "|[1-9][0-9]|[0-9]))");
 
     /**
-     * Valid UCS characters defined in RFC 3987.
+     * Valid UCS characters defined in RFC 3987. Excludes space characters.
      */
-    private static final String UCS_CHAR =
+    private static final String UCS_CHAR = "[" +
             "\u00A0-\uD7FF" +
             "\uF900-\uFDCF" +
             "\uFDF0-\uFFEF" +
@@ -270,7 +270,8 @@
             "\uDA80\uDC00-\uDABF\uDFFD" +
             "\uDAC0\uDC00-\uDAFF\uDFFD" +
             "\uDB00\uDC00-\uDB3F\uDFFD" +
-            "\uDB44\uDC00-\uDB7F\uDFFD";
+            "\uDB44\uDC00-\uDB7F\uDFFD" +
+            "&&[^\u00A0[\u2000-\u200A]\u2028\u2029\u202F\u3000]]";
 
     /**
      * Valid characters for IRI label defined in RFC 3987.
diff --git a/core/java/android/view/ThreadedRenderer.java b/core/java/android/view/ThreadedRenderer.java
index c972476..c4ed94f 100644
--- a/core/java/android/view/ThreadedRenderer.java
+++ b/core/java/android/view/ThreadedRenderer.java
@@ -893,6 +893,10 @@
         nSerializeDisplayListTree(mNativeProxy);
     }
 
+    public static boolean copySurfaceInto(Surface surface, Bitmap bitmap) {
+        return nCopySurfaceInto(surface, bitmap);
+    }
+
     @Override
     protected void finalize() throws Throwable {
         try {
@@ -1029,4 +1033,6 @@
 
     private static native long nAddFrameMetricsObserver(long nativeProxy, FrameMetricsObserver observer);
     private static native void nRemoveFrameMetricsObserver(long nativeProxy, long nativeObserver);
+
+    private static native boolean nCopySurfaceInto(Surface surface, Bitmap bitmap);
 }
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index b0aa5c3..307e700 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -8877,7 +8877,7 @@
      * @hide
      */
     public void clearAccessibilityFocus() {
-        clearAccessibilityFocusNoCallbacks();
+        clearAccessibilityFocusNoCallbacks(0);
 
         // Clear the global reference of accessibility focus if this view or
         // any of its descendants had accessibility focus. This will NOT send
@@ -8920,14 +8920,27 @@
     /**
      * Clears accessibility focus without calling any callback methods
      * normally invoked in {@link #clearAccessibilityFocus()}. This method
-     * is used for clearing accessibility focus when giving this focus to
-     * another view.
+     * is used separately from that one for clearing accessibility focus when
+     * giving this focus to another view.
+     *
+     * @param action The action, if any, that led to focus being cleared. Set to
+     * AccessibilityNodeInfo#ACTION_ACCESSIBILITY_FOCUS to specify that focus is moving within
+     * the window.
      */
-    void clearAccessibilityFocusNoCallbacks() {
+    void clearAccessibilityFocusNoCallbacks(int action) {
         if ((mPrivateFlags2 & PFLAG2_ACCESSIBILITY_FOCUSED) != 0) {
             mPrivateFlags2 &= ~PFLAG2_ACCESSIBILITY_FOCUSED;
             invalidate();
-            sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUS_CLEARED);
+            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
+                AccessibilityEvent event = AccessibilityEvent.obtain(
+                        AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUS_CLEARED);
+                event.setAction(action);
+                if (mAccessibilityDelegate != null) {
+                    mAccessibilityDelegate.sendAccessibilityEventUnchecked(this, event);
+                } else {
+                    sendAccessibilityEventUnchecked(event);
+                }
+            }
         }
     }
 
@@ -10265,7 +10278,8 @@
      */
     @Visibility boolean dispatchVisibilityAggregated(boolean isVisible) {
         final boolean thisVisible = getVisibility() == VISIBLE;
-        if (thisVisible) {
+        // If we're not visible but something is telling us we are, ignore it.
+        if (thisVisible || !isVisible) {
             onVisibilityAggregated(isVisible);
         }
         return thisVisible && isVisible;
diff --git a/core/java/android/view/ViewAnimationUtils.java b/core/java/android/view/ViewAnimationUtils.java
index 4c75935..3e277eb 100644
--- a/core/java/android/view/ViewAnimationUtils.java
+++ b/core/java/android/view/ViewAnimationUtils.java
@@ -41,6 +41,22 @@
      * As a result {@link AnimatorListener#onAnimationEnd(Animator)}
      * will occur after the animation has ended, but it may be delayed depending
      * on thread responsiveness.
+     * <p>
+     * Note that if any start delay is set on the reveal animator, the start radius
+     * will not be applied to the reveal circle until the start delay has passed.
+     * If it's desired to set a start radius on the reveal circle during the start
+     * delay, one workaround could be adding an animator with the same start and
+     * end radius. For example:
+     * <pre><code>
+     * public static Animator createRevealWithDelay(View view, int centerX, int centerY, float startRadius, float endRadius) {
+     *     Animator delayAnimator = ViewAnimationUtils.createCircularReveal(view, centerX, centerY, startRadius, startRadius);
+     *     delayAnimator.setDuration(delayTimeMS);
+     *     Animator revealAnimator = ViewAnimationUtils.createCircularReveal(view, centerX, centerY, startRadius, endRadius);
+     *     AnimatorSet set = new AnimatorSet();
+     *     set.playSequentially(delayAnimator, revealAnimator);
+     *     return set;
+     * }
+     * </code></pre>
      *
      * @param view The View will be clipped to the animating circle.
      * @param centerX The x coordinate of the center of the animating circle, relative to
diff --git a/core/java/android/view/ViewRootImpl.java b/core/java/android/view/ViewRootImpl.java
index 5b2877f..a324767 100644
--- a/core/java/android/view/ViewRootImpl.java
+++ b/core/java/android/view/ViewRootImpl.java
@@ -3071,7 +3071,8 @@
 
             // Clear accessibility focus on the host after clearing state since
             // this method may be reentrant.
-            focusHost.clearAccessibilityFocusNoCallbacks();
+            focusHost.clearAccessibilityFocusNoCallbacks(
+                    AccessibilityNodeInfo.ACTION_ACCESSIBILITY_FOCUS);
 
             AccessibilityNodeProvider provider = focusHost.getAccessibilityNodeProvider();
             if (provider != null) {
@@ -3088,7 +3089,8 @@
         }
         if (mAccessibilityFocusedHost != null) {
             // Clear accessibility focus in the view.
-            mAccessibilityFocusedHost.clearAccessibilityFocusNoCallbacks();
+            mAccessibilityFocusedHost.clearAccessibilityFocusNoCallbacks(
+                    AccessibilityNodeInfo.ACTION_ACCESSIBILITY_FOCUS);
         }
 
         // Set the new focus host and node.
@@ -6623,7 +6625,7 @@
             // Error state: virtual view with no provider. Clear focus.
             mAccessibilityFocusedHost = null;
             mAccessibilityFocusedVirtualView = null;
-            focusedHost.clearAccessibilityFocusNoCallbacks();
+            focusedHost.clearAccessibilityFocusNoCallbacks(0);
             return;
         }
 
@@ -6673,7 +6675,7 @@
         if (mAccessibilityFocusedVirtualView == null) {
             // Error state: The node no longer exists. Clear focus.
             mAccessibilityFocusedHost = null;
-            focusedHost.clearAccessibilityFocusNoCallbacks();
+            focusedHost.clearAccessibilityFocusNoCallbacks(0);
 
             // This will probably fail, but try to keep the provider's internal
             // state consistent by clearing focus.
diff --git a/core/java/android/view/WindowManager.java b/core/java/android/view/WindowManager.java
index c372c30..584233c 100644
--- a/core/java/android/view/WindowManager.java
+++ b/core/java/android/view/WindowManager.java
@@ -1240,6 +1240,13 @@
         public static final int PRIVATE_FLAG_LAYOUT_CHILD_WINDOW_IN_PARENT_FRAME = 0x00010000;
 
         /**
+         * Flag to indicate that this window is always drawing the status bar background, no matter
+         * what the other flags are.
+         * @hide
+         */
+        public static final int PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND = 0x00020000;
+
+        /**
          * Control flags that are private to the platform.
          * @hide
          */
@@ -1701,6 +1708,14 @@
          */
         public int accessibilityIdOfAnchor = -1;
 
+        /**
+         * The window title isn't kept in sync with what is displayed in the title bar, so we
+         * separately track the currently shown title to provide to accessibility.
+         *
+         * @hide
+         */
+        public CharSequence accessibilityTitle;
+
         public LayoutParams() {
             super(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
             type = TYPE_APPLICATION;
@@ -1749,6 +1764,7 @@
                 title = "";
 
             mTitle = TextUtils.stringOrSpannedString(title);
+            accessibilityTitle = mTitle;
         }
 
         public final CharSequence getTitle() {
@@ -1808,6 +1824,7 @@
             out.writeInt(hasManualSurfaceInsets ? 1 : 0);
             out.writeInt(needsMenuKey);
             out.writeInt(accessibilityIdOfAnchor);
+            TextUtils.writeToParcel(accessibilityTitle, out, parcelableFlags);
         }
 
         public static final Parcelable.Creator<LayoutParams> CREATOR
@@ -1859,6 +1876,7 @@
             hasManualSurfaceInsets = in.readInt() != 0;
             needsMenuKey = in.readInt();
             accessibilityIdOfAnchor = in.readInt();
+            accessibilityTitle = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
         }
 
         @SuppressWarnings({"PointlessBitwiseExpression"})
@@ -1900,6 +1918,8 @@
         /** {@hide} */
         public static final int ACCESSIBILITY_ANCHOR_CHANGED = 1 << 24;
         /** {@hide} */
+        public static final int ACCESSIBILITY_TITLE_CHANGED = 1 << 25;
+        /** {@hide} */
         public static final int EVERYTHING_CHANGED = 0xffffffff;
 
         // internal buffer to backup/restore parameters under compatibility mode.
@@ -2065,6 +2085,13 @@
                 changes |= ACCESSIBILITY_ANCHOR_CHANGED;
             }
 
+            if (!Objects.equals(accessibilityTitle, o.accessibilityTitle)
+                    && o.accessibilityTitle != null) {
+                // NOTE: accessibilityTitle only copied if the originator set one.
+                accessibilityTitle = o.accessibilityTitle;
+                changes |= ACCESSIBILITY_TITLE_CHANGED;
+            }
+
             return changes;
         }
 
diff --git a/core/java/android/view/inputmethod/CursorAnchorInfo.java b/core/java/android/view/inputmethod/CursorAnchorInfo.java
index fd73432..24739bf 100644
--- a/core/java/android/view/inputmethod/CursorAnchorInfo.java
+++ b/core/java/android/view/inputmethod/CursorAnchorInfo.java
@@ -16,6 +16,7 @@
 
 package android.view.inputmethod;
 
+import android.annotation.NonNull;
 import android.graphics.Matrix;
 import android.graphics.RectF;
 import android.os.Parcel;
@@ -25,6 +26,7 @@
 import android.text.TextUtils;
 import android.view.inputmethod.SparseRectFArray.SparseRectFArrayBuilder;
 
+import java.util.Arrays;
 import java.util.Objects;
 
 /**
@@ -36,6 +38,11 @@
  */
 public final class CursorAnchorInfo implements Parcelable {
     /**
+     * The pre-computed hash code.
+     */
+    private final int mHashCode;
+
+    /**
      * The index of the first character of the selected text (inclusive). {@code -1} when there is
      * no text selection.
      */
@@ -100,7 +107,8 @@
      * Transformation matrix that is applied to any positional information of this class to
      * transform local coordinates into screen coordinates.
      */
-    private final Matrix mMatrix;
+    @NonNull
+    private final float[] mMatrixValues;
 
     /**
      * Flag for {@link #getInsertionMarkerFlags()} and {@link #getCharacterBoundsFlags(int)}: the
@@ -121,6 +129,7 @@
     public static final int FLAG_IS_RTL = 0x04;
 
     public CursorAnchorInfo(final Parcel source) {
+        mHashCode = source.readInt();
         mSelectionStart = source.readInt();
         mSelectionEnd = source.readInt();
         mComposingTextStart = source.readInt();
@@ -131,8 +140,7 @@
         mInsertionMarkerBaseline = source.readFloat();
         mInsertionMarkerBottom = source.readFloat();
         mCharacterBoundsArray = source.readParcelable(SparseRectFArray.class.getClassLoader());
-        mMatrix = new Matrix();
-        mMatrix.setValues(source.createFloatArray());
+        mMatrixValues = source.createFloatArray();
     }
 
     /**
@@ -143,6 +151,7 @@
      */
     @Override
     public void writeToParcel(Parcel dest, int flags) {
+        dest.writeInt(mHashCode);
         dest.writeInt(mSelectionStart);
         dest.writeInt(mSelectionEnd);
         dest.writeInt(mComposingTextStart);
@@ -153,27 +162,12 @@
         dest.writeFloat(mInsertionMarkerBaseline);
         dest.writeFloat(mInsertionMarkerBottom);
         dest.writeParcelable(mCharacterBoundsArray, flags);
-        final float[] matrixArray = new float[9];
-        mMatrix.getValues(matrixArray);
-        dest.writeFloatArray(matrixArray);
+        dest.writeFloatArray(mMatrixValues);
     }
 
     @Override
     public int hashCode(){
-        final float floatHash = mInsertionMarkerHorizontal + mInsertionMarkerTop
-                + mInsertionMarkerBaseline + mInsertionMarkerBottom;
-        int hash = floatHash > 0 ? (int) floatHash : (int)(-floatHash);
-        hash *= 31;
-        hash += mInsertionMarkerFlags;
-        hash *= 31;
-        hash += mSelectionStart + mSelectionEnd + mComposingTextStart;
-        hash *= 31;
-        hash += Objects.hashCode(mComposingText);
-        hash *= 31;
-        hash += Objects.hashCode(mCharacterBoundsArray);
-        hash *= 31;
-        hash += Objects.hashCode(mMatrix);
-        return hash;
+        return mHashCode;
     }
 
     /**
@@ -202,13 +196,13 @@
         if (hashCode() != that.hashCode()) {
             return false;
         }
+
+        // Check fields that are not covered by hashCode() first.
+
         if (mSelectionStart != that.mSelectionStart || mSelectionEnd != that.mSelectionEnd) {
             return false;
         }
-        if (mComposingTextStart != that.mComposingTextStart
-                || !Objects.equals(mComposingText, that.mComposingText)) {
-            return false;
-        }
+
         if (mInsertionMarkerFlags != that.mInsertionMarkerFlags
                 || !areSameFloatImpl(mInsertionMarkerHorizontal, that.mInsertionMarkerHorizontal)
                 || !areSameFloatImpl(mInsertionMarkerTop, that.mInsertionMarkerTop)
@@ -216,18 +210,35 @@
                 || !areSameFloatImpl(mInsertionMarkerBottom, that.mInsertionMarkerBottom)) {
             return false;
         }
+
         if (!Objects.equals(mCharacterBoundsArray, that.mCharacterBoundsArray)) {
             return false;
         }
-        if (!Objects.equals(mMatrix, that.mMatrix)) {
+
+        // Following fields are (partially) covered by hashCode().
+
+        if (mComposingTextStart != that.mComposingTextStart
+                || !Objects.equals(mComposingText, that.mComposingText)) {
             return false;
         }
+
+        // We do not use Arrays.equals(float[], float[]) to keep the previous behavior regarding
+        // NaN, 0.0f, and -0.0f.
+        if (mMatrixValues.length != that.mMatrixValues.length) {
+            return false;
+        }
+        for (int i = 0; i < mMatrixValues.length; ++i) {
+            if (mMatrixValues[i] != that.mMatrixValues[i]) {
+                return false;
+            }
+        }
         return true;
     }
 
     @Override
     public String toString() {
-        return "SelectionInfo{mSelection=" + mSelectionStart + "," + mSelectionEnd
+        return "CursorAnchorInfo{mHashCode=" + mHashCode
+                + " mSelection=" + mSelectionStart + "," + mSelectionEnd
                 + " mComposingTextStart=" + mComposingTextStart
                 + " mComposingText=" + Objects.toString(mComposingText)
                 + " mInsertionMarkerFlags=" + mInsertionMarkerFlags
@@ -236,7 +247,7 @@
                 + " mInsertionMarkerBaseline=" + mInsertionMarkerBaseline
                 + " mInsertionMarkerBottom=" + mInsertionMarkerBottom
                 + " mCharacterBoundsArray=" + Objects.toString(mCharacterBoundsArray)
-                + " mMatrix=" + Objects.toString(mMatrix)
+                + " mMatrix=" + Arrays.toString(mMatrixValues)
                 + "}";
     }
 
@@ -254,7 +265,7 @@
         private float mInsertionMarkerBottom = Float.NaN;
         private int mInsertionMarkerFlags = 0;
         private SparseRectFArrayBuilder mCharacterBoundsArrayBuilder = null;
-        private final Matrix mMatrix = new Matrix(Matrix.IDENTITY_MATRIX);
+        private float[] mMatrixValues = null;
         private boolean mMatrixInitialized = false;
 
         /**
@@ -349,7 +360,10 @@
          * is interpreted as an identity matrix.
          */
         public Builder setMatrix(final Matrix matrix) {
-            mMatrix.set(matrix != null ? matrix : Matrix.IDENTITY_MATRIX);
+            if (mMatrixValues == null) {
+                mMatrixValues = new float[9];
+            }
+            (matrix != null ? matrix : Matrix.IDENTITY_MATRIX).getValues(mMatrixValues);
             mMatrixInitialized = true;
             return this;
         }
@@ -391,7 +405,6 @@
             mInsertionMarkerTop = Float.NaN;
             mInsertionMarkerBaseline = Float.NaN;
             mInsertionMarkerBottom = Float.NaN;
-            mMatrix.set(Matrix.IDENTITY_MATRIX);
             mMatrixInitialized = false;
             if (mCharacterBoundsArrayBuilder != null) {
                 mCharacterBoundsArrayBuilder.reset();
@@ -411,7 +424,18 @@
         mInsertionMarkerBottom = builder.mInsertionMarkerBottom;
         mCharacterBoundsArray = builder.mCharacterBoundsArrayBuilder != null ?
                 builder.mCharacterBoundsArrayBuilder.build() : null;
-        mMatrix = new Matrix(builder.mMatrix);
+        mMatrixValues = new float[9];
+        if (builder.mMatrixInitialized) {
+            System.arraycopy(builder.mMatrixValues, 0, mMatrixValues, 0, 9);
+        } else {
+            Matrix.IDENTITY_MATRIX.getValues(mMatrixValues);
+        }
+
+        // To keep hash function simple, we only use some complex objects for hash.
+        int hash = Objects.hashCode(mComposingText);
+        hash *= 31;
+        hash += Arrays.hashCode(mMatrixValues);
+        mHashCode = hash;
     }
 
     /**
@@ -527,7 +551,9 @@
      * @return a new instance (copy) of the transformation matrix.
      */
     public Matrix getMatrix() {
-        return new Matrix(mMatrix);
+        final Matrix matrix = new Matrix();
+        matrix.setValues(mMatrixValues);
+        return matrix;
     }
 
     /**
diff --git a/core/java/android/view/inputmethod/InputMethodSubtype.java b/core/java/android/view/inputmethod/InputMethodSubtype.java
index a42f4d9..dc433b1 100644
--- a/core/java/android/view/inputmethod/InputMethodSubtype.java
+++ b/core/java/android/view/inputmethod/InputMethodSubtype.java
@@ -68,6 +68,7 @@
     // TODO: remove this
     private static final String EXTRA_KEY_UNTRANSLATABLE_STRING_IN_SUBTYPE_NAME =
             "UntranslatableReplacementStringInSubtypeName";
+    private static final int SUBTYPE_ID_NONE = 0;
 
     private final boolean mIsAuxiliary;
     private final boolean mOverridesImplicitlyEnabledSubtype;
@@ -157,13 +158,13 @@
          * track of enabled subtypes by ID. When the IME package gets upgraded, enabled IDs will
          * stay enabled even if other attributes are different. If the ID is unspecified or 0,
          * Arrays.hashCode(new Object[] {locale, mode, extraValue,
-         * isAuxiliary, overridesImplicitlyEnabledSubtype}) will be used instead.
+         * isAuxiliary, overridesImplicitlyEnabledSubtype, isAsciiCapable}) will be used instead.
          */
         public InputMethodSubtypeBuilder setSubtypeId(int subtypeId) {
             mSubtypeId = subtypeId;
             return this;
         }
-        private int mSubtypeId = 0;
+        private int mSubtypeId = SUBTYPE_ID_NONE;
 
         /**
          * @param subtypeLocale is the locale supported by this subtype.
@@ -268,7 +269,7 @@
      * subtypes by ID. When the IME package gets upgraded, enabled IDs will stay enabled even if
      * other attributes are different. If the ID is unspecified or 0,
      * Arrays.hashCode(new Object[] {locale, mode, extraValue,
-     * isAuxiliary, overridesImplicitlyEnabledSubtype}) will be used instead.
+     * isAuxiliary, overridesImplicitlyEnabledSubtype, isAsciiCapable}) will be used instead.
      */
     public InputMethodSubtype(int nameId, int iconId, String locale, String mode, String extraValue,
             boolean isAuxiliary, boolean overridesImplicitlyEnabledSubtype, int id) {
@@ -293,9 +294,12 @@
         mIsAsciiCapable = builder.mIsAsciiCapable;
         // If hashCode() of this subtype is 0 and you want to specify it as an id of this subtype,
         // just specify 0 as this subtype's id. Then, this subtype's id is treated as 0.
-        mSubtypeHashCode = mSubtypeId != 0 ? mSubtypeId : hashCodeInternal(mSubtypeLocale,
-                mSubtypeMode, mSubtypeExtraValue, mIsAuxiliary, mOverridesImplicitlyEnabledSubtype,
-                mIsAsciiCapable);
+        if (mSubtypeId != SUBTYPE_ID_NONE) {
+            mSubtypeHashCode = mSubtypeId;
+        } else {
+            mSubtypeHashCode = hashCodeInternal(mSubtypeLocale, mSubtypeMode, mSubtypeExtraValue,
+                    mIsAuxiliary, mOverridesImplicitlyEnabledSubtype, mIsAsciiCapable);
+        }
     }
 
     InputMethodSubtype(Parcel source) {
@@ -501,6 +505,22 @@
         return mSubtypeHashCode;
     }
 
+    /**
+     * @hide
+     * @return {@code true} if a valid subtype ID exists.
+     */
+    public final boolean hasSubtypeId() {
+        return mSubtypeId != SUBTYPE_ID_NONE;
+    }
+
+    /**
+     * @hide
+     * @return subtype ID. {@code 0} means that not subtype ID is specified.
+     */
+    public final int getSubtypeId() {
+        return mSubtypeId;
+    }
+
     @Override
     public boolean equals(Object o) {
         if (o instanceof InputMethodSubtype) {
diff --git a/core/java/android/webkit/WebViewProviderResponse.java b/core/java/android/webkit/WebViewProviderResponse.java
index f5e09e2..c0aeb59 100644
--- a/core/java/android/webkit/WebViewProviderResponse.java
+++ b/core/java/android/webkit/WebViewProviderResponse.java
@@ -21,7 +21,7 @@
 import android.os.Parcelable;
 
 /** @hide */
-public class WebViewProviderResponse implements Parcelable {
+public final class WebViewProviderResponse implements Parcelable {
 
     public WebViewProviderResponse(PackageInfo packageInfo, int status) {
         this.packageInfo = packageInfo;
@@ -56,6 +56,6 @@
         out.writeInt(status);
     }
 
-    PackageInfo packageInfo;
-    int status;
+    public final PackageInfo packageInfo;
+    public final int status;
 }
diff --git a/core/java/android/widget/RadialTimePickerView.java b/core/java/android/widget/RadialTimePickerView.java
index 7220256..24d2c8e 100644
--- a/core/java/android/widget/RadialTimePickerView.java
+++ b/core/java/android/widget/RadialTimePickerView.java
@@ -58,8 +58,8 @@
 
     private static final String TAG = "RadialTimePickerView";
 
-    private static final int HOURS = 0;
-    private static final int MINUTES = 1;
+    public static final int HOURS = 0;
+    public static final int MINUTES = 1;
     private static final int HOURS_INNER = 2;
 
     private static final int SELECTOR_CIRCLE = 0;
diff --git a/core/java/android/widget/RemoteViews.java b/core/java/android/widget/RemoteViews.java
index 6d2cea6..a9b7f4e 100644
--- a/core/java/android/widget/RemoteViews.java
+++ b/core/java/android/widget/RemoteViews.java
@@ -1856,6 +1856,7 @@
         public static final int LAYOUT_MARGIN_END = 1;
         /** Set width */
         public static final int LAYOUT_WIDTH = 2;
+        public static final int LAYOUT_MARGIN_BOTTOM = 3;
 
         /**
          * @param viewId ID of the view alter
@@ -1898,6 +1899,12 @@
                         target.setLayoutParams(layoutParams);
                     }
                     break;
+                case LAYOUT_MARGIN_BOTTOM:
+                    if (layoutParams instanceof ViewGroup.MarginLayoutParams) {
+                        ((ViewGroup.MarginLayoutParams) layoutParams).bottomMargin = value;
+                        target.setLayoutParams(layoutParams);
+                    }
+                    break;
                 case LAYOUT_WIDTH:
                     layoutParams.width = value;
                     target.setLayoutParams(layoutParams);
@@ -2870,6 +2877,16 @@
     }
 
     /**
+     * Equivalent to setting {@link android.view.ViewGroup.MarginLayoutParams#bottomMargin}.
+     *
+     * @hide
+     */
+    public void setViewLayoutMarginBottom(int viewId, int bottomMargin) {
+        addAction(new LayoutParamAction(viewId, LayoutParamAction.LAYOUT_MARGIN_BOTTOM,
+                bottomMargin));
+    }
+
+    /**
      * Equivalent to setting {@link android.view.ViewGroup.LayoutParams#width}.
      * @hide
      */
diff --git a/core/java/android/widget/TextClock.java b/core/java/android/widget/TextClock.java
index ff10287..a585d75 100644
--- a/core/java/android/widget/TextClock.java
+++ b/core/java/android/widget/TextClock.java
@@ -555,7 +555,15 @@
         filter.addAction(Intent.ACTION_TIME_CHANGED);
         filter.addAction(Intent.ACTION_TIMEZONE_CHANGED);
 
-        getContext().registerReceiver(mIntentReceiver, filter, null, getHandler());
+        // OK, this is gross but needed. This class is supported by the
+        // remote views mechanism and as a part of that the remote views
+        // can be inflated by a context for another user without the app
+        // having interact users permission - just for loading resources.
+        // For example, when adding widgets from a managed profile to the
+        // home screen. Therefore, we register the receiver as the user
+        // the app is running as not the one the context is for.
+        getContext().registerReceiverAsUser(mIntentReceiver, android.os.Process.myUserHandle(),
+                filter, null, getHandler());
     }
 
     private void registerObserver() {
diff --git a/core/java/android/widget/TimePickerClockDelegate.java b/core/java/android/widget/TimePickerClockDelegate.java
index 4a24e26..0c3892d 100644
--- a/core/java/android/widget/TimePickerClockDelegate.java
+++ b/core/java/android/widget/TimePickerClockDelegate.java
@@ -58,8 +58,8 @@
     private static final long DELAY_COMMIT_MILLIS = 2000;
 
     // Index used by RadialPickerLayout
-    private static final int HOUR_INDEX = 0;
-    private static final int MINUTE_INDEX = 1;
+    private static final int HOUR_INDEX = RadialTimePickerView.HOURS;
+    private static final int MINUTE_INDEX = RadialTimePickerView.MINUTES;
 
     // NOT a real index for the purpose of what's showing.
     private static final int AMPM_INDEX = 2;
@@ -82,6 +82,10 @@
 
     private final Calendar mTempCalendar;
 
+    // Accessibility strings.
+    private final String mSelectHours;
+    private final String mSelectMinutes;
+
     private boolean mIsEnabled = true;
     private boolean mAllowAutoAdvance;
     private int mInitialHourOfDay;
@@ -89,10 +93,6 @@
     private boolean mIs24Hour;
     private boolean mIsAmPmAtStart;
 
-    // Accessibility strings.
-    private String mSelectHours;
-    private String mSelectMinutes;
-
     // Localization data.
     private boolean mHourFormatShowLeadingZero;
     private boolean mHourFormatStartsAtZero;
@@ -520,11 +520,15 @@
         } else {
             flags |= DateUtils.FORMAT_12HOUR;
         }
+
         mTempCalendar.set(Calendar.HOUR_OF_DAY, getHour());
         mTempCalendar.set(Calendar.MINUTE, getMinute());
-        String selectedDate = DateUtils.formatDateTime(mContext,
+
+        final String selectedTime = DateUtils.formatDateTime(mContext,
                 mTempCalendar.getTimeInMillis(), flags);
-        event.getText().add(selectedDate);
+        final String selectionMode = mRadialTimePickerView.getCurrentItemShowing() == HOUR_INDEX ?
+                mSelectHours : mSelectMinutes;
+        event.getText().add(selectedTime + " " + selectionMode);
     }
 
     /**
diff --git a/core/java/com/android/internal/app/ChooserActivity.java b/core/java/com/android/internal/app/ChooserActivity.java
index a4e489c..ed6ab56 100644
--- a/core/java/com/android/internal/app/ChooserActivity.java
+++ b/core/java/com/android/internal/app/ChooserActivity.java
@@ -41,12 +41,12 @@
 import android.os.IBinder;
 import android.os.Message;
 import android.os.Parcelable;
+import android.os.Process;
 import android.os.RemoteException;
 import android.os.ResultReceiver;
 import android.os.UserHandle;
 import android.os.UserManager;
 import android.os.storage.StorageManager;
-import android.provider.DocumentsContract;
 import android.service.chooser.ChooserTarget;
 import android.service.chooser.ChooserTargetService;
 import android.service.chooser.IChooserTargetResult;
@@ -70,6 +70,7 @@
 import com.android.internal.R;
 import com.android.internal.logging.MetricsLogger;
 import com.android.internal.logging.MetricsProto.MetricsEvent;
+import com.google.android.collect.Lists;
 
 import java.io.File;
 import java.util.ArrayList;
@@ -89,6 +90,7 @@
     private IntentSender mChosenComponentSender;
     private IntentSender mRefinementIntentSender;
     private RefinementResultReceiver mRefinementResultReceiver;
+    private ChooserTarget[] mCallerChooserTargets;
 
     private Intent mReferrerFillInIntent;
 
@@ -97,6 +99,7 @@
 
     private SharedPreferences mPinnedSharedPrefs;
     private static final float PINNED_TARGET_SCORE_BOOST = 1000.f;
+    private static final float CALLER_TARGET_SCORE_BOOST = 900.f;
     private static final String PINNED_SHARED_PREFS_NAME = "chooser_pin_settings";
     private static final String TARGET_DETAILS_FRAGMENT_TAG = "targetDetailsFragment";
 
@@ -219,6 +222,34 @@
                 Intent.EXTRA_CHOOSER_REFINEMENT_INTENT_SENDER);
         setSafeForwardingMode(true);
 
+        pa = intent.getParcelableArrayExtra(Intent.EXTRA_EXCLUDE_COMPONENTS);
+        if (pa != null) {
+            ComponentName[] names = new ComponentName[pa.length];
+            for (int i = 0; i < pa.length; i++) {
+                if (!(pa[i] instanceof ComponentName)) {
+                    Log.w(TAG, "Filtered component #" + i + " not a ComponentName: " + pa[i]);
+                    names = null;
+                    break;
+                }
+                names[i] = (ComponentName) pa[i];
+            }
+            setFilteredComponents(names);
+        }
+
+        pa = intent.getParcelableArrayExtra(Intent.EXTRA_CHOOSER_TARGETS);
+        if (pa != null) {
+            ChooserTarget[] targets = new ChooserTarget[pa.length];
+            for (int i = 0; i < pa.length; i++) {
+                if (!(pa[i] instanceof ChooserTarget)) {
+                    Log.w(TAG, "Chooser target #" + i + " not a ChooserTarget: " + pa[i]);
+                    targets = null;
+                    break;
+                }
+                targets[i] = (ChooserTarget) pa[i];
+            }
+            mCallerChooserTargets = targets;
+        }
+
         mPinnedSharedPrefs = getPinnedSharedPrefs(this);
         super.onCreate(savedInstanceState, target, title, defaultTitleRes, initialIntents,
                 null, false);
@@ -292,6 +323,9 @@
             boolean alwaysUseOption) {
         final ListView listView = adapterView instanceof ListView ? (ListView) adapterView : null;
         mChooserListAdapter = (ChooserListAdapter) adapter;
+        if (mCallerChooserTargets != null && mCallerChooserTargets.length > 0) {
+            mChooserListAdapter.addServiceResults(null, Lists.newArrayList(mCallerChooserTargets));
+        }
         mChooserRowAdapter = new ChooserRowAdapter(mChooserListAdapter);
         mChooserRowAdapter.registerDataSetObserver(new OffsetDataSetObserver(adapterView));
         adapterView.setAdapter(mChooserRowAdapter);
@@ -427,13 +461,19 @@
                         continue;
                     }
                 } catch (NameNotFoundException e) {
-                    Log.e(TAG, "Could not look up service " + serviceComponent, e);
+                    Log.e(TAG, "Could not look up service " + serviceComponent
+                            + "; component name not found");
                     continue;
                 }
 
                 final ChooserTargetServiceConnection conn =
                         new ChooserTargetServiceConnection(this, dri);
-                if (bindService(serviceIntent, conn, BIND_AUTO_CREATE | BIND_NOT_FOREGROUND)) {
+
+                // Explicitly specify Process.myUserHandle instead of calling bindService
+                // to avoid the warning from calling from the system process without an explicit
+                // user handle
+                if (bindServiceAsUser(serviceIntent, conn, BIND_AUTO_CREATE | BIND_NOT_FOREGROUND,
+                        Process.myUserHandle())) {
                     if (DEBUG) {
                         Log.d(TAG, "Binding service connection for target " + dri
                                 + " intent " + serviceIntent);
@@ -635,7 +675,11 @@
             if (mSourceInfo != null) {
                 return mSourceInfo.getResolvedIntent();
             }
-            return getTargetIntent();
+
+            final Intent targetIntent = new Intent(getTargetIntent());
+            targetIntent.setComponent(mChooserTarget.getComponentName());
+            targetIntent.putExtras(mChooserTarget.getIntentExtras());
+            return targetIntent;
         }
 
         @Override
@@ -650,8 +694,7 @@
         }
 
         private Intent getBaseIntentToSend() {
-            Intent result = mSourceInfo != null
-                    ? mSourceInfo.getResolvedIntent() : getTargetIntent();
+            Intent result = getResolvedIntent();
             if (result == null) {
                 Log.e(TAG, "ChooserTargetInfo: no base intent available to send");
             } else {
@@ -677,7 +720,19 @@
             }
             intent.setComponent(mChooserTarget.getComponentName());
             intent.putExtras(mChooserTarget.getIntentExtras());
-            activity.startActivityAsCaller(intent, options, true, userId);
+
+            // Important: we will ignore the target security checks in ActivityManager
+            // if and only if the ChooserTarget's target package is the same package
+            // where we got the ChooserTargetService that provided it. This lets a
+            // ChooserTargetService provide a non-exported or permission-guarded target
+            // to the chooser for the user to pick.
+            //
+            // If mSourceInfo is null, we got this ChooserTarget from the caller or elsewhere
+            // so we'll obey the caller's normal security checks.
+            final boolean ignoreTargetSecurity = mSourceInfo != null
+                    && mSourceInfo.getResolvedComponentName().getPackageName()
+                    .equals(mChooserTarget.getComponentName().getPackageName());
+            activity.startActivityAsCaller(intent, options, ignoreTargetSecurity, userId);
             return true;
         }
 
@@ -810,6 +865,9 @@
 
         @Override
         public float getScore(DisplayResolveInfo target) {
+            if (target == null) {
+                return CALLER_TARGET_SCORE_BOOST;
+            }
             float score = super.getScore(target);
             if (target.isPinned()) {
                 score += PINNED_TARGET_SCORE_BOOST;
@@ -1281,7 +1339,7 @@
     }
 
     static class ChooserTargetServiceConnection implements ServiceConnection {
-        private final DisplayResolveInfo mOriginalTarget;
+        private DisplayResolveInfo mOriginalTarget;
         private ComponentName mConnectedComponent;
         private ChooserActivity mChooserActivity;
         private final Object mLock = new Object();
@@ -1359,6 +1417,7 @@
         public void destroy() {
             synchronized (mLock) {
                 mChooserActivity = null;
+                mOriginalTarget = null;
             }
         }
 
@@ -1366,7 +1425,9 @@
         public String toString() {
             return "ChooserTargetServiceConnection{service="
                     + mConnectedComponent + ", activity="
-                    + mOriginalTarget.getResolveInfo().activityInfo.toString() + "}";
+                    + (mOriginalTarget != null
+                    ? mOriginalTarget.getResolveInfo().activityInfo.toString()
+                    : "<connection destroyed>") + "}";
         }
     }
 
diff --git a/core/java/com/android/internal/app/LocaleHelper.java b/core/java/com/android/internal/app/LocaleHelper.java
index a9d5113..7e9587a 100644
--- a/core/java/com/android/internal/app/LocaleHelper.java
+++ b/core/java/com/android/internal/app/LocaleHelper.java
@@ -90,6 +90,15 @@
         return str.toUpperCase();
     }
 
+    // For some locales we want to use a "dialect" form, for instance
+    // "Dari" instead of "Persian (Afghanistan)", or "Moldavian" instead of "Romanian (Moldova)"
+    private static boolean shouldUseDialectName(Locale locale) {
+        final String lang = locale.getLanguage();
+        return "fa".equals(lang) // Persian
+                || "ro".equals(lang) // Romanian
+                || "zh".equals(lang); // Chinese
+    }
+
     /**
      * Returns the locale localized for display in the provided locale.
      *
@@ -99,8 +108,10 @@
      * @return the localized name of the locale.
      */
     public static String getDisplayName(Locale locale, Locale displayLocale, boolean sentenceCase) {
-        String result = ULocale.getDisplayNameWithDialect(locale.toLanguageTag(),
-                ULocale.forLocale(displayLocale));
+        final ULocale displayULocale = ULocale.forLocale(displayLocale);
+        String result = shouldUseDialectName(locale)
+                ? ULocale.getDisplayNameWithDialect(locale.toLanguageTag(), displayULocale)
+                : ULocale.getDisplayName(locale.toLanguageTag(), displayULocale);
         return sentenceCase ? toSentenceCase(result, displayLocale) : result;
     }
 
@@ -112,9 +123,7 @@
      * @return the localized name of the locale.
      */
     public static String getDisplayName(Locale locale, boolean sentenceCase) {
-        String result = ULocale.getDisplayNameWithDialect(locale.toLanguageTag(),
-                ULocale.getDefault());
-        return sentenceCase ? toSentenceCase(result, Locale.getDefault()) : result;
+        return getDisplayName(locale, Locale.getDefault(), sentenceCase);
     }
 
     /**
diff --git a/core/java/com/android/internal/app/ResolverActivity.java b/core/java/com/android/internal/app/ResolverActivity.java
index ff680e2..1f2acc9 100644
--- a/core/java/com/android/internal/app/ResolverActivity.java
+++ b/core/java/com/android/internal/app/ResolverActivity.java
@@ -105,6 +105,7 @@
     private final ArrayList<Intent> mIntents = new ArrayList<>();
     private ResolverComparator mResolverComparator;
     private PickTargetOptionRequest mPickOptionRequest;
+    private ComponentName[] mFilteredComponents;
 
     protected ResolverDrawerLayout mResolverDrawerLayout;
 
@@ -332,6 +333,24 @@
         }
     }
 
+    public final void setFilteredComponents(ComponentName[] components) {
+        mFilteredComponents = components;
+    }
+
+    public final boolean isComponentFiltered(ComponentInfo component) {
+        if (mFilteredComponents == null) {
+            return false;
+        }
+
+        final ComponentName checkName = component.getComponentName();
+        for (ComponentName name : mFilteredComponents) {
+            if (name.equals(checkName)) {
+                return true;
+            }
+        }
+        return false;
+    }
+
     /**
      * Perform any initialization needed for voice interaction.
      */
@@ -741,7 +760,7 @@
                 } else {
                     try {
                         AppGlobals.getPackageManager().setLastChosenActivity(intent,
-                                intent.resolveTypeIfNeeded(getContentResolver()),
+                                intent.resolveType(getContentResolver()),
                                 PackageManager.MATCH_DEFAULT_ONLY,
                                 filter, bestMatch, intent.getComponent());
                     } catch (RemoteException re) {
@@ -1269,7 +1288,8 @@
                                 ai.applicationInfo.uid, ai.exported);
                         boolean suspended = (ai.applicationInfo.flags
                                 & ApplicationInfo.FLAG_SUSPENDED) != 0;
-                        if (granted != PackageManager.PERMISSION_GRANTED || suspended) {
+                        if (granted != PackageManager.PERMISSION_GRANTED || suspended
+                                || isComponentFiltered(ai)) {
                             // Access not allowed!
                             if (mOrigResolveList == currentResolveList) {
                                 mOrigResolveList = new ArrayList<>(mOrigResolveList);
diff --git a/core/java/com/android/internal/app/UnlaunchableAppActivity.java b/core/java/com/android/internal/app/UnlaunchableAppActivity.java
index f6fbaab..27588e9 100644
--- a/core/java/com/android/internal/app/UnlaunchableAppActivity.java
+++ b/core/java/com/android/internal/app/UnlaunchableAppActivity.java
@@ -26,6 +26,7 @@
 import android.content.Context;
 import android.content.DialogInterface;
 import android.content.Intent;
+import android.content.IntentSender;
 import android.content.pm.ApplicationInfo;
 import android.content.pm.PackageManager;
 import android.content.pm.PackageManager.NameNotFoundException;
@@ -53,6 +54,7 @@
 
     private int mUserId;
     private int mReason;
+    private IntentSender mTarget;
 
     @Override
     protected void onCreate(Bundle savedInstanceState) {
@@ -60,6 +62,7 @@
         Intent intent = getIntent();
         mReason = intent.getIntExtra(EXTRA_UNLAUNCHABLE_REASON, -1);
         mUserId = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL);
+        mTarget = intent.getParcelableExtra(Intent.EXTRA_INTENT);
 
         if (mUserId == UserHandle.USER_NULL) {
             Log.wtf(TAG, "Invalid user id: " + mUserId + ". Stopping.");
@@ -105,6 +108,14 @@
     public void onClick(DialogInterface dialog, int which) {
         if (mReason == UNLAUNCHABLE_REASON_QUIET_MODE && which == DialogInterface.BUTTON_POSITIVE) {
             UserManager.get(this).setQuietModeEnabled(mUserId, false);
+
+            if (mTarget != null) {
+                try {
+                    startIntentSenderForResult(mTarget, -1, null, 0, 0, 0);
+                } catch (IntentSender.SendIntentException e) {
+                    /* ignore */
+                }
+            }
         }
     }
 
@@ -121,4 +132,10 @@
         intent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
         return intent;
     }
+
+    public static Intent createInQuietModeDialogIntent(int userId, IntentSender target) {
+        Intent intent = createInQuietModeDialogIntent(userId);
+        intent.putExtra(Intent.EXTRA_INTENT, target);
+        return intent;
+    }
 }
diff --git a/core/java/com/android/internal/app/procstats/ProcessStats.java b/core/java/com/android/internal/app/procstats/ProcessStats.java
index 06542f7..2f80b86 100644
--- a/core/java/com/android/internal/app/procstats/ProcessStats.java
+++ b/core/java/com/android/internal/app/procstats/ProcessStats.java
@@ -516,7 +516,7 @@
                 out.writeInt((int)val);
             } else {
                 int top = ~((int)((val>>32)&0x7fffffff));
-                int bottom = (int)(val&0xfffffff);
+                int bottom = (int)(val&0x0ffffffffL);
                 out.writeInt(top);
                 out.writeInt(bottom);
             }
diff --git a/core/java/com/android/internal/app/procstats/SparseMappingTable.java b/core/java/com/android/internal/app/procstats/SparseMappingTable.java
index 7252276..f941836 100644
--- a/core/java/com/android/internal/app/procstats/SparseMappingTable.java
+++ b/core/java/com/android/internal/app/procstats/SparseMappingTable.java
@@ -68,11 +68,8 @@
      * A table of data as stored in a SparseMappingTable.
      */
     public static class Table {
-        // When mSequence is this this our data better be empty
-        private static final int UNINITIALIZED_SEQUENCE = -1;
-
         private SparseMappingTable mParent;
-        private int mSequence = UNINITIALIZED_SEQUENCE;
+        private int mSequence = 1;
         private int[] mTable;
         private int mSize;
 
@@ -119,12 +116,6 @@
          *         but should be considered opaque to the caller.
          */
         public int getOrAddKey(byte id, int count) {
-            // This is the only place we add data to mParent.mLongs, so this is the time
-            // to update our sequence to match there.
-            if (mSequence == UNINITIALIZED_SEQUENCE) {
-                mSequence = mParent.mSequence;
-            }
-
             assertConsistency();
 
             final int idx = binarySearch(id);
@@ -311,7 +302,7 @@
             // Reset our sequence number.  This will make all read/write calls
             // start to fail, and then when we re-allocate it will be re-synced
             // to that of mParent.
-            mSequence = UNINITIALIZED_SEQUENCE;
+            mSequence = mParent.mSequence;
         }
 
         /**
@@ -372,29 +363,27 @@
          * Throw an exception if one of a variety of internal consistency checks fails.
          */
         private void assertConsistency() {
-            // Assert that our sequewnce number has been initialized. If it hasn't
-            // that means someone tried to read or write data without allocating it
-            // since we were created or reset.
-            if (mSequence == UNINITIALIZED_SEQUENCE) {
-                logOrThrow("mSequence == UNINITIALIZED_SEQUENCE in"
-                        + " SparseMappingTable.Table.  -- "
-                        + dumpInternalState());
-                return;
-            }
-
-            // Assert that our sequence number matches mParent's.  If it isn't that means
-            // we have been reset and our
-            if (mSequence != mParent.mSequence) {
-                if (mSequence < mParent.mSequence) {
-                    logOrThrow("Sequence mismatch. SparseMappingTable.resetTable()"
-                            + " called but not Table.resetTable() -- "
-                            + dumpInternalState());
-                    return;
-                } else if (mSequence > mParent.mSequence) {
-                    logOrThrow("Sequence mismatch. Table.resetTable()"
-                            + " called but not SparseMappingTable.resetTable() -- "
-                            + dumpInternalState());
-                    return;
+            // Something with this checking isn't working and is triggering
+            // more problems than it's helping to debug.
+            //   Original bug: b/27045736
+            //   New bug: b/27960286
+            if (false) {
+                // Assert that our sequence number matches mParent's.  If it isn't that means
+                // we have been reset and our.  If our sequence is UNITIALIZED_SEQUENCE, then 
+                // it's possible that everything is working fine and we just haven't been
+                // written to since the last resetTable().
+                if (mSequence != mParent.mSequence) {
+                    if (mSequence < mParent.mSequence) {
+                        logOrThrow("Sequence mismatch. SparseMappingTable.reset()"
+                                + " called but not Table.resetTable() -- "
+                                + dumpInternalState());
+                        return;
+                    } else if (mSequence > mParent.mSequence) {
+                        logOrThrow("Sequence mismatch. Table.resetTable()"
+                                + " called but not SparseMappingTable.reset() -- "
+                                + dumpInternalState());
+                        return;
+                    }
                 }
             }
         }
@@ -488,6 +477,10 @@
         }
     }
 
+    public SparseMappingTable() {
+        mLongs.add(new long[ARRAY_SIZE]);
+    }
+
     /**
      * Wipe out all the data.
      */
@@ -539,6 +532,35 @@
     }
 
     /**
+     * Return a string for debugging.
+     */
+    public String dumpInternalState(boolean includeData) {
+        final StringBuilder sb = new StringBuilder();
+        sb.append("SparseMappingTable{");
+        sb.append("mSequence=");
+        sb.append(mSequence);
+        sb.append(" mNextIndex=");
+        sb.append(mNextIndex);
+        sb.append(" mLongs.size=");
+        final int N = mLongs.size();
+        sb.append(N);
+        sb.append("\n");
+        if (includeData) {
+            for (int i=0; i<N; i++) {
+                final long[] array = mLongs.get(i);
+                for (int j=0; j<array.length; j++) {
+                    if (i == N-1 && j == mNextIndex) {
+                        break;
+                    }
+                    sb.append(String.format(" %4d %d 0x%016x %-19d\n", i, j, array[j], array[j]));
+                }
+            }
+        }
+        sb.append("}");
+        return sb.toString();
+    }
+
+    /**
      * Write the long array to the parcel in a compacted form.  Does not allow negative
      * values in the array.
      */
@@ -553,7 +575,7 @@
                 out.writeInt((int)val);
             } else {
                 int top = ~((int)((val>>32)&0x7fffffff));
-                int bottom = (int)(val&0xfffffff);
+                int bottom = (int)(val&0x0ffffffffL);
                 out.writeInt(top);
                 out.writeInt(bottom);
             }
@@ -623,7 +645,7 @@
      * this is an eng build.)
      */
     private static void logOrThrow(String message, Throwable th) {
-        Slog.wtf(TAG, message, th);
+        Slog.e(TAG, message, th);
         if (Build.TYPE.equals("eng")) {
             throw new RuntimeException(message, th);
         }
diff --git a/core/java/com/android/internal/inputmethod/InputMethodSubtypeSwitchingController.java b/core/java/com/android/internal/inputmethod/InputMethodSubtypeSwitchingController.java
index 85cc841..8d11783 100644
--- a/core/java/com/android/internal/inputmethod/InputMethodSubtypeSwitchingController.java
+++ b/core/java/com/android/internal/inputmethod/InputMethodSubtypeSwitchingController.java
@@ -16,6 +16,7 @@
 
 package com.android.internal.inputmethod;
 
+import android.annotation.Nullable;
 import android.content.Context;
 import android.content.pm.PackageManager;
 import android.text.TextUtils;
@@ -284,8 +285,22 @@
             return -1;
         }
 
+        /**
+         * Provides the basic operation to implement bi-directional IME rotation.
+         * @param onlyCurrentIme {@code true} to limit the search space to IME subtypes that belong
+         * to {@code imi}.
+         * @param imi {@link InputMethodInfo} that will be used in conjunction with {@code subtype}
+         * from which we find the adjacent IME subtype.
+         * @param subtype {@link InputMethodSubtype} that will be used in conjunction with
+         * {@code imi} from which we find the next IME subtype.  {@code null} if the input method
+         * does not have a subtype.
+         * @param forward {@code true} to do forward search the next IME subtype. Specify
+         * {@code false} to do backward search.
+         * @return The IME subtype found. {@code null} if no IME subtype is found.
+         */
+        @Nullable
         public ImeSubtypeListItem getNextInputMethodLocked(boolean onlyCurrentIme,
-                InputMethodInfo imi, InputMethodSubtype subtype) {
+                InputMethodInfo imi, @Nullable InputMethodSubtype subtype, boolean forward) {
             if (imi == null) {
                 return null;
             }
@@ -297,8 +312,9 @@
                 return null;
             }
             final int N = mImeSubtypeList.size();
-            for (int offset = 1; offset < N; ++offset) {
-                // Start searching the next IME/subtype from the next of the current index.
+            for (int i = 1; i < N; ++i) {
+                // Start searching the next IME/subtype from +/- 1 indices.
+                final int offset = forward ? i : N - i;
                 final int candidateIndex = (currentIndex + offset) % N;
                 final ImeSubtypeListItem candidate = mImeSubtypeList.get(candidateIndex);
                 // Skip if searching inside the current IME only, but the candidate is not
@@ -370,8 +386,22 @@
             mUsageHistoryOfSubtypeListItemIndex[0] = currentItemIndex;
         }
 
+        /**
+         * Provides the basic operation to implement bi-directional IME rotation.
+         * @param onlyCurrentIme {@code true} to limit the search space to IME subtypes that belong
+         * to {@code imi}.
+         * @param imi {@link InputMethodInfo} that will be used in conjunction with {@code subtype}
+         * from which we find the adjacent IME subtype.
+         * @param subtype {@link InputMethodSubtype} that will be used in conjunction with
+         * {@code imi} from which we find the next IME subtype.  {@code null} if the input method
+         * does not have a subtype.
+         * @param forward {@code true} to do forward search the next IME subtype. Specify
+         * {@code false} to do backward search.
+         * @return The IME subtype found. {@code null} if no IME subtype is found.
+         */
+        @Nullable
         public ImeSubtypeListItem getNextInputMethodLocked(boolean onlyCurrentIme,
-                InputMethodInfo imi, InputMethodSubtype subtype) {
+                InputMethodInfo imi, @Nullable InputMethodSubtype subtype, boolean forward) {
             int currentUsageRank = getUsageRank(imi, subtype);
             if (currentUsageRank < 0) {
                 if (DEBUG) {
@@ -381,7 +411,8 @@
             }
             final int N = mUsageHistoryOfSubtypeListItemIndex.length;
             for (int i = 1; i < N; i++) {
-                final int subtypeListItemRank = (currentUsageRank + i) % N;
+                final int offset = forward ? i : N - i;
+                final int subtypeListItemRank = (currentUsageRank + offset) % N;
                 final int subtypeListItemIndex =
                         mUsageHistoryOfSubtypeListItemIndex[subtypeListItemRank];
                 final ImeSubtypeListItem subtypeListItem =
@@ -454,17 +485,31 @@
             mSwitchingUnawareRotationList = switchingUnawareRotationList;
         }
 
+        /**
+         * Provides the basic operation to implement bi-directional IME rotation.
+         * @param onlyCurrentIme {@code true} to limit the search space to IME subtypes that belong
+         * to {@code imi}.
+         * @param imi {@link InputMethodInfo} that will be used in conjunction with {@code subtype}
+         * from which we find the adjacent IME subtype.
+         * @param subtype {@link InputMethodSubtype} that will be used in conjunction with
+         * {@code imi} from which we find the next IME subtype.  {@code null} if the input method
+         * does not have a subtype.
+         * @param forward {@code true} to do forward search the next IME subtype. Specify
+         * {@code false} to do backward search.
+         * @return The IME subtype found. {@code null} if no IME subtype is found.
+         */
+        @Nullable
         public ImeSubtypeListItem getNextInputMethod(boolean onlyCurrentIme, InputMethodInfo imi,
-                InputMethodSubtype subtype) {
+                @Nullable InputMethodSubtype subtype, boolean forward) {
             if (imi == null) {
                 return null;
             }
             if (imi.supportsSwitchingToNextInputMethod()) {
                 return mSwitchingAwareRotationList.getNextInputMethodLocked(onlyCurrentIme, imi,
-                        subtype);
+                        subtype, forward);
             } else {
                 return mSwitchingUnawareRotationList.getNextInputMethodLocked(onlyCurrentIme, imi,
-                        subtype);
+                        subtype, forward);
             }
         }
 
@@ -532,14 +577,14 @@
     }
 
     public ImeSubtypeListItem getNextInputMethodLocked(boolean onlyCurrentIme, InputMethodInfo imi,
-            InputMethodSubtype subtype) {
+            InputMethodSubtype subtype, boolean forward) {
         if (mController == null) {
             if (DEBUG) {
                 Log.e(TAG, "mController shouldn't be null.");
             }
             return null;
         }
-        return mController.getNextInputMethod(onlyCurrentIme, imi, subtype);
+        return mController.getNextInputMethod(onlyCurrentIme, imi, subtype, forward);
     }
 
     public List<ImeSubtypeListItem> getSortedInputMethodAndSubtypeListLocked(
diff --git a/core/java/com/android/internal/os/InstallerConnection.java b/core/java/com/android/internal/os/InstallerConnection.java
index 2a9264d..47f2c70 100644
--- a/core/java/com/android/internal/os/InstallerConnection.java
+++ b/core/java/com/android/internal/os/InstallerConnection.java
@@ -103,21 +103,7 @@
         }
     }
 
-    public void execute(String cmd, Object... args) throws InstallerException {
-        final String resRaw = executeForResult(cmd, args);
-        int res = -1;
-        try {
-            res = Integer.parseInt(resRaw);
-        } catch (NumberFormatException ignored) {
-        }
-        if (res != 0) {
-            throw new InstallerException(
-                    "Failed to execute " + cmd + " " + Arrays.toString(args) + ": " + res);
-        }
-    }
-
-    public String executeForResult(String cmd, Object... args)
-            throws InstallerException {
+    public String[] execute(String cmd, Object... args) throws InstallerException {
         final StringBuilder builder = new StringBuilder(cmd);
         for (Object arg : args) {
             String escaped;
@@ -135,7 +121,17 @@
             }
             builder.append(' ').append(escaped);
         }
-        return transact(builder.toString());
+        final String[] resRaw = transact(builder.toString()).split(" ");
+        int res = -1;
+        try {
+            res = Integer.parseInt(resRaw[0]);
+        } catch (ArrayIndexOutOfBoundsException | NumberFormatException ignored) {
+        }
+        if (res != 0) {
+            throw new InstallerException(
+                    "Failed to execute " + cmd + " " + Arrays.toString(args) + ": " + res);
+        }
+        return resRaw;
     }
 
     public void dexopt(String apkPath, int uid, String instructionSet, int dexoptNeeded,
@@ -160,19 +156,15 @@
     }
 
     public boolean mergeProfiles(int uid, String pkgName) throws InstallerException {
-        String rawReply = executeForResult("merge_profiles", uid, pkgName);
-        if (rawReply == null) {
-            throw new IllegalStateException("Unexpected null reply");
-        }
-        final String res[] = rawReply.split(" ");
+        final String[] res = execute("merge_profiles", uid, pkgName);
 
         if ((res == null) || (res.length != 2)) {
-            throw new InstallerException("Invalid size result: " + rawReply);
+            throw new InstallerException("Invalid size result: " + Arrays.toString(res));
         }
 
         // Just as a sanity check. Anything != "true" will be interpreted as false by parseBoolean.
         if (!res[1].equals("true") && !res[1].equals("false")) {
-            throw new InstallerException("Invalid boolean result: " + rawReply);
+            throw new InstallerException("Invalid boolean result: " + Arrays.toString(res));
         }
 
         return Boolean.parseBoolean(res[1]);
diff --git a/core/java/com/android/internal/os/ZygoteInit.java b/core/java/com/android/internal/os/ZygoteInit.java
index 5980ab6..78b5d61 100644
--- a/core/java/com/android/internal/os/ZygoteInit.java
+++ b/core/java/com/android/internal/os/ZygoteInit.java
@@ -43,6 +43,7 @@
 import dalvik.system.DexFile;
 import dalvik.system.PathClassLoader;
 import dalvik.system.VMRuntime;
+import dalvik.system.ZygoteHooks;
 
 import libcore.io.IoUtils;
 
@@ -597,6 +598,10 @@
     }
 
     public static void main(String argv[]) {
+        // Mark zygote start. This ensures that thread creation will throw
+        // an error.
+        ZygoteHooks.startZygoteNoThreadCreation();
+
         try {
             Trace.traceBegin(Trace.TRACE_TAG_DALVIK, "ZygoteInit");
             RuntimeInit.enableDdms();
@@ -648,6 +653,8 @@
             // Zygote process unmounts root storage spaces.
             Zygote.nativeUnmountStorageOnInit();
 
+            ZygoteHooks.stopZygoteNoThreadCreation();
+
             if (startSystemServer) {
                 startSystemServer(abiList, socketName);
             }
diff --git a/core/java/com/android/internal/policy/DecorView.java b/core/java/com/android/internal/policy/DecorView.java
index ea0fbda..3aa7719 100644
--- a/core/java/com/android/internal/policy/DecorView.java
+++ b/core/java/com/android/internal/policy/DecorView.java
@@ -45,7 +45,6 @@
 import android.graphics.Rect;
 import android.graphics.Shader;
 import android.graphics.drawable.Drawable;
-import android.os.Build;
 import android.os.RemoteException;
 import android.util.DisplayMetrics;
 import android.util.Log;
@@ -81,6 +80,8 @@
 import static android.app.ActivityManager.StackId.FULLSCREEN_WORKSPACE_STACK_ID;
 import static android.app.ActivityManager.StackId.INVALID_STACK_ID;
 import static android.content.res.Configuration.ORIENTATION_PORTRAIT;
+import static android.os.Build.VERSION_CODES.M;
+import static android.os.Build.VERSION_CODES.N;
 import static android.view.View.MeasureSpec.AT_MOST;
 import static android.view.View.MeasureSpec.EXACTLY;
 import static android.view.View.MeasureSpec.getMode;
@@ -171,7 +172,7 @@
     private final Interpolator mShowInterpolator;
     private final Interpolator mHideInterpolator;
     private final int mBarEnterExitDuration;
-    private final boolean mForceWindowDrawsStatusBarBackground;
+    final boolean mForceWindowDrawsStatusBarBackground;
     private final int mSemiTransparentStatusBarColor;
 
     private final BackgroundFallback mBackgroundFallback = new BackgroundFallback();
@@ -209,7 +210,6 @@
     private Drawable mResizingBackgroundDrawable;
     private Drawable mCaptionBackgroundDrawable;
     private Drawable mUserCaptionBackgroundDrawable;
-    private Drawable mOriginalBackgroundDrawable;
 
     private float mAvailableWidth;
 
@@ -236,7 +236,8 @@
         mBarEnterExitDuration = context.getResources().getInteger(
                 R.integer.dock_enter_exit_duration);
         mForceWindowDrawsStatusBarBackground = context.getResources().getBoolean(
-                R.bool.config_forceWindowDrawsStatusBarBackground);
+                R.bool.config_forceWindowDrawsStatusBarBackground)
+                && context.getApplicationInfo().targetSdkVersion >= N;
         mSemiTransparentStatusBarColor = context.getResources().getColor(
                 R.color.system_bar_background_semi_transparent, null /* theme */);
 
@@ -889,11 +890,6 @@
                 mBackgroundPadding.setEmpty();
             }
             drawableChanged();
-
-            // Make sure we don't reset to the old drawable when finishing resizing.
-            if (mResizeMode != RESIZE_MODE_INVALID) {
-                mOriginalBackgroundDrawable = null;
-            }
         }
     }
 
@@ -1458,6 +1454,8 @@
             st.menu.close();
         }
 
+        releaseThreadedRenderer();
+
         if (mWindowResizeCallbacksAdded) {
             getViewRootImpl().removeWindowCallbacks(this);
             mWindowResizeCallbacksAdded = false;
@@ -1956,9 +1954,6 @@
             updateElevation();
 
             updateColorViews(null /* insets */, false);
-
-            mOriginalBackgroundDrawable = getBackground();
-            setBackgroundDrawable(null);
         }
         mResizeMode = resizeMode;
         getViewRootImpl().requestInvalidateRootRenderNode();
@@ -1970,10 +1965,6 @@
         updateColorViews(null /* insets */, false);
         mResizeMode = RESIZE_MODE_INVALID;
         getViewRootImpl().requestInvalidateRootRenderNode();
-        if (mOriginalBackgroundDrawable != null) {
-            setBackgroundDrawable(mOriginalBackgroundDrawable);
-            mOriginalBackgroundDrawable = null;
-        }
     }
 
     @Override
@@ -2208,7 +2199,7 @@
         public void onDestroyActionMode(ActionMode mode) {
             mWrapped.onDestroyActionMode(mode);
             final boolean isMncApp = mContext.getApplicationInfo().targetSdkVersion
-                    >= Build.VERSION_CODES.M;
+                    >= M;
             final boolean isPrimary;
             final boolean isFloating;
             if (isMncApp) {
diff --git a/core/java/com/android/internal/policy/DividerSnapAlgorithm.java b/core/java/com/android/internal/policy/DividerSnapAlgorithm.java
index 9907ea9..669e1ef 100644
--- a/core/java/com/android/internal/policy/DividerSnapAlgorithm.java
+++ b/core/java/com/android/internal/policy/DividerSnapAlgorithm.java
@@ -17,9 +17,13 @@
 package com.android.internal.policy;
 
 import android.content.Context;
+import android.content.res.Configuration;
 import android.content.res.Resources;
 import android.graphics.Rect;
+import android.hardware.display.DisplayManager;
 import android.util.Log;
+import android.view.Display;
+import android.view.DisplayInfo;
 
 import java.util.ArrayList;
 
@@ -57,6 +61,7 @@
     private final ArrayList<SnapTarget> mTargets = new ArrayList<>();
     private final Rect mInsets = new Rect();
     private final int mSnapMode;
+    private final int mMinimalSizeResizableTask;
     private final float mFixedRatio;
     private boolean mIsHorizontalDivision;
 
@@ -70,6 +75,22 @@
     private final SnapTarget mDismissEndTarget;
     private final SnapTarget mMiddleTarget;
 
+    public static DividerSnapAlgorithm create(Context ctx, Rect insets) {
+        DisplayInfo displayInfo = new DisplayInfo();
+        ctx.getSystemService(DisplayManager.class).getDisplay(
+                Display.DEFAULT_DISPLAY).getDisplayInfo(displayInfo);
+        int dividerWindowWidth = ctx.getResources().getDimensionPixelSize(
+                com.android.internal.R.dimen.docked_stack_divider_thickness);
+        int dividerInsets = ctx.getResources().getDimensionPixelSize(
+                com.android.internal.R.dimen.docked_stack_divider_insets);
+        return new DividerSnapAlgorithm(ctx.getResources(),
+                displayInfo.logicalWidth, displayInfo.logicalHeight,
+                dividerWindowWidth - 2 * dividerInsets,
+                ctx.getResources().getConfiguration().orientation
+                        == Configuration.ORIENTATION_PORTRAIT,
+                insets);
+    }
+
     public DividerSnapAlgorithm(Resources res, int displayWidth, int displayHeight, int dividerSize,
             boolean isHorizontalDivision, Rect insets) {
         mMinFlingVelocityPxPerSecond =
@@ -85,6 +106,8 @@
                 com.android.internal.R.integer.config_dockedStackDividerSnapMode);
         mFixedRatio = res.getFraction(
                 com.android.internal.R.fraction.docked_stack_divider_fixed_ratio, 1, 1);
+        mMinimalSizeResizableTask = res.getDimensionPixelSize(
+                com.android.internal.R.dimen.default_minimal_size_resizable_task);
         calculateTargets(isHorizontalDivision);
         mFirstSplitTarget = mTargets.get(1);
         mLastSplitTarget = mTargets.get(mTargets.size() - 2);
@@ -93,6 +116,20 @@
         mMiddleTarget = mTargets.get(mTargets.size() / 2);
     }
 
+    /**
+     * @return whether it's feasible to enable split screen in the current configuration, i.e. when
+     *         snapping in the middle both tasks are larger than the minimal task size.
+     */
+    public boolean isSplitScreenFeasible() {
+        int statusBarSize = mInsets.top;
+        int navBarSize = mIsHorizontalDivision ? mInsets.bottom : mInsets.right;
+        int size = mIsHorizontalDivision
+                ? mDisplayHeight
+                : mDisplayWidth;
+        int availableSpace = size - navBarSize - statusBarSize - mDividerSize;
+        return availableSpace / 2 >= mMinimalSizeResizableTask;
+    }
+
     public SnapTarget calculateSnapTarget(int position, float velocity) {
         return calculateSnapTarget(position, velocity, true /* hardDismiss */);
     }
@@ -212,10 +249,10 @@
         mTargets.add(new SnapTarget(-mDividerSize, SnapTarget.FLAG_DISMISS_START, 0.35f));
         switch (mSnapMode) {
             case SNAP_MODE_16_9:
-                addRatio16_9Targets(isHorizontalDivision);
+                addRatio16_9Targets(isHorizontalDivision, dividerMax);
                 break;
             case SNAP_FIXED_RATIO:
-                addFixedDivisionTargets(isHorizontalDivision);
+                addFixedDivisionTargets(isHorizontalDivision, dividerMax);
                 break;
             case SNAP_ONLY_1_1:
                 addMiddleTarget(isHorizontalDivision);
@@ -225,19 +262,24 @@
         mTargets.add(new SnapTarget(dividerMax - navBarSize, SnapTarget.FLAG_DISMISS_END, 0.35f));
     }
 
-    private void addFixedDivisionTargets(boolean isHorizontalDivision) {
+    private void addNonDismissingTargets(boolean isHorizontalDivision, int topPosition,
+            int bottomPosition, int dividerMax) {
+        maybeAddTarget(topPosition, topPosition - mInsets.top);
+        addMiddleTarget(isHorizontalDivision);
+        maybeAddTarget(bottomPosition, dividerMax - mInsets.bottom
+                - (bottomPosition + mDividerSize));
+    }
+    private void addFixedDivisionTargets(boolean isHorizontalDivision, int dividerMax) {
         int start = isHorizontalDivision ? mInsets.top : mInsets.left;
         int end = isHorizontalDivision
                 ? mDisplayHeight - mInsets.bottom
                 : mDisplayWidth - mInsets.right;
-        mTargets.add(new SnapTarget((int) (start + mFixedRatio * (end - start)) - mDividerSize / 2,
-                SnapTarget.FLAG_NONE));
-        addMiddleTarget(isHorizontalDivision);
-        mTargets.add(new SnapTarget((int) (start + (1 - mFixedRatio) * (end - start))
-                - mDividerSize / 2, SnapTarget.FLAG_NONE));
+        int topPosition = (int) (start + mFixedRatio * (end - start)) - mDividerSize / 2;
+        int bottomPosition = (int) (start + (1 - mFixedRatio) * (end - start)) - mDividerSize / 2;
+        addNonDismissingTargets(isHorizontalDivision, topPosition, bottomPosition, dividerMax);
     }
 
-    private void addRatio16_9Targets(boolean isHorizontalDivision) {
+    private void addRatio16_9Targets(boolean isHorizontalDivision, int dividerMax) {
         int start = isHorizontalDivision ? mInsets.top : mInsets.left;
         int end = isHorizontalDivision
                 ? mDisplayHeight - mInsets.bottom
@@ -248,9 +290,19 @@
                 : mDisplayHeight - mInsets.bottom;
         float size = 9.0f / 16.0f * (endOther - startOther);
         int sizeInt = (int) Math.floor(size);
-        mTargets.add(new SnapTarget(start + sizeInt, SnapTarget.FLAG_NONE));
-        addMiddleTarget(isHorizontalDivision);
-        mTargets.add(new SnapTarget(end - sizeInt - mDividerSize, SnapTarget.FLAG_NONE));
+        int topPosition = start + sizeInt;
+        int bottomPosition = end - sizeInt - mDividerSize;
+        addNonDismissingTargets(isHorizontalDivision, topPosition, bottomPosition, dividerMax);
+    }
+
+    /**
+     * Adds a target at {@param position} but only if the area with size of {@param smallerSize}
+     * meets the minimal size requirement.
+     */
+    private void maybeAddTarget(int position, int smallerSize) {
+        if (smallerSize >= mMinimalSizeResizableTask) {
+            mTargets.add(new SnapTarget(position, SnapTarget.FLAG_NONE));
+        }
     }
 
     private void addMiddleTarget(boolean isHorizontalDivision) {
diff --git a/core/java/com/android/internal/policy/PhoneWindow.java b/core/java/com/android/internal/policy/PhoneWindow.java
index 0f257d7..d2ff9bc 100644
--- a/core/java/com/android/internal/policy/PhoneWindow.java
+++ b/core/java/com/android/internal/policy/PhoneWindow.java
@@ -516,8 +516,8 @@
         }
         mTitle = title;
         WindowManager.LayoutParams params = getAttributes();
-        if (!TextUtils.equals(title, params.getTitle())) {
-            params.setTitle(title);
+        if (!TextUtils.equals(title, params.accessibilityTitle)) {
+            params.accessibilityTitle = TextUtils.stringOrSpannedString(title);
             dispatchWindowAttributesChanged(getAttributes());
         }
     }
@@ -2435,6 +2435,8 @@
             mNavigationBarColor = a.getColor(R.styleable.Window_navigationBarColor, 0xFF000000);
         }
 
+        WindowManager.LayoutParams params = getAttributes();
+
         // Non-floating windows on high end devices must put up decor beneath the system bars and
         // therefore must know about visibility changes of those.
         if (!mIsFloating && ActivityManager.isHighEndGfx()) {
@@ -2444,6 +2446,9 @@
                 setFlags(FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS,
                         FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS & ~getForcedWindowFlags());
             }
+            if (mDecor.mForceWindowDrawsStatusBarBackground) {
+                params.privateFlags |= PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
+            }
         }
         if (a.getBoolean(R.styleable.Window_windowLightStatusBar, false)) {
             decor.setSystemUiVisibility(
@@ -2459,8 +2464,6 @@
             }
         }
 
-        WindowManager.LayoutParams params = getAttributes();
-
         if (!hasSoftInputMode()) {
             params.softInputMode = a.getInt(
                     R.styleable.Window_windowSoftInputMode,
diff --git a/core/java/com/android/internal/util/ArrayUtils.java b/core/java/com/android/internal/util/ArrayUtils.java
index bed5a2e..18f715e 100644
--- a/core/java/com/android/internal/util/ArrayUtils.java
+++ b/core/java/com/android/internal/util/ArrayUtils.java
@@ -27,6 +27,7 @@
 import java.lang.reflect.Array;
 import java.util.ArrayList;
 import java.util.Arrays;
+import java.util.Collection;
 import java.util.Collections;
 import java.util.List;
 import java.util.Objects;
@@ -128,7 +129,7 @@
     /**
      * Checks if given array is null or has zero elements.
      */
-    public static boolean isEmpty(@Nullable List<?> array) {
+    public static boolean isEmpty(@Nullable Collection<?> array) {
         return array == null || array.isEmpty();
     }
 
@@ -451,7 +452,7 @@
         }
     }
 
-    public static <T> boolean contains(@Nullable ArrayList<T> cur, T val) {
+    public static <T> boolean contains(@Nullable Collection<T> cur, T val) {
         return (cur != null) ? cur.contains(val) : false;
     }
 
diff --git a/core/java/com/android/internal/util/Protocol.java b/core/java/com/android/internal/util/Protocol.java
index 5992f7a..b075db8 100644
--- a/core/java/com/android/internal/util/Protocol.java
+++ b/core/java/com/android/internal/util/Protocol.java
@@ -57,7 +57,7 @@
     public static final int BASE_DATA_CONNECTION                                    = 0x00040000;
     public static final int BASE_DATA_CONNECTION_AC                                 = 0x00041000;
     public static final int BASE_DATA_CONNECTION_TRACKER                            = 0x00042000;
-    public static final int BASE_DNS_PINGER                                         = 0x00050000;
+    public static final int BASE_TETHERING                                          = 0x00050000;
     public static final int BASE_NSD_MANAGER                                        = 0x00060000;
     public static final int BASE_NETWORK_STATE_TRACKER                              = 0x00070000;
     public static final int BASE_CONNECTIVITY_MANAGER                               = 0x00080000;
diff --git a/core/java/com/android/internal/widget/ImageFloatingTextView.java b/core/java/com/android/internal/widget/ImageFloatingTextView.java
index 78c5e34..e2d8ffc 100644
--- a/core/java/com/android/internal/widget/ImageFloatingTextView.java
+++ b/core/java/com/android/internal/widget/ImageFloatingTextView.java
@@ -16,13 +16,18 @@
 
 package com.android.internal.widget;
 
+import com.android.internal.R;
+
 import android.annotation.Nullable;
 import android.content.Context;
+import android.content.res.Configuration;
+import android.content.res.TypedArray;
 import android.text.BoringLayout;
 import android.text.Layout;
 import android.text.StaticLayout;
 import android.text.TextUtils;
 import android.util.AttributeSet;
+import android.util.TypedValue;
 import android.view.RemotableViewMethod;
 import android.widget.RemoteViews;
 import android.widget.TextView;
@@ -35,7 +40,8 @@
 @RemoteViews.RemoteView
 public class ImageFloatingTextView extends TextView {
 
-    private boolean mHasImage;
+    /** Number of lines from the top to indent */
+    private int mIndentLines;
 
     public ImageFloatingTextView(Context context) {
         this(context, null);
@@ -69,10 +75,16 @@
                 .setEllipsizedWidth(ellipsisWidth)
                 .setBreakStrategy(Layout.BREAK_STRATEGY_HIGH_QUALITY)
                 .setHyphenationFrequency(Layout.HYPHENATION_FREQUENCY_FULL);
-        // we set the endmargin on the first 2 lines. this works just in our case but that's
-        // sufficient for now.
-        int endMargin = (int) (getResources().getDisplayMetrics().density * 52);
-        int[] margins = mHasImage ? new int[] {endMargin, endMargin, 0} : null;
+        // we set the endmargin on the requested number of lines.
+        int endMargin = getContext().getResources().getDimensionPixelSize(
+                R.dimen.notification_content_picture_margin);
+        int[] margins = null;
+        if (mIndentLines > 0) {
+            margins = new int[mIndentLines + 1];
+            for (int i = 0; i < mIndentLines; i++) {
+                margins[i] = endMargin;
+            }
+        }
         if (getLayoutDirection() == LAYOUT_DIRECTION_RTL) {
             builder.setIndents(margins, null);
         } else {
@@ -84,8 +96,22 @@
 
     @RemotableViewMethod
     public void setHasImage(boolean hasImage) {
-        mHasImage = hasImage;
+        mIndentLines = hasImage ? 2 : 0;
         // The new layout will be automatically created when the text is
         // set again by the notification.
     }
+
+    /**
+     * @param lines the number of lines at the top that should be indented by indentEnd
+     * @return whether a change was made
+     */
+    public boolean setNumIndentLines(int lines) {
+        if (mIndentLines != lines) {
+            mIndentLines = lines;
+            // Invalidate layout.
+            setHint(getHint());
+            return true;
+        }
+        return false;
+    }
 }
diff --git a/core/java/com/android/internal/widget/MessagingLinearLayout.java b/core/java/com/android/internal/widget/MessagingLinearLayout.java
new file mode 100644
index 0000000..dc7b7f5
--- /dev/null
+++ b/core/java/com/android/internal/widget/MessagingLinearLayout.java
@@ -0,0 +1,278 @@
+/*
+ * 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 com.android.internal.widget;
+
+import com.android.internal.R;
+
+import android.annotation.Nullable;
+import android.content.Context;
+import android.content.res.TypedArray;
+import android.graphics.Canvas;
+import android.util.AttributeSet;
+import android.view.RemotableViewMethod;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.RemoteViews;
+
+/**
+ * A custom-built layout for the Notification.MessagingStyle.
+ *
+ * Evicts children until they all fit.
+ */
+@RemoteViews.RemoteView
+public class MessagingLinearLayout extends ViewGroup {
+
+    /**
+     * Spacing to be applied between views.
+     */
+    private int mSpacing;
+
+    /**
+     * The maximum height allowed.
+     */
+    private int mMaxHeight;
+
+    private int mIndentLines;
+
+    public MessagingLinearLayout(Context context, @Nullable AttributeSet attrs) {
+        super(context, attrs);
+
+        final TypedArray a = context.obtainStyledAttributes(attrs,
+                R.styleable.MessagingLinearLayout, 0,
+                0);
+
+        final int N = a.getIndexCount();
+        for (int i = 0; i < N; i++) {
+            int attr = a.getIndex(i);
+            switch (attr) {
+                case R.styleable.MessagingLinearLayout_maxHeight:
+                    mMaxHeight = a.getDimensionPixelSize(i, 0);
+                    break;
+                case R.styleable.MessagingLinearLayout_spacing:
+                    mSpacing = a.getDimensionPixelSize(i, 0);
+                    break;
+            }
+        }
+
+        if (mMaxHeight <= 0) {
+            throw new IllegalStateException(
+                    "MessagingLinearLayout: Must specify positive maxHeight");
+        }
+
+        a.recycle();
+    }
+
+
+    @Override
+    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+        // This is essentially a bottom-up linear layout that only adds children that fit entirely
+        // up to a maximum height.
+
+        switch (MeasureSpec.getMode(heightMeasureSpec)) {
+            case MeasureSpec.AT_MOST:
+                heightMeasureSpec = MeasureSpec.makeMeasureSpec(
+                        Math.min(mMaxHeight, MeasureSpec.getSize(heightMeasureSpec)),
+                        MeasureSpec.AT_MOST);
+                break;
+            case MeasureSpec.UNSPECIFIED:
+                heightMeasureSpec = MeasureSpec.makeMeasureSpec(
+                        mMaxHeight,
+                        MeasureSpec.AT_MOST);
+                break;
+            case MeasureSpec.EXACTLY:
+                break;
+        }
+        final int targetHeight = MeasureSpec.getSize(heightMeasureSpec);
+        final int count = getChildCount();
+
+        for (int i = 0; i < count; ++i) {
+            final View child = getChildAt(i);
+            final LayoutParams lp = (LayoutParams) child.getLayoutParams();
+            lp.hide = true;
+        }
+
+        int totalHeight = mPaddingTop + mPaddingBottom;
+        boolean first = true;
+
+        // Starting from the bottom: we measure every view as if it were the only one. If it still
+        // fits, we take it, otherwise we stop there.
+        for (int i = count - 1; i >= 0 && totalHeight < targetHeight; i--) {
+            if (getChildAt(i).getVisibility() == GONE) {
+                continue;
+            }
+            final View child = getChildAt(i);
+            LayoutParams lp = (LayoutParams) getChildAt(i).getLayoutParams();
+
+            if (child instanceof ImageFloatingTextView) {
+                // Pretend we need the image padding for all views, we don't know which
+                // one will end up needing to do this (might end up not using all the space,
+                // but calculating this exactly would be more expensive).
+                ((ImageFloatingTextView) child).setNumIndentLines(mIndentLines);
+            }
+
+            measureChildWithMargins(child, widthMeasureSpec, 0, heightMeasureSpec, 0);
+
+            final int childHeight = child.getMeasuredHeight();
+            int newHeight = Math.max(totalHeight, totalHeight + childHeight + lp.topMargin +
+                    lp.bottomMargin + (first ? 0 : mSpacing));
+            first = false;
+
+            if (newHeight <= targetHeight) {
+                totalHeight = newHeight;
+                lp.hide = false;
+            } else {
+                break;
+            }
+        }
+
+        // Now that we know which views to take, fix up the indents and see what width we get.
+        int measuredWidth = mPaddingLeft + mPaddingRight;
+        int imageLines = mIndentLines;
+        for (int i = 0; i < count; i++) {
+            final View child = getChildAt(i);
+            final LayoutParams lp = (LayoutParams) child.getLayoutParams();
+
+            if (child.getVisibility() == GONE || lp.hide) {
+                continue;
+            }
+
+            if (child instanceof ImageFloatingTextView) {
+                ImageFloatingTextView textChild = (ImageFloatingTextView) child;
+                if (imageLines == 2 && textChild.getLineCount() > 2) {
+                    // HACK: If we need indent for two lines, and they're coming from the same
+                    // view, we need extra spacing to compensate for the lack of margins,
+                    // so add an extra line of indent.
+                    imageLines = 3;
+                }
+                boolean changed = textChild.setNumIndentLines(Math.max(0, imageLines));
+                if (changed) {
+                    measureChildWithMargins(child, widthMeasureSpec, 0, heightMeasureSpec, 0);
+                }
+                imageLines -= textChild.getLineCount();
+            }
+
+            measuredWidth = Math.max(measuredWidth,
+                    child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin
+                            + mPaddingLeft + mPaddingRight);
+        }
+
+
+        setMeasuredDimension(
+                resolveSize(Math.max(getSuggestedMinimumWidth(), measuredWidth),
+                        widthMeasureSpec),
+                resolveSize(Math.max(getSuggestedMinimumHeight(), totalHeight),
+                        heightMeasureSpec));
+    }
+
+    @Override
+    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+        final int paddingLeft = mPaddingLeft;
+
+        int childTop;
+
+        // Where right end of child should go
+        final int width = right - left;
+        final int childRight = width - mPaddingRight;
+
+        final int layoutDirection = getLayoutDirection();
+        final int count = getChildCount();
+
+        childTop = mPaddingTop;
+
+        boolean first = true;
+
+        for (int i = 0; i < count; i++) {
+            final View child = getChildAt(i);
+            final LayoutParams lp = (LayoutParams) child.getLayoutParams();
+
+            if (child.getVisibility() == GONE || lp.hide) {
+                continue;
+            }
+
+            final int childWidth = child.getMeasuredWidth();
+            final int childHeight = child.getMeasuredHeight();
+
+            int childLeft;
+            if (layoutDirection == LAYOUT_DIRECTION_RTL) {
+                childLeft = childRight - childWidth - lp.rightMargin;
+            } else {
+                childLeft = paddingLeft + lp.leftMargin;
+            }
+
+            if (!first) {
+                childTop += mSpacing;
+            }
+
+            childTop += lp.topMargin;
+            child.layout(childLeft, childTop, childLeft + childWidth, childTop + childHeight);
+
+            childTop += childHeight + lp.bottomMargin;
+
+            first = false;
+        }
+    }
+
+    @Override
+    protected boolean drawChild(Canvas canvas, View child, long drawingTime) {
+        final LayoutParams lp = (LayoutParams) child.getLayoutParams();
+        if (lp.hide) {
+            return true;
+        }
+        return super.drawChild(canvas, child, drawingTime);
+    }
+
+    @Override
+    public LayoutParams generateLayoutParams(AttributeSet attrs) {
+        return new LayoutParams(mContext, attrs);
+    }
+
+    @Override
+    protected LayoutParams generateDefaultLayoutParams() {
+        return new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
+
+    }
+
+    @Override
+    protected LayoutParams generateLayoutParams(ViewGroup.LayoutParams lp) {
+        LayoutParams copy = new LayoutParams(lp.width, lp.height);
+        if (lp instanceof MarginLayoutParams) {
+            copy.copyMarginsFrom((MarginLayoutParams) lp);
+        }
+        return copy;
+    }
+
+    @RemotableViewMethod
+    /**
+     * Sets how many lines should be indented to avoid a floating image.
+     */
+    public void setNumIndentLines(int numberLines) {
+        mIndentLines = numberLines;
+    }
+
+    public static class LayoutParams extends MarginLayoutParams {
+
+        boolean hide = false;
+
+        public LayoutParams(Context c, AttributeSet attrs) {
+            super(c, attrs);
+        }
+
+        public LayoutParams(int width, int height) {
+            super(width, height);
+        }
+    }
+}
diff --git a/core/java/com/android/internal/widget/ResolverDrawerLayout.java b/core/java/com/android/internal/widget/ResolverDrawerLayout.java
index 25b487e..c4347f8 100644
--- a/core/java/com/android/internal/widget/ResolverDrawerLayout.java
+++ b/core/java/com/android/internal/widget/ResolverDrawerLayout.java
@@ -17,14 +17,9 @@
 
 package com.android.internal.widget;
 
-import android.annotation.NonNull;
 import android.content.Context;
 import android.content.res.TypedArray;
-import android.graphics.Canvas;
-import android.graphics.Color;
 import android.graphics.Rect;
-import android.graphics.drawable.ColorDrawable;
-import android.graphics.drawable.Drawable;
 import android.os.Bundle;
 import android.os.Parcel;
 import android.os.Parcelable;
@@ -90,10 +85,6 @@
     private final float mMinFlingVelocity;
     private final OverScroller mScroller;
     private final VelocityTracker mVelocityTracker;
-    private final Drawable mScrollIndicatorDrawable;
-    private final Drawable mFakeForeground;
-
-    private View mButtonBar;
 
     private OnDismissedListener mOnDismissedListener;
     private RunOnDismissedListener mRunOnDismissedListener;
@@ -115,8 +106,6 @@
                 }
             };
 
-    private final int[] mTempOffset = new int[2];
-
     public ResolverDrawerLayout(Context context) {
         this(context, null);
     }
@@ -138,9 +127,6 @@
                 mMaxCollapsedHeight);
         a.recycle();
 
-        mScrollIndicatorDrawable = mContext.getDrawable(R.drawable.scroll_indicator_material);
-        mFakeForeground = new ColorDrawable(Color.TRANSPARENT);
-
         mScroller = new OverScroller(context, AnimationUtils.loadInterpolator(context,
                 android.R.interpolator.decelerate_quint));
         mVelocityTracker = VelocityTracker.obtain();
@@ -152,13 +138,6 @@
         setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
     }
 
-    @Override
-    protected void onFinishInflate() {
-        super.onFinishInflate();
-
-        mButtonBar = findViewById(R.id.button_bar);
-    }
-
     public void setSmallCollapsed(boolean smallCollapsed) {
         mSmallCollapsed = smallCollapsed;
         requestLayout();
@@ -223,7 +202,8 @@
             }
             final boolean isCollapsedNew = mCollapseOffset != 0;
             if (isCollapsedOld != isCollapsedNew) {
-                onCollapsedChanged(isCollapsedNew);
+                notifyViewAccessibilityStateChangedIfNeeded(
+                        AccessibilityEvent.CONTENT_CHANGE_TYPE_UNDEFINED);
             }
         } else {
             // Start out collapsed at first unless we restored state for otherwise
@@ -462,7 +442,8 @@
             mTopOffset += dy;
             final boolean isCollapsedNew = newPos != 0;
             if (isCollapsedOld != isCollapsedNew) {
-                onCollapsedChanged(isCollapsedNew);
+                notifyViewAccessibilityStateChangedIfNeeded(
+                        AccessibilityEvent.CONTENT_CHANGE_TYPE_UNDEFINED);
             }
             postInvalidateOnAnimation();
             return dy;
@@ -470,14 +451,6 @@
         return 0;
     }
 
-    private void onCollapsedChanged(boolean isCollapsed) {
-        notifyViewAccessibilityStateChangedIfNeeded(
-                AccessibilityEvent.CONTENT_CHANGE_TYPE_UNDEFINED);
-
-        // Set a fake foreground so that we receive onDrawForeground().
-        setForeground(isCollapsed ? mFakeForeground : null);
-    }
-
     void dispatchOnDismissed() {
         if (mOnDismissedListener != null) {
             mOnDismissedListener.onDismissed();
@@ -736,23 +709,6 @@
     }
 
     @Override
-    public void onDrawForeground(Canvas canvas) {
-        if (isCollapsed() && mButtonBar != null) {
-            // Draw the scroll indicator directly above the button bar.
-            final int height = mScrollIndicatorDrawable.getIntrinsicHeight();
-            mButtonBar.getLocationInWindow(mTempOffset);
-            final int barTop = mTempOffset[1];
-            getLocationInWindow(mTempOffset);
-            final int myTop = mTempOffset[1];
-            final int top = (barTop - myTop) - height;
-            mScrollIndicatorDrawable.setBounds(0, top, getWidth(), top + height);
-            mScrollIndicatorDrawable.draw(canvas);
-        }
-
-        super.onDrawForeground(canvas);
-    }
-
-    @Override
     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
         final int sourceWidth = MeasureSpec.getSize(widthMeasureSpec);
         int widthSize = sourceWidth;
diff --git a/core/jni/android/graphics/FontFamily.cpp b/core/jni/android/graphics/FontFamily.cpp
index 6dc251c..1c2d13d 100644
--- a/core/jni/android/graphics/FontFamily.cpp
+++ b/core/jni/android/graphics/FontFamily.cpp
@@ -53,36 +53,14 @@
     fontFamily->Unref();
 }
 
-static jboolean addSkTypeface(FontFamily* family, SkTypeface* face) {
-    MinikinFont* minikinFont = new MinikinFontSkia(face);
+static jboolean addSkTypeface(FontFamily* family, SkTypeface* face, const void* fontData,
+        size_t fontSize, int ttcIndex) {
+    MinikinFont* minikinFont = new MinikinFontSkia(face, fontData, fontSize, ttcIndex);
     bool result = family->addFont(minikinFont);
     minikinFont->Unref();
     return result;
 }
 
-static jboolean FontFamily_addFont(JNIEnv* env, jobject clazz, jlong familyPtr, jstring path,
-        jint ttcIndex) {
-    NPE_CHECK_RETURN_ZERO(env, path);
-    ScopedUtfChars str(env, path);
-    SkTypeface* face = SkTypeface::CreateFromFile(str.c_str(), ttcIndex);
-    if (face == NULL) {
-        ALOGE("addFont failed to create font %s", str.c_str());
-        return false;
-    }
-    FontFamily* fontFamily = reinterpret_cast<FontFamily*>(familyPtr);
-    return addSkTypeface(fontFamily, face);
-}
-
-static struct {
-    jmethodID mGet;
-    jmethodID mSize;
-} gListClassInfo;
-
-static struct {
-    jfieldID mTag;
-    jfieldID mStyleValue;
-} gAxisClassInfo;
-
 static void release_global_ref(const void* /*data*/, void* context) {
     JNIEnv* env = AndroidRuntime::getJNIEnv();
     bool needToAttach = (env == NULL);
@@ -106,6 +84,47 @@
     }
 }
 
+static jboolean FontFamily_addFont(JNIEnv* env, jobject clazz, jlong familyPtr, jobject bytebuf,
+        jint ttcIndex) {
+    NPE_CHECK_RETURN_ZERO(env, bytebuf);
+    const void* fontPtr = env->GetDirectBufferAddress(bytebuf);
+    if (fontPtr == NULL) {
+        ALOGE("addFont failed to create font, buffer invalid");
+        return false;
+    }
+    jlong fontSize = env->GetDirectBufferCapacity(bytebuf);
+    if (fontSize < 0) {
+        ALOGE("addFont failed to create font, buffer size invalid");
+        return false;
+    }
+    jobject fontRef = MakeGlobalRefOrDie(env, bytebuf);
+    SkAutoTUnref<SkData> data(SkData::NewWithProc(fontPtr, fontSize,
+            release_global_ref, reinterpret_cast<void*>(fontRef)));
+    std::unique_ptr<SkStreamAsset> fontData(new SkMemoryStream(data));
+
+    SkFontMgr::FontParameters params;
+    params.setCollectionIndex(ttcIndex);
+
+    SkAutoTUnref<SkFontMgr> fm(SkFontMgr::RefDefault());
+    SkTypeface* face = fm->createFromStream(fontData.release(), params);
+    if (face == NULL) {
+        ALOGE("addFont failed to create font");
+        return false;
+    }
+    FontFamily* fontFamily = reinterpret_cast<FontFamily*>(familyPtr);
+    return addSkTypeface(fontFamily, face, fontPtr, (size_t)fontSize, ttcIndex);
+}
+
+static struct {
+    jmethodID mGet;
+    jmethodID mSize;
+} gListClassInfo;
+
+static struct {
+    jfieldID mTag;
+    jfieldID mStyleValue;
+} gAxisClassInfo;
+
 static jboolean FontFamily_addFontWeightStyle(JNIEnv* env, jobject clazz, jlong familyPtr,
         jobject font, jint ttcIndex, jobject listOfAxis, jint weight, jboolean isItalic) {
     NPE_CHECK_RETURN_ZERO(env, font);
@@ -133,7 +152,7 @@
         }
     }
 
-    void* fontPtr = env->GetDirectBufferAddress(font);
+    const void* fontPtr = env->GetDirectBufferAddress(font);
     if (fontPtr == NULL) {
         ALOGE("addFont failed to create font, buffer invalid");
         return false;
@@ -159,7 +178,7 @@
         return false;
     }
     FontFamily* fontFamily = reinterpret_cast<FontFamily*>(familyPtr);
-    MinikinFont* minikinFont = new MinikinFontSkia(face);
+    MinikinFont* minikinFont = new MinikinFontSkia(face, fontPtr, (size_t)fontSize, ttcIndex);
     fontFamily->addFont(minikinFont, FontStyle(weight / 100, isItalic));
     minikinFont->Unref();
     return true;
@@ -191,6 +210,7 @@
         return false;
     }
 
+    size_t bufSize = asset->getLength();
     SkAutoTUnref<SkData> data(SkData::NewWithProc(buf, asset->getLength(), releaseAsset, asset));
     SkMemoryStream* stream = new SkMemoryStream(data);
     // CreateFromStream takes ownership of stream.
@@ -200,7 +220,7 @@
         return false;
     }
     FontFamily* fontFamily = reinterpret_cast<FontFamily*>(familyPtr);
-    return addSkTypeface(fontFamily, face);
+    return addSkTypeface(fontFamily, face, buf, bufSize, /* ttcIndex */ 0);
 }
 
 ///////////////////////////////////////////////////////////////////////////////
@@ -208,7 +228,7 @@
 static const JNINativeMethod gFontFamilyMethods[] = {
     { "nCreateFamily",         "(Ljava/lang/String;I)J", (void*)FontFamily_create },
     { "nUnrefFamily",          "(J)V", (void*)FontFamily_unref },
-    { "nAddFont",              "(JLjava/lang/String;I)Z", (void*)FontFamily_addFont },
+    { "nAddFont",              "(JLjava/nio/ByteBuffer;I)Z", (void*)FontFamily_addFont },
     { "nAddFontWeightStyle",   "(JLjava/nio/ByteBuffer;ILjava/util/List;IZ)Z",
             (void*)FontFamily_addFontWeightStyle },
     { "nAddFontFromAsset",     "(JLandroid/content/res/AssetManager;Ljava/lang/String;)Z",
diff --git a/core/jni/android_graphics_drawable_VectorDrawable.cpp b/core/jni/android_graphics_drawable_VectorDrawable.cpp
index b04293e..50d86ff 100644
--- a/core/jni/android_graphics_drawable_VectorDrawable.cpp
+++ b/core/jni/android_graphics_drawable_VectorDrawable.cpp
@@ -176,6 +176,9 @@
     PathParser::ParseResult result;
     PathData data;
     PathParser::getPathDataFromString(&data, &result, pathString, stringLength);
+    if (result.failureOccurred) {
+        doThrowIAE(env, result.failureMessage.c_str());
+    }
     path->mutateStagingProperties()->setData(data);
     env->ReleaseStringUTFChars(inputStr, pathString);
 }
@@ -340,7 +343,7 @@
 }
 
 static const JNINativeMethod gMethods[] = {
-        {"nCreateRenderer", "!(J)J", (void*)createTree},
+        {"nCreateTree", "!(J)J", (void*)createTree},
         {"nSetRendererViewportSize", "!(JFF)V", (void*)setTreeViewportSize},
         {"nSetRootAlpha", "!(JF)Z", (void*)setRootAlpha},
         {"nGetRootAlpha", "!(J)F", (void*)getRootAlpha},
diff --git a/core/jni/android_hardware_location_ContextHubService.cpp b/core/jni/android_hardware_location_ContextHubService.cpp
index 91a3b4f..5c961d9 100644
--- a/core/jni/android_hardware_location_ContextHubService.cpp
+++ b/core/jni/android_hardware_location_ContextHubService.cpp
@@ -21,8 +21,8 @@
 
 #include <inttypes.h>
 #include <jni.h>
-#include <map>
 #include <queue>
+#include <unordered_map>
 #include <string.h>
 #include <stdint.h>
 #include <stdio.h>
@@ -105,7 +105,7 @@
     context_hub_info_s hubInfo;
     jniInfo_s jniInfo;
     std::queue<int> freeIds;
-    std::map<int, app_instance_info_s *> appInstances;
+    std::unordered_map<int, app_instance_info_s> appInstances;
 };
 
 }  // unnamed namespace
@@ -137,7 +137,7 @@
     const context_hub_t *info = get_hub_info(hubHandle);
 
     if (info) {
-        msg->app = info->os_app_name;
+        msg->app_name = info->os_app_name;
         return 0;
     } else {
         ALOGD("%s: Hub information is null for hubHandle %d", __FUNCTION__, hubHandle);
@@ -154,23 +154,23 @@
 }
 
 static int get_hub_id_for_app_instance(int id) {
-    if (db.appInstances.find(id) == db.appInstances.end()) {
+    if (!db.appInstances.count(id)) {
         ALOGD("%s: Cannot find app for app instance %d", __FUNCTION__, id);
         return -1;
     }
 
-    int hubHandle = db.appInstances[id]->hubHandle;
+    int hubHandle = db.appInstances[id].hubHandle;
 
     return db.hubInfo.hubs[hubHandle].hub_id;
 }
 
 static int set_dest_app(hub_message_t *msg, int id) {
-    if (db.appInstances.find(id) == db.appInstances.end()) {
+    if (!db.appInstances.count(id)) {
         ALOGD("%s: Cannod find app for app instance %d", __FUNCTION__, id);
         return -1;
     }
 
-    msg->app = db.appInstances[id]->appInfo.name;
+    msg->app_name = db.appInstances[id].appInfo.app_name;
     return 0;
 }
 
@@ -210,76 +210,43 @@
 
 int add_app_instance(const hub_app_info *appInfo, uint32_t hubHandle, JNIEnv *env) {
     // Not checking if the apps are indeed distinct
-
-    app_instance_info_s *entry;
-    void *appName;
-    hub_app_name_t *name;
-
-    assert(appInfo && appInfo->name && appInfo->name->app_name);
-
-    entry = (app_instance_info_s *) malloc(sizeof(app_instance_info_s));
-    appName = malloc(appInfo->name->app_name_len);
-    name = (hub_app_name_t *) malloc(sizeof(hub_app_name_t));
-
+    app_instance_info_s entry;
     int appInstanceHandle = generate_id();
 
-    if (appInstanceHandle < 0 || !appName || !entry || !name) {
-        ALOGE("Cannot find resources to add app instance %d, %p, %p",
-            appInstanceHandle, appName, entry);
+    assert(appInfo);
 
-        free(appName);
-        free(entry);
-        free(name);
-
-        if (appInstanceHandle >= 0) {
-            return_id(appInstanceHandle);
-        }
-
+    if (appInstanceHandle < 0) {
+        ALOGE("Cannot find resources to add app instance %d",
+              appInstanceHandle);
         return -1;
     }
 
-    memcpy(&(entry->appInfo), appInfo, sizeof(entry->appInfo));
-    memcpy(appName, appInfo->name->app_name, appInfo->name->app_name_len);
-    name->app_name = appName;
-    name->app_name_len = appInfo->name->app_name_len;
-    entry->appInfo.name = name;
-    entry->truncName = 0;
-    memcpy(&(entry->truncName), name->app_name,
-           sizeof(entry->truncName) < name->app_name_len ?
-           sizeof(entry->truncName) : name->app_name_len);
-
-    // Not checking for sanity of hubId
-    entry->hubHandle = hubHandle;
-    entry->instanceId = appInstanceHandle;
+    entry.appInfo = *appInfo;
+    entry.instanceId = appInstanceHandle;
+    entry.truncName = appInfo->app_name.id;
+    entry.hubHandle = hubHandle;
     db.appInstances[appInstanceHandle] = entry;
 
     // Finally - let the service know of this app instance
     env->CallIntMethod(db.jniInfo.jContextHubService,
                        db.jniInfo.contextHubServiceAddAppInstance,
-                       hubHandle, entry->instanceId, entry->truncName,
-                       entry->appInfo.version);
+                       hubHandle, entry.instanceId, entry.truncName,
+                       entry.appInfo.version);
 
     ALOGW("Added App 0x%" PRIx64 " on hub Handle %" PRId32
-          " as appInstance %d, original name_length %" PRId32, entry->truncName,
-          entry->hubHandle, appInstanceHandle, name->app_name_len);
+          " as appInstance %d", entry.truncName,
+          entry.hubHandle, appInstanceHandle);
 
     return appInstanceHandle;
 }
 
 int delete_app_instance(int id) {
-    if (db.appInstances.find(id) == db.appInstances.end()) {
+    if (!db.appInstances.count(id)) {
         return -1;
     }
 
     return_id(id);
-
-    if (db.appInstances[id]) {
-        // Losing the const cast below. This is intentional.
-        free((void *)db.appInstances[id]->appInfo.name->app_name);
-        free((void *)db.appInstances[id]->appInfo.name);
-        free(db.appInstances[id]);
-        db.appInstances.erase(id);
-    }
+    db.appInstances.erase(id);
 
     return 0;
 }
@@ -353,27 +320,20 @@
 }
 
 int handle_query_apps_response(char *msg, int msgLen, uint32_t hubHandle) {
-    int i;
     JNIEnv *env;
     if ((db.jniInfo.vm)->AttachCurrentThread(&env, nullptr) != JNI_OK) {
             return -1;
     }
 
     int numApps = msgLen/sizeof(hub_app_info);
-    hub_app_info *info = (hub_app_info *)malloc(msgLen); // handle possible alignment
+    hub_app_info info;
+    hub_app_info *unalignedInfoAddr = (hub_app_info*)msg;
 
-    if (!info) {
-        return -1;
+    for (int i = 0; i < numApps; i++, unalignedInfoAddr++) {
+        memcpy(&info, unalignedInfoAddr, sizeof(info));
+        add_app_instance(&info, hubHandle, env);
     }
 
-    memcpy(info, msg, msgLen);
-    for (i = 0; i < numApps; i++) {
-        add_app_instance(info, hubHandle, env);
-        info++;
-    }
-
-    free(info);
-
     return 0;
 }
 
@@ -410,10 +370,6 @@
             retVal = 0;
             break;
 
-        case CONTEXT_HUB_LOAD_OS:
-            retVal = 0;
-            break;
-
         default:
             retVal = -1;
             break;
diff --git a/core/jni/android_util_PathParser.cpp b/core/jni/android_util_PathParser.cpp
index 0927120..0c867f1 100644
--- a/core/jni/android_util_PathParser.cpp
+++ b/core/jni/android_util_PathParser.cpp
@@ -15,6 +15,7 @@
  */
 
 #include "jni.h"
+#include "GraphicsJNI.h"
 
 #include <PathParser.h>
 #include <SkPath.h>
@@ -27,7 +28,7 @@
 
 using namespace uirenderer;
 
-static bool parseStringForPath(JNIEnv* env, jobject, jlong skPathHandle, jstring inputPathStr,
+static void parseStringForPath(JNIEnv* env, jobject, jlong skPathHandle, jstring inputPathStr,
         jint strLength) {
     const char* pathString = env->GetStringUTFChars(inputPathStr, NULL);
     SkPath* skPath = reinterpret_cast<SkPath*>(skPathHandle);
@@ -36,9 +37,8 @@
     PathParser::parseStringForSkPath(skPath, &result, pathString, strLength);
     env->ReleaseStringUTFChars(inputPathStr, pathString);
     if (result.failureOccurred) {
-        ALOGE(result.failureMessage.c_str());
+        doThrowIAE(env, result.failureMessage.c_str());
     }
-    return !result.failureOccurred;
 }
 
 static long createEmptyPathData(JNIEnv*, jobject) {
@@ -62,7 +62,7 @@
         return reinterpret_cast<jlong>(pathData);
     } else {
         delete pathData;
-        ALOGE(result.failureMessage.c_str());
+        doThrowIAE(env, result.failureMessage.c_str());
         return NULL;
     }
 }
@@ -100,7 +100,7 @@
 }
 
 static const JNINativeMethod gMethods[] = {
-    {"nParseStringForPath", "(JLjava/lang/String;I)Z", (void*)parseStringForPath},
+    {"nParseStringForPath", "(JLjava/lang/String;I)V", (void*)parseStringForPath},
     {"nCreateEmptyPathData", "!()J", (void*)createEmptyPathData},
     {"nCreatePathData", "!(J)J", (void*)createPathData},
     {"nCreatePathDataFromString", "(Ljava/lang/String;I)J", (void*)createPathDataFromStringPath},
diff --git a/core/jni/android_view_ThreadedRenderer.cpp b/core/jni/android_view_ThreadedRenderer.cpp
index 3d65209..faa4192 100644
--- a/core/jni/android_view_ThreadedRenderer.cpp
+++ b/core/jni/android_view_ThreadedRenderer.cpp
@@ -663,6 +663,14 @@
     proxy->setContentDrawBounds(left, top, right, bottom);
 }
 
+static jboolean android_view_ThreadedRenderer_copySurfaceInto(JNIEnv* env,
+        jobject clazz, jobject jsurface, jobject jbitmap) {
+    SkBitmap bitmap;
+    GraphicsJNI::getSkBitmap(env, jbitmap, &bitmap);
+    sp<Surface> surface = android_view_Surface_getSurface(env, jsurface);
+    return RenderProxy::copySurfaceInto(surface, &bitmap);
+}
+
 // ----------------------------------------------------------------------------
 // FrameMetricsObserver
 // ----------------------------------------------------------------------------
@@ -768,6 +776,8 @@
     { "nRemoveFrameMetricsObserver",
             "(JJ)V",
             (void*)android_view_ThreadedRenderer_removeFrameMetricsObserver },
+    { "nCopySurfaceInto", "(Landroid/view/Surface;Landroid/graphics/Bitmap;)Z",
+                (void*)android_view_ThreadedRenderer_copySurfaceInto },
 };
 
 int register_android_view_ThreadedRenderer(JNIEnv* env) {
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index 9a2e39c7..778f797 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -420,6 +420,7 @@
     <protected-broadcast android:name="android.os.storage.action.VOLUME_STATE_CHANGED" />
     <protected-broadcast android:name="android.os.storage.action.DISK_SCANNED" />
     <protected-broadcast android:name="com.android.server.action.UPDATE_TWILIGHT_STATE" />
+    <protected-broadcast android:name="com.android.server.action.RESET_TWILIGHT_AUTO" />
     <protected-broadcast android:name="com.android.server.device_idle.STEP_IDLE_STATE" />
     <protected-broadcast android:name="com.android.server.device_idle.STEP_LIGHT_IDLE_STATE" />
     <protected-broadcast android:name="com.android.server.Wifi.action.TOGGLE_PNO" />
diff --git a/core/res/res/drawable-hdpi/ic_launcher_android.png b/core/res/res/drawable-hdpi/ic_launcher_android.png
index cce5187..2e9b196 100644
--- a/core/res/res/drawable-hdpi/ic_launcher_android.png
+++ b/core/res/res/drawable-hdpi/ic_launcher_android.png
Binary files differ
diff --git a/core/res/res/drawable-ldpi/ic_launcher_android.png b/core/res/res/drawable-ldpi/ic_launcher_android.png
index 628a8de..245e4b7 100644
--- a/core/res/res/drawable-ldpi/ic_launcher_android.png
+++ b/core/res/res/drawable-ldpi/ic_launcher_android.png
Binary files differ
diff --git a/core/res/res/drawable-mdpi/ic_launcher_android.png b/core/res/res/drawable-mdpi/ic_launcher_android.png
index 6a97d5b..baacd4f 100644
--- a/core/res/res/drawable-mdpi/ic_launcher_android.png
+++ b/core/res/res/drawable-mdpi/ic_launcher_android.png
Binary files differ
diff --git a/core/res/res/drawable-xhdpi/ic_launcher_android.png b/core/res/res/drawable-xhdpi/ic_launcher_android.png
index b1097d6..00b69a5 100644
--- a/core/res/res/drawable-xhdpi/ic_launcher_android.png
+++ b/core/res/res/drawable-xhdpi/ic_launcher_android.png
Binary files differ
diff --git a/core/res/res/drawable-xxhdpi/ic_launcher_android.png b/core/res/res/drawable-xxhdpi/ic_launcher_android.png
new file mode 100644
index 0000000..ad05cd5
--- /dev/null
+++ b/core/res/res/drawable-xxhdpi/ic_launcher_android.png
Binary files differ
diff --git a/core/res/res/drawable/ic_corp_user_badge.xml b/core/res/res/drawable/ic_corp_user_badge.xml
new file mode 100644
index 0000000..23809d5
--- /dev/null
+++ b/core/res/res/drawable/ic_corp_user_badge.xml
@@ -0,0 +1,24 @@
+<!--
+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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+        android:width="36dp"
+        android:height="36dp"
+        android:viewportWidth="36.0"
+        android:viewportHeight="36.0">
+    <path
+        android:fillColor="#FFFFFFFF"
+        android:pathData="M18,0C8.06,-0 0,8.06 0,18C0,27.94 8.06,36 18,36C27.94,36 36,27.94 36,18C36,8.06 27.94,0 18,0zM15.5,10.5L20.5,10.5L21.75,11.75L21.75,13L24.66,13C25.57,13 26.34,13.74 26.34,14.66L26.34,18C26.34,18.92 25.57,19.66 24.66,19.66L19.66,19.66L19.66,18.41L16.34,18.41L16.34,19.66L11.34,19.66C10.43,19.66 9.66,18.92 9.66,18L9.66,14.66C9.66,13.74 10.43,13 11.34,13L14.25,13L14.25,11.78L15.5,10.5zM15.5,11.75L15.5,13L20.5,13L20.5,11.75L15.5,11.75zM10.5,20.5L16.34,20.5L16.34,21.75L19.66,21.75L19.66,20.5L25.5,20.5L25.5,23.84C25.5,24.76 24.76,25.5 23.84,25.5L12.16,25.5C11.24,25.5 10.5,24.76 10.5,23.84L10.5,20.5z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_done.xml b/core/res/res/drawable/ic_input_extract_action_done.xml
new file mode 100644
index 0000000..f6e872e
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_done.xml
@@ -0,0 +1,19 @@
+<!--
+     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.
+-->
+<vector android:height="24dp" android:viewportHeight="48.0"
+    android:viewportWidth="48.0" android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
+    <path android:fillColor="#FFFFFF" android:pathData="M18,32.34L9.66,24l-2.83,2.83L18,38l24,-24 -2.83,-2.83z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_go.xml b/core/res/res/drawable/ic_input_extract_action_go.xml
new file mode 100644
index 0000000..edbc826
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_go.xml
@@ -0,0 +1,19 @@
+<!--
+     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.
+-->
+<vector android:height="24dp" android:viewportHeight="48.0"
+    android:viewportWidth="48.0" android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
+    <path android:fillColor="#FFFFFF" android:pathData="M6,22h28.34l-7.17,-7.17L30,12l12,12 -12,12 -2.83,-2.83L34.34,26H6z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_next.xml b/core/res/res/drawable/ic_input_extract_action_next.xml
new file mode 100644
index 0000000..ffef346
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_next.xml
@@ -0,0 +1,19 @@
+<!--
+     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.
+-->
+<vector android:height="24dp" android:viewportHeight="48.0"
+    android:viewportWidth="48.0" android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
+    <path android:fillColor="#FFFFFF" android:pathData="M23.17,14.83L30.34,22H2v4h28.34l-7.17,7.17L26,36l12,-12 -12,-12 -2.83,2.83zM40,12v24h4V12h-4z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_previous.xml b/core/res/res/drawable/ic_input_extract_action_previous.xml
new file mode 100644
index 0000000..89777b0
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_previous.xml
@@ -0,0 +1,19 @@
+<!--
+     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.
+-->
+<vector android:height="24dp" android:viewportHeight="48.0"
+    android:viewportWidth="48.0" android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
+    <path android:fillColor="#FFFFFF" android:pathData="M22.83,14.83L15.66,22H44v4H15.66l7.17,7.17L20,36 8,24l12,-12 2.83,2.83zM6,12v24H2V12h4z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_return.xml b/core/res/res/drawable/ic_input_extract_action_return.xml
new file mode 100644
index 0000000..cb2de5a
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_return.xml
@@ -0,0 +1,19 @@
+<!--
+     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.
+-->
+<vector android:height="24dp" android:viewportHeight="48.0"
+    android:viewportWidth="48.0" android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
+    <path android:fillColor="#FFFFFF" android:pathData="M38,14v8H11.66l7.17,-7.17L16,12 4,24l12,12 2.83,-2.83L11.66,26H42V14z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_search.xml b/core/res/res/drawable/ic_input_extract_action_search.xml
new file mode 100644
index 0000000..dcbcdbf
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_search.xml
@@ -0,0 +1,19 @@
+<!--
+     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.
+-->
+<vector android:height="24dp" android:viewportHeight="48.0"
+    android:viewportWidth="48.0" android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
+    <path android:fillColor="#FFFFFF" android:pathData="M31,28h-1.59l-0.55,-0.55C30.82,25.18 32,22.23 32,19c0,-7.18 -5.82,-13 -13,-13S6,11.82 6,19s5.82,13 13,13c3.23,0 6.18,-1.18 8.45,-3.13l0.55,0.55L28,31l10,9.98L40.98,38 31,28zM19,28c-4.97,0 -9,-4.03 -9,-9s4.03,-9 9,-9 9,4.03 9,9 -4.03,9 -9,9z"/>
+</vector>
diff --git a/core/res/res/drawable/ic_input_extract_action_send.xml b/core/res/res/drawable/ic_input_extract_action_send.xml
new file mode 100644
index 0000000..6494bee5
--- /dev/null
+++ b/core/res/res/drawable/ic_input_extract_action_send.xml
@@ -0,0 +1,24 @@
+<!--
+     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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+        android:width="36dp"
+        android:height="36dp"
+        android:viewportWidth="48.0"
+        android:viewportHeight="48.0">
+    <path
+        android:pathData="M4.02,42L46,24 4.02,6 4,20l30,4 -30,4z"
+        android:fillColor="#FFFFFF"/>
+</vector>
diff --git a/core/res/res/drawable/input_extract_action_bg_material_dark.xml b/core/res/res/drawable/input_extract_action_bg_material_dark.xml
new file mode 100644
index 0000000..9c6a6c3
--- /dev/null
+++ b/core/res/res/drawable/input_extract_action_bg_material_dark.xml
@@ -0,0 +1,21 @@
+<?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.
+-->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:drawable="@drawable/input_extract_action_bg_pressed_material_dark"
+        android:state_pressed="true"/>
+    <item android:drawable="@drawable/input_extract_action_bg_normal_material_dark"/>
+</selector>
diff --git a/core/res/res/drawable/input_extract_action_bg_normal_material_dark.xml b/core/res/res/drawable/input_extract_action_bg_normal_material_dark.xml
new file mode 100644
index 0000000..8449978
--- /dev/null
+++ b/core/res/res/drawable/input_extract_action_bg_normal_material_dark.xml
@@ -0,0 +1,19 @@
+<?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.
+-->
+<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="oval">
+    <solid android:color="@color/material_deep_teal_200"/>
+</shape>
diff --git a/core/res/res/drawable/input_extract_action_bg_pressed_material_dark.xml b/core/res/res/drawable/input_extract_action_bg_pressed_material_dark.xml
new file mode 100644
index 0000000..adade104
--- /dev/null
+++ b/core/res/res/drawable/input_extract_action_bg_pressed_material_dark.xml
@@ -0,0 +1,19 @@
+<?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.
+-->
+<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="oval">
+    <solid android:color="@color/material_deep_teal_100"/>
+</shape>
diff --git a/core/res/res/layout-watch/input_method_extract_view.xml b/core/res/res/layout-watch/input_method_extract_view.xml
new file mode 100644
index 0000000..e3cd2ce
--- /dev/null
+++ b/core/res/res/layout-watch/input_method_extract_view.xml
@@ -0,0 +1,55 @@
+<?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.
+-->
+<android.inputmethodservice.CompactExtractEditLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:orientation="horizontal"
+    android:gravity="center_vertical"
+    android:baselineAligned="false">
+
+    <android.inputmethodservice.ExtractEditText
+        android:id="@id/inputExtractEditText"
+        android:layout_width="0dp"
+        android:layout_height="24dp"
+        android:background="@null"
+        android:singleLine="true"
+        android:inputType="text"
+        android:layout_weight="1"
+        android:fontFamily="sans-serif-condensed-light"
+        android:textColor="@color/primary_text_default_material_dark"
+        android:textColorHighlight="@color/accent_material_dark"
+        android:textSize="18dp"
+        android:cursorVisible="false"
+        android:gravity="bottom|right"
+        />
+
+    <FrameLayout
+        android:id="@id/inputExtractAccessories"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginLeft="8dp"
+        android:visibility="visible">
+        <ImageButton
+            android:id="@id/inputExtractAction"
+            android:layout_width="@dimen/input_extract_action_button_width"
+            android:layout_height="@dimen/input_extract_action_button_width"
+            android:background="@drawable/input_extract_action_bg_material_dark"
+            android:padding="4dp"
+            android:scaleType="centerInside" />
+    </FrameLayout>
+</android.inputmethodservice.CompactExtractEditLayout>
diff --git a/core/res/res/layout/notification_template_material_messaging.xml b/core/res/res/layout/notification_template_material_messaging.xml
new file mode 100644
index 0000000..7d718e0
--- /dev/null
+++ b/core/res/res/layout/notification_template_material_messaging.xml
@@ -0,0 +1,80 @@
+<?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
+  -->
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:id="@+id/status_bar_latest_event_content"
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:tag="messaging"
+    >
+    <include layout="@layout/notification_template_header" />
+    <LinearLayout
+            android:layout_width="match_parent"
+            android:layout_height="match_parent"
+            android:layout_gravity="top"
+            android:layout_marginTop="@dimen/notification_content_margin_top"
+            android:clipToPadding="false"
+            android:orientation="vertical">
+
+        <LinearLayout
+            android:id="@+id/notification_main_column"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_gravity="top"
+            android:paddingStart="@dimen/notification_content_margin_start"
+            android:paddingEnd="@dimen/notification_content_margin_end"
+            android:minHeight="@dimen/notification_min_content_height"
+            android:clipToPadding="false"
+            android:orientation="vertical"
+            >
+            <include layout="@layout/notification_template_part_line1"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content" />
+
+            <com.android.internal.widget.MessagingLinearLayout
+                android:id="@+id/notification_messaging"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:paddingBottom="@dimen/notification_content_margin_bottom"
+                android:spacing="@dimen/notification_messaging_spacing"
+                android:maxHeight="212dp">
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text0"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text1"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text2"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text3"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text4"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text5"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+                <com.android.internal.widget.ImageFloatingTextView android:id="@+id/inbox_text6"
+                    style="@style/Widget.Material.Notification.MessagingText"
+                    />
+            </com.android.internal.widget.MessagingLinearLayout>
+        </LinearLayout>
+        <include layout="@layout/notification_material_action_list" />
+    </LinearLayout>
+    <include layout="@layout/notification_template_right_icon" />
+</FrameLayout>
diff --git a/core/res/res/layout/notification_template_right_icon.xml b/core/res/res/layout/notification_template_right_icon.xml
index 15ccc67..b652127 100644
--- a/core/res/res/layout/notification_template_right_icon.xml
+++ b/core/res/res/layout/notification_template_right_icon.xml
@@ -16,9 +16,9 @@
   -->
 
 <ImageView android:id="@+id/right_icon" xmlns:android="http://schemas.android.com/apk/res/android"
-    android:layout_width="40dp"
-    android:layout_height="40dp"
-    android:layout_marginEnd="16dp"
+    android:layout_width="@dimen/notification_large_icon_width"
+    android:layout_height="@dimen/notification_large_icon_width"
+    android:layout_marginEnd="@dimen/notification_content_margin_end"
     android:layout_marginTop="36dp"
     android:layout_gravity="top|end"
     android:scaleType="centerCrop"
diff --git a/core/res/res/layout/resolver_list.xml b/core/res/res/layout/resolver_list.xml
index fe43e1c..5850e50 100644
--- a/core/res/res/layout/resolver_list.xml
+++ b/core/res/res/layout/resolver_list.xml
@@ -30,37 +30,33 @@
         android:layout_height="wrap_content"
         android:layout_alwaysShow="true"
         android:elevation="8dp"
-        android:background="@color/white">
-
-        <TextView
-            android:id="@+id/profile_button"
-            android:layout_width="wrap_content"
-            android:layout_height="48dp"
-            android:layout_marginEnd="8dp"
-            android:paddingStart="8dp"
-            android:paddingEnd="8dp"
-            android:visibility="gone"
-            style="?attr/borderlessButtonStyle"
-            android:textAppearance="?attr/textAppearanceButton"
-            android:textColor="@color/material_deep_teal_500"
-            android:gravity="center_vertical"
-            android:layout_alignParentTop="true"
-            android:layout_alignParentRight="true"
-            android:singleLine="true" />
-
-        <TextView
-            android:id="@+id/title"
-            android:layout_width="wrap_content"
-            android:layout_height="wrap_content"
-            android:minHeight="56dp"
-            android:textAppearance="?attr/textAppearanceMedium"
-            android:gravity="start|center_vertical"
-            android:paddingStart="?attr/dialogPreferredPadding"
-            android:paddingEnd="?attr/dialogPreferredPadding"
-            android:paddingTop="8dp"
-            android:layout_below="@id/profile_button"
-            android:layout_alignParentLeft="true"
-            android:paddingBottom="8dp" />
+        android:background="@color/white" >
+        <TextView android:id="@+id/profile_button"
+                  android:layout_width="wrap_content"
+                  android:layout_height="48dp"
+                  android:layout_marginEnd="8dp"
+                  android:paddingStart="8dp"
+                  android:paddingEnd="8dp"
+                  android:visibility="gone"
+                  style="?attr/borderlessButtonStyle"
+                  android:textAppearance="?attr/textAppearanceButton"
+                  android:textColor="@color/material_deep_teal_500"
+                  android:gravity="center_vertical"
+                  android:layout_alignParentTop="true"
+                  android:layout_alignParentRight="true"
+                  android:singleLine="true"/>
+        <TextView android:id="@+id/title"
+                  android:layout_width="wrap_content"
+                  android:layout_height="wrap_content"
+                  android:minHeight="56dp"
+                  android:textAppearance="?attr/textAppearanceMedium"
+                  android:gravity="start|center_vertical"
+                  android:paddingStart="?attr/dialogPreferredPadding"
+                  android:paddingEnd="?attr/dialogPreferredPadding"
+                  android:paddingTop="8dp"
+                  android:layout_below="@id/profile_button"
+                  android:layout_alignParentLeft="true"
+                  android:paddingBottom="8dp" />
     </RelativeLayout>
 
     <ListView
@@ -72,23 +68,23 @@
         android:background="@color/white"
         android:elevation="8dp"
         android:nestedScrollingEnabled="true"
-        android:scrollIndicators="top|bottom"
         android:divider="@null" />
 
-    <TextView
-        android:id="@+id/empty"
-        android:layout_width="match_parent"
-        android:layout_height="match_parent"
-        android:layout_alwaysShow="true"
-        android:text="@string/noApplications"
-        android:padding="32dp"
-        android:gravity="center"
-        android:visibility="gone" />
+    <TextView android:id="@+id/empty"
+              android:layout_width="match_parent"
+              android:layout_height="wrap_content"
+              android:background="@color/white"
+              android:elevation="8dp"
+              android:layout_alwaysShow="true"
+              android:text="@string/noApplications"
+              android:padding="32dp"
+              android:gravity="center"
+              android:visibility="gone" />
 
     <LinearLayout
         android:id="@+id/button_bar"
         android:visibility="gone"
-        style="?attr/buttonBarStyle"
+        style="?android:attr/buttonBarStyle"
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
         android:layout_ignoreOffset="true"
@@ -103,30 +99,26 @@
         android:paddingStart="12dp"
         android:paddingEnd="12dp"
         android:elevation="8dp">
-
-        <Button
-            android:id="@+id/button_once"
-            android:layout_width="wrap_content"
-            android:layout_gravity="start"
-            android:maxLines="2"
-            style="?attr/buttonBarNegativeButtonStyle"
-            android:minHeight="@dimen/alert_dialog_button_bar_height"
-            android:layout_height="wrap_content"
-            android:enabled="false"
-            android:text="@string/activity_resolver_use_once"
-            android:onClick="onButtonClick" />
-
-        <Button
-            android:id="@+id/button_always"
-            android:layout_width="wrap_content"
-            android:layout_gravity="end"
-            android:maxLines="2"
-            android:minHeight="@dimen/alert_dialog_button_bar_height"
-            style="?attr/buttonBarPositiveButtonStyle"
-            android:layout_height="wrap_content"
-            android:enabled="false"
-            android:text="@string/activity_resolver_use_always"
-            android:onClick="onButtonClick" />
+        <Button android:id="@+id/button_once"
+                android:layout_width="wrap_content"
+                android:layout_gravity="start"
+                android:maxLines="2"
+                style="?android:attr/buttonBarNegativeButtonStyle"
+                android:minHeight="@dimen/alert_dialog_button_bar_height"
+                android:layout_height="wrap_content"
+                android:enabled="false"
+                android:text="@string/activity_resolver_use_once"
+                android:onClick="onButtonClick" />
+        <Button android:id="@+id/button_always"
+                android:layout_width="wrap_content"
+                android:layout_gravity="end"
+                android:maxLines="2"
+                android:minHeight="@dimen/alert_dialog_button_bar_height"
+                style="?android:attr/buttonBarPositiveButtonStyle"
+                android:layout_height="wrap_content"
+                android:enabled="false"
+                android:text="@string/activity_resolver_use_always"
+                android:onClick="onButtonClick" />
     </LinearLayout>
 
 </com.android.internal.widget.ResolverDrawerLayout>
diff --git a/core/res/res/layout/resolver_list_with_default.xml b/core/res/res/layout/resolver_list_with_default.xml
index ed7ef5e..31361e5 100644
--- a/core/res/res/layout/resolver_list_with_default.xml
+++ b/core/res/res/layout/resolver_list_with_default.xml
@@ -22,7 +22,8 @@
     android:layout_height="match_parent"
     android:maxWidth="@dimen/resolver_max_width"
     android:maxCollapsedHeight="144dp"
-    android:id="@id/contentPanel">
+    android:id="@id/contentPanel"
+    >
 
     <LinearLayout
         android:layout_width="match_parent"
@@ -30,75 +31,66 @@
         android:layout_alwaysShow="true"
         android:orientation="vertical"
         android:background="@color/white"
-        android:elevation="8dp">
+        android:elevation="8dp" >
 
         <LinearLayout
             android:layout_width="match_parent"
             android:layout_height="64dp"
-            android:orientation="horizontal">
+            android:orientation="horizontal" >
 
-            <ImageView
-                android:id="@+id/icon"
-                android:layout_width="24dp"
-                android:layout_height="24dp"
-                android:layout_gravity="start|top"
-                android:layout_marginStart="16dp"
-                android:layout_marginEnd="16dp"
-                android:layout_marginTop="20dp"
-                android:scaleType="fitCenter" />
-
-            <TextView
-                android:id="@+id/title"
-                android:layout_width="0dp"
-                android:layout_weight="1"
-                android:layout_height="?attr/listPreferredItemHeight"
-                android:layout_marginStart="16dp"
-                android:textAppearance="?attr/textAppearanceMedium"
-                android:gravity="start|center_vertical"
-                android:paddingEnd="16dp" />
-
-            <LinearLayout
-                android:id="@+id/profile_button"
-                android:layout_width="wrap_content"
-                android:layout_height="48dp"
-                android:layout_marginTop="4dp"
-                android:layout_marginEnd="4dp"
-                android:paddingStart="8dp"
-                android:paddingEnd="8dp"
-                android:paddingTop="4dp"
-                android:paddingBottom="4dp"
-                android:focusable="true"
-                android:visibility="gone"
-                style="?attr/borderlessButtonStyle">
-
-                <ImageView
-                    android:id="@+id/icon"
-                    android:layout_width="24dp"
-                    android:layout_height="24dp"
-                    android:layout_gravity="start|center_vertical"
-                    android:layout_marginEnd="?attr/listPreferredItemPaddingEnd"
-                    android:layout_marginTop="12dp"
-                    android:layout_marginBottom="12dp"
-                    android:scaleType="fitCenter" />
-
-                <TextView
-                    android:id="@id/text1"
-                    android:layout_width="wrap_content"
-                    android:layout_height="wrap_content"
-                    android:layout_gravity="start|center_vertical"
-                    android:layout_marginEnd="?attr/listPreferredItemPaddingEnd"
-                    android:textAppearance="?attr/textAppearanceButton"
-                    android:textColor="?attr/textColorPrimary"
-                    android:minLines="1"
-                    android:maxLines="1"
-                    android:ellipsize="marquee" />
+            <ImageView android:id="@+id/icon"
+                       android:layout_width="24dp"
+                       android:layout_height="24dp"
+                       android:layout_gravity="start|top"
+                       android:layout_marginStart="16dp"
+                       android:layout_marginEnd="16dp"
+                       android:layout_marginTop="20dp"
+                       android:scaleType="fitCenter" />
+            <TextView android:id="@+id/title"
+                      android:layout_width="0dp"
+                      android:layout_weight="1"
+                      android:layout_height="?android:attr/listPreferredItemHeight"
+                      android:layout_marginStart="16dp"
+                      android:textAppearance="?android:attr/textAppearanceMedium"
+                      android:gravity="start|center_vertical"
+                      android:paddingEnd="16dp" />
+            <LinearLayout android:id="@+id/profile_button"
+                          android:layout_width="wrap_content"
+                          android:layout_height="48dp"
+                          android:layout_marginTop="4dp"
+                          android:layout_marginEnd="4dp"
+                          android:paddingStart="8dp"
+                          android:paddingEnd="8dp"
+                          android:paddingTop="4dp"
+                          android:paddingBottom="4dp"
+                          android:focusable="true"
+                          android:visibility="gone"
+                          style="?attr/borderlessButtonStyle">
+                <ImageView android:id="@+id/icon"
+                           android:layout_width="24dp"
+                           android:layout_height="24dp"
+                           android:layout_gravity="start|center_vertical"
+                           android:layout_marginEnd="?attr/listPreferredItemPaddingEnd"
+                           android:layout_marginTop="12dp"
+                           android:layout_marginBottom="12dp"
+                           android:scaleType="fitCenter" />
+                <TextView android:id="@id/text1"
+                          android:layout_width="wrap_content"
+                          android:layout_height="wrap_content"
+                          android:layout_gravity="start|center_vertical"
+                          android:layout_marginEnd="?attr/listPreferredItemPaddingEnd"
+                          android:textAppearance="?attr/textAppearanceButton"
+                          android:textColor="?attr/textColorPrimary"
+                          android:minLines="1"
+                          android:maxLines="1"
+                          android:ellipsize="marquee" />
             </LinearLayout>
         </LinearLayout>
 
         <LinearLayout
             android:id="@+id/button_bar"
             android:visibility="gone"
-            style="?attr/buttonBarStyle"
+            style="?android:attr/buttonBarStyle"
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
             android:layout_alwaysShow="true"
@@ -112,36 +104,30 @@
             android:paddingEnd="12dp"
             android:background="@color/white"
             android:elevation="8dp">
-
-            <Button
-                android:id="@+id/button_once"
-                android:layout_width="wrap_content"
-                android:layout_gravity="start"
-                android:maxLines="2"
-                style="?attr/buttonBarNegativeButtonStyle"
-                android:minHeight="@dimen/alert_dialog_button_bar_height"
-                android:layout_height="wrap_content"
-                android:enabled="false"
-                android:text="@string/activity_resolver_use_once"
-                android:onClick="onButtonClick" />
-
-            <Button
-                android:id="@+id/button_always"
-                android:layout_width="wrap_content"
-                android:layout_gravity="end"
-                android:maxLines="2"
-                android:minHeight="@dimen/alert_dialog_button_bar_height"
-                style="?attr/buttonBarPositiveButtonStyle"
-                android:layout_height="wrap_content"
-                android:enabled="false"
-                android:text="@string/activity_resolver_use_always"
-                android:onClick="onButtonClick" />
+            <Button android:id="@+id/button_once"
+                    android:layout_width="wrap_content"
+                    android:layout_gravity="start"
+                    android:maxLines="2"
+                    style="?android:attr/buttonBarNegativeButtonStyle"
+                    android:minHeight="@dimen/alert_dialog_button_bar_height"
+                    android:layout_height="wrap_content"
+                    android:enabled="false"
+                    android:text="@string/activity_resolver_use_once"
+                    android:onClick="onButtonClick" />
+            <Button android:id="@+id/button_always"
+                    android:layout_width="wrap_content"
+                    android:layout_gravity="end"
+                    android:maxLines="2"
+                    android:minHeight="@dimen/alert_dialog_button_bar_height"
+                    style="?android:attr/buttonBarPositiveButtonStyle"
+                    android:layout_height="wrap_content"
+                    android:enabled="false"
+                    android:text="@string/activity_resolver_use_always"
+                    android:onClick="onButtonClick" />
         </LinearLayout>
-
-        <View
-            android:layout_width="match_parent"
-            android:layout_height="1dp"
-            android:background="?attr/dividerVertical" />
+        <View android:layout_width="match_parent"
+              android:layout_height="1dp"
+              android:background="?android:attr/dividerVertical" />
     </LinearLayout>
 
     <ListView
@@ -154,6 +140,6 @@
         android:elevation="8dp"
         android:nestedScrollingEnabled="true"
         android:divider="@null"
-        android:scrollIndicators="top|bottom" />
+        />
 
 </com.android.internal.widget.ResolverDrawerLayout>
diff --git a/core/res/res/values-af/strings.xml b/core/res/res/values-af/strings.xml
index 2a16a1e..6a85537 100644
--- a/core/res/res/values-af/strings.xml
+++ b/core/res/res/values-af/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Vra PIN voordat jy ontspeld"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Vra ontsluitpatroon voordat jy ontspeld"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Vra wagwoord voordat jy ontspeld"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Program sal dalk nie met verdeelde skerm werk nie."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Program steun nie verdeelde skerm nie."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Deur jou administrateur geïnstalleer"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Opgedateer deur jou administrateur"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Deur jou administrateur uitgevee"</string>
diff --git a/core/res/res/values-am/strings.xml b/core/res/res/values-am/strings.xml
index 0668c35..7a3673f 100644
--- a/core/res/res/values-am/strings.xml
+++ b/core/res/res/values-am/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ከመንቀል በፊት ፒን ጠይቅ"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ከመንቀል በፊት የማስከፈቻ ስርዓተ-ጥለት ጠይቅ"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ከመንቀል በፊት የይለፍ ቃል ጠይቅ"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"መተግበሪያ ከተከፈለ ማያ ገጽ ጋር ላይሠራ ይችላል"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"መተግበሪያው የተከፈለ ማያ ገጽን አይደግፍም።"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"በእርስዎ አስተዳዳሪ ተጭኗል"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"በአስተዳዳሪዎ ተዘምኗል"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"በእርስዎ አስተዳዳሪ ተሰርዟል"</string>
diff --git a/core/res/res/values-ar/strings.xml b/core/res/res/values-ar/strings.xml
index 6a7c76c..70ebba16 100644
--- a/core/res/res/values-ar/strings.xml
+++ b/core/res/res/values-ar/strings.xml
@@ -56,8 +56,8 @@
     <string name="badPin" msgid="9015277645546710014">"‏رمز PIN القديم الذي كتبته غير صحيح."</string>
     <string name="badPuk" msgid="5487257647081132201">"‏رمز PUK الذي كتبته غير صحيح."</string>
     <string name="mismatchPin" msgid="609379054496863419">"أرقام التعريف الشخصية التي كتبتها غير مطابقة."</string>
-    <string name="invalidPin" msgid="3850018445187475377">"اكتب رقم تعريف شخصيًا مكونًا من 4 إلى ثمانية أعداد."</string>
-    <string name="invalidPuk" msgid="8761456210898036513">"‏اكتب رمز PUK مكونًا من 8 أرقام أو أكثر."</string>
+    <string name="invalidPin" msgid="3850018445187475377">"ادخل رقم تعريف شخصي مكون من ٤ إلى ٨ أرقام."</string>
+    <string name="invalidPuk" msgid="8761456210898036513">"‏اكتب رمز PUK مكونًا من ٨ أرقام أو أكثر."</string>
     <string name="needPuk" msgid="919668385956251611">"‏شريحة SIM مؤمّنة بكود PUK. اكتب كود PUK لإلغاء تأمينها."</string>
     <string name="needPuk2" msgid="4526033371987193070">"‏اكتب PUK2 لإلغاء تأمين شريحة SIM."</string>
     <string name="enablePin" msgid="209412020907207950">"‏محاولة غير ناجحة، مكّن قفل SIM/RUIM."</string>
@@ -904,7 +904,7 @@
     <string name="editTextMenuTitle" msgid="4909135564941815494">"إجراءات النص"</string>
     <string name="low_internal_storage_view_title" msgid="5576272496365684834">"مساحة التخزين منخفضة"</string>
     <string name="low_internal_storage_view_text" msgid="6640505817617414371">"قد لا تعمل بعض وظائف النظام"</string>
-    <string name="low_internal_storage_view_text_no_boot" msgid="6935190099204693424">"ليست هناك سعة تخزينية كافية للنظام. تأكد من أنه لديك مساحة خالية تبلغ 250 ميغابايت وأعد التشغيل."</string>
+    <string name="low_internal_storage_view_text_no_boot" msgid="6935190099204693424">"ليست هناك سعة تخزينية كافية للنظام. تأكد من أنه لديك مساحة خالية تبلغ ۲۵۰ ميغابايت وأعد التشغيل."</string>
     <string name="app_running_notification_title" msgid="8718335121060787914">"<xliff:g id="APP_NAME">%1$s</xliff:g> قيد التشغيل"</string>
     <string name="app_running_notification_text" msgid="4653586947747330058">"المس للحصول على مزيد من المعلومات أو لإيقاف التطبيق."</string>
     <string name="ok" msgid="5970060430562524910">"موافق"</string>
@@ -1343,8 +1343,8 @@
     <string name="kg_enter_confirm_pin_hint" msgid="325676184762529976">"‏تأكيد رمز رمز PIN المراد"</string>
     <string name="kg_sim_unlock_progress_dialog_message" msgid="8950398016976865762">"‏جارٍ إلغاء تأمين شريحة SIM…"</string>
     <string name="kg_password_wrong_pin_code" msgid="1139324887413846912">"‏رمز PIN غير صحيح."</string>
-    <string name="kg_invalid_sim_pin_hint" msgid="8795159358110620001">"‏اكتب رمز PIN المكون من 4 إلى 8 أرقام."</string>
-    <string name="kg_invalid_sim_puk_hint" msgid="6025069204539532000">"‏يجب أن يتكون رمز PUK من 8 أرقام."</string>
+    <string name="kg_invalid_sim_pin_hint" msgid="8795159358110620001">"اكتب  رقم التعريف الشخصي المكون من ٤ إلى ٨ أرقام."</string>
+    <string name="kg_invalid_sim_puk_hint" msgid="6025069204539532000">"‏يجب أن يتكون رمز PUK من ۸ أرقام."</string>
     <string name="kg_invalid_puk" msgid="3638289409676051243">"‏أعد إدخال رمز PUK الصحيح. وستؤدي المحاولات المتكررة إلى تعطيل شريحة SIM نهائيًا."</string>
     <string name="kg_invalid_confirm_pin_hint" product="default" msgid="7003469261464593516">"‏لا يتطابق رمزا رمز PIN"</string>
     <string name="kg_login_too_many_attempts" msgid="6486842094005698475">"محاولات النقش كثيرة جدًا"</string>
@@ -1478,7 +1478,7 @@
     <string name="restr_pin_confirm_pin" msgid="8501523829633146239">"‏تأكيد رمز PIN الجديد"</string>
     <string name="restr_pin_create_pin" msgid="8017600000263450337">"إنشاء رقم تعريف شخصي لتعديل القيود"</string>
     <string name="restr_pin_error_doesnt_match" msgid="2224214190906994548">"أرقام التعريف الشخصية لا تتطابق، أعد المحاولة."</string>
-    <string name="restr_pin_error_too_short" msgid="8173982756265777792">"‏رمز PIN أقصر مما يلزم، يجب ألا يقل عن 4 أرقام. "</string>
+    <string name="restr_pin_error_too_short" msgid="8173982756265777792">"رقم التعريف الشخصي أقصر مما يلزم، يجب ألا يقل عن ٤ أرقام. "</string>
     <plurals name="restr_pin_countdown" formatted="false" msgid="9061246974881224688">
       <item quantity="zero">حاول مرة أخرى خلال أقل من ثانية <xliff:g id="COUNT">%d</xliff:g></item>
       <item quantity="two">حاول مرة أخرى خلال ثانيتين (<xliff:g id="COUNT">%d</xliff:g>)</item>
@@ -1508,8 +1508,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"المطالبة برقم التعريف الشخصي قبل إزالة التثبيت"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"المطالبة بنقش إلغاء القفل قبل إزالة التثبيت"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"المطالبة بكلمة المرور قبل إزالة التثبيت"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"يمكن ألا يعمل التطبيق مع وضع تقسيم الشاشة."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"التطبيق لا يتيح تقسيم الشاشة."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"تم تثبيت الحزمة عن طريق المشرف"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"تم التحديث بواسطة المشرف"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"تم حذف الحزمة عن طريق المشرف"</string>
diff --git a/core/res/res/values-az-rAZ/strings.xml b/core/res/res/values-az-rAZ/strings.xml
index e76ce87..2e4c10d 100644
--- a/core/res/res/values-az-rAZ/strings.xml
+++ b/core/res/res/values-az-rAZ/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Ayırmadan öncə PIN istənilsin"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Ayırmadan öncə kilid modeli istənilsin"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Ayırmadan öncə parol istənilsin"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Tətbiq bölünmüş ekran ilə işləməyə bilər."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Tətbiq ekran bölünməsini dəstəkləmir."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Administratorunuz tərəfindən quraşdırılıb"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Sizin administrator tərəfindən yeniləndi"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Administratorunuz tərəfindən silinib"</string>
diff --git a/core/res/res/values-b+sr+Latn/strings.xml b/core/res/res/values-b+sr+Latn/strings.xml
index 9231e9a..b1d086e 100644
--- a/core/res/res/values-b+sr+Latn/strings.xml
+++ b/core/res/res/values-b+sr+Latn/strings.xml
@@ -1478,8 +1478,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Traži PIN pre otkačinjanja"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Traži šablon za otključavanje pre otkačinjanja"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Traži lozinku pre otkačinjanja"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija možda neće funkcionisati sa podeljenim ekranom."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podržava podeljeni ekran."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalirao je vaš administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ažurirao je administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Izbrisao je vaš admiistrator"</string>
diff --git a/core/res/res/values-be-rBY/strings.xml b/core/res/res/values-be-rBY/strings.xml
index 8a23529..3152943 100644
--- a/core/res/res/values-be-rBY/strings.xml
+++ b/core/res/res/values-be-rBY/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Запытваць PIN-код перад адмацаваннем"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Запытваць узор разблакіроўкі перад адмацаваннем"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Запытваць пароль перад адмацаваннем"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Праграма можа не працаваць у рэжыме дзялення экрана."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Праграма не падтрымлівае функцыю дзялення экрана."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Усталявана вашым адміністратарам"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Абноўлена вашым адміністратарам"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Выдалена вашым адміністратарам"</string>
diff --git a/core/res/res/values-bg/strings.xml b/core/res/res/values-bg/strings.xml
index 76c7002..ec7ba3a 100644
--- a/core/res/res/values-bg/strings.xml
+++ b/core/res/res/values-bg/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Запитване за ПИН код преди освобождаване"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Запитване за фигура за отключване преди освобождаване"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Запитване за парола преди освобождаване"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Приложението може да не работи в режим на разделен екран."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Приложението не поддържа разделен екран."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Инсталирано от администратора ви"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Актуализирано от администратора ви"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Изтрито от администратора ви"</string>
diff --git a/core/res/res/values-bn-rBD/strings.xml b/core/res/res/values-bn-rBD/strings.xml
index 620e532..491b3a2 100644
--- a/core/res/res/values-bn-rBD/strings.xml
+++ b/core/res/res/values-bn-rBD/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"আনপিন করার আগে পিন চান"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"আনপিন করার আগে আনলক প্যাটার্ন চান"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"আনপিন করার আগে পাসওয়ার্ড চান"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"অ্যাপ্লিকেশানটি বিভক্ত স্ক্রীনে কাজ নাও করতে পারে৷"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"অ্যাপ্লিকেশান বিভক্ত-স্ক্রীন সমর্থন করে না৷"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"আপনার প্রশাসক দ্বারা ইনস্টল করা হয়েছে"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"আপনার প্রশাসক দ্বারা আপডেট করা হয়েছে"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"আপনার প্রশাসক দ্বারা মুছে ফেলা হয়েছে"</string>
diff --git a/core/res/res/values-bs-rBA/strings.xml b/core/res/res/values-bs-rBA/strings.xml
index 82639af..ba164ee 100644
--- a/core/res/res/values-bs-rBA/strings.xml
+++ b/core/res/res/values-bs-rBA/strings.xml
@@ -1478,8 +1478,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Traži PIN prije nego se otkači"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Traži uzorak za otključavanje prije nego se otkači"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Traži lozinku prije nego se otkači"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija možda neće raditi na podijeljenom ekranu"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podržava dijeljenje ekrana."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalirao administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ažurirao administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Izbrisao administrator"</string>
diff --git a/core/res/res/values-ca/strings.xml b/core/res/res/values-ca/strings.xml
index 6fcadfa..6980cd5 100644
--- a/core/res/res/values-ca/strings.xml
+++ b/core/res/res/values-ca/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Sol·licita el codi PIN per anul·lar"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Sol·licita el patró de desbloqueig per anul·lar"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Demana la contrasenya per anul·lar"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"És possible que l\'aplicació no funcioni amb la pantalla dividida."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"L\'aplicació no admet la pantalla dividida."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"L\'administrador ho ha instal·lat"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"L\'administrador l\'ha actualitzat"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"L\'administrador ho ha suprimit"</string>
diff --git a/core/res/res/values-cs/strings.xml b/core/res/res/values-cs/strings.xml
index 127d38b..612475a 100644
--- a/core/res/res/values-cs/strings.xml
+++ b/core/res/res/values-cs/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Před uvolněním požádat o PIN"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Před uvolněním požádat o bezpečnostní gesto"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Před uvolněním požádat o heslo"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikace v režimu rozdělené obrazovky nemusí fungovat."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikace nepodporuje režim rozdělené obrazovky."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Nainstalováno administrátorem"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Aktualizováno administrátorem"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Smazáno administrátorem"</string>
diff --git a/core/res/res/values-da/strings.xml b/core/res/res/values-da/strings.xml
index 407f1f8..f25492b 100644
--- a/core/res/res/values-da/strings.xml
+++ b/core/res/res/values-da/strings.xml
@@ -1194,8 +1194,8 @@
     <string name="time_picker_decrement_minute_button" msgid="6246834937080684791">"Sænk minuttal"</string>
     <string name="time_picker_increment_hour_button" msgid="3652056055810223139">"Forøg timetal"</string>
     <string name="time_picker_decrement_hour_button" msgid="1377479863429214792">"Sænk timetal"</string>
-    <string name="time_picker_increment_set_pm_button" msgid="4147590696151230863">"Indstil PM"</string>
-    <string name="time_picker_decrement_set_am_button" msgid="8302140353539486752">"Indstil AM"</string>
+    <string name="time_picker_increment_set_pm_button" msgid="4147590696151230863">"Indstil e.m."</string>
+    <string name="time_picker_decrement_set_am_button" msgid="8302140353539486752">"Indstil f.m."</string>
     <string name="date_picker_increment_month_button" msgid="5369998479067934110">"Senere måned"</string>
     <string name="date_picker_decrement_month_button" msgid="1832698995541726019">"Tidligere måned"</string>
     <string name="date_picker_increment_day_button" msgid="7130465412308173903">"Senere dag"</string>
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Bed om pinkode inden frigørelse"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Bed om oplåsningsmønster ved deaktivering"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Bed om adgangskode inden frigørelse"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Appen fungerer muligvis ikke i delt skærm."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Appen understøtter ikke delt skærm."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installeret af din administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Opdateret af administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Slettet af din administrator"</string>
diff --git a/core/res/res/values-de/strings.xml b/core/res/res/values-de/strings.xml
index e539a28..898883e 100644
--- a/core/res/res/values-de/strings.xml
+++ b/core/res/res/values-de/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Vor dem Beenden nach PIN fragen"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Vor dem Beenden nach Entsperrungsmuster fragen"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Vor dem Beenden nach Passwort fragen"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Die App funktioniert unter Umständen bei geteiltem Bildschirm nicht."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Das Teilen des Bildschirms wird in dieser App nicht unterstützt."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Von deinem Administrator installiert"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Von deinem Administrator aktualisiert"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Von deinem Administrator gelöscht"</string>
diff --git a/core/res/res/values-el/strings.xml b/core/res/res/values-el/strings.xml
index 1e891d0..58ff631 100644
--- a/core/res/res/values-el/strings.xml
+++ b/core/res/res/values-el/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Να γίνεται ερώτηση για το PIN, πριν από το ξεκαρφίτσωμα"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Να γίνεται ερώτηση για το μοτίβο ξεκλειδώματος, πριν από το ξεκαρφίτσωμα"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Να γίνεται ερώτηση για τον κωδικό πρόσβασης, πριν από το ξεκαρφίτσωμα"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Δεν είναι δυνατή η λειτουργία της εφαρμογής με διαχωρισμό οθόνης."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Η εφαρμογή δεν υποστηρίζει διαχωρισμό οθόνης."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Εγκαταστάθηκε από το διαχειριστή σας"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ενημερώθηκε από το διαχειριστή σας"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Διαγράφηκε από το διαχειριστή σας"</string>
diff --git a/core/res/res/values-en-rAU/strings.xml b/core/res/res/values-en-rAU/strings.xml
index b94222c..fe9d8db 100644
--- a/core/res/res/values-en-rAU/strings.xml
+++ b/core/res/res/values-en-rAU/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Ask for PIN before unpinning"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Ask for unlock pattern before unpinning"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Ask for password before unpinning"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"App may not work with split-screen."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App does not support split-screen."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installed by your administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Updated by your administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Deleted by your administrator"</string>
diff --git a/core/res/res/values-en-rGB/strings.xml b/core/res/res/values-en-rGB/strings.xml
index b94222c..fe9d8db 100644
--- a/core/res/res/values-en-rGB/strings.xml
+++ b/core/res/res/values-en-rGB/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Ask for PIN before unpinning"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Ask for unlock pattern before unpinning"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Ask for password before unpinning"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"App may not work with split-screen."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App does not support split-screen."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installed by your administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Updated by your administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Deleted by your administrator"</string>
diff --git a/core/res/res/values-en-rIN/strings.xml b/core/res/res/values-en-rIN/strings.xml
index b94222c..fe9d8db 100644
--- a/core/res/res/values-en-rIN/strings.xml
+++ b/core/res/res/values-en-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Ask for PIN before unpinning"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Ask for unlock pattern before unpinning"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Ask for password before unpinning"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"App may not work with split-screen."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App does not support split-screen."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installed by your administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Updated by your administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Deleted by your administrator"</string>
diff --git a/core/res/res/values-es-rUS/strings.xml b/core/res/res/values-es-rUS/strings.xml
index 0bfb9e0..289c6ba 100644
--- a/core/res/res/values-es-rUS/strings.xml
+++ b/core/res/res/values-es-rUS/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Solicitar PIN para quitar fijación"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Solicitar patrón de desbloqueo para quitar fijación"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Solicitar contraseña para quitar fijación"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Es posible que la app no funcione en el modo de pantalla dividida."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"La app no es compatible con la función de pantalla dividida."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Lo instaló el administrador."</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Actualizado por el administrador"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Lo eliminó el administrador."</string>
diff --git a/core/res/res/values-es/strings.xml b/core/res/res/values-es/strings.xml
index 99202ab..8bd955b 100644
--- a/core/res/res/values-es/strings.xml
+++ b/core/res/res/values-es/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Solicitar PIN para desactivar"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Solicitar patrón de desbloqueo para desactivar"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Solicitar contraseña para desactivar"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Es posible que la aplicación no funcione con la pantalla dividida."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"La aplicación no admite la pantalla dividida."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalado por tu administrador"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Actualizado por tu administrador"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Eliminado por tu administrador"</string>
diff --git a/core/res/res/values-et-rEE/strings.xml b/core/res/res/values-et-rEE/strings.xml
index b1cc971..1aaf4ae 100644
--- a/core/res/res/values-et-rEE/strings.xml
+++ b/core/res/res/values-et-rEE/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Enne vabastamist küsi PIN-koodi"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Enne vabastamist küsi avamismustrit"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Enne vabastamist küsi parooli"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Rakendus ei pruugi poolitatud ekraaniga töötada."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Rakendus ei toeta jagatud ekraani."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installis teie administraator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Värskendas administraator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Kustutas teie administraator"</string>
diff --git a/core/res/res/values-eu-rES/strings.xml b/core/res/res/values-eu-rES/strings.xml
index ea666d9..4601ff8 100644
--- a/core/res/res/values-eu-rES/strings.xml
+++ b/core/res/res/values-eu-rES/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Eskatu PIN kodea aingura kendu aurretik"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Eskatu desblokeatzeko eredua aingura kendu aurretik"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Eskatu pasahitza aingura kendu aurretik"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Baliteke aplikazioak ez funtzionatzea pantaila zatituan."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikazioak ez du onartzen pantaila zatitua"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Administratzaileak instalatu du"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Administratzaileak eguneratu du"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Administratzaileak ezabatu du"</string>
diff --git a/core/res/res/values-fa/strings.xml b/core/res/res/values-fa/strings.xml
index df9d78f..064055e 100644
--- a/core/res/res/values-fa/strings.xml
+++ b/core/res/res/values-fa/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"درخواست کد پین قبل از برداشتن پین"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"درخواست الگوی باز کردن قفل قبل از برداشتن پین"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"درخواست گذرواژه قبل از برداشتن پین"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"ممکن است برنامه با تقسیم صفحه کار نکند."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"برنامه از تقسیم صفحه پشتیبانی نمی‌کند."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"توسط سرپرستتان نصب شد"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"توسط سرپرست شما به‌روزرسانی شد"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"توسط سرپرستتان حذف شد"</string>
diff --git a/core/res/res/values-fi/strings.xml b/core/res/res/values-fi/strings.xml
index c869961..41c583f 100644
--- a/core/res/res/values-fi/strings.xml
+++ b/core/res/res/values-fi/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Pyydä PIN ennen irrotusta"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pyydä lukituksenpoistokuvio ennen irrotusta"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pyydä salasana ennen irrotusta"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Sovellus ei ehkä toimi jaetulla näytöllä."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Sovellus ei tue jaetun näytön tilaa."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Järjestelmänvalvoja on asentanut paketin."</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Järjestelmänvalvojasi on päivittänyt paketin."</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Järjestelmänvalvoja on poistanut paketin."</string>
diff --git a/core/res/res/values-fr-rCA/strings.xml b/core/res/res/values-fr-rCA/strings.xml
index efc8af3..3607382 100644
--- a/core/res/res/values-fr-rCA/strings.xml
+++ b/core/res/res/values-fr-rCA/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Demander le NIP avant d\'annuler l\'épinglage"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Demander le schéma de déverrouillage avant d\'annuler l\'épinglage"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Demander le mot de passe avant d\'annuler l\'épinglage"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Il est possible que l\'application ne fonctionne pas en mode Écran partagé."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"L\'application n\'est pas compatible avec l\'écran partagé."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installé par votre administrateur"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Mis à jour par votre administrateur"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Supprimé par votre administrateur"</string>
diff --git a/core/res/res/values-fr/strings.xml b/core/res/res/values-fr/strings.xml
index 4e83fa9..27e1b70 100644
--- a/core/res/res/values-fr/strings.xml
+++ b/core/res/res/values-fr/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Demander le code PIN avant d\'annuler l\'épinglage"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Demander le schéma de déverrouillage avant d\'annuler l\'épinglage"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Demander le mot de passe avant d\'annuler l\'épinglage"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Il est possible que l\'application ne fonctionne pas en mode Écran partagé."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Application incompatible avec l\'écran partagé."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installé par votre administrateur"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Mis à jour par votre administrateur"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Supprimé par votre administrateur"</string>
diff --git a/core/res/res/values-gl-rES/strings.xml b/core/res/res/values-gl-rES/strings.xml
index 2fa6087..c724f8c 100644
--- a/core/res/res/values-gl-rES/strings.xml
+++ b/core/res/res/values-gl-rES/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Solicitar un PIN antes de soltar a pantalla"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Solicitar un padrón de desbloqueo antes de soltar a pantalla"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Solicitar un contrasinal antes de soltar a pantalla"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Pode que a aplicación non funcione coa pantalla dividida."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"A aplicación non é compatible coa función de pantalla dividida."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalado polo administrador"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Actualizado polo administrador"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Eliminado polo administrador"</string>
diff --git a/core/res/res/values-gu-rIN/strings.xml b/core/res/res/values-gu-rIN/strings.xml
index 0b9f4ad..49acd99 100644
--- a/core/res/res/values-gu-rIN/strings.xml
+++ b/core/res/res/values-gu-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"અનપિન કરતાં પહેલાં PIN માટે પૂછો"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"અનપિન કરતા પહેલાં અનલૉક પેટર્ન માટે પૂછો"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"અનપિન કરતાં પહેલાં પાસવર્ડ માટે પૂછો"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"વિભાજિત-સ્ક્રીન સાથે ઍપ્લિકેશન કદાચ કામ ન કરે."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ઍપ્લિકેશન સ્ક્રીન-વિભાજનનું સમર્થન કરતી નથી."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"તમારા વ્યવસ્થાપક દ્વારા ઇન્સ્ટોલ કરેલ"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"તમારા વ્યવસ્થાપક દ્વારા અપડેટ થયેલ"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"તમારા વ્યવસ્થાપક દ્વારા કાઢી નાખેલ"</string>
diff --git a/core/res/res/values-hi/strings.xml b/core/res/res/values-hi/strings.xml
index 474e81e..b621005 100644
--- a/core/res/res/values-hi/strings.xml
+++ b/core/res/res/values-hi/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"अनपिन करने से पहले पिन के लिए पूछें"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"अनपिन करने से पहले अनलॉक पैटर्न के लिए पूछें"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"अनपिन करने से पहले पासवर्ड के लिए पूछें"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"हो सकता है कि ऐप्लिकेशन विभाजित स्क्रीन के साथ काम ना करे."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ऐप विभाजित स्‍क्रीन का समर्थन नहीं करता है."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"आपके नियंत्रक द्वारा इंस्‍टॉल किया गया"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"आपके नियंत्रक द्वारा अपडेट किया गया"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"आपके नियंत्रक द्वारा हटाया गया"</string>
diff --git a/core/res/res/values-hr/strings.xml b/core/res/res/values-hr/strings.xml
index 837aa56..6bc0d6e 100644
--- a/core/res/res/values-hr/strings.xml
+++ b/core/res/res/values-hr/strings.xml
@@ -1478,8 +1478,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Traži PIN radi otkvačivanja"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Traži uzorak za otključavanje radi otkvačivanja"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Traži zaporku radi otkvačivanja"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija možda neće funkcionirati s podijeljenim zaslonom."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podržava podijeljeni zaslon."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalirao administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ažurira vaš administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Izbrisao administrator"</string>
diff --git a/core/res/res/values-hu/strings.xml b/core/res/res/values-hu/strings.xml
index 0c4705d..dd39cca 100644
--- a/core/res/res/values-hu/strings.xml
+++ b/core/res/res/values-hu/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"PIN-kód kérése a rögzítés feloldásához"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Feloldási minta kérése a rögzítés feloldásához"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Jelszó kérése a rögzítés feloldásához"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Lehet, hogy az alkalmazás nem működik osztott képernyős nézetben."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Az alkalmazás nem támogatja az osztott képernyős nézetet."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"A rendszergazda telepítette"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Frissítette a rendszergazda"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"A rendszergazda törölte"</string>
diff --git a/core/res/res/values-hy-rAM/strings.xml b/core/res/res/values-hy-rAM/strings.xml
index 4be90da..e41bf64 100644
--- a/core/res/res/values-hy-rAM/strings.xml
+++ b/core/res/res/values-hy-rAM/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Ապաամրացնելուց առաջ հարցնել PIN-կոդը"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Ապաամրացնելուց առաջ հարցնել ապակողպող նախշը"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Ապաամրացնելուց առաջ հարցնել գաղտնաբառը"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Հավելվածը չի կարող աշխատել տրոհված էկրանի ռեժիմում:"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Հավելվածը չի աջակցում էկրանի տրոհումը:"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Ադմինիստրատորը տեղադրել է այն"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ադմինիստրատորը թարմացրել է այն"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Ադմինիստրատորը ջնջել է այն"</string>
diff --git a/core/res/res/values-in/strings.xml b/core/res/res/values-in/strings.xml
index 7218617..8940875 100644
--- a/core/res/res/values-in/strings.xml
+++ b/core/res/res/values-in/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Meminta PIN sebelum melepas sematan"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Meminta pola pembukaan kunci sebelum melepas sematan"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Meminta sandi sebelum melepas sematan"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikasi mungkin tidak berfungsi dengan layar terpisah."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App tidak mendukung layar terpisah."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Dipasang oleh administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Diperbarui oleh administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Dihapus oleh administrator"</string>
diff --git a/core/res/res/values-is-rIS/strings.xml b/core/res/res/values-is-rIS/strings.xml
index cebc4cc..546af60 100644
--- a/core/res/res/values-is-rIS/strings.xml
+++ b/core/res/res/values-is-rIS/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Biðja um PIN-númer til að losa"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Biðja um opnunarmynstur til að losa"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Biðja um aðgangsorð til að losa"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Hugsanlega virkar forritið ekki ef skjánum er skipt upp."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Forritið styður ekki að skjánum sé skipt."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Uppsett af kerfisstjóra"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Uppfært af kerfisstjóranum"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Eytt af kerfisstjóra"</string>
diff --git a/core/res/res/values-it/strings.xml b/core/res/res/values-it/strings.xml
index 2a73990..fc13359 100644
--- a/core/res/res/values-it/strings.xml
+++ b/core/res/res/values-it/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Richiedi il PIN per lo sblocco"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Richiedi sequenza di sblocco prima di sbloccare"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Richiedi password prima di sbloccare"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"L\'app potrebbe non funzionare con lo schermo diviso."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"L\'app non supporta la modalità Schermo diviso."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installato dall\'amministratore"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Aggiornato dall\'amministratore"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Eliminato dall\'amministratore"</string>
diff --git a/core/res/res/values-iw/strings.xml b/core/res/res/values-iw/strings.xml
index 80435b6..5b9b5e1 100644
--- a/core/res/res/values-iw/strings.xml
+++ b/core/res/res/values-iw/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"‏בקש PIN לפני ביטול הצמדה"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"בקש קו ביטול נעילה לפני ביטול הצמדה"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"בקש סיסמה לפני ביטול הצמדה"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"ייתכן שהיישום לא יפעל עם מסך מפוצל."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"האפליקציה אינה תומכת במסך מפוצל."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"הותקנה על ידי מנהל המערכת שלך"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"עודכן על ידי מנהל המערכת שלך"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"נמחקה על ידי מנהל המערכת שלך"</string>
diff --git a/core/res/res/values-ja/strings.xml b/core/res/res/values-ja/strings.xml
index 394775f..d3ecef8 100644
--- a/core/res/res/values-ja/strings.xml
+++ b/core/res/res/values-ja/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"オフライン再生を解除する前にPINの入力を求める"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"画面固定を解除する前にロック解除パターンの入力を求める"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"オフライン再生を解除する前にパスワードの入力を求める"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"アプリは分割画面では動作しないことがあります。"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"アプリで分割画面がサポートされていません。"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"管理者によってインストールされました"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"管理者によって更新されています"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"管理者によって削除されました"</string>
diff --git a/core/res/res/values-ka-rGE/strings.xml b/core/res/res/values-ka-rGE/strings.xml
index fcc56da..20b1055 100644
--- a/core/res/res/values-ka-rGE/strings.xml
+++ b/core/res/res/values-ka-rGE/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ფიქსაციის მოხსნამდე PIN-ის მოთხოვნა"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ფიქსაციის მოხსნამდე განბლოკვის ნიმუშის მოთხოვნა"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ფიქსაციის მოხსნამდე პაროლის მოთხოვნა"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"აპმა შეიძლება არ იმუშაოს გაყოფილი ეკრანის რეჟიმში."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ეკრანის გაყოფა არ არის მხარდაჭერილი აპის მიერ."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"თქვენი ადმინისტრატორის მიერ დაყენებული"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"განახლებულია თქვენი ადმინისტრატორის მიერ"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"თქვენი ადმინისტრატორის მიერ წაშლილი"</string>
diff --git a/core/res/res/values-kk-rKZ/strings.xml b/core/res/res/values-kk-rKZ/strings.xml
index 6eaa770..1372064 100644
--- a/core/res/res/values-kk-rKZ/strings.xml
+++ b/core/res/res/values-kk-rKZ/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Босату алдында PIN кодын сұрау"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Босату алдында бекітпесін ашу өрнегін сұрау"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Босату алдында құпия сөзді сұрау"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Қолданба бөлінген экранда жұмыс істемеуі мүмкін."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Қодланба бөлінген экранды қолдамайды."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Әкімші орнатқан"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Әкімші жаңартты"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Әкімші жойған"</string>
diff --git a/core/res/res/values-km-rKH/strings.xml b/core/res/res/values-km-rKH/strings.xml
index 30d3c0a..d57659c 100644
--- a/core/res/res/values-km-rKH/strings.xml
+++ b/core/res/res/values-km-rKH/strings.xml
@@ -1470,8 +1470,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"សួរ​រក​កូដ PIN មុន​ពេល​ផ្ដាច់"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"សួរ​រក​លំនាំ​ដោះ​សោ​មុន​ពេល​ផ្ដាច់"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"សួរ​រក​ពាក្យ​សម្ងាត់​មុន​ពេល​ផ្ដាច់"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"កម្មវិធីអាចនឹងមិនដំណើរការនៅលើអេក្រង់បំបែកទេ"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"កម្មវិធីមិនគាំទ្រអេក្រង់បំបែកជាពីរទេ"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"បានដំឡើងដោយអ្នកគ្រប់គ្រងរបស់អ្នក"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"បានធ្វើបច្ចុប្បន្នភាពដោយអ្នកគ្រប់គ្រងរបស់អ្នក"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"បានលុបដោយអ្នកគ្រប់គ្រងរបស់អ្នក"</string>
diff --git a/core/res/res/values-kn-rIN/strings.xml b/core/res/res/values-kn-rIN/strings.xml
index 087b399..7f94a1d 100644
--- a/core/res/res/values-kn-rIN/strings.xml
+++ b/core/res/res/values-kn-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ಅನ್‌ಪಿನ್ ಮಾಡಲು ಪಿನ್‌ ಕೇಳು"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ಅನ್‌ಪಿನ್ ಮಾಡಲು ಅನ್‌ಲಾಕ್ ಪ್ಯಾಟರ್ನ್ ಕೇಳಿ"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ಅನ್‌ಪಿನ್ ಮಾಡಲು ಪಾಸ್‌ವರ್ಡ್ ಕೇಳು"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"ವಿಭಜಿಸಿದ ಪರದೆಯಲ್ಲಿ ಅಪ್ಲಿಕೇಶನ್ ಕೆಲಸ ಮಾಡದೇ ಇರಬಹುದು."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ಅಪ್ಲಿಕೇಶನ್ ಸ್ಪ್ಲಿಟ್ ಸ್ಕ್ರೀನ್ ಅನ್ನು ಬೆಂಬಲಿಸುವುದಿಲ್ಲ."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"ನಿಮ್ಮ ನಿರ್ವಾಹಕರಿಂದ ಸ್ಥಾಪಿಸಲಾಗಿದೆ"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"ನಿಮ್ಮ ನಿರ್ವಾಹಕರಿಂದ ನವೀಕರಿಸಲಾಗಿದೆ"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"ನಿಮ್ಮ ನಿರ್ವಾಹಕರಿಂದ ಅಳಿಸಲಾಗಿದೆ"</string>
diff --git a/core/res/res/values-ko/strings.xml b/core/res/res/values-ko/strings.xml
index 52de5ba..4f6d602 100644
--- a/core/res/res/values-ko/strings.xml
+++ b/core/res/res/values-ko/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"고정 해제 이전에 PIN 요청"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"고정 해제 이전에 잠금해제 패턴 요청"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"고정 해제 이전에 비밀번호 요청"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"앱이 분할 화면에서 작동하지 않을 수 있습니다."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"앱이 화면 분할을 지원하지 않습니다."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"관리자가 설치함"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"관리자에 의해 업데이트됨"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"관리자가 삭제함"</string>
diff --git a/core/res/res/values-ky-rKG/strings.xml b/core/res/res/values-ky-rKG/strings.xml
index 34cc7e5..c7d32d11 100644
--- a/core/res/res/values-ky-rKG/strings.xml
+++ b/core/res/res/values-ky-rKG/strings.xml
@@ -1469,8 +1469,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Бошотуудан мурун PIN суралсын"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Бошотуудан мурун кулпуну ачкан үлгү суралсын"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Бошотуудан мурун сырсөз суралсын"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Колдонмодо экран бөлүнбөшү мүмкүн."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Колдонмодо экран бөлүнбөйт."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Администраторуңуз тарабынан орнотулган"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Администраторуңуз жаңырткан"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Администраторуңуз тарабынан жок кылынган"</string>
diff --git a/core/res/res/values-lo-rLA/strings.xml b/core/res/res/values-lo-rLA/strings.xml
index ea62f9b..a69ccb7 100644
--- a/core/res/res/values-lo-rLA/strings.xml
+++ b/core/res/res/values-lo-rLA/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"​ຖາມ​ຫາ PIN ກ່ອນ​ຍົກ​ເລີກ​ການປັກ​ໝຸດ"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"​ຖາມ​ຫາ​ຮູບ​ແບບ​ປົດ​ລັອກ​ກ່ອນ​ຍົກ​ເລີກ​ການ​ປັກ​ໝຸດ"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"​ຖາມ​ຫາ​ລະ​ຫັດ​ຜ່ານ​ກ່ອນ​ຍົກ​ເລີກ​ການ​ປັກ​ໝຸດ"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"ແອັບອາດໃຊ້ບໍ່ໄດ້ກັບການແບ່ງໜ້າຈໍ."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ແອັບບໍ່ຮອງຮັບໜ້າຈໍແບບແຍກກັນ."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"ຜູ້​ຄວບ​ຄຸມ​ຂອງ​ທ່ານ​ຕິດ​ຕັ້ງ​ໃສ່​ແລ້ວ"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"ອັບ​ເດດ​ໂດຍ​ຜູ້​ຄວບ​ຄຸມ​ຂອງ​ທ່ານ​ແລ້ວ"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"ຖືກ​ຜູ້​ຄວບ​ຄຸມ​ຂອງ​ທ່ານ​ລຶບ​ໄປ​ແລ້ວ"</string>
diff --git a/core/res/res/values-lt/strings.xml b/core/res/res/values-lt/strings.xml
index 3e815ec..9130d2c 100644
--- a/core/res/res/values-lt/strings.xml
+++ b/core/res/res/values-lt/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Prašyti PIN kodo prieš atsegant"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Prašyti atrakinimo piešinio prieš atsegant"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Prašyti slaptažodžio prieš atsegant"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Programa gali neveikti naudojant skaidytą ekraną."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Programoje nepalaikomas skaidytas ekranas."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Įdiegė administratorius"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Atnaujino administratorius"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Ištrynė administratorius"</string>
diff --git a/core/res/res/values-lv/strings.xml b/core/res/res/values-lv/strings.xml
index 56001fc..19aa282 100644
--- a/core/res/res/values-lv/strings.xml
+++ b/core/res/res/values-lv/strings.xml
@@ -1478,8 +1478,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Prasīt PIN kodu pirms atspraušanas"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pirms atspraušanas pieprasīt grafisko atslēgu"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pirms atspraušanas pieprasīt paroli"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Iespējams, lietotnē nedarbosies ekrāna sadalīšana."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Lietotnē netiek atbalstīta ekrāna sadalīšana."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalēja jūsu administrators"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Atjaunināja administrators"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Izdzēsa jūsu administrators"</string>
diff --git a/core/res/res/values-mk-rMK/strings.xml b/core/res/res/values-mk-rMK/strings.xml
index 060a9fa..425722d 100644
--- a/core/res/res/values-mk-rMK/strings.xml
+++ b/core/res/res/values-mk-rMK/strings.xml
@@ -1470,8 +1470,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Прашај за ПИН пред откачување"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Прашај за шема за отклучување пред откачување"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Прашај за лозинка пред откачување"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Апликацијата можеби нема да работи во поделен екран."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Апликацијата не поддржува поделен екран."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Инсталирано од администраторот"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ажурирано од администраторот"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Избришано од администраторот"</string>
diff --git a/core/res/res/values-ml-rIN/strings.xml b/core/res/res/values-ml-rIN/strings.xml
index f6ff1d8..1e24d01 100644
--- a/core/res/res/values-ml-rIN/strings.xml
+++ b/core/res/res/values-ml-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ചെയ്യുംമുമ്പ് പിൻ ചോദിക്കൂ"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"അൺപിൻ ചെയ്യുന്നതിനുമുമ്പ് അൺലോക്ക് പാറ്റേൺ ആവശ്യപ്പെടുക"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"അൺപിൻ ചെയ്യുന്നതിനുമുമ്പ് പാസ്‌വേഡ് ആവശ്യപ്പെടുക"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"സ്പ്ലിറ്റ്-സ്ക്രീനിനൊപ്പം ആപ്പ് പ്രവർത്തിച്ചേക്കില്ല."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"സ്പ്ലിറ്റ്-സ്ക്രീനിനെ ആപ്പ് പിന്തുണയ്ക്കുന്നില്ല."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"നിങ്ങളുടെ അഡ്‌മിനിസ്‌ട്രേറ്റർ ഇൻസ്റ്റാളുചെയ്‌തു"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"നിങ്ങളുടെ അഡ്‌മിനിസ്‌ട്രേറ്റർ അപ്‌ഡേറ്റുചെയ്‌തു"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"നിങ്ങളുടെ അഡ്‌മിനിസ്‌ട്രേറ്റർ ഇല്ലാതാക്കി"</string>
diff --git a/core/res/res/values-mn-rMN/strings.xml b/core/res/res/values-mn-rMN/strings.xml
index 75105e6..0e2f8af 100644
--- a/core/res/res/values-mn-rMN/strings.xml
+++ b/core/res/res/values-mn-rMN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Тогтоосныг суллахаас өмнө PIN асуух"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Тогтоосныг суллахаас өмнө түгжээ тайлах хээ асуух"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Тогтоосныг суллахаас өмнө нууц үг асуух"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Апп хуваагдсан дэлгэцэд ажиллахгүй."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Энэ апп нь дэлгэц хуваах тохиргоог дэмждэггүй."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Таны админ суулгасан байна"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Танай админ шинэчилсэн"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Таны админ устгасан байна"</string>
diff --git a/core/res/res/values-mr-rIN/strings.xml b/core/res/res/values-mr-rIN/strings.xml
index 8a3e564..5dc9721 100644
--- a/core/res/res/values-mr-rIN/strings.xml
+++ b/core/res/res/values-mr-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"अनपिन करण्‍यापूर्वी पिन साठी विचारा"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"अनपिन करण्‍यापूर्वी अनलॉक नमुन्यासाठी विचारा"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"अनपिन करण्‍यापूर्वी संकेतशब्दासाठी विचारा"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"अॅप कदाचित विभाजित-स्क्रीनसह कार्य करू शकत नाही."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"अॅप स्क्रीन-विभाजनास समर्थन देत नाही."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"आपल्या प्रशासकाद्वारे स्थापित केले आहे"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"आपल्या प्रशासकाद्वारे अद्यतनित केले"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"आपल्या प्रशासकाद्वारे हटविले आहे"</string>
diff --git a/core/res/res/values-ms-rMY/strings.xml b/core/res/res/values-ms-rMY/strings.xml
index 5db9c77..ced967b 100644
--- a/core/res/res/values-ms-rMY/strings.xml
+++ b/core/res/res/values-ms-rMY/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Minta PIN sebelum menyahsemat"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Minta corak buka kunci sebelum menyahsemat"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Minta kata laluan sebelum menyahsemat"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Apl mungkin tidak berfungsi dengan skrin pisah."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Apl tidak menyokong skrin pisah."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Dipasang oleh pentadbir anda"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Dikemas kini oleh pentadbir anda"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Dipadamkan oleh pentadbir anda"</string>
diff --git a/core/res/res/values-my-rMM/strings.xml b/core/res/res/values-my-rMM/strings.xml
index 5e5ec4e..4e88bb40 100644
--- a/core/res/res/values-my-rMM/strings.xml
+++ b/core/res/res/values-my-rMM/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ပင်မဖြုတ်မီမှာ PIN ကို မေးကြည့်ရန်"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ပင်မဖြုတ်မီမှာ သော့ဖွင့် ရေးဆွဲမှုပုံစံကို မေးကြည့်ရန်"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ပင်မဖြုတ်မီမှာ စကားဝှက်ကို မေးကြည့်ရန်"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"မျက်နှာပြင် ခွဲခြမ်းပြသမှုဖြင့် အက်ပ်သည် အလုပ်လုပ်မည် မဟုတ်ပါ။"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"အက်ပ်သည် မျက်နှာပြင်ခွဲပြရန် ပံ့ပိုးထားခြင်းမရှိပါ။"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"သင့် အက်ဒမင်မှ သွင်းယူထား၏"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"သင့်စီမံခန့်ခွဲသူမှ အဆင့်မြှင့်ထားပါသည်။"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"သင့် အက်ဒမင်အား ဖျက်ပစ်ရန်"</string>
diff --git a/core/res/res/values-nb/strings.xml b/core/res/res/values-nb/strings.xml
index cfccdeb..ff28307 100644
--- a/core/res/res/values-nb/strings.xml
+++ b/core/res/res/values-nb/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"PIN-kode for å løsne apper"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Krev bruk av opplåsningsmønster for å løsne apper"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Krev passord for å løsne apper"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Det kan hende at appen ikke fungerer med delt skjerm."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Appen støtter ikke delt skjerm."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Installert av administratoren"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Oppdatert av administratoren"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Slettet av administratoren"</string>
diff --git a/core/res/res/values-ne-rNP/strings.xml b/core/res/res/values-ne-rNP/strings.xml
index fb817b5..878eff9f 100644
--- a/core/res/res/values-ne-rNP/strings.xml
+++ b/core/res/res/values-ne-rNP/strings.xml
@@ -1474,8 +1474,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"पिन निकाल्नुअघि PIN सोध्नुहोस्"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"पिन निकाल्नुअघि खोल्ने रूपरेखा सोध्नुहोस्"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"पिन निकाल्नुअघि पासवर्ड सोध्नुहोस्"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"अनुप्रयोगले विभाजित-स्क्रिनमा काम नगर्न सक्छ।"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"अनुप्रयोगले विभाजित-स्क्रिनलाई समर्थन गर्दैन।"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"तपाईँको प्रशासकद्वारा स्थापना गरिएको"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"तपाईँको प्रशासकद्वारा अद्यावधिक गरिएको"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"तपाईँको प्रशासकद्वारा हटाइएको"</string>
diff --git a/core/res/res/values-nl/strings.xml b/core/res/res/values-nl/strings.xml
index 3de8496..f76d185 100644
--- a/core/res/res/values-nl/strings.xml
+++ b/core/res/res/values-nl/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Vraag pin voor losmaken"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Vraag patroon voor losmaken"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Vraag wachtwoord voor losmaken"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"App werkt mogelijk niet met gesplitst scherm."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App biedt geen ondersteuning voor gesplitst scherm."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Geïnstalleerd door je beheerder"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Geüpdatet door je beheerder"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Verwijderd door je beheerder"</string>
diff --git a/core/res/res/values-pa-rIN/strings.xml b/core/res/res/values-pa-rIN/strings.xml
index 87f973f..26d5af9 100644
--- a/core/res/res/values-pa-rIN/strings.xml
+++ b/core/res/res/values-pa-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ਅਨਪਿਨ ਕਰਨ ਤੋਂ ਪਹਿਲਾਂ PIN ਮੰਗੋ"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ਅਨਪਿਨ ਕਰਨ ਤੋਂ ਪਹਿਲਾਂ ਪੈਟਰਨ ਅਨਲੌਕ ਕਰਨ ਲਈ ਪੁੱਛੋ"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ਅਨਪਿਨ ਕਰਨ ਤੋਂ ਪਹਿਲਾਂ ਪਾਸਵਰਡ ਮੰਗੋ"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"ਹੋ ਸਕਦਾ ਹੈ ਕਿ ਐਪ ਸਪਲਿਟ-ਸਕ੍ਰੀਨ ਨਾਲ ਕੰਮ ਨਾ ਕਰੇ।"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ਐਪ ਸਪਲਿਟ-ਸਕ੍ਰੀਨ ਨੂੰ ਸਮਰਥਨ ਨਹੀਂ ਕਰਦੀ।"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"ਤੁਹਾਡੇ ਪ੍ਰਬੰਧਕ ਵੱਲੋਂ ਇੰਸਟੌਲ ਕੀਤਾ ਗਿਆ"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"ਤੁਹਾਡੇ ਪ੍ਰਸ਼ਾਸਕ ਦੁਆਰਾ ਅਪਡੇਟ ਕੀਤਾ ਗਿਆ"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"ਤੁਹਾਡੇ ਪ੍ਰਬੰਧਕ ਵੱਲੋਂ ਮਿਟਾਇਆ ਗਿਆ"</string>
diff --git a/core/res/res/values-pl/strings.xml b/core/res/res/values-pl/strings.xml
index 6be9a9d..6bfac83 100644
--- a/core/res/res/values-pl/strings.xml
+++ b/core/res/res/values-pl/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Podaj PIN, aby odpiąć"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Aby odpiąć, poproś o wzór odblokowania"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Aby odpiąć, poproś o hasło"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacja może nie działać przy podzielonym ekranie."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacja nie obsługuje dzielonego ekranu."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Zainstalowany przez administratora"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Zaktualizowane przez administratora"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Usunięty przez administratora"</string>
diff --git a/core/res/res/values-pt-rBR/strings.xml b/core/res/res/values-pt-rBR/strings.xml
index c8004bf..241ee823 100644
--- a/core/res/res/values-pt-rBR/strings.xml
+++ b/core/res/res/values-pt-rBR/strings.xml
@@ -254,7 +254,7 @@
     <string name="permgrouplab_sensors" msgid="416037179223226722">"Sensores corporais"</string>
     <string name="permgroupdesc_sensors" msgid="7147968539346634043">"acesse dados do sensor sobre seus sinais vitais"</string>
     <string name="capability_title_canRetrieveWindowContent" msgid="3901717936930170320">"Recuperar cont. da janela"</string>
-    <string name="capability_desc_canRetrieveWindowContent" msgid="3772225008605310672">"Inspecionar o conteúdo da janela com que você está interagindo."</string>
+    <string name="capability_desc_canRetrieveWindowContent" msgid="3772225008605310672">"Inspecionar o conteúdo da janela com a qual você está interagindo."</string>
     <string name="capability_title_canRequestTouchExploration" msgid="3108723364676667320">"Ativar Explorar por toque"</string>
     <string name="capability_desc_canRequestTouchExploration" msgid="5800552516779249356">"Itens tocados serão falados em voz alta e a tela poderá ser explorada por meio de gestos."</string>
     <string name="capability_title_canRequestEnhancedWebAccessibility" msgid="1739881766522594073">"Ativar acessibilidade na Web aprimorada"</string>
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Pedir PIN antes de liberar"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pedir padrão de desbloqueio antes de liberar"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pedir senha antes de liberar"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"É possível que o app não funcione com o recurso de divisão de tela."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"O app não é compatível com a divisão de tela."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalado pelo seu administrador"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Atualizado pelo administrador"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Excluído pelo seu administrador"</string>
diff --git a/core/res/res/values-pt-rPT/strings.xml b/core/res/res/values-pt-rPT/strings.xml
index c2ba8ad..ebe6efb 100644
--- a/core/res/res/values-pt-rPT/strings.xml
+++ b/core/res/res/values-pt-rPT/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Pedir PIN antes de soltar"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pedir sequência de desbloqueio antes de soltar"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pedir palavra-passe antes de soltar"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"A aplicação pode não funcionar com o ecrã dividido."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"A aplicação não é compatível com o ecrã dividido."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalado pelo administrador"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Atualizado pelo administrador"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Eliminado pelo administrador"</string>
diff --git a/core/res/res/values-pt/strings.xml b/core/res/res/values-pt/strings.xml
index c8004bf..241ee823 100644
--- a/core/res/res/values-pt/strings.xml
+++ b/core/res/res/values-pt/strings.xml
@@ -254,7 +254,7 @@
     <string name="permgrouplab_sensors" msgid="416037179223226722">"Sensores corporais"</string>
     <string name="permgroupdesc_sensors" msgid="7147968539346634043">"acesse dados do sensor sobre seus sinais vitais"</string>
     <string name="capability_title_canRetrieveWindowContent" msgid="3901717936930170320">"Recuperar cont. da janela"</string>
-    <string name="capability_desc_canRetrieveWindowContent" msgid="3772225008605310672">"Inspecionar o conteúdo da janela com que você está interagindo."</string>
+    <string name="capability_desc_canRetrieveWindowContent" msgid="3772225008605310672">"Inspecionar o conteúdo da janela com a qual você está interagindo."</string>
     <string name="capability_title_canRequestTouchExploration" msgid="3108723364676667320">"Ativar Explorar por toque"</string>
     <string name="capability_desc_canRequestTouchExploration" msgid="5800552516779249356">"Itens tocados serão falados em voz alta e a tela poderá ser explorada por meio de gestos."</string>
     <string name="capability_title_canRequestEnhancedWebAccessibility" msgid="1739881766522594073">"Ativar acessibilidade na Web aprimorada"</string>
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Pedir PIN antes de liberar"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pedir padrão de desbloqueio antes de liberar"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pedir senha antes de liberar"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"É possível que o app não funcione com o recurso de divisão de tela."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"O app não é compatível com a divisão de tela."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalado pelo seu administrador"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Atualizado pelo administrador"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Excluído pelo seu administrador"</string>
diff --git a/core/res/res/values-ro/strings.xml b/core/res/res/values-ro/strings.xml
index 7485e65..951e365 100644
--- a/core/res/res/values-ro/strings.xml
+++ b/core/res/res/values-ro/strings.xml
@@ -1478,8 +1478,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Solicită codul PIN înainte de a anula fixarea"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Solicită modelul pentru deblocare înainte de a anula fixarea"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Solicită parola înainte de a anula fixarea"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Este posibil ca aplicația să nu funcționeze cu ecranul împărțit."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplicația nu acceptă ecranul împărțit."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Instalat de administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Actualizat de un administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Șters de administrator"</string>
diff --git a/core/res/res/values-round-watch/dimens.xml b/core/res/res/values-round-watch/dimens.xml
new file mode 100644
index 0000000..a12f499
--- /dev/null
+++ b/core/res/res/values-round-watch/dimens.xml
@@ -0,0 +1,27 @@
+<?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.
+-->
+<resources>
+    <!-- each of these are relative to the display size -->
+    <item name="input_extract_layout_height" type="fraction">25.2%</item>
+    <item name="input_extract_layout_padding_left" type="fraction">7.5%</item>
+    <item name="input_extract_layout_padding_left_no_action" type="fraction">@fraction/input_extract_layout_padding_right</item>
+    <item name="input_extract_layout_padding_right" type="fraction">21.4%</item>
+    <item name="input_extract_text_margin_bottom" type="fraction">5.5%</item>
+    <item name="input_extract_action_margin_bottom" type="fraction">2.1%</item>
+    <item name="input_extract_action_button_width" type="dimen">32dp</item>
+    <item name="input_extract_action_button_height" type="dimen">32dp</item>
+</resources>
diff --git a/core/res/res/values-ru/strings.xml b/core/res/res/values-ru/strings.xml
index 5926bfd..a012a95 100644
--- a/core/res/res/values-ru/strings.xml
+++ b/core/res/res/values-ru/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"PIN-код для отключения"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Запрашивать графический ключ для отключения блокировки"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Запрашивать пароль для отключения блокировки"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Приложение не поддерживает разделение экрана."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Приложение не поддерживает разделение экрана."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Установлено администратором"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Обновлено администратором"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Удалено администратором"</string>
diff --git a/core/res/res/values-si-rLK/strings.xml b/core/res/res/values-si-rLK/strings.xml
index 6c76da0..9175e7e 100644
--- a/core/res/res/values-si-rLK/strings.xml
+++ b/core/res/res/values-si-rLK/strings.xml
@@ -1470,8 +1470,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ගැලවීමට පෙර PIN විමසන්න"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ගැලවීමට පෙර අගුළු අරින රටාව සඳහා අසන්න"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ගැලවීමට පෙර මුරපදය විමසන්න"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"යෙදුම බෙදුම්-තිරය සමග ක්‍රියා නොකළ හැකිය."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"යෙදුම බෙදුණු-තිරය සඳහා සහාය නොදක්වයි."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"ඔබගේ පරිපාලක විසින් ස්ථාපනය කරන ලද"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"ඔබගේ පරිපාලක විසින් යාවත්කාලීන කරන ලදී"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"ඔබගේ පරිපාලක විසින් මකන ලද"</string>
diff --git a/core/res/res/values-sk/strings.xml b/core/res/res/values-sk/strings.xml
index ec45070..e09ed27 100644
--- a/core/res/res/values-sk/strings.xml
+++ b/core/res/res/values-sk/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Pred uvoľnením požiadať o číslo PIN"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pred uvoľnením požiadať o bezpečnostný vzor"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pred uvoľnením požiadať o heslo"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikácia nemusí fungovať so zapnutou rozdelenou obrazovkou."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikácia nepodporuje rozdelenú obrazovku."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Inštalovaný správcom"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Aktualizované správcom"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Odstránený správcom"</string>
diff --git a/core/res/res/values-sl/strings.xml b/core/res/res/values-sl/strings.xml
index b2dba7e0..6cdcf31 100644
--- a/core/res/res/values-sl/strings.xml
+++ b/core/res/res/values-sl/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Zahtevaj PIN pred odpenjanjem"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Pred odpenjanjem vprašaj za vzorec za odklepanje"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Pred odpenjanjem vprašaj za geslo"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija morda ne deluje v načinu razdeljenega zaslona."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podpira načina razdeljenega zaslona."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Namestil skrbnik"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Posodobil skrbnik"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Izbrisal skrbnik"</string>
diff --git a/core/res/res/values-sq-rAL/strings.xml b/core/res/res/values-sq-rAL/strings.xml
index 1846399..e5d8eaa 100644
--- a/core/res/res/values-sq-rAL/strings.xml
+++ b/core/res/res/values-sq-rAL/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Zhgozhdimi kërkon PIN-in"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Kërko model shkyçjeje para heqjes së gozhdimit"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Kërko fjalëkalim para heqjes nga gozhdimi."</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacioni mund të mos funksionojë me ekranin e ndarë."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacioni nuk mbështet ekranin e ndarë."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"U instalua nga administratori yt"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Përditësuar nga administratori"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"U fshi nga administratori yt"</string>
diff --git a/core/res/res/values-sr/strings.xml b/core/res/res/values-sr/strings.xml
index 2112dbb..5ebe971c 100644
--- a/core/res/res/values-sr/strings.xml
+++ b/core/res/res/values-sr/strings.xml
@@ -1478,8 +1478,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Тражи PIN пре откачињања"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Тражи шаблон за откључавање пре откачињања"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Тражи лозинку пре откачињања"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Апликација можда неће функционисати са подељеним екраном."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Апликација не подржава подељени екран."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Инсталирао је ваш администратор"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ажурирао је администратор"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Избрисао је ваш адмиистратор"</string>
diff --git a/core/res/res/values-sv/strings.xml b/core/res/res/values-sv/strings.xml
index 832d4a2..bf64512 100644
--- a/core/res/res/values-sv/strings.xml
+++ b/core/res/res/values-sv/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Be om pinkod innan skärmen slutar fästas"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Be om upplåsningsmönster innan skärmen slutar fästas"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Be om lösenord innan skärmen slutar fästas"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Appen kanske inte fungerar med delad skärm."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Appen har inte stöd för delad skärm."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Paketet har installerats av administratören"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Uppdaterat av administratören"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Paketet har raderats av administratören"</string>
diff --git a/core/res/res/values-sw/strings.xml b/core/res/res/values-sw/strings.xml
index e0a32f6..6c2952a 100644
--- a/core/res/res/values-sw/strings.xml
+++ b/core/res/res/values-sw/strings.xml
@@ -1470,8 +1470,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Omba PIN kabla hujabandua"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Omba mchoro wa kufungua kabla hujabandua"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Omba nenosiri kabla hujabandua"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Huenda programu isifanye kazi kwenye skrini inayogawanywa."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Programu haiwezi kutumia skrini iliyogawanywa."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Kilisakinishwa na msimamizi wako"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Kimesasiswa na msimamizi wako"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Kilifutwa na msimamizi wako"</string>
diff --git a/core/res/res/values-ta-rIN/strings.xml b/core/res/res/values-ta-rIN/strings.xml
index 773301f..e805360 100644
--- a/core/res/res/values-ta-rIN/strings.xml
+++ b/core/res/res/values-ta-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"அகற்றும் முன் PINஐக் கேள்"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"அகற்றும் முன் திறத்தல் வடிவத்தைக் கேள்"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"அகற்றும் முன் கடவுச்சொல்லைக் கேள்"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"திரைப் பிரிப்பில் பயன்பாடு வேலைசெய்யாமல் போகக்கூடும்."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"திரையைப் பிரிப்பதைப் பயன்பாடு ஆதரிக்கவில்லை."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"நிர்வாகி நிறுவினார்"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"உங்கள் நிர்வாகி புதுப்பித்துள்ளார்"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"நிர்வாகி நீக்கிவிட்டார்"</string>
diff --git a/core/res/res/values-te-rIN/strings.xml b/core/res/res/values-te-rIN/strings.xml
index 4809c98..8585c07 100644
--- a/core/res/res/values-te-rIN/strings.xml
+++ b/core/res/res/values-te-rIN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"అన్‌పిన్ చేయడానికి ముందు పిన్‌ కోసం అడుగు"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"అన్‌పిన్ చేయడానికి ముందు అన్‌లాక్ నమూనా కోసం అడుగు"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"అన్‌పిన్ చేయడానికి ముందు పాస్‌వర్డ్ కోసం అడుగు"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"స్క్రీన్ విభజనతో అనువర్తనం పని చేయకపోవచ్చు."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"అనువర్తనంలో స్క్రీన్ విభజనకు మద్దతు లేదు."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"మీ నిర్వాహకులు ఇన్‌స్టాల్ చేసారు"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"మీ నిర్వాహకుడు నవీకరించారు"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"మీ నిర్వాహకులు తొలగించారు"</string>
diff --git a/core/res/res/values-th/strings.xml b/core/res/res/values-th/strings.xml
index 0ea2e52..17a732f 100644
--- a/core/res/res/values-th/strings.xml
+++ b/core/res/res/values-th/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"ขอ PIN ก่อนเลิกตรึง"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"ขอรูปแบบการปลดล็อกก่อนเลิกตรึง"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"ขอรหัสผ่านก่อนเลิกตรึง"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"แอปอาจใช้ไม่ได้กับโหมดแยกหน้าจอ"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"แอปไม่สนับสนุนการแยกหน้าจอ"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"ติดตั้งโดยผู้ดูแลระบบของคุณ"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"อัปเดตโดยผู้ดูแลระบบ"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"ลบโดยผู้ดูแลระบบของคุณ"</string>
diff --git a/core/res/res/values-tl/strings.xml b/core/res/res/values-tl/strings.xml
index 00918a4..7f4393e 100644
--- a/core/res/res/values-tl/strings.xml
+++ b/core/res/res/values-tl/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Humingi ng PIN bago mag-unpin"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Humingi ng pattern sa pag-unlock bago mag-unpin"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Humingi ng password bago mag-unpin"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Maaaring hindi gumana ang app sa split-screen."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Hindi sinusuportahan ng app ang split-screen."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Na-install ng iyong administrator"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Na-update ng iyong administrator"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Na-delete ng iyong administrator"</string>
diff --git a/core/res/res/values-tr/strings.xml b/core/res/res/values-tr/strings.xml
index 4db8264..1dbf7f3 100644
--- a/core/res/res/values-tr/strings.xml
+++ b/core/res/res/values-tr/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Sabitlemeyi kaldırmadan önce PIN\'i sor"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Sabitlemeyi kaldırmadan önce kilit açma desenini sor"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Sabitlemeyi kaldırmadan önce şifre sor"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Uygulama bölünmüş ekranda çalışmayabilir."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Uygulama bölünmüş ekranı desteklemiyor."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Yöneticiniz tarafından yüklendi"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Yöneticiniz tarafından güncellendi"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Yöneticiniz tarafından silindi"</string>
diff --git a/core/res/res/values-uk/strings.xml b/core/res/res/values-uk/strings.xml
index fe7be12..78a2947 100644
--- a/core/res/res/values-uk/strings.xml
+++ b/core/res/res/values-uk/strings.xml
@@ -1488,8 +1488,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"PIN-код для відкріплення"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Запитувати ключ розблокування перед відкріпленням"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Запитувати пароль перед відкріпленням"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Додаток може не працювати в режимі розділеного екрана."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Додаток не підтримує розділення екрана."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Установив адміністратор"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Оновлено адміністратором"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Видалив адміністратор"</string>
diff --git a/core/res/res/values-ur-rPK/strings.xml b/core/res/res/values-ur-rPK/strings.xml
index 5236b7f..f5ffbde 100644
--- a/core/res/res/values-ur-rPK/strings.xml
+++ b/core/res/res/values-ur-rPK/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"‏پن ہٹانے سے پہلے PIN طلب کریں"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"پن ہٹانے سے پہلے غیر مقفل کرنے کا پیٹرن طلب کریں"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"پن ہٹانے سے پہلے پاس ورڈ طلب کریں"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"ممکن ہے کہ ایپ سپلٹ اسکرین کے ساتھ کام نہ کرے۔"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ایپ سپلٹ اسکرین کو سپورٹ نہیں کرتی۔"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"آپ کے منتظم کی جانب سے انسٹال کر دیا گیا"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"آپ کے منتظم نے اپ ڈيٹ کر دیا"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"آپ کے منتظم کی جانب سے حذف کر دیا گیا"</string>
diff --git a/core/res/res/values-uz-rUZ/strings.xml b/core/res/res/values-uz-rUZ/strings.xml
index 6cb65a3..0b6a0cc 100644
--- a/core/res/res/values-uz-rUZ/strings.xml
+++ b/core/res/res/values-uz-rUZ/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Yechishda PIN-kod so‘ralsin"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Bo‘shatishdan oldin chizmali parol so‘ralsin"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Bo‘shatishdan oldin parol so‘ralsin"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Ilova ekranni ikkiga bo‘lish rejimini qo‘llab-quvvatlamaydi."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Bu ilova ekranni bo‘lish xususiyatini qo‘llab-quvvatlamaydi."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Administratoringiz tomonidan o‘rnatilgan"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Administratoringiz tomonidan yangilandi"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Administratoringiz tomonidan o‘chirilgan"</string>
diff --git a/core/res/res/values-vi/strings.xml b/core/res/res/values-vi/strings.xml
index 29eef92..6236153 100644
--- a/core/res/res/values-vi/strings.xml
+++ b/core/res/res/values-vi/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Hỏi mã PIN trước khi bỏ ghim"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Hỏi hình mở khóa trước khi bỏ ghim"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Hỏi mật khẩu trước khi bỏ ghim"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Ứng dụng có thể không hoạt động với tính năng chia đôi màn hình."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Ứng dụng không hỗ trợ chia đôi màn hình."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Được cài đặt bởi quản trị viên của bạn"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Được cập nhật bởi quản trị viên của bạn"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Đã bị xóa bởi quản trị viên của bạn"</string>
diff --git a/core/res/res/values-w170dp-notround-watch/dimens.xml b/core/res/res/values-w170dp-notround-watch/dimens.xml
new file mode 100644
index 0000000..c91cbc1
--- /dev/null
+++ b/core/res/res/values-w170dp-notround-watch/dimens.xml
@@ -0,0 +1,20 @@
+<?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.
+-->
+<resources>
+    <!-- each of these are relative to the display size -->
+    <item name="input_extract_layout_padding_right" type="fraction">7.5%</item>
+</resources>
diff --git a/core/res/res/values-h426dp-port/integers.xml b/core/res/res/values-w320dp-h426dp/integers.xml
similarity index 100%
rename from core/res/res/values-h426dp-port/integers.xml
rename to core/res/res/values-w320dp-h426dp/integers.xml
diff --git a/core/res/res/values-w320dp/dimens.xml b/core/res/res/values-w320dp/dimens.xml
new file mode 100644
index 0000000..ad6d2ec
--- /dev/null
+++ b/core/res/res/values-w320dp/dimens.xml
@@ -0,0 +1,23 @@
+<?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.
+-->
+<resources>
+    <!-- The platform's desired fixed width for a dialog along the major axis
+         (the screen is in landscape). This may be either a fraction or a dimension.-->
+    <item type="dimen" name="dialog_fixed_width_major">320dp</item>
+    <!-- The platform's desired fixed width for a dialog along the minor axis
+         (the screen is in portrait). This may be either a fraction or a dimension.-->
+    <item type="dimen" name="dialog_fixed_width_minor">320dp</item>
+</resources>
diff --git a/core/res/res/values-w426dp-land/integers.xml b/core/res/res/values-w426dp-h320dp/integers.xml
similarity index 100%
rename from core/res/res/values-w426dp-land/integers.xml
rename to core/res/res/values-w426dp-h320dp/integers.xml
diff --git a/core/res/res/values-watch/dimens.xml b/core/res/res/values-watch/dimens.xml
new file mode 100644
index 0000000..f103aa9
--- /dev/null
+++ b/core/res/res/values-watch/dimens.xml
@@ -0,0 +1,27 @@
+<?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.
+-->
+<resources>
+    <!-- each of these are relative to the display size -->
+    <item name="input_extract_layout_height" type="fraction">17.5%</item>
+    <item name="input_extract_layout_padding_left" type="fraction">3.6%</item>
+    <item name="input_extract_layout_padding_left_no_action" type="fraction">@fraction/input_extract_layout_padding_right</item>
+    <item name="input_extract_layout_padding_right" type="fraction">2.5%</item>
+    <item name="input_extract_text_margin_bottom" type="fraction">0%</item>
+    <item name="input_extract_action_margin_bottom" type="fraction">0%</item>
+    <item name="input_extract_action_button_width" type="dimen">24dp</item>
+    <item name="input_extract_action_button_height" type="dimen">24dp</item>
+</resources>
diff --git a/core/res/res/values-watch/themes.xml b/core/res/res/values-watch/themes.xml
index 756a94b..6d6065f 100644
--- a/core/res/res/values-watch/themes.xml
+++ b/core/res/res/values-watch/themes.xml
@@ -18,6 +18,7 @@
     <style name="Theme.Dialog.AppError" parent="Theme.Micro.Dialog.AppError" />
     <style name="Theme.Holo.Dialog.Alert" parent="Theme.Micro.Dialog.Alert" />
     <style name="Theme.Holo.Light.Dialog.Alert" parent="Theme.Micro.Dialog.Alert" />
+    <style name="Theme.InputMethod" parent="Theme.Micro.InputMethod" />
     <style name="Theme.Material.Dialog.Alert" parent="Theme.Micro.Dialog.Alert" />
     <style name="Theme.Material.Light.Dialog.Alert" parent="Theme.Micro.Dialog.Alert" />
 </resources>
diff --git a/core/res/res/values-watch/themes_device_defaults.xml b/core/res/res/values-watch/themes_device_defaults.xml
index 61753b1..66509fb 100644
--- a/core/res/res/values-watch/themes_device_defaults.xml
+++ b/core/res/res/values-watch/themes_device_defaults.xml
@@ -19,14 +19,16 @@
     <style name="Theme.DeviceDefault.Dialog" parent="Theme.Micro.Dialog" />
     <style name="Theme.DeviceDefault.DialogWhenLarge" parent="Theme.Micro.Dialog" />
     <style name="Theme.DeviceDefault.Dialog.Alert" parent="Theme.Micro.Dialog.Alert" />
+    <style name="Theme.DeviceDefault.InputMethod" parent="Theme.Micro.InputMethod"  />
+    <style name="Theme.DeviceDefault.Panel" parent="Theme.Micro.Panel"  />
     <style name="Theme.DeviceDefault.Light" parent="Theme.Micro.Light" />
     <style name="Theme.DeviceDefault.Light.NoActionBar" parent="Theme.Micro.Light" />
     <style name="Theme.DeviceDefault.Light.DarkActionBar" parent="Theme.Micro.Light" />
     <style name="Theme.DeviceDefault.Light.Dialog" parent="Theme.Micro.Dialog" />
     <style name="Theme.DeviceDefault.Light.DialogWhenLarge" parent="Theme.Micro.Dialog" />
     <style name="Theme.DeviceDefault.Light.Dialog.Alert" parent="Theme.Micro.Dialog.Alert" />
+    <style name="Theme.DeviceDefault.Light.Panel" parent="Theme.Micro.Light.Panel"  />
     <style name="Theme.DeviceDefault.Settings" parent="Theme.Micro" />
     <style name="Theme.DeviceDefault.Wallpaper" parent="Theme.Micro" />
-
 </resources>
 
diff --git a/core/res/res/values-zh-rCN/strings.xml b/core/res/res/values-zh-rCN/strings.xml
index 3b26e46..708f1be 100644
--- a/core/res/res/values-zh-rCN/strings.xml
+++ b/core/res/res/values-zh-rCN/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"取消时要求输入PIN码"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"取消时要求绘制解锁图案"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"取消时要求输入密码"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"应用可能无法在分屏模式下正常运行。"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"应用不支持分屏。"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"已由管理员安装"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"由您单位的管理员更新"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"已被管理员删除"</string>
diff --git a/core/res/res/values-zh-rHK/strings.xml b/core/res/res/values-zh-rHK/strings.xml
index 28f2bac..95b7244 100644
--- a/core/res/res/values-zh-rHK/strings.xml
+++ b/core/res/res/values-zh-rHK/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"取消固定時必須輸入 PIN"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"取消固定時必須畫出解鎖圖案"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"取消固定時必須輸入密碼"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"應用程式可能無法在分割畫面中運作。"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"應用程式不支援分割畫面。"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"已由管理員安裝"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"已由您的管理員更新"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"已由管理員刪除"</string>
diff --git a/core/res/res/values-zh-rTW/strings.xml b/core/res/res/values-zh-rTW/strings.xml
index dfc7890..7c980bd 100644
--- a/core/res/res/values-zh-rTW/strings.xml
+++ b/core/res/res/values-zh-rTW/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"取消固定時必須輸入 PIN"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"取消固定時必須畫出解鎖圖案"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"取消固定時必須輸入密碼"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"應用程式可能無法在分割畫面中運作。"</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"這個應用程式不支援分割畫面。"</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"已由管理員安裝"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"由您的管理員更新"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"已遭管理員刪除"</string>
diff --git a/core/res/res/values-zu/strings.xml b/core/res/res/values-zu/strings.xml
index e32f26b..d64e79c 100644
--- a/core/res/res/values-zu/strings.xml
+++ b/core/res/res/values-zu/strings.xml
@@ -1468,8 +1468,6 @@
     <string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Cela iphinikhodi ngaphambi kokuphina"</string>
     <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Cela iphethini yokuvula ngaphambi kokususa ukuphina"</string>
     <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Cela iphasiwedi ngaphambi kokususa ukuphina"</string>
-    <string name="dock_forced_resizable" msgid="5914261505436217520">"Izinhlelo zokusebenza kungenzeka zingasebenzi ngesikrini esihlukanisiwe."</string>
-    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Uhlelo lokusebenza alusekeli isikrini esihlukanisiwe."</string>
     <string name="package_installed_device_owner" msgid="8420696545959087545">"Ifakwe ngumlawuli wakho"</string>
     <string name="package_updated_device_owner" msgid="8856631322440187071">"Ibuyekezwe ngumqondisi wakho"</string>
     <string name="package_deleted_device_owner" msgid="7650577387493101353">"Isuswe ngumlawuli wakho"</string>
diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml
index 0ed1f13..a320ef6 100644
--- a/core/res/res/values/attrs.xml
+++ b/core/res/res/values/attrs.xml
@@ -8129,6 +8129,11 @@
         <attr name="maxCollapsedHeightSmall" format="dimension" />
     </declare-styleable>
 
+    <declare-styleable name="MessagingLinearLayout">
+        <attr name="maxHeight" />
+        <attr name="spacing" />
+    </declare-styleable>
+
     <declare-styleable name="ResolverDrawerLayout_LayoutParams">
         <attr name="layout_alwaysShow" format="boolean" />
         <attr name="layout_ignoreOffset" format="boolean" />
diff --git a/core/res/res/values/colors_material.xml b/core/res/res/values/colors_material.xml
index 7399fa9..c8ca116 100644
--- a/core/res/res/values/colors_material.xml
+++ b/core/res/res/values/colors_material.xml
@@ -75,7 +75,9 @@
     <color name="material_grey_100">#fff5f5f5</color>
     <color name="material_grey_50">#fffafafa</color>
 
+    <color name="material_deep_teal_100">#ffb2dfdb</color>
     <color name="material_deep_teal_200">#ff80cbc4</color>
+    <color name="material_deep_teal_300">#ff4db6ac</color>
     <color name="material_deep_teal_500">#ff009688</color>
 
     <color name="material_blue_grey_800">#ff37474f</color>
diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml
index b4371c1..aada05d 100644
--- a/core/res/res/values/config.xml
+++ b/core/res/res/values/config.xml
@@ -265,19 +265,6 @@
         <item>"0,1"</item>
     </string-array>
 
-    <!-- Set of NetworkInfo.getType() that reflect data usage. -->
-    <integer-array translatable="false" name="config_data_usage_network_types">
-        <item>0</item> <!-- TYPE_MOBILE -->
-        <item>2</item> <!-- TYPE_MOBILE_MMS -->
-        <item>3</item> <!-- TYPE_MOBILE_SUPL -->
-        <item>4</item> <!-- TYPE_MOBILE_DUN -->
-        <item>5</item> <!-- TYPE_MOBILE_HIPRI -->
-        <item>10</item> <!-- TYPE_MOBILE_FOTA -->
-        <item>11</item> <!-- TYPE_MOBILE_IMS -->
-        <item>12</item> <!-- TYPE_MOBILE_CBS -->
-        <item>14</item> <!-- TYPE_MOBILE_IA -->
-    </integer-array>
-
     <!-- The maximum duration (in milliseconds) we expect a network transition to take -->
     <integer name="config_networkTransitionTimeout">60000</integer>
 
@@ -433,9 +420,6 @@
     <!-- Boolean indicating we re-try re-associating once upon disconnection and RSSI is high failure  -->
     <bool translatable="true" name="config_wifi_enable_disconnection_debounce">true</bool>
 
-    <!-- Boolean indicating autojoin will prefer 5GHz and choose 5GHz BSSIDs -->
-    <bool translatable="true" name="config_wifi_enable_5GHz_preference">true</bool>
-
     <!-- Boolean indicating whether or not to revert to default country code when cellular
          radio is unable to find any MCC information to infer wifi country code from -->
     <bool translatable="false" name="config_wifi_revert_country_code_on_cellular_loss">false</bool>
@@ -452,8 +436,6 @@
     <!-- Integer specifying the basic autojoin parameters -->
     <integer translatable="false" name="config_wifi_framework_5GHz_preference_boost_threshold">-65</integer>
     <integer translatable="false" name="config_wifi_framework_5GHz_preference_boost_factor">40</integer>
-    <integer translatable="false" name="config_wifi_framework_current_association_hysteresis_high">16</integer>
-    <integer translatable="false" name="config_wifi_framework_current_association_hysteresis_low">10</integer>
     <integer translatable="false" name="config_wifi_framework_5GHz_preference_penalty_threshold">-75</integer>
     <integer translatable="false" name="config_wifi_framework_RSSI_SCORE_OFFSET">85</integer>
     <integer translatable="false" name="config_wifi_framework_RSSI_SCORE_SLOPE">4</integer>
@@ -508,15 +490,9 @@
     <!-- Integer indicating disconnect mode short scan interval in milliseconds -->
     <integer translatable="false" name="config_wifi_disconnected_short_scan_interval">15000</integer>
 
-    <!-- Integer indicating disconnect mode long scan interval in milliseconds -->
-    <integer translatable="false" name="config_wifi_disconnected_long_scan_interval">120000</integer>
-
     <!-- Integer indicating associated partial scan short interval in milliseconds -->
     <integer translatable="false" name="config_wifi_associated_short_scan_interval">20000</integer>
 
-    <!-- Integer indicating associated partial scan long interval in milliseconds -->
-    <integer translatable="false" name="config_wifi_associated_long_scan_interval">180000</integer>
-
     <!-- Integer indicating associated full scan backoff, representing a fraction: xx/8 -->
     <integer translatable="false" name="config_wifi_framework_associated_full_scan_backoff">12</integer>
 
@@ -529,18 +505,6 @@
     <!-- Integer indicating associated full scan max num active channels -->
     <integer translatable="false" name="config_wifi_framework_associated_partial_scan_max_num_active_channels">6</integer>
 
-    <!-- Integer indicating associated full scan max num passive channels -->
-    <integer translatable="false" name="config_wifi_framework_associated_partial_scan_max_num_passive_channels">3</integer>
-
-    <!-- Integer indicating number of association errors leading to blacklisting of the network -->
-    <integer translatable="false" name="config_wifi_framework_max_connection_errors_to_blacklist">4</integer>
-
-    <!-- Integer indicating number of authentication errors leading to blacklisting of the network -->
-    <integer translatable="false" name="config_wifi_framework_max_auth_errors_to_blacklist">4</integer>
-
-    <!-- Integer indicating minimum blacklisting delay of a wofo configuration due to connectin or auth errors -->
-    <integer translatable="false" name="config_wifi_framework_network_black_list_min_time_milli">120000</integer>
-
     <!-- Integer indicating RSSI boost given to current network -->
     <integer translatable="false" name="config_wifi_framework_current_network_boost">16</integer>
 
@@ -556,12 +520,6 @@
     <!-- Wifi driver supports batched scan -->
     <bool translatable="false" name="config_wifi_batched_scan_supported">false</bool>
 
-    <!-- Wifi HAL supported PNO -->
-    <bool translatable="false" name="config_wifi_hal_pno_enable">false</bool>
-
-    <!-- Wifi SSID white list (can't be enabled if config_wifi_hal_pno_enable is not) -->
-    <bool translatable="false" name="config_wifi_ssid_white_list_enable">true</bool>
-
     <!-- Idle Receive current for wifi radio. 0 by default-->
     <integer translatable="false" name="config_wifi_idle_receive_cur_ma">0</integer>
 
@@ -2434,10 +2392,6 @@
          disables NetworkPolicyManagerService's presentation of data-usage notifications. -->
     <string translatable="false" name="config_networkPolicyNotificationComponent"></string>
 
-    <!-- The fraction of display size (lower of height and width) that will be used to determine
-         the default minimal size for resizeable tasks. -->
-    <fraction name="config_displayFractionForDefaultMinimalSizeOfResizeableTask">25%</fraction>
-
     <!-- The BT name of the keyboard packaged with the device. If this is defined, SystemUI will
          automatically try to pair with it when the device exits tablet mode. -->
     <string translatable="false" name="config_packagedKeyboardName"></string>
diff --git a/core/res/res/values/dimens.xml b/core/res/res/values/dimens.xml
index a21f276..9178305 100644
--- a/core/res/res/values/dimens.xml
+++ b/core/res/res/values/dimens.xml
@@ -112,10 +112,10 @@
 
     <!-- The platform's desired fixed width for a dialog along the major axis
          (the screen is in landscape). This may be either a fraction or a dimension.-->
-    <item type="dimen" name="dialog_fixed_width_major">320dp</item>
+    <item type="dimen" name="dialog_fixed_width_major">100%</item>
     <!-- The platform's desired fixed width for a dialog along the minor axis
          (the screen is in portrait). This may be either a fraction or a dimension.-->
-    <item type="dimen" name="dialog_fixed_width_minor">320dp</item>
+    <item type="dimen" name="dialog_fixed_width_minor">100%</item>
     <!-- The platform's desired fixed height for a dialog along the major axis
          (the screen is in portrait). This may be either a fraction or a dimension.-->
     <item type="dimen" name="dialog_fixed_height_major">80%</item>
@@ -162,9 +162,9 @@
     <dimen name="notification_min_height">92dp</dimen>
 
     <!-- The width of the big icons in notifications. -->
-    <dimen name="notification_large_icon_width">64dp</dimen>
+    <dimen name="notification_large_icon_width">40dp</dimen>
     <!-- The width of the big icons in notifications. -->
-    <dimen name="notification_large_icon_height">64dp</dimen>
+    <dimen name="notification_large_icon_height">40dp</dimen>
 
     <!-- The minimum width of the app name in the header if it shrinks -->
     <dimen name="notification_header_shrink_min_width">72dp</dimen>
@@ -181,6 +181,9 @@
     <!-- The margin of the content to an image-->
     <dimen name="notification_content_image_margin_end">8dp</dimen>
 
+    <!-- The spacing between messages in Notification.MessagingStyle -->
+    <dimen name="notification_messaging_spacing">6dp</dimen>
+
     <!-- Preferred width of the search view. -->
     <dimen name="search_view_preferred_width">320dip</dimen>
 
@@ -455,4 +458,7 @@
     <item type="fraction" name="docked_stack_divider_fixed_ratio">34.15%</item>
 
     <dimen name="resize_shadow_size">5dp</dimen>
+
+    <!-- The default minimal size of a resizable task, in both dimensions. -->
+    <dimen name="default_minimal_size_resizable_task">220dp</dimen>
 </resources>
diff --git a/core/res/res/values/strings.xml b/core/res/res/values/strings.xml
index b4f95dc..96731cf 100644
--- a/core/res/res/values/strings.xml
+++ b/core/res/res/values/strings.xml
@@ -4018,12 +4018,6 @@
     <!-- Lock-to-app unlock password string -->
     <string name="lock_to_app_unlock_password">Ask for password before unpinning</string>
 
-    <!-- Multi-Window strings -->
-    <!-- Warning message when an app that got forced to be resizable gets shown in split-screen -->
-    <string name="dock_forced_resizable">App may not work with split-screen.</string>
-    <!-- Warning message when we try to dock a non-resizeble tasks and launch it in fullscreen instead. -->
-    <string name="dock_non_resizeble_failed_to_dock_text">App does not support split-screen.</string>
-
     <!-- Notification shown when device owner silently installs a package [CHAR LIMIT=NONE] -->
     <string name="package_installed_device_owner">Installed by your administrator</string>
     <!-- Notification shown when device owner silently updates a package [CHAR LIMIT=NONE] -->
diff --git a/core/res/res/values/styles_material.xml b/core/res/res/values/styles_material.xml
index 2420c1a..8a33406 100644
--- a/core/res/res/values/styles_material.xml
+++ b/core/res/res/values/styles_material.xml
@@ -456,6 +456,14 @@
 
     <style name="Widget.Material.Notification.ProgressBar" parent="Widget.Material.Light.ProgressBar.Horizontal" />
 
+    <style name="Widget.Material.Notification.MessagingText" parent="Widget.Material.Light.TextView">
+        <item name="layout_width">match_parent</item>
+        <item name="layout_height">wrap_content</item>
+        <item name="ellipsize">end</item>
+        <item name="visibility">gone</item>
+        <item name="textAppearance">@style/TextAppearance.Material.Notification</item>
+    </style>
+
     <!-- Widget Styles -->
 
     <style name="Material"/>
diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml
index 2215bd4..03d2192 100644
--- a/core/res/res/values/symbols.xml
+++ b/core/res/res/values/symbols.xml
@@ -295,7 +295,6 @@
   <java-symbol type="bool" name="config_wifi_framework_enable_associated_network_selection" />
   <java-symbol type="bool" name="config_wifi_only_link_same_credential_configurations" />
   <java-symbol type="bool" name="config_wifi_enable_disconnection_debounce" />
-  <java-symbol type="bool" name="config_wifi_enable_5GHz_preference" />
   <java-symbol type="bool" name="config_wifi_revert_country_code_on_cellular_loss" />
   <java-symbol type="bool" name="config_wifi_enable_wifi_firmware_debugging" />
   <java-symbol type="integer" name="config_wifi_logger_ring_buffer_size_limit_kb" />
@@ -312,8 +311,6 @@
   <java-symbol type="integer" name="config_wifi_framework_5GHz_preference_boost_threshold" />
   <java-symbol type="integer" name="config_wifi_framework_5GHz_preference_boost_factor" />
   <java-symbol type="integer" name="config_wifi_framework_5GHz_preference_penalty_threshold" />
-  <java-symbol type="integer" name="config_wifi_framework_current_association_hysteresis_high" />
-  <java-symbol type="integer" name="config_wifi_framework_current_association_hysteresis_low" />
   <java-symbol type="integer" name="config_wifi_framework_5GHz_preference_penalty_threshold" />
   <java-symbol type="integer" name="config_wifi_framework_RSSI_SCORE_OFFSET" />
   <java-symbol type="integer" name="config_wifi_framework_RSSI_SCORE_SLOPE" />
@@ -322,14 +319,11 @@
   <java-symbol type="integer" name="config_wifi_framework_PASSPOINT_SECURITY_AWARD" />
   <java-symbol type="integer" name="config_wifi_framework_SECURITY_AWARD" />
   <java-symbol type="integer" name="config_wifi_disconnected_short_scan_interval" />
-  <java-symbol type="integer" name="config_wifi_disconnected_long_scan_interval" />
   <java-symbol type="integer" name="config_wifi_associated_short_scan_interval" />
-  <java-symbol type="integer" name="config_wifi_associated_long_scan_interval" />
   <java-symbol type="integer" name="config_wifi_framework_associated_full_scan_backoff" />
   <java-symbol type="integer" name="config_wifi_framework_associated_full_scan_max_interval" />
   <java-symbol type="integer" name="config_wifi_framework_associated_full_scan_max_total_dwell_time" />
   <java-symbol type="integer" name="config_wifi_framework_associated_partial_scan_max_num_active_channels" />
-  <java-symbol type="integer" name="config_wifi_framework_associated_partial_scan_max_num_passive_channels" />
   <java-symbol type="integer" name="config_wifi_framework_wifi_score_bad_rssi_threshold_24GHz" />
   <java-symbol type="integer" name="config_wifi_framework_wifi_score_low_rssi_threshold_24GHz" />
   <java-symbol type="integer" name="config_wifi_framework_wifi_score_good_rssi_threshold_24GHz" />
@@ -359,9 +353,6 @@
   <java-symbol type="integer" name="config_wifi_framework_associated_partial_scan_rx_packet_threshold" />
   <java-symbol type="integer" name="config_wifi_framework_network_switch_tx_packet_threshold" />
   <java-symbol type="integer" name="config_wifi_framework_network_switch_rx_packet_threshold" />
-  <java-symbol type="integer" name="config_wifi_framework_max_connection_errors_to_blacklist" />
-  <java-symbol type="integer" name="config_wifi_framework_max_auth_errors_to_blacklist" />
-  <java-symbol type="integer" name="config_wifi_framework_network_black_list_min_time_milli" />
   <java-symbol type="integer" name="config_wifi_framework_current_network_boost" />
   <java-symbol type="integer" name="config_bluetooth_max_advertisers" />
   <java-symbol type="integer" name="config_bluetooth_max_scan_filters" />
@@ -399,9 +390,7 @@
   <java-symbol type="integer" name="config_wifi_supplicant_scan_interval" />
   <java-symbol type="integer" name="config_wifi_no_network_periodic_scan_interval" />
   <java-symbol type="integer" name="config_wifi_scan_interval_p2p_connected" />
-  <java-symbol type="bool" name="config_wifi_hal_pno_enable" />
   <java-symbol type="integer" name="config_windowOutsetBottom" />
-  <java-symbol type="bool" name="config_wifi_ssid_white_list_enable" />
   <java-symbol type="integer" name="db_connection_pool_size" />
   <java-symbol type="integer" name="db_journal_size_limit" />
   <java-symbol type="integer" name="db_wal_autocheckpoint" />
@@ -613,8 +602,6 @@
   <java-symbol type="string" name="display_manager_overlay_display_name" />
   <java-symbol type="string" name="display_manager_overlay_display_secure_suffix" />
   <java-symbol type="string" name="display_manager_overlay_display_title" />
-  <java-symbol type="string" name="dock_forced_resizable" />
-  <java-symbol type="string" name="dock_non_resizeble_failed_to_dock_text" />
   <java-symbol type="string" name="double_tap_toast" />
   <java-symbol type="string" name="durationDays" />
   <java-symbol type="string" name="durationDayHours" />
@@ -1130,7 +1117,6 @@
   <java-symbol type="plurals" name="pinpuk_attempts" />
 
   <java-symbol type="array" name="carrier_properties" />
-  <java-symbol type="array" name="config_data_usage_network_types" />
   <java-symbol type="array" name="config_sms_enabled_locking_shift_tables" />
   <java-symbol type="array" name="config_sms_enabled_single_shift_tables" />
   <java-symbol type="array" name="config_twoDigitNumberPattern" />
@@ -1267,6 +1253,7 @@
   <java-symbol type="drawable" name="ic_corp_badge" />
   <java-symbol type="drawable" name="ic_corp_badge_off" />
   <java-symbol type="drawable" name="ic_corp_icon_badge" />
+  <java-symbol type="drawable" name="ic_corp_user_badge" />
   <java-symbol type="drawable" name="ic_corp_badge_no_background" />
   <java-symbol type="drawable" name="ic_corp_icon" />
   <java-symbol type="drawable" name="ic_corp_statusbar_icon" />
@@ -1728,7 +1715,7 @@
   <java-symbol type="id" name="replace_app_icon" />
   <java-symbol type="id" name="replace_message" />
   <java-symbol type="fraction" name="config_dimBehindFadeDuration" />
-  <java-symbol type="fraction" name="config_displayFractionForDefaultMinimalSizeOfResizeableTask" />
+  <java-symbol type="dimen" name="default_minimal_size_resizable_task" />
   <java-symbol type="fraction" name="config_screenAutoBrightnessDozeScaleFactor" />
   <java-symbol type="fraction" name="config_autoBrightnessAdjustmentMaxGamma" />
   <java-symbol type="integer" name="config_autoBrightnessAmbientLightHorizon"/>
@@ -2507,6 +2494,8 @@
   <java-symbol type="bool" name="config_strongAuthRequiredOnBoot" />
 
   <java-symbol type="layout" name="app_anr_dialog" />
+  <java-symbol type="layout" name="notification_template_material_messaging" />
+
   <java-symbol type="id" name="aerr_wait" />
 
   <java-symbol type="id" name="notification_content_container" />
@@ -2536,11 +2525,34 @@
   <java-symbol type="string" name="carrier_app_notification_text" />
   <java-symbol type="string" name="negative_duration" />
 
+  <java-symbol type="dimen" name="notification_messaging_spacing" />
+
   <!-- WallpaperManager config -->
   <java-symbol type="string" name="config_wallpaperCropperPackage" />
 
   <java-symbol type="id" name="textSpacerNoTitle" />
   <java-symbol type="id" name="titleDividerNoCustom" />
 
+  <java-symbol type="id" name="notification_messaging" />
+
   <java-symbol type="bool" name="config_sustainedPerformanceModeSupported" />
+
+  <!-- Wearable input extract edit view -->
+  <java-symbol type="drawable" name="ic_input_extract_action_go" />
+  <java-symbol type="drawable" name="ic_input_extract_action_search" />
+  <java-symbol type="drawable" name="ic_input_extract_action_send" />
+  <java-symbol type="drawable" name="ic_input_extract_action_next" />
+  <java-symbol type="drawable" name="ic_input_extract_action_done" />
+  <java-symbol type="drawable" name="ic_input_extract_action_previous" />
+  <java-symbol type="drawable" name="ic_input_extract_action_return" />
+
+  <java-symbol type="fraction" name="input_extract_layout_height" />
+  <java-symbol type="fraction" name="input_extract_layout_padding_left" />
+  <java-symbol type="fraction" name="input_extract_layout_padding_left_no_action" />
+  <java-symbol type="fraction" name="input_extract_layout_padding_right" />
+  <java-symbol type="fraction" name="input_extract_text_margin_bottom" />
+  <java-symbol type="fraction" name="input_extract_action_margin_bottom" />
+
+  <java-symbol type="dimen" name="input_extract_action_button_width" />
+  <java-symbol type="dimen" name="input_extract_action_button_height" />
 </resources>
diff --git a/core/res/res/values/themes_material.xml b/core/res/res/values/themes_material.xml
index 6611eb1..2ea5c5e 100644
--- a/core/res/res/values/themes_material.xml
+++ b/core/res/res/values/themes_material.xml
@@ -890,6 +890,11 @@
         <item name="listDivider">@null</item>
 
         <item name="preferencePanelStyle">@style/PreferencePanel.Dialog</item>
+
+        <item name="windowFixedWidthMajor">@null</item>
+        <item name="windowFixedWidthMinor">@null</item>
+        <item name="windowFixedHeightMajor">@null</item>
+        <item name="windowFixedHeightMinor">@null</item>
     </style>
 
     <!-- Theme overlay that overrides window properties to display as a date picker dialog. -->
diff --git a/core/res/res/values/themes_micro.xml b/core/res/res/values/themes_micro.xml
index 478d66c..25a6e00 100644
--- a/core/res/res/values/themes_micro.xml
+++ b/core/res/res/values/themes_micro.xml
@@ -83,4 +83,18 @@
         <item name="fontFamily">sans-serif-condensed-light</item>
         <item name="textColor">@color/micro_text_light</item>
     </style>
+
+   <style name="Theme.Micro.Panel" parent="Theme.Material.Panel"  />
+   <style name="Theme.Micro.Light.Panel" parent="Theme.Material.Light.Panel"  />
+
+    <!-- Default theme for material style input methods, which is used by the
+         {@link android.inputmethodservice.InputMethodService} class.
+         This inherits from Theme.Panel, but sets up IME appropriate animations
+         and a few custom attributes. -->
+    <style name="Theme.Micro.InputMethod" parent="Theme.Micro.Panel">
+        <item name="windowAnimationStyle">@style/Animation.InputMethod</item>
+        <item name="imeFullscreenBackground">#1e282c</item>
+        <item name="imeExtractEnterAnimation">@anim/input_method_extract_enter</item>
+        <item name="imeExtractExitAnimation">@anim/input_method_extract_exit</item>
+    </style>
 </resources>
diff --git a/core/tests/coretests/src/android/util/PatternsTest.java b/core/tests/coretests/src/android/util/PatternsTest.java
index 348f8fd..edb3082 100644
--- a/core/tests/coretests/src/android/util/PatternsTest.java
+++ b/core/tests/coretests/src/android/util/PatternsTest.java
@@ -419,6 +419,36 @@
                 Patterns.AUTOLINK_WEB_URL.matcher(url).matches());
     }
 
+    @SmallTest
+    public void testAutoLinkWebUrl_doesNotMatchUnicodeSpaces() throws Exception {
+        String part1 = "http://and";
+        String part2 = "roid";
+        String[] emptySpaces = new String[]{
+                "\u00A0", // no-break space
+                "\u2000", // en quad
+                "\u2001", // em quad
+                "\u2002", // en space
+                "\u2003", // em space
+                "\u2004", // three-per-em space
+                "\u2005", // four-per-em space
+                "\u2006", // six-per-em space
+                "\u2007", // figure space
+                "\u2008", // punctuation space
+                "\u2009", // thin space
+                "\u200A", // hair space
+                "\u2028", // line separator
+                "\u2029", // paragraph separator
+                "\u202F", // narrow no-break space
+                "\u3000" // ideographic space
+        };
+
+        for (String emptySpace : emptySpaces) {
+            String url = part1 + emptySpace + part2;
+            assertFalse("Should not match empty space - code:" + emptySpace.codePointAt(0),
+                    Patterns.AUTOLINK_WEB_URL.matcher(url).matches());
+        }
+    }
+
     // Tests for Patterns.IP_ADDRESS
 
     @SmallTest
diff --git a/core/tests/coretests/src/com/android/internal/app/procstats/SparseMappingTableTest.java b/core/tests/coretests/src/com/android/internal/app/procstats/SparseMappingTableTest.java
new file mode 100644
index 0000000..fd57baa
--- /dev/null
+++ b/core/tests/coretests/src/com/android/internal/app/procstats/SparseMappingTableTest.java
@@ -0,0 +1,209 @@
+/*
+ * 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 com.android.internal.app.procstats;
+
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.util.ArrayList;
+
+import android.os.BatteryStats;
+import android.os.Parcel;
+import android.test.suitebuilder.annotation.SmallTest;
+import android.util.Log;
+
+import junit.framework.Assert;
+import junit.framework.TestCase;
+
+import org.mockito.Mockito;
+
+/**
+ * Provides test cases for SparseMappingTable.
+ */
+public class SparseMappingTableTest extends TestCase {
+    private static final String TAG = "SparseMappingTableTest";
+
+    final byte ID1 = 1;
+    final byte ID2 = 2;
+
+    final long VALUE1 = 100;
+    final long VALUE2 = 10000000000L;
+
+    /**
+     * Test the parceling and unparceling logic when there is no data.
+     */
+    @SmallTest
+    public void testParcelingEmpty() throws Exception  {
+        final SparseMappingTable data = new SparseMappingTable();
+        final SparseMappingTable.Table table = new SparseMappingTable.Table(data);
+
+        final Parcel dataParcel = Parcel.obtain();
+        data.writeToParcel(dataParcel);
+
+        final Parcel tableParcel = Parcel.obtain();
+        table.writeToParcel(tableParcel);
+
+        dataParcel.setDataPosition(0);
+        final SparseMappingTable data1 = new SparseMappingTable();
+        data1.readFromParcel(dataParcel);
+        Assert.assertEquals(0, dataParcel.dataAvail());
+        dataParcel.recycle();
+
+        tableParcel.setDataPosition(0);
+        final SparseMappingTable.Table table1 = new SparseMappingTable.Table(data1);
+        table1.readFromParcel(tableParcel);
+        Assert.assertEquals(0, tableParcel.dataAvail());
+        tableParcel.recycle();
+    }
+
+    /**
+     * Test the parceling and unparceling logic.
+     */
+    @SmallTest
+    public void testParceling() throws Exception  {
+        int key;
+        final SparseMappingTable data = new SparseMappingTable();
+        final SparseMappingTable.Table table = new SparseMappingTable.Table(data);
+
+        key = table.getOrAddKey(ID1, 1);
+        table.setValue(key, VALUE1);
+
+        key = table.getOrAddKey(ID2, 1);
+        table.setValue(key, VALUE2);
+
+        final Parcel dataParcel = Parcel.obtain();
+        data.writeToParcel(dataParcel);
+
+        final Parcel tableParcel = Parcel.obtain();
+        table.writeToParcel(tableParcel);
+
+        dataParcel.setDataPosition(0);
+        final SparseMappingTable data1 = new SparseMappingTable();
+        data1.readFromParcel(dataParcel);
+        Assert.assertEquals(0, dataParcel.dataAvail());
+        dataParcel.recycle();
+
+        tableParcel.setDataPosition(0);
+        final SparseMappingTable.Table table1 = new SparseMappingTable.Table(data1);
+        table1.readFromParcel(tableParcel);
+        Assert.assertEquals(0, tableParcel.dataAvail());
+        tableParcel.recycle();
+
+        key = table1.getKey(ID1);
+        Assert.assertEquals(VALUE1, table1.getValue(key));
+
+        key = table1.getKey(ID2);
+        Assert.assertEquals(VALUE2, table1.getValue(key));
+    }
+
+
+    /**
+     * Test that after resetting you can still read data, you just get no values.
+     */
+    @SmallTest
+    public void testParcelingWithReset() throws Exception  {
+        int key;
+        final SparseMappingTable data = new SparseMappingTable();
+        final SparseMappingTable.Table table = new SparseMappingTable.Table(data);
+
+        key = table.getOrAddKey(ID1, 1);
+        table.setValue(key, VALUE1);
+
+        data.reset();
+        table.resetTable();
+
+        key = table.getOrAddKey(ID2, 1);
+        table.setValue(key, VALUE2);
+
+        Log.d(TAG, "before: " + data.dumpInternalState(true));
+        Log.d(TAG, "before: " + table.dumpInternalState());
+
+        final Parcel dataParcel = Parcel.obtain();
+        data.writeToParcel(dataParcel);
+
+        final Parcel tableParcel = Parcel.obtain();
+        table.writeToParcel(tableParcel);
+
+        dataParcel.setDataPosition(0);
+        final SparseMappingTable data1 = new SparseMappingTable();
+        data1.readFromParcel(dataParcel);
+        Assert.assertEquals(0, dataParcel.dataAvail());
+        dataParcel.recycle();
+
+        tableParcel.setDataPosition(0);
+        final SparseMappingTable.Table table1 = new SparseMappingTable.Table(data1);
+        table1.readFromParcel(tableParcel);
+        Assert.assertEquals(0, tableParcel.dataAvail());
+        tableParcel.recycle();
+
+        key = table1.getKey(ID1);
+        Assert.assertEquals(SparseMappingTable.INVALID_KEY, key);
+
+        key = table1.getKey(ID2);
+        Assert.assertEquals(VALUE2, table1.getValue(key));
+
+        Log.d(TAG, " after: " + data1.dumpInternalState(true));
+        Log.d(TAG, " after: " + table1.dumpInternalState());
+    }
+
+    /**
+     * Test that it fails if you reset the data and not the table.
+     *
+     * Resetting the table and not the data is basically okay. The data in the
+     * SparseMappingTable will be leaked.
+     */
+    @SmallTest
+    public void testResetDataOnlyFails() throws Exception {
+        int key;
+        final SparseMappingTable data = new SparseMappingTable();
+        final SparseMappingTable.Table table = new SparseMappingTable.Table(data);
+
+        key = table.getOrAddKey(ID1, 1);
+        table.setValue(key, VALUE1);
+
+        Assert.assertEquals(VALUE1, table.getValue(key));
+
+        data.reset();
+
+        try {
+            table.getValue(key);
+            throw new Exception("Exception not thrown after mismatched reset calls.");
+        } catch (RuntimeException ex) {
+            // Good
+        }
+    }
+
+    /**
+     * Test that trying to get data that you didn't add fails correctly.
+     */
+    @SmallTest
+    public void testInvalidKey() throws Exception {
+        int key;
+        final SparseMappingTable data = new SparseMappingTable();
+        final SparseMappingTable.Table table = new SparseMappingTable.Table(data);
+
+        key = table.getKey(ID1);
+
+        // The key should be INVALID_KEY
+        Assert.assertEquals(SparseMappingTable.INVALID_KEY, key);
+
+        // If you get the value with getValueForId you get 0.
+        Assert.assertEquals(0, table.getValueForId(ID1));
+    }
+}
+
+
+
diff --git a/core/tests/coretests/src/com/android/internal/inputmethod/InputMethodSubtypeSwitchingControllerTest.java b/core/tests/coretests/src/com/android/internal/inputmethod/InputMethodSubtypeSwitchingControllerTest.java
index ec5220f..ba5206a 100644
--- a/core/tests/coretests/src/com/android/internal/inputmethod/InputMethodSubtypeSwitchingControllerTest.java
+++ b/core/tests/coretests/src/com/android/internal/inputmethod/InputMethodSubtypeSwitchingControllerTest.java
@@ -27,7 +27,6 @@
 
 import com.android.internal.inputmethod.InputMethodSubtypeSwitchingController.ControllerImpl;
 import com.android.internal.inputmethod.InputMethodSubtypeSwitchingController.ImeSubtypeListItem;
-import com.android.internal.inputmethod.InputMethodUtils;
 
 import java.util.ArrayList;
 import java.util.Arrays;
@@ -68,7 +67,7 @@
         ri.serviceInfo = si;
         List<InputMethodSubtype> subtypes = null;
         if (subtypeLocales != null) {
-            subtypes = new ArrayList<InputMethodSubtype>();
+            subtypes = new ArrayList<>();
             for (String subtypeLocale : subtypeLocales) {
                 subtypes.add(createDummySubtype(subtypeLocale));
             }
@@ -89,7 +88,7 @@
     }
 
     private static List<ImeSubtypeListItem> createEnabledImeSubtypes() {
-        final List<ImeSubtypeListItem> items = new ArrayList<ImeSubtypeListItem>();
+        final List<ImeSubtypeListItem> items = new ArrayList<>();
         addDummyImeSubtypeListItems(items, "LatinIme", "LatinIme", Arrays.asList("en_US", "fr"),
                 true /* supportsSwitchingToNextInputMethod*/);
         addDummyImeSubtypeListItems(items, "switchUnawareLatinIme", "switchUnawareLatinIme",
@@ -105,7 +104,7 @@
     }
 
     private static List<ImeSubtypeListItem> createDisabledImeSubtypes() {
-        final List<ImeSubtypeListItem> items = new ArrayList<ImeSubtypeListItem>();
+        final List<ImeSubtypeListItem> items = new ArrayList<>();
         addDummyImeSubtypeListItems(items,
                 "UnknownIme", "UnknownIme",
                 Arrays.asList("en_US", "hi"),
@@ -121,15 +120,18 @@
     }
 
     private void assertNextInputMethod(final ControllerImpl controller,
-            final boolean onlyCurrentIme,
-            final ImeSubtypeListItem currentItem, final ImeSubtypeListItem nextItem) {
+            final boolean onlyCurrentIme, final ImeSubtypeListItem currentItem,
+            final ImeSubtypeListItem nextItem, final ImeSubtypeListItem prevItem) {
         InputMethodSubtype subtype = null;
         if (currentItem.mSubtypeName != null) {
             subtype = createDummySubtype(currentItem.mSubtypeName.toString());
         }
         final ImeSubtypeListItem nextIme = controller.getNextInputMethod(onlyCurrentIme,
-                currentItem.mImi, subtype);
+                currentItem.mImi, subtype, true /* forward */);
         assertEquals(nextItem, nextIme);
+        final ImeSubtypeListItem prevIme = controller.getNextInputMethod(onlyCurrentIme,
+                currentItem.mImi, subtype, false /* forward */);
+        assertEquals(prevItem, prevIme);
     }
 
     private void assertRotationOrder(final ControllerImpl controller,
@@ -138,11 +140,13 @@
         final int N = expectedRotationOrderOfImeSubtypeList.length;
         for (int i = 0; i < N; i++) {
             final int currentIndex = i;
+            final int prevIndex = (currentIndex + N - 1) % N;
             final int nextIndex = (currentIndex + 1) % N;
             final ImeSubtypeListItem currentItem =
                     expectedRotationOrderOfImeSubtypeList[currentIndex];
             final ImeSubtypeListItem nextItem = expectedRotationOrderOfImeSubtypeList[nextIndex];
-            assertNextInputMethod(controller, onlyCurrentIme, currentItem, nextItem);
+            final ImeSubtypeListItem prevItem = expectedRotationOrderOfImeSubtypeList[prevIndex];
+            assertNextInputMethod(controller, onlyCurrentIme, currentItem, nextItem, prevItem);
         }
     }
 
@@ -190,29 +194,29 @@
         assertRotationOrder(controller, true /* onlyCurrentIme */,
                 switchingUnawarelatinIme_en_UK, switchingUnawarelatinIme_hi);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                subtypeUnawareIme, null);
+                subtypeUnawareIme, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                japaneseIme_ja_JP, null);
+                japaneseIme_ja_JP, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                switchUnawareJapaneseIme_ja_JP, null);
+                switchUnawareJapaneseIme_ja_JP, null, null);
 
         // Make sure that disabled IMEs are not accepted.
         assertNextInputMethod(controller, false /* onlyCurrentIme */,
-                disabledIme_en_US, null);
+                disabledIme_en_US, null, null);
         assertNextInputMethod(controller, false /* onlyCurrentIme */,
-                disabledIme_hi, null);
+                disabledIme_hi, null, null);
         assertNextInputMethod(controller, false /* onlyCurrentIme */,
-                disabledSwitchingUnawareIme, null);
+                disabledSwitchingUnawareIme, null, null);
         assertNextInputMethod(controller, false /* onlyCurrentIme */,
-                disabledSubtypeUnawareIme, null);
+                disabledSubtypeUnawareIme, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                disabledIme_en_US, null);
+                disabledIme_en_US, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                disabledIme_hi, null);
+                disabledIme_hi, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                disabledSwitchingUnawareIme, null);
+                disabledSwitchingUnawareIme, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                disabledSubtypeUnawareIme, null);
+                disabledSubtypeUnawareIme, null, null);
     }
 
     @SmallTest
@@ -246,7 +250,7 @@
                 japaneseIme_ja_JP, latinIme_fr, latinIme_en_US);
         // Check onlyCurrentIme == true.
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                japaneseIme_ja_JP, null);
+                japaneseIme_ja_JP, null, null);
         assertRotationOrder(controller, true /* onlyCurrentIme */,
                 latinIme_fr, latinIme_en_US);
         assertRotationOrder(controller, true /* onlyCurrentIme */,
@@ -270,9 +274,9 @@
         assertRotationOrder(controller, true /* onlyCurrentIme */,
                 switchingUnawarelatinIme_en_UK, switchingUnawarelatinIme_hi);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                subtypeUnawareIme, null);
+                subtypeUnawareIme, null, null);
         assertNextInputMethod(controller, true /* onlyCurrentIme */,
-                switchUnawareJapaneseIme_ja_JP, null);
+                switchUnawareJapaneseIme_ja_JP, null, null);
 
         // Rotation order should be preserved when created with the same subtype list.
         final List<ImeSubtypeListItem> sameEnabledItems = createEnabledImeSubtypes();
@@ -298,7 +302,7 @@
 
     @SmallTest
     public void testImeSubtypeListItem() throws Exception {
-        final List<ImeSubtypeListItem> items = new ArrayList<ImeSubtypeListItem>();
+        final List<ImeSubtypeListItem> items = new ArrayList<>();
         addDummyImeSubtypeListItems(items, "LatinIme", "LatinIme",
                 Arrays.asList("en_US", "fr", "en", "en_uk", "enn", "e", "EN_US"),
                 true /* supportsSwitchingToNextInputMethod*/);
diff --git a/core/tests/notificationtests/Android.mk b/core/tests/notificationtests/Android.mk
index be2e6bf..702218c 100644
--- a/core/tests/notificationtests/Android.mk
+++ b/core/tests/notificationtests/Android.mk
@@ -11,6 +11,9 @@
 LOCAL_JAVA_LIBRARIES := android.test.runner
 LOCAL_PACKAGE_NAME := NotificationStressTests
 
+LOCAL_STATIC_JAVA_LIBRARIES := \
+    ub-uiautomator
+
 include $(BUILD_PACKAGE)
 
 include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/core/tests/notificationtests/src/android/app/NotificationStressTest.java b/core/tests/notificationtests/src/android/app/NotificationStressTest.java
index 4cb617e..6e86c37 100644
--- a/core/tests/notificationtests/src/android/app/NotificationStressTest.java
+++ b/core/tests/notificationtests/src/android/app/NotificationStressTest.java
@@ -16,15 +16,19 @@
 
 package android.app;
 
-
 import android.content.Context;
 import android.content.Intent;
 import android.net.Uri;
+import android.os.Build;
+import android.os.RemoteException;
 import android.os.SystemClock;
+import android.support.test.uiautomator.UiDevice;
 import android.test.InstrumentationTestCase;
 import android.test.RepetitiveTest;
-import android.test.TimedTest;
+import android.util.Log;
 
+import java.lang.InterruptedException;
+import java.lang.reflect.Method;
 import java.util.Random;
 
 /**
@@ -34,51 +38,78 @@
 public class NotificationStressTest extends InstrumentationTestCase {
 
     private static final int NUM_ITERATIONS = 200;
+    private static final int NUM_ITERATIONS_2 = 30;
+    private static final int LONG_TIMEOUT = 2000;
+    // 50 notifications per app: defined as Variable MAX_PACKAGE_NOTIFICATIONS in
+    // NotificationManagerService.java
+    private static final int MAX_NOTIFCATIONS = 50;
     private static final int[] ICONS = new int[] {
-        android.R.drawable.stat_notify_call_mute,
-        android.R.drawable.stat_notify_chat,
-        android.R.drawable.stat_notify_error,
-        android.R.drawable.stat_notify_missed_call,
-        android.R.drawable.stat_notify_more,
-        android.R.drawable.stat_notify_sdcard,
-        android.R.drawable.stat_notify_sdcard_prepare,
-        android.R.drawable.stat_notify_sdcard_usb,
-        android.R.drawable.stat_notify_sync,
-        android.R.drawable.stat_notify_sync_noanim,
-        android.R.drawable.stat_notify_voicemail,
+            android.R.drawable.stat_notify_call_mute,
+            android.R.drawable.stat_notify_chat,
+            android.R.drawable.stat_notify_error,
+            android.R.drawable.stat_notify_missed_call,
+            android.R.drawable.stat_notify_more,
+            android.R.drawable.stat_notify_sdcard,
+            android.R.drawable.stat_notify_sdcard_prepare,
+            android.R.drawable.stat_notify_sdcard_usb,
+            android.R.drawable.stat_notify_sync,
+            android.R.drawable.stat_notify_sync_noanim,
+            android.R.drawable.stat_notify_voicemail,
     };
 
     private final Random mRandom = new Random();
     private Context mContext;
     private NotificationManager mNotificationManager;
-    private int notifyId = 0;
+    private UiDevice mDevice = null;
+    private int mNotifyId = 0;
 
     @Override
     protected void setUp() throws Exception {
         super.setUp();
+        mDevice = UiDevice.getInstance(getInstrumentation());
         mContext = getInstrumentation().getContext();
         mNotificationManager = (NotificationManager) mContext.getSystemService(
                 Context.NOTIFICATION_SERVICE);
+        mDevice.setOrientationNatural();
+        mNotificationManager.cancelAll();
     }
 
     @Override
     protected void tearDown() throws Exception {
         super.tearDown();
+        mDevice.unfreezeRotation();
         mNotificationManager.cancelAll();
     }
 
-    @RepetitiveTest(numIterations=NUM_ITERATIONS)
+    @RepetitiveTest(numIterations = NUM_ITERATIONS)
     public void testNotificationStress() {
         // Cancel one of every five notifications to vary load on notification manager
-        if (notifyId % 5 == 4) {
-            mNotificationManager.cancel(notifyId - 4);
+        if (mNotifyId % 5 == 4) {
+            mNotificationManager.cancel(mNotifyId - 4);
         }
-        sendNotification(notifyId++, "testNotificationStressNotify");
+        sendNotification(mNotifyId++, "testNotificationStressNotify");
+    }
+
+    @RepetitiveTest(numIterations = NUM_ITERATIONS_2)
+    public void testNotificationsWithShadeStress() throws Exception {
+        mDevice.openNotification();
+        Thread.sleep(LONG_TIMEOUT);
+        for (int j = 0; j < MAX_NOTIFCATIONS; j++) {
+            sendNotification(mNotifyId++, "testNotificationStressNotify");
+        }
+        Thread.sleep(500);
+        assertTrue(mNotificationManager.getActiveNotifications().length == MAX_NOTIFCATIONS);
+        for (int j = 0; j < MAX_NOTIFCATIONS; j++) {
+            mNotificationManager.cancel(--mNotifyId);
+        }
+        if (isLockScreen()) {
+            fail("Notification stress test failed, back to lockscreen");
+        }
     }
 
     private void sendNotification(int id, CharSequence text) {
         // Fill in arbitrary content
-        Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse("http://www.google.com"));
+        Intent intent = new Intent(Intent.ACTION_VIEW);
         PendingIntent pendingIntent = PendingIntent.getActivity(mContext, 0, intent, 0);
         CharSequence title = text + " " + id;
         CharSequence subtitle = String.valueOf(System.currentTimeMillis());
@@ -90,8 +121,19 @@
                 .setContentTitle(title)
                 .setContentText(subtitle)
                 .setContentIntent(pendingIntent)
+                .setPriority(Notification.PRIORITY_HIGH)
                 .build();
         mNotificationManager.notify(id, notification);
         SystemClock.sleep(10);
     }
+
+    private boolean isLockScreen() {
+        KeyguardManager myKM = (KeyguardManager) mContext
+                .getSystemService(Context.KEYGUARD_SERVICE);
+        if (myKM.inKeyguardRestrictedInputMode()) {
+            return true;
+        } else {
+            return false;
+        }
+    }
 }
diff --git a/data/etc/platform.xml b/data/etc/platform.xml
index d412d7c..8a7d39b 100644
--- a/data/etc/platform.xml
+++ b/data/etc/platform.xml
@@ -111,6 +111,20 @@
         <group gid="media" />
     </permission>
 
+    <!-- These are permissions that were mapped to gids but we need
+         to keep them here until an upgrade from L to the current
+         version is to be supported. These permissions are built-in
+         and in L were not stored in packages.xml as a result if they
+         are not defined here while parsing packages.xml we would
+         ignore these permissions being granted to apps and not
+         propagate the granted state. From N we are storing the
+         built-in permissions in packages.xml as the saved storage
+         is negligible (one tag with the permission) compared to
+         the fragility as one can remove a built-in permission which
+         no longer needs to be mapped to gids and break grant propagation. -->
+    <permission name="android.permission.READ_EXTERNAL_STORAGE" />
+    <permission name="android.permission.WRITE_EXTERNAL_STORAGE" />
+
     <!-- ================================================================== -->
     <!-- ================================================================== -->
     <!-- ================================================================== -->
diff --git a/docs/html/guide/topics/manifest/application-element.jd b/docs/html/guide/topics/manifest/application-element.jd
index 5600b5c..887b4ea 100644
--- a/docs/html/guide/topics/manifest/application-element.jd
+++ b/docs/html/guide/topics/manifest/application-element.jd
@@ -472,6 +472,8 @@
 {@link android.os.StrictMode.VmPolicy.Builder#detectCleartextNetwork() StrictMode.VmPolicy.Builder.detectCleartextNetwork()}.
 
 <p>This attribute was added in API level 23.</p>
+
+<p>This flag is ignored on Android N and above if an Android Network Security Config is present.</p>
 </dd>
 
 <dt><a name="vmSafeMode"></a>{@code android:vmSafeMode}</dt>
diff --git a/graphics/java/android/graphics/FontFamily.java b/graphics/java/android/graphics/FontFamily.java
index f741e3c..e48bf79 100644
--- a/graphics/java/android/graphics/FontFamily.java
+++ b/graphics/java/android/graphics/FontFamily.java
@@ -17,8 +17,12 @@
 package android.graphics;
 
 import android.content.res.AssetManager;
+import android.util.Log;
 
+import java.io.FileInputStream;
+import java.io.IOException;
 import java.nio.ByteBuffer;
+import java.nio.channels.FileChannel;
 import java.util.List;
 
 /**
@@ -27,6 +31,9 @@
  * @hide
  */
 public class FontFamily {
+
+    private static String TAG = "FontFamily";
+
     /**
      * @hide
      */
@@ -62,7 +69,15 @@
     }
 
     public boolean addFont(String path, int ttcIndex) {
-        return nAddFont(mNativePtr, path, ttcIndex);
+        try (FileInputStream file = new FileInputStream(path)) {
+            FileChannel fileChannel = file.getChannel();
+            long fontSize = fileChannel.size();
+            ByteBuffer fontBuffer = fileChannel.map(FileChannel.MapMode.READ_ONLY, 0, fontSize);
+            return nAddFont(mNativePtr, fontBuffer, ttcIndex);
+        } catch (IOException e) {
+            Log.e(TAG, "Error mapping font file " + path);
+            return false;
+        }
     }
 
     public boolean addFontWeightStyle(ByteBuffer font, int ttcIndex, List<FontListParser.Axis> axes,
@@ -76,7 +91,7 @@
 
     private static native long nCreateFamily(String lang, int variant);
     private static native void nUnrefFamily(long nativePtr);
-    private static native boolean nAddFont(long nativeFamily, String path, int ttcIndex);
+    private static native boolean nAddFont(long nativeFamily, ByteBuffer font, int ttcIndex);
     private static native boolean nAddFontWeightStyle(long nativeFamily, ByteBuffer font,
             int ttcIndex, List<FontListParser.Axis> listOfAxis,
             int weight, boolean isItalic);
diff --git a/graphics/java/android/graphics/PixelCopy.java b/graphics/java/android/graphics/PixelCopy.java
new file mode 100644
index 0000000..c599126
--- /dev/null
+++ b/graphics/java/android/graphics/PixelCopy.java
@@ -0,0 +1,104 @@
+package android.graphics;
+
+import android.annotation.NonNull;
+import android.os.Handler;
+import android.view.Surface;
+import android.view.SurfaceView;
+import android.view.ThreadedRenderer;
+
+/**
+ * Provides a mechanisms to issue pixel copy requests to allow for copy
+ * operations from {@link Surface} to {@link Bitmap}
+ *
+ * @hide
+ */
+public final class PixelCopy {
+    /**
+     * Contains the result of a pixel copy request
+     */
+    public static final class Response {
+        /**
+         * Indicates whether or not the copy request completed successfully.
+         * If this is true, then {@link #bitmap} contains the result of the copy.
+         * If this is false, {@link #bitmap} is unmodified from the originally
+         * passed destination.
+         *
+         * For example a request might fail if the source is protected content
+         * so copies are not allowed. Similarly if the source has nothing to
+         * copy from, because either no frames have been produced yet or because
+         * it has already been destroyed, then this will be false.
+         */
+        public boolean success;
+
+        /**
+         * The output bitmap. This is always the same object that was passed
+         * to request() as the 'dest' bitmap. If {@link #success} is true this
+         * contains a copy of the pixels of the source object. If {@link #success}
+         * is false then this is unmodified.
+         */
+        @NonNull
+        public Bitmap bitmap;
+    }
+
+    public interface OnPixelCopyFinished {
+        /**
+         * Callback for when a pixel copy request has completed. This will be called
+         * regardless of whether the copy succeeded or failed.
+         *
+         * @param response Contains the result of the copy request which includes
+         * whether or not the copy was successful.
+         */
+        void onPixelCopyFinished(PixelCopy.Response response);
+    }
+
+    /**
+     * Requests for the display content of a {@link SurfaceView} to be copied
+     * into a provided {@link Bitmap}.
+     *
+     * The contents of the source will be scaled to fit exactly inside the bitmap.
+     * The pixel format of the source buffer will be converted, as part of the copy,
+     * to fit the the bitmap's {@link Bitmap.Config}. The most recently queued buffer
+     * in the SurfaceView's Surface will be used as the source of the copy.
+     *
+     * @param source The source from which to copy
+     * @param dest The destination of the copy. The source will be scaled to
+     * match the width, height, and format of this bitmap.
+     * @param listener Callback for when the pixel copy request completes
+     * @param listenerThread The callback will be invoked on this Handler when
+     * the copy is finished.
+     */
+    public static void request(@NonNull SurfaceView source, @NonNull Bitmap dest,
+            @NonNull OnPixelCopyFinished listener, @NonNull Handler listenerThread) {
+        request(source.getHolder().getSurface(), dest, listener, listenerThread);
+    }
+
+    /**
+     * Requests a copy of the pixels from a {@link Surface} to be copied into
+     * a provided {@link Bitmap}.
+     *
+     * The contents of the source will be scaled to fit exactly inside the bitmap.
+     * The pixel format of the source buffer will be converted, as part of the copy,
+     * to fit the the bitmap's {@link Bitmap.Config}. The most recently queued buffer
+     * in the Surface will be used as the source of the copy.
+     *
+     * @param source The source from which to copy
+     * @param dest The destination of the copy. The source will be scaled to
+     * match the width, height, and format of this bitmap.
+     * @param listener Callback for when the pixel copy request completes
+     * @param listenerThread The callback will be invoked on this Handler when
+     * the copy is finished.
+     */
+    public static void request(@NonNull Surface source, @NonNull Bitmap dest,
+            @NonNull OnPixelCopyFinished listener, @NonNull Handler listenerThread) {
+        // TODO: Make this actually async and fast and cool and stuff
+        final PixelCopy.Response response = new PixelCopy.Response();
+        response.success = ThreadedRenderer.copySurfaceInto(source, dest);
+        response.bitmap = dest;
+        listenerThread.post(new Runnable() {
+            @Override
+            public void run() {
+                listener.onPixelCopyFinished(response);
+            }
+        });
+    }
+}
diff --git a/graphics/java/android/graphics/drawable/VectorDrawable.java b/graphics/java/android/graphics/drawable/VectorDrawable.java
index e75fb98..0e45780 100644
--- a/graphics/java/android/graphics/drawable/VectorDrawable.java
+++ b/graphics/java/android/graphics/drawable/VectorDrawable.java
@@ -534,13 +534,17 @@
     public void inflate(@NonNull Resources r, @NonNull XmlPullParser parser,
             @NonNull AttributeSet attrs, @Nullable Theme theme)
             throws XmlPullParserException, IOException {
-        if (mVectorState.mRootGroup != null || mVectorState.mNativeRendererRefBase != null) {
+        if (mVectorState.mRootGroup != null || mVectorState.mNativeTree != null) {
             // This VD has been used to display other VD resource content, clean up.
-            mVectorState.mRootGroup = new VGroup();
-            if (mVectorState.mNativeRendererRefBase != null) {
-                mVectorState.mNativeRendererRefBase.release();
+            if (mVectorState.mRootGroup != null) {
+                // Remove child nodes' reference to tree
+                mVectorState.mRootGroup.setTree(null);
             }
-            mVectorState.createNativeRenderer(mVectorState.mRootGroup.mNativePtr);
+            mVectorState.mRootGroup = new VGroup();
+            if (mVectorState.mNativeTree != null) {
+                mVectorState.mNativeTree.release();
+            }
+            mVectorState.createNativeTree(mVectorState.mRootGroup);
         }
         final VectorDrawableState state = mVectorState;
         state.setDensity(Drawable.resolveDensity(r, 0));
@@ -734,7 +738,7 @@
         Insets mOpticalInsets = Insets.NONE;
         String mRootName = null;
         VGroup mRootGroup;
-        VirtualRefBasePtr mNativeRendererRefBase = null;
+        VirtualRefBasePtr mNativeTree = null;
 
         int mDensity = DisplayMetrics.DENSITY_DEFAULT;
         final ArrayMap<String, Object> mVGTargetsMap = new ArrayMap<>();
@@ -755,7 +759,7 @@
                 mTintMode = copy.mTintMode;
                 mAutoMirrored = copy.mAutoMirrored;
                 mRootGroup = new VGroup(copy.mRootGroup, mVGTargetsMap);
-                createNativeRenderer(mRootGroup.mNativePtr);
+                createNativeTree(mRootGroup);
 
                 mBaseWidth = copy.mBaseWidth;
                 mBaseHeight = copy.mBaseHeight;
@@ -770,15 +774,16 @@
             }
         }
 
-        private void createNativeRenderer(long rootGroupPtr) {
-            mNativeRendererRefBase = new VirtualRefBasePtr(nCreateRenderer(rootGroupPtr));
+        private void createNativeTree(VGroup rootGroup) {
+            mNativeTree = new VirtualRefBasePtr(nCreateTree(rootGroup.mNativePtr));
+            mRootGroup.setTree(mNativeTree);
         }
 
         long getNativeRenderer() {
-            if (mNativeRendererRefBase == null) {
+            if (mNativeTree == null) {
                 return 0;
             }
-            return mNativeRendererRefBase.get();
+            return mNativeTree.get();
         }
 
         public boolean canReuseCache() {
@@ -817,7 +822,7 @@
 
         public VectorDrawableState() {
             mRootGroup = new VGroup();
-            createNativeRenderer(mRootGroup.mNativePtr);
+            createNativeTree(mRootGroup);
         }
 
         @Override
@@ -881,16 +886,16 @@
          * has changed.
          */
         public boolean setAlpha(float alpha) {
-            return nSetRootAlpha(mNativeRendererRefBase.get(), alpha);
+            return nSetRootAlpha(mNativeTree.get(), alpha);
         }
 
         @SuppressWarnings("unused")
         public float getAlpha() {
-            return nGetRootAlpha(mNativeRendererRefBase.get());
+            return nGetRootAlpha(mNativeTree.get());
         }
     }
 
-    static class VGroup implements VObject {
+    static class VGroup extends VObject {
         private static final int ROTATE_INDEX = 0;
         private static final int PIVOT_X_INDEX = 1;
         private static final int PIVOT_Y_INDEX = 2;
@@ -984,11 +989,18 @@
         public void addChild(VObject child) {
             nAddChild(mNativePtr, child.getNativePtr());
             mChildren.add(child);
-
             mIsStateful |= child.isStateful();
         }
 
         @Override
+        public void setTree(VirtualRefBasePtr treeRoot) {
+            super.setTree(treeRoot);
+            for (int i = 0; i < mChildren.size(); i++) {
+                mChildren.get(i).setTree(treeRoot);
+            }
+        }
+
+        @Override
         public long getNativePtr() {
             return mNativePtr;
         }
@@ -1101,79 +1113,93 @@
         /* Setters and Getters, used by animator from AnimatedVectorDrawable. */
         @SuppressWarnings("unused")
         public float getRotation() {
-            return nGetRotation(mNativePtr);
+            return isTreeValid() ? nGetRotation(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setRotation(float rotation) {
-            nSetRotation(mNativePtr, rotation);
+            if (isTreeValid()) {
+                nSetRotation(mNativePtr, rotation);
+            }
         }
 
         @SuppressWarnings("unused")
         public float getPivotX() {
-            return nGetPivotX(mNativePtr);
+            return isTreeValid() ? nGetPivotX(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setPivotX(float pivotX) {
-            nSetPivotX(mNativePtr, pivotX);
+            if (isTreeValid()) {
+                nSetPivotX(mNativePtr, pivotX);
+            }
         }
 
         @SuppressWarnings("unused")
         public float getPivotY() {
-            return nGetPivotY(mNativePtr);
+            return isTreeValid() ? nGetPivotY(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setPivotY(float pivotY) {
-            nSetPivotY(mNativePtr, pivotY);
+            if (isTreeValid()) {
+                nSetPivotY(mNativePtr, pivotY);
+            }
         }
 
         @SuppressWarnings("unused")
         public float getScaleX() {
-            return nGetScaleX(mNativePtr);
+            return isTreeValid() ? nGetScaleX(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setScaleX(float scaleX) {
-            nSetScaleX(mNativePtr, scaleX);
+            if (isTreeValid()) {
+                nSetScaleX(mNativePtr, scaleX);
+            }
         }
 
         @SuppressWarnings("unused")
         public float getScaleY() {
-            return nGetScaleY(mNativePtr);
+            return isTreeValid() ? nGetScaleY(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setScaleY(float scaleY) {
-            nSetScaleY(mNativePtr, scaleY);
+            if (isTreeValid()) {
+                nSetScaleY(mNativePtr, scaleY);
+            }
         }
 
         @SuppressWarnings("unused")
         public float getTranslateX() {
-            return nGetTranslateX(mNativePtr);
+            return isTreeValid() ? nGetTranslateX(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setTranslateX(float translateX) {
-            nSetTranslateX(mNativePtr, translateX);
+            if (isTreeValid()) {
+                nSetTranslateX(mNativePtr, translateX);
+            }
         }
 
         @SuppressWarnings("unused")
         public float getTranslateY() {
-            return nGetTranslateY(mNativePtr);
+            return isTreeValid() ? nGetTranslateY(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         public void setTranslateY(float translateY) {
-            nSetTranslateY(mNativePtr, translateY);
+            if (isTreeValid()) {
+                nSetTranslateY(mNativePtr, translateY);
+            }
         }
     }
 
     /**
      * Common Path information for clip path and normal path.
      */
-    static abstract class VPath implements VObject {
+    static abstract class VPath extends VObject {
         protected PathParser.PathData mPathData = null;
 
         String mPathName;
@@ -1203,7 +1229,9 @@
         @SuppressWarnings("unused")
         public void setPathData(PathParser.PathData pathData) {
             mPathData.setPathData(pathData);
-            nSetPathData(getNativePtr(), mPathData.getNativePtr());
+            if (isTreeValid()) {
+                nSetPathData(getNativePtr(), mPathData.getNativePtr());
+            }
         }
     }
 
@@ -1549,97 +1577,120 @@
         /* Setters and Getters, used by animator from AnimatedVectorDrawable. */
         @SuppressWarnings("unused")
         int getStrokeColor() {
-            return nGetStrokeColor(mNativePtr);
+            return isTreeValid() ? nGetStrokeColor(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setStrokeColor(int strokeColor) {
             mStrokeColors = null;
-            nSetStrokeColor(mNativePtr, strokeColor);
+            if (isTreeValid()) {
+                nSetStrokeColor(mNativePtr, strokeColor);
+            }
         }
 
         @SuppressWarnings("unused")
         float getStrokeWidth() {
-            return nGetStrokeWidth(mNativePtr);
+            return isTreeValid() ? nGetStrokeWidth(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setStrokeWidth(float strokeWidth) {
-            nSetStrokeWidth(mNativePtr, strokeWidth);
+            if (isTreeValid()) {
+                nSetStrokeWidth(mNativePtr, strokeWidth);
+            }
         }
 
         @SuppressWarnings("unused")
         float getStrokeAlpha() {
-            return nGetStrokeAlpha(mNativePtr);
+            return isTreeValid() ? nGetStrokeAlpha(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setStrokeAlpha(float strokeAlpha) {
-            nSetStrokeAlpha(mNativePtr, strokeAlpha);
+            if (isTreeValid()) {
+                nSetStrokeAlpha(mNativePtr, strokeAlpha);
+            }
         }
 
         @SuppressWarnings("unused")
         int getFillColor() {
-            return nGetFillColor(mNativePtr);
+            return isTreeValid() ? nGetFillColor(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setFillColor(int fillColor) {
             mFillColors = null;
-            nSetFillColor(mNativePtr, fillColor);
+            if (isTreeValid()) {
+                nSetFillColor(mNativePtr, fillColor);
+            }
         }
 
         @SuppressWarnings("unused")
         float getFillAlpha() {
-            return nGetFillAlpha(mNativePtr);
+            return isTreeValid() ? nGetFillAlpha(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setFillAlpha(float fillAlpha) {
-            nSetFillAlpha(mNativePtr, fillAlpha);
+            if (isTreeValid()) {
+                nSetFillAlpha(mNativePtr, fillAlpha);
+            }
         }
 
         @SuppressWarnings("unused")
         float getTrimPathStart() {
-            return nGetTrimPathStart(mNativePtr);
+            return isTreeValid() ? nGetTrimPathStart(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setTrimPathStart(float trimPathStart) {
-            nSetTrimPathStart(mNativePtr, trimPathStart);
+            if (isTreeValid()) {
+                nSetTrimPathStart(mNativePtr, trimPathStart);
+            }
         }
 
         @SuppressWarnings("unused")
         float getTrimPathEnd() {
-            return nGetTrimPathEnd(mNativePtr);
+            return isTreeValid() ? nGetTrimPathEnd(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setTrimPathEnd(float trimPathEnd) {
-            nSetTrimPathEnd(mNativePtr, trimPathEnd);
+            if (isTreeValid()) {
+                nSetTrimPathEnd(mNativePtr, trimPathEnd);
+            }
         }
 
         @SuppressWarnings("unused")
         float getTrimPathOffset() {
-            return nGetTrimPathOffset(mNativePtr);
+            return isTreeValid() ? nGetTrimPathOffset(mNativePtr) : 0;
         }
 
         @SuppressWarnings("unused")
         void setTrimPathOffset(float trimPathOffset) {
-            nSetTrimPathOffset(mNativePtr, trimPathOffset);
+            if (isTreeValid()) {
+                nSetTrimPathOffset(mNativePtr, trimPathOffset);
+            }
         }
     }
 
-    interface VObject {
-        long getNativePtr();
-        void inflate(Resources r, AttributeSet attrs, Theme theme);
-        boolean canApplyTheme();
-        void applyTheme(Theme t);
-        boolean onStateChange(int[] state);
-        boolean isStateful();
+    abstract static class VObject {
+        VirtualRefBasePtr mTreePtr = null;
+        boolean isTreeValid() {
+            return mTreePtr != null && mTreePtr.get() != 0;
+        }
+        void setTree(VirtualRefBasePtr ptr) {
+            mTreePtr = ptr;
+        }
+        abstract long getNativePtr();
+        abstract void inflate(Resources r, AttributeSet attrs, Theme theme);
+        abstract boolean canApplyTheme();
+        abstract void applyTheme(Theme t);
+        abstract boolean onStateChange(int[] state);
+        abstract boolean isStateful();
     }
 
-    private static native long nCreateRenderer(long rootGroupPtr);
+    private static native long nCreateTree(long rootGroupPtr);
     private static native void nSetRendererViewportSize(long rendererPtr, float viewportWidth,
             float viewportHeight);
     private static native boolean nSetRootAlpha(long rendererPtr, float alpha);
diff --git a/libs/hwui/Android.mk b/libs/hwui/Android.mk
index be816f78..717a1e6 100644
--- a/libs/hwui/Android.mk
+++ b/libs/hwui/Android.mk
@@ -84,6 +84,7 @@
     Properties.cpp \
     PropertyValuesHolder.cpp \
     PropertyValuesAnimatorSet.cpp \
+    Readback.cpp \
     RenderBufferCache.cpp \
     RenderNode.cpp \
     RenderProperties.cpp \
@@ -248,16 +249,17 @@
     tests/unit/FatVectorTests.cpp \
     tests/unit/GlopBuilderTests.cpp \
     tests/unit/GpuMemoryTrackerTests.cpp \
+    tests/unit/GradientCacheTests.cpp \
     tests/unit/LayerUpdateQueueTests.cpp \
     tests/unit/LinearAllocatorTests.cpp \
     tests/unit/MatrixTests.cpp \
     tests/unit/OffscreenBufferPoolTests.cpp \
     tests/unit/RenderNodeTests.cpp \
     tests/unit/SkiaBehaviorTests.cpp \
+    tests/unit/SnapshotTests.cpp \
     tests/unit/StringUtilsTests.cpp \
     tests/unit/TextDropShadowCacheTests.cpp \
-    tests/unit/VectorDrawableTests.cpp \
-    tests/unit/GradientCacheTests.cpp
+    tests/unit/VectorDrawableTests.cpp
 
 ifeq (true, $(HWUI_NEW_OPS))
     LOCAL_SRC_FILES += \
diff --git a/libs/hwui/BakedOpState.cpp b/libs/hwui/BakedOpState.cpp
index b70d586..9f98241 100644
--- a/libs/hwui/BakedOpState.cpp
+++ b/libs/hwui/BakedOpState.cpp
@@ -50,7 +50,7 @@
     }
 
     // resolvedClipRect = intersect(parentMatrix * localClip, parentClip)
-    clipState = snapshot.mutateClipArea().serializeIntersectedClip(allocator,
+    clipState = snapshot.serializeIntersectedClip(allocator,
             recordedOp.localClip, *(snapshot.transform));
     LOG_ALWAYS_FATAL_IF(!clipState, "must clip!");
 
@@ -85,8 +85,7 @@
 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));
+    clipState = snapshot.serializeIntersectedClip(allocator, localClip, *(snapshot.transform));
     clippedBounds = clipState->rect;
     clipSideFlags = OpClipSideFlags::Full;
     localProjectionPathMask = nullptr;
diff --git a/libs/hwui/ClipArea.cpp b/libs/hwui/ClipArea.cpp
index f886dda..35fe06d 100644
--- a/libs/hwui/ClipArea.cpp
+++ b/libs/hwui/ClipArea.cpp
@@ -217,6 +217,7 @@
 
 void ClipArea::clipRectWithTransform(const Rect& r, const mat4* transform,
         SkRegion::Op op) {
+    if (op == SkRegion::kReplace_Op) mReplaceOpObserved = true;
     if (!mPostViewportClipObserved && op == SkRegion::kIntersect_Op) op = SkRegion::kReplace_Op;
     onClipUpdated();
     switch (mMode) {
@@ -233,6 +234,7 @@
 }
 
 void ClipArea::clipRegion(const SkRegion& region, SkRegion::Op op) {
+    if (op == SkRegion::kReplace_Op) mReplaceOpObserved = true;
     if (!mPostViewportClipObserved && op == SkRegion::kIntersect_Op) op = SkRegion::kReplace_Op;
     onClipUpdated();
     enterRegionMode();
@@ -242,6 +244,7 @@
 
 void ClipArea::clipPathWithTransform(const SkPath& path, const mat4* transform,
         SkRegion::Op op) {
+    if (op == SkRegion::kReplace_Op) mReplaceOpObserved = true;
     if (!mPostViewportClipObserved && op == SkRegion::kIntersect_Op) op = SkRegion::kReplace_Op;
     onClipUpdated();
     SkMatrix skTransform;
@@ -379,6 +382,7 @@
             serialization->rect.set(mClipRegion.getBounds());
             break;
         }
+        serialization->intersectWithRoot = mReplaceOpObserved;
         // TODO: this is only done for draw time, should eventually avoid for record time
         serialization->rect.snapToPixelBoundaries();
         mLastSerialization = serialization;
diff --git a/libs/hwui/ClipArea.h b/libs/hwui/ClipArea.h
index 1654eb8..6eb2eef 100644
--- a/libs/hwui/ClipArea.h
+++ b/libs/hwui/ClipArea.h
@@ -103,6 +103,7 @@
             : mode(ClipMode::Rectangle)
             , rect(rect) {}
     const ClipMode mode;
+    bool intersectWithRoot = false;
     // Bounds of the clipping area, used to define the scissor, and define which
     // portion of the stencil is updated/used
     Rect rect;
@@ -173,8 +174,8 @@
         return mMode == ClipMode::RectangleList;
     }
 
-    const ClipBase* serializeClip(LinearAllocator& allocator);
-    const ClipBase* serializeIntersectedClip(LinearAllocator& allocator,
+    WARN_UNUSED_RESULT const ClipBase* serializeClip(LinearAllocator& allocator);
+    WARN_UNUSED_RESULT const ClipBase* serializeIntersectedClip(LinearAllocator& allocator,
             const ClipBase* recordedClip, const Matrix4& recordedClipTransform);
     void applyClip(const ClipBase* recordedClip, const Matrix4& recordedClipTransform);
 
@@ -214,6 +215,7 @@
 
     ClipMode mMode;
     bool mPostViewportClipObserved = false;
+    bool mReplaceOpObserved = false;
 
     /**
      * If mLastSerialization is non-null, it represents an already serialized copy
diff --git a/libs/hwui/DisplayList.h b/libs/hwui/DisplayList.h
index e209e2a..aba5d4b 100644
--- a/libs/hwui/DisplayList.h
+++ b/libs/hwui/DisplayList.h
@@ -137,6 +137,9 @@
 
         // whether children with non-zero Z in the chunk should be reordered
         bool reorderChildren;
+#if HWUI_NEW_OPS
+        const ClipBase* reorderClip;
+#endif
     };
 
     DisplayList();
diff --git a/libs/hwui/FrameBuilder.cpp b/libs/hwui/FrameBuilder.cpp
index 0401f2d..6fc74a5 100644
--- a/libs/hwui/FrameBuilder.cpp
+++ b/libs/hwui/FrameBuilder.cpp
@@ -269,7 +269,8 @@
 }
 
 template <typename V>
-void FrameBuilder::defer3dChildren(ChildrenSelectMode mode, const V& zTranslatedNodes) {
+void FrameBuilder::defer3dChildren(const ClipBase* reorderClip, ChildrenSelectMode mode,
+        const V& zTranslatedNodes) {
     const int size = zTranslatedNodes.size();
     if (size == 0
             || (mode == ChildrenSelectMode::Negative&& zTranslatedNodes[0].key > 0.0f)
@@ -305,7 +306,7 @@
             // attempt to render the shadow if the caster about to be drawn is its caster,
             // OR if its caster's Z value is similar to the previous potential caster
             if (shadowIndex == drawIndex || casterZ - lastCasterZ < 0.1f) {
-                deferShadow(*casterNodeOp);
+                deferShadow(reorderClip, *casterNodeOp);
 
                 lastCasterZ = casterZ; // must do this even if current caster not casting a shadow
                 shadowIndex++;
@@ -319,7 +320,7 @@
     }
 }
 
-void FrameBuilder::deferShadow(const RenderNodeOp& casterNodeOp) {
+void FrameBuilder::deferShadow(const ClipBase* reorderClip, const RenderNodeOp& casterNodeOp) {
     auto& node = *casterNodeOp.renderNode;
     auto& properties = node.properties();
 
@@ -365,6 +366,10 @@
         casterPath = frameAllocatedPath;
     }
 
+    // apply reorder clip to shadow, so it respects clip at beginning of reorderable chunk
+    int restoreTo = mCanvasState.save(SaveFlags::MatrixClip);
+    mCanvasState.writableSnapshot()->applyClip(reorderClip,
+            *mCanvasState.currentSnapshot()->transform);
     if (CC_LIKELY(!mCanvasState.getRenderTargetClipBounds().isEmpty())) {
         Matrix4 shadowMatrixXY(casterNodeOp.localMatrix);
         Matrix4 shadowMatrixZ(casterNodeOp.localMatrix);
@@ -386,6 +391,7 @@
             currentLayer().deferUnmergeableOp(mAllocator, bakedOpState, OpBatchType::Shadow);
         }
     }
+    mCanvasState.restoreToCount(restoreTo);
 }
 
 void FrameBuilder::deferProjectedChildren(const RenderNode& renderNode) {
@@ -438,11 +444,11 @@
 
     // can't be null, since DL=null node rejection happens before deferNodePropsAndOps
     const DisplayList& displayList = *(renderNode.getDisplayList());
-    for (const DisplayList::Chunk& chunk : displayList.getChunks()) {
+    for (auto& chunk : displayList.getChunks()) {
         FatVector<ZRenderNodeOpPair, 16> zTranslatedNodes;
         buildZSortedChildList(&zTranslatedNodes, displayList, chunk);
 
-        defer3dChildren(ChildrenSelectMode::Negative, zTranslatedNodes);
+        defer3dChildren(chunk.reorderClip, ChildrenSelectMode::Negative, zTranslatedNodes);
         for (size_t opIndex = chunk.beginOpIndex; opIndex < chunk.endOpIndex; opIndex++) {
             const RecordedOp* op = displayList.getOps()[opIndex];
             receivers[op->opId](*this, *op);
@@ -453,7 +459,7 @@
                 deferProjectedChildren(renderNode);
             }
         }
-        defer3dChildren(ChildrenSelectMode::Positive, zTranslatedNodes);
+        defer3dChildren(chunk.reorderClip, ChildrenSelectMode::Positive, zTranslatedNodes);
     }
 }
 
@@ -462,7 +468,7 @@
     int count = mCanvasState.save(SaveFlags::MatrixClip);
 
     // apply state from RecordedOp (clip first, since op's clip is transformed by current matrix)
-    mCanvasState.writableSnapshot()->mutateClipArea().applyClip(op.localClip,
+    mCanvasState.writableSnapshot()->applyClip(op.localClip,
             *mCanvasState.currentSnapshot()->transform);
     mCanvasState.concatMatrix(op.localMatrix);
 
diff --git a/libs/hwui/FrameBuilder.h b/libs/hwui/FrameBuilder.h
index 039ab6b..a6fd761 100644
--- a/libs/hwui/FrameBuilder.h
+++ b/libs/hwui/FrameBuilder.h
@@ -193,9 +193,10 @@
     void deferNodePropsAndOps(RenderNode& node);
 
     template <typename V>
-    void defer3dChildren(ChildrenSelectMode mode, const V& zTranslatedNodes);
+    void defer3dChildren(const ClipBase* reorderClip, ChildrenSelectMode mode,
+            const V& zTranslatedNodes);
 
-    void deferShadow(const RenderNodeOp& casterOp);
+    void deferShadow(const ClipBase* reorderClip, const RenderNodeOp& casterOp);
 
     void deferProjectedChildren(const RenderNode& renderNode);
 
diff --git a/libs/hwui/JankTracker.cpp b/libs/hwui/JankTracker.cpp
index d1ff670..9d4eccc 100644
--- a/libs/hwui/JankTracker.cpp
+++ b/libs/hwui/JankTracker.cpp
@@ -285,6 +285,7 @@
 void JankTracker::reset() {
     mData->jankTypeCounts.fill(0);
     mData->frameCounts.fill(0);
+    mData->slowFrameCounts.fill(0);
     mData->totalFrameCount = 0;
     mData->jankFrameCount = 0;
     mData->statStartTime = systemTime(CLOCK_MONOTONIC);
diff --git a/libs/hwui/OpDumper.cpp b/libs/hwui/OpDumper.cpp
index c34cfbe..cab93e8 100644
--- a/libs/hwui/OpDumper.cpp
+++ b/libs/hwui/OpDumper.cpp
@@ -33,10 +33,15 @@
     op.localMatrix.mapRect(localBounds);
     output << sOpNameLut[op.opId] << " " << localBounds;
 
-    if (op.localClip && !op.localClip->rect.contains(localBounds)) {
+    if (op.localClip
+            && (!op.localClip->rect.contains(localBounds) || op.localClip->intersectWithRoot)) {
         output << std::fixed << std::setprecision(0)
              << " clip=" << op.localClip->rect
              << " mode=" << (int)op.localClip->mode;
+
+        if (op.localClip->intersectWithRoot) {
+             output << " iwr";
+        }
     }
 }
 
diff --git a/libs/hwui/PathCache.cpp b/libs/hwui/PathCache.cpp
index 8f914ac..a8ace8c 100644
--- a/libs/hwui/PathCache.cpp
+++ b/libs/hwui/PathCache.cpp
@@ -19,6 +19,7 @@
 #include <SkColor.h>
 #include <SkPaint.h>
 #include <SkPath.h>
+#include <SkPathEffect.h>
 #include <SkRect.h>
 
 #include <utils/JenkinsHash.h>
@@ -35,18 +36,34 @@
 namespace android {
 namespace uirenderer {
 
+template <class T>
+static bool compareWidthHeight(const T& lhs, const T& rhs) {
+    return (lhs.mWidth == rhs.mWidth) && (lhs.mHeight == rhs.mHeight);
+}
+
+static bool compareRoundRects(const PathDescription::Shape::RoundRect& lhs,
+        const PathDescription::Shape::RoundRect& rhs) {
+    return compareWidthHeight(lhs, rhs) && lhs.mRx == rhs.mRx && lhs.mRy == rhs.mRy;
+}
+
+static bool compareArcs(const PathDescription::Shape::Arc& lhs, const PathDescription::Shape::Arc& rhs) {
+    return compareWidthHeight(lhs, rhs) && lhs.mStartAngle == rhs.mStartAngle &&
+            lhs.mSweepAngle == rhs.mSweepAngle && lhs.mUseCenter == rhs.mUseCenter;
+}
+
 ///////////////////////////////////////////////////////////////////////////////
 // Cache entries
 ///////////////////////////////////////////////////////////////////////////////
 
 PathDescription::PathDescription()
-        : type(kShapeNone)
+        : type(ShapeType::None)
         , join(SkPaint::kDefault_Join)
         , cap(SkPaint::kDefault_Cap)
         , style(SkPaint::kFill_Style)
         , miter(4.0f)
         , strokeWidth(1.0f)
         , pathEffect(nullptr) {
+    // Shape bits should be set to zeroes, because they are used for hash calculation.
     memset(&shape, 0, sizeof(Shape));
 }
 
@@ -58,11 +75,12 @@
         , miter(paint->getStrokeMiter())
         , strokeWidth(paint->getStrokeWidth())
         , pathEffect(paint->getPathEffect()) {
+    // Shape bits should be set to zeroes, because they are used for hash calculation.
     memset(&shape, 0, sizeof(Shape));
 }
 
 hash_t PathDescription::hash() const {
-    uint32_t hash = JenkinsHashMix(0, type);
+    uint32_t hash = JenkinsHashMix(0, static_cast<int>(type));
     hash = JenkinsHashMix(hash, join);
     hash = JenkinsHashMix(hash, cap);
     hash = JenkinsHashMix(hash, style);
@@ -73,6 +91,32 @@
     return JenkinsHashWhiten(hash);
 }
 
+bool PathDescription::operator==(const PathDescription& rhs) const {
+    if (type != rhs.type) return false;
+    if (join != rhs.join) return false;
+    if (cap != rhs.cap) return false;
+    if (style != rhs.style) return false;
+    if (miter != rhs.miter) return false;
+    if (strokeWidth != rhs.strokeWidth) return false;
+    if (pathEffect != rhs.pathEffect) return false;
+    switch (type) {
+        case ShapeType::None:
+            return 0;
+        case ShapeType::Rect:
+            return compareWidthHeight(shape.rect, rhs.shape.rect);
+        case ShapeType::RoundRect:
+            return compareRoundRects(shape.roundRect, rhs.shape.roundRect);
+        case ShapeType::Circle:
+            return shape.circle.mRadius == rhs.shape.circle.mRadius;
+        case ShapeType::Oval:
+            return compareWidthHeight(shape.oval, rhs.shape.oval);
+        case ShapeType::Arc:
+            return compareArcs(shape.arc, rhs.shape.arc);
+        case ShapeType::Path:
+            return shape.path.mGenerationID == rhs.shape.path.mGenerationID;
+    }
+}
+
 ///////////////////////////////////////////////////////////////////////////////
 // Utilities
 ///////////////////////////////////////////////////////////////////////////////
@@ -322,7 +366,7 @@
             LruCache<PathDescription, PathTexture*>::Iterator iter(mCache);
             while (iter.next()) {
                 const PathDescription& key = iter.key();
-                if (key.type == kShapePath && key.shape.path.mGenerationID == generationID) {
+                if (key.type == ShapeType::Path && key.shape.path.mGenerationID == generationID) {
                     pathsToRemove.push(key);
                 }
             }
@@ -336,7 +380,7 @@
 }
 
 PathTexture* PathCache::get(const SkPath* path, const SkPaint* paint) {
-    PathDescription entry(kShapePath, paint);
+    PathDescription entry(ShapeType::Path, paint);
     entry.shape.path.mGenerationID = path->getGenerationID();
 
     PathTexture* texture = mCache.get(entry);
@@ -366,9 +410,8 @@
     return texture;
 }
 
-void PathCache::remove(const SkPath* path, const SkPaint* paint)
-{
-    PathDescription entry(kShapePath, paint);
+void PathCache::remove(const SkPath* path, const SkPaint* paint) {
+    PathDescription entry(ShapeType::Path, paint);
     entry.shape.path.mGenerationID = path->getGenerationID();
     mCache.remove(entry);
 }
@@ -378,7 +421,7 @@
         return;
     }
 
-    PathDescription entry(kShapePath, paint);
+    PathDescription entry(ShapeType::Path, paint);
     entry.shape.path.mGenerationID = path->getGenerationID();
 
     PathTexture* texture = mCache.get(entry);
@@ -417,7 +460,7 @@
 
 PathTexture* PathCache::getRoundRect(float width, float height,
         float rx, float ry, const SkPaint* paint) {
-    PathDescription entry(kShapeRoundRect, paint);
+    PathDescription entry(ShapeType::RoundRect, paint);
     entry.shape.roundRect.mWidth = width;
     entry.shape.roundRect.mHeight = height;
     entry.shape.roundRect.mRx = rx;
@@ -442,7 +485,7 @@
 ///////////////////////////////////////////////////////////////////////////////
 
 PathTexture* PathCache::getCircle(float radius, const SkPaint* paint) {
-    PathDescription entry(kShapeCircle, paint);
+    PathDescription entry(ShapeType::Circle, paint);
     entry.shape.circle.mRadius = radius;
 
     PathTexture* texture = get(entry);
@@ -462,7 +505,7 @@
 ///////////////////////////////////////////////////////////////////////////////
 
 PathTexture* PathCache::getOval(float width, float height, const SkPaint* paint) {
-    PathDescription entry(kShapeOval, paint);
+    PathDescription entry(ShapeType::Oval, paint);
     entry.shape.oval.mWidth = width;
     entry.shape.oval.mHeight = height;
 
@@ -485,7 +528,7 @@
 ///////////////////////////////////////////////////////////////////////////////
 
 PathTexture* PathCache::getRect(float width, float height, const SkPaint* paint) {
-    PathDescription entry(kShapeRect, paint);
+    PathDescription entry(ShapeType::Rect, paint);
     entry.shape.rect.mWidth = width;
     entry.shape.rect.mHeight = height;
 
@@ -509,7 +552,7 @@
 
 PathTexture* PathCache::getArc(float width, float height,
         float startAngle, float sweepAngle, bool useCenter, const SkPaint* paint) {
-    PathDescription entry(kShapeArc, paint);
+    PathDescription entry(ShapeType::Arc, paint);
     entry.shape.arc.mWidth = width;
     entry.shape.arc.mHeight = height;
     entry.shape.arc.mStartAngle = startAngle;
diff --git a/libs/hwui/PathCache.h b/libs/hwui/PathCache.h
index d2633aa..6368ddd 100644
--- a/libs/hwui/PathCache.h
+++ b/libs/hwui/PathCache.h
@@ -25,6 +25,7 @@
 #include "utils/Pair.h"
 
 #include <GLES2/gl2.h>
+#include <SkPaint.h>
 #include <SkPath.h>
 #include <utils/LruCache.h>
 #include <utils/Mutex.h>
@@ -108,18 +109,18 @@
     sp<Task<SkBitmap*> > mTask;
 }; // struct PathTexture
 
-enum ShapeType {
-    kShapeNone,
-    kShapeRect,
-    kShapeRoundRect,
-    kShapeCircle,
-    kShapeOval,
-    kShapeArc,
-    kShapePath
+enum class ShapeType {
+    None,
+    Rect,
+    RoundRect,
+    Circle,
+    Oval,
+    Arc,
+    Path
 };
 
 struct PathDescription {
-    DESCRIPTION_TYPE(PathDescription);
+    HASHABLE_TYPE(PathDescription);
     ShapeType type;
     SkPaint::Join join;
     SkPaint::Cap cap;
@@ -159,8 +160,6 @@
 
     PathDescription();
     PathDescription(ShapeType shapeType, const SkPaint* paint);
-
-    hash_t hash() const;
 };
 
 /**
diff --git a/libs/hwui/PathParser.cpp b/libs/hwui/PathParser.cpp
index 4e9ac9c..7e85333 100644
--- a/libs/hwui/PathParser.cpp
+++ b/libs/hwui/PathParser.cpp
@@ -156,6 +156,12 @@
     return;
 }
 
+bool PathParser::isVerbValid(char verb) {
+    verb = tolower(verb);
+    return verb == 'a' || verb == 'c' || verb == 'h' || verb == 'l' || verb == 'm' || verb == 'q'
+            || verb == 's' || verb == 't' || verb == 'v' || verb == 'z';
+}
+
 void PathParser::getPathDataFromString(PathData* data, ParseResult* result,
         const char* pathStr, size_t strLen) {
     if (pathStr == NULL) {
@@ -171,6 +177,12 @@
         end = nextStart(pathStr, strLen, end);
         std::vector<float> points;
         getFloats(&points, result, pathStr, start, end);
+        if (!isVerbValid(pathStr[start])) {
+            result->failureOccurred = true;
+            result->failureMessage = "Invalid pathData. Failure occurred at position "
+                    + std::to_string(start) + " of path: " + pathStr;
+        }
+        // If either verb or points is not valid, return immediately.
         if (result->failureOccurred) {
             return;
         }
@@ -182,10 +194,15 @@
     }
 
     if ((end - start) == 1 && start < strLen) {
+        if (!isVerbValid(pathStr[start])) {
+            result->failureOccurred = true;
+            result->failureMessage = "Invalid pathData. Failure occurred at position "
+                    + std::to_string(start) + " of path: " + pathStr;
+            return;
+        }
         data->verbs.push_back(pathStr[start]);
         data->verbSizes.push_back(0);
     }
-    return;
 }
 
 void PathParser::dump(const PathData& data) {
@@ -218,7 +235,8 @@
     // Check if there is valid data coming out of parsing the string.
     if (pathData.verbs.size() == 0) {
         result->failureOccurred = true;
-        result->failureMessage = "No verbs found in the string for pathData";
+        result->failureMessage = "No verbs found in the string for pathData: ";
+        result->failureMessage += pathStr;
         return;
     }
     VectorDrawableUtils::verbsToPath(skPath, pathData);
diff --git a/libs/hwui/PathParser.h b/libs/hwui/PathParser.h
index c4bbb74..180a7a3 100644
--- a/libs/hwui/PathParser.h
+++ b/libs/hwui/PathParser.h
@@ -44,6 +44,7 @@
     ANDROID_API static void getPathDataFromString(PathData* outData, ParseResult* result,
             const char* pathStr, size_t strLength);
     static void dump(const PathData& data);
+    static bool isVerbValid(char verb);
 };
 
 }; // namespace uirenderer
diff --git a/libs/hwui/Readback.cpp b/libs/hwui/Readback.cpp
new file mode 100644
index 0000000..d7df77c
--- /dev/null
+++ b/libs/hwui/Readback.cpp
@@ -0,0 +1,159 @@
+/*
+ * 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.
+ */
+
+#include "Readback.h"
+
+#include "Caches.h"
+#include "Image.h"
+#include "GlopBuilder.h"
+#include "renderstate/RenderState.h"
+#include "renderthread/EglManager.h"
+#include "utils/GLUtils.h"
+
+#include <GLES2/gl2.h>
+#include <ui/Fence.h>
+#include <ui/GraphicBuffer.h>
+
+namespace android {
+namespace uirenderer {
+
+bool Readback::copySurfaceInto(renderthread::RenderThread& renderThread,
+        Surface& surface, SkBitmap* bitmap) {
+    // TODO: Clean this up and unify it with LayerRenderer::copyLayer,
+    // of which most of this is copied from.
+    renderThread.eglManager().initialize();
+
+    Caches& caches = Caches::getInstance();
+    RenderState& renderState = renderThread.renderState();
+    int destWidth = bitmap->width();
+    int destHeight = bitmap->height();
+    if (destWidth > caches.maxTextureSize
+                || destHeight > caches.maxTextureSize) {
+        ALOGW("Can't copy surface into bitmap, %dx%d exceeds max texture size %d",
+                destWidth, destHeight, caches.maxTextureSize);
+        return false;
+    }
+    GLuint fbo = renderState.createFramebuffer();
+    if (!fbo) {
+        ALOGW("Could not obtain an FBO");
+        return false;
+    }
+
+    SkAutoLockPixels alp(*bitmap);
+
+    GLuint texture;
+
+    GLenum format;
+    GLenum type;
+
+    switch (bitmap->colorType()) {
+        case kAlpha_8_SkColorType:
+            format = GL_ALPHA;
+            type = GL_UNSIGNED_BYTE;
+            break;
+        case kRGB_565_SkColorType:
+            format = GL_RGB;
+            type = GL_UNSIGNED_SHORT_5_6_5;
+            break;
+        case kARGB_4444_SkColorType:
+            format = GL_RGBA;
+            type = GL_UNSIGNED_SHORT_4_4_4_4;
+            break;
+        case kN32_SkColorType:
+        default:
+            format = GL_RGBA;
+            type = GL_UNSIGNED_BYTE;
+            break;
+    }
+
+    renderState.bindFramebuffer(fbo);
+
+    // TODO: Use layerPool or something to get this maybe? But since we
+    // need explicit format control we can't currently.
+
+    // Setup the rendertarget
+    glGenTextures(1, &texture);
+    caches.textureState().activateTexture(0);
+    caches.textureState().bindTexture(texture);
+    glPixelStorei(GL_PACK_ALIGNMENT, bitmap->bytesPerPixel());
+    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
+    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
+    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+    glTexImage2D(GL_TEXTURE_2D, 0, format, destWidth, destHeight,
+            0, format, type, nullptr);
+    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
+            GL_TEXTURE_2D, texture, 0);
+
+    // Setup the source
+    sp<GraphicBuffer> sourceBuffer;
+    sp<Fence> sourceFence;
+    // FIXME: Waiting on an API from libgui for this
+    // surface.getLastQueuedBuffer(&sourceBuffer, &sourceFence);
+    if (!sourceBuffer.get()) {
+        ALOGW("Surface doesn't have any previously queued frames, nothing to readback from");
+        return false;
+    }
+    int err = sourceFence->wait(500 /* ms */);
+    if (err != NO_ERROR) {
+        ALOGE("Timeout (500ms) exceeded waiting for buffer fence, abandoning readback attempt");
+        return false;
+    }
+    Image sourceImage(sourceBuffer);
+    if (!sourceImage.getTexture()) {
+        ALOGW("Failed to make an EGLImage from the GraphicBuffer");
+        return false;
+    }
+    Texture sourceTexture(caches);
+    sourceTexture.wrap(sourceImage.getTexture(),
+            sourceBuffer->getWidth(), sourceBuffer->getHeight(), 0 /* total lie */);
+
+    {
+        // Draw & readback
+        renderState.setViewport(destWidth, destHeight);
+        renderState.scissor().setEnabled(false);
+        renderState.blend().syncEnabled();
+        renderState.stencil().disable();
+
+        Rect destRect(destWidth, destHeight);
+        Glop glop;
+        GlopBuilder(renderState, caches, &glop)
+                .setRoundRectClipState(nullptr)
+                .setMeshTexturedUvQuad(nullptr, Rect(0, 1, 1, 0)) // TODO: simplify with VBO
+                .setFillLayer(sourceTexture, nullptr, 1.0f, SkXfermode::kSrc_Mode,
+                        Blend::ModeOrderSwap::NoSwap)
+                .setTransform(Matrix4::identity(), TransformFlags::None)
+                .setModelViewMapUnitToRect(destRect)
+                .build();
+        Matrix4 ortho;
+        ortho.loadOrtho(destWidth, destHeight);
+        renderState.render(glop, ortho);
+
+        glReadPixels(0, 0, bitmap->width(), bitmap->height(), format,
+                type, bitmap->getPixels());
+    }
+
+    // Cleanup
+    caches.textureState().deleteTexture(texture);
+    renderState.deleteFramebuffer(fbo);
+
+    GL_CHECKPOINT(MODERATE);
+
+    return true;
+}
+
+} // namespace uirenderer
+} // namespace android
diff --git a/libs/hwui/Readback.h b/libs/hwui/Readback.h
new file mode 100644
index 0000000..ea03c82
--- /dev/null
+++ b/libs/hwui/Readback.h
@@ -0,0 +1,34 @@
+/*
+ * 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.
+ */
+
+#pragma once
+
+#include "renderthread/RenderThread.h"
+
+#include <SkBitmap.h>
+#include <gui/Surface.h>
+
+namespace android {
+namespace uirenderer {
+
+class Readback {
+public:
+    static bool copySurfaceInto(renderthread::RenderThread& renderThread,
+            Surface& surface, SkBitmap* bitmap);
+};
+
+} // namespace uirenderer
+} // namespace android
diff --git a/libs/hwui/RecordingCanvas.cpp b/libs/hwui/RecordingCanvas.cpp
index b78497d..ab733f1 100644
--- a/libs/hwui/RecordingCanvas.cpp
+++ b/libs/hwui/RecordingCanvas.cpp
@@ -57,6 +57,16 @@
     return displayList;
 }
 
+void RecordingCanvas::insertReorderBarrier(bool enableReorder) {
+    if (enableReorder) {
+        mDeferredBarrierType = DeferredBarrierType::OutOfOrder;
+        mDeferredBarrierClip = getRecordedClip();
+    } else {
+        mDeferredBarrierType = DeferredBarrierType::InOrder;
+        mDeferredBarrierClip = nullptr;
+    }
+}
+
 SkCanvas* RecordingCanvas::asSkCanvas() {
     LOG_ALWAYS_FATAL_IF(!mDisplayList,
             "attempting to get an SkCanvas when we are not recording!");
@@ -610,6 +620,7 @@
         newChunk.beginOpIndex = insertIndex;
         newChunk.endOpIndex = insertIndex + 1;
         newChunk.reorderChildren = (mDeferredBarrierType == DeferredBarrierType::OutOfOrder);
+        newChunk.reorderClip = mDeferredBarrierClip;
 
         int nextChildIndex = mDisplayList->children.size();
         newChunk.beginChildIndex = newChunk.endChildIndex = nextChildIndex;
diff --git a/libs/hwui/RecordingCanvas.h b/libs/hwui/RecordingCanvas.h
index acb88e2..219296c 100644
--- a/libs/hwui/RecordingCanvas.h
+++ b/libs/hwui/RecordingCanvas.h
@@ -55,10 +55,7 @@
 // ----------------------------------------------------------------------------
 // MISC HWUI OPERATIONS - TODO: CATEGORIZE
 // ----------------------------------------------------------------------------
-    virtual void insertReorderBarrier(bool enableReorder) override {
-        mDeferredBarrierType = enableReorder
-                ? DeferredBarrierType::OutOfOrder : DeferredBarrierType::InOrder;
-    }
+    virtual void insertReorderBarrier(bool enableReorder) override;
 
     virtual void drawLayer(DeferredLayerUpdater* layerHandle) override;
     virtual void drawRenderNode(RenderNode* renderNode) override;
@@ -312,6 +309,7 @@
     std::unique_ptr<SkiaCanvasProxy> mSkiaCanvasProxy;
     ResourceCache& mResourceCache;
     DeferredBarrierType mDeferredBarrierType = DeferredBarrierType::None;
+    const ClipBase* mDeferredBarrierClip = nullptr;
     DisplayList* mDisplayList = nullptr;
     bool mHighContrastText = false;
     SkAutoTUnref<SkDrawFilter> mDrawFilter;
diff --git a/libs/hwui/Snapshot.cpp b/libs/hwui/Snapshot.cpp
index d784280..2c9c9d9 100644
--- a/libs/hwui/Snapshot.cpp
+++ b/libs/hwui/Snapshot.cpp
@@ -242,6 +242,33 @@
 #endif
 }
 
+static Snapshot* getClipRoot(Snapshot* target) {
+    while (target->previous && target->previous->previous) {
+        target = target->previous;
+    }
+    return target;
+}
+
+const ClipBase* Snapshot::serializeIntersectedClip(LinearAllocator& allocator,
+        const ClipBase* recordedClip, const Matrix4& recordedClipTransform) {
+    auto target = this;
+    if (CC_UNLIKELY(recordedClip && recordedClip->intersectWithRoot)) {
+        // Clip must be intersected with root, instead of current clip.
+        target = getClipRoot(this);
+    }
+
+    return target->mClipArea->serializeIntersectedClip(allocator,
+            recordedClip, recordedClipTransform);
+}
+
+void Snapshot::applyClip(const ClipBase* recordedClip, const Matrix4& transform) {
+    if (CC_UNLIKELY(recordedClip && recordedClip->intersectWithRoot)) {
+        // current clip is being replaced, but must intersect with clip root
+        *mClipArea = *(getClipRoot(this)->mClipArea);
+    }
+    mClipArea->applyClip(recordedClip, transform);
+}
+
 ///////////////////////////////////////////////////////////////////////////////
 // Queries
 ///////////////////////////////////////////////////////////////////////////////
diff --git a/libs/hwui/Snapshot.h b/libs/hwui/Snapshot.h
index 3a01d04..d8f926e 100644
--- a/libs/hwui/Snapshot.h
+++ b/libs/hwui/Snapshot.h
@@ -170,6 +170,10 @@
     const ClipArea& getClipArea() const { return *mClipArea; }
     ClipArea& mutateClipArea() { return *mClipArea; }
 
+    WARN_UNUSED_RESULT const ClipBase* serializeIntersectedClip(LinearAllocator& allocator,
+            const ClipBase* recordedClip, const Matrix4& recordedClipTransform);
+    void applyClip(const ClipBase* clip, const Matrix4& transform);
+
     /**
      * Resets the clip to the specified rect.
      */
diff --git a/libs/hwui/TessellationCache.cpp b/libs/hwui/TessellationCache.cpp
index 14c8f392..cfdc084 100644
--- a/libs/hwui/TessellationCache.cpp
+++ b/libs/hwui/TessellationCache.cpp
@@ -35,13 +35,14 @@
 ///////////////////////////////////////////////////////////////////////////////
 
 TessellationCache::Description::Description()
-        : type(kNone)
+        : type(Type::None)
         , scaleX(1.0f)
         , scaleY(1.0f)
         , aa(false)
         , cap(SkPaint::kDefault_Cap)
         , style(SkPaint::kFill_Style)
         , strokeWidth(1.0f) {
+    // Shape bits should be set to zeroes, because they are used for hash calculation.
     memset(&shape, 0, sizeof(Shape));
 }
 
@@ -52,11 +53,30 @@
         , style(paint.getStyle())
         , strokeWidth(paint.getStrokeWidth()) {
     PathTessellator::extractTessellationScales(transform, &scaleX, &scaleY);
+    // Shape bits should be set to zeroes, because they are used for hash calculation.
     memset(&shape, 0, sizeof(Shape));
 }
 
+bool TessellationCache::Description::operator==(const TessellationCache::Description& rhs) const {
+    if (type != rhs.type) return false;
+    if (scaleX != rhs.scaleX) return false;
+    if (scaleY != rhs.scaleY) return false;
+    if (aa != rhs.aa) return false;
+    if (cap != rhs.cap) return false;
+    if (style != rhs.style) return false;
+    if (strokeWidth != rhs.strokeWidth) return false;
+    if (type == Type::None) return true;
+    const Shape::RoundRect& lRect = shape.roundRect;
+    const Shape::RoundRect& rRect = rhs.shape.roundRect;
+
+    if (lRect.width != rRect.width) return false;
+    if (lRect.height != rRect.height) return false;
+    if (lRect.rx != rRect.rx) return false;
+    return lRect.ry == rRect.ry;
+}
+
 hash_t TessellationCache::Description::hash() const {
-    uint32_t hash = JenkinsHashMix(0, type);
+    uint32_t hash = JenkinsHashMix(0, static_cast<int>(type));
     hash = JenkinsHashMix(hash, aa);
     hash = JenkinsHashMix(hash, cap);
     hash = JenkinsHashMix(hash, style);
@@ -77,17 +97,23 @@
 
 TessellationCache::ShadowDescription::ShadowDescription()
         : nodeKey(nullptr) {
-    memset(&matrixData, 0, 16 * sizeof(float));
+    memset(&matrixData, 0, sizeof(matrixData));
 }
 
-TessellationCache::ShadowDescription::ShadowDescription(const void* nodeKey, const Matrix4* drawTransform)
+TessellationCache::ShadowDescription::ShadowDescription(const SkPath* nodeKey, const Matrix4* drawTransform)
         : nodeKey(nodeKey) {
-    memcpy(&matrixData, drawTransform->data, 16 * sizeof(float));
+    memcpy(&matrixData, drawTransform->data, sizeof(matrixData));
+}
+
+bool TessellationCache::ShadowDescription::operator==(
+        const TessellationCache::ShadowDescription& rhs) const {
+    return nodeKey == rhs.nodeKey
+            && memcmp(&matrixData, &rhs.matrixData, sizeof(matrixData)) == 0;
 }
 
 hash_t TessellationCache::ShadowDescription::hash() const {
     uint32_t hash = JenkinsHashMixBytes(0, (uint8_t*) &nodeKey, sizeof(const void*));
-    hash = JenkinsHashMixBytes(hash, (uint8_t*) &matrixData, 16 * sizeof(float));
+    hash = JenkinsHashMixBytes(hash, (uint8_t*) &matrixData, sizeof(matrixData));
     return JenkinsHashWhiten(hash);
 }
 
@@ -428,7 +454,7 @@
 TessellationCache::Buffer* TessellationCache::getRoundRectBuffer(
         const Matrix4& transform, const SkPaint& paint,
         float width, float height, float rx, float ry) {
-    Description entry(Description::kRoundRect, transform, paint);
+    Description entry(Description::Type::RoundRect, transform, paint);
     entry.shape.roundRect.width = width;
     entry.shape.roundRect.height = height;
     entry.shape.roundRect.rx = rx;
diff --git a/libs/hwui/TessellationCache.h b/libs/hwui/TessellationCache.h
index 0bd6365..6141b4e 100644
--- a/libs/hwui/TessellationCache.h
+++ b/libs/hwui/TessellationCache.h
@@ -52,10 +52,10 @@
     typedef Pair<VertexBuffer*, VertexBuffer*> vertexBuffer_pair_t;
 
     struct Description {
-        DESCRIPTION_TYPE(Description);
-        enum Type {
-            kNone,
-            kRoundRect,
+        HASHABLE_TYPE(Description);
+        enum class Type {
+            None,
+            RoundRect,
         };
 
         Type type;
@@ -76,18 +76,16 @@
 
         Description();
         Description(Type type, const Matrix4& transform, const SkPaint& paint);
-        hash_t hash() const;
         void setupMatrixAndPaint(Matrix4* matrix, SkPaint* paint) const;
     };
 
     struct ShadowDescription {
-        DESCRIPTION_TYPE(ShadowDescription);
-        const void* nodeKey;
+        HASHABLE_TYPE(ShadowDescription);
+        const SkPath* nodeKey;
         float matrixData[16];
 
         ShadowDescription();
-        ShadowDescription(const void* nodeKey, const Matrix4* drawTransform);
-        hash_t hash() const;
+        ShadowDescription(const SkPath* nodeKey, const Matrix4* drawTransform);
     };
 
     class ShadowTask : public Task<vertexBuffer_pair_t> {
diff --git a/libs/hwui/hwui/MinikinSkia.cpp b/libs/hwui/hwui/MinikinSkia.cpp
index b9e3358..a455f57 100644
--- a/libs/hwui/hwui/MinikinSkia.cpp
+++ b/libs/hwui/hwui/MinikinSkia.cpp
@@ -22,8 +22,10 @@
 
 namespace android {
 
-MinikinFontSkia::MinikinFontSkia(SkTypeface *typeface) :
-    mTypeface(typeface) {
+MinikinFontSkia::MinikinFontSkia(SkTypeface* typeface, const void* fontData, size_t fontSize,
+        int ttcIndex) :
+    MinikinFont(typeface->uniqueID()), mTypeface(typeface), mFontData(fontData),
+    mFontSize(fontSize), mTtcIndex(ttcIndex) {
 }
 
 MinikinFontSkia::~MinikinFontSkia() {
@@ -66,24 +68,36 @@
     bounds->mBottom = skBounds.fBottom;
 }
 
-bool MinikinFontSkia::GetTable(uint32_t tag, uint8_t *buf, size_t *size) {
-    if (buf == NULL) {
-        const size_t tableSize = mTypeface->getTableSize(tag);
-        *size = tableSize;
-        return tableSize != 0;
-    } else {
-        const size_t actualSize = mTypeface->getTableData(tag, 0, *size, buf);
-        *size = actualSize;
-        return actualSize != 0;
+const void* MinikinFontSkia::GetTable(uint32_t tag, size_t* size, MinikinDestroyFunc* destroy) {
+    // we don't have a buffer to the font data, copy to own buffer
+    const size_t tableSize = mTypeface->getTableSize(tag);
+    *size = tableSize;
+    if (tableSize == 0) {
+        return nullptr;
     }
+    void* buf = malloc(tableSize);
+    if (buf == nullptr) {
+        return nullptr;
+    }
+    mTypeface->getTableData(tag, 0, tableSize, buf);
+    *destroy = free;
+    return buf;
 }
 
 SkTypeface *MinikinFontSkia::GetSkTypeface() const {
     return mTypeface;
 }
 
-int32_t MinikinFontSkia::GetUniqueId() const {
-    return mTypeface->uniqueID();
+const void* MinikinFontSkia::GetFontData() const {
+    return mFontData;
+}
+
+size_t MinikinFontSkia::GetFontSize() const {
+    return mFontSize;
+}
+
+int MinikinFontSkia::GetFontIndex() const {
+    return mTtcIndex;
 }
 
 uint32_t MinikinFontSkia::packPaintFlags(const SkPaint* paint) {
diff --git a/libs/hwui/hwui/MinikinSkia.h b/libs/hwui/hwui/MinikinSkia.h
index 1d50168..a7c9fb0 100644
--- a/libs/hwui/hwui/MinikinSkia.h
+++ b/libs/hwui/hwui/MinikinSkia.h
@@ -28,7 +28,8 @@
 class ANDROID_API MinikinFontSkia : public MinikinFont {
 public:
     // Note: this takes ownership of the reference (will unref on dtor)
-    explicit MinikinFontSkia(SkTypeface *typeface);
+    explicit MinikinFontSkia(SkTypeface *typeface, const void* fontData, size_t fontSize,
+        int ttcIndex);
 
     ~MinikinFontSkia();
 
@@ -38,20 +39,28 @@
     void GetBounds(MinikinRect* bounds, uint32_t glyph_id,
         const MinikinPaint &paint) const;
 
-    // If buf is NULL, just update size
-    bool GetTable(uint32_t tag, uint8_t *buf, size_t *size);
-
-    int32_t GetUniqueId() const;
+    const void* GetTable(uint32_t tag, size_t* size, MinikinDestroyFunc* destroy);
 
     SkTypeface* GetSkTypeface() const;
 
+    // Access to underlying raw font bytes
+    const void* GetFontData() const;
+    size_t GetFontSize() const;
+    int GetFontIndex() const;
+
     static uint32_t packPaintFlags(const SkPaint* paint);
     static void unpackPaintFlags(SkPaint* paint, uint32_t paintFlags);
 
     // set typeface and fake bold/italic parameters
     static void populateSkPaint(SkPaint* paint, const MinikinFont* font, FontFakery fakery);
 private:
-    SkTypeface *mTypeface;
+    SkTypeface* mTypeface;
+
+    // A raw pointer to the font data - it should be owned by some other object with
+    // lifetime at least as long as this object.
+    const void* mFontData;
+    size_t mFontSize;
+    int mTtcIndex;
 };
 
 }  // namespace android
diff --git a/libs/hwui/hwui/Typeface.cpp b/libs/hwui/hwui/Typeface.cpp
index fa8ad5d..c583988 100644
--- a/libs/hwui/hwui/Typeface.cpp
+++ b/libs/hwui/hwui/Typeface.cpp
@@ -66,7 +66,10 @@
         ALOGD("makeFontCollection adding %s", fn);
         SkTypeface *skFace = SkTypeface::CreateFromFile(fn);
         if (skFace != NULL) {
-            MinikinFont *font = new MinikinFontSkia(skFace);
+            // TODO: might be a nice optimization to get access to the underlying font
+            // data, but would require us opening the file ourselves and passing that
+            // to the appropriate Create method of SkTypeface.
+            MinikinFont *font = new MinikinFontSkia(skFace, NULL, 0, 0);
             family->addFont(font);
             font->Unref();
         } else {
diff --git a/libs/hwui/renderthread/RenderProxy.cpp b/libs/hwui/renderthread/RenderProxy.cpp
index 2e99d0b..096093c 100644
--- a/libs/hwui/renderthread/RenderProxy.cpp
+++ b/libs/hwui/renderthread/RenderProxy.cpp
@@ -19,6 +19,7 @@
 #include "DeferredLayerUpdater.h"
 #include "DisplayList.h"
 #include "LayerRenderer.h"
+#include "Readback.h"
 #include "Rect.h"
 #include "renderthread/CanvasContext.h"
 #include "renderthread/RenderTask.h"
@@ -52,14 +53,6 @@
     MethodInvokeRenderTask* task = new MethodInvokeRenderTask((RunnableMethod) Bridge_ ## method); \
     ARGS(method) *args = (ARGS(method) *) task->payload()
 
-namespace DumpFlags {
-    enum {
-        FrameStats = 1 << 0,
-        Reset      = 1 << 1,
-        JankStats  = 1 << 2,
-    };
-};
-
 CREATE_BRIDGE4(createContext, RenderThread* thread, bool translucent,
         RenderNode* rootRenderNode, IContextFactory* contextFactory) {
     return new CanvasContext(*args->thread, args->translucent,
@@ -425,6 +418,9 @@
     if (args->dumpFlags & DumpFlags::Reset) {
         args->context->resetFrameStats();
     }
+    if (args->dumpFlags & DumpFlags::JankStats) {
+        args->thread->jankTracker().dump(args->fd);
+    }
     return nullptr;
 }
 
@@ -609,6 +605,20 @@
     post(task);
 }
 
+CREATE_BRIDGE3(copySurfaceInto, RenderThread* thread,
+        Surface* surface, SkBitmap* bitmap) {
+    return (void*) Readback::copySurfaceInto(*args->thread,
+            *args->surface, args->bitmap);
+}
+
+bool RenderProxy::copySurfaceInto(sp<Surface>& surface, SkBitmap* bitmap) {
+    SETUP_TASK(copySurfaceInto);
+    args->bitmap = bitmap;
+    args->surface = surface.get();
+    args->thread = &RenderThread::getInstance();
+    return (bool) staticPostAndWait(task);
+}
+
 void RenderProxy::post(RenderTask* task) {
     mRenderThread.queue(task);
 }
diff --git a/libs/hwui/renderthread/RenderProxy.h b/libs/hwui/renderthread/RenderProxy.h
index 97194fe..98aace0 100644
--- a/libs/hwui/renderthread/RenderProxy.h
+++ b/libs/hwui/renderthread/RenderProxy.h
@@ -50,6 +50,14 @@
 class RenderThread;
 class RenderProxyBridge;
 
+namespace DumpFlags {
+    enum {
+        FrameStats = 1 << 0,
+        Reset      = 1 << 1,
+        JankStats  = 1 << 2,
+    };
+};
+
 /*
  * RenderProxy is strictly single threaded. All methods must be invoked on the owning
  * thread. It is important to note that RenderProxy may be deleted while it has
@@ -118,6 +126,8 @@
     ANDROID_API void removeFrameMetricsObserver(FrameMetricsObserver* observer);
     ANDROID_API long getDroppedFrameReportCount();
 
+    ANDROID_API static bool copySurfaceInto(sp<Surface>& surface, SkBitmap* bitmap);
+
 private:
     RenderThread& mRenderThread;
     CanvasContext* mContext;
diff --git a/libs/hwui/tests/macrobench/TestSceneRunner.cpp b/libs/hwui/tests/macrobench/TestSceneRunner.cpp
index cc0fdd5..c5af061 100644
--- a/libs/hwui/tests/macrobench/TestSceneRunner.cpp
+++ b/libs/hwui/tests/macrobench/TestSceneRunner.cpp
@@ -122,5 +122,5 @@
         }
     }
 
-    proxy->dumpProfileInfo(STDOUT_FILENO, 0);
+    proxy->dumpProfileInfo(STDOUT_FILENO, DumpFlags::JankStats);
 }
diff --git a/libs/hwui/tests/unit/ClipAreaTests.cpp b/libs/hwui/tests/unit/ClipAreaTests.cpp
index 822d04f..b864703 100644
--- a/libs/hwui/tests/unit/ClipAreaTests.cpp
+++ b/libs/hwui/tests/unit/ClipAreaTests.cpp
@@ -132,8 +132,7 @@
         auto serializedClip = area.serializeClip(allocator);
         ASSERT_NE(nullptr, serializedClip);
         ASSERT_EQ(ClipMode::Rectangle, serializedClip->mode);
-        auto clipRect = reinterpret_cast<const ClipRect*>(serializedClip);
-        EXPECT_EQ(Rect(200, 200), clipRect->rect);
+        EXPECT_EQ(Rect(200, 200), serializedClip->rect);
         EXPECT_EQ(serializedClip, area.serializeClip(allocator))
                 << "Requery of clip on unmodified ClipArea must return same pointer.";
     }
@@ -192,8 +191,7 @@
         auto resolvedClip = area.serializeIntersectedClip(allocator, &recordedClip, translateScale);
         ASSERT_NE(nullptr, resolvedClip);
         ASSERT_EQ(ClipMode::Rectangle, resolvedClip->mode);
-        EXPECT_EQ(Rect(100, 100, 200, 200),
-                reinterpret_cast<const ClipRect*>(resolvedClip)->rect);
+        EXPECT_EQ(Rect(100, 100, 200, 200), resolvedClip->rect);
 
         EXPECT_EQ(resolvedClip, area.serializeIntersectedClip(allocator, &recordedClip, translateScale))
                 << "Must return previous serialization, since input is same";
diff --git a/libs/hwui/tests/unit/FrameBuilderTests.cpp b/libs/hwui/tests/unit/FrameBuilderTests.cpp
index 0ea246f..209a104 100644
--- a/libs/hwui/tests/unit/FrameBuilderTests.cpp
+++ b/libs/hwui/tests/unit/FrameBuilderTests.cpp
@@ -1722,6 +1722,35 @@
     EXPECT_EQ(4, renderer.getIndex());
 }
 
+RENDERTHREAD_TEST(FrameBuilder, shadowClipping) {
+    class ShadowClippingTestRenderer : public TestRendererBase {
+    public:
+        void onShadowOp(const ShadowOp& op, const BakedOpState& state) override {
+            EXPECT_EQ(0, mIndex++);
+            EXPECT_EQ(Rect(25, 25, 75, 75), state.computedState.clipState->rect)
+                    << "Shadow must respect pre-barrier canvas clip value.";
+        }
+        void onRectOp(const RectOp& op, const BakedOpState& state) override {
+            EXPECT_EQ(1, mIndex++);
+        }
+    };
+    auto parent = TestUtils::createNode(0, 0, 100, 100,
+            [](RenderProperties& props, RecordingCanvas& canvas) {
+        // Apply a clip before the reorder barrier/shadow casting child is drawn.
+        // This clip must be applied to the shadow cast by the child.
+        canvas.clipRect(25, 25, 75, 75, SkRegion::kIntersect_Op);
+        canvas.insertReorderBarrier(true);
+        canvas.drawRenderNode(createWhiteRectShadowCaster(5.0f).get());
+    });
+
+    FrameBuilder frameBuilder(sEmptyLayerUpdateQueue, SkRect::MakeWH(100, 100), 100, 100,
+            TestUtils::createSyncedNodeList(parent),
+            (FrameBuilder::LightGeometry) {{ 100, 100, 100 }, 50}, Caches::getInstance());
+    ShadowClippingTestRenderer renderer;
+    frameBuilder.replayBakedOps<TestDispatcher>(renderer);
+    EXPECT_EQ(2, renderer.getIndex());
+}
+
 static void testProperty(std::function<void(RenderProperties&)> propSetupCallback,
         std::function<void(const RectOp&, const BakedOpState&)> opValidateCallback) {
     class PropertyTestRenderer : public TestRendererBase {
@@ -1946,5 +1975,28 @@
     EXPECT_MATRIX_APPROX_EQ(Matrix4::identity(), observedData.rectMatrix);
 }
 
+RENDERTHREAD_TEST(FrameBuilder, clip_replace) {
+    class ClipReplaceTestRenderer : public TestRendererBase {
+    public:
+        void onColorOp(const ColorOp& op, const BakedOpState& state) override {
+            EXPECT_EQ(0, mIndex++);
+            EXPECT_TRUE(op.localClip->intersectWithRoot);
+            EXPECT_EQ(Rect(20, 10, 30, 40), state.computedState.clipState->rect)
+                    << "Expect resolved clip to be intersection of viewport clip and clip op";
+        }
+    };
+    auto node = TestUtils::createNode(20, 20, 30, 30,
+            [](RenderProperties& props, RecordingCanvas& canvas) {
+        canvas.clipRect(0, -20, 10, 30, SkRegion::kReplace_Op);
+        canvas.drawColor(SK_ColorWHITE, SkXfermode::Mode::kSrcOver_Mode);
+    });
+
+    FrameBuilder frameBuilder(sEmptyLayerUpdateQueue, SkRect::MakeLTRB(10, 10, 40, 40), 50, 50,
+            TestUtils::createSyncedNodeList(node), sLightGeometry, Caches::getInstance());
+    ClipReplaceTestRenderer renderer;
+    frameBuilder.replayBakedOps<TestDispatcher>(renderer);
+    EXPECT_EQ(1, renderer.getIndex());
+}
+
 } // namespace uirenderer
 } // namespace android
diff --git a/libs/hwui/tests/unit/RecordingCanvasTests.cpp b/libs/hwui/tests/unit/RecordingCanvasTests.cpp
index 58376c6..18171de 100644
--- a/libs/hwui/tests/unit/RecordingCanvasTests.cpp
+++ b/libs/hwui/tests/unit/RecordingCanvasTests.cpp
@@ -569,6 +569,19 @@
     EXPECT_CLIP_RECT(Rect(-100, -100, 300, 300), dl->getOps()[0]->localClip);
 }
 
+TEST(RecordingCanvas, replaceClipIntersectWithRoot) {
+    auto dl = TestUtils::createDisplayList<RecordingCanvas>(100, 100, [](RecordingCanvas& canvas) {
+        canvas.save(SaveFlags::MatrixClip);
+        canvas.clipRect(-10, -10, 110, 110, SkRegion::kReplace_Op);
+        canvas.drawColor(SK_ColorWHITE, SkXfermode::Mode::kSrcOver_Mode);
+        canvas.restore();
+    });
+    ASSERT_EQ(1u, dl->getOps().size()) << "Must have one op";
+    // first clip must be preserved, even if it extends beyond canvas bounds
+    EXPECT_CLIP_RECT(Rect(-10, -10, 110, 110), dl->getOps()[0]->localClip);
+    EXPECT_TRUE(dl->getOps()[0]->localClip->intersectWithRoot);
+}
+
 TEST(RecordingCanvas, insertReorderBarrier) {
     auto dl = TestUtils::createDisplayList<RecordingCanvas>(200, 200, [](RecordingCanvas& canvas) {
         canvas.drawRect(0, 0, 400, 400, SkPaint());
@@ -590,6 +603,36 @@
     EXPECT_TRUE(chunks[1].reorderChildren);
 }
 
+TEST(RecordingCanvas, insertReorderBarrier_clip) {
+    auto dl = TestUtils::createDisplayList<RecordingCanvas>(200, 200, [](RecordingCanvas& canvas) {
+        // first chunk: no recorded clip
+        canvas.insertReorderBarrier(true);
+        canvas.drawRect(0, 0, 400, 400, SkPaint());
+
+        // second chunk: no recorded clip, since inorder region
+        canvas.clipRect(0, 0, 200, 200, SkRegion::kIntersect_Op);
+        canvas.insertReorderBarrier(false);
+        canvas.drawRect(0, 0, 400, 400, SkPaint());
+
+        // third chunk: recorded clip
+        canvas.insertReorderBarrier(true);
+        canvas.drawRect(0, 0, 400, 400, SkPaint());
+    });
+
+    auto chunks = dl->getChunks();
+    ASSERT_EQ(3u, chunks.size());
+
+    EXPECT_TRUE(chunks[0].reorderChildren);
+    EXPECT_EQ(nullptr, chunks[0].reorderClip);
+
+    EXPECT_FALSE(chunks[1].reorderChildren);
+    EXPECT_EQ(nullptr, chunks[1].reorderClip);
+
+    EXPECT_TRUE(chunks[2].reorderChildren);
+    ASSERT_NE(nullptr, chunks[2].reorderClip);
+    EXPECT_EQ(Rect(200, 200), chunks[2].reorderClip->rect);
+}
+
 TEST(RecordingCanvas, refPaint) {
     SkPaint paint;
 
diff --git a/libs/hwui/tests/unit/SnapshotTests.cpp b/libs/hwui/tests/unit/SnapshotTests.cpp
new file mode 100644
index 0000000..11797a8
--- /dev/null
+++ b/libs/hwui/tests/unit/SnapshotTests.cpp
@@ -0,0 +1,74 @@
+/*
+ * 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.
+ */
+
+#include <gtest/gtest.h>
+
+#include <Snapshot.h>
+
+#include <tests/common/TestUtils.h>
+
+using namespace android::uirenderer;
+
+TEST(Snapshot, serializeIntersectedClip) {
+    auto actualRoot = TestUtils::makeSnapshot(Matrix4::identity(), Rect(0, 0, 100, 100));
+    auto root = TestUtils::makeSnapshot(Matrix4::identity(), Rect(10, 10, 90, 90));
+    auto child = TestUtils::makeSnapshot(Matrix4::identity(), Rect(50, 50, 90, 90));
+    root->previous = actualRoot.get();
+    child->previous = root.get();
+
+    LinearAllocator allocator;
+    ClipRect rect(Rect(0, 0, 75, 75));
+    {
+        auto intersectWithChild = child->serializeIntersectedClip(allocator,
+                &rect, Matrix4::identity());
+        ASSERT_NE(nullptr, intersectWithChild);
+        EXPECT_EQ(Rect(50, 50, 75, 75), intersectWithChild->rect) << "Expect intersect with child";
+    }
+
+    rect.intersectWithRoot = true;
+    {
+        auto intersectWithRoot = child->serializeIntersectedClip(allocator,
+                &rect, Matrix4::identity());
+        ASSERT_NE(nullptr, intersectWithRoot);
+        EXPECT_EQ(Rect(10, 10, 75, 75), intersectWithRoot->rect) << "Expect intersect with root";
+    }
+}
+
+TEST(Snapshot, applyClip) {
+    auto actualRoot = TestUtils::makeSnapshot(Matrix4::identity(), Rect(0, 0, 100, 100));
+    auto root = TestUtils::makeSnapshot(Matrix4::identity(), Rect(10, 10, 90, 90));
+    root->previous = actualRoot.get();
+
+    ClipRect rect(Rect(0, 0, 75, 75));
+    {
+        auto child = TestUtils::makeSnapshot(Matrix4::identity(), Rect(50, 50, 90, 90));
+        child->previous = root.get();
+        child->applyClip(&rect, Matrix4::identity());
+
+        EXPECT_TRUE(child->getClipArea().isSimple());
+        EXPECT_EQ(Rect(50, 50, 75, 75), child->getRenderTargetClip());
+    }
+
+    {
+        rect.intersectWithRoot = true;
+        auto child = TestUtils::makeSnapshot(Matrix4::identity(), Rect(50, 50, 90, 90));
+        child->previous = root.get();
+        child->applyClip(&rect, Matrix4::identity());
+
+        EXPECT_TRUE(child->getClipArea().isSimple());
+        EXPECT_EQ(Rect(10, 10, 75, 75), child->getRenderTargetClip());
+    }
+}
diff --git a/libs/hwui/tests/unit/VectorDrawableTests.cpp b/libs/hwui/tests/unit/VectorDrawableTests.cpp
index 7208547..796169e 100644
--- a/libs/hwui/tests/unit/VectorDrawableTests.cpp
+++ b/libs/hwui/tests/unit/VectorDrawableTests.cpp
@@ -231,11 +231,12 @@
 };
 
 const StringPath sStringPaths[] = {
-    {"3e...3", false},
-    {"L.M.F.A.O", false},
-    {"m 1 1", true},
-    {"z", true},
-    {"1-2e34567", false}
+    {"3e...3", false}, // Not starting with a verb and ill-formatted float
+    {"L.M.F.A.O", false}, // No floats following verbs
+    {"m 1 1", true}, // Valid path data
+    {"z", true}, // Valid path data
+    {"1-2e34567", false}, // Not starting with a verb and ill-formatted float
+    {"f 4 5", false} // Invalid verb
 };
 
 
diff --git a/libs/hwui/utils/Macros.h b/libs/hwui/utils/Macros.h
index ccf2287..7212897b 100644
--- a/libs/hwui/utils/Macros.h
+++ b/libs/hwui/utils/Macros.h
@@ -23,12 +23,10 @@
         Type(const Type&) = delete; \
         void operator=(const Type&) = delete
 
-#define DESCRIPTION_TYPE(Type) \
-        int compare(const Type& rhs) const { return memcmp(this, &rhs, sizeof(Type));} \
-        bool operator==(const Type& other) const { return compare(other) == 0; } \
-        bool operator!=(const Type& other) const { return compare(other) != 0; } \
-        friend inline int strictly_order_type(const Type& lhs, const Type& rhs) { return lhs.compare(rhs) < 0; } \
-        friend inline int compare_type(const Type& lhs, const Type& rhs) { return lhs.compare(rhs); } \
+#define HASHABLE_TYPE(Type) \
+        bool operator==(const Type& other) const; \
+        hash_t hash() const; \
+        bool operator!=(const Type& other) const { return !(*this == other); } \
         friend inline hash_t hash_type(const Type& entry) { return entry.hash(); }
 
 #define REQUIRE_COMPATIBLE_LAYOUT(Type) \
diff --git a/location/java/android/location/GnssClock.java b/location/java/android/location/GnssClock.java
index d1b1be9..25d247d 100644
--- a/location/java/android/location/GnssClock.java
+++ b/location/java/android/location/GnssClock.java
@@ -97,7 +97,7 @@
      *
      * <p>The sign of the value is defined by the following equation:
      * <pre>
-     *     UtcTimeNanos = TimeNanos + (FullBiasNanos + BiasNanos) - LeapSecond * 1,000,000,000</pre>
+     *     UtcTimeNanos = TimeNanos - (FullBiasNanos + BiasNanos) - LeapSecond * 1,000,000,000</pre>
      *
      * <p>The value is only available if {@link #hasLeapSecond()} is {@code true}.
      */
@@ -130,9 +130,9 @@
      *
      * <p>This value is expected to be monotonically increasing while the hardware clock remains
      * powered on. For the case of a hardware clock that is not continuously on, see the
-     * {@link #getHardwareClockDiscontinuityCount} field. The GPS time can be derived by adding
-     * {@link #getFullBiasNanos()} and {@link #getBiasNanos()} (when they are available) to this
-     * value. Sub-nanosecond accuracy can be provided by means of {@link #getBiasNanos()}.
+     * {@link #getHardwareClockDiscontinuityCount} field. The GPS time can be derived by subtracting
+     * the sum of {@link #getFullBiasNanos()} and {@link #getBiasNanos()} (when they are available)
+     * from this value. Sub-nanosecond accuracy can be provided by means of {@link #getBiasNanos()}.
      *
      * <p>The error estimate for this value (if applicable) is {@link #getTimeUncertaintyNanos()}.
      */
@@ -213,7 +213,7 @@
      * <p>The sign of the value is defined by the following equation:
      *
      * <pre>
-     *     local estimate of GPS time = TimeNanos + (FullBiasNanos + BiasNanos)</pre>
+     *     local estimate of GPS time = TimeNanos - (FullBiasNanos + BiasNanos)</pre>
      */
     public long getFullBiasNanos() {
         return mFullBiasNanos;
diff --git a/media/java/android/media/AudioRecord.java b/media/java/android/media/AudioRecord.java
index ca306cc..a5550ec 100644
--- a/media/java/android/media/AudioRecord.java
+++ b/media/java/android/media/AudioRecord.java
@@ -37,6 +37,8 @@
 import android.util.ArrayMap;
 import android.util.Log;
 
+import com.android.internal.annotations.GuardedBy;
+
 /**
  * The AudioRecord class manages the audio resources for Java applications
  * to record audio from the audio input hardware of the platform. This is
@@ -1320,6 +1322,7 @@
      * Note: The query is only valid if the AudioRecord is currently recording. If it is not,
      * <code>getRoutedDevice()</code> will return null.
      */
+    @Override
     public AudioDeviceInfo getRoutedDevice() {
         int deviceId = native_getRoutedDeviceId();
         if (deviceId == 0) {
@@ -1338,8 +1341,8 @@
     /*
      * Call BEFORE adding a routing callback handler.
      */
-    private void testEnableNativeRoutingCallbacks() {
-        if (mRoutingChangeListeners.size() == 0 && mNewRoutingChangeListeners.size() == 0) {
+    private void testEnableNativeRoutingCallbacksLocked() {
+        if (mRoutingChangeListeners.size() == 0) {
             native_enableDeviceCallback();
         }
     }
@@ -1347,24 +1350,23 @@
     /*
      * Call AFTER removing a routing callback handler.
      */
-    private void testDisableNativeRoutingCallbacks() {
-        if (mRoutingChangeListeners.size() == 0 && mNewRoutingChangeListeners.size() == 0) {
+    private void testDisableNativeRoutingCallbacksLocked() {
+        if (mRoutingChangeListeners.size() == 0) {
             native_disableDeviceCallback();
         }
     }
 
     //--------------------------------------------------------------------------
-    // >= "N" (Re)Routing Info
+    // (Re)Routing Info
     //--------------------
     /**
      * The list of AudioRouting.OnRoutingChangedListener interfaces added (with
-     * {@link AudioRecord#addOnRoutingListener(AudioRouting.OnRoutingChangedListener,
-     *      android.os.Handler)}
-     * by an app to receive (re)routing notifications.
+     * {@link AudioRecord#addOnRoutingChangedListener} by an app to receive
+     * (re)routing notifications.
      */
-    private ArrayMap<AudioRouting.OnRoutingChangedListener, NativeNewRoutingEventHandlerDelegate>
-    mNewRoutingChangeListeners =
-        new ArrayMap<AudioRouting.OnRoutingChangedListener, NativeNewRoutingEventHandlerDelegate>();
+    @GuardedBy("mRoutingChangeListeners")
+    private ArrayMap<AudioRouting.OnRoutingChangedListener,
+            NativeRoutingEventHandlerDelegate> mRoutingChangeListeners = new ArrayMap<>();
 
     /**
      * Adds an {@link AudioRouting.OnRoutingChangedListener} to receive notifications of
@@ -1375,14 +1377,15 @@
      * the callback. If <code>null</code>, the {@link Handler} associated with the main
      * {@link Looper} will be used.
      */
-    public void addOnRoutingListener(AudioRouting.OnRoutingChangedListener listener,
+    @Override
+    public void addOnRoutingChangedListener(AudioRouting.OnRoutingChangedListener listener,
             android.os.Handler handler) {
-        if (listener != null && !mNewRoutingChangeListeners.containsKey(listener)) {
-            synchronized (mNewRoutingChangeListeners) {
-                testEnableNativeRoutingCallbacks();
-                mNewRoutingChangeListeners.put(
-                    listener, new NativeNewRoutingEventHandlerDelegate(this, listener,
-                            handler != null ? handler : new Handler(mInitializationLooper)));
+        synchronized (mRoutingChangeListeners) {
+            if (listener != null && !mRoutingChangeListeners.containsKey(listener)) {
+                testEnableNativeRoutingCallbacksLocked();
+                mRoutingChangeListeners.put(
+                        listener, new NativeRoutingEventHandlerDelegate(this, listener,
+                                handler != null ? handler : new Handler(mInitializationLooper)));
             }
         }
     }
@@ -1393,39 +1396,42 @@
     * @param listener The previously added {@link AudioRouting.OnRoutingChangedListener} interface
     * to remove.
     */
-    public void removeOnRoutingListener(AudioRouting.OnRoutingChangedListener listener) {
-        synchronized (mNewRoutingChangeListeners) {
-            if (mNewRoutingChangeListeners.containsKey(listener)) {
-                mNewRoutingChangeListeners.remove(listener);
-                testDisableNativeRoutingCallbacks();
+    @Override
+    public void removeOnRoutingChangedListener(AudioRouting.OnRoutingChangedListener listener) {
+        synchronized (mRoutingChangeListeners) {
+            if (mRoutingChangeListeners.containsKey(listener)) {
+                mRoutingChangeListeners.remove(listener);
+                testDisableNativeRoutingCallbacksLocked();
             }
         }
     }
 
     //--------------------------------------------------------------------------
-    // Marshmallow (Re)Routing Info
+    // (Re)Routing Info
     //--------------------
     /**
-     * Defines the interface by which applications can receive notifications of routing
-     * changes for the associated {@link AudioRecord}.
+     * Defines the interface by which applications can receive notifications of
+     * routing changes for the associated {@link AudioRecord}.
+     *
+     * @deprecated users should switch to the general purpose
+     *             {@link AudioRouting.OnRoutingChangedListener} class instead.
      */
-    public interface OnRoutingChangedListener {
+    @Deprecated
+    public interface OnRoutingChangedListener extends AudioRouting.OnRoutingChangedListener {
         /**
-         * Called when the routing of an AudioRecord changes from either and explicit or
-         * policy rerouting. Use {@link #getRoutedDevice()} to retrieve the newly routed-from
-         * device.
+         * Called when the routing of an AudioRecord changes from either and
+         * explicit or policy rerouting. Use {@link #getRoutedDevice()} to
+         * retrieve the newly routed-from device.
          */
         public void onRoutingChanged(AudioRecord audioRecord);
-    }
 
-    /**
-     * The list of AudioRecord.OnRoutingChangedListener interface added (with
-     * {@link AudioRecord#addOnRoutingChangedListener(OnRoutingChangedListener,android.os.Handler)}
-     * by an app to receive (re)routing notifications.
-     */
-    private ArrayMap<OnRoutingChangedListener, NativeRoutingEventHandlerDelegate>
-        mRoutingChangeListeners =
-            new ArrayMap<OnRoutingChangedListener, NativeRoutingEventHandlerDelegate>();
+        @Override
+        default public void onRoutingChanged(AudioRouting router) {
+            if (router instanceof AudioRecord) {
+                onRoutingChanged((AudioRecord) router);
+            }
+        }
+    }
 
     /**
      * Adds an {@link OnRoutingChangedListener} to receive notifications of routing changes
@@ -1435,88 +1441,28 @@
      * @param handler  Specifies the {@link Handler} object for the thread on which to execute
      * the callback. If <code>null</code>, the {@link Handler} associated with the main
      * {@link Looper} will be used.
+     * @deprecated users should switch to the general purpose
+     *             {@link AudioRouting.OnRoutingChangedListener} class instead.
      */
     @Deprecated
     public void addOnRoutingChangedListener(OnRoutingChangedListener listener,
             android.os.Handler handler) {
-        if (listener != null && !mRoutingChangeListeners.containsKey(listener)) {
-            synchronized (mRoutingChangeListeners) {
-                testEnableNativeRoutingCallbacks();
-                mRoutingChangeListeners.put(
-                    listener, new NativeRoutingEventHandlerDelegate(this, listener,
-                            handler != null ? handler : new Handler(mInitializationLooper)));
-            }
-        }
+        addOnRoutingChangedListener((AudioRouting.OnRoutingChangedListener) listener, handler);
     }
 
     /**
       * Removes an {@link OnRoutingChangedListener} which has been previously added
      * to receive rerouting notifications.
      * @param listener The previously added {@link OnRoutingChangedListener} interface to remove.
+     * @deprecated users should switch to the general purpose
+     *             {@link AudioRouting.OnRoutingChangedListener} class instead.
      */
     @Deprecated
     public void removeOnRoutingChangedListener(OnRoutingChangedListener listener) {
-        synchronized (mRoutingChangeListeners) {
-            if (mRoutingChangeListeners.containsKey(listener)) {
-                mRoutingChangeListeners.remove(listener);
-                testDisableNativeRoutingCallbacks();
-            }
-        }
+        removeOnRoutingChangedListener((AudioRouting.OnRoutingChangedListener) listener);
     }
 
     /**
-     * >= "N" Routing
-     * Helper class to handle the forwarding of native events to the appropriate listener
-     * (potentially) handled in a different thread
-     */
-    private class NativeNewRoutingEventHandlerDelegate {
-        private final Handler mHandler;
-
-        NativeNewRoutingEventHandlerDelegate(final AudioRecord record,
-                                   final AudioRouting.OnRoutingChangedListener listener,
-                                   Handler handler) {
-            // find the looper for our new event handler
-            Looper looper;
-            if (handler != null) {
-                looper = handler.getLooper();
-            } else {
-                // no given handler, use the looper the AudioRecord was created in
-                looper = mInitializationLooper;
-            }
-
-            // construct the event handler with this looper
-            if (looper != null) {
-                // implement the event handler delegate
-                mHandler = new Handler(looper) {
-                    @Override
-                    public void handleMessage(Message msg) {
-                        if (record == null) {
-                            return;
-                        }
-                        switch(msg.what) {
-                        case AudioSystem.NATIVE_EVENT_ROUTING_CHANGE:
-                            if (listener != null) {
-                                listener.onRoutingChanged(record);
-                            }
-                            break;
-                        default:
-                            loge("Unknown native event type: " + msg.what);
-                            break;
-                        }
-                    }
-                };
-            } else {
-                mHandler = null;
-            }
-        }
-
-        Handler getHandler() {
-            return mHandler;
-        }
-    }
-
-    /**
-     * Marshmallow Routing
      * Helper class to handle the forwarding of native events to the appropriate listener
      * (potentially) handled in a different thread
      */
@@ -1524,7 +1470,7 @@
         private final Handler mHandler;
 
         NativeRoutingEventHandlerDelegate(final AudioRecord record,
-                                   final OnRoutingChangedListener listener,
+                                   final AudioRouting.OnRoutingChangedListener listener,
                                    Handler handler) {
             // find the looper for our new event handler
             Looper looper;
@@ -1571,26 +1517,12 @@
      */
     private void broadcastRoutingChange() {
         AudioManager.resetAudioPortGeneration();
-        // Marshmallow Routing
-        Collection<NativeRoutingEventHandlerDelegate> values;
         synchronized (mRoutingChangeListeners) {
-            values = mRoutingChangeListeners.values();
-        }
-        for(NativeRoutingEventHandlerDelegate delegate : values) {
-            Handler handler = delegate.getHandler();
-            if (handler != null) {
-                handler.sendEmptyMessage(AudioSystem.NATIVE_EVENT_ROUTING_CHANGE);
-            }
-        }
-        // >= "N" Routing
-        Collection<NativeNewRoutingEventHandlerDelegate> newValues;
-        synchronized (mNewRoutingChangeListeners) {
-            newValues = mNewRoutingChangeListeners.values();
-        }
-        for(NativeNewRoutingEventHandlerDelegate delegate : newValues) {
-            Handler handler = delegate.getHandler();
-            if (handler != null) {
-                handler.sendEmptyMessage(AudioSystem.NATIVE_EVENT_ROUTING_CHANGE);
+            for (NativeRoutingEventHandlerDelegate delegate : mRoutingChangeListeners.values()) {
+                Handler handler = delegate.getHandler();
+                if (handler != null) {
+                    handler.sendEmptyMessage(AudioSystem.NATIVE_EVENT_ROUTING_CHANGE);
+                }
             }
         }
     }
@@ -1623,6 +1555,7 @@
      * @return true if successful, false if the specified {@link AudioDeviceInfo} is non-null and
      * does not correspond to a valid audio input device.
      */
+    @Override
     public boolean setPreferredDevice(AudioDeviceInfo deviceInfo) {
         // Do some validation....
         if (deviceInfo != null && !deviceInfo.isSource()) {
@@ -1643,6 +1576,7 @@
      * Returns the selected input specified by {@link #setPreferredDevice}. Note that this
      * is not guarenteed to correspond to the actual device being used for recording.
      */
+    @Override
     public AudioDeviceInfo getPreferredDevice() {
         synchronized (this) {
             return mPreferredDevice;
@@ -1683,7 +1617,6 @@
      * (potentially) handled in a different thread
      */
     private class NativeEventHandler extends Handler {
-
         private final AudioRecord mAudioRecord;
 
         NativeEventHandler(AudioRecord recorder, Looper looper) {
@@ -1714,8 +1647,7 @@
                 break;
             }
         }
-    };
-
+    }
 
     //---------------------------------------------------------
     // Java methods called from the native side
diff --git a/media/java/android/media/AudioRouting.java b/media/java/android/media/AudioRouting.java
index 41f92d4..26fa631 100644
--- a/media/java/android/media/AudioRouting.java
+++ b/media/java/android/media/AudioRouting.java
@@ -57,7 +57,7 @@
      * the callback. If <code>null</code>, the {@link Handler} associated with the main
      * {@link Looper} will be used.
      */
-    public void addOnRoutingListener(OnRoutingChangedListener listener,
+    public void addOnRoutingChangedListener(OnRoutingChangedListener listener,
             Handler handler);
 
     /**
@@ -66,7 +66,7 @@
      * @param listener The previously added {@link AudioRouting.OnRoutingChangedListener} interface
      * to remove.
      */
-    public void removeOnRoutingListener(OnRoutingChangedListener listener);
+    public void removeOnRoutingChangedListener(OnRoutingChangedListener listener);
 
     /**
      * Defines the interface by which applications can receive notifications of routing
diff --git a/media/java/android/media/AudioTrack.java b/media/java/android/media/AudioTrack.java
index 621129d..9d360db 100644
--- a/media/java/android/media/AudioTrack.java
+++ b/media/java/android/media/AudioTrack.java
@@ -40,6 +40,7 @@
 import android.util.ArrayMap;
 import android.util.Log;
 
+import com.android.internal.annotations.GuardedBy;
 import com.android.internal.app.IAppOpsService;
 
 /**
@@ -1489,6 +1490,7 @@
      * @deprecated Applications should use {@link #setVolume} instead, as it
      * more gracefully scales down to mono, and up to multi-channel content beyond stereo.
      */
+    @Deprecated
     public int setStereoVolume(float leftGain, float rightGain) {
         if (isRestricted()) {
             return SUCCESS;
@@ -2397,6 +2399,7 @@
      * @return true if succesful, false if the specified {@link AudioDeviceInfo} is non-null and
      * does not correspond to a valid audio output device.
      */
+    @Override
     public boolean setPreferredDevice(AudioDeviceInfo deviceInfo) {
         // Do some validation....
         if (deviceInfo != null && !deviceInfo.isSink()) {
@@ -2416,6 +2419,7 @@
      * Returns the selected output specified by {@link #setPreferredDevice}. Note that this
      * is not guaranteed to correspond to the actual device being used for playback.
      */
+    @Override
     public AudioDeviceInfo getPreferredDevice() {
         synchronized (this) {
             return mPreferredDevice;
@@ -2427,6 +2431,7 @@
      * Note: The query is only valid if the AudioTrack is currently playing. If it is not,
      * <code>getRoutedDevice()</code> will return null.
      */
+    @Override
     public AudioDeviceInfo getRoutedDevice() {
         int deviceId = native_getRoutedDeviceId();
         if (deviceId == 0) {
@@ -2445,8 +2450,8 @@
     /*
      * Call BEFORE adding a routing callback handler.
      */
-    private void testEnableNativeRoutingCallbacks() {
-        if (mRoutingChangeListeners.size() == 0 && mNewRoutingChangeListeners.size() == 0) {
+    private void testEnableNativeRoutingCallbacksLocked() {
+        if (mRoutingChangeListeners.size() == 0) {
             native_enableDeviceCallback();
         }
     }
@@ -2454,24 +2459,23 @@
     /*
      * Call AFTER removing a routing callback handler.
      */
-    private void testDisableNativeRoutingCallbacks() {
-        if (mRoutingChangeListeners.size() == 0 && mNewRoutingChangeListeners.size() == 0) {
+    private void testDisableNativeRoutingCallbacksLocked() {
+        if (mRoutingChangeListeners.size() == 0) {
             native_disableDeviceCallback();
         }
     }
 
     //--------------------------------------------------------------------------
-    // >= "N" (Re)Routing Info
+    // (Re)Routing Info
     //--------------------
     /**
      * The list of AudioRouting.OnRoutingChangedListener interfaces added (with
-     * {@link AudioTrack#addOnRoutingListener(AudioRouting.OnRoutingChangedListener,
-     *          android.os.Handler)}
-     * by an app to receive (re)routing notifications.
+     * {@link AudioRecord#addOnRoutingChangedListener} by an app to receive
+     * (re)routing notifications.
      */
-   private ArrayMap<AudioRouting.OnRoutingChangedListener, NativeNewRoutingEventHandlerDelegate>
-    mNewRoutingChangeListeners =
-        new ArrayMap<AudioRouting.OnRoutingChangedListener, NativeNewRoutingEventHandlerDelegate>();
+    @GuardedBy("mRoutingChangeListeners")
+    private ArrayMap<AudioRouting.OnRoutingChangedListener,
+            NativeRoutingEventHandlerDelegate> mRoutingChangeListeners = new ArrayMap<>();
 
    /**
     * Adds an {@link AudioRouting.OnRoutingChangedListener} to receive notifications of routing
@@ -2482,14 +2486,15 @@
     * the callback. If <code>null</code>, the {@link Handler} associated with the main
     * {@link Looper} will be used.
     */
-    public void addOnRoutingListener(AudioRouting.OnRoutingChangedListener listener,
+    @Override
+    public void addOnRoutingChangedListener(AudioRouting.OnRoutingChangedListener listener,
             Handler handler) {
-        if (listener != null && !mNewRoutingChangeListeners.containsKey(listener)) {
-            synchronized (mNewRoutingChangeListeners) {
-                testEnableNativeRoutingCallbacks();
-                mNewRoutingChangeListeners.put(
-                    listener, new NativeNewRoutingEventHandlerDelegate(this, listener,
-                            handler != null ? handler : new Handler(mInitializationLooper)));
+        synchronized (mRoutingChangeListeners) {
+            if (listener != null && !mRoutingChangeListeners.containsKey(listener)) {
+                testEnableNativeRoutingCallbacksLocked();
+                mRoutingChangeListeners.put(
+                        listener, new NativeRoutingEventHandlerDelegate(this, listener,
+                                handler != null ? handler : new Handler(mInitializationLooper)));
             }
         }
     }
@@ -2500,39 +2505,42 @@
      * @param listener The previously added {@link AudioRouting.OnRoutingChangedListener} interface
      * to remove.
      */
-    public void removeOnRoutingListener(AudioRouting.OnRoutingChangedListener listener) {
-        if (mNewRoutingChangeListeners.containsKey(listener)) {
-            mNewRoutingChangeListeners.remove(listener);
+    @Override
+    public void removeOnRoutingChangedListener(AudioRouting.OnRoutingChangedListener listener) {
+        synchronized (mRoutingChangeListeners) {
+            if (mRoutingChangeListeners.containsKey(listener)) {
+                mRoutingChangeListeners.remove(listener);
+            }
+            testDisableNativeRoutingCallbacksLocked();
         }
-        testDisableNativeRoutingCallbacks();
     }
 
     //--------------------------------------------------------------------------
-    // Marshmallow (Re)Routing Info
+    // (Re)Routing Info
     //--------------------
     /**
-     * Defines the interface by which applications can receive notifications of routing
-     * changes for the associated {@link AudioTrack}.
+     * Defines the interface by which applications can receive notifications of
+     * routing changes for the associated {@link AudioTrack}.
+     *
+     * @deprecated users should switch to the general purpose
+     *             {@link AudioRouting.OnRoutingChangedListener} class instead.
      */
     @Deprecated
-    public interface OnRoutingChangedListener {
+    public interface OnRoutingChangedListener extends AudioRouting.OnRoutingChangedListener {
         /**
-         * Called when the routing of an AudioTrack changes from either and explicit or
-         * policy rerouting.  Use {@link #getRoutedDevice()} to retrieve the newly routed-to
-         * device.
+         * Called when the routing of an AudioTrack changes from either and
+         * explicit or policy rerouting. Use {@link #getRoutedDevice()} to
+         * retrieve the newly routed-to device.
          */
-        @Deprecated
         public void onRoutingChanged(AudioTrack audioTrack);
-    }
 
-    /**
-     * The list of AudioTrack.OnRoutingChangedListener interfaces added (with
-     * {@link AudioTrack#addOnRoutingChangedListener(OnRoutingChangedListener, android.os.Handler)}
-     * by an app to receive (re)routing notifications.
-     */
-    private ArrayMap<OnRoutingChangedListener, NativeRoutingEventHandlerDelegate>
-        mRoutingChangeListeners =
-            new ArrayMap<OnRoutingChangedListener, NativeRoutingEventHandlerDelegate>();
+        @Override
+        default public void onRoutingChanged(AudioRouting router) {
+            if (router instanceof AudioTrack) {
+                onRoutingChanged((AudioTrack) router);
+            }
+        }
+    }
 
     /**
      * Adds an {@link OnRoutingChangedListener} to receive notifications of routing changes
@@ -2542,33 +2550,25 @@
      * @param handler  Specifies the {@link Handler} object for the thread on which to execute
      * the callback. If <code>null</code>, the {@link Handler} associated with the main
      * {@link Looper} will be used.
+     * @deprecated users should switch to the general purpose
+     *             {@link AudioRouting.OnRoutingChangedListener} class instead.
      */
     @Deprecated
     public void addOnRoutingChangedListener(OnRoutingChangedListener listener,
             android.os.Handler handler) {
-        if (listener != null && !mRoutingChangeListeners.containsKey(listener)) {
-            synchronized (mRoutingChangeListeners) {
-                testEnableNativeRoutingCallbacks();
-                mRoutingChangeListeners.put(
-                    listener, new NativeRoutingEventHandlerDelegate(this, listener,
-                            handler != null ? handler : new Handler(mInitializationLooper)));
-            }
-        }
+        addOnRoutingChangedListener((AudioRouting.OnRoutingChangedListener) listener, handler);
     }
 
     /**
      * Removes an {@link OnRoutingChangedListener} which has been previously added
      * to receive rerouting notifications.
      * @param listener The previously added {@link OnRoutingChangedListener} interface to remove.
+     * @deprecated users should switch to the general purpose
+     *             {@link AudioRouting.OnRoutingChangedListener} class instead.
      */
     @Deprecated
     public void removeOnRoutingChangedListener(OnRoutingChangedListener listener) {
-        synchronized (mRoutingChangeListeners) {
-            if (mRoutingChangeListeners.containsKey(listener)) {
-                mRoutingChangeListeners.remove(listener);
-            }
-            testDisableNativeRoutingCallbacks();
-        }
+        removeOnRoutingChangedListener((AudioRouting.OnRoutingChangedListener) listener);
     }
 
     /**
@@ -2576,27 +2576,12 @@
      */
     private void broadcastRoutingChange() {
         AudioManager.resetAudioPortGeneration();
-
-        // Marshmallow Routing
-        Collection<NativeRoutingEventHandlerDelegate> values;
         synchronized (mRoutingChangeListeners) {
-            values = mRoutingChangeListeners.values();
-        }
-        for(NativeRoutingEventHandlerDelegate delegate : values) {
-            Handler handler = delegate.getHandler();
-            if (handler != null) {
-                handler.sendEmptyMessage(AudioSystem.NATIVE_EVENT_ROUTING_CHANGE);
-            }
-        }
-        // >= "N" Routing
-        Collection<NativeNewRoutingEventHandlerDelegate> newValues;
-        synchronized (mNewRoutingChangeListeners) {
-            newValues = mNewRoutingChangeListeners.values();
-        }
-        for(NativeNewRoutingEventHandlerDelegate delegate : newValues) {
-            Handler handler = delegate.getHandler();
-            if (handler != null) {
-                handler.sendEmptyMessage(AudioSystem.NATIVE_EVENT_ROUTING_CHANGE);
+            for (NativeRoutingEventHandlerDelegate delegate : mRoutingChangeListeners.values()) {
+                Handler handler = delegate.getHandler();
+                if (handler != null) {
+                    handler.sendEmptyMessage(AudioSystem.NATIVE_EVENT_ROUTING_CHANGE);
+                }
             }
         }
     }
@@ -2681,7 +2666,6 @@
     }
 
     /**
-     * Marshmallow Routing API.
      * Helper class to handle the forwarding of native events to the appropriate listener
      * (potentially) handled in a different thread
      */
@@ -2689,57 +2673,6 @@
         private final Handler mHandler;
 
         NativeRoutingEventHandlerDelegate(final AudioTrack track,
-                                   final OnRoutingChangedListener listener,
-                                   Handler handler) {
-            // find the looper for our new event handler
-            Looper looper;
-            if (handler != null) {
-                looper = handler.getLooper();
-            } else {
-                // no given handler, use the looper the AudioTrack was created in
-                looper = mInitializationLooper;
-            }
-
-            // construct the event handler with this looper
-            if (looper != null) {
-                // implement the event handler delegate
-                mHandler = new Handler(looper) {
-                    @Override
-                    public void handleMessage(Message msg) {
-                        if (track == null) {
-                            return;
-                        }
-                        switch(msg.what) {
-                        case AudioSystem.NATIVE_EVENT_ROUTING_CHANGE:
-                            if (listener != null) {
-                                listener.onRoutingChanged(track);
-                            }
-                            break;
-                        default:
-                            loge("Unknown native event type: " + msg.what);
-                            break;
-                        }
-                    }
-                };
-            } else {
-                mHandler = null;
-            }
-        }
-
-        Handler getHandler() {
-            return mHandler;
-        }
-    }
-
-    /**
-     * Marshmallow Routing API.
-     * Helper class to handle the forwarding of native events to the appropriate listener
-     * (potentially) handled in a different thread
-     */
-    private class NativeNewRoutingEventHandlerDelegate {
-        private final Handler mHandler;
-
-        NativeNewRoutingEventHandlerDelegate(final AudioTrack track,
                                    final AudioRouting.OnRoutingChangedListener listener,
                                    Handler handler) {
             // find the looper for our new event handler
diff --git a/media/java/android/media/ExifInterface.java b/media/java/android/media/ExifInterface.java
index 3d7e744..72f5742 100644
--- a/media/java/android/media/ExifInterface.java
+++ b/media/java/android/media/ExifInterface.java
@@ -697,7 +697,8 @@
 
     /**
      * Reads Exif tags from the specified image file descriptor. Attribute mutation is supported
-     * for writable and seekable file descriptors only.
+     * for writable and seekable file descriptors only. This constructor will not rewind the offset
+     * of the given file descriptor. Developers should close the file descriptor after use.
      */
     public ExifInterface(FileDescriptor fileDescriptor) throws IOException {
         if (fileDescriptor == null) {
@@ -730,7 +731,8 @@
 
     /**
      * Reads Exif tags from the specified image input stream. Attribute mutation is not supported
-     * for input streams.
+     * for input streams. The given input stream will proceed its current position. Developers
+     * should close the input stream after use.
      */
     public ExifInterface(InputStream inputStream) throws IOException {
         if (inputStream == null) {
diff --git a/media/java/android/media/MediaCodecInfo.java b/media/java/android/media/MediaCodecInfo.java
index 2bd9781..7af9c24 100644
--- a/media/java/android/media/MediaCodecInfo.java
+++ b/media/java/android/media/MediaCodecInfo.java
@@ -2611,10 +2611,13 @@
         public static final int VP8ProfileMain = 0x01;
 
         // from OMX_VIDEO_VP9PROFILETYPE
-        public static final int VP9Profile0 = 0x00;
-        public static final int VP9Profile1 = 0x01;
-        public static final int VP9Profile2 = 0x02;
-        public static final int VP9Profile3 = 0x03;
+        public static final int VP9Profile0 = 0x01;
+        public static final int VP9Profile1 = 0x02;
+        public static final int VP9Profile2 = 0x04;
+        public static final int VP9Profile3 = 0x08;
+        // HDR profiles also support passing HDR metadata
+        public static final int VP9Profile2HDR = 0x1000;
+        public static final int VP9Profile3HDR = 0x2000;
 
         // from OMX_VIDEO_VP9LEVELTYPE
         public static final int VP9Level1  = 0x0;
diff --git a/media/java/android/media/MediaPlayer.java b/media/java/android/media/MediaPlayer.java
index b78869e..55d5f42 100644
--- a/media/java/android/media/MediaPlayer.java
+++ b/media/java/android/media/MediaPlayer.java
@@ -1107,6 +1107,9 @@
      * as this call returns.
      *
      * @param afd the AssetFileDescriptor for the file you want to play
+     * @throws IllegalStateException if it is called in an invalid state
+     * @throws IllegalArgumentException if afd is not a valid AssetFileDescriptor
+     * @throws IOException if afd can not be read
      */
     public void setDataSource(@NonNull AssetFileDescriptor afd)
             throws IOException, IllegalArgumentException, IllegalStateException {
@@ -1127,6 +1130,8 @@
      *
      * @param fd the FileDescriptor for the file you want to play
      * @throws IllegalStateException if it is called in an invalid state
+     * @throws IllegalArgumentException if fd is not a valid FileDescriptor
+     * @throws IOException if fd can not be read
      */
     public void setDataSource(FileDescriptor fd)
             throws IOException, IllegalArgumentException, IllegalStateException {
@@ -1143,6 +1148,8 @@
      * @param offset the offset into the file where the data to be played starts, in bytes
      * @param length the length in bytes of the data to be played
      * @throws IllegalStateException if it is called in an invalid state
+     * @throws IllegalArgumentException if fd is not a valid FileDescriptor
+     * @throws IOException if fd can not be read
      */
     public void setDataSource(FileDescriptor fd, long offset, long length)
             throws IOException, IllegalArgumentException, IllegalStateException {
@@ -1157,6 +1164,7 @@
      *
      * @param dataSource the MediaDataSource for the media you want to play
      * @throws IllegalStateException if it is called in an invalid state
+     * @throws IllegalArgumentException if dataSource is not a valid MediaDataSource
      */
     public void setDataSource(MediaDataSource dataSource)
             throws IllegalArgumentException, IllegalStateException {
diff --git a/media/java/android/media/tv/TvTrackInfo.java b/media/java/android/media/tv/TvTrackInfo.java
index e623353..d718a7e 100644
--- a/media/java/android/media/tv/TvTrackInfo.java
+++ b/media/java/android/media/tv/TvTrackInfo.java
@@ -20,9 +20,12 @@
 import android.os.Bundle;
 import android.os.Parcel;
 import android.os.Parcelable;
+import android.text.TextUtils;
 
 import com.android.internal.util.Preconditions;
 
+import java.util.Objects;
+
 /**
  * Encapsulates the format of tracks played in {@link TvInputService}.
  */
@@ -245,6 +248,37 @@
         dest.writeBundle(mExtra);
     }
 
+    @Override
+    public boolean equals(Object o) {
+        if (this == o) {
+          return true;
+        }
+
+        if (!(o instanceof TvTrackInfo)) {
+          return false;
+        }
+
+        TvTrackInfo obj = (TvTrackInfo) o;
+        return TextUtils.equals(mId, obj.mId)
+                && mType == obj.mType
+                && TextUtils.equals(mLanguage, obj.mLanguage)
+                && TextUtils.equals(mDescription, obj.mDescription)
+                && Objects.equals(mExtra, obj.mExtra)
+                && (mType == TYPE_AUDIO
+                        ? mAudioChannelCount == obj.mAudioChannelCount
+                        && mAudioSampleRate == obj.mAudioSampleRate
+                        : (mType == TYPE_VIDEO
+                                ? mVideoWidth == obj.mVideoWidth
+                                && mVideoHeight == obj.mVideoHeight
+                                && mVideoFrameRate == obj.mVideoFrameRate
+                                && mVideoPixelAspectRatio == obj.mVideoPixelAspectRatio : true));
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hashCode(mId);
+    }
+
     public static final Parcelable.Creator<TvTrackInfo> CREATOR =
             new Parcelable.Creator<TvTrackInfo>() {
                 @Override
diff --git a/media/java/android/mtp/MtpServer.java b/media/java/android/mtp/MtpServer.java
index 3814630..61fbfb9 100644
--- a/media/java/android/mtp/MtpServer.java
+++ b/media/java/android/mtp/MtpServer.java
@@ -23,12 +23,14 @@
 public class MtpServer implements Runnable {
 
     private long mNativeContext; // accessed by native methods
+    private final MtpDatabase mDatabase;
 
     static {
         System.loadLibrary("media_jni");
     }
 
     public MtpServer(MtpDatabase database, boolean usePtp) {
+        mDatabase = database;
         native_setup(database, usePtp);
         database.setServer(this);
     }
@@ -42,6 +44,7 @@
     public void run() {
         native_run();
         native_cleanup();
+        mDatabase.close();
     }
 
     public void sendObjectAdded(int handle) {
diff --git a/packages/DocumentsUI/res/color/item_root_icon.xml b/packages/DocumentsUI/res/color/item_root_icon.xml
index 0aa2c13..e1d7e61 100644
--- a/packages/DocumentsUI/res/color/item_root_icon.xml
+++ b/packages/DocumentsUI/res/color/item_root_icon.xml
@@ -15,5 +15,10 @@
 -->
 
 <selector xmlns:android="http://schemas.android.com/apk/res/android">
-    <item android:color="@*android:color/secondary_text_material_light" />
+    <item
+        android:state_activated="false"
+        android:color="@*android:color/secondary_text_material_light" />
+    <item
+        android:state_activated="true"
+        android:color="@color/root_activated_color" />
 </selector>
diff --git a/packages/DocumentsUI/res/values-af/strings.xml b/packages/DocumentsUI/res/values-af/strings.xml
index 1a7c620..27c4bbc 100644
--- a/packages/DocumentsUI/res/values-af/strings.xml
+++ b/packages/DocumentsUI/res/values-af/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumente"</string>
-    <string name="files_label" msgid="6051402950202690279">"Lêers"</string>
     <string name="downloads_label" msgid="959113951084633612">"Aflaaie"</string>
     <string name="title_open" msgid="4353228937663917801">"Maak oop vanuit"</string>
     <string name="title_save" msgid="2433679664882857999">"Stoor na"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> gekies</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> gekies</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> items</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Vee \"<xliff:g id="NAME">%1$s</xliff:g>\" uit?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Vee vouer \"<xliff:g id="NAME">%1$s</xliff:g>\" en sy inhoud uit?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-am/strings.xml b/packages/DocumentsUI/res/values-am/strings.xml
index ca43dab..0e1a34d 100644
--- a/packages/DocumentsUI/res/values-am/strings.xml
+++ b/packages/DocumentsUI/res/values-am/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ሰነዶች"</string>
-    <string name="files_label" msgid="6051402950202690279">"ፋይሎች"</string>
     <string name="downloads_label" msgid="959113951084633612">"የወረዱ"</string>
     <string name="title_open" msgid="4353228937663917801">"ክፈት ከ"</string>
     <string name="title_save" msgid="2433679664882857999">"አስቀምጥ ወደ"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ተመርጠዋል</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ተመርጠዋል</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ንጥሎች</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ንጥሎች</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"«<xliff:g id="NAME">%1$s</xliff:g>» ይሰረዝ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"አቃፊ «<xliff:g id="NAME">%1$s</xliff:g>» እና ይዘቶቹ ይሰረዙ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ar/strings.xml b/packages/DocumentsUI/res/values-ar/strings.xml
index e6fac50..264a275 100644
--- a/packages/DocumentsUI/res/values-ar/strings.xml
+++ b/packages/DocumentsUI/res/values-ar/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"مستندات"</string>
-    <string name="files_label" msgid="6051402950202690279">"الملفات"</string>
     <string name="downloads_label" msgid="959113951084633612">"التنزيلات"</string>
     <string name="title_open" msgid="4353228937663917801">"فتح من"</string>
     <string name="title_save" msgid="2433679664882857999">"حفظ في"</string>
@@ -152,6 +151,14 @@
       <item quantity="other">تم تحديد <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">تم تحديد <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="zero"><xliff:g id="COUNT_1">%1$d</xliff:g> عنصر</item>
+      <item quantity="two">عنصران (<xliff:g id="COUNT_1">%1$d</xliff:g>)</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> عناصر</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> عنصرًا</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> عنصر</item>
+      <item quantity="one">عنصر واحد (<xliff:g id="COUNT_0">%1$d</xliff:g>)</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"هل تريد حذف \"<xliff:g id="NAME">%1$s</xliff:g>\"؟"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"هل تريد حذف المجلد \"<xliff:g id="NAME">%1$s</xliff:g>\" ومحتوياته؟"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-az-rAZ/strings.xml b/packages/DocumentsUI/res/values-az-rAZ/strings.xml
index 75a0686..e1d6050 100644
--- a/packages/DocumentsUI/res/values-az-rAZ/strings.xml
+++ b/packages/DocumentsUI/res/values-az-rAZ/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Sənədlər"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fayllar"</string>
     <string name="downloads_label" msgid="959113951084633612">"Endirmələr"</string>
     <string name="title_open" msgid="4353228937663917801">"Vasitəsilə açın"</string>
     <string name="title_save" msgid="2433679664882857999">"buraya saxlayın"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> seçilib</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> seçilib</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> element</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> element</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" silinsin?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" qovluğu və onun məzmunu silinsin?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-b+sr+Latn/strings.xml b/packages/DocumentsUI/res/values-b+sr+Latn/strings.xml
index 34c08bd..83f2763 100644
--- a/packages/DocumentsUI/res/values-b+sr+Latn/strings.xml
+++ b/packages/DocumentsUI/res/values-b+sr+Latn/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"Datoteke"</string>
     <string name="downloads_label" msgid="959113951084633612">"Preuzimanja"</string>
     <string name="title_open" msgid="4353228937663917801">"Otvori sa"</string>
     <string name="title_save" msgid="2433679664882857999">"Sačuvaj u"</string>
@@ -128,6 +127,11 @@
       <item quantity="few">Izabrane su <xliff:g id="COUNT_1">%1$d</xliff:g> stavke</item>
       <item quantity="other">Izabrano je <xliff:g id="COUNT_1">%1$d</xliff:g> stavki</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> stavka</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> stavke</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> stavki</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Želite li da izbrišete „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Želite li da izbrišete direktorijum „<xliff:g id="NAME">%1$s</xliff:g>“ i njegov sadržaj?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-be-rBY/strings.xml b/packages/DocumentsUI/res/values-be-rBY/strings.xml
index 8493c477..1c06cd1 100644
--- a/packages/DocumentsUI/res/values-be-rBY/strings.xml
+++ b/packages/DocumentsUI/res/values-be-rBY/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Дакументы"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файлы"</string>
     <string name="downloads_label" msgid="959113951084633612">"Спампоўкі"</string>
     <string name="title_open" msgid="4353228937663917801">"Адкрыць з"</string>
     <string name="title_save" msgid="2433679664882857999">"Захаваць у"</string>
@@ -125,7 +124,7 @@
     <string name="rename_error" msgid="4203041674883412606">"Не атрымалася перайменаваць дакумент"</string>
     <string name="notification_copy_files_converted_title" msgid="3153573223054275181">"Некаторыя файлы былі сканвертаваныя"</string>
     <string name="open_external_dialog_request" msgid="5789329484285817629">"Даць праграме <xliff:g id="APPNAME"><b>^1</b></xliff:g> доступ да дырэкторыі <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> у <xliff:g id="STORAGE"><i>^3</i></xliff:g>?"</string>
-    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"Даць праграме <xliff:g id="APPNAME"><b>^1</b></xliff:g> доступ да дырэкторыі <xliff:g id="DIRECTORY"><i>^2</i></xliff:g>?"</string>
+    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"Даць праграме <xliff:g id="APPNAME"><b>^1</b></xliff:g> доступ да каталога <xliff:g id="DIRECTORY"><i>^2</i></xliff:g>?"</string>
     <string name="open_external_dialog_root_request" msgid="8899108702926347720">"Даць <xliff:g id="APPNAME"><b>^1</b></xliff:g> доступ да вашых даных, у тым ліку фатаграфій і відэа, на <xliff:g id="STORAGE"><i>^2</i></xliff:g>?"</string>
     <string name="never_ask_again" msgid="4295278542972859268">"Больш не пытацца"</string>
     <string name="allow" msgid="7225948811296386551">"Дазволіць"</string>
@@ -136,6 +135,12 @@
       <item quantity="many">Выбрана <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="other">Выбрана <xliff:g id="COUNT_1">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> элемент</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> элементы</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> элементаў</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> элемента</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Выдаліць \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Выдаліць папку \"<xliff:g id="NAME">%1$s</xliff:g>\" і яе змесціва?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-bg/strings.xml b/packages/DocumentsUI/res/values-bg/strings.xml
index 1914bf5..16922c8 100644
--- a/packages/DocumentsUI/res/values-bg/strings.xml
+++ b/packages/DocumentsUI/res/values-bg/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документи"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файлове"</string>
     <string name="downloads_label" msgid="959113951084633612">"Изтегляния"</string>
     <string name="title_open" msgid="4353228937663917801">"Отваряне от"</string>
     <string name="title_save" msgid="2433679664882857999">"Запазване във:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">Избрахте <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">Избрахте <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> елемента</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> елемент</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Искате ли да изтриете „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Искате ли да изтриете папката „<xliff:g id="NAME">%1$s</xliff:g>“ и съдържанието в нея?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-bn-rBD/strings.xml b/packages/DocumentsUI/res/values-bn-rBD/strings.xml
index d931c2b..4be7dc80 100644
--- a/packages/DocumentsUI/res/values-bn-rBD/strings.xml
+++ b/packages/DocumentsUI/res/values-bn-rBD/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"দস্তাবেজগুলি"</string>
-    <string name="files_label" msgid="6051402950202690279">"ফাইলগুলি"</string>
     <string name="downloads_label" msgid="959113951084633612">"ডাউনলোডগুলি"</string>
     <string name="title_open" msgid="4353228937663917801">"এখান থেকে খুলুন"</string>
     <string name="title_save" msgid="2433679664882857999">"এতে সংরক্ষণ করুন"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g>টি নির্বাচন করা হয়েছে</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g>টি নির্বাচন করা হয়েছে</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g>টি আইটেম</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g>টি আইটেম</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" মুছবেন?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ফোল্ডার এবং এটির সামগ্রীগুলিকে মুছবেন?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-bs-rBA/strings.xml b/packages/DocumentsUI/res/values-bs-rBA/strings.xml
index 47ff436..aae7986 100644
--- a/packages/DocumentsUI/res/values-bs-rBA/strings.xml
+++ b/packages/DocumentsUI/res/values-bs-rBA/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fajlovi"</string>
     <string name="downloads_label" msgid="959113951084633612">"Preuzimanja"</string>
     <string name="title_open" msgid="4353228937663917801">"Otvori iz"</string>
     <string name="title_save" msgid="2433679664882857999">"Sačuvaj u"</string>
@@ -128,6 +127,11 @@
       <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> stavke su odabrane</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> stavki je odabrano</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> stavka</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> stavke</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> stavki</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Želite li izbrisati \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Želite li izbrisati folder \"<xliff:g id="NAME">%1$s</xliff:g>\" i njegov sadržaj?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ca/strings.xml b/packages/DocumentsUI/res/values-ca/strings.xml
index 09af97d..85b42076 100644
--- a/packages/DocumentsUI/res/values-ca/strings.xml
+++ b/packages/DocumentsUI/res/values-ca/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documents"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fitxers"</string>
     <string name="downloads_label" msgid="959113951084633612">"Baixades"</string>
     <string name="title_open" msgid="4353228937663917801">"Obre des de"</string>
     <string name="title_save" msgid="2433679664882857999">"Desa a"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elements seleccionats</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> element seleccionat</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elements</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> element</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Vols suprimir el fitxer <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Vols suprimir la carpeta <xliff:g id="NAME">%1$s</xliff:g> i el seu contingut?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-cs/strings.xml b/packages/DocumentsUI/res/values-cs/strings.xml
index cba2e0e..5ab5a41 100644
--- a/packages/DocumentsUI/res/values-cs/strings.xml
+++ b/packages/DocumentsUI/res/values-cs/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenty"</string>
-    <string name="files_label" msgid="6051402950202690279">"Soubory"</string>
     <string name="downloads_label" msgid="959113951084633612">"Stahování"</string>
     <string name="title_open" msgid="4353228937663917801">"Otevřít"</string>
     <string name="title_save" msgid="2433679664882857999">"Uložit do"</string>
@@ -136,6 +135,12 @@
       <item quantity="other">Vybráno <xliff:g id="COUNT_1">%1$d</xliff:g> položek</item>
       <item quantity="one">Vybrána <xliff:g id="COUNT_0">%1$d</xliff:g> položka</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> položky</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> položky</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> položek</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> položka</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Smazat soubor <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Smazat složku <xliff:g id="NAME">%1$s</xliff:g> a její obsah?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-da/strings.xml b/packages/DocumentsUI/res/values-da/strings.xml
index f048e34..840dc00 100644
--- a/packages/DocumentsUI/res/values-da/strings.xml
+++ b/packages/DocumentsUI/res/values-da/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenter"</string>
-    <string name="files_label" msgid="6051402950202690279">"Filer"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Åbn fra"</string>
     <string name="title_save" msgid="2433679664882857999">"Gem i"</string>
@@ -120,6 +119,10 @@
       <item quantity="one">Der er valgt <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="other">Der er valgt <xliff:g id="COUNT_1">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> element</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementer</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Vil du slette \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Vil du slette mappen \"<xliff:g id="NAME">%1$s</xliff:g>\" og dens indhold?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-de/strings.xml b/packages/DocumentsUI/res/values-de/strings.xml
index a6eae70..eb81827 100644
--- a/packages/DocumentsUI/res/values-de/strings.xml
+++ b/packages/DocumentsUI/res/values-de/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumente"</string>
-    <string name="files_label" msgid="6051402950202690279">"Dateien"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Öffnen von"</string>
     <string name="title_save" msgid="2433679664882857999">"Speichern unter"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ausgewählt</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ausgewählt</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> Einträge</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> Eintrag</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" löschen?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Ordner \"<xliff:g id="NAME">%1$s</xliff:g>\" und dessen Inhalte löschen?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-el/strings.xml b/packages/DocumentsUI/res/values-el/strings.xml
index 7dc2067..ad681bd 100644
--- a/packages/DocumentsUI/res/values-el/strings.xml
+++ b/packages/DocumentsUI/res/values-el/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Έγγραφα"</string>
-    <string name="files_label" msgid="6051402950202690279">"Αρχεία"</string>
     <string name="downloads_label" msgid="959113951084633612">"Λήψεις"</string>
     <string name="title_open" msgid="4353228937663917801">"Άνοιγμα από"</string>
     <string name="title_save" msgid="2433679664882857999">"Αποθήκευση σε"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> επιλεγμένα</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> επιλεγμένο</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> στοιχεία</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> στοιχείο</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Να διαγραφεί το αρχείο \"<xliff:g id="NAME">%1$s</xliff:g>\";"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Να διαγραφεί ο φάκελος \"<xliff:g id="NAME">%1$s</xliff:g>\" και τα περιεχόμενά του;"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-en-rAU/strings.xml b/packages/DocumentsUI/res/values-en-rAU/strings.xml
index 8524de5..406d2ec 100644
--- a/packages/DocumentsUI/res/values-en-rAU/strings.xml
+++ b/packages/DocumentsUI/res/values-en-rAU/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documents"</string>
-    <string name="files_label" msgid="6051402950202690279">"Files"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Open from"</string>
     <string name="title_save" msgid="2433679664882857999">"Save to"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selected</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> selected</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> items</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Delete \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Delete folder \"<xliff:g id="NAME">%1$s</xliff:g>\" and its contents?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-en-rGB/strings.xml b/packages/DocumentsUI/res/values-en-rGB/strings.xml
index 8524de5..406d2ec 100644
--- a/packages/DocumentsUI/res/values-en-rGB/strings.xml
+++ b/packages/DocumentsUI/res/values-en-rGB/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documents"</string>
-    <string name="files_label" msgid="6051402950202690279">"Files"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Open from"</string>
     <string name="title_save" msgid="2433679664882857999">"Save to"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selected</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> selected</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> items</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Delete \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Delete folder \"<xliff:g id="NAME">%1$s</xliff:g>\" and its contents?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-en-rIN/strings.xml b/packages/DocumentsUI/res/values-en-rIN/strings.xml
index 8524de5..406d2ec 100644
--- a/packages/DocumentsUI/res/values-en-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-en-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documents"</string>
-    <string name="files_label" msgid="6051402950202690279">"Files"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Open from"</string>
     <string name="title_save" msgid="2433679664882857999">"Save to"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selected</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> selected</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> items</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Delete \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Delete folder \"<xliff:g id="NAME">%1$s</xliff:g>\" and its contents?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-es-rUS/strings.xml b/packages/DocumentsUI/res/values-es-rUS/strings.xml
index 87641a7..bb471f7 100644
--- a/packages/DocumentsUI/res/values-es-rUS/strings.xml
+++ b/packages/DocumentsUI/res/values-es-rUS/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documentos"</string>
-    <string name="files_label" msgid="6051402950202690279">"Archivos"</string>
     <string name="downloads_label" msgid="959113951084633612">"Descargas"</string>
     <string name="title_open" msgid="4353228937663917801">"Abrir desde"</string>
     <string name="title_save" msgid="2433679664882857999">"Guardar en"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementos seleccionados</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elemento seleccionado</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementos</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elemento</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"¿Deseas borrar \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"¿Deseas borrar la carpeta \"<xliff:g id="NAME">%1$s</xliff:g>\" y su contenido?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-es/strings.xml b/packages/DocumentsUI/res/values-es/strings.xml
index 9054561..2373e60 100644
--- a/packages/DocumentsUI/res/values-es/strings.xml
+++ b/packages/DocumentsUI/res/values-es/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documentos"</string>
-    <string name="files_label" msgid="6051402950202690279">"Archivos"</string>
     <string name="downloads_label" msgid="959113951084633612">"Descargas"</string>
     <string name="title_open" msgid="4353228937663917801">"Abrir desde"</string>
     <string name="title_save" msgid="2433679664882857999">"Guardar en"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> seleccionados</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> seleccionado</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementos</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elemento</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"¿Eliminar <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"¿Eliminar la carpeta <xliff:g id="NAME">%1$s</xliff:g> y su contenido?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-et-rEE/strings.xml b/packages/DocumentsUI/res/values-et-rEE/strings.xml
index 4bb2a9b..6bc3942 100644
--- a/packages/DocumentsUI/res/values-et-rEE/strings.xml
+++ b/packages/DocumentsUI/res/values-et-rEE/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumendid"</string>
-    <string name="files_label" msgid="6051402950202690279">"Failid"</string>
     <string name="downloads_label" msgid="959113951084633612">"Allalaadimised"</string>
     <string name="title_open" msgid="4353228937663917801">"Ava:"</string>
     <string name="title_save" msgid="2433679664882857999">"Salvesta:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> on valitud</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> on valitud</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> üksust</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> üksus</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Kas kustutada fail „<xliff:g id="NAME">%1$s</xliff:g>”?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Kas kustutada kaust „<xliff:g id="NAME">%1$s</xliff:g>” ja selle sisu?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-eu-rES/strings.xml b/packages/DocumentsUI/res/values-eu-rES/strings.xml
index d2bf89d..da11c5c 100644
--- a/packages/DocumentsUI/res/values-eu-rES/strings.xml
+++ b/packages/DocumentsUI/res/values-eu-rES/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumentuak"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fitxategiak"</string>
     <string name="downloads_label" msgid="959113951084633612">"Deskargak"</string>
     <string name="title_open" msgid="4353228937663917801">"Ireki hemendik"</string>
     <string name="title_save" msgid="2433679664882857999">"Gorde hemen"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> hautatuta</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> hautatuta</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementu</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elementu</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ezabatu nahi duzu?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" karpeta eta bertako edukia ezabatu nahi duzu?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-fa/strings.xml b/packages/DocumentsUI/res/values-fa/strings.xml
index 1a4c035..fb4b487 100644
--- a/packages/DocumentsUI/res/values-fa/strings.xml
+++ b/packages/DocumentsUI/res/values-fa/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"اسناد"</string>
-    <string name="files_label" msgid="6051402950202690279">"فایل‌ها"</string>
     <string name="downloads_label" msgid="959113951084633612">"بارگیری‌ها"</string>
     <string name="title_open" msgid="4353228937663917801">"باز کردن از"</string>
     <string name="title_save" msgid="2433679664882857999">"ذخیره در"</string>
@@ -120,6 +119,10 @@
       <item quantity="one">‏<xliff:g id="COUNT_1">%1$d</xliff:g> مورد انتخاب شد</item>
       <item quantity="other">‏<xliff:g id="COUNT_1">%1$d</xliff:g> مورد انتخاب شد</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> مورد</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> مورد</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"«<xliff:g id="NAME">%1$s</xliff:g>» حذف شود؟"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"پوشه «<xliff:g id="NAME">%1$s</xliff:g>» و محتوای آن حذف شود؟"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-fi/strings.xml b/packages/DocumentsUI/res/values-fi/strings.xml
index dfcfe89..21c0ce2 100644
--- a/packages/DocumentsUI/res/values-fi/strings.xml
+++ b/packages/DocumentsUI/res/values-fi/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Asiakirjat"</string>
-    <string name="files_label" msgid="6051402950202690279">"Tiedostot"</string>
     <string name="downloads_label" msgid="959113951084633612">"Lataukset"</string>
     <string name="title_open" msgid="4353228937663917801">"Avaa sijainnista"</string>
     <string name="title_save" msgid="2433679664882857999">"Tallenna kohteeseen"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> valittu</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> valittu</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> kohdetta</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> kohde</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Poistetaanko <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Poistetaanko kansio <xliff:g id="NAME">%1$s</xliff:g> ja sen sisältö?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-fr-rCA/strings.xml b/packages/DocumentsUI/res/values-fr-rCA/strings.xml
index 543e226..a741e6b 100644
--- a/packages/DocumentsUI/res/values-fr-rCA/strings.xml
+++ b/packages/DocumentsUI/res/values-fr-rCA/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documents"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fichiers"</string>
     <string name="downloads_label" msgid="959113951084633612">"Téléchargements"</string>
     <string name="title_open" msgid="4353228937663917801">"Ouvrir à partir de"</string>
     <string name="title_save" msgid="2433679664882857999">"Enregistrer dans"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> élément sélectionné</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> éléments sélectionnés</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> article</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> articles</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Supprimer « <xliff:g id="NAME">%1$s</xliff:g> »?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Supprimer le dossier «  <xliff:g id="NAME">%1$s</xliff:g> » et son contenu?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-fr/strings.xml b/packages/DocumentsUI/res/values-fr/strings.xml
index 05716d7..d41137e 100644
--- a/packages/DocumentsUI/res/values-fr/strings.xml
+++ b/packages/DocumentsUI/res/values-fr/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Docs"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fichiers"</string>
     <string name="downloads_label" msgid="959113951084633612">"Téléchargements"</string>
     <string name="title_open" msgid="4353228937663917801">"Ouvrir à partir de"</string>
     <string name="title_save" msgid="2433679664882857999">"Enregistrer sous"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> élément sélectionné</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> éléments sélectionnés</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> élément</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> éléments</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Supprimer \"<xliff:g id="NAME">%1$s</xliff:g>\" ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Supprimer le dossier \"<xliff:g id="NAME">%1$s</xliff:g>\" et son contenu ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-gl-rES/strings.xml b/packages/DocumentsUI/res/values-gl-rES/strings.xml
index 5797a96..77cc59d6 100644
--- a/packages/DocumentsUI/res/values-gl-rES/strings.xml
+++ b/packages/DocumentsUI/res/values-gl-rES/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documentos"</string>
-    <string name="files_label" msgid="6051402950202690279">"Ficheiros"</string>
     <string name="downloads_label" msgid="959113951084633612">"Descargas"</string>
     <string name="title_open" msgid="4353228937663917801">"Abrir desde"</string>
     <string name="title_save" msgid="2433679664882857999">"Gardar en"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">Seleccionáronse <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">Seleccionouse <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementos</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elemento</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Queres eliminar \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Queres eliminar o cartafol \"<xliff:g id="NAME">%1$s</xliff:g>\" e o seu contido?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-gu-rIN/strings.xml b/packages/DocumentsUI/res/values-gu-rIN/strings.xml
index 48e43c4..e3cd4cf 100644
--- a/packages/DocumentsUI/res/values-gu-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-gu-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"દસ્તાવેજો"</string>
-    <string name="files_label" msgid="6051402950202690279">"ફાઇલો"</string>
     <string name="downloads_label" msgid="959113951084633612">"ડાઉનલોડ્સ"</string>
     <string name="title_open" msgid="4353228937663917801">"અહીંથી ખોલો"</string>
     <string name="title_save" msgid="2433679664882857999">"આમાં સાચવો"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> પસંદ કરી</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> પસંદ કરી</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> આઇટમ</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> આઇટમ</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ને કાઢી નાખીએ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ફોલ્ડર અને તેની સામગ્રીઓને કાઢી નાખીએ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-hi/strings.xml b/packages/DocumentsUI/res/values-hi/strings.xml
index fa82ee8..fa27dff 100644
--- a/packages/DocumentsUI/res/values-hi/strings.xml
+++ b/packages/DocumentsUI/res/values-hi/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"दस्तावेज़"</string>
-    <string name="files_label" msgid="6051402950202690279">"फ़ाइलें"</string>
     <string name="downloads_label" msgid="959113951084633612">"डाउनलोड"</string>
     <string name="title_open" msgid="4353228937663917801">"यहां से खोलें"</string>
     <string name="title_save" msgid="2433679664882857999">"यहां सहेजें"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> चयनित</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> चयनित</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> आइटम</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> आइटम</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" को हटाएं?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" फ़ोल्डर और उसकी सामग्रियां हटाएं?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-hr/strings.xml b/packages/DocumentsUI/res/values-hr/strings.xml
index 7988c71..66a8329 100644
--- a/packages/DocumentsUI/res/values-hr/strings.xml
+++ b/packages/DocumentsUI/res/values-hr/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"Datoteke"</string>
     <string name="downloads_label" msgid="959113951084633612">"Preuzimanja"</string>
     <string name="title_open" msgid="4353228937663917801">"Otvori iz"</string>
     <string name="title_save" msgid="2433679664882857999">"Spremi u"</string>
@@ -128,6 +127,11 @@
       <item quantity="few">Odabrano: <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="other">Odabrano: <xliff:g id="COUNT_1">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> stavka</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> stavke</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> stavki</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Želite li izbrisati datoteku \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Želite li izbrisati mapu \"<xliff:g id="NAME">%1$s</xliff:g>\" i njezin sadržaj?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-hu/strings.xml b/packages/DocumentsUI/res/values-hu/strings.xml
index fb666b5..962653c 100644
--- a/packages/DocumentsUI/res/values-hu/strings.xml
+++ b/packages/DocumentsUI/res/values-hu/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumentumok"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fájlok"</string>
     <string name="downloads_label" msgid="959113951084633612">"Letöltések"</string>
     <string name="title_open" msgid="4353228937663917801">"Megnyitás innen"</string>
     <string name="title_save" msgid="2433679664882857999">"Mentés ide"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> kiválasztva</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> kiválasztva</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elem</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elem</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Törli a következőt: „<xliff:g id="NAME">%1$s</xliff:g>”?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Törli „<xliff:g id="NAME">%1$s</xliff:g>” mappát a tartalmával együtt?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-hy-rAM/strings.xml b/packages/DocumentsUI/res/values-hy-rAM/strings.xml
index f6c3ad5..ab83358 100644
--- a/packages/DocumentsUI/res/values-hy-rAM/strings.xml
+++ b/packages/DocumentsUI/res/values-hy-rAM/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Փաստաթղթեր"</string>
-    <string name="files_label" msgid="6051402950202690279">"Ֆայլեր"</string>
     <string name="downloads_label" msgid="959113951084633612">"Ներբեռնումներ"</string>
     <string name="title_open" msgid="4353228937663917801">"Բացել այստեղից"</string>
     <string name="title_save" msgid="2433679664882857999">"Պահել այստեղ"</string>
@@ -120,6 +119,10 @@
       <item quantity="one">Ընտրված է՝ <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="other">Ընտրված է՝ <xliff:g id="COUNT_1">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> տարր</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> տարր</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Ջնջե՞լ «<xliff:g id="NAME">%1$s</xliff:g>» ֆայլը:"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Ջնջե՞լ «<xliff:g id="NAME">%1$s</xliff:g>» պանակը՝ բովանդակության հետ մեկտեղ:"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-in/strings.xml b/packages/DocumentsUI/res/values-in/strings.xml
index a8aee52..745bf45 100644
--- a/packages/DocumentsUI/res/values-in/strings.xml
+++ b/packages/DocumentsUI/res/values-in/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumen"</string>
-    <string name="files_label" msgid="6051402950202690279">"File"</string>
     <string name="downloads_label" msgid="959113951084633612">"Unduhan"</string>
     <string name="title_open" msgid="4353228937663917801">"Buka dari"</string>
     <string name="title_save" msgid="2433679664882857999">"Simpan ke"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> dipilih</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> dipilih</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> item</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Hapus \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Hapus folder \"<xliff:g id="NAME">%1$s</xliff:g>\" dan kontennya?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-is-rIS/strings.xml b/packages/DocumentsUI/res/values-is-rIS/strings.xml
index 88aaced..47c3d35 100644
--- a/packages/DocumentsUI/res/values-is-rIS/strings.xml
+++ b/packages/DocumentsUI/res/values-is-rIS/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Skjöl"</string>
-    <string name="files_label" msgid="6051402950202690279">"Skrár"</string>
     <string name="downloads_label" msgid="959113951084633612">"Niðurhal"</string>
     <string name="title_open" msgid="4353228937663917801">"Opna frá"</string>
     <string name="title_save" msgid="2433679664882857999">"Vista í"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> valið</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> valin</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> atriði</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> atriði</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Eyða „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Eyða möppunni „<xliff:g id="NAME">%1$s</xliff:g>“ og öllu innihaldi hennar?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-it/strings.xml b/packages/DocumentsUI/res/values-it/strings.xml
index b7497db..0321fb1 100644
--- a/packages/DocumentsUI/res/values-it/strings.xml
+++ b/packages/DocumentsUI/res/values-it/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"File"</string>
     <string name="downloads_label" msgid="959113951084633612">"Download"</string>
     <string name="title_open" msgid="4353228937663917801">"Apri da"</string>
     <string name="title_save" msgid="2433679664882857999">"Salva in"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementi selezionati</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elemento selezionato</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementi</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> elemento</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Eliminare \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Eliminare la cartella \"<xliff:g id="NAME">%1$s</xliff:g>\" e i relativi contenuti?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-iw/strings.xml b/packages/DocumentsUI/res/values-iw/strings.xml
index 4498f8c..4e69606 100644
--- a/packages/DocumentsUI/res/values-iw/strings.xml
+++ b/packages/DocumentsUI/res/values-iw/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"מסמכים"</string>
-    <string name="files_label" msgid="6051402950202690279">"קבצים"</string>
     <string name="downloads_label" msgid="959113951084633612">"הורדות"</string>
     <string name="title_open" msgid="4353228937663917801">"פתח מ-"</string>
     <string name="title_save" msgid="2433679664882857999">"שמור ב-"</string>
@@ -136,6 +135,12 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> נבחרו</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> נבחר</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="two"><xliff:g id="COUNT_1">%1$d</xliff:g> פריטים</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> פריטים</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> פריטים</item>
+      <item quantity="one">פריט <xliff:g id="COUNT_0">%1$d</xliff:g></item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"האם למחוק את \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"האם למחוק את התיקייה \"<xliff:g id="NAME">%1$s</xliff:g>\" ואת התוכן שלה?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ja/strings.xml b/packages/DocumentsUI/res/values-ja/strings.xml
index bfb1c3a..027bc03 100644
--- a/packages/DocumentsUI/res/values-ja/strings.xml
+++ b/packages/DocumentsUI/res/values-ja/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ドキュメント"</string>
-    <string name="files_label" msgid="6051402950202690279">"ファイル"</string>
     <string name="downloads_label" msgid="959113951084633612">"ダウンロード"</string>
     <string name="title_open" msgid="4353228937663917801">"次から開く:"</string>
     <string name="title_save" msgid="2433679664882857999">"次に保存:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> 個を選択中</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> 個を選択中</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> 個のアイテム</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> 個のアイテム</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"「<xliff:g id="NAME">%1$s</xliff:g>」を削除しますか?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"フォルダ「<xliff:g id="NAME">%1$s</xliff:g>」とそのコンテンツを削除しますか?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ka-rGE/strings.xml b/packages/DocumentsUI/res/values-ka-rGE/strings.xml
index f0e9e86..4ac61f2 100644
--- a/packages/DocumentsUI/res/values-ka-rGE/strings.xml
+++ b/packages/DocumentsUI/res/values-ka-rGE/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"დოკუმენტები"</string>
-    <string name="files_label" msgid="6051402950202690279">"ფაილები"</string>
     <string name="downloads_label" msgid="959113951084633612">"ჩამოტვირთვები"</string>
     <string name="title_open" msgid="4353228937663917801">"გახსნა აქედან:"</string>
     <string name="title_save" msgid="2433679664882857999">"შენახვა აქ:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">არჩეულია <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">არჩეულია <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ერთეული</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ერთეული</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"გსურთ, წაშალოთ „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"გსურთ, წაშალოთ საქაღალდე „<xliff:g id="NAME">%1$s</xliff:g>“ და მისი შიგთავსი?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-kk-rKZ/strings.xml b/packages/DocumentsUI/res/values-kk-rKZ/strings.xml
index 2687900..1babc72 100644
--- a/packages/DocumentsUI/res/values-kk-rKZ/strings.xml
+++ b/packages/DocumentsUI/res/values-kk-rKZ/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Құжаттар"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файлдар"</string>
     <string name="downloads_label" msgid="959113951084633612">"Жүктеулер"</string>
     <string name="title_open" msgid="4353228937663917801">"Мынадан ашу:"</string>
     <string name="title_save" msgid="2433679664882857999">"Сақталатын орны"</string>
@@ -111,7 +110,7 @@
     <string name="rename_error" msgid="4203041674883412606">"Құжат қайта аталмады"</string>
     <string name="notification_copy_files_converted_title" msgid="3153573223054275181">"Кейбір файлдар түрлендірілді"</string>
     <string name="open_external_dialog_request" msgid="5789329484285817629">"<xliff:g id="APPNAME"><b>^1</b></xliff:g> қолданбасына <xliff:g id="STORAGE"><i>^3</i></xliff:g> қоймасындағы <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> каталогына өтуге рұқсат беру керек пе?"</string>
-    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"<xliff:g id="APPNAME"><b>^1</b></xliff:g> қолданбасына <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> каталогына қатынас беру керек пе?"</string>
+    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"<xliff:g id="APPNAME"><b>^1</b></xliff:g> қолданбасына <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> каталогына кіруге рұқсат беру керек пе?"</string>
     <string name="open_external_dialog_root_request" msgid="8899108702926347720">"<xliff:g id="APPNAME"><b>^1</b></xliff:g> <xliff:g id="STORAGE"><i>^2</i></xliff:g> қоймасындағы деректерге, соның ішінде фотосуреттерге және бейнелерге кіру мүмкіндігін беру керек пе?"</string>
     <string name="never_ask_again" msgid="4295278542972859268">"Қайта сұралмасын"</string>
     <string name="allow" msgid="7225948811296386551">"Рұқсат беру"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> таңдалды</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> таңдалды</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> элемент</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> элемент</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" жою керек пе?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" қалтасын және оның мазмұнын жою керек пе?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-km-rKH/strings.xml b/packages/DocumentsUI/res/values-km-rKH/strings.xml
index ea24043..37eb3cb 100644
--- a/packages/DocumentsUI/res/values-km-rKH/strings.xml
+++ b/packages/DocumentsUI/res/values-km-rKH/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ឯកសារ"</string>
-    <string name="files_label" msgid="6051402950202690279">"ឯកសារ"</string>
     <string name="downloads_label" msgid="959113951084633612">"ដោនឡូត"</string>
     <string name="title_open" msgid="4353228937663917801">"បើក​ពី"</string>
     <string name="title_save" msgid="2433679664882857999">"រក្សា​ទុក​ទៅ"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">បានជ្រើស <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">បានជ្រើស <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ធាតុ</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ធាតុ</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"លុប \"<xliff:g id="NAME">%1$s</xliff:g>\" ឬ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"លុបថតឯកសារ \"<xliff:g id="NAME">%1$s</xliff:g>\" និងមាតិការបស់វាឬ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-kn-rIN/strings.xml b/packages/DocumentsUI/res/values-kn-rIN/strings.xml
index c756009..ad287d4 100644
--- a/packages/DocumentsUI/res/values-kn-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-kn-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ಡಾಕ್ಯುಮೆಂಟ್‌ಗಳು"</string>
-    <string name="files_label" msgid="6051402950202690279">"ಫೈಲ್‌ಗಳು"</string>
     <string name="downloads_label" msgid="959113951084633612">"ಡೌನ್‌ಲೋಡ್‌ಗಳು"</string>
     <string name="title_open" msgid="4353228937663917801">"ಇದರ ಮೂಲಕ ತೆರೆಯಿರಿ"</string>
     <string name="title_save" msgid="2433679664882857999">"ಇವುಗಳಲ್ಲಿ ಉಳಿಸಿ"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ಆಯ್ಕೆಮಾಡಲಾಗಿದೆ</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ಆಯ್ಕೆಮಾಡಲಾಗಿದೆ</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ಐಟಂಗಳು</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ಐಟಂಗಳು</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ಅಳಿಸುವುದೇ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ಫೋಲ್ಡರ್‌ ಮತ್ತು ಅದರ ವಿಷಯಗಳನ್ನು ಅಳಿಸುವುದೇ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ko/strings.xml b/packages/DocumentsUI/res/values-ko/strings.xml
index 4d5dcf9..9441a10 100644
--- a/packages/DocumentsUI/res/values-ko/strings.xml
+++ b/packages/DocumentsUI/res/values-ko/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"문서"</string>
-    <string name="files_label" msgid="6051402950202690279">"파일"</string>
     <string name="downloads_label" msgid="959113951084633612">"다운로드"</string>
     <string name="title_open" msgid="4353228937663917801">"열기:"</string>
     <string name="title_save" msgid="2433679664882857999">"저장 위치:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g>개 선택됨</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g>개 선택됨</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other">항목 <xliff:g id="COUNT_1">%1$d</xliff:g>개</item>
+      <item quantity="one">항목 <xliff:g id="COUNT_0">%1$d</xliff:g>개</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"<xliff:g id="NAME">%1$s</xliff:g>을(를) 삭제하시겠습니까?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\'<xliff:g id="NAME">%1$s</xliff:g>\' 폴더와 폴더에 포함된 콘텐츠를 삭제하시겠습니까?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ky-rKG/strings.xml b/packages/DocumentsUI/res/values-ky-rKG/strings.xml
index 1b39039..1856eeb 100644
--- a/packages/DocumentsUI/res/values-ky-rKG/strings.xml
+++ b/packages/DocumentsUI/res/values-ky-rKG/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документтер"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файлдар"</string>
     <string name="downloads_label" msgid="959113951084633612">"Жүктөлүп алынгандар"</string>
     <string name="title_open" msgid="4353228937663917801">"Кийинкиден ачуу:"</string>
     <string name="title_save" msgid="2433679664882857999">"Кийинкиге сактоо:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> тандалды</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> тандалды</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> нерсе</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> нерсе</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" жок кылынсынбы?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" куржуну мазмуну менен жок кылынсынбы?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-lo-rLA/strings.xml b/packages/DocumentsUI/res/values-lo-rLA/strings.xml
index a4f381d..1923940 100644
--- a/packages/DocumentsUI/res/values-lo-rLA/strings.xml
+++ b/packages/DocumentsUI/res/values-lo-rLA/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ເອ​ກະ​ສານ"</string>
-    <string name="files_label" msgid="6051402950202690279">"​ໄຟລ໌"</string>
     <string name="downloads_label" msgid="959113951084633612">"ການດາວໂຫລດ"</string>
     <string name="title_open" msgid="4353228937663917801">"ເປີດ​ຈາກ"</string>
     <string name="title_save" msgid="2433679664882857999">"ບັນທຶກໄປທີ່"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">ເລືອກ <xliff:g id="COUNT_1">%1$d</xliff:g> ແລ້ວ</item>
       <item quantity="one">ເລືອກ <xliff:g id="COUNT_0">%1$d</xliff:g> ແລ້ວ</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ລາຍການ</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ລາຍການ</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"ລຶບ \"<xliff:g id="NAME">%1$s</xliff:g>\" ອອກບໍ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"ລຶບໂຟນເດີ \"<xliff:g id="NAME">%1$s</xliff:g>\" ແລະ ເນື້ອຫາທັງໝົດຂອງມັນອອກບໍ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-lt/strings.xml b/packages/DocumentsUI/res/values-lt/strings.xml
index 2e0df93..d7d6c69 100644
--- a/packages/DocumentsUI/res/values-lt/strings.xml
+++ b/packages/DocumentsUI/res/values-lt/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumentai"</string>
-    <string name="files_label" msgid="6051402950202690279">"Failai"</string>
     <string name="downloads_label" msgid="959113951084633612">"Atsisiuntimai"</string>
     <string name="title_open" msgid="4353228937663917801">"Atidaryti iš"</string>
     <string name="title_save" msgid="2433679664882857999">"Išsaugoti į"</string>
@@ -136,6 +135,12 @@
       <item quantity="many">Pasirinkta <xliff:g id="COUNT_1">%1$d</xliff:g> elemento</item>
       <item quantity="other">Pasirinkta <xliff:g id="COUNT_1">%1$d</xliff:g> elementų</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> elementas</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> elementai</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> elemento</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementų</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Ištrinti „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Ištrinti aplanką „<xliff:g id="NAME">%1$s</xliff:g>“ ir jo turinį?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-lv/strings.xml b/packages/DocumentsUI/res/values-lv/strings.xml
index fb81aa0..ef2e6e6 100644
--- a/packages/DocumentsUI/res/values-lv/strings.xml
+++ b/packages/DocumentsUI/res/values-lv/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"Faili"</string>
     <string name="downloads_label" msgid="959113951084633612">"Lejupielādes"</string>
     <string name="title_open" msgid="4353228937663917801">"Atvēršana no:"</string>
     <string name="title_save" msgid="2433679664882857999">"Saglabāšana:"</string>
@@ -128,6 +127,11 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> atlasīts</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> atlasīti</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="zero"><xliff:g id="COUNT_1">%1$d</xliff:g> vienumu</item>
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> vienums</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> vienumi</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Vai izdzēst failu “<xliff:g id="NAME">%1$s</xliff:g>”?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Vai izdzēst mapi “<xliff:g id="NAME">%1$s</xliff:g>” un tās saturu?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-mk-rMK/strings.xml b/packages/DocumentsUI/res/values-mk-rMK/strings.xml
index ad428a0..c6f58c0 100644
--- a/packages/DocumentsUI/res/values-mk-rMK/strings.xml
+++ b/packages/DocumentsUI/res/values-mk-rMK/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документи"</string>
-    <string name="files_label" msgid="6051402950202690279">"Датотеки"</string>
     <string name="downloads_label" msgid="959113951084633612">"Преземања"</string>
     <string name="title_open" msgid="4353228937663917801">"Отвори од"</string>
     <string name="title_save" msgid="2433679664882857999">"Зачувај во"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> е избрана</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> се избрани</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ставка</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ставки</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Да се избрише „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Да се избрише папката „<xliff:g id="NAME">%1$s</xliff:g>“ и нејзините содржини?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ml-rIN/strings.xml b/packages/DocumentsUI/res/values-ml-rIN/strings.xml
index 5a16512..5bafacd 100644
--- a/packages/DocumentsUI/res/values-ml-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-ml-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"പ്രമാണങ്ങൾ"</string>
-    <string name="files_label" msgid="6051402950202690279">"ഫയലുകൾ"</string>
     <string name="downloads_label" msgid="959113951084633612">"ഡൗണ്‍ലോഡുകൾ"</string>
     <string name="title_open" msgid="4353228937663917801">"ഇതിൽ നിന്നും തുറക്കുക"</string>
     <string name="title_save" msgid="2433679664882857999">"ഇതില്‍‌ സംരക്ഷിക്കുക"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> തിരഞ്ഞെടുത്തു</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> തിരഞ്ഞെടുത്തു</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ഇനങ്ങൾ</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ഇനം</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ഇല്ലാതാക്കണോ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" എന്ന ഫോൾഡറും അതിലെ ഉള്ളടങ്ങളും ഇല്ലാതാക്കണോ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-mn-rMN/strings.xml b/packages/DocumentsUI/res/values-mn-rMN/strings.xml
index cf2c2d4..2323d23 100644
--- a/packages/DocumentsUI/res/values-mn-rMN/strings.xml
+++ b/packages/DocumentsUI/res/values-mn-rMN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документүүд"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файл"</string>
     <string name="downloads_label" msgid="959113951084633612">"Таталт"</string>
     <string name="title_open" msgid="4353228937663917801">"Нээх"</string>
     <string name="title_save" msgid="2433679664882857999">"Хадгалах"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> сонгосон</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> сонгосон</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> зүйл</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> зүйл</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\"-г устгах уу?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" фолдер болон үүний агуулгыг устгах уу?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-mr-rIN/strings.xml b/packages/DocumentsUI/res/values-mr-rIN/strings.xml
index 09dd133..eb7dab3 100644
--- a/packages/DocumentsUI/res/values-mr-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-mr-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"दस्तऐवज"</string>
-    <string name="files_label" msgid="6051402950202690279">"फायली"</string>
     <string name="downloads_label" msgid="959113951084633612">"डाउनलोड"</string>
     <string name="title_open" msgid="4353228937663917801">"वरून उघडा"</string>
     <string name="title_save" msgid="2433679664882857999">"येथे जतन करा"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> निवडला</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> निवडले</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> आयटम</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> आयटम</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" हटवायची?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" फोल्डर आणि त्यामधील सामग्री हटवायची?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ms-rMY/strings.xml b/packages/DocumentsUI/res/values-ms-rMY/strings.xml
index 9eb3d49..71118d8 100644
--- a/packages/DocumentsUI/res/values-ms-rMY/strings.xml
+++ b/packages/DocumentsUI/res/values-ms-rMY/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumen"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fail"</string>
     <string name="downloads_label" msgid="959113951084633612">"Muat turun"</string>
     <string name="title_open" msgid="4353228937663917801">"Buka dari"</string>
     <string name="title_save" msgid="2433679664882857999">"Simpan ke"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> dipilih</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> dipilih</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> item</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Padamkan \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Padamkan folder \"<xliff:g id="NAME">%1$s</xliff:g>\" dan kandungannya?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-my-rMM/strings.xml b/packages/DocumentsUI/res/values-my-rMM/strings.xml
index 7c637c4..a0b1777 100644
--- a/packages/DocumentsUI/res/values-my-rMM/strings.xml
+++ b/packages/DocumentsUI/res/values-my-rMM/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"စာရွက်စာတန်းများ"</string>
-    <string name="files_label" msgid="6051402950202690279">"ဖိုင်များ"</string>
     <string name="downloads_label" msgid="959113951084633612">"ဒေါင်းလုဒ်များ"</string>
     <string name="title_open" msgid="4353228937663917801">"မှ ဖွင့်ပါ"</string>
     <string name="title_save" msgid="2433679664882857999">"သို့ သိမ်းပါ"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ခုရွေးချယ်ထားသည်</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ခုရွေးချယ်ထားသည်</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ခု</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ခု</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ကိုဖျက်မလား။"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ဖိုင်တွဲနှင့် ၎င်းတွင်ပါဝင်သည့် အကြောင်းအရာများကို ဖျက်မလား။"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-nb/strings.xml b/packages/DocumentsUI/res/values-nb/strings.xml
index 3c344eb..fd07c8d 100644
--- a/packages/DocumentsUI/res/values-nb/strings.xml
+++ b/packages/DocumentsUI/res/values-nb/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenter"</string>
-    <string name="files_label" msgid="6051402950202690279">"Filer"</string>
     <string name="downloads_label" msgid="959113951084633612">"Nedlastinger"</string>
     <string name="title_open" msgid="4353228937663917801">"Åpne fra"</string>
     <string name="title_save" msgid="2433679664882857999">"Lagre i"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> er valgt</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> er valgt</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> varer</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> vare</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Vil du slette «<xliff:g id="NAME">%1$s</xliff:g>»?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Vil du slette «<xliff:g id="NAME">%1$s</xliff:g>»-mappen og innholdet i den?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ne-rNP/strings.xml b/packages/DocumentsUI/res/values-ne-rNP/strings.xml
index 9fef037..31085d5 100644
--- a/packages/DocumentsUI/res/values-ne-rNP/strings.xml
+++ b/packages/DocumentsUI/res/values-ne-rNP/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"कागजातहरू"</string>
-    <string name="files_label" msgid="6051402950202690279">"फाइलहरू"</string>
     <string name="downloads_label" msgid="959113951084633612">"डाउनलोडहरू"</string>
     <string name="title_open" msgid="4353228937663917801">"यसबाट खोल्नुहोस्"</string>
     <string name="title_save" msgid="2433679664882857999">"यसमा सुरक्षित गर्नुहोस्"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> लाई चयन गरियो</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> लाई चयन गरियो</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> वस्तुहरू</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> वस्तु</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" लाई मेट्ने हो?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"फोल्डर \"<xliff:g id="NAME">%1$s</xliff:g>\" र यसका सामग्रीहरूलाई मेट्ने हो?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-nl/strings.xml b/packages/DocumentsUI/res/values-nl/strings.xml
index c5b9d76..7b0ce93 100644
--- a/packages/DocumentsUI/res/values-nl/strings.xml
+++ b/packages/DocumentsUI/res/values-nl/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documenten"</string>
-    <string name="files_label" msgid="6051402950202690279">"Bestanden"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Openen vanuit"</string>
     <string name="title_save" msgid="2433679664882857999">"Opslaan in"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> geselecteerd</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> geselecteerd</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> items</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"<xliff:g id="NAME">%1$s</xliff:g> verwijderen?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Map <xliff:g id="NAME">%1$s</xliff:g> en de bijbehorende inhoud verwijderen?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-pa-rIN/strings.xml b/packages/DocumentsUI/res/values-pa-rIN/strings.xml
index 7d5e14a..25e4cd6 100644
--- a/packages/DocumentsUI/res/values-pa-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-pa-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ਦਸਤਾਵੇਜ਼"</string>
-    <string name="files_label" msgid="6051402950202690279">"ਫਾਈਲਾਂ"</string>
     <string name="downloads_label" msgid="959113951084633612">"ਡਾਊਨਲੋਡ"</string>
     <string name="title_open" msgid="4353228937663917801">"ਤੋਂ ਖੋਲ੍ਹੋ"</string>
     <string name="title_save" msgid="2433679664882857999">"ਇਸ ਵਿੱਚ ਸੁਰੱਖਿਅਤ ਕਰੋ"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ਚੁਣੀ ਗਈ</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ਚੁਣੀਆਂ ਗਈਆਂ</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ਆਈਟਮਾਂ</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ਆਈਟਮਾਂ</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"ਕੀ \"<xliff:g id="NAME">%1$s</xliff:g>\" ਨੂੰ ਮਿਟਾਉਣਾ ਹੈ?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"ਫੋਲਡਰ \"<xliff:g id="NAME">%1$s</xliff:g>\" ਅਤੇ ਉਸ ਦੀਆਂ ਸਮੱਗਰੀਆਂ ਨੂੰ ਮਿਟਾਉਣਾ ਹੈ?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-pl/strings.xml b/packages/DocumentsUI/res/values-pl/strings.xml
index ca007d7..09ca839 100644
--- a/packages/DocumentsUI/res/values-pl/strings.xml
+++ b/packages/DocumentsUI/res/values-pl/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenty"</string>
-    <string name="files_label" msgid="6051402950202690279">"Pliki"</string>
     <string name="downloads_label" msgid="959113951084633612">"Pobrane"</string>
     <string name="title_open" msgid="4353228937663917801">"Otwórz z"</string>
     <string name="title_save" msgid="2433679664882857999">"Zapisz w"</string>
@@ -136,6 +135,12 @@
       <item quantity="other">Wybrano <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">Wybrano <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> elementy</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> elementów</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementu</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> element</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Usunąć „<xliff:g id="NAME">%1$s</xliff:g>”?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Usunąć folder „<xliff:g id="NAME">%1$s</xliff:g>” i jego zawartość?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-pt-rBR/strings.xml b/packages/DocumentsUI/res/values-pt-rBR/strings.xml
index 21359c7..921be33 100644
--- a/packages/DocumentsUI/res/values-pt-rBR/strings.xml
+++ b/packages/DocumentsUI/res/values-pt-rBR/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documentos"</string>
-    <string name="files_label" msgid="6051402950202690279">"Arquivos"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Abrir de"</string>
     <string name="title_save" msgid="2433679664882857999">"Salvar em"</string>
@@ -111,7 +110,7 @@
     <string name="rename_error" msgid="4203041674883412606">"Falha ao renomear documento"</string>
     <string name="notification_copy_files_converted_title" msgid="3153573223054275181">"Alguns arquivos foram convertidos"</string>
     <string name="open_external_dialog_request" msgid="5789329484285817629">"Conceder ao <xliff:g id="APPNAME"><b>^1</b></xliff:g> acesso ao diretório <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> no <xliff:g id="STORAGE"><i>^3</i></xliff:g>?"</string>
-    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"Conceder acesso a <xliff:g id="APPNAME"><b>^1</b></xliff:g> ao diretório <xliff:g id="DIRECTORY"><i>^2</i></xliff:g>?"</string>
+    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"Conceder acesso ao diretório <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> para <xliff:g id="APPNAME"><b>^1</b></xliff:g>?"</string>
     <string name="open_external_dialog_root_request" msgid="8899108702926347720">"Conceder a <xliff:g id="APPNAME"><b>^1</b></xliff:g> acesso aos seus dados, incluindo fotos e vídeos, no/na <xliff:g id="STORAGE"><i>^2</i></xliff:g>?"</string>
     <string name="never_ask_again" msgid="4295278542972859268">"Não perguntar novamente"</string>
     <string name="allow" msgid="7225948811296386551">"Permitir"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> selecionados</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selecionados</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> itens</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> itens</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Excluir \" <xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Excluir pasta \"<xliff:g id="NAME">%1$s</xliff:g>\" e o respectivo conteúdo?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-pt-rPT/strings.xml b/packages/DocumentsUI/res/values-pt-rPT/strings.xml
index aea1249..c80bdd2 100644
--- a/packages/DocumentsUI/res/values-pt-rPT/strings.xml
+++ b/packages/DocumentsUI/res/values-pt-rPT/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documentos"</string>
-    <string name="files_label" msgid="6051402950202690279">"Ficheiros"</string>
     <string name="downloads_label" msgid="959113951084633612">"Transferências"</string>
     <string name="title_open" msgid="4353228937663917801">"Abrir de"</string>
     <string name="title_save" msgid="2433679664882857999">"Guardar em"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selecionados</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> selecionado</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> itens</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Pretende eliminar \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Pretende eliminar a pasta \"<xliff:g id="NAME">%1$s</xliff:g>\" e os respetivos conteúdos?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-pt/strings.xml b/packages/DocumentsUI/res/values-pt/strings.xml
index 21359c7..921be33 100644
--- a/packages/DocumentsUI/res/values-pt/strings.xml
+++ b/packages/DocumentsUI/res/values-pt/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documentos"</string>
-    <string name="files_label" msgid="6051402950202690279">"Arquivos"</string>
     <string name="downloads_label" msgid="959113951084633612">"Downloads"</string>
     <string name="title_open" msgid="4353228937663917801">"Abrir de"</string>
     <string name="title_save" msgid="2433679664882857999">"Salvar em"</string>
@@ -111,7 +110,7 @@
     <string name="rename_error" msgid="4203041674883412606">"Falha ao renomear documento"</string>
     <string name="notification_copy_files_converted_title" msgid="3153573223054275181">"Alguns arquivos foram convertidos"</string>
     <string name="open_external_dialog_request" msgid="5789329484285817629">"Conceder ao <xliff:g id="APPNAME"><b>^1</b></xliff:g> acesso ao diretório <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> no <xliff:g id="STORAGE"><i>^3</i></xliff:g>?"</string>
-    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"Conceder acesso a <xliff:g id="APPNAME"><b>^1</b></xliff:g> ao diretório <xliff:g id="DIRECTORY"><i>^2</i></xliff:g>?"</string>
+    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"Conceder acesso ao diretório <xliff:g id="DIRECTORY"><i>^2</i></xliff:g> para <xliff:g id="APPNAME"><b>^1</b></xliff:g>?"</string>
     <string name="open_external_dialog_root_request" msgid="8899108702926347720">"Conceder a <xliff:g id="APPNAME"><b>^1</b></xliff:g> acesso aos seus dados, incluindo fotos e vídeos, no/na <xliff:g id="STORAGE"><i>^2</i></xliff:g>?"</string>
     <string name="never_ask_again" msgid="4295278542972859268">"Não perguntar novamente"</string>
     <string name="allow" msgid="7225948811296386551">"Permitir"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> selecionados</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selecionados</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> itens</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> itens</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Excluir \" <xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Excluir pasta \"<xliff:g id="NAME">%1$s</xliff:g>\" e o respectivo conteúdo?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ro/strings.xml b/packages/DocumentsUI/res/values-ro/strings.xml
index 4b833b1..ced834c 100644
--- a/packages/DocumentsUI/res/values-ro/strings.xml
+++ b/packages/DocumentsUI/res/values-ro/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Documente"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fișiere"</string>
     <string name="downloads_label" msgid="959113951084633612">"Descărcări"</string>
     <string name="title_open" msgid="4353228937663917801">"Deschideți din"</string>
     <string name="title_save" msgid="2433679664882857999">"Salvați în"</string>
@@ -128,6 +127,11 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> selectate</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> selectat</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> elemente</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> de elemente</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> element</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Ștergeți „<xliff:g id="NAME">%1$s</xliff:g>”?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Ștergeți dosarul „<xliff:g id="NAME">%1$s</xliff:g>” și conținutul acestuia?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ru/strings.xml b/packages/DocumentsUI/res/values-ru/strings.xml
index 6ba635d..02077cf 100644
--- a/packages/DocumentsUI/res/values-ru/strings.xml
+++ b/packages/DocumentsUI/res/values-ru/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документы"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файлы"</string>
     <string name="downloads_label" msgid="959113951084633612">"Загрузки"</string>
     <string name="title_open" msgid="4353228937663917801">"Открыть"</string>
     <string name="title_save" msgid="2433679664882857999">"Сохранить"</string>
@@ -136,6 +135,12 @@
       <item quantity="many">Выбрано: <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="other">Выбрано: <xliff:g id="COUNT_1">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> объект</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> объекта</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> объектов</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> объекта</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Удалить файл \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Удалить папку \"<xliff:g id="NAME">%1$s</xliff:g>\" со всем содержимым?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-si-rLK/strings.xml b/packages/DocumentsUI/res/values-si-rLK/strings.xml
index 41c9d4a..d39e853 100644
--- a/packages/DocumentsUI/res/values-si-rLK/strings.xml
+++ b/packages/DocumentsUI/res/values-si-rLK/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ලේඛන"</string>
-    <string name="files_label" msgid="6051402950202690279">"ගොනු"</string>
     <string name="downloads_label" msgid="959113951084633612">"බාගැනීම්"</string>
     <string name="title_open" msgid="4353228937663917801">"විවෘත වන්නේ"</string>
     <string name="title_save" msgid="2433679664882857999">"සුරකින්නේ"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g>ක් තෝරන ලදී</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g>ක් තෝරන ලදී</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one">අයිතම <xliff:g id="COUNT_1">%1$d</xliff:g></item>
+      <item quantity="other">අයිතම <xliff:g id="COUNT_1">%1$d</xliff:g></item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" මකන්නද?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ෆෝල්ඩරය හා එහි අන්තර්ගත මකන්නද?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-sk/strings.xml b/packages/DocumentsUI/res/values-sk/strings.xml
index 1ff01b0..eb59a51 100644
--- a/packages/DocumentsUI/res/values-sk/strings.xml
+++ b/packages/DocumentsUI/res/values-sk/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenty"</string>
-    <string name="files_label" msgid="6051402950202690279">"Súbory"</string>
     <string name="downloads_label" msgid="959113951084633612">"Stiahnuté súbory"</string>
     <string name="title_open" msgid="4353228937663917801">"Otvoriť z"</string>
     <string name="title_save" msgid="2433679664882857999">"Uložiť do"</string>
@@ -136,6 +135,12 @@
       <item quantity="other">Vybraté: <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">Vybraté: <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> položky</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> položky</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> položiek</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> položka</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Odstrániť <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Odstrániť priečinok <xliff:g id="NAME">%1$s</xliff:g> a jeho obsah?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-sl/strings.xml b/packages/DocumentsUI/res/values-sl/strings.xml
index d8b983c..d3daabb 100644
--- a/packages/DocumentsUI/res/values-sl/strings.xml
+++ b/packages/DocumentsUI/res/values-sl/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"Datoteke"</string>
     <string name="downloads_label" msgid="959113951084633612">"Prenosi"</string>
     <string name="title_open" msgid="4353228937663917801">"Odpri iz mape"</string>
     <string name="title_save" msgid="2433679664882857999">"Shrani v"</string>
@@ -136,6 +135,12 @@
       <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> izbrani</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> izbranih</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> element</item>
+      <item quantity="two"><xliff:g id="COUNT_1">%1$d</xliff:g> elementa</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> elementi</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> elementov</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Ali želite izbrisati »<xliff:g id="NAME">%1$s</xliff:g>«?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Ali želite izbrisati mapo »<xliff:g id="NAME">%1$s</xliff:g>« in njeno vsebino?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-sq-rAL/strings.xml b/packages/DocumentsUI/res/values-sq-rAL/strings.xml
index 933a537..fe93300 100644
--- a/packages/DocumentsUI/res/values-sq-rAL/strings.xml
+++ b/packages/DocumentsUI/res/values-sq-rAL/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokumente"</string>
-    <string name="files_label" msgid="6051402950202690279">"Skedarët"</string>
     <string name="downloads_label" msgid="959113951084633612">"Shkarkimet"</string>
     <string name="title_open" msgid="4353228937663917801">"Hap nga"</string>
     <string name="title_save" msgid="2433679664882857999">"Ruaje te"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> të zgjedhur</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> i zgjedhur</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> artikuj</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> artikull</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Të fshihet \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Të fshihet dosja \"<xliff:g id="NAME">%1$s</xliff:g>\" dhe përmbajtja e saj?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-sr/strings.xml b/packages/DocumentsUI/res/values-sr/strings.xml
index 0505f42..95af81f 100644
--- a/packages/DocumentsUI/res/values-sr/strings.xml
+++ b/packages/DocumentsUI/res/values-sr/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документи"</string>
-    <string name="files_label" msgid="6051402950202690279">"Датотеке"</string>
     <string name="downloads_label" msgid="959113951084633612">"Преузимања"</string>
     <string name="title_open" msgid="4353228937663917801">"Отвори са"</string>
     <string name="title_save" msgid="2433679664882857999">"Сачувај у"</string>
@@ -128,6 +127,11 @@
       <item quantity="few">Изабране су <xliff:g id="COUNT_1">%1$d</xliff:g> ставке</item>
       <item quantity="other">Изабрано је <xliff:g id="COUNT_1">%1$d</xliff:g> ставки</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ставка</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> ставке</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ставки</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Желите ли да избришете „<xliff:g id="NAME">%1$s</xliff:g>“?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Желите ли да избришете директоријум „<xliff:g id="NAME">%1$s</xliff:g>“ и његов садржај?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-sv/strings.xml b/packages/DocumentsUI/res/values-sv/strings.xml
index 99f334b..17dfffd 100644
--- a/packages/DocumentsUI/res/values-sv/strings.xml
+++ b/packages/DocumentsUI/res/values-sv/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokument"</string>
-    <string name="files_label" msgid="6051402950202690279">"Filer"</string>
     <string name="downloads_label" msgid="959113951084633612">"Nedladdningar"</string>
     <string name="title_open" msgid="4353228937663917801">"Öppna från"</string>
     <string name="title_save" msgid="2433679664882857999">"Spara till"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> har valts</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> har valts</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> objekt</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> objekt</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Vill du radera <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Vill du radera mappen <xliff:g id="NAME">%1$s</xliff:g> och dess innehåll?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-sw/strings.xml b/packages/DocumentsUI/res/values-sw/strings.xml
index 566e6a4..cf9c8c7 100644
--- a/packages/DocumentsUI/res/values-sw/strings.xml
+++ b/packages/DocumentsUI/res/values-sw/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Hati"</string>
-    <string name="files_label" msgid="6051402950202690279">"Faili"</string>
     <string name="downloads_label" msgid="959113951084633612">"Vipakuliwa"</string>
     <string name="title_open" msgid="4353228937663917801">"Fungua kutoka"</string>
     <string name="title_save" msgid="2433679664882857999">"Hifadhi kwenye"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">Imechagua <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">Imechagua <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other">Vipengee <xliff:g id="COUNT_1">%1$d</xliff:g></item>
+      <item quantity="one">Kipengee <xliff:g id="COUNT_0">%1$d</xliff:g></item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Ungependa kufuta \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Ungependa kufuta folda ya \"<xliff:g id="NAME">%1$s</xliff:g>\" na maudhui yake?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ta-rIN/strings.xml b/packages/DocumentsUI/res/values-ta-rIN/strings.xml
index 9a8b4ec..d4c2f6a 100644
--- a/packages/DocumentsUI/res/values-ta-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-ta-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"ஆவணங்கள்"</string>
-    <string name="files_label" msgid="6051402950202690279">"கோப்புகள்"</string>
     <string name="downloads_label" msgid="959113951084633612">"இறக்கங்கள்"</string>
     <string name="title_open" msgid="4353228937663917801">"இதில் திற"</string>
     <string name="title_save" msgid="2433679664882857999">"இதில் சேமி"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> தேர்ந்தெடுக்கப்பட்டன</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> தேர்ந்தெடுக்கப்பட்டது</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> உருப்படிகள்</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> உருப்படி</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\"ஐ நீக்கவா?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" கோப்புறையையும் அதன் உள்ளடக்கத்தையும் நீக்கவா?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-te-rIN/strings.xml b/packages/DocumentsUI/res/values-te-rIN/strings.xml
index 224d0db..3a91252 100644
--- a/packages/DocumentsUI/res/values-te-rIN/strings.xml
+++ b/packages/DocumentsUI/res/values-te-rIN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"పత్రాలు"</string>
-    <string name="files_label" msgid="6051402950202690279">"ఫైల్‌లు"</string>
     <string name="downloads_label" msgid="959113951084633612">"డౌన్‌లోడ్‌లు"</string>
     <string name="title_open" msgid="4353228937663917801">"ఇక్కడి నుండి తెరువు"</string>
     <string name="title_save" msgid="2433679664882857999">"ఇందులో సేవ్ చేయి"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ఎంచుకోబడ్డాయి</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ఎంచుకోబడింది</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> అంశాలు</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> అంశం</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\"ని తొలగించాలా?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" ఫోల్డర్‌ని మరియు అందులోని కంటెంట్‌లను తొలగించాలా?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-th/strings.xml b/packages/DocumentsUI/res/values-th/strings.xml
index af07584..f739eda 100644
--- a/packages/DocumentsUI/res/values-th/strings.xml
+++ b/packages/DocumentsUI/res/values-th/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"เอกสาร"</string>
-    <string name="files_label" msgid="6051402950202690279">"ไฟล์"</string>
     <string name="downloads_label" msgid="959113951084633612">"การดาวน์โหลด"</string>
     <string name="title_open" msgid="4353228937663917801">"เปิดจาก"</string>
     <string name="title_save" msgid="2433679664882857999">"บันทึกไปยัง"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">เลือกไว้ <xliff:g id="COUNT_1">%1$d</xliff:g> รายการ</item>
       <item quantity="one">เลือกไว้ <xliff:g id="COUNT_0">%1$d</xliff:g> รายการ</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> รายการ</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> รายการ</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"ลบ \"<xliff:g id="NAME">%1$s</xliff:g>\" ไหม"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"ลบโฟลเดอร์ \"<xliff:g id="NAME">%1$s</xliff:g>\" และเนื้อหาข้างในไหม"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-tl/strings.xml b/packages/DocumentsUI/res/values-tl/strings.xml
index b2acf05..3474be8 100644
--- a/packages/DocumentsUI/res/values-tl/strings.xml
+++ b/packages/DocumentsUI/res/values-tl/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Mga Dokumento"</string>
-    <string name="files_label" msgid="6051402950202690279">"Mga File"</string>
     <string name="downloads_label" msgid="959113951084633612">"Mga Download"</string>
     <string name="title_open" msgid="4353228937663917801">"Buksan mula sa"</string>
     <string name="title_save" msgid="2433679664882857999">"I-save sa"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> ang napili</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ang napili</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> item</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> na item</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Gusto mo bang i-delete ang \"<xliff:g id="NAME">%1$s</xliff:g>?\""</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Gusto mo bang i-delete ang folder na \"<xliff:g id="NAME">%1$s</xliff:g>\" at ang mga content nito?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-tr/strings.xml b/packages/DocumentsUI/res/values-tr/strings.xml
index c5653c9..b685568 100644
--- a/packages/DocumentsUI/res/values-tr/strings.xml
+++ b/packages/DocumentsUI/res/values-tr/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Dokümanlar"</string>
-    <string name="files_label" msgid="6051402950202690279">"Dosyalar"</string>
     <string name="downloads_label" msgid="959113951084633612">"İndirilenler"</string>
     <string name="title_open" msgid="4353228937663917801">"Şuradan aç:"</string>
     <string name="title_save" msgid="2433679664882857999">"Şuraya kaydet:"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> öğe seçildi</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> öğe seçildi</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> öğe</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> öğe</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" silinsin mi?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" adlı klasör ve içindekiler silinsin mi?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-uk/strings.xml b/packages/DocumentsUI/res/values-uk/strings.xml
index 21532b6..b255459 100644
--- a/packages/DocumentsUI/res/values-uk/strings.xml
+++ b/packages/DocumentsUI/res/values-uk/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Документи"</string>
-    <string name="files_label" msgid="6051402950202690279">"Файли"</string>
     <string name="downloads_label" msgid="959113951084633612">"Завантаження"</string>
     <string name="title_open" msgid="4353228937663917801">"Відкрити"</string>
     <string name="title_save" msgid="2433679664882857999">"Зберегти в"</string>
@@ -136,6 +135,12 @@
       <item quantity="many">Вибрано <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="other">Вибрано <xliff:g id="COUNT_1">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> елемент</item>
+      <item quantity="few"><xliff:g id="COUNT_1">%1$d</xliff:g> елементи</item>
+      <item quantity="many"><xliff:g id="COUNT_1">%1$d</xliff:g> елементів</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> елемента</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Видалити файл <xliff:g id="NAME">%1$s</xliff:g>?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Видалити папку \"<xliff:g id="NAME">%1$s</xliff:g>\" та її вміст?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-ur-rPK/strings.xml b/packages/DocumentsUI/res/values-ur-rPK/strings.xml
index eb0cfc8..8d85a2b 100644
--- a/packages/DocumentsUI/res/values-ur-rPK/strings.xml
+++ b/packages/DocumentsUI/res/values-ur-rPK/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"دستاویزات"</string>
-    <string name="files_label" msgid="6051402950202690279">"فائلیں"</string>
     <string name="downloads_label" msgid="959113951084633612">"ڈاؤن لوڈز"</string>
     <string name="title_open" msgid="4353228937663917801">"کھولیں از"</string>
     <string name="title_save" msgid="2433679664882857999">"اس میں محفوظ کریں"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> منتخب کردہ</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> منتخب کردہ</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> آئٹمز</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> آئٹم</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"\"<xliff:g id="NAME">%1$s</xliff:g>\" حذف کریں؟"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"\"<xliff:g id="NAME">%1$s</xliff:g>\" فولڈر اور اس کی مشمولات حذف کریں؟"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-uz-rUZ/strings.xml b/packages/DocumentsUI/res/values-uz-rUZ/strings.xml
index 2654308..76e82da 100644
--- a/packages/DocumentsUI/res/values-uz-rUZ/strings.xml
+++ b/packages/DocumentsUI/res/values-uz-rUZ/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Hujjatlar"</string>
-    <string name="files_label" msgid="6051402950202690279">"Fayllar"</string>
     <string name="downloads_label" msgid="959113951084633612">"Yuklanishlar"</string>
     <string name="title_open" msgid="4353228937663917801">"Ochish"</string>
     <string name="title_save" msgid="2433679664882857999">"Saqlash"</string>
@@ -120,6 +119,10 @@
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ta belgilandi</item>
       <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ta belgilandi</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> ta element</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> ta element</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"“<xliff:g id="NAME">%1$s</xliff:g>” fayli o‘chirib tashlansinmi?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"“<xliff:g id="NAME">%1$s</xliff:g>” jildi ichidagi kontentlari bilan o‘chirib tashlansinmi?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-vi/strings.xml b/packages/DocumentsUI/res/values-vi/strings.xml
index 9af7db0..9e69e0f 100644
--- a/packages/DocumentsUI/res/values-vi/strings.xml
+++ b/packages/DocumentsUI/res/values-vi/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Tài liệu"</string>
-    <string name="files_label" msgid="6051402950202690279">"Tệp"</string>
     <string name="downloads_label" msgid="959113951084633612">"Tài nguyên đã tải xuống"</string>
     <string name="title_open" msgid="4353228937663917801">"Mở từ"</string>
     <string name="title_save" msgid="2433679664882857999">"Lưu vào"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">Đã chọn <xliff:g id="COUNT_1">%1$d</xliff:g></item>
       <item quantity="one">Đã chọn <xliff:g id="COUNT_0">%1$d</xliff:g></item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> mục</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> mục</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Xóa \"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Xóa thư mục \"<xliff:g id="NAME">%1$s</xliff:g>\" và nội dung của thư mục?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-zh-rCN/strings.xml b/packages/DocumentsUI/res/values-zh-rCN/strings.xml
index e3db1a0..00e4c91 100644
--- a/packages/DocumentsUI/res/values-zh-rCN/strings.xml
+++ b/packages/DocumentsUI/res/values-zh-rCN/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"文档"</string>
-    <string name="files_label" msgid="6051402950202690279">"文件"</string>
     <string name="downloads_label" msgid="959113951084633612">"下载"</string>
     <string name="title_open" msgid="4353228937663917801">"打开文件"</string>
     <string name="title_save" msgid="2433679664882857999">"保存文件"</string>
@@ -111,7 +110,7 @@
     <string name="rename_error" msgid="4203041674883412606">"无法重命名文档"</string>
     <string name="notification_copy_files_converted_title" msgid="3153573223054275181">"部分文件已转换成其他格式"</string>
     <string name="open_external_dialog_request" msgid="5789329484285817629">"要授权<xliff:g id="APPNAME"><b>^1</b></xliff:g>访问 <xliff:g id="STORAGE"><i>^3</i></xliff:g>上的“<xliff:g id="DIRECTORY"><i>^2</i></xliff:g>”目录吗?"</string>
-    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"要授权<xliff:g id="APPNAME"><b>^1</b></xliff:g>访问<xliff:g id="DIRECTORY"><i>^2</i></xliff:g>目录吗?"</string>
+    <string name="open_external_dialog_request_primary_volume" msgid="6635562535713428688">"要授权<xliff:g id="APPNAME"><b>^1</b></xliff:g>访问“<xliff:g id="DIRECTORY"><i>^2</i></xliff:g>”目录吗?"</string>
     <string name="open_external_dialog_root_request" msgid="8899108702926347720">"要授权<xliff:g id="APPNAME"><b>^1</b></xliff:g>访问您 <xliff:g id="STORAGE"><i>^2</i></xliff:g>上的数据(包括照片和视频)吗?"</string>
     <string name="never_ask_again" msgid="4295278542972859268">"不再询问"</string>
     <string name="allow" msgid="7225948811296386551">"允许"</string>
@@ -120,6 +119,7 @@
       <item quantity="other">已选择 <xliff:g id="COUNT_1">%1$d</xliff:g> 项</item>
       <item quantity="one">已选择 <xliff:g id="COUNT_0">%1$d</xliff:g> 项</item>
     </plurals>
+    <!-- no translation found for elements_dragged (3727204615215602228) -->
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"要删除“<xliff:g id="NAME">%1$s</xliff:g>”吗?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"要删除文件夹“<xliff:g id="NAME">%1$s</xliff:g>”及其中的内容吗?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-zh-rHK/strings.xml b/packages/DocumentsUI/res/values-zh-rHK/strings.xml
index f13a4bd1..4b0f4e2 100644
--- a/packages/DocumentsUI/res/values-zh-rHK/strings.xml
+++ b/packages/DocumentsUI/res/values-zh-rHK/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"文件"</string>
-    <string name="files_label" msgid="6051402950202690279">"檔案"</string>
     <string name="downloads_label" msgid="959113951084633612">"下載"</string>
     <string name="title_open" msgid="4353228937663917801">"開啟檔案"</string>
     <string name="title_save" msgid="2433679664882857999">"儲存至"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">已選取 <xliff:g id="COUNT_1">%1$d</xliff:g> 個項目</item>
       <item quantity="one">已選取 <xliff:g id="COUNT_0">%1$d</xliff:g> 個項目</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> 個項目</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> 個項目</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"要刪除「<xliff:g id="NAME">%1$s</xliff:g>」嗎?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"要刪除「<xliff:g id="NAME">%1$s</xliff:g>」資料夾及其內容嗎?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-zh-rTW/strings.xml b/packages/DocumentsUI/res/values-zh-rTW/strings.xml
index f8f8282..07c5c2a 100644
--- a/packages/DocumentsUI/res/values-zh-rTW/strings.xml
+++ b/packages/DocumentsUI/res/values-zh-rTW/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"文件"</string>
-    <string name="files_label" msgid="6051402950202690279">"檔案"</string>
     <string name="downloads_label" msgid="959113951084633612">"下載內容"</string>
     <string name="title_open" msgid="4353228937663917801">"開啟檔案"</string>
     <string name="title_save" msgid="2433679664882857999">"儲存至"</string>
@@ -120,6 +119,10 @@
       <item quantity="other">已選取 <xliff:g id="COUNT_1">%1$d</xliff:g> 個項目</item>
       <item quantity="one">已選取 <xliff:g id="COUNT_0">%1$d</xliff:g> 個項目</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> 個項目</item>
+      <item quantity="one"><xliff:g id="COUNT_0">%1$d</xliff:g> 個項目</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"要刪除「<xliff:g id="NAME">%1$s</xliff:g>」嗎?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"要刪除「<xliff:g id="NAME">%1$s</xliff:g>」資料夾和當中的內容嗎?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/res/values-zu/strings.xml b/packages/DocumentsUI/res/values-zu/strings.xml
index a0b9f7f..095d275 100644
--- a/packages/DocumentsUI/res/values-zu/strings.xml
+++ b/packages/DocumentsUI/res/values-zu/strings.xml
@@ -17,7 +17,6 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_label" msgid="2783841764617238354">"Amadokhumenti"</string>
-    <string name="files_label" msgid="6051402950202690279">"Amafayela"</string>
     <string name="downloads_label" msgid="959113951084633612">"Okulandiwe"</string>
     <string name="title_open" msgid="4353228937663917801">"Vula kusuka ku-"</string>
     <string name="title_save" msgid="2433679664882857999">"Londoloza ku-"</string>
@@ -120,6 +119,10 @@
       <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> okukhethiwe</item>
       <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> okukhethiwe</item>
     </plurals>
+    <plurals name="elements_dragged" formatted="false" msgid="3727204615215602228">
+      <item quantity="one"><xliff:g id="COUNT_1">%1$d</xliff:g> izinto</item>
+      <item quantity="other"><xliff:g id="COUNT_1">%1$d</xliff:g> izinto</item>
+    </plurals>
     <string name="delete_filename_confirmation_message" msgid="5312817725577537488">"Susa i-\"<xliff:g id="NAME">%1$s</xliff:g>\"?"</string>
     <string name="delete_foldername_confirmation_message" msgid="5885501832257285329">"Susa ifolda engu-\"<xliff:g id="NAME">%1$s</xliff:g>\" nokuqukethwe kwalo?"</string>
     <plurals name="delete_files_confirmation_message" formatted="false" msgid="8417505791395471802">
diff --git a/packages/DocumentsUI/src/com/android/documentsui/BaseActivity.java b/packages/DocumentsUI/src/com/android/documentsui/BaseActivity.java
index 4ee37a5..3b0be57 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/BaseActivity.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/BaseActivity.java
@@ -257,7 +257,6 @@
 
     @Override
     public boolean onOptionsItemSelected(MenuItem item) {
-        Metrics.logMenuAction(this, item.getItemId());
 
         switch (item.getItemId()) {
             case android.R.id.home:
@@ -279,6 +278,7 @@
             case R.id.menu_sort_date:
                 setUserSortOrder(State.SORT_ORDER_LAST_MODIFIED);
                 return true;
+
             case R.id.menu_sort_size:
                 setUserSortOrder(State.SORT_ORDER_SIZE);
                 return true;
@@ -307,6 +307,8 @@
                 return true;
 
             case R.id.menu_settings:
+                Metrics.logUserAction(this, Metrics.USER_ACTION_SETTINGS);
+
                 final RootInfo root = getCurrentRoot();
                 final Intent intent = new Intent(DocumentsContract.ACTION_DOCUMENT_ROOT_SETTINGS);
                 intent.setDataAndType(root.getUri(), DocumentsContract.Root.MIME_TYPE_ITEM);
@@ -323,6 +325,8 @@
     }
 
     void showCreateDirectoryDialog() {
+        Metrics.logUserAction(this, Metrics.USER_ACTION_CREATE_DIR);
+
         CreateDirectoryFragment.show(getFragmentManager());
     }
 
@@ -469,13 +473,25 @@
                         "com.android.providers.downloads.documents", "downloads");
     }
 
+    /**
+     * Set internal storage visible based on explicit user action.
+     */
     void setDisplayAdvancedDevices(boolean display) {
+        Metrics.logUserAction(this,
+                display ? Metrics.USER_ACTION_SHOW_ADVANCED : Metrics.USER_ACTION_HIDE_ADVANCED);
+
         mState.showAdvanced = display;
         RootsFragment.get(getFragmentManager()).onDisplayStateChanged();
         invalidateOptionsMenu();
     }
 
+    /**
+     * Set file size visible based on explicit user action.
+     */
     void setDisplayFileSize(boolean display) {
+        Metrics.logUserAction(this,
+                display ? Metrics.USER_ACTION_SHOW_SIZE : Metrics.USER_ACTION_HIDE_SIZE);
+
         LocalPreferences.setDisplayFileSize(this, display);
         mState.showSize = display;
         DirectoryFragment dir = getDirectoryFragment();
@@ -489,6 +505,18 @@
      * Set state sort order based on explicit user action.
      */
     void setUserSortOrder(int sortOrder) {
+        switch(sortOrder) {
+            case State.SORT_ORDER_DISPLAY_NAME:
+                Metrics.logUserAction(this, Metrics.USER_ACTION_SORT_NAME);
+                break;
+            case State.SORT_ORDER_LAST_MODIFIED:
+                Metrics.logUserAction(this, Metrics.USER_ACTION_SORT_DATE);
+                break;
+            case State.SORT_ORDER_SIZE:
+                Metrics.logUserAction(this, Metrics.USER_ACTION_SORT_SIZE);
+                break;
+        }
+
         mState.userSortOrder = sortOrder;
         DirectoryFragment dir = getDirectoryFragment();
         if (dir != null) {
@@ -500,6 +528,12 @@
      * Set mode based on explicit user action.
      */
     void setViewMode(@ViewMode int mode) {
+        if (mode == State.MODE_GRID) {
+            Metrics.logUserAction(this, Metrics.USER_ACTION_GRID);
+        } else if (mode == State.MODE_LIST) {
+            Metrics.logUserAction(this, Metrics.USER_ACTION_LIST);
+        }
+
         LocalPreferences.setViewMode(this, getCurrentRoot(), mode);
         mState.derivedMode = mode;
 
@@ -621,12 +655,10 @@
                 return true;
             }
         } else if (keyCode == KeyEvent.KEYCODE_TAB) {
-            Metrics.logKeyboardAction(this, Metrics.ACTION_KEYBOARD_SWITCH_FOCUS);
             // Tab toggles focus on the navigation drawer.
             toggleNavDrawerFocus();
             return true;
         } else if (keyCode == KeyEvent.KEYCODE_DEL) {
-            Metrics.logKeyboardAction(this, Metrics.ACTION_KEYBOARD_BACK);
             popDir();
             return true;
         }
diff --git a/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java b/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java
index 40b54d3..7a7d3a1 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/DocumentsActivity.java
@@ -232,12 +232,13 @@
         final MenuItem list = menu.findItem(R.id.menu_list);
         final MenuItem fileSize = menu.findItem(R.id.menu_file_size);
 
-        boolean recents = cwd == null;
 
-        createDir.setVisible(picking && !recents && cwd.isCreateSupported());
+        createDir.setVisible(picking);
+        createDir.setEnabled(canCreateDirectory());
 
         // No display options in recent directories
-        if (picking && recents) {
+        boolean inRecents = cwd == null;
+        if (picking && inRecents) {
             grid.setVisible(false);
             list.setVisible(false);
         }
diff --git a/packages/DocumentsUI/src/com/android/documentsui/FilesActivity.java b/packages/DocumentsUI/src/com/android/documentsui/FilesActivity.java
index 527eb78..84fc6fe 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/FilesActivity.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/FilesActivity.java
@@ -98,7 +98,7 @@
             assert(uri == null || uri.getAuthority() == null ||
                     LauncherActivity.isLaunchUri(uri));
             refreshCurrentRootAndDirectory(AnimationView.ANIM_NONE);
-        } else if (intent.getAction() == Intent.ACTION_VIEW) {
+        } else if (Intent.ACTION_VIEW.equals(intent.getAction())) {
             assert(uri != null);
             new OpenUriForViewTask(this).executeOnExecutor(
                     ProviderExecutor.forAuthority(uri.getAuthority()), uri);
@@ -228,13 +228,12 @@
             default:
                 return super.onOptionsItemSelected(item);
         }
-
-        Metrics.logMenuAction(this, item.getItemId());
         return true;
     }
 
     private void createNewWindow() {
-        Metrics.logMultiWindow(this);
+        Metrics.logUserAction(this, Metrics.USER_ACTION_NEW_WINDOW);
+
         Intent intent = LauncherActivity.createLaunchIntent(this);
         intent.putExtra(Shared.EXTRA_STACK, (Parcelable) mState.stack);
 
@@ -277,18 +276,6 @@
 
     @Override
     public void onDocumentPicked(DocumentInfo doc, Model model) {
-        if (doc.isContainer()) {
-            openContainerDocument(doc);
-        } else {
-            openDocument(doc, model);
-        }
-    }
-
-    /**
-     * Launches an intent to view the specified document.
-     */
-    private void openDocument(DocumentInfo doc, Model model) {
-
         // Anything on downloads goes through the back through downloads manager
         // (that's the MANAGE_DOCUMENT bit).
         // This is done for two reasons:
@@ -298,7 +285,13 @@
         //    like origin URL.
         // All other files not on downloads, event APKs, would get no benefit from this
         // treatment, thusly the "isDownloads" check.
-        if (getCurrentRoot().isDownloads()) {
+
+        // Launch MANAGE_DOCUMENTS only for the root level files, so it's not called for
+        // files in archives. Also, if the activity is already browsing a ZIP from downloads,
+        // then skip MANAGE_DOCUMENTS.
+        final boolean isViewing = Intent.ACTION_VIEW.equals(getIntent().getAction());
+        final boolean isInArchive = mState.stack.size() > 1;
+        if (getCurrentRoot().isDownloads() && !isInArchive && !isViewing) {
             // First try managing the document; we expect manager to filter
             // based on authority, so we don't grant.
             final Intent manage = new Intent(DocumentsContract.ACTION_MANAGE_DOCUMENT);
@@ -312,6 +305,17 @@
             }
         }
 
+        if (doc.isContainer()) {
+            openContainerDocument(doc);
+        } else {
+            openDocument(doc, model);
+        }
+    }
+
+    /**
+     * Launches an intent to view the specified document.
+     */
+    private void openDocument(DocumentInfo doc, Model model) {
         Intent intent = new QuickViewIntentBuilder(
                 getPackageManager(), getResources(), doc, model).build();
 
@@ -352,21 +356,18 @@
             case KeyEvent.KEYCODE_A:
                 dir = getDirectoryFragment();
                 if (dir != null) {
-                    Metrics.logKeyboardAction(this, Metrics.ACTION_KEYBOARD_SELECT_ALL);
                     dir.selectAllFiles();
                 }
                 return true;
             case KeyEvent.KEYCODE_C:
                 dir = getDirectoryFragment();
                 if (dir != null) {
-                    Metrics.logKeyboardAction(this, Metrics.ACTION_KEYBOARD_COPY);
                     dir.copySelectedToClipboard();
                 }
                 return true;
             case KeyEvent.KEYCODE_V:
                 dir = getDirectoryFragment();
                 if (dir != null) {
-                    Metrics.logKeyboardAction(this, Metrics.ACTION_KEYBOARD_PASTE);
                     dir.pasteFromClipboard();
                 }
                 return true;
diff --git a/packages/DocumentsUI/src/com/android/documentsui/Metrics.java b/packages/DocumentsUI/src/com/android/documentsui/Metrics.java
index 05cc7e6..69a6e1f 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/Metrics.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/Metrics.java
@@ -62,16 +62,13 @@
     private static final String COUNT_GET_CONTENT_MIME = "docsui_get_content_mime";
     private static final String COUNT_BROWSE_ROOT = "docsui_browse_root";
     @Deprecated private static final String COUNT_MANAGE_ROOT = "docsui_manage_root";
-    private static final String COUNT_MULTI_WINDOW = "docsui_multi_window";
+    @Deprecated private static final String COUNT_MULTI_WINDOW = "docsui_multi_window";
     private static final String COUNT_FILEOP_SYSTEM = "docsui_fileop_system";
     private static final String COUNT_FILEOP_EXTERNAL = "docsui_fileop_external";
     private static final String COUNT_FILEOP_CANCELED = "docsui_fileop_canceled";
     private static final String COUNT_STARTUP_MS = "docsui_startup_ms";
     private static final String COUNT_DRAWER_OPENED = "docsui_drawer_opened";
-    private static final String COUNT_DRAG_N_DROP = "docsui_drag_n_drop";
-    private static final String COUNT_SEARCH = "docsui_search";
-    private static final String COUNT_MENU_ACTION = "docsui_menu_action";
-    private static final String COUNT_KEYBOARD_ACTION = "docsui_keyboard_action";
+    private static final String COUNT_USER_ACTION = "docsui_menu_action";
 
     // Indices for bucketing roots in the roots histogram. "Other" is the catch-all index for any
     // root that is not explicitly recognized by the Metrics code (see {@link
@@ -215,54 +212,67 @@
     public @interface Provider {}
 
 
-    // Codes representing different menu actions. These are used for bucketing stats in the
-    // COUNT_MENU_ACTION histogram.
-    // Both regular toolbar menu and action mode menu operations are included.
+    // Codes representing different user actions. These are used for bucketing stats in the
+    // COUNT_USER_ACTION histogram.
+    // The historgram includes action triggered from menu or invoked by keyboard shortcut.
     // Do not change or rearrange these values, that will break historical data. Only add to the
     // list.
     // Do not use negative numbers or zero; clearcut only handles positive integers.
-    private static final int ACTION_MENU_OTHER = 1;
-    private static final int ACTION_MENU_GRID = 2;
-    private static final int ACTION_MENU_LIST = 3;
-    private static final int ACTION_MENU_SORT = 4;
-    private static final int ACTION_MENU_SORT_NAME = 5;
-    private static final int ACTION_MENU_SORT_DATE = 6;
-    private static final int ACTION_MENU_SORT_SIZE = 7;
-    private static final int ACTION_MENU_SEARCH = 8;
-    private static final int ACTION_MENU_SHOW_SIZE = 9;
-    private static final int ACTION_MENU_SETTINGS = 10;
-    private static final int ACTION_MENU_COPY_TO = 11;
-    private static final int ACTION_MENU_MOVE_TO = 12;
-    private static final int ACTION_MENU_DELETE = 13;
-    private static final int ACTION_MENU_RENAME = 14;
-    private static final int ACTION_MENU_CREATE_DIR = 15;
-    private static final int ACTION_MENU_SELECT_ALL = 16;
-    private static final int ACTION_MENU_SHARE = 17;
-    private static final int ACTION_MENU_OPEN = 18;
-    private static final int ACTION_MENU_ADVANCED = 19;
+    public static final int USER_ACTION_OTHER = 1;
+    public static final int USER_ACTION_GRID = 2;
+    public static final int USER_ACTION_LIST = 3;
+    public static final int USER_ACTION_SORT_NAME = 4;
+    public static final int USER_ACTION_SORT_DATE = 5;
+    public static final int USER_ACTION_SORT_SIZE = 6;
+    public static final int USER_ACTION_SEARCH = 7;
+    public static final int USER_ACTION_SHOW_SIZE = 8;
+    public static final int USER_ACTION_HIDE_SIZE = 9;
+    public static final int USER_ACTION_SETTINGS = 10;
+    public static final int USER_ACTION_COPY_TO = 11;
+    public static final int USER_ACTION_MOVE_TO = 12;
+    public static final int USER_ACTION_DELETE = 13;
+    public static final int USER_ACTION_RENAME = 14;
+    public static final int USER_ACTION_CREATE_DIR = 15;
+    public static final int USER_ACTION_SELECT_ALL = 16;
+    public static final int USER_ACTION_SHARE = 17;
+    public static final int USER_ACTION_OPEN = 18;
+    public static final int USER_ACTION_SHOW_ADVANCED = 19;
+    public static final int USER_ACTION_HIDE_ADVANCED = 20;
+    public static final int USER_ACTION_NEW_WINDOW = 21;
+    public static final int USER_ACTION_PASTE_CLIPBOARD = 22;
+    public static final int USER_ACTION_COPY_CLIPBOARD = 23;
+    public static final int USER_ACTION_DRAG_N_DROP = 24;
+    public static final int USER_ACTION_DRAG_N_DROP_MULTI_WINDOW = 25;
 
     @IntDef(flag = false, value = {
-            ACTION_MENU_OTHER,
-            ACTION_MENU_GRID,
-            ACTION_MENU_LIST,
-            ACTION_MENU_SORT,
-            ACTION_MENU_SORT_NAME,
-            ACTION_MENU_SORT_DATE,
-            ACTION_MENU_SORT_SIZE,
-            ACTION_MENU_SHOW_SIZE,
-            ACTION_MENU_SETTINGS,
-            ACTION_MENU_COPY_TO,
-            ACTION_MENU_MOVE_TO,
-            ACTION_MENU_DELETE,
-            ACTION_MENU_RENAME,
-            ACTION_MENU_CREATE_DIR,
-            ACTION_MENU_SELECT_ALL,
-            ACTION_MENU_SHARE,
-            ACTION_MENU_OPEN,
-            ACTION_MENU_ADVANCED
+            USER_ACTION_OTHER,
+            USER_ACTION_GRID,
+            USER_ACTION_LIST,
+            USER_ACTION_SORT_NAME,
+            USER_ACTION_SORT_DATE,
+            USER_ACTION_SORT_SIZE,
+            USER_ACTION_SEARCH,
+            USER_ACTION_SHOW_SIZE,
+            USER_ACTION_HIDE_SIZE,
+            USER_ACTION_SETTINGS,
+            USER_ACTION_COPY_TO,
+            USER_ACTION_MOVE_TO,
+            USER_ACTION_DELETE,
+            USER_ACTION_RENAME,
+            USER_ACTION_CREATE_DIR,
+            USER_ACTION_SELECT_ALL,
+            USER_ACTION_SHARE,
+            USER_ACTION_OPEN,
+            USER_ACTION_SHOW_ADVANCED,
+            USER_ACTION_HIDE_ADVANCED,
+            USER_ACTION_NEW_WINDOW,
+            USER_ACTION_PASTE_CLIPBOARD,
+            USER_ACTION_COPY_CLIPBOARD,
+            USER_ACTION_DRAG_N_DROP,
+            USER_ACTION_DRAG_N_DROP_MULTI_WINDOW
     })
     @Retention(RetentionPolicy.SOURCE)
-    public @interface MenuAction {}
+    public @interface UserAction {}
 
     // Codes representing different menu actions. These are used for bucketing stats in the
     // COUNT_MENU_ACTION histogram.
@@ -291,31 +301,6 @@
     @Retention(RetentionPolicy.SOURCE)
     public @interface MetricsAction {}
 
-    // Codes representing different keyboard shortcut triggered actions. These are used for
-    // bucketing stats in the COUNT_KEYBOARD_ACTION histogram.
-    // Do not change or rearrange these values, that will break historical data. Only add to the
-    // list.
-    // Do not use negative numbers or zero; clearcut only handles positive integers.
-    public static final int ACTION_KEYBOARD_OTHER = 1;
-    public static final int ACTION_KEYBOARD_PASTE = 2;
-    public static final int ACTION_KEYBOARD_COPY = 3;
-    public static final int ACTION_KEYBOARD_DELETE = 4;
-    public static final int ACTION_KEYBOARD_SELECT_ALL = 5;
-    public static final int ACTION_KEYBOARD_BACK = 6;
-    public static final int ACTION_KEYBOARD_SWITCH_FOCUS = 7;
-
-    @IntDef(flag = false, value = {
-            ACTION_KEYBOARD_OTHER,
-            ACTION_KEYBOARD_PASTE,
-            ACTION_KEYBOARD_COPY,
-            ACTION_KEYBOARD_DELETE,
-            ACTION_KEYBOARD_SELECT_ALL,
-            ACTION_KEYBOARD_BACK,
-            ACTION_KEYBOARD_SWITCH_FOCUS
-    })
-    @Retention(RetentionPolicy.SOURCE)
-    public @interface KeyboardAction {}
-
     // Codes representing different actions to open the drawer. They are used for bucketing stats in
     // the COUNT_DRAWER_OPENED histogram.
     // Do not change or rearrange these values, that will break historical data. Only add to the
@@ -382,15 +367,6 @@
     }
 
     /**
-     * Logs a multi-window start. Call this when the user spawns a new DocumentsUI window.
-     *
-     * @param context
-     */
-    public static void logMultiWindow(Context context) {
-        logCount(context, COUNT_MULTI_WINDOW);
-    }
-
-    /**
      * Logs a drawer opened event. Call this when the user opens drawer by swipe or by clicking the
      * hamburger icon.
      * @param context
@@ -496,7 +472,7 @@
      * @param context
      */
     public static void logCreateDirError(Context context) {
-        logHistogram(context, COUNT_FILEOP_SYSTEM, FILEOP_CREATE_DIR);
+        logHistogram(context, COUNT_FILEOP_SYSTEM, FILEOP_CREATE_DIR_ERROR);
     }
 
     /**
@@ -520,16 +496,6 @@
     }
 
     /**
-     * Logs keyboard shortcut actions. Since keyboard shortcuts have their corresponding menu items,
-     * they are identified by menu item resource id for convenience.
-     * @param context
-     * @param keyCode
-     */
-    public static void logKeyboardAction(Context context, @KeyboardAction int action) {
-        logHistogram(context, COUNT_KEYBOARD_ACTION, action);
-    }
-
-    /**
      * Logs startup time in milliseconds.
      * @param context
      * @param startupMs Startup time in milliseconds.
@@ -538,25 +504,6 @@
         logHistogram(context, COUNT_STARTUP_MS, startupMs);
     }
 
-    /**
-     * Logs a drag and drop action. Call this when the user drops the content triggering copy.
-     * operation.
-     *
-     * @param context
-     */
-    public static void logDragNDrop(Context context) {
-        logCount(context, COUNT_DRAG_N_DROP);
-    }
-
-    /**
-     * Logs a search. Call this when the search operation is finished.
-     *
-     * @param context
-     */
-    public static void logSearch(Context context) {
-        logCount(context, COUNT_SEARCH);
-    }
-
     private static void logInterProviderFileOps(
             Context context,
             String histogram,
@@ -677,71 +624,12 @@
     }
 
     /**
-     * Logs menu action that was selected by user.
+     * Logs the action that was started by user.
      * @param context
-     * @param id Resource id of the menu item.
+     * @param userAction
      */
-    public static void logMenuAction(Context context, int id) {
-        @MenuAction int menuAction = ACTION_MENU_OTHER;
-        switch (id) {
-            case R.id.menu_grid:
-                menuAction = ACTION_MENU_GRID;
-                break;
-            case R.id.menu_list:
-                menuAction = ACTION_MENU_LIST;
-                break;
-            case R.id.menu_sort:
-                menuAction = ACTION_MENU_SORT;
-                break;
-            case R.id.menu_sort_name:
-                menuAction = ACTION_MENU_SORT_NAME;
-                break;
-            case R.id.menu_sort_date:
-                menuAction = ACTION_MENU_SORT_DATE;
-                break;
-            case R.id.menu_sort_size:
-                menuAction = ACTION_MENU_SORT_SIZE;
-                break;
-            case R.id.menu_search:
-                menuAction = ACTION_MENU_SEARCH;
-                break;
-            case R.id.menu_file_size:
-                menuAction = ACTION_MENU_SHOW_SIZE;
-                break;
-            case R.id.menu_settings:
-                menuAction = ACTION_MENU_SETTINGS;
-                break;
-            case R.id.menu_copy_to:
-                menuAction = ACTION_MENU_COPY_TO;
-                break;
-            case R.id.menu_move_to:
-                menuAction = ACTION_MENU_MOVE_TO;
-                break;
-            case R.id.menu_delete:
-                menuAction = ACTION_MENU_DELETE;
-                break;
-            case R.id.menu_rename:
-                menuAction = ACTION_MENU_RENAME;
-                break;
-            case R.id.menu_create_dir:
-                menuAction = ACTION_MENU_CREATE_DIR;
-                break;
-            case R.id.menu_select_all:
-                menuAction = ACTION_MENU_SELECT_ALL;
-                break;
-            case R.id.menu_share:
-                menuAction = ACTION_MENU_SHARE;
-                break;
-            case R.id.menu_open:
-                menuAction = ACTION_MENU_OPEN;
-                break;
-            case R.id.menu_advanced:
-                menuAction = ACTION_MENU_ADVANCED;
-                break;
-            default:
-                break;
-        }
-        logHistogram(context, COUNT_MENU_ACTION, menuAction);
+    public static void logUserAction(Context context, @UserAction int userAction) {
+        logHistogram(context, COUNT_USER_ACTION, userAction);
     }
 
     /**
diff --git a/packages/DocumentsUI/src/com/android/documentsui/SearchViewManager.java b/packages/DocumentsUI/src/com/android/documentsui/SearchViewManager.java
index 945ed34..11b8891 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/SearchViewManager.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/SearchViewManager.java
@@ -185,9 +185,6 @@
         if(mFullBar) {
             Menu menu = mActionBar.getMenu();
             menu.setGroupVisible(R.id.group_hide_when_searching, false);
-        } else {
-            // If search in full-bar mode it will be logged in FilesActivity#onOptionsItemSelected
-            Metrics.logMenuAction(mActionBar.getContext(), R.id.menu_search);
         }
     }
 
diff --git a/packages/DocumentsUI/src/com/android/documentsui/dirlist/DirectoryFragment.java b/packages/DocumentsUI/src/com/android/documentsui/dirlist/DirectoryFragment.java
index 1c85a8a..aa9f356 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/dirlist/DirectoryFragment.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/dirlist/DirectoryFragment.java
@@ -605,8 +605,6 @@
 
         @Override
         public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
-            Metrics.logMenuAction(getContext(), item.getItemId());
-
             Selection selection = mSelectionManager.getSelection(new Selection());
 
             switch (item.getItemId()) {
@@ -674,6 +672,8 @@
     }
 
     private void openDocuments(final Selection selected) {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_OPEN);
+
         new GetDocumentsTask() {
             @Override
             void onDocumentsReady(List<DocumentInfo> docs) {
@@ -684,6 +684,8 @@
     }
 
     private void shareDocuments(final Selection selected) {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_SHARE);
+
         new GetDocumentsTask() {
             @Override
             void onDocumentsReady(List<DocumentInfo> docs) {
@@ -765,6 +767,8 @@
     }
 
     private void deleteDocuments(final Selection selected) {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_DELETE);
+
         assert(!selected.isEmpty());
 
         final DocumentInfo srcParent = getDisplayState().stack.peek();
@@ -815,6 +819,12 @@
     }
 
     private void transferDocuments(final Selection selected, final @OpType int mode) {
+        if(mode == FileOperationService.OPERATION_COPY) {
+            Metrics.logUserAction(getContext(), Metrics.USER_ACTION_COPY_TO);
+        } else if (mode == FileOperationService.OPERATION_MOVE) {
+            Metrics.logUserAction(getContext(), Metrics.USER_ACTION_MOVE_TO);
+        }
+
         // Pop up a dialog to pick a destination.  This is inadequate but works for now.
         // TODO: Implement a picker that is to spec.
         final Intent intent = new Intent(
@@ -823,6 +833,15 @@
                 getActivity(),
                 DocumentsActivity.class);
 
+
+        // Relay any config overrides bits present in the original intent.
+        Intent original = getActivity().getIntent();
+        if (original != null && original.hasExtra(Shared.EXTRA_PRODUCTIVITY_MODE)) {
+            intent.putExtra(
+                    Shared.EXTRA_PRODUCTIVITY_MODE,
+                    original.getBooleanExtra(Shared.EXTRA_PRODUCTIVITY_MODE, false));
+        }
+
         // Set an appropriate title on the drawer when it is shown in the picker.
         // Coupled with the fact that we auto-open the drawer for copy/move operations
         // it should basically be the thing people see first.
@@ -861,6 +880,8 @@
     }
 
     private void renameDocuments(Selection selected) {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_RENAME);
+
         // Batch renaming not supported
         // Rename option is only available in menu when 1 document selected
         assert(selected.size() == 1);
@@ -1020,6 +1041,8 @@
     }
 
     public void copySelectedToClipboard() {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_COPY_CLIPBOARD);
+
         Selection selection = mSelectionManager.getSelection(new Selection());
         if (!selection.isEmpty()) {
             copySelectionToClipboard(selection);
@@ -1043,6 +1066,8 @@
     }
 
     public void pasteFromClipboard() {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_PASTE_CLIPBOARD);
+
         copyFromClipboard();
         getActivity().invalidateOptionsMenu();
     }
@@ -1073,6 +1098,8 @@
     }
 
     public void selectAllFiles() {
+        Metrics.logUserAction(getContext(), Metrics.USER_ACTION_SELECT_ALL);
+
         // Exclude disabled files
         List<String> enabled = new ArrayList<String>();
         for (String id : mAdapter.getModelIds()) {
@@ -1147,7 +1174,14 @@
                     if (Objects.equals(src, dst)) {
                         return false;
                     }
-                    Metrics.logDragNDrop(getContext());
+                    // Recognize multi-window drag and drop based on the fact that localState is not
+                    // carried between processes. It will stop working when the localsState behavior
+                    // is changed. The info about window should be passed in the localState then.
+                    // The localState could also be null for copying from Recents in single window
+                    // mode, but Recents doesn't offer this functionality (no directories).
+                    Metrics.logUserAction(getContext(),
+                            src == null ? Metrics.USER_ACTION_DRAG_N_DROP_MULTI_WINDOW
+                                    : Metrics.USER_ACTION_DRAG_N_DROP);
                     copyFromClipData(event.getClipData(), dst);
                     return true;
             }
@@ -1387,7 +1421,6 @@
                     // This has to be handled here instead of in a keyboard shortcut, because
                     // keyboard shortcuts all have to be modified with the 'Ctrl' key.
                     if (mSelectionManager.hasSelection()) {
-                        Metrics.logKeyboardAction(getContext(), Metrics.ACTION_KEYBOARD_DELETE);
                         deleteDocuments(mSelectionManager.getSelection());
                     }
                     // Always handle the key, even if there was nothing to delete. This is a
@@ -1674,8 +1707,9 @@
     @Override
     public void onLoadFinished(Loader<DirectoryResult> loader, DirectoryResult result) {
         if (!isAdded()) return;
+
         if (mSearchMode) {
-            Metrics.logSearch(getContext());
+            Metrics.logUserAction(getContext(), Metrics.USER_ACTION_SEARCH);
         }
 
         State state = getDisplayState();
diff --git a/packages/DocumentsUI/src/com/android/documentsui/dirlist/DocumentHolder.java b/packages/DocumentsUI/src/com/android/documentsui/dirlist/DocumentHolder.java
index 450341f..2288fe74 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/dirlist/DocumentHolder.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/dirlist/DocumentHolder.java
@@ -139,11 +139,13 @@
             }
 
             // Do everything in global coordinates - it makes things simpler.
-            Rect rect = new Rect();
-            mSelectionHotspot.getGlobalVisibleRect(rect);
+            int[] coords = new int[2];
+            mSelectionHotspot.getLocationOnScreen(coords);
+            Rect rect = new Rect(coords[0], coords[1], coords[0] + mSelectionHotspot.getWidth(),
+                    coords[1] + mSelectionHotspot.getHeight());
 
             // If the tap occurred within the icon rect, consider it a selection.
-            if (rect.contains((int)event.getRawX(), (int)event.getRawY())) {
+            if (rect.contains((int) event.getRawX(), (int) event.getRawY())) {
                 return mEventListener.onSelect(this);
             } else {
                 return mEventListener.onActivate(this);
diff --git a/packages/DocumentsUI/src/com/android/documentsui/dirlist/MultiSelectManager.java b/packages/DocumentsUI/src/com/android/documentsui/dirlist/MultiSelectManager.java
index b80486d..1285b34 100644
--- a/packages/DocumentsUI/src/com/android/documentsui/dirlist/MultiSelectManager.java
+++ b/packages/DocumentsUI/src/com/android/documentsui/dirlist/MultiSelectManager.java
@@ -672,9 +672,9 @@
         /**
          * Used by CREATOR.
          */
-        private Selection(String directoryKey, List<String> selection) {
+        private Selection(String directoryKey, Set<String> selection) {
             mDirectoryKey = directoryKey;
-            mSelection = new HashSet<String>(selection);
+            mSelection = selection;
             mProvisionalSelection = new HashSet<String>();
         }
 
@@ -887,7 +887,7 @@
 
         public void writeToParcel(Parcel dest, int flags) {
             dest.writeString(mDirectoryKey);
-            dest.writeList(new ArrayList<>(mSelection));
+            dest.writeStringList(new ArrayList<>(mSelection));
             // We don't include provisional selection since it is
             // typically coupled to some other runtime state (like a band).
         }
@@ -901,9 +901,12 @@
 
             @Override
             public Selection createFromParcel(Parcel in, ClassLoader loader) {
-                return new Selection(
-                        in.readString(),
-                        in.readArrayList(loader));
+                String directoryKey = in.readString();
+
+                ArrayList<String> selected = new ArrayList<>();
+                in.readStringList(selected);
+
+                return new Selection(directoryKey, new HashSet<String>(selected));
             }
 
             @Override
diff --git a/packages/ExtServices/res/values/strings.xml b/packages/ExtServices/res/values/strings.xml
index 0763403..b77ff10 100644
--- a/packages/ExtServices/res/values/strings.xml
+++ b/packages/ExtServices/res/values/strings.xml
@@ -17,4 +17,5 @@
 <resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_name">Android Services Library</string>
     <string name="notification_ranker">Android Notification Ranking Service</string>
+    <string name="notification_ranker_autobundle_explanation">Auto-grouping updated by Ranking Service</string>
 </resources>
diff --git a/packages/ExtServices/src/android/ext/services/notification/Ranker.java b/packages/ExtServices/src/android/ext/services/notification/Ranker.java
index 0b2b1a4..3ef2aea 100644
--- a/packages/ExtServices/src/android/ext/services/notification/Ranker.java
+++ b/packages/ExtServices/src/android/ext/services/notification/Ranker.java
@@ -16,16 +16,36 @@
 
 package android.ext.services.notification;
 
+import static android.service.notification.NotificationListenerService.Ranking.IMPORTANCE_UNSPECIFIED;
+
+import android.os.Bundle;
+import android.service.notification.Adjustment;
 import android.service.notification.NotificationRankerService;
 import android.service.notification.StatusBarNotification;
 import android.util.Log;
+import android.util.Slog;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.LinkedHashSet;
+import java.util.List;
+import java.util.Map;
+
+import android.ext.services.R;
 
 /**
  * Class that provides an updatable ranker module for the notification manager..
  */
 public final class Ranker extends NotificationRankerService {
     private static final String TAG = "RocketRanker";
-    private static final boolean DEBUG =  Log.isLoggable(TAG, Log.DEBUG);;
+    private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
+
+    private static final int AUTOBUNDLE_AT_COUNT = 4;
+    private static final String AUTOBUNDLE_KEY = "ranker_bundle";
+
+    // Map of package : notification keys. Only contains notifications that are not bundled
+    // by the app (aka no group or sort key).
+    Map<String, LinkedHashSet<String>> mUnbundledNotifications;
 
     @Override
     public Adjustment onNotificationEnqueued(StatusBarNotification sbn, int importance,
@@ -37,10 +57,146 @@
     @Override
     public void onNotificationPosted(StatusBarNotification sbn) {
         if (DEBUG) Log.i(TAG, "POSTED " + sbn.getKey());
+        try {
+            List<String> notificationsToBundle = new ArrayList<>();
+            if (!sbn.isGroup()) {
+                // Not grouped by the app, add to the list of notifications for the app;
+                // send bundling update if app exceeds the autobundling limit.
+                synchronized (mUnbundledNotifications) {
+                    LinkedHashSet<String> notificationsForPackage
+                            = mUnbundledNotifications.get(sbn.getPackageName());
+                    if (notificationsForPackage == null) {
+                        notificationsForPackage = new LinkedHashSet<>();
+                    }
+                    if (notificationsForPackage.contains(sbn.getKey())) {
+                        return;
+                    }
+                    notificationsForPackage.add(sbn.getKey());
+                    mUnbundledNotifications.put(sbn.getPackageName(), notificationsForPackage);
+
+                    if (notificationsForPackage.size() >= AUTOBUNDLE_AT_COUNT) {
+                        // Autobundle all but the most recently posted (not updated) notification.
+                        int count = 0;
+                        for (String key : notificationsForPackage) {
+                            if (count < notificationsForPackage.size() - 1) {
+                                notificationsToBundle.add(key);
+                            }
+                            count++;
+                        }
+                    }
+                }
+                if (notificationsToBundle.size() > 0) {
+                    adjustAutobundlingSummary(sbn.getPackageName(), notificationsToBundle.get(0),
+                            true);
+                    adjustNotificationBundling(sbn.getPackageName(), notificationsToBundle, true);
+                }
+            } else {
+                // Grouped, but not by us. Send updates to unautobundle, if we bundled it.
+                maybeUnbundle(sbn, false);
+            }
+        } catch (Exception e) {
+            Slog.e(TAG, "Failure processing new notification", e);
+        }
+    }
+
+    @Override
+    public void onNotificationRemoved(StatusBarNotification sbn) {
+        try {
+            maybeUnbundle(sbn, true);
+        } catch (Exception e) {
+            Slog.e(TAG, "Error processing canceled notification", e);
+        }
+    }
+
+    /**
+     * Un-autobundles notifications that are now grouped by the app. Additionally cancels
+     * autobundling if the status change of this notification resulted in the loose notification
+     * count being under the limit.
+     */
+    private void maybeUnbundle(StatusBarNotification sbn, boolean notificationGone) {
+        List<String> notificationsToUnAutobundle = new ArrayList<>();
+        boolean removeSummary = false;
+        synchronized (mUnbundledNotifications) {
+            LinkedHashSet<String> notificationsForPackage
+                    = mUnbundledNotifications.get(sbn.getPackageName());
+            if (notificationsForPackage == null || notificationsForPackage.size() == 0) {
+                return;
+            }
+            if (notificationsForPackage.remove(sbn.getKey())) {
+                if (!notificationGone) {
+                    // Add the current notification to the unbundling list if it still exists.
+                    notificationsToUnAutobundle.add(sbn.getKey());
+                }
+                // If the status change of this notification has brought the number of loose
+                // notifications back below the limit, remove the summary and un-autobundle.
+                if (notificationsForPackage.size() == AUTOBUNDLE_AT_COUNT - 1) {
+                    removeSummary = true;
+                    for (String key : notificationsForPackage) {
+                        notificationsToUnAutobundle.add(key);
+                    }
+                }
+            }
+        }
+        if (notificationsToUnAutobundle.size() > 0) {
+            if (removeSummary) {
+                adjustAutobundlingSummary(sbn.getPackageName(), null, false);
+            }
+            adjustNotificationBundling(sbn.getPackageName(), notificationsToUnAutobundle, false);
+        }
     }
 
     @Override
     public void onListenerConnected() {
         if (DEBUG) Log.i(TAG, "CONNECTED");
+        mUnbundledNotifications = new HashMap<>();
+        for (StatusBarNotification sbn : getActiveNotifications()) {
+            onNotificationPosted(sbn);
+        }
     }
+
+    private void adjustAutobundlingSummary(String packageName, String key, boolean summaryNeeded) {
+        Bundle signals = new Bundle();
+        if (summaryNeeded) {
+            signals.putBoolean(Adjustment.NEEDS_AUTOGROUPING_KEY, true);
+            signals.putString(Adjustment.GROUP_KEY_OVERRIDE_KEY, AUTOBUNDLE_KEY);
+        } else {
+            signals.putBoolean(Adjustment.NEEDS_AUTOGROUPING_KEY, false);
+        }
+        Adjustment adjustment = new Adjustment(packageName, key, IMPORTANCE_UNSPECIFIED, signals,
+                getContext().getString(R.string.notification_ranker_autobundle_explanation), null);
+        if (DEBUG) {
+            Log.i(TAG, "Summary update for: " + packageName + " "
+                    + (summaryNeeded ? "adding" : "removing"));
+        }
+        try {
+            adjustNotification(adjustment);
+        } catch (Exception e) {
+            Slog.e(TAG, "Adjustment failed", e);
+        }
+
+    }
+    private void adjustNotificationBundling(String packageName, List<String> keys, boolean bundle) {
+        List<Adjustment> adjustments = new ArrayList<>();
+        for (String key : keys) {
+            adjustments.add(createBundlingAdjustment(packageName, key, bundle));
+            if (DEBUG) Log.i(TAG, "Sending bundling adjustment for: " + key);
+        }
+        try {
+            adjustNotifications(adjustments);
+        } catch (Exception e) {
+            Slog.e(TAG, "Adjustments failed", e);
+        }
+    }
+
+    private Adjustment createBundlingAdjustment(String packageName, String key, boolean bundle) {
+        Bundle signals = new Bundle();
+        if (bundle) {
+            signals.putString(Adjustment.GROUP_KEY_OVERRIDE_KEY, AUTOBUNDLE_KEY);
+        } else {
+            signals.putString(Adjustment.GROUP_KEY_OVERRIDE_KEY, null);
+        }
+        return new Adjustment(packageName, key, IMPORTANCE_UNSPECIFIED, signals,
+                getContext().getString(R.string.notification_ranker_autobundle_explanation), null);
+    }
+
 }
\ No newline at end of file
diff --git a/packages/Keyguard/res/values-ar/strings.xml b/packages/Keyguard/res/values-ar/strings.xml
index 442f29e..426d60f 100644
--- a/packages/Keyguard/res/values-ar/strings.xml
+++ b/packages/Keyguard/res/values-ar/strings.xml
@@ -72,8 +72,8 @@
     <string name="kg_puk_enter_pin_hint" msgid="7871604527429602024">"‏إدخال رمز رمز PIN المراد"</string>
     <string name="kg_enter_confirm_pin_hint" msgid="325676184762529976">"‏تأكيد رمز رمز PIN المراد"</string>
     <string name="kg_sim_unlock_progress_dialog_message" msgid="8950398016976865762">"‏جارٍ إلغاء تأمين شريحة SIM…"</string>
-    <string name="kg_invalid_sim_pin_hint" msgid="8795159358110620001">"‏اكتب رمز PIN المكون من 4 إلى 8 أرقام."</string>
-    <string name="kg_invalid_sim_puk_hint" msgid="7553388325654369575">"‏يجب أن يتضمن رمز PUK‏ 8 أرقام أو أكثر."</string>
+    <string name="kg_invalid_sim_pin_hint" msgid="8795159358110620001">"اكتب  رقم التعريف الشخصي المكون من ٤ إلى ٨ أرقام."</string>
+    <string name="kg_invalid_sim_puk_hint" msgid="7553388325654369575">"‏يجب أن يتضمن رمز PUK‏ ۸ أرقام أو أكثر."</string>
     <string name="kg_invalid_puk" msgid="3638289409676051243">"‏أعد إدخال رمز PUK الصحيح. وستؤدي المحاولات المتكررة إلى تعطيل شريحة SIM نهائيًا."</string>
     <string name="kg_invalid_confirm_pin_hint" product="default" msgid="7003469261464593516">"‏لا يتطابق رمزا رمز PIN"</string>
     <string name="kg_login_too_many_attempts" msgid="6486842094005698475">"محاولات النقش كثيرة جدًا"</string>
diff --git a/packages/MtpDocumentsProvider/jni/com_android_mtp_AppFuse.cpp b/packages/MtpDocumentsProvider/jni/com_android_mtp_AppFuse.cpp
index eb96015..7c8806e 100644
--- a/packages/MtpDocumentsProvider/jni/com_android_mtp_AppFuse.cpp
+++ b/packages/MtpDocumentsProvider/jni/com_android_mtp_AppFuse.cpp
@@ -14,7 +14,6 @@
  * limitations under the License.
  */
 
-#define LOG_NDEBUG 0
 #define LOG_TAG "AppFuseJNI"
 #include "utils/Log.h"
 
@@ -451,7 +450,7 @@
     ScopedFd fd(static_cast<int>(jfd));
     AppFuse appfuse(env, self);
 
-    ALOGD("Start fuse loop.");
+    ALOGV("Start fuse loop.");
     while (true) {
         FuseRequest request;
 
diff --git a/packages/MtpDocumentsProvider/src/com/android/mtp/DocumentLoader.java b/packages/MtpDocumentsProvider/src/com/android/mtp/DocumentLoader.java
index 246b95de..6ed4ea1 100644
--- a/packages/MtpDocumentsProvider/src/com/android/mtp/DocumentLoader.java
+++ b/packages/MtpDocumentsProvider/src/com/android/mtp/DocumentLoader.java
@@ -33,7 +33,6 @@
 import java.io.FileNotFoundException;
 import java.io.IOException;
 import java.util.ArrayList;
-import java.util.Arrays;
 import java.util.Date;
 import java.util.LinkedList;
 
@@ -118,9 +117,10 @@
     synchronized @Nullable LoaderTask getNextTaskOrReleaseBackgroundThread() {
         Preconditions.checkState(mBackgroundThread != null);
 
-        final LoaderTask task = mTaskList.findRunningTask();
-        if (task != null) {
-            return task;
+        for (final LoaderTask task : mTaskList) {
+            if (task.getState() == LoaderTask.STATE_LOADING) {
+                return task;
+            }
         }
 
         final Identifier identifier = mDatabase.getUnmappedDocumentsParent(mDevice.deviceId);
@@ -161,8 +161,21 @@
         mTaskList.clearCompletedTasks();
     }
 
-    synchronized void clearTask(Identifier parentIdentifier) {
-        mTaskList.clearTask(parentIdentifier);
+    /**
+     * Cancels the task for |parentIdentifier|.
+     *
+     * Task is removed from the cached list and it will create new task when |parentIdentifier|'s
+     * children are queried next.
+     */
+    void cancelTask(Identifier parentIdentifier) {
+        final LoaderTask task;
+        synchronized (this) {
+            task = mTaskList.findTask(parentIdentifier);
+        }
+        if (task != null) {
+            task.cancel();
+            mTaskList.remove(task);
+        }
     }
 
     /**
@@ -183,9 +196,10 @@
                 }
                 task.loadObjectInfoList(NUM_LOADING_ENTRIES);
                 final boolean shouldNotify =
-                        task.mLastNotified.getTime() <
-                        new Date().getTime() - NOTIFY_PERIOD_MS ||
-                        task.getState() != LoaderTask.STATE_LOADING;
+                        task.getState() != LoaderTask.STATE_CANCELLED &&
+                        (task.mLastNotified.getTime() <
+                         new Date().getTime() - NOTIFY_PERIOD_MS ||
+                         task.getState() != LoaderTask.STATE_LOADING);
                 if (shouldNotify) {
                     task.notify(mResolver);
                 }
@@ -205,14 +219,6 @@
             return null;
         }
 
-        LoaderTask findRunningTask() {
-            for (int i = 0; i < size(); i++) {
-                if (get(i).getState() == LoaderTask.STATE_LOADING)
-                    return get(i);
-            }
-            return null;
-        }
-
         void clearCompletedTasks() {
             int i = 0;
             while (i < size()) {
@@ -223,17 +229,6 @@
                 }
             }
         }
-
-        void clearTask(Identifier parentIdentifier) {
-            for (int i = 0; i < size(); i++) {
-                final LoaderTask task = get(i);
-                if (task.mIdentifier.mDeviceId == parentIdentifier.mDeviceId &&
-                        task.mIdentifier.mObjectHandle == parentIdentifier.mObjectHandle) {
-                    remove(i);
-                    return;
-                }
-            }
-        }
     }
 
     /**
@@ -245,6 +240,7 @@
         static final int STATE_LOADING = 1;
         static final int STATE_COMPLETED = 2;
         static final int STATE_ERROR = 3;
+        static final int STATE_CANCELLED = 4;
 
         final MtpManager mManager;
         final MtpDatabase mDatabase;
@@ -272,6 +268,7 @@
 
         synchronized void loadObjectHandles() {
             assert mState == STATE_START;
+            mPosition = 0;
             int parentHandle = mIdentifier.mObjectHandle;
             // Need to pass the special value MtpManager.OBJECT_HANDLE_ROOT_CHILDREN to
             // getObjectHandles if we would like to obtain children under the root.
@@ -303,12 +300,10 @@
                 case STATE_ERROR:
                     throw mError;
             }
-
             final Cursor cursor =
                     mDatabase.queryChildDocuments(columnNames, mIdentifier.mDocumentId);
+            cursor.setExtras(extras);
             cursor.setNotificationUri(resolver, createUri());
-            cursor.respond(extras);
-
             return cursor;
         }
 
@@ -374,6 +369,10 @@
                 }
             }
             synchronized (this) {
+                // Check if the task is cancelled or not.
+                if (mState != STATE_LOADING) {
+                    return;
+                }
                 try {
                     mDatabase.getMapper().putChildDocuments(
                             mIdentifier.mDeviceId,
@@ -403,6 +402,14 @@
         }
 
         /**
+         * Cancels the task.
+         */
+        synchronized void cancel() {
+            mDatabase.getMapper().cancelAddingDocuments(mIdentifier.mDocumentId);
+            mState = STATE_CANCELLED;
+        }
+
+        /**
          * Returns a state of the task.
          */
         int getState() {
diff --git a/packages/MtpDocumentsProvider/src/com/android/mtp/Mapper.java b/packages/MtpDocumentsProvider/src/com/android/mtp/Mapper.java
index adc71ae..63f18f3 100644
--- a/packages/MtpDocumentsProvider/src/com/android/mtp/Mapper.java
+++ b/packages/MtpDocumentsProvider/src/com/android/mtp/Mapper.java
@@ -363,6 +363,41 @@
     }
 
     /**
+     * Cancels adding documents.
+     * @param parentId
+     */
+    void cancelAddingDocuments(@Nullable String parentId) {
+        final String selection;
+        final String[] args;
+        if (parentId != null) {
+            selection = COLUMN_PARENT_DOCUMENT_ID + " = ?";
+            args = strings(parentId);
+        } else {
+            selection = COLUMN_PARENT_DOCUMENT_ID + " IS NULL";
+            args = EMPTY_ARGS;
+        }
+
+        final SQLiteDatabase database = mDatabase.getSQLiteDatabase();
+        database.beginTransaction();
+        try {
+            if (!mInMappingIds.contains(parentId)) {
+                return;
+            }
+            mInMappingIds.remove(parentId);
+            final ContentValues values = new ContentValues();
+            values.put(COLUMN_ROW_STATE, ROW_STATE_VALID);
+            mDatabase.getSQLiteDatabase().update(
+                    TABLE_DOCUMENTS,
+                    values,
+                    selection + " AND " + COLUMN_ROW_STATE + " = ?",
+                    DatabaseUtils.appendSelectionArgs(args, strings(ROW_STATE_INVALIDATED)));
+            database.setTransactionSuccessful();
+        } finally {
+            database.endTransaction();
+        }
+    }
+
+    /**
      * Queries candidate for each mappingKey, and returns the first cursor that includes a
      * candidate.
      *
diff --git a/packages/MtpDocumentsProvider/src/com/android/mtp/MtpDocumentsProvider.java b/packages/MtpDocumentsProvider/src/com/android/mtp/MtpDocumentsProvider.java
index 50781bf..1823711 100644
--- a/packages/MtpDocumentsProvider/src/com/android/mtp/MtpDocumentsProvider.java
+++ b/packages/MtpDocumentsProvider/src/com/android/mtp/MtpDocumentsProvider.java
@@ -308,7 +308,7 @@
             final Identifier parentIdentifier = mDatabase.getParentIdentifier(documentId);
             mMtpManager.deleteDocument(identifier.mDeviceId, identifier.mObjectHandle);
             mDatabase.deleteDocument(documentId);
-            getDocumentLoader(parentIdentifier).clearTask(parentIdentifier);
+            getDocumentLoader(parentIdentifier).cancelTask(parentIdentifier);
             notifyChildDocumentsChange(parentIdentifier.mDocumentId);
             if (parentIdentifier.mDocumentType == MtpDatabaseConstants.DOCUMENT_TYPE_STORAGE) {
                 // If the parent is storage, the object might be appeared as child of device because
@@ -402,7 +402,7 @@
             final String documentId = mDatabase.putNewDocument(
                     parentId.mDeviceId, parentDocumentId, record.operationsSupported,
                     infoWithHandle, 0l);
-            getDocumentLoader(parentId).clearTask(parentId);
+            getDocumentLoader(parentId).cancelTask(parentId);
             notifyChildDocumentsChange(parentDocumentId);
             return documentId;
         } catch (FileNotFoundException | RuntimeException error) {
diff --git a/packages/MtpDocumentsProvider/tests/src/com/android/mtp/DocumentLoaderTest.java b/packages/MtpDocumentsProvider/tests/src/com/android/mtp/DocumentLoaderTest.java
index 45f89e4..a3c6bd7 100644
--- a/packages/MtpDocumentsProvider/tests/src/com/android/mtp/DocumentLoaderTest.java
+++ b/packages/MtpDocumentsProvider/tests/src/com/android/mtp/DocumentLoaderTest.java
@@ -21,6 +21,7 @@
 import android.mtp.MtpObjectInfo;
 import android.net.Uri;
 import android.provider.DocumentsContract;
+import android.provider.DocumentsContract.Document;
 import android.test.AndroidTestCase;
 import android.test.suitebuilder.annotation.MediumTest;
 
@@ -28,6 +29,7 @@
 import java.util.HashMap;
 import java.util.Map;
 import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeoutException;
 
 @MediumTest
 public class DocumentLoaderTest extends AndroidTestCase {
@@ -141,6 +143,38 @@
         }
     }
 
+    public void testCancelTask() throws IOException, InterruptedException, TimeoutException {
+        setUpDocument(mManager,
+                DocumentLoader.NUM_INITIAL_ENTRIES + 1);
+
+        // Block the first iteration in the background thread.
+        mManager.blockDocument(
+                0, DocumentLoader.NUM_INITIAL_ENTRIES + 1);
+        setUpLoader();
+        try (final Cursor cursor = mLoader.queryChildDocuments(
+                MtpDocumentsProvider.DEFAULT_DOCUMENT_PROJECTION, mParentIdentifier)) {
+            assertTrue(cursor.getExtras().getBoolean(DocumentsContract.EXTRA_LOADING));
+        }
+
+        final Uri uri = DocumentsContract.buildChildDocumentsUri(
+                MtpDocumentsProvider.AUTHORITY, mParentIdentifier.mDocumentId);
+        assertEquals(0, mResolver.getChangeCount(uri));
+
+        // Clear task while the first iteration is being blocked.
+        mLoader.cancelTask(mParentIdentifier);
+        mManager.unblockDocument(
+                0, DocumentLoader.NUM_INITIAL_ENTRIES + 1);
+        Thread.sleep(DocumentLoader.NOTIFY_PERIOD_MS);
+        assertEquals(0, mResolver.getChangeCount(uri));
+
+        // Check if it's OK to query invalidated task.
+        try (final Cursor cursor = mLoader.queryChildDocuments(
+                MtpDocumentsProvider.DEFAULT_DOCUMENT_PROJECTION, mParentIdentifier)) {
+            assertTrue(cursor.getExtras().getBoolean(DocumentsContract.EXTRA_LOADING));
+        }
+        mResolver.waitForNotification(uri, 1);
+    }
+
     private void setUpLoader() {
         mLoader = new DocumentLoader(
                 new MtpDeviceRecord(
diff --git a/packages/PrintSpooler/res/values-ar/strings.xml b/packages/PrintSpooler/res/values-ar/strings.xml
index 1208298..b9d1902 100644
--- a/packages/PrintSpooler/res/values-ar/strings.xml
+++ b/packages/PrintSpooler/res/values-ar/strings.xml
@@ -30,7 +30,7 @@
     <string name="destination_default_text" msgid="5422708056807065710">"اختر طابعة"</string>
     <string name="template_all_pages" msgid="3322235982020148762">"جميع الصفحات وعددها <xliff:g id="PAGE_COUNT">%1$s</xliff:g>"</string>
     <string name="template_page_range" msgid="428638530038286328">"النطاق <xliff:g id="PAGE_COUNT">%1$s</xliff:g>"</string>
-    <string name="pages_range_example" msgid="8558694453556945172">"على سبيل المثال، 1—5،8،11—13"</string>
+    <string name="pages_range_example" msgid="8558694453556945172">"مثلاً، ۱—۵،‏۹،۷—۱۰"</string>
     <string name="print_preview" msgid="8010217796057763343">"معاينة قبل الطباعة"</string>
     <string name="install_for_print_preview" msgid="6366303997385509332">"‏تثبيت برنامج عرض PDF للمعاينة"</string>
     <string name="printing_app_crashed" msgid="854477616686566398">"تعطّل تطبيق الطباعة"</string>
diff --git a/packages/SettingsLib/res/values-af/strings.xml b/packages/SettingsLib/res/values-af/strings.xml
index c44f0d0..f32cd13 100644
--- a/packages/SettingsLib/res/values-af/strings.xml
+++ b/packages/SettingsLib/res/values-af/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Hierdie kenmerk is eksperimenteel en kan werkverrigting beïnvloed."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Geneutraliseer deur <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Ongeveer <xliff:g id="TIME">%1$s</xliff:g> oor"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> oor"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – sowat <xliff:g id="TIME">%2$s</xliff:g> oor"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> oor"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> tot vol"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> tot vol op WS"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> tot vol oor USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> tot vol vanaf draadloos"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Onbekend"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Laai"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Laai tans op WS"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Laai tans"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Laai tans oor USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Laai tans"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Laai tans draadloos"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Laai tans"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Laai nie"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Laai nie"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Vol"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Groter"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Grootste"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Gepasmaak (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-am/strings.xml b/packages/SettingsLib/res/values-am/strings.xml
index cd05135..1bb27e2 100644
--- a/packages/SettingsLib/res/values-am/strings.xml
+++ b/packages/SettingsLib/res/values-am/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ይህ ባህሪ የሙከራ ነውና አፈጻጸም ላይ ተጽዕኖ ሊኖረው ይችላል።"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"በ<xliff:g id="TITLE">%1$s</xliff:g> ተሽሯል"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"<xliff:g id="TIME">%1$s</xliff:g> ገደማ ቀርቷል"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> ቀርቷል"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ገደማ <xliff:g id="TIME">%2$s</xliff:g> ይቀራል"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ይቀራል"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> እስከሚሞላ ድረስ"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> በኤሲ ላይ እስከሚሞላ ድረስ"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> በዩኤስቢ ላይ እስከሚሞላ ድረስ"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> በገመድ አልባ ላይ እስከሚሞላ ድረስ"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"ያልታወቀ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ኃይል በመሙላት ላይ"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"በኤሲ ሃይል በመሙላት ላይ"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ኃይል በመሙላት ላይ"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"በዩኤስቢ ሃይል በመሙላት ላይ"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ኃይል በመሙላት ላይ"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"በገመድ አልባ ሃይል በመሙላት ላይ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ኃይል በመሙላት ላይ"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ባትሪ እየሞላ አይደለም"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ኃይል  እየሞላ አይደለም"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ሙሉነው"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ተለቅ ያለ"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"በጣም ተለቅ ያለ"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"ብጁ (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ar/strings.xml b/packages/SettingsLib/res/values-ar/strings.xml
index b3f55eb..0f6b315 100644
--- a/packages/SettingsLib/res/values-ar/strings.xml
+++ b/packages/SettingsLib/res/values-ar/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"هذه الميزة تجريبية وقد تؤثر في الأداء."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"تم الاستبدال بـ <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"يتبقى <xliff:g id="TIME">%1$s</xliff:g> تقريبًا"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"يتبقى <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - تبقى <xliff:g id="TIME">%2$s</xliff:g> تقريبًا"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - يتبقى <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> حتى الاكتمال"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> حتى الاكتمال باستخدام التيار المتردد"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"‏<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> حتى الاكتمال عبر USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> حتى الاكتمال بالشحن اللاسلكي"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"غير معروف"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"شحن"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"جارٍ الشحن بتيار متردد"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"جارٍ الشحن"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"‏جارٍ الشحن عبر USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"جارٍ الشحن"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"جارٍ الشحن لاسلكيًا"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"جارٍ الشحن"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"لا يتم الشحن"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"لا يتم الشحن"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ممتلئة"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"أكبر"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"أكبر مستوى"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"مخصص (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-az-rAZ/strings.xml b/packages/SettingsLib/res/values-az-rAZ/strings.xml
index 9a099af..5b2214a 100644
--- a/packages/SettingsLib/res/values-az-rAZ/strings.xml
+++ b/packages/SettingsLib/res/values-az-rAZ/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Bu funksiya eksperimentaldır və performansa təsir edə bilər."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> tərəfindən qəbul edilmir"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Təxminən <xliff:g id="TIME">%1$s</xliff:g> qalıb"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> qalıb"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - təxminən <xliff:g id="TIME">%2$s</xliff:g> qalıb"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> qalıb"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> dolana qədər"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC üzərindən dolana qədər"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB üzərindən dolana qədər"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> naqilsiz üzərindən dolana qədər"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Naməlum"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Enerji doldurma"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Dəyişən cərəyanda qidalanır"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Qidalanır"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB üzərindən qidalanır"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Qidalanır"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Naqilsiz qidalanır"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Qidalanır"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Doldurulmur"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Enerji doldurulmur"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Tam"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Daha böyük"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Ən böyük"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Fərdi (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-b+sr+Latn/strings.xml b/packages/SettingsLib/res/values-b+sr+Latn/strings.xml
index 85b6ac2..e361efd 100644
--- a/packages/SettingsLib/res/values-b+sr+Latn/strings.xml
+++ b/packages/SettingsLib/res/values-b+sr+Latn/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ova funkcija je eksperimentalna i može da utiče na performanse."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Zamenjuje ga <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Još otprilike <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Preostalo vreme: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – preostalo oko <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"Preostalo je <xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> dok se ne napuni"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> dok se ne napuni punjačem"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> dok se ne napuni preko USB-a"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> dok se ne napuni bežično"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Nepoznato"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Punjenje"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Punjenje preko punjača"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Puni se"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Punjenje preko USB-a"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Puni se"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Bežično punjenje"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Puni se"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ne puni se"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ne puni se"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Puno"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Veći"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Najveći"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Prilagođeni (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-be-rBY/strings.xml b/packages/SettingsLib/res/values-be-rBY/strings.xml
index c8098ec..05c6d9af 100644
--- a/packages/SettingsLib/res/values-be-rBY/strings.xml
+++ b/packages/SettingsLib/res/values-be-rBY/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Гэтая функцыя з\'яўляецца эксперыментальнай і можа паўплываць на прадукцыйнасць."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Перавызначаны <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Засталося прыблізна <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Засталося <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – засталося прыблізна <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – засталося <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> да поўнай зарадкі"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> да поўнай зарадкі ад сеткі пер. току"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> да поўнай зарадкі па USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> да поўн. зарадкі бесправадным шляхам"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Невядома"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Зарадка"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Зар. ад сеткі пер. току"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Зарадка"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Зарадка па USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Зарадка"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Бесправадная зарадка"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Зарадка"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Не зараджаецца"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Не зараджаецца"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Поўная"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Большы"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Найвялікшы"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Карыстальніцкі (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-bg/strings.xml b/packages/SettingsLib/res/values-bg/strings.xml
index 35b24bf..f596b04 100644
--- a/packages/SettingsLib/res/values-bg/strings.xml
+++ b/packages/SettingsLib/res/values-bg/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Тази функция е експериментална и може да се отрази на ефективността."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Заменено от „<xliff:g id="TITLE">%1$s</xliff:g>“"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Прибл. оставащо време: <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Оставащо време: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – приблизително оставащо време: <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – оставащо време: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до пълно зареждане"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до пълно зареждане при променлив ток"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> ˜– <xliff:g id="TIME">%2$s</xliff:g> до пълно зареждане през USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до пълно безжично зареждане"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Неизвестно"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Зарежда се"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Зареждане при AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Зарежда се"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Зареждане през USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Зарежда се"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Безжично зареждане"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Зарежда се"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Не се зарежда"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Не се зарежда"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Пълна"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"По-голямо"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Най-голямо"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Персонализирано (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-bn-rBD/strings.xml b/packages/SettingsLib/res/values-bn-rBD/strings.xml
index 14c2c95..f691278 100644
--- a/packages/SettingsLib/res/values-bn-rBD/strings.xml
+++ b/packages/SettingsLib/res/values-bn-rBD/strings.xml
@@ -331,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"খুব বড়"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"বৃহত্তম"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"কাস্টম (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-bs-rBA/strings.xml b/packages/SettingsLib/res/values-bs-rBA/strings.xml
index f9c7fcad..e4bd011 100644
--- a/packages/SettingsLib/res/values-bs-rBA/strings.xml
+++ b/packages/SettingsLib/res/values-bs-rBA/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ova funkcija je eksperimentalna te može utjecati na performanse."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Zamjenjuje <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Još otprilike <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Imate još <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – preostalo vreme je otprilike <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - imate još <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pune baterije"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do kraja punjenja na el. napajanju"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pune baterije preko USB-a"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pune baterije bežičnim punjenjem"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Nepoznato"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Puni se"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Puni se na punjaču"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Punjenje"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Punjenje preko USB-a"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Punjenje"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Bežično punjenje"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Punjenje"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ne puni se"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ne puni se"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Puna"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Veće"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Najveće"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Prilagodi (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ca/strings.xml b/packages/SettingsLib/res/values-ca/strings.xml
index a070740..ba19e30 100644
--- a/packages/SettingsLib/res/values-ca/strings.xml
+++ b/packages/SettingsLib/res/values-ca/strings.xml
@@ -331,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Més gran"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Màxim"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalitzat (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-cs/strings.xml b/packages/SettingsLib/res/values-cs/strings.xml
index 040c9f0..03208bf 100644
--- a/packages/SettingsLib/res/values-cs/strings.xml
+++ b/packages/SettingsLib/res/values-cs/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Funkce je experimentální a může mít vliv na výkon."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Přepsáno nastavením <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Zbývající čas: <xliff:g id="TIME">%1$s</xliff:g> (přibližně)"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Zbývající čas: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – zbývá přibližně <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – zbývá <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabití"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabití ze zásuvky"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabití přes USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabití bezdrátově"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Neznámé"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Nabíjí se"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Nabíjení z adaptéru"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Nabíjení"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Nabíjení přes USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Nabíjení"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Bezdrátové nabíjení"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Nabíjení"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nenabíjí se"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nenabíjí se"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Nabitá"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Větší"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Největší"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Vlastní (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-da/strings.xml b/packages/SettingsLib/res/values-da/strings.xml
index ddad673..d58fe62d 100644
--- a/packages/SettingsLib/res/values-da/strings.xml
+++ b/packages/SettingsLib/res/values-da/strings.xml
@@ -331,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Større"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Størst"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Tilpasset (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-de/strings.xml b/packages/SettingsLib/res/values-de/strings.xml
index 514228f..dc38dae 100644
--- a/packages/SettingsLib/res/values-de/strings.xml
+++ b/packages/SettingsLib/res/values-de/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Hierbei handelt es sich um eine experimentelle Funktion. Dies kann sich auf die Leistung auswirken."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Außer Kraft gesetzt von \"<xliff:g id="TITLE">%1$s</xliff:g>\""</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Noch ca. <xliff:g id="TIME">%1$s</xliff:g> verbleibend"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Noch <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – noch etwa <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – noch <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – voll in <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – bei Stromanschluss voll in <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – über USB voll in <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – bei kabellosem Laden voll in <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Unbekannt"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Wird aufgeladen"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Laden über Netzteil"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Ladevorgang"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Laden über USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Ladevorgang"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Kabelloses Laden"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Ladevorgang"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Wird nicht geladen"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Wird nicht geladen"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Voll"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Größer"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Am größten"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Benutzerdefiniert (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-el/strings.xml b/packages/SettingsLib/res/values-el/strings.xml
index 8df693a..87d5a98 100644
--- a/packages/SettingsLib/res/values-el/strings.xml
+++ b/packages/SettingsLib/res/values-el/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Αυτή η λειτουργία είναι πειραματική και ενδεχομένως να επηρεάσει τις επιδόσεις."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Αντικαταστάθηκε από <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Απομένουν περίπου <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Απομένει/ουν <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - απομένουν περίπου <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - απομένει/ουν <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> για πλήρη φόρτιση"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> για πλήρη φόρτιση με φορτιστή AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> για πλήρη φόρτιση μέσω USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> για πλήρη ασύρματη φόρτιση"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Άγνωστο"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Φόρτιση"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Φόρτιση με AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Φόρτιση"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Φόρτιση μέσω USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Φόρτιση"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Ασύρματη φόρτιση"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Φόρτιση"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Δεν φορτίζει"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Δεν φορτίζει"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Πλήρης"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Πιο μεγάλα"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Μεγαλύτερα"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Προσαρμοσμένη (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-en-rAU/strings.xml b/packages/SettingsLib/res/values-en-rAU/strings.xml
index 466291a..fe490a2 100644
--- a/packages/SettingsLib/res/values-en-rAU/strings.xml
+++ b/packages/SettingsLib/res/values-en-rAU/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"This feature is experimental and may affect performance."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Overridden by <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Approx. <xliff:g id="TIME">%1$s</xliff:g> left"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> left"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – approx. <xliff:g id="TIME">%2$s</xliff:g> left"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> left"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full on AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full over USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full from wireless"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Unknown"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Charging"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Charging on AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Charging"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Charging over USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Charging"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Charging wirelessly"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Charging"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Not charging"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Not charging"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Full"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Larger"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Largest"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Custom (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-en-rGB/strings.xml b/packages/SettingsLib/res/values-en-rGB/strings.xml
index 466291a..fe490a2 100644
--- a/packages/SettingsLib/res/values-en-rGB/strings.xml
+++ b/packages/SettingsLib/res/values-en-rGB/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"This feature is experimental and may affect performance."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Overridden by <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Approx. <xliff:g id="TIME">%1$s</xliff:g> left"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> left"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – approx. <xliff:g id="TIME">%2$s</xliff:g> left"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> left"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full on AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full over USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full from wireless"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Unknown"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Charging"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Charging on AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Charging"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Charging over USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Charging"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Charging wirelessly"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Charging"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Not charging"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Not charging"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Full"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Larger"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Largest"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Custom (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-en-rIN/strings.xml b/packages/SettingsLib/res/values-en-rIN/strings.xml
index 466291a..fe490a2 100644
--- a/packages/SettingsLib/res/values-en-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-en-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"This feature is experimental and may affect performance."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Overridden by <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Approx. <xliff:g id="TIME">%1$s</xliff:g> left"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> left"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – approx. <xliff:g id="TIME">%2$s</xliff:g> left"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> left"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full on AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full over USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> until full from wireless"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Unknown"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Charging"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Charging on AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Charging"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Charging over USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Charging"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Charging wirelessly"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Charging"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Not charging"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Not charging"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Full"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Larger"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Largest"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Custom (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-es-rUS/strings.xml b/packages/SettingsLib/res/values-es-rUS/strings.xml
index 9bc2cf4..03d9a95 100644
--- a/packages/SettingsLib/res/values-es-rUS/strings.xml
+++ b/packages/SettingsLib/res/values-es-rUS/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Esta función es experimental y puede afectar el rendimiento."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Reemplazado por <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Falta <xliff:g id="TIME">%1$s</xliff:g> aproximadamente"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Tiempo restante: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g>: alrededor de <xliff:g id="TIME">%2$s</xliff:g> para completar la carga"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - Tiempo restante: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g>: <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g>: <xliff:g id="TIME">%2$s</xliff:g> para completar la carga"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g>: <xliff:g id="TIME">%2$s</xliff:g> para completar la carga por CA"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g>: <xliff:g id="TIME">%2$s</xliff:g> para completar la carga por USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g>: <xliff:g id="TIME">%2$s</xliff:g> para completar la carga inalámbrica"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Desconocido"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Cargando"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Carga en CA"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Cargando"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Carga con USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Cargando"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Carga inalámbrica"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Cargando"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"No se está cargando."</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"No se realiza la carga"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Cargado"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Más grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Máximo"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizado (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-es/strings.xml b/packages/SettingsLib/res/values-es/strings.xml
index ec0cafe..4aaad05 100644
--- a/packages/SettingsLib/res/values-es/strings.xml
+++ b/packages/SettingsLib/res/values-es/strings.xml
@@ -331,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Más grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Lo más grande posible"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizado (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-et-rEE/strings.xml b/packages/SettingsLib/res/values-et-rEE/strings.xml
index 29a1aea..8526112 100644
--- a/packages/SettingsLib/res/values-et-rEE/strings.xml
+++ b/packages/SettingsLib/res/values-et-rEE/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"See funktsioon on katseline ja võib mõjutada toimivust."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Alistas <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Umbes <xliff:g id="TIME">%1$s</xliff:g> on jäänud"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> on jäänud"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – jäänud on umbes <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> on jäänud"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, kuni aku on täis"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, kuni aku on täis (vahelduvvool)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, kuni aku on täis (USB)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, kuni aku on täis (juhtmeta laad.)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Tundmatu"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Laadimine"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Laad. vahelduvv.-v."</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Laadimine"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Laadimine USB kaudu"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Laadimine"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Juhtmevaba laadimine"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Laadimine"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ei lae"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ei lae"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Täis"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Suurem"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Suurim"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Kohandatud (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-eu-rES/strings.xml b/packages/SettingsLib/res/values-eu-rES/strings.xml
index 4f55e35..2cc73bb 100644
--- a/packages/SettingsLib/res/values-eu-rES/strings.xml
+++ b/packages/SettingsLib/res/values-eu-rES/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Eginbidea esperimentala da eta eragina izan dezake funtzionamenduan."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> hobespena gainjarri zaio"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"<xliff:g id="TIME">%1$s</xliff:g> inguru guztiz kargatu arte"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> guztiz kargatu arte"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> inguru. <xliff:g id="TIME">%2$s</xliff:g> geratzen d(ir)a"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> guztiz kargatu arte"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> guztiz kargatu arte"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> korrontearen bidez guztiz kargatu arte"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB bidez guztiz kargatu arte"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> haririk gabe guztiz kargatu arte"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Ezezaguna"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Kargatzea"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"KA bidez kargatzen"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Kargatzen"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB bidez kargatzen"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Kargatzen"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Hari gabe kargatzen"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Kargatzen"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ez da kargatzen ari"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ez da kargatzen ari"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Beteta"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Oso handia"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Handiena"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Pertsonalizatua (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-fa/strings.xml b/packages/SettingsLib/res/values-fa/strings.xml
index e9d63fd..3fdb474 100644
--- a/packages/SettingsLib/res/values-fa/strings.xml
+++ b/packages/SettingsLib/res/values-fa/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"این قابلیت آزمایشی است و ممکن است عملکرد را تحت تأثیر قرار دهد."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"توسط <xliff:g id="TITLE">%1$s</xliff:g> لغو شد"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"تقریباً <xliff:g id="TIME">%1$s</xliff:g> باقی مانده است"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> باقی مانده"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - تقریباً ‏<xliff:g id="TIME">%2$s</xliff:g> باقی مانده است"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> باقی مانده"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - ‏<xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - ‏<xliff:g id="TIME">%2$s</xliff:g> تا شارژ کامل"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - ‏<xliff:g id="TIME">%2$s</xliff:g> تا شارژ کامل با جریان متناوب"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"‏<xliff:g id="LEVEL">%1$s</xliff:g> - ‏<xliff:g id="TIME">%2$s</xliff:g> تا شارژ کامل از طریق USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - ‏<xliff:g id="TIME">%2$s</xliff:g> تا شارژ کامل به‌طور بی‌سیم"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"ناشناس"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"در حال شارژ شدن"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"شارژ با جریان متناوب"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"درحال شارژ شدن"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"‏شارژ از طریق USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"درحال شارژ شدن"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"شارژ به صورت بی‌سیم"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"درحال شارژ شدن"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"شارژ نمی‌شود"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"شارژ نمی‌شود"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"پر"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"بزرگ‌تر"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"بزرگ‌ترین"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"سفارشی (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-fi/strings.xml b/packages/SettingsLib/res/values-fi/strings.xml
index 5531d27..b70d6a0 100644
--- a/packages/SettingsLib/res/values-fi/strings.xml
+++ b/packages/SettingsLib/res/values-fi/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Tämä ominaisuus on kokeellinen ja voi vaikuttaa suorituskykyyn."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Tämän ohittaa <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Noin <xliff:g id="TIME">%1$s</xliff:g> jäljellä"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> jäljellä"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – noin <xliff:g id="TIME">%2$s</xliff:g> jäljellä"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> jäljellä"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> kunnes täynnä"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> kunnes täynnä (laturilataus)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> kunnes täynnä (USB-lataus)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> kunnes täynnä (WiFi-lataus)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Tuntematon"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Ladataan"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Laturilataus"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Ladataan"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB-lataus"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Ladataan"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Langaton lataus"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Ladataan"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ei laturissa"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ei laturissa"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Täynnä"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Suurempi"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Suurin"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Muokattu (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-fr-rCA/strings.xml b/packages/SettingsLib/res/values-fr-rCA/strings.xml
index df6bdc6..cc8e7f6 100644
--- a/packages/SettingsLib/res/values-fr-rCA/strings.xml
+++ b/packages/SettingsLib/res/values-fr-rCA/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Cette fonctionnalité est expérimentale et peut toucher les performances."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Remplacé par <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Il reste environ <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Temps restant : <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> %% – Temps restant : environ <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – Temps restant : <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> %% (chargée à 100 %% dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> %% (charge complète sur c.a. dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> %% (chargée à 100 %% par USB dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> %% (chargée à 100 %% avec chargeur sans fil dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Inconnu"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Batterie en charge"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"En charge (c.a.)"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Charge en cours..."</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"En charge par USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Charge en cours..."</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"En charge sans fil"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Charge en cours..."</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"N\'est pas en charge"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"N\'est pas en charge"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Pleine"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Plus grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"La plus grande"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personnalisée (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-fr/strings.xml b/packages/SettingsLib/res/values-fr/strings.xml
index ee40b2a..a1b85a0 100644
--- a/packages/SettingsLib/res/values-fr/strings.xml
+++ b/packages/SettingsLib/res/values-fr/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Cette fonctionnalité est expérimentale et peut affecter les performances."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Remplacé par <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Il reste environ <xliff:g id="TIME">%1$s</xliff:g>."</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Temps restant : <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – Temps restant : <xliff:g id="TIME">%2$s</xliff:g> environ"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – Temps restant : <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> (chargée à 100 %% dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> (chargée à 100 %% sur secteur dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> (chargée à 100 %% via USB dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> (chargée à 100 %% sans fil dans <xliff:g id="TIME">%2$s</xliff:g>)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Inconnu"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Batterie en charge"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"En charge sur secteur"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"En charge"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"En charge via USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"En charge"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"En charge sans fil"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"En charge"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Pas en charge"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Débranchée"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"pleine"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Plus grand"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Le plus grand"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personnalisé (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-gl-rES/strings.xml b/packages/SettingsLib/res/values-gl-rES/strings.xml
index 4a0451e..1bdddd9 100644
--- a/packages/SettingsLib/res/values-gl-rES/strings.xml
+++ b/packages/SettingsLib/res/values-gl-rES/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Esta función é experimental e pode afectar ao rendemento."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Anulado por <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Duración aproximada de <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Tempo restante: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - faltan aproximadamente <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> (tempo restante: <xliff:g id="TIME">%2$s</xliff:g>)"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> para completar a carga"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> (<xliff:g id="TIME">%2$s</xliff:g>)"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> para completar a carga con CA"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> (<xliff:g id="TIME">%2$s</xliff:g>)"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> para completar a carga con USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> (<xliff:g id="TIME">%2$s</xliff:g>)"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> para completar a carga co modo sen fíos"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> (<xliff:g id="TIME">%2$s</xliff:g>)"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Descoñecido"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Cargando"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Cargando con CA"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Cargando"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Cargando por USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Cargando"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Cargando sen fíos"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Cargando"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Non se está cargando"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Non está cargando"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Completa"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Máis grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"O máis grande"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizado (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-gu-rIN/strings.xml b/packages/SettingsLib/res/values-gu-rIN/strings.xml
index becda28..eafb8b1 100644
--- a/packages/SettingsLib/res/values-gu-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-gu-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"આ સુવિધા પ્રાયોગિક છે અને કામગીરી પર અસર કરી શકે છે."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> દ્વારા ઓવરરાઇડ થયું"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"અંદાજે. <xliff:g id="TIME">%1$s</xliff:g> બાકી"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> બાકી"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - આશરે <xliff:g id="TIME">%2$s</xliff:g> બાકી"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> બાકી"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"સંપૂર્ણ થવામાં <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g>, AC પર પૂર્ણ ચાર્જ થયાંને <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g>, USB પર પૂર્ણ ચાર્જ થયાંને <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> વાયરલેસ દ્વારા પૂર્ણ થાય ત્યાં સુધી"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"અજાણ્યું"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ચાર્જ થઈ રહ્યું છે"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC પર ચાર્જિંગ"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ચાર્જ થઈ રહ્યું છે"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB થી ચાર્જિંગ"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ચાર્જ થઈ રહ્યું છે"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"વાયરલેસથી ચાર્જિંગ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ચાર્જ થઈ રહ્યું છે"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ચાર્જ થઈ રહ્યું નથી"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ચાર્જ થઈ રહ્યું નથી"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"પૂર્ણ"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"વધુ મોટું"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"સૌથી મોટું"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"કસ્ટમ (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-hi/strings.xml b/packages/SettingsLib/res/values-hi/strings.xml
index 6dffdd9..b008e1f 100644
--- a/packages/SettingsLib/res/values-hi/strings.xml
+++ b/packages/SettingsLib/res/values-hi/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"यह सुविधा प्रायोगिक है और निष्पादन को प्रभावित कर सकती है."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> के द्वारा ओवरराइड किया गया"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"लगभग <xliff:g id="TIME">%1$s</xliff:g> शेष"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> शेष"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - लगभग <xliff:g id="TIME">%2$s</xliff:g> शेष"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> शेष"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> पूरी होने तक"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC पर पूरी होने तक"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB पर पूरी होने तक"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> वायरलेस से पूरी होने तक"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"अज्ञात"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"चार्ज हो रही है"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC से चार्ज हो रही"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"चार्ज हो रहा है"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB पर चार्ज हो रही"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"चार्ज हो रहा है"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"वायरलेस रूप से चार्ज हो रही"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"चार्ज हो रहा है"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"चार्ज नहीं हो रही है"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"चार्ज नहीं हो रही है"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"पूरी"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"अधिक बड़ा"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"सबसे बड़ा"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"कस्टम (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-hr/strings.xml b/packages/SettingsLib/res/values-hr/strings.xml
index 1edb015..6ba366c 100644
--- a/packages/SettingsLib/res/values-hr/strings.xml
+++ b/packages/SettingsLib/res/values-hr/strings.xml
@@ -331,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Veće"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Najveće"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Prilagođeno (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-hu/strings.xml b/packages/SettingsLib/res/values-hu/strings.xml
index 060599c..b10f5be 100644
--- a/packages/SettingsLib/res/values-hu/strings.xml
+++ b/packages/SettingsLib/res/values-hu/strings.xml
@@ -331,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Nagyobb"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Legnagyobb"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Egyéni (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-hy-rAM/strings.xml b/packages/SettingsLib/res/values-hy-rAM/strings.xml
index 63c4336..2021520 100644
--- a/packages/SettingsLib/res/values-hy-rAM/strings.xml
+++ b/packages/SettingsLib/res/values-hy-rAM/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Սա փորձնական գործառույթ է և կարող է ազդել աշխատանքի վրա:"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Գերազանցված է <xliff:g id="TITLE">%1$s</xliff:g>-ից"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Մնացել է մոտ <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Մնացել է <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - մնաց մոտավորապես <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - մնացել է <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> մինչև լրիվ լիցքավորումը"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> մինչև լրիվ լիցքավորումը հոսանքից"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> մինչև լրիվ լիցքավորումը USB-ով"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> մինչև լրիվ լիցքավորումը անլար ցանցից"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Անհայտ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Լիցքավորում"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Լիցքավորում AC-ով"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Լիցքավորում"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Լիցքավորում USB-ով"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Լիցքավորում"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Անլար լիցքավորում"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Լիցքավորում"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Չի լիցքավորվում"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Չի լիցքավորվում"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Լիցքավորված"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Ավելի մեծ"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Ամենամեծ"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Հատուկ (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-in/strings.xml b/packages/SettingsLib/res/values-in/strings.xml
index c86c768..c02e3fa 100644
--- a/packages/SettingsLib/res/values-in/strings.xml
+++ b/packages/SettingsLib/res/values-in/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Fitur ini bersifat eksperimental dan dapat memengaruhi kinerja."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Digantikan oleh <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Kira-kira tersisa <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> tersisa"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - kira-kira tersisa. <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> tersisa"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sampai penuh"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sampai penuh pada AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sampai penuh melalui USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sampai penuh dari nirkabel"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Tidak diketahui"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Mengisi daya"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Mengisi daya pada AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Mengisi daya"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Isi daya lewat USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Mengisi daya"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Isi daya nirkabel"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Mengisi daya"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Tidak mengisi daya"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Tidak mengisi daya"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Penuh"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Lebih besar"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Terbesar"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"(<xliff:g id="DENSITYDPI">%d</xliff:g>) khusus"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-is-rIS/strings.xml b/packages/SettingsLib/res/values-is-rIS/strings.xml
index 1fc0dc0..bdf5a35 100644
--- a/packages/SettingsLib/res/values-is-rIS/strings.xml
+++ b/packages/SettingsLib/res/values-is-rIS/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Þessi eiginleiki er á tilraunastigi og getur haft áhrif á frammistöðu."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Hnekkt af <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Um það bil <xliff:g id="TIME">%1$s</xliff:g> eftir"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> eftir"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – u.þ.b. <xliff:g id="TIME">%2$s</xliff:g> eftir"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> eftir"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> í fulla hleðslu"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> í fulla hleðslu með hleðslutæki"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> í fulla hleðslu í gegnum USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> í fulla hleðslu þráðlaust"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Óþekkt"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Í hleðslu"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Hleðslutæki tengt"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Í hleðslu"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Hleður um USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Í hleðslu"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Hleður þráðlaust"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Í hleðslu"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ekki í hleðslu"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ekki í hleðslu"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Fullhlaðin"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Stærra"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Stærst"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Sérsniðið (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-it/strings.xml b/packages/SettingsLib/res/values-it/strings.xml
index 78cd29b..43c41d7 100644
--- a/packages/SettingsLib/res/values-it/strings.xml
+++ b/packages/SettingsLib/res/values-it/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Questa funzione è sperimentale e potrebbe influire sulle prestazioni."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Valore sostituito da <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Circa <xliff:g id="TIME">%1$s</xliff:g> rimanenti"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Tempo rimanente: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – Tempo rimanente: <xliff:g id="TIME">%2$s</xliff:g> circa"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - Tempo rimanente: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> alla carica completa"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> alla carica completa tramite CA"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> alla carica completa tramite USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> lla carica completa con wireless"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Sconosciuta"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"In carica"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"In carica tramite CA"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"In carica"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"In carica tramite USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"In carica"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"In carica, wireless"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"In carica"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Non in carica"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Non in carica"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Carica"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Più grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Massimo"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizzato (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-iw/strings.xml b/packages/SettingsLib/res/values-iw/strings.xml
index 16e0f44..e25d218 100644
--- a/packages/SettingsLib/res/values-iw/strings.xml
+++ b/packages/SettingsLib/res/values-iw/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"תכונה זו היא ניסיונית ועשויה להשפיע על הביצועים."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"נעקף על ידי <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"נשארו <xliff:g id="TIME">%1$s</xliff:g> בערך"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"נותרו <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ‏<xliff:g id="TIME">%2$s</xliff:g> בקירוב עד לסיום"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - נותרו <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g>‏ - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> ‏- <xliff:g id="TIME">%2$s</xliff:g> עד למילוי"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> ‏- <xliff:g id="TIME">%2$s</xliff:g> עד למילוי בזרם חילופין"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"‏<xliff:g id="LEVEL">%1$s</xliff:g> ‏- <xliff:g id="TIME">%2$s</xliff:g> עד למילוי ב-USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> ‏- <xliff:g id="TIME">%2$s</xliff:g> עד למילוי בטעינה אלחוטית"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"לא ידוע"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"טוען"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"טוען בזרם חילופין"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"בטעינה"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"‏טוען ב-USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"בטעינה"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"טוען באופן אלחוטי"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"בטעינה"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"לא בטעינה"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"לא טוען"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"מלא"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"יותר גדול"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"הכי גדול"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"מותאם אישית (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ja/strings.xml b/packages/SettingsLib/res/values-ja/strings.xml
index ce405df..ac239fe 100644
--- a/packages/SettingsLib/res/values-ja/strings.xml
+++ b/packages/SettingsLib/res/values-ja/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"この機能は試験運用機能であり、パフォーマンスに影響することがあります。"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g>によって上書き済み"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"あと約 <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g>(残り時間)"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - 残り約<xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>(残り時間)"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - フル充電まで<xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - フル充電まで<xliff:g id="TIME">%2$s</xliff:g>(AC)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - フル充電まで<xliff:g id="TIME">%2$s</xliff:g>(USB)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - フル充電まで<xliff:g id="TIME">%2$s</xliff:g>(ワイヤレス)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"不明"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"充電中"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"ACで充電しています"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"充電しています"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USBで充電しています"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"充電しています"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"無線で充電しています"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"充電しています"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"充電していません"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"充電していません"</string>
     <!-- String.format failed for translation -->
@@ -342,4 +333,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"特大"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"最大"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"カスタム(<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ka-rGE/strings.xml b/packages/SettingsLib/res/values-ka-rGE/strings.xml
index 20a1d2a..883d637 100644
--- a/packages/SettingsLib/res/values-ka-rGE/strings.xml
+++ b/packages/SettingsLib/res/values-ka-rGE/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ეს ფუნქცია საცდელია და შეიძლება გავლენა იქონიოს შესრულებაზე."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"უკუგებულია <xliff:g id="TITLE">%1$s</xliff:g>-ის მიერ"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"დარჩენილია დაახლოებით <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"დარჩენილია <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"დაახლ. <xliff:g id="LEVEL">%1$s</xliff:g> დარჩენილია <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> — დარჩენილია <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> სრულ დატენვამდე"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ელკვებით სრულ დატენვამდე"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB-თი სრულ დატენვამდე"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> უსადენოდან სრულ დატენვამდე"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"უცნობი"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"იტენება"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"დატენვა ელკვებაზე"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"იტენება"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"დატენვა USB-ზე"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"იტენება"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"დატენვა უსადენოდ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"იტენება"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"არ იტენება"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"არ იტენება"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ბატარეა დატენილია"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"უფრო დიდი"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"უდიდესი"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"მორგებული (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-kk-rKZ/strings.xml b/packages/SettingsLib/res/values-kk-rKZ/strings.xml
index e71c8d0..3270170 100644
--- a/packages/SettingsLib/res/values-kk-rKZ/strings.xml
+++ b/packages/SettingsLib/res/values-kk-rKZ/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Бұл мүмкіндік эксперименттік болып табылады және өнімділікке әсер етуі мүмкін."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> үстінен басқан"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Шамамен <xliff:g id="TIME">%1$s</xliff:g> қалды"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> қалды"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - шамамен <xliff:g id="TIME">%2$s</xliff:g> қалды"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> қалды"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - толғанша <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - айнымалы токпен толғанша <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - USB арқылы толғанша <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - сымсыз толғанша <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Белгісіз"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Зарядталуда"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Айнымалы токпен зар."</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Зарядталуда"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB арқылы зарядтау"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Зарядталуда"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Сымсыз зарядтау"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Зарядталуда"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Зарядталу орындалып жатқан жоқ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Зарядталып тұрған жоқ"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Толық"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Үлкенірек"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Ең үлкен"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Арнаулы (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-km-rKH/strings.xml b/packages/SettingsLib/res/values-km-rKH/strings.xml
index 687b71b..9d6d3475 100644
--- a/packages/SettingsLib/res/values-km-rKH/strings.xml
+++ b/packages/SettingsLib/res/values-km-rKH/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"លក្ខណៈ​នេះ​គឺ​ជា​ការ​ពិសោធន៍ ហើយ​អាច​ប៉ះពាល់​ការ​អនុវត្ត។"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"បដិសេធ​ដោយ <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"នៅសល់ប្រហែល <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"នៅសល់ <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - នៅ​សល់​ប្រហែល <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - នៅសល់ <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> រហូត​ដល់​ពេញ"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> រហូត​ដល់ពេញ​រចន្ត​ឆ្លាស់"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> រហូត​ដល់​ពេញ​តាមយូអេសប៊ី"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> រហូត​ដល់​ពេញ​ពី​ឥតខ្សែ"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"មិន​ស្គាល់"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"កំពុងបញ្ចូល​ថ្ម"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"បញ្ចូលថ្មតាម AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"កំពុងសាកថ្ម"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"បញ្ចូលថ្មតាមយូអេសប៊ី"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"កំពុងសាកថ្ម"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"បញ្ចូលថ្មដោយ​​ឥតខ្សែ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"កំពុងសាកថ្ម"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"មិនកំពុង​បញ្ចូល​ថ្ម"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"មិន​បញ្ចូលថ្ម"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ពេញ"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ធំជាង"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"ធំបំផុត"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"ផ្ទាល់ខ្លួន (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-kn-rIN/strings.xml b/packages/SettingsLib/res/values-kn-rIN/strings.xml
index 713d9b3..dc35604 100644
--- a/packages/SettingsLib/res/values-kn-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-kn-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ಇದು ಪ್ರಾಯೋಗಿಕ ವೈಶಿಷ್ಟ್ಯವಾಗಿದೆ. ಕಾರ್ಯಕ್ಷಮತೆ ಮೇಲೆ ಪರಿಣಾಮ ಬೀರಬಹುದು."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> ಮೂಲಕ ಅತಿಕ್ರಮಿಸುತ್ತದೆ"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"ಸುಮಾರು <xliff:g id="TIME">%1$s</xliff:g> ಉಳಿದಿದೆ"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> ಉಳಿದಿದೆ"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"ಸುಮಾರು <xliff:g id="LEVEL">%1$s</xliff:g> <xliff:g id="TIME">%2$s</xliff:g> ಉಳಿದಿದೆ"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ಉಳಿದಿದೆ"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ಪೂರ್ಣವಾಗುವವರೆಗೆ"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC ನಲ್ಲಿ ಪೂರ್ಣವಾಗುವವರೆಗೆ"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB ಮೂಲಕ ಪೂರ್ಣವಾಗುವವರೆಗೆ"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ವೈರ್‌‌ಲೆಸ್‌ನಿಂದ ಪೂರ್ಣವಾಗುವವರೆಗೆ"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"ಅಜ್ಞಾತ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ಚಾರ್ಜ್ ಆಗುತ್ತಿದೆ"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC ನಲ್ಲಿ ಚಾರ್ಜ್‌"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ಚಾರ್ಜ್ ಆಗುತ್ತಿದೆ"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB ಮೂಲಕ ಚಾರ್ಜ್‌"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ಚಾರ್ಜ್ ಆಗುತ್ತಿದೆ"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"ನಿಸ್ತಂತುವಾಗಿ ಚಾರ್ಜ್‌"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ಚಾರ್ಜ್ ಆಗುತ್ತಿದೆ"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ಚಾರ್ಜ್‌ ಆಗುತ್ತಿಲ್ಲ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ಚಾರ್ಜ್ ಆಗುತ್ತಿಲ್ಲ"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ಭರ್ತಿ"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ಸ್ವಲ್ಪ ದೊಡ್ಡ"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"ದೊಡ್ಡ"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"ಕಸ್ಟಮ್ (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ko/strings.xml b/packages/SettingsLib/res/values-ko/strings.xml
index 348141e..fc8f478 100644
--- a/packages/SettingsLib/res/values-ko/strings.xml
+++ b/packages/SettingsLib/res/values-ko/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"실험실 기능이며 성능에 영향을 줄 수 있습니다."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> 우선 적용됨"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"약 <xliff:g id="TIME">%1$s</xliff:g> 남음"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> 남음"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - 대략 <xliff:g id="TIME">%2$s</xliff:g> 남음"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 남음"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 후 충전 완료"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 후 충전 완료(AC 전원)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 후 충전 완료(USB)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 후 충전 완료(무선)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"알 수 없음"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"충전 중"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"충전 중(AC 전원)"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"충전 중"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"충전 중(USB)"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"충전 중"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"충전 중(무선)"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"충전 중"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"충전 안함"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"충전 안함"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"충전 완료"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"더 크게"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"가장 크게"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"맞춤(<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ky-rKG/strings.xml b/packages/SettingsLib/res/values-ky-rKG/strings.xml
index 2016f04..8b0119e 100644
--- a/packages/SettingsLib/res/values-ky-rKG/strings.xml
+++ b/packages/SettingsLib/res/values-ky-rKG/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Бул сынамык мүмкүнчүлүк болгондуктан, иштин майнаптуулугуна таасир этиши мүмкүн."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> менен алмаштырылган"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Болжол менен <xliff:g id="TIME">%1$s</xliff:g> калды"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> калды"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - болжол менен <xliff:g id="TIME">%2$s</xliff:g> саат калды"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> калды"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> толгончо"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC аркылуу толгончо"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB аркылуу толгончо"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> зымсыз кубаттоо аркылуу толгончо"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Белгисиз"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Кубатталууда"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"ӨА кубатталууда"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Кубатталууда"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB\'ден кубатталууда"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Кубатталууда"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Зымсыз кубатталууда"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Кубатталууда"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Кубат алган жок"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Кубатталган жок"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Толук"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Чоңураак"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Эң чоң"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Ыңгайлаштырылган (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-lo-rLA/strings.xml b/packages/SettingsLib/res/values-lo-rLA/strings.xml
index 7e6db5e..3532137 100644
--- a/packages/SettingsLib/res/values-lo-rLA/strings.xml
+++ b/packages/SettingsLib/res/values-lo-rLA/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"​ຄຸນ​ສົມ​ບັດ​ນີ້​ກຳ​ລັງ​ຢູ່​ໃນ​ການ​ທົດ​ລອງ​ແລະ​ອາດ​ມີ​ຜົນ​ຕໍ່​ປະ​ສິດ​ທິ​ພາບ."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"ຖືກແທນໂດຍ <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"ຍັງເຫຼືອປະມານ <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"ຍັງເຫຼືອ <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ​ເຫຼືອປະ​ມານ <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - ຍັງເຫຼືອ <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ຈຶ່ງ​ຈະ​ເຕັມ"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ​ຈຶ່ງ​ຈະ​ເຕັມ​ໂດຍສາກ​ດ້ວຍ​ໄຟ AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ຈຶ່ງ​ຈະ​ເຕັມ​ໂດຍສາກ​ດ້ວຍ USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ​ຈຶ່ງ​ຈະ​ເຕັມ​ໂດຍ​ສາກ​ແບບ​ໄຮ້​ສາຍ"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"ບໍ່ຮູ້ຈັກ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ກຳລັງສາກໄຟ"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"ກຳ​​ລັງ​ສາກ​ຜ່ານ​ໝໍ້​ໄຟ"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ກຳລັງສາກໄຟ"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"ກຳ​ລັງ​ສາກ​ຜ່ານ USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ກຳລັງສາກໄຟ"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"ກຳ​ລັງ​ສາກ​ໄຮ້​ສາຍ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ກຳລັງສາກໄຟ"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ບໍ່ໄດ້ສາກໄຟ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ບໍ່ໄດ້ສາກໄຟ"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ເຕັມ"</string>
@@ -340,4 +331,5 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ໃຫຍ່ກວ່າ"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"ໃຫຍ່ທີ່ສຸດ"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"ປັບແຕ່ງເອງ (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <string name="help_feedback_label" msgid="6815040660801785649">"ຊ່ວຍເຫຼືອ &amp; ຄຳຕິຊົມ"</string>
 </resources>
diff --git a/packages/SettingsLib/res/values-lt/strings.xml b/packages/SettingsLib/res/values-lt/strings.xml
index d49876e..02739f3 100644
--- a/packages/SettingsLib/res/values-lt/strings.xml
+++ b/packages/SettingsLib/res/values-lt/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ši funkcija yra eksperimentinė ir ji gali turėti įtakos našumui."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Nepaisyta naudojant nuostatą „<xliff:g id="TITLE">%1$s</xliff:g>“"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Liko maždaug <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Liko <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – liko maždaug <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – liko <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> iki visiško įkrovimo"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> iki visiško įkrovimo naud. kint. sr."</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> iki visiško įkrovimo naudojant USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> iki visiško įkrovimo belaid. ryš."</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Nežinomas"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Kraunasi..."</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Įkr. naud. kint. sr."</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Įkraunama"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Įkraunama naud. USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Įkraunama"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Įkraunama be laidų"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Įkraunama"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nekraunama"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nekraunama"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Visiškai įkrautas"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Didesnis"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Didžiausias"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Tinkintas (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-lv/strings.xml b/packages/SettingsLib/res/values-lv/strings.xml
index 6cd9cfd5..54c75ff 100644
--- a/packages/SettingsLib/res/values-lv/strings.xml
+++ b/packages/SettingsLib/res/values-lv/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Šī funkcija ir eksperimentāla un var ietekmēt veiktspēju."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Jaunā preference: <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Atlikušais laiks: aptuveni <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Atlicis: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> — aptuvenais atlikušais laiks: <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> — atlicis: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g> līdz pilnai uzlādei"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g> līdz pilnai maiņstrāvas uzlādei"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g> līdz pilnai USB uzlādei"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g> līdz pilnai bezvadu uzlādei"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> — <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Nezināms"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Uzlāde"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Maiņstrāvas uzlāde"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Notiek uzlāde"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB uzlāde"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Notiek uzlāde"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Bezvadu uzlāde"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Notiek uzlāde"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nenotiek uzlāde"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nenotiek uzlāde"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Pilns"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Lielāks"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Vislielākais"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Pielāgots (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-mk-rMK/strings.xml b/packages/SettingsLib/res/values-mk-rMK/strings.xml
index f8f65ec..8f11118 100644
--- a/packages/SettingsLib/res/values-mk-rMK/strings.xml
+++ b/packages/SettingsLib/res/values-mk-rMK/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Функцијата е експериментална и може да влијае на изведбата."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Прескокнато според <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Преостанаа прибл. <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"уште <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – преостанува приближно <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - уште <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до целосно полна"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до целосно полна на AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до целосно полна преку USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до целосно полна, безжично"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Непознато"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Се полни"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Полнење на струја"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Се полни"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Полнење преку УСБ"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Се полни"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Безжично полнење"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Се полни"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Не се полни"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Не се полни"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Целосна"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Поголем"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Најголем"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Приспособен (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ml-rIN/strings.xml b/packages/SettingsLib/res/values-ml-rIN/strings.xml
index 7350b7f..f39b109 100644
--- a/packages/SettingsLib/res/values-ml-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-ml-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ഈ ഫീച്ചർ പരീക്ഷണാത്മകമായതിനാൽ പ്രകടനത്തെ ബാധിച്ചേക്കാം."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> ഉപയോഗിച്ച് അസാധുവാക്കി"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"ഏകദേശം <xliff:g id="TIME">%1$s</xliff:g> ശേഷിക്കുന്നു"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> ശേഷിക്കുന്നു"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ഏകദേശം <xliff:g id="TIME">%2$s</xliff:g> ശേഷിക്കുന്നു"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ശേഷിക്കുന്നു"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - പൂർണ്ണമായും ചാർജ്ജാകുന്നതിന്, <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - AC-യിൽ പൂർണ്ണമായും ചാർജ്ജാകുന്നതിന്, <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - USB വഴി പൂർണ്ണമായും ചാർജ്ജാകുന്നതിന്, <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - വയർലെസ് വഴി പൂർണ്ണമായും ചാർജ്ജാകുന്നതിന്, <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"അജ്ഞാതം"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ചാർജ്ജുചെയ്യുന്നു"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC-യിൽ ചാർജ്ജുചെയ്യുന്നു"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ചാർജ്ജുചെയ്യുന്നു"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB-യിലൂടെ ചാർജ്ജുചെയ്യുന്നു"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ചാർജ്ജുചെയ്യുന്നു"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"വയർലെസ്സ് കണക്ഷനിലൂടെ ചാർജ്ജുചെയ്യുന്നു"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ചാർജ്ജുചെയ്യുന്നു"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ചാർജ്ജുചെയ്യുന്നില്ല"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ചാർജ്ജുചെയ്യുന്നില്ല"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"നിറഞ്ഞു"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"കൂടുതൽ വലുത്"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"ഏറ്റവും വലുത്"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"ഇഷ്ടാനുസൃതം ( <xliff:g id="DENSITYDPI">%d</xliff:g> )"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-mn-rMN/strings.xml b/packages/SettingsLib/res/values-mn-rMN/strings.xml
index 7eeae06..8b005d1 100644
--- a/packages/SettingsLib/res/values-mn-rMN/strings.xml
+++ b/packages/SettingsLib/res/values-mn-rMN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Энэ функц туршилтынх бөгөөд ажиллагаанд нөлөөлж болзошгүй."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Давхарласан <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Ойролцоогоор <xliff:g id="TIME">%1$s</xliff:g> үлдсэн"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> үлдсэн"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ойролцоогоор <xliff:g id="TIME">%2$s</xliff:g> үлдсэн"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> үлдсэн"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"дүүртэл <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"АС-р дүүртэл <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"USB-р дүүртэл <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"утасгүй цэнэглэгчээр дүүртэл <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Тодорхойгүй"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Цэнэглэж байна"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC-р цэнэглэж байна"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Цэнэглэж байна"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB-р цэнэглэж байна"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Цэнэглэж байна"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Кабльгүйгээр цэнэглэж байна"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Цэнэглэж байна"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Цэнэглэхгүй байна"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Цэнэглэхгүй байна"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Дүүрэн"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Илүү том"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Хамгийн том"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Тогтмол утга (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-mr-rIN/strings.xml b/packages/SettingsLib/res/values-mr-rIN/strings.xml
index 0521ba1..9296a32 100644
--- a/packages/SettingsLib/res/values-mr-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-mr-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"हे वैशिष्‍ट्य प्रायोगिक आहे आणि कदाचित कार्यप्रदर्शन प्रभावित करू शकते."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> द्वारे अधिलिखित"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"अंदाजे. <xliff:g id="TIME">%1$s</xliff:g> शिल्लक"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> शिल्लक"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - अंदाजे. <xliff:g id="TIME">%2$s</xliff:g> शिल्लक"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> शिल्लक"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> पूर्ण होण्यात"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC वरून पूर्ण होण्यात"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB वरून पूर्ण होण्यात"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> वायरलेसवरून पूर्ण होण्यात"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"अज्ञात"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"चार्ज होत आहे"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC वर चार्ज करीत आहे"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"चार्ज होत आहे"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB वरून चार्ज करीत आहे"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"चार्ज होत आहे"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"वायरलेस वरून चार्ज करीत आहे"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"चार्ज होत आहे"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"चार्ज होत नाही"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"चार्ज होत नाही"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"पूर्ण"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"आणखी मोठा"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"सर्वात मोठा"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"सानुकूल करा (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ms-rMY/strings.xml b/packages/SettingsLib/res/values-ms-rMY/strings.xml
index a8be0e5..60a5298 100644
--- a/packages/SettingsLib/res/values-ms-rMY/strings.xml
+++ b/packages/SettingsLib/res/values-ms-rMY/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ciri ini adalah percubaan dan boleh menjejaskan prestasi."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Diatasi oleh <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Kira-kira <xliff:g id="TIME">%1$s</xliff:g> lagi"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> lagi"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - kira-kira. <xliff:g id="TIME">%2$s</xliff:g> yang tinggal"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> lagi"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sehingga penuh"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sehingga penuh di AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sehingga penuh melalui USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> sehingga penuh dari wayarles"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Tidak diketahui"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Mengecas"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Mengecas pada AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Mengecas"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Mengecas melalui USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Mengecas"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Mengecas tanpa wayar"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Mengecas"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Tidak mengecas"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Tidak mengecas"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Penuh"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Lebih besar"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Terbesar"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Tersuai (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-my-rMM/strings.xml b/packages/SettingsLib/res/values-my-rMM/strings.xml
index 220deff..e512aac 100644
--- a/packages/SettingsLib/res/values-my-rMM/strings.xml
+++ b/packages/SettingsLib/res/values-my-rMM/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ဒီအင်္ဂါရပ်မှာ စမ်းသပ်မှု ဖြစ်၍ လုပ်ကိုင်မှုကို အကျိုးသက်ရောက်နိုင်သည်။"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> မှ ကျော်၍ လုပ်ထားသည်။"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"ခန့်မှန်းခြေ <xliff:g id="TIME">%1$s</xliff:g> ကျန်ပါသည်"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> ကျန်သည်"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ခန့်မှန်းခြေ။ <xliff:g id="TIME">%2$s</xliff:g> ကျန်ရှိနေ"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ကျန်သည်"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> အပြည့်အထိ"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> လျှပ်စစ်ဖြင့် အပြည့်အထိ"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB ဖြင့် အပြည့်အထိ"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ကြိုးမဲ့ဖြင့် အပြည့်အထိ"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"အကြောင်းအရာ မသိရှိ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"အားသွင်းနေပါသည်"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"လျှပ်စစ်ဖြင့် အားသွင်းနေ"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"အားသွင်းနေသည်"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USBဖြင့် အားသွင်းနေ"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"အားသွင်းနေသည်"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"ကြိုးမဲ့ အားသွင်းနေ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"အားသွင်းနေသည်"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"အားသွင်းမနေပါ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"အားသွင်းမနေပါ"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"အပြည့်"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ပိုကြီး"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"အကြီးဆုံး"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"စိတ်ကြိုက် (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-nb/strings.xml b/packages/SettingsLib/res/values-nb/strings.xml
index a1407ac..3d01254 100644
--- a/packages/SettingsLib/res/values-nb/strings.xml
+++ b/packages/SettingsLib/res/values-nb/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Denne funksjonen er eksperimentell og kan påvirke ytelsen."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Overstyres av <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Ca. <xliff:g id="TIME">%1$s</xliff:g> gjenstår"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> gjenstår"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – ca. <xliff:g id="TIME">%2$s</xliff:g> igjen"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> gjenstår"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – fulladet om <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> –  fulladet om <xliff:g id="TIME">%2$s</xliff:g> med vekselstrøm"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – fulladet om <xliff:g id="TIME">%2$s</xliff:g> via USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – fulladet om <xliff:g id="TIME">%2$s</xliff:g> via trådløs lading"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Ukjent"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Lader"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Lader via strømuttak"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Lader"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Lader via USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Lader"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Lader trådløst"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Lader"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Lader ikke"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Lader ikke"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Fullt"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Større"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Størst"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Egendefinert (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ne-rNP/strings.xml b/packages/SettingsLib/res/values-ne-rNP/strings.xml
index 83e2e74..f2e6ea4 100644
--- a/packages/SettingsLib/res/values-ne-rNP/strings.xml
+++ b/packages/SettingsLib/res/values-ne-rNP/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"यो सुविधा प्रयोगात्मक छ र प्रदर्शनमा असर गर्न सक्छ।"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> द्वारा अधिरोहित"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"लगभग <xliff:g id="TIME">%1$s</xliff:g> बाँकी छ"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> बाँकी छ"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - लगभग। <xliff:g id="TIME">%2$s</xliff:g> बायाँ"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> बाँकी छ"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> पूर्ण नभए सम्म"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC मा पूर्ण नभए सम्म"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB मा पूर्ण नभए सम्म"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> वायरलेसबाट पूर्ण नभए सम्म"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"अज्ञात"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"चार्ज हुँदै"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC मा चार्ज गर्दै"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"चार्ज हुँदै"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB मा चार्ज गर्दै"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"चार्ज हुँदै"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"बिना तार चार्ज गर्दै"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"चार्ज हुँदै"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"चार्ज भइरहेको छैन"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"चार्ज हुँदै छैन"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"पूर्ण"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"अझ ठूलो"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"सबैभन्दा ठूलो"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"अनुकूलन (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-nl/strings.xml b/packages/SettingsLib/res/values-nl/strings.xml
index 55017d8..4ae1fb0b 100644
--- a/packages/SettingsLib/res/values-nl/strings.xml
+++ b/packages/SettingsLib/res/values-nl/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Deze functie is experimenteel en kan invloed hebben op de prestaties."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Overschreven door <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Ca. <xliff:g id="TIME">%1$s</xliff:g> resterend"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> resterend"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ca. <xliff:g id="TIME">%2$s</xliff:g> resterend"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> resterend"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> tot vol"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> tot vol via wisselstroom"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> tot vol via USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> tot vol via draadloos"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Onbekend"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Opladen"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Opladen via netvoeding"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Opladen"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Opladen via USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Opladen"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Draadloos opladen"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Opladen"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Wordt niet opgeladen"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Wordt niet opgeladen"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Volledig"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Groter"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Grootst"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Aangepast (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-pa-rIN/strings.xml b/packages/SettingsLib/res/values-pa-rIN/strings.xml
index eb1eaac..5596cbc 100644
--- a/packages/SettingsLib/res/values-pa-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-pa-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ਇਹ ਵਿਸ਼ੇਸ਼ਤਾ ਪ੍ਰਯੋਗਾਤਮਿਕ ਹੈ ਅਤੇ ਪ੍ਰਦਰਸ਼ਨ ਤੇ ਅਸਰ ਪਾ ਸਕਦੀ ਹੈ।"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> ਦੁਆਰਾ ਓਵਰਰਾਈਡ ਕੀਤਾ"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"ਲਗਭਗ <xliff:g id="TIME">%1$s</xliff:g> ਬਾਕੀ"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> ਬਾਕੀ"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ਲਗਭਗ <xliff:g id="TIME">%2$s</xliff:g> ਬਾਕੀ"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ਬਾਕੀ"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ਪੂਰੀ ਹੋਣ ਤੱਕ"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC ਤੇ ਪੂਰਾ ਹੋਣ ਤੱਕ"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB ਤੇ ਪੂਰਾ ਹੋਣ ਤੱਕ"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> ਵਾਇਰਲੈਸ ਤੋਂ ਪੂਰਾ ਹੋਣ ਤੱਕ"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"ਅਗਿਆਤ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ਚਾਰਜਿੰਗ"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC ਤੇ ਚਾਰਜਿੰਗ"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ਚਾਰਜ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB ਤੇ ਚਾਰਜਿੰਗ"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ਚਾਰਜ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"ਵਾਇਰਲੈਸ ਤੌਰ ਤੇ ਚਾਰਜਿੰਗ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ਚਾਰਜ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ਚਾਰਜ ਨਹੀਂ ਹੋ ਰਿਹਾ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ਚਾਰਜ ਨਹੀਂ ਹੋ ਰਿਹਾ"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"ਪੂਰੀ"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ਥੋੜ੍ਹਾ ਵੱਡਾ"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"ਸਭ ਤੋਂ ਵੱਡਾ"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"ਵਿਸ਼ੇਸ਼-ਵਿਉਂਤਬੱਧ (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-pl/strings.xml b/packages/SettingsLib/res/values-pl/strings.xml
index 1e56cfd..81ebed8 100644
--- a/packages/SettingsLib/res/values-pl/strings.xml
+++ b/packages/SettingsLib/res/values-pl/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"To jest funkcja eksperymentalna i może wpływać na działanie urządzenia."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Nadpisana przez <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Pozostało około <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Zostało <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – zostało ok. <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – zostało <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pełnego naładowania"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pełnego naładowania z gniazdka"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pełnego naładowania przez USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do pełnego naładowania bezprzewodowo"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Nieznane"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Ładowanie"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Ładowanie zasilaczem"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Ładowanie"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Ładowanie przez USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Ładowanie"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Ład. bezprzewodowe"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Ładowanie"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nie podłączony"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nie podłączony"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Naładowana"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Większe"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Największe"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Niestandardowe (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-pt-rBR/strings.xml b/packages/SettingsLib/res/values-pt-rBR/strings.xml
index 93f333a..5bfbc2d 100644
--- a/packages/SettingsLib/res/values-pt-rBR/strings.xml
+++ b/packages/SettingsLib/res/values-pt-rBR/strings.xml
@@ -115,7 +115,7 @@
     <string name="tts_engine_network_required" msgid="1190837151485314743">"Este idioma requer uma conexão de rede ativa para a conversão de texto em voz."</string>
     <string name="tts_default_sample_string" msgid="4040835213373086322">"Este é um exemplo de sintetização de voz."</string>
     <string name="tts_status_title" msgid="7268566550242584413">"Status de idioma padrão"</string>
-    <string name="tts_status_ok" msgid="1309762510278029765">"<xliff:g id="LOCALE">%1$s</xliff:g> é totalmente suportada"</string>
+    <string name="tts_status_ok" msgid="1309762510278029765">"<xliff:g id="LOCALE">%1$s</xliff:g> é totalmente suportado"</string>
     <string name="tts_status_requires_network" msgid="6042500821503226892">"<xliff:g id="LOCALE">%1$s</xliff:g> requer conexão de rede"</string>
     <string name="tts_status_not_supported" msgid="4491154212762472495">"<xliff:g id="LOCALE">%1$s</xliff:g> não é suportado"</string>
     <string name="tts_status_checking" msgid="5339150797940483592">"Verificando..."</string>
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Este recurso é experimental e pode afetar o desempenho."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Substituído por <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Aproximadamente <xliff:g id="TIME">%1$s</xliff:g> restante(s)"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> restante(s)"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - cerca de <xliff:g id="TIME">%2$s</xliff:g> restantes"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> restante(s)"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir em CA"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir via USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir sem fio"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Desconhecido"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Carregando"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Carregamento CA"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Carregando"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Carregamento via USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Carregando"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Carregamento sem fio"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Carregando"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Não está carregando"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Não está carregando"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Cheio"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Muito grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Maior"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizada (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-pt-rPT/strings.xml b/packages/SettingsLib/res/values-pt-rPT/strings.xml
index dda00fe..244e27d 100644
--- a/packages/SettingsLib/res/values-pt-rPT/strings.xml
+++ b/packages/SettingsLib/res/values-pt-rPT/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Esta funcionalidade é experimental e pode afetar o desempenho."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Substituído por <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Resta(m) aproximadamente <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Resta(m) <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – resta(m) aprox. <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – resta(m) <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> até ficar completa"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> até ficar completa através de CA"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> até ficar completa através de USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até ficar compl. por rede s/ fios"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Desconhecido"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"A carregar"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"A carregar por CA"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"A carregar"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"A carregar por USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"A carregar"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"A carregar sem fios"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"A carregar"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Não está a carregar"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Não está a carregar"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Completo"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Maior"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"O maior"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizado (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-pt/strings.xml b/packages/SettingsLib/res/values-pt/strings.xml
index 93f333a..5bfbc2d 100644
--- a/packages/SettingsLib/res/values-pt/strings.xml
+++ b/packages/SettingsLib/res/values-pt/strings.xml
@@ -115,7 +115,7 @@
     <string name="tts_engine_network_required" msgid="1190837151485314743">"Este idioma requer uma conexão de rede ativa para a conversão de texto em voz."</string>
     <string name="tts_default_sample_string" msgid="4040835213373086322">"Este é um exemplo de sintetização de voz."</string>
     <string name="tts_status_title" msgid="7268566550242584413">"Status de idioma padrão"</string>
-    <string name="tts_status_ok" msgid="1309762510278029765">"<xliff:g id="LOCALE">%1$s</xliff:g> é totalmente suportada"</string>
+    <string name="tts_status_ok" msgid="1309762510278029765">"<xliff:g id="LOCALE">%1$s</xliff:g> é totalmente suportado"</string>
     <string name="tts_status_requires_network" msgid="6042500821503226892">"<xliff:g id="LOCALE">%1$s</xliff:g> requer conexão de rede"</string>
     <string name="tts_status_not_supported" msgid="4491154212762472495">"<xliff:g id="LOCALE">%1$s</xliff:g> não é suportado"</string>
     <string name="tts_status_checking" msgid="5339150797940483592">"Verificando..."</string>
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Este recurso é experimental e pode afetar o desempenho."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Substituído por <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Aproximadamente <xliff:g id="TIME">%1$s</xliff:g> restante(s)"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> restante(s)"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - cerca de <xliff:g id="TIME">%2$s</xliff:g> restantes"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> restante(s)"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir em CA"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir via USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> até concluir sem fio"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Desconhecido"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Carregando"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Carregamento CA"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Carregando"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Carregamento via USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Carregando"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Carregamento sem fio"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Carregando"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Não está carregando"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Não está carregando"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Cheio"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Muito grande"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Maior"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizada (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ro/strings.xml b/packages/SettingsLib/res/values-ro/strings.xml
index 3c46d41..668d19c 100644
--- a/packages/SettingsLib/res/values-ro/strings.xml
+++ b/packages/SettingsLib/res/values-ro/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Această funcție este experimentală și poate afecta performanțele."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Valoare înlocuită de <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Timp rămas: aproximativ <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Timp rămas: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – timp rămas: aproximativ <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – timp rămas: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> până la încărcare completă"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> până la încărcare completă la c.a."</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> până la încărcare completă prin USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> până la încărcare completă wireless"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Necunoscut"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Încarcă"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Se încarcă la C.A."</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Se încarcă"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Se încarcă prin USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Se încarcă"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Se încarcă fără fir"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Se încarcă"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nu se încarcă"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nu încarcă"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Complet"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Mai mare"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Cel mai mare"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Personalizat (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ru/strings.xml b/packages/SettingsLib/res/values-ru/strings.xml
index f4929de..a9d4abc 100644
--- a/packages/SettingsLib/res/values-ru/strings.xml
+++ b/packages/SettingsLib/res/values-ru/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Это экспериментальная функция, она может снизить производительность устройства."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Новая настройка: <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Осталось примерно <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Осталось: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – осталось около <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g>, осталось: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до полной зарядки"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до полной зарядки (от сети)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до полной зарядки (через USB)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до полной зарядки (беспроводная)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Неизвестно"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Идет зарядка"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Зарядка от сети"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Зарядка"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Зарядка через USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Зарядка"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Беспроводная зарядка"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Зарядка"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Не заряжается"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Не заряжается"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Батарея заряжена"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Очень крупный"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Максимальный"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Другой (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-si-rLK/strings.xml b/packages/SettingsLib/res/values-si-rLK/strings.xml
index 99f018b..90b82f1 100644
--- a/packages/SettingsLib/res/values-si-rLK/strings.xml
+++ b/packages/SettingsLib/res/values-si-rLK/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"මෙම විශේෂාංගය පරීක්ෂණාත්මක සහ ඇතැම් විට ක්‍රියාකාරිත්වයට බලපෑ හැක."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> මගින් ඉක්මවන ලදී"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"දළ වශයෙන් <xliff:g id="TIME">%1$s</xliff:g>ක් ඉතිරිය"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"ඉතිරි <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - ආසන්න <xliff:g id="TIME">%2$s</xliff:g> වම"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - ඉතිරි <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> සම්පුර්ණ වන තෙක්"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"AC හි <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> සම්පුර්ණ වන තෙක්"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"USB හරහ <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> සම්පුර්ණ වන තෙක්"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"රේඩියෝව වෙතින් <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> සම්පූර්ණ වන තෙක්"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"නොදනී"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ආරෝපණය වෙමින්"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC හි ආරෝපණය වෙමින්"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ආරෝපණය වෙමින්"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB හරහා ආරෝපණය වෙමින්"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ආරෝපණය වෙමින්"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"රැහැන් රහිතව ආරෝපණය වෙමින්"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ආරෝපණය වෙමින්"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ආරෝපණය නොවේ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ආරෝපණය නොවෙමින්"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"පූර්ණ"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"වඩා විශාල"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"විශාලතම"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"අභිරුචි (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-sk/strings.xml b/packages/SettingsLib/res/values-sk/strings.xml
index 4dffdef..dbb4dde 100644
--- a/packages/SettingsLib/res/values-sk/strings.xml
+++ b/packages/SettingsLib/res/values-sk/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Funkcia je experimentálna a môže mať vplyv na výkonnosť."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Prekonané predvoľbou <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Zostáva cca. <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Zostávajúci čas: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – zostáva približne <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – zostávajúci čas: <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabitia"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabitia zo zásuvky"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabitia cez USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do úplného nabitia bezdrôtovo"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Neznáme"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Nabíjanie"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Nabíjanie zo zásuvky"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Nabíjanie"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Nabíjanie cez USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Nabíjanie"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Bezdrôtové nabíjanie"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Nabíjanie"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nenabíja sa"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nenabíja sa"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Nabitá"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Väčšie"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Najväčšie"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Vlastné (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-sl/strings.xml b/packages/SettingsLib/res/values-sl/strings.xml
index 676a3ab..54e8636 100644
--- a/packages/SettingsLib/res/values-sl/strings.xml
+++ b/packages/SettingsLib/res/values-sl/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"To je preskusna funkcija in lahko vpliva na učinkovitost delovanja."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Preglasila nastavitev: <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Še približno <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Še <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – še približno <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – še <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do napolnjenosti"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do napolnjenosti prek napajalnika"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do napolnjenosti prek USB-ja"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> do napolnjenosti prek brezž. pol."</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Neznano"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Polnjenje"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Polnj. prek iz. toka"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Polnjenje"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Polnj. prek USB-ja"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Polnjenje"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Brezžično polnjenje"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Polnjenje"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Se ne polni"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Se ne polni"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Poln"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Večje"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Največje"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Po meri (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-sq-rAL/strings.xml b/packages/SettingsLib/res/values-sq-rAL/strings.xml
index c18e639..ecc10f4 100644
--- a/packages/SettingsLib/res/values-sq-rAL/strings.xml
+++ b/packages/SettingsLib/res/values-sq-rAL/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ky funksion është eksperimental dhe mund të ndikojë në veprimtari."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Mbivendosur nga <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Afërsisht <xliff:g id="TIME">%1$s</xliff:g> të mbetura"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> të mbetura"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - afërsisht <xliff:g id="TIME">%2$s</xliff:g> të mbetura"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> të mbetura"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> derisa të jetë e plotë"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> deri sa të mbushet në AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> deri sa të mbushet me USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> deri sa të mbushet nga lidhja pa tel"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"I panjohur"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Po ngarkohet"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Po ngarkohet në AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Po ngarkohet"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Po ngarkohet me USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Po ngarkohet"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Po ngarkohet me valë"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Po ngarkohet"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Nuk po ngarkohet"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Nuk po ngarkohet"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"E mbushur"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Më i madh"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Më i madhi"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"I personalizuar (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-sr/strings.xml b/packages/SettingsLib/res/values-sr/strings.xml
index c0791fc..5330893 100644
--- a/packages/SettingsLib/res/values-sr/strings.xml
+++ b/packages/SettingsLib/res/values-sr/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ова функција је експериментална и може да утиче на перформансе."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Замењује га <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Још отприлике <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Преостало време: <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – преостало око <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"Преостало је <xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> док се не напуни"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> док се не напуни пуњачем"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> док се не напуни преко USB-а"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> док се не напуни бежично"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Непознато"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Пуњење"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Пуњење преко пуњача"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Пуни се"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Пуњење преко USB-а"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Пуни се"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Бежично пуњење"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Пуни се"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Не пуни се"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Не пуни се"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Пуно"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Већи"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Највећи"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Прилагођени (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-sv/strings.xml b/packages/SettingsLib/res/values-sv/strings.xml
index 60c42a5..0a054578 100644
--- a/packages/SettingsLib/res/values-sv/strings.xml
+++ b/packages/SettingsLib/res/values-sv/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Den här funktionen är experimentell och kan påverka prestandan."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Har åsidosatts av <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Ca <xliff:g id="TIME">%1$s</xliff:g> kvar"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> kvar"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – ca <xliff:g id="TIME">%2$s</xliff:g> kvar"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> kvar"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> till fulladdat"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> till fulladdat via laddare"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> till fulladdat via USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> till fulladdat via trådlös laddning"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Okänd"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Laddar"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Laddas via adapter"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Laddar"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Laddas via USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Laddar"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Laddas trådlöst"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Laddar"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Laddar inte"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Laddar inte"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Fullt"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Större"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Störst"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Anpassad (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-sw/strings.xml b/packages/SettingsLib/res/values-sw/strings.xml
index 5de7686..20d3cc8 100644
--- a/packages/SettingsLib/res/values-sw/strings.xml
+++ b/packages/SettingsLib/res/values-sw/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Kipengele hiki ni cha majaribio na huenda kikaathiri utendaji."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Imetanguliwa na <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Zimesalia takribani <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Zimesalia <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - imesalia takriban <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"Imechaji <xliff:g id="LEVEL">%1$s</xliff:g> - Zimesalia <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - imesalia <xliff:g id="TIME">%2$s</xliff:g> hadi ijae"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - imesalia <xliff:g id="TIME">%2$s</xliff:g> hadi ijae kwa kutumia AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g>%% - imesalia <xliff:g id="TIME">%2$s</xliff:g> hadi ijae kwa kutumia USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - imesalia <xliff:g id="TIME">%2$s</xliff:g> hadi ijae kwa isiyotumia waya"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Haijulikani"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Inachaji"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Inachaji kupitia AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Inachaji"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Inachaji kupitia USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Inachaji"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Inachaji bila kutumia waya"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Inachaji"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Haichaji"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Haichaji"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Imejaa"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Kubwa kiasi"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Kubwa zaidi"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Kiwango maalum (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ta-rIN/strings.xml b/packages/SettingsLib/res/values-ta-rIN/strings.xml
index a5f04d0..304680b 100644
--- a/packages/SettingsLib/res/values-ta-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-ta-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"இது சோதனை முறையிலான அம்சம், இது செயல்திறனைப் பாதிக்கலாம்."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> மூலம் மேலெழுதப்பட்டது"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"தோராயமாக <xliff:g id="TIME">%1$s</xliff:g> உள்ளது"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> மீதமுள்ளது"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"தோராயம்: <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> உள்ளது"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> மீதமுள்ளது"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"முழு சார்ஜிற்கு: <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"முழு AC சார்ஜிற்கு: <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"முழு USB சார்ஜிற்கு: <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"முழு வயர்லெஸ் சார்ஜிற்கு: <xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"அறியப்படாத"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"சார்ஜ் ஏற்றப்படுகிறது"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC மூலம் சார்ஜாகிறது"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"சார்ஜ் ஏறுகிறது"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB மூலம் சார்ஜாகிறது"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"சார்ஜ் ஏறுகிறது"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"வயர்லெஸில் சார்ஜாகிறது"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"சார்ஜ் ஏறுகிறது"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"சார்ஜ் செய்யப்படவில்லை"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"சார்ஜ் ஏறவில்லை"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"முழுமை"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"கொஞ்சம் பெரியது"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"மிகப் பெரியது"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"தனிப்பயன் (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-te-rIN/strings.xml b/packages/SettingsLib/res/values-te-rIN/strings.xml
index fe40766..b6457c7 100644
--- a/packages/SettingsLib/res/values-te-rIN/strings.xml
+++ b/packages/SettingsLib/res/values-te-rIN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"ఈ లక్షణం ప్రయోగాత్మకమైనది మరియు పనితీరుపై ప్రభావం చూపవచ్చు."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> ద్వారా భర్తీ చేయబడింది"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"సుమారు <xliff:g id="TIME">%1$s</xliff:g> మిగిలి ఉంది"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> మిగిలి ఉంది"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - సుమారు <xliff:g id="TIME">%2$s</xliff:g> మిగిలి ఉంది"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> మిగిలి ఉంది"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - పూర్తిగా నిండటానికి <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - ACలో పూర్తిగా నిండటానికి <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - USB ద్వారా పూర్తిగా నిండటానికి <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - వైర్‌లెస్ నుండి పూర్తిగా నిండటానికి <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"తెలియదు"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"ఛార్జ్ అవుతోంది"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"ACలో ఛార్జ్ అవుతోంది"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"ఛార్జ్ అవుతోంది"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB ద్వారా ఛార్జ్ అవుతోంది"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"ఛార్జ్ అవుతోంది"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"వైర్‌లెస్‌ ద్వారా ఛార్జ్ అవుతోంది"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"ఛార్జ్ అవుతోంది"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ఛార్జ్ కావడం లేదు"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ఛార్జ్ కావడం లేదు"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"నిండింది"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"చాలా పెద్దగా"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"అతి పెద్దగా"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"అనుకూలం (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-th/strings.xml b/packages/SettingsLib/res/values-th/strings.xml
index c58692f..345da0f 100644
--- a/packages/SettingsLib/res/values-th/strings.xml
+++ b/packages/SettingsLib/res/values-th/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"คุณลักษณะนี้เป็นแบบทดลองและอาจส่งผลต่อประสิทธิภาพการทำงาน"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"แทนที่โดย <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"เหลืออีกประมาณ <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"เหลือเวลา <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - เหลือประมาณ <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - เหลืออีก <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> จนกว่าจะเต็ม"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> จนกว่าจะเต็มเมื่อชาร์จผ่าน AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> จนกว่าจะเต็มเมื่อชาร์จผ่าน USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> จนกว่าจะเต็มเมื่อชาร์จผ่านระบบไร้สาย"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"ไม่ทราบ"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"กำลังชาร์จ"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"กำลังชาร์จไฟ AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"กำลังชาร์จ"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"กำลังชาร์จผ่าน USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"กำลังชาร์จ"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"กำลังชาร์จแบบไร้สาย"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"กำลังชาร์จ"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"ไม่ได้ชาร์จ"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"ไม่ได้ชาร์จ"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"เต็ม"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"ใหญ่ขึ้น"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"ใหญ่ที่สุด"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"กำหนดเอง (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-tl/strings.xml b/packages/SettingsLib/res/values-tl/strings.xml
index 093256c..f820ab8 100644
--- a/packages/SettingsLib/res/values-tl/strings.xml
+++ b/packages/SettingsLib/res/values-tl/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Ang feature na ito ay pinag-eeksperimentuhan at maaaring makaapekto sa pagganap."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Na-override ng <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Humigit-kumulang <xliff:g id="TIME">%1$s</xliff:g> na lang ang natitira"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> pa"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - humigit kumulang <xliff:g id="TIME">%2$s</xliff:g> ang natitira"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> pa"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> bago mapuno"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> bago mapuno sa AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> bago mapuno sa USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> bago mapuno mula sa wireless"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Hindi Kilala"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Nagcha-charge"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Nagcha-charge sa AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Nagcha-charge"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Nagcha-charge sa USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Nagcha-charge"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Wireless nag-charge"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Nagcha-charge"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Hindi nagcha-charge"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Hindi nagkakarga"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Puno"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Mas malaki"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Pinakamalaki"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Custom (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-tr/strings.xml b/packages/SettingsLib/res/values-tr/strings.xml
index 1947d39..9766dea 100644
--- a/packages/SettingsLib/res/values-tr/strings.xml
+++ b/packages/SettingsLib/res/values-tr/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Bu özellik deneyseldir ve performansı etkileyebilir."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> tarafından geçersiz kılındı"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Yaklaşık <xliff:g id="TIME">%1$s</xliff:g> kaldı"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> kaldı"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - yaklaşık <xliff:g id="TIME">%2$s</xliff:g> kaldı"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> kaldı"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - tam şarj olmasına <xliff:g id="TIME">%2$s</xliff:g> var"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - prize takılı, tam şarj olmasına <xliff:g id="TIME">%2$s</xliff:g> var"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - USB üzerinden şarj olmasına <xliff:g id="TIME">%2$s</xliff:g> var"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - kablosuzdan tam şarj olmasına <xliff:g id="TIME">%2$s</xliff:g> var"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Bilinmiyor"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Şarj oluyor"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"AC ile şarj oluyor"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Şarj oluyor"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"USB ile şarj oluyor"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Şarj oluyor"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Kablosuz şarj oluyor"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Şarj oluyor"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Şarj olmuyor"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Şarj etmiyor"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Dolu"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Daha büyük"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"En büyük"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Özel (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-uk/strings.xml b/packages/SettingsLib/res/values-uk/strings.xml
index 0ed6cc0..831484f 100644
--- a/packages/SettingsLib/res/values-uk/strings.xml
+++ b/packages/SettingsLib/res/values-uk/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Це експериментальна функція. Вона може вплинути на продуктивність."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Замінено на <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Залишилося приблизно <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Залишилося <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – залишилось близько <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – залишилося <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до повного зарядження"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до повного зарядження з розетки"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до повного зарядження через USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> до повного з бездротового зарядження"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Невідомо"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Зарядж-ся"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Заряджання з розетки"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Заряджається"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Заряджання через USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Заряджається"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Заряджання без дроту"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Заряджається"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Не заряджається"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Не заряджається"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Акумулятор заряджено"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Більші елементи"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Найбільші елементи"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Спеціальний масштаб (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-ur-rPK/strings.xml b/packages/SettingsLib/res/values-ur-rPK/strings.xml
index 99a0f2b..15277ae 100644
--- a/packages/SettingsLib/res/values-ur-rPK/strings.xml
+++ b/packages/SettingsLib/res/values-ur-rPK/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"یہ خصوصیت تجرباتی ہے اور اس کی وجہ سے کاکردگی متاثر ہو سکتی ہے۔"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> کے ذریعہ منسوخ کردیا گیا"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"تقریبا <xliff:g id="TIME">%1$s</xliff:g> باقی ہیں"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> باقی ہے"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"‏‎<xliff:g id="LEVEL">%1$s</xliff:g>‎ - تقریبا <xliff:g id="TIME">%2$s</xliff:g> باقی"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> باقی ہے"</string>
     <string name="power_charging" msgid="1779532561355864267">"‎<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>‎"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"‏‎<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>‎ پورا ہونے تک"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"‏‎<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> AC‎ پر پورا ہونے تک"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"‏‎<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> USB‎ پر پورا ہونے تک"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"‏‎<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>‎ وائرلیس سے پورا ہونے تک"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"نامعلوم"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"چارج ہو رہا ہے"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"‏AC پر چارج ہو رہی ہے"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"چارجنگ ہو رہی ہے"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"‏‫USB پر چارج ہورہی ہے"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"چارجنگ ہو رہی ہے"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"وائرلیس چارجنگ"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"چارجنگ ہو رہی ہے"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"چارج نہیں ہو رہا ہے"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"چارج نہیں ہو رہا ہے"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"مکمل"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"قدرے بڑا"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"سب سے بڑا"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"حسب ضرورت (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-uz-rUZ/strings.xml b/packages/SettingsLib/res/values-uz-rUZ/strings.xml
index b9c0243..374e7fc 100644
--- a/packages/SettingsLib/res/values-uz-rUZ/strings.xml
+++ b/packages/SettingsLib/res/values-uz-rUZ/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Bu funksiya tajribaviy bo‘lib, u qurilma unumdorligiga ta’sir qilishi mumkin."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"<xliff:g id="TITLE">%1$s</xliff:g> bilan almashtirildi"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Taxminan <xliff:g id="TIME">%1$s</xliff:g> qoldi"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> qoldi"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> – taxminan <xliff:g id="TIME">%2$s</xliff:g> qoldi"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g> qoldi"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, to‘lguncha"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, o‘zgaruvchan tok orqali to‘lguncha"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, USB orqali to‘lguncha"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>, simsiz quvvatlash orqali to‘lguncha"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> – <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Noma’lum"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Quvvat olmoqda"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Quvvat olmoqda (AC)"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Quvvat olmoqda"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Quvvat olmoqda (USB)"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Quvvat olmoqda"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Simsiz quvvat olmoqda"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Quvvat olmoqda"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Quvvat olmayapti"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Quvvatlanmayapti"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"To‘la"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Kattaroq"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Eng katta"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Moslashtirilgan (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-vi/strings.xml b/packages/SettingsLib/res/values-vi/strings.xml
index 0c3dc89..1c86175 100644
--- a/packages/SettingsLib/res/values-vi/strings.xml
+++ b/packages/SettingsLib/res/values-vi/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Tính năng này là tính năng thử nghiệm và có thể ảnh hưởng đến hoạt động."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Bị ghi đè bởi <xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Còn khoảng <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"Còn lại <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - còn khoảng <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - còn lại <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> cho đến khi đầy"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> cho đến khi đầy khi cắm vào nguồn AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> cho đến khi đầy qua USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> cho đến khi đầy từ không dây"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Không xác định"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Đang sạc"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Sạc trên AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Đang sạc"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Sạc qua USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Đang sạc"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Sạc không dây"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Đang sạc"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Hiện không sạc"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Hiện không sạc"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Đầy"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Lớn hơn"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Lớn nhất"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Tùy chỉnh (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-zh-rCN/strings.xml b/packages/SettingsLib/res/values-zh-rCN/strings.xml
index 2b8ce65..d0dc925 100644
--- a/packages/SettingsLib/res/values-zh-rCN/strings.xml
+++ b/packages/SettingsLib/res/values-zh-rCN/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"此功能为实验性功能,可能会影响性能。"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"已被“<xliff:g id="TITLE">%1$s</xliff:g>”覆盖"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"还剩大约 <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"还可用 <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - 还可用大约<xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - 还可用 <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - 还需<xliff:g id="TIME">%2$s</xliff:g>充满"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - 还需<xliff:g id="TIME">%2$s</xliff:g>充满(交流电充电)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - 还需<xliff:g id="TIME">%2$s</xliff:g>充满(USB充电)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - 还需<xliff:g id="TIME">%2$s</xliff:g>充满(无线充电)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"未知"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"正在充电"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"正在通过交流电源充电"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"正在充电"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"正在通过USB充电"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"正在充电"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"正在无线充电"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"正在充电"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"未在充电"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"未在充电"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"电量充足"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"较大"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"最大"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"自定义 (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-zh-rHK/strings.xml b/packages/SettingsLib/res/values-zh-rHK/strings.xml
index 8dd0417..9bb0a4c 100644
--- a/packages/SettingsLib/res/values-zh-rHK/strings.xml
+++ b/packages/SettingsLib/res/values-zh-rHK/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"這是一項實驗性功能,可能會影響效能。"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"已由「<xliff:g id="TITLE">%1$s</xliff:g>」覆寫"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"尚餘大約 <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"尚餘 <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - 尚餘大約 <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - 尚餘 <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 後完成充電"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 後完成充電 (透過插頭充電)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 後完成充電 (透過 USB 充電)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> 後完成充電 (無線充電)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"未知"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"充電中"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"正在透過 AC 充電"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"正在充電"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"正在透過 USB 充電"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"正在充電"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"正在透過無線方式充電"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"正在充電"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"非充電中"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"未開始充電"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"電量已滿"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"較大"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"最大"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"自訂 (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-zh-rTW/strings.xml b/packages/SettingsLib/res/values-zh-rTW/strings.xml
index dd59954..bf3880b 100644
--- a/packages/SettingsLib/res/values-zh-rTW/strings.xml
+++ b/packages/SettingsLib/res/values-zh-rTW/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"這是一項實驗性功能,可能會對效能造成影響。"</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"已改為<xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"還剩大約 <xliff:g id="TIME">%1$s</xliff:g>"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"還剩 <xliff:g id="TIME">%1$s</xliff:g>"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - 大約還剩 <xliff:g id="TIME">%2$s</xliff:g>"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - 還剩 <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>後充飽"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>後充飽 (AC)"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>後充飽 (USB)"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>後充飽 (無線充電)"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"不明"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"充電中"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"正在透過 AC 變壓器充電"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"充電中"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"正在透過 USB 充電"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"充電中"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"正在透過無線方式充電"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"充電中"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"非充電中"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"非充電中"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"電力充足"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"較大"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"最大"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"自訂 (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values-zu/strings.xml b/packages/SettingsLib/res/values-zu/strings.xml
index 610cac4..7953372 100644
--- a/packages/SettingsLib/res/values-zu/strings.xml
+++ b/packages/SettingsLib/res/values-zu/strings.xml
@@ -296,35 +296,26 @@
     <string name="accessibility_display_daltonizer_preference_subtitle" msgid="3484969015295282911">"Lesi sici esesilingo futhi singathinta ukusebenza."</string>
     <string name="daltonizer_type_overridden" msgid="3116947244410245916">"Igitshezwe ngaphezulu yi-<xliff:g id="TITLE">%1$s</xliff:g>"</string>
     <string name="power_remaining_duration_only" msgid="4400068916452346544">"Cishe ngu-<xliff:g id="TIME">%1$s</xliff:g> osele"</string>
-    <!-- no translation found for power_remaining_duration_only_short (5329694252258605547) -->
-    <skip />
+    <string name="power_remaining_duration_only_short" msgid="5329694252258605547">"<xliff:g id="TIME">%1$s</xliff:g> esisele"</string>
     <string name="power_discharging_duration" msgid="1605929174734600590">"<xliff:g id="LEVEL">%1$s</xliff:g> - isilinganiso esingu-<xliff:g id="TIME">%2$s</xliff:g> esisele"</string>
-    <!-- no translation found for power_discharging_duration_short (4192244429001842403) -->
-    <skip />
+    <string name="power_discharging_duration_short" msgid="4192244429001842403">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> okusele"</string>
     <string name="power_charging" msgid="1779532561355864267">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="STATE">%2$s</xliff:g>"</string>
     <string name="power_charging_duration" msgid="2853265177761520490">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> kuze igcwale"</string>
-    <!-- no translation found for power_charging_duration_short (1098603958472207920) -->
-    <skip />
+    <string name="power_charging_duration_short" msgid="1098603958472207920">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_ac" msgid="3969186192576594254">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> kuze igcwale ku-AC"</string>
-    <!-- no translation found for power_charging_duration_ac_short (7895864687218765582) -->
-    <skip />
+    <string name="power_charging_duration_ac_short" msgid="7895864687218765582">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_usb" msgid="182405645340976546">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> kuze igcwale ngaphezulu kwe-USB"</string>
-    <!-- no translation found for power_charging_duration_usb_short (941854728040426399) -->
-    <skip />
+    <string name="power_charging_duration_usb_short" msgid="941854728040426399">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="power_charging_duration_wireless" msgid="1829295708243159464">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g> kuze igcwale kusukela kokungenantambo"</string>
-    <!-- no translation found for power_charging_duration_wireless_short (1642664799869599476) -->
-    <skip />
+    <string name="power_charging_duration_wireless_short" msgid="1642664799869599476">"<xliff:g id="LEVEL">%1$s</xliff:g> - <xliff:g id="TIME">%2$s</xliff:g>"</string>
     <string name="battery_info_status_unknown" msgid="196130600938058547">"Akwaziwa"</string>
     <string name="battery_info_status_charging" msgid="1705179948350365604">"Iyashaja"</string>
     <string name="battery_info_status_charging_ac" msgid="2909861890674399949">"Iyashaja ku-AC"</string>
-    <!-- no translation found for battery_info_status_charging_ac_short (7431401092096415502) -->
-    <skip />
+    <string name="battery_info_status_charging_ac_short" msgid="7431401092096415502">"Iyashaja"</string>
     <string name="battery_info_status_charging_usb" msgid="2207489369680923929">"Iyashaja ngaphezulu kwe-USB"</string>
-    <!-- no translation found for battery_info_status_charging_usb_short (6733371990319101366) -->
-    <skip />
+    <string name="battery_info_status_charging_usb_short" msgid="6733371990319101366">"Iyashaja"</string>
     <string name="battery_info_status_charging_wireless" msgid="3574032603735446573">"Iyashaja ngaphandle kwentambo"</string>
-    <!-- no translation found for battery_info_status_charging_wireless_short (752569941028903610) -->
-    <skip />
+    <string name="battery_info_status_charging_wireless_short" msgid="752569941028903610">"Iyashaja"</string>
     <string name="battery_info_status_discharging" msgid="310932812698268588">"Ayishaji"</string>
     <string name="battery_info_status_not_charging" msgid="2820070506621483576">"Ayishaji"</string>
     <string name="battery_info_status_full" msgid="2824614753861462808">"Kugcwele"</string>
@@ -340,4 +331,6 @@
     <string name="screen_zoom_summary_very_large" msgid="7108563375663670067">"Okukhulu kakhulu"</string>
     <string name="screen_zoom_summary_extremely_large" msgid="7427320168263276227">"Okukhulu kakhulu"</string>
     <string name="screen_zoom_summary_custom" msgid="5611979864124160447">"Ngokwezifiso (<xliff:g id="DENSITYDPI">%d</xliff:g>)"</string>
+    <!-- no translation found for help_feedback_label (6815040660801785649) -->
+    <skip />
 </resources>
diff --git a/packages/SettingsLib/res/values/strings.xml b/packages/SettingsLib/res/values/strings.xml
index a560e3c..985fe3c 100644
--- a/packages/SettingsLib/res/values/strings.xml
+++ b/packages/SettingsLib/res/values/strings.xml
@@ -804,7 +804,7 @@
     <string name="disabled_by_admin">Disabled by administrator</string>
 
     <!-- Option in navigation drawer that leads to Settings main screen [CHAR LIMIT=30] -->
-    <string name="home">Home</string>
+    <string name="home">Settings Home</string>
 
     <string-array name="battery_labels" translatable="false">
         <item>0%</item>
@@ -850,5 +850,7 @@
     <!-- Description for a custom screen zoom level. This shows the requested display
          density in raw pixels per inch rather than using a relative description. [CHAR LIMIT=24] -->
     <string name="screen_zoom_summary_custom">Custom (<xliff:g id="densityDpi" example="160">%d</xliff:g>)</string>
+    <!-- Label for Help and feedback menu item -->
+    <string name="help_feedback_label">Help &amp; feedback</string>
 
 </resources>
diff --git a/packages/SettingsLib/src/com/android/settingslib/HelpUtils.java b/packages/SettingsLib/src/com/android/settingslib/HelpUtils.java
new file mode 100644
index 0000000..320cd58
--- /dev/null
+++ b/packages/SettingsLib/src/com/android/settingslib/HelpUtils.java
@@ -0,0 +1,205 @@
+/*
+ * Copyright (C) 2012 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.settingslib;
+
+import android.app.Activity;
+import android.content.ActivityNotFoundException;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager.NameNotFoundException;
+import android.content.res.Resources.Theme;
+import android.net.Uri;
+import android.text.TextUtils;
+import android.util.Log;
+import android.util.TypedValue;
+import android.view.Menu;
+import android.view.MenuItem;
+import android.view.MenuItem.OnMenuItemClickListener;
+
+import java.net.URISyntaxException;
+import java.util.Locale;
+
+/**
+ * Functions to easily prepare contextual help menu option items with an intent that opens up the
+ * browser to a particular URL, while taking into account the preferred language and app version.
+ */
+public class HelpUtils {
+    private final static String TAG = HelpUtils.class.getSimpleName();
+
+    private static final int MENU_HELP = Menu.FIRST + 100;
+
+    /**
+     * Help URL query parameter key for the preferred language.
+     */
+    private final static String PARAM_LANGUAGE_CODE = "hl";
+
+    /**
+     * Help URL query parameter key for the app version.
+     */
+    private final static String PARAM_VERSION = "version";
+
+    // Constants for help intents.
+    private static final String EXTRA_CONTEXT = "EXTRA_CONTEXT";
+    private static final String EXTRA_THEME = "EXTRA_THEME";
+    private static final String EXTRA_PRIMARY_COLOR = "EXTRA_PRIMARY_COLOR";
+    private static final String EXTRA_BACKUP_URI = "EXTRA_BACKUP_URI";
+
+    /**
+     * Cached version code to prevent repeated calls to the package manager.
+     */
+    private static String sCachedVersionCode = null;
+
+    /** Static helper that is not instantiable*/
+    private HelpUtils() { }
+
+    public static boolean prepareHelpMenuItem(Activity activity, Menu menu, String helpUri,
+            String backupContext) {
+        MenuItem helpItem = menu.add(0, MENU_HELP, 0, R.string.help_feedback_label);
+        return prepareHelpMenuItem(activity, helpItem, helpUri, backupContext);
+    }
+
+    public static boolean prepareHelpMenuItem(Activity activity, Menu menu, int helpUriResource,
+            String backupContext) {
+        MenuItem helpItem = menu.add(0, MENU_HELP, 0, R.string.help_feedback_label);
+        return prepareHelpMenuItem(activity, helpItem, activity.getString(helpUriResource),
+                backupContext);
+    }
+
+    /**
+     * Prepares the help menu item by doing the following.
+     * - If the helpUrlString is empty or null, the help menu item is made invisible.
+     * - Otherwise, this makes the help menu item visible and sets the intent for the help menu
+     *   item to view the URL.
+     *
+     * @return returns whether the help menu item has been made visible.
+     */
+    public static boolean prepareHelpMenuItem(final Activity activity, MenuItem helpMenuItem,
+            String helpUriString, String backupContext) {
+        if (TextUtils.isEmpty(helpUriString)) {
+            // The help url string is empty or null, so set the help menu item to be invisible.
+            helpMenuItem.setVisible(false);
+
+            // return that the help menu item is not visible (i.e. false)
+            return false;
+        } else {
+            final Intent intent = getHelpIntent(activity, helpUriString, backupContext);
+
+            // Set the intent to the help menu item, show the help menu item in the overflow
+            // menu, and make it visible.
+            if (intent != null) {
+                helpMenuItem.setOnMenuItemClickListener(new OnMenuItemClickListener() {
+                    @Override
+                    public boolean onMenuItemClick(MenuItem item) {
+                        try {
+                            activity.startActivityForResult(intent, 0);
+                        } catch (ActivityNotFoundException exc) {
+                            Log.e(TAG, "No activity found for intent: " + intent);
+                        }
+                        return true;
+                    }
+                });
+                helpMenuItem.setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER);
+                helpMenuItem.setVisible(true);
+            } else {
+                helpMenuItem.setVisible(false);
+                return false;
+            }
+
+            // return that the help menu item is visible (i.e., true)
+            return true;
+        }
+    }
+
+    public static Intent getHelpIntent(Context context, String helpUriString,
+            String backupContext) {
+        // Try to handle as Intent Uri, otherwise just treat as Uri.
+        try {
+            Intent intent = Intent.parseUri(helpUriString,
+                    Intent.URI_ANDROID_APP_SCHEME | Intent.URI_INTENT_SCHEME);
+            addIntentParameters(context, intent, backupContext);
+            ComponentName component = intent.resolveActivity(context.getPackageManager());
+            if (component != null) {
+                return intent;
+            } else if (intent.hasExtra(EXTRA_BACKUP_URI)) {
+                // This extra contains a backup URI for when the intent isn't available.
+                return getHelpIntent(context, intent.getStringExtra(EXTRA_BACKUP_URI),
+                        backupContext);
+            } else {
+                return null;
+            }
+        } catch (URISyntaxException e) {
+        }
+        // The help url string exists, so first add in some extra query parameters.
+        final Uri fullUri = uriWithAddedParameters(context, Uri.parse(helpUriString));
+
+        // Then, create an intent that will be fired when the user
+        // selects this help menu item.
+        Intent intent = new Intent(Intent.ACTION_VIEW, fullUri);
+        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
+                | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
+        return intent;
+    }
+
+    private static void addIntentParameters(Context context, Intent intent, String backupContext) {
+        if (!intent.hasExtra(EXTRA_CONTEXT)) {
+            // Insert some context if none exists.
+            intent.putExtra(EXTRA_CONTEXT, backupContext);
+        }
+        intent.putExtra(EXTRA_THEME, 1 /* Light, dark action bar */);
+        Theme theme = context.getTheme();
+        TypedValue typedValue = new TypedValue();
+        theme.resolveAttribute(android.R.attr.colorPrimary, typedValue, true);
+        intent.putExtra(EXTRA_PRIMARY_COLOR, context.getColor(typedValue.resourceId));
+    }
+
+    /**
+     * Adds two query parameters into the Uri, namely the language code and the version code
+     * of the app's package as gotten via the context.
+     * @return the uri with added query parameters
+     */
+    public static Uri uriWithAddedParameters(Context context, Uri baseUri) {
+        Uri.Builder builder = baseUri.buildUpon();
+
+        // Add in the preferred language
+        builder.appendQueryParameter(PARAM_LANGUAGE_CODE, Locale.getDefault().toString());
+
+        // Add in the package version code
+        if (sCachedVersionCode == null) {
+            // There is no cached version code, so try to get it from the package manager.
+            try {
+                // cache the version code
+                PackageInfo info = context.getPackageManager().getPackageInfo(
+                        context.getPackageName(), 0);
+                sCachedVersionCode = Integer.toString(info.versionCode);
+
+                // append the version code to the uri
+                builder.appendQueryParameter(PARAM_VERSION, sCachedVersionCode);
+            } catch (NameNotFoundException e) {
+                // Cannot find the package name, so don't add in the version parameter
+                // This shouldn't happen.
+                Log.wtf(TAG, "Invalid package name for context", e);
+            }
+        } else {
+            builder.appendQueryParameter(PARAM_VERSION, sCachedVersionCode);
+        }
+
+        // Build the full uri and return it
+        return builder.build();
+    }
+}
diff --git a/packages/SettingsLib/src/com/android/settingslib/Utils.java b/packages/SettingsLib/src/com/android/settingslib/Utils.java
index 586f269..ca0b86a 100644
--- a/packages/SettingsLib/src/com/android/settingslib/Utils.java
+++ b/packages/SettingsLib/src/com/android/settingslib/Utils.java
@@ -15,7 +15,7 @@
 import android.os.BatteryManager;
 import android.os.UserManager;
 import com.android.internal.util.UserIcons;
-import com.android.settingslib.drawable.CircleFramedDrawable;
+import com.android.settingslib.drawable.UserIconDrawable;
 
 import java.text.NumberFormat;
 
@@ -73,21 +73,22 @@
     /**
      * Returns a circular icon for a user.
      */
-    public static Drawable getUserIcon(Context context, UserManager um, UserInfo user) {
+    public static UserIconDrawable getUserIcon(Context context, UserManager um, UserInfo user) {
+        final int iconSize = UserIconDrawable.getSizeForList(context);
         if (user.isManagedProfile()) {
             // We use predefined values for managed profiles
             Bitmap b = BitmapFactory.decodeResource(context.getResources(),
                     com.android.internal.R.drawable.ic_corp_icon);
-            return CircleFramedDrawable.getInstance(context, b);
+            return new UserIconDrawable(iconSize).setIcon(b).bake();
         }
         if (user.iconPath != null) {
             Bitmap icon = um.getUserIcon(user.id);
             if (icon != null) {
-                return CircleFramedDrawable.getInstance(context, icon);
+                return new UserIconDrawable(iconSize).setIcon(icon).bake();
             }
         }
-        return CircleFramedDrawable.getInstance(context, UserIcons.convertToBitmap(
-                UserIcons.getDefaultUserIcon(user.id, /* light= */ false)));
+        return new UserIconDrawable(iconSize).setIconDrawable(
+                UserIcons.getDefaultUserIcon(user.id, /* light= */ false)).bake();
     }
 
     /** Formats the ratio of amount/total as a percentage. */
diff --git a/packages/SettingsLib/src/com/android/settingslib/applications/ApplicationsState.java b/packages/SettingsLib/src/com/android/settingslib/applications/ApplicationsState.java
index d353f31..8881034 100644
--- a/packages/SettingsLib/src/com/android/settingslib/applications/ApplicationsState.java
+++ b/packages/SettingsLib/src/com/android/settingslib/applications/ApplicationsState.java
@@ -534,6 +534,7 @@
         Comparator<AppEntry> mRebuildComparator;
         ArrayList<AppEntry> mRebuildResult;
         ArrayList<AppEntry> mLastAppList;
+        boolean mRebuildForeground;
 
         Session(Callbacks callbacks) {
             mCallbacks = callbacks;
@@ -572,6 +573,11 @@
 
         // Creates a new list of app entries with the given filter and comparator.
         public ArrayList<AppEntry> rebuild(AppFilter filter, Comparator<AppEntry> comparator) {
+            return rebuild(filter, comparator, true);
+        }
+
+        public ArrayList<AppEntry> rebuild(AppFilter filter, Comparator<AppEntry> comparator,
+                boolean foreground) {
             synchronized (mRebuildSync) {
                 synchronized (mEntriesMap) {
                     mRebuildingSessions.add(this);
@@ -579,6 +585,7 @@
                     mRebuildAsync = false;
                     mRebuildFilter = filter;
                     mRebuildComparator = comparator;
+                    mRebuildForeground = foreground;
                     mRebuildResult = null;
                     if (!mBackgroundHandler.hasMessages(BackgroundHandler.MSG_REBUILD_LIST)) {
                         Message msg = mBackgroundHandler.obtainMessage(
@@ -620,10 +627,12 @@
                 mRebuildRequested = false;
                 mRebuildFilter = null;
                 mRebuildComparator = null;
+                if (mRebuildForeground) {
+                    Process.setThreadPriority(Process.THREAD_PRIORITY_FOREGROUND);
+                    mRebuildForeground = false;
+                }
             }
 
-            Process.setThreadPriority(Process.THREAD_PRIORITY_FOREGROUND);
-
             if (filter != null) {
                 filter.init();
             }
@@ -640,7 +649,10 @@
                 if (filter == null || filter.filterApp(entry)) {
                     synchronized (mEntriesMap) {
                         if (DEBUG_LOCKING) Log.v(TAG, "rebuild acquired lock");
-                        entry.ensureLabel(mContext);
+                        if (comparator != null) {
+                            // Only need the label if we are going to be sorting.
+                            entry.ensureLabel(mContext);
+                        }
                         if (DEBUG) Log.i(TAG, "Using " + entry.info.packageName + ": " + entry);
                         filteredApps.add(entry);
                         if (DEBUG_LOCKING) Log.v(TAG, "rebuild releasing lock");
@@ -648,7 +660,9 @@
                 }
             }
 
-            Collections.sort(filteredApps, comparator);
+            if (comparator != null) {
+                Collections.sort(filteredApps, comparator);
+            }
 
             synchronized (mRebuildSync) {
                 if (!mRebuildRequested) {
diff --git a/packages/SettingsLib/src/com/android/settingslib/drawable/UserIconDrawable.java b/packages/SettingsLib/src/com/android/settingslib/drawable/UserIconDrawable.java
new file mode 100644
index 0000000..32478a7
--- /dev/null
+++ b/packages/SettingsLib/src/com/android/settingslib/drawable/UserIconDrawable.java
@@ -0,0 +1,428 @@
+/*
+ * 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 com.android.settingslib.drawable;
+
+import android.annotation.NonNull;
+import android.app.admin.DevicePolicyManager;
+import android.content.Context;
+import android.content.res.ColorStateList;
+import android.graphics.Bitmap;
+import android.graphics.BitmapShader;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.ColorFilter;
+import android.graphics.Matrix;
+import android.graphics.Paint;
+import android.graphics.PixelFormat;
+import android.graphics.PorterDuff;
+import android.graphics.PorterDuffColorFilter;
+import android.graphics.PorterDuffXfermode;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.Shader;
+import android.graphics.drawable.Drawable;
+
+import com.android.settingslib.R;
+
+/**
+ * Converts the user avatar icon to a circularly clipped one with an optional badge and frame
+ */
+public class UserIconDrawable extends Drawable implements Drawable.Callback {
+
+    private Drawable mUserDrawable;
+    private Bitmap mUserIcon;
+    private Bitmap mBitmap; // baked representation. Required for transparent border around badge
+    private final Paint mIconPaint = new Paint();
+    private final Paint mPaint = new Paint();
+    private final Matrix mIconMatrix = new Matrix();
+    private float mIntrinsicRadius;
+    private float mDisplayRadius;
+    private float mPadding = 0;
+    private int mSize = 0; // custom "intrinsic" size for this drawable if non-zero
+    private boolean mInvalidated = true;
+    private ColorStateList mTintColor = null;
+    private PorterDuff.Mode mTintMode = PorterDuff.Mode.SRC_ATOP;
+
+    private float mFrameWidth;
+    private float mFramePadding;
+    private ColorStateList mFrameColor = null;
+    private Paint mFramePaint;
+
+    private Drawable mBadge;
+    private Paint mClearPaint;
+    private float mBadgeRadius;
+    private float mBadgeMargin;
+
+    /**
+     * Gets the system default managed-user badge as a drawable
+     * @param context
+     * @return drawable containing just the badge
+     */
+    public static Drawable getManagedUserBadgeDrawable(Context context) {
+        int displayDensity = context.getResources().getDisplayMetrics().densityDpi;
+        return context.getResources().getDrawableForDensity(
+                com.android.internal.R.drawable.ic_corp_user_badge,
+                displayDensity, context.getTheme());
+    }
+
+    /**
+     * Gets the preferred list-item size of this drawable.
+     * @param context
+     * @return size in pixels
+     */
+    public static int getSizeForList(Context context) {
+        return (int) context.getResources().getDimension(R.dimen.circle_avatar_size);
+    }
+
+    public UserIconDrawable() {
+        this(0);
+    }
+
+    /**
+     * Use this constructor if the drawable is intended to be placed in listviews
+     * @param intrinsicSize if 0, the intrinsic size will come from the icon itself
+     */
+    public UserIconDrawable(int intrinsicSize) {
+        super();
+        mIconPaint.setAntiAlias(true);
+        mIconPaint.setFilterBitmap(true);
+        mPaint.setFilterBitmap(true);
+        mPaint.setAntiAlias(true);
+        if (intrinsicSize > 0) {
+            setBounds(0, 0, intrinsicSize, intrinsicSize);
+            setIntrinsicSize(intrinsicSize);
+        }
+        setIcon(null);
+    }
+
+    public UserIconDrawable setIcon(Bitmap icon) {
+        if (mUserDrawable != null) {
+            mUserDrawable.setCallback(null);
+            mUserDrawable = null;
+        }
+        mUserIcon = icon;
+        if (mUserIcon == null) {
+            mIconPaint.setShader(null);
+            mBitmap = null;
+        } else {
+            mIconPaint.setShader(new BitmapShader(icon, Shader.TileMode.CLAMP,
+                    Shader.TileMode.CLAMP));
+        }
+        onBoundsChange(getBounds());
+        return this;
+    }
+
+    public UserIconDrawable setIconDrawable(Drawable icon) {
+        if (mUserDrawable != null) {
+            mUserDrawable.setCallback(null);
+        }
+        mUserIcon = null;
+        mUserDrawable = icon;
+        if (mUserDrawable == null) {
+            mBitmap = null;
+        } else {
+            mUserDrawable.setCallback(this);
+        }
+        onBoundsChange(getBounds());
+        return this;
+    }
+
+    public UserIconDrawable setBadge(Drawable badge) {
+        mBadge = badge;
+        if (mBadge != null) {
+            if (mClearPaint == null) {
+                mClearPaint = new Paint();
+                mClearPaint.setAntiAlias(true);
+                mClearPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
+                mClearPaint.setStyle(Paint.Style.FILL);
+            }
+            // update metrics
+            onBoundsChange(getBounds());
+        } else {
+            invalidateSelf();
+        }
+        return this;
+    }
+
+    public UserIconDrawable setBadgeIfManagedUser(Context context, int userId) {
+        Drawable badge = null;
+        boolean isManaged = context.getSystemService(DevicePolicyManager.class)
+                .getProfileOwnerAsUser(userId) != null;
+        if (isManaged) {
+            badge = getManagedUserBadgeDrawable(context);
+        }
+        return setBadge(badge);
+    }
+
+    public void setBadgeRadius(float radius) {
+        mBadgeRadius = radius;
+        onBoundsChange(getBounds());
+    }
+
+    public void setBadgeMargin(float margin) {
+        mBadgeMargin = margin;
+        onBoundsChange(getBounds());
+    }
+
+    /**
+     * Sets global padding of icon/frame. Doesn't effect the badge.
+     * @param padding
+     */
+    public void setPadding(float padding) {
+        mPadding = padding;
+        onBoundsChange(getBounds());
+    }
+
+    private void initFramePaint() {
+        if (mFramePaint == null) {
+            mFramePaint = new Paint();
+            mFramePaint.setStyle(Paint.Style.STROKE);
+            mFramePaint.setAntiAlias(true);
+        }
+    }
+
+    public void setFrameWidth(float width) {
+        initFramePaint();
+        mFrameWidth = width;
+        mFramePaint.setStrokeWidth(width);
+        onBoundsChange(getBounds());
+    }
+
+    public void setFramePadding(float padding) {
+        initFramePaint();
+        mFramePadding = padding;
+        onBoundsChange(getBounds());
+    }
+
+    public void setFrameColor(int color) {
+        initFramePaint();
+        mFramePaint.setColor(color);
+        invalidateSelf();
+    }
+
+    public void setFrameColor(ColorStateList colorList) {
+        initFramePaint();
+        mFrameColor = colorList;
+        invalidateSelf();
+    }
+
+    /**
+     * This sets the "intrinsic" size of this drawable. Useful for views which use the drawable's
+     * intrinsic size for layout. It is independent of the bounds.
+     * @param size if 0, the intrinsic size will be set to the displayed icon's size
+     */
+    public void setIntrinsicSize(int size) {
+        mSize = size;
+    }
+
+    @Override
+    public void draw(Canvas canvas) {
+        if (mInvalidated) {
+            rebake();
+        }
+        if (mBitmap != null) {
+            if (mTintColor == null) {
+                mPaint.setColorFilter(null);
+            } else {
+                int color = mTintColor.getColorForState(getState(), mTintColor.getDefaultColor());
+                if (mPaint.getColorFilter() == null) {
+                    mPaint.setColorFilter(new PorterDuffColorFilter(color, mTintMode));
+                } else {
+                    ((PorterDuffColorFilter) mPaint.getColorFilter()).setMode(mTintMode);
+                    ((PorterDuffColorFilter) mPaint.getColorFilter()).setColor(color);
+                }
+            }
+
+            canvas.drawBitmap(mBitmap, 0, 0, mPaint);
+        }
+    }
+
+    @Override
+    public void setAlpha(int alpha) {
+        mPaint.setAlpha(alpha);
+        super.invalidateSelf();
+    }
+
+    @Override
+    public void setColorFilter(ColorFilter colorFilter) {
+    }
+
+    @Override
+    public void setTintList(ColorStateList tintList) {
+        mTintColor = tintList;
+        super.invalidateSelf();
+    }
+
+    @Override
+    public void setTintMode(@NonNull PorterDuff.Mode mode) {
+        mTintMode = mode;
+        super.invalidateSelf();
+    }
+
+    /**
+     * This 'bakes' the current state of this icon into a bitmap and removes/recycles the source
+     * bitmap/drawable. Use this when no more changes will be made and an intrinsic size is set.
+     * This effectively turns this into a static drawable.
+     */
+    public UserIconDrawable bake() {
+        if (mSize <= 0) {
+            throw new IllegalStateException("Baking requires an explicit intrinsic size");
+        }
+        onBoundsChange(new Rect(0, 0, mSize, mSize));
+        rebake();
+        mFrameColor = null;
+        mFramePaint = null;
+        mClearPaint = null;
+        if (mUserDrawable != null) {
+            mUserDrawable.setCallback(null);
+            mUserDrawable = null;
+        } else if (mUserIcon != null) {
+            mUserIcon.recycle();
+            mUserIcon = null;
+        }
+        return this;
+    }
+
+    private void rebake() {
+        mInvalidated = false;
+
+        if (mBitmap == null || (mUserDrawable == null && mUserIcon == null)) {
+            return;
+        }
+
+        final Canvas canvas = new Canvas(mBitmap);
+        canvas.drawColor(0, PorterDuff.Mode.CLEAR);
+
+        if(mUserDrawable != null) {
+            mUserDrawable.draw(canvas);
+        } else if (mUserIcon != null) {
+            int saveId = canvas.save();
+            canvas.concat(mIconMatrix);
+            canvas.drawCircle(mUserIcon.getWidth() * 0.5f, mUserIcon.getHeight() * 0.5f,
+                    mIntrinsicRadius, mIconPaint);
+            canvas.restoreToCount(saveId);
+        }
+
+        if (mFrameColor != null) {
+            mFramePaint.setColor(mFrameColor.getColorForState(getState(), Color.TRANSPARENT));
+        }
+        if ((mFrameWidth + mFramePadding) > 0.001f) {
+            float radius = mDisplayRadius - mPadding - mFrameWidth * 0.5f;
+            canvas.drawCircle(getBounds().exactCenterX(), getBounds().exactCenterY(),
+                    radius, mFramePaint);
+        }
+
+        if ((mBadge != null) && (mBadgeRadius > 0.001f)) {
+            final float badgeDiameter = mBadgeRadius * 2f;
+            final float badgeTop = mBitmap.getHeight() - badgeDiameter;
+            float badgeLeft = mBitmap.getWidth() - badgeDiameter;
+
+            mBadge.setBounds((int) badgeLeft, (int) badgeTop,
+                    (int) (badgeLeft + badgeDiameter), (int) (badgeTop + badgeDiameter));
+
+            final float borderRadius = mBadge.getBounds().width() * 0.5f + mBadgeMargin;
+            canvas.drawCircle(badgeLeft + mBadgeRadius, badgeTop + mBadgeRadius,
+                    borderRadius, mClearPaint);
+
+            mBadge.draw(canvas);
+        }
+    }
+
+    @Override
+    protected void onBoundsChange(Rect bounds) {
+        if (bounds.isEmpty() || (mUserIcon == null && mUserDrawable == null)) {
+            return;
+        }
+
+        // re-create bitmap if applicable
+        float newDisplayRadius = Math.min(bounds.width(), bounds.height()) * 0.5f;
+        int size = (int) (newDisplayRadius * 2);
+        if (mBitmap == null || size != ((int) (mDisplayRadius * 2))) {
+            mDisplayRadius = newDisplayRadius;
+            if (mBitmap != null) {
+                mBitmap.recycle();
+            }
+            mBitmap = Bitmap.createBitmap(size, size, Bitmap.Config.ARGB_8888);
+        }
+
+        // update metrics
+        mDisplayRadius = Math.min(bounds.width(), bounds.height()) * 0.5f;
+        final float iconRadius = mDisplayRadius - mFrameWidth - mFramePadding - mPadding;
+        RectF dstRect = new RectF(bounds.exactCenterX() - iconRadius,
+                                  bounds.exactCenterY() - iconRadius,
+                                  bounds.exactCenterX() + iconRadius,
+                                  bounds.exactCenterY() + iconRadius);
+        if (mUserDrawable != null) {
+            Rect rounded = new Rect();
+            dstRect.round(rounded);
+            mIntrinsicRadius = Math.min(mUserDrawable.getIntrinsicWidth(),
+                                        mUserDrawable.getIntrinsicHeight()) * 0.5f;
+            mUserDrawable.setBounds(rounded);
+        } else if (mUserIcon != null) {
+            // Build square-to-square transformation matrix
+            final float iconCX = mUserIcon.getWidth() * 0.5f;
+            final float iconCY = mUserIcon.getHeight() * 0.5f;
+            mIntrinsicRadius = Math.min(iconCX, iconCY);
+            RectF srcRect = new RectF(iconCX - mIntrinsicRadius, iconCY - mIntrinsicRadius,
+                                      iconCX + mIntrinsicRadius, iconCY + mIntrinsicRadius);
+            mIconMatrix.setRectToRect(srcRect, dstRect, Matrix.ScaleToFit.FILL);
+        }
+
+        invalidateSelf();
+    }
+
+    @Override
+    public void invalidateSelf() {
+        super.invalidateSelf();
+        mInvalidated = true;
+    }
+
+    @Override
+    public boolean isStateful() {
+        return mFrameColor != null && mFrameColor.isStateful();
+    }
+
+    @Override
+    public int getOpacity() {
+        return PixelFormat.TRANSLUCENT;
+    }
+
+    @Override
+    public int getIntrinsicWidth() {
+        return (mSize <= 0 ? (int) mIntrinsicRadius * 2 : mSize);
+    }
+
+    @Override
+    public int getIntrinsicHeight() {
+        return getIntrinsicWidth();
+    }
+
+    @Override
+    public void invalidateDrawable(@NonNull Drawable who) {
+        invalidateSelf();
+    }
+
+    @Override
+    public void scheduleDrawable(@NonNull Drawable who, @NonNull Runnable what, long when) {
+        scheduleSelf(what, when);
+    }
+
+    @Override
+    public void unscheduleDrawable(@NonNull Drawable who, @NonNull Runnable what) {
+        unscheduleSelf(what);
+    }
+}
diff --git a/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java b/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java
index ff70190..bcbc6ac 100644
--- a/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java
+++ b/packages/SettingsLib/src/com/android/settingslib/drawer/SettingsDrawerActivity.java
@@ -216,6 +216,8 @@
         if (sDashboardCategories == null) {
             sTileCache = new HashMap<>();
             sConfigTracker = new InterestingConfigChanges();
+            // Apply initial current config.
+            sConfigTracker.applyNewConfig(getResources());
             sDashboardCategories = TileUtils.getCategories(this, sTileCache);
         }
         return sDashboardCategories;
diff --git a/packages/SettingsLib/src/com/android/settingslib/drawer/UserAdapter.java b/packages/SettingsLib/src/com/android/settingslib/drawer/UserAdapter.java
index f9fa805f..750601d 100644
--- a/packages/SettingsLib/src/com/android/settingslib/drawer/UserAdapter.java
+++ b/packages/SettingsLib/src/com/android/settingslib/drawer/UserAdapter.java
@@ -33,7 +33,7 @@
 import android.widget.SpinnerAdapter;
 import android.widget.TextView;
 import com.android.internal.util.UserIcons;
-import com.android.settingslib.drawable.CircleFramedDrawable;
+import com.android.settingslib.drawable.UserIconDrawable;
 
 import com.android.settingslib.R;
 
@@ -71,7 +71,8 @@
         }
 
         private static Drawable encircle(Context context, Drawable icon) {
-            return CircleFramedDrawable.getInstance(context, UserIcons.convertToBitmap(icon));
+            return new UserIconDrawable(UserIconDrawable.getSizeForList(context))
+                    .setIconDrawable(icon).bake();
         }
     }
     private ArrayList<UserDetails> data;
diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
index 61c9f2b..640399f 100644
--- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
+++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
@@ -1831,14 +1831,11 @@
         private void maybeNotifyProfiles(int userId, Uri uri, String name,
                 Set<String> keysCloned) {
             if (keysCloned.contains(name)) {
-                List<UserInfo> profiles = mUserManager.getProfiles(userId);
-                int size = profiles.size();
-                for (int i = 0; i < size; i++) {
-                    UserInfo profile = profiles.get(i);
+                for (int profileId : mUserManager.getProfileIdsWithDisabled(userId)) {
                     // the notification for userId has already been sent.
-                    if (profile.id != userId) {
+                    if (profileId != userId) {
                         mHandler.obtainMessage(MyHandler.MSG_NOTIFY_URI_CHANGED,
-                                profile.id, 0, uri).sendToTarget();
+                                profileId, 0, uri).sendToTarget();
                     }
                 }
             }
@@ -1942,7 +1939,7 @@
         }
 
         private final class UpgradeController {
-            private static final int SETTINGS_VERSION = 126;
+            private static final int SETTINGS_VERSION = 127;
 
             private final int mUserId;
 
@@ -2167,6 +2164,36 @@
                     currentVersion = 126;
                 }
 
+                if (currentVersion == 126) {
+                    // Version 126: copy the primary values of LOCK_SCREEN_SHOW_NOTIFICATIONS and
+                    // LOCK_SCREEN_ALLOW_PRIVATE_NOTIFICATIONS into managed profile.
+                    if (mUserManager.isManagedProfile(userId)) {
+                        final SettingsState systemSecureSettings =
+                                getSecureSettingsLocked(UserHandle.USER_SYSTEM);
+
+                        final Setting showNotifications = systemSecureSettings.getSettingLocked(
+                                Settings.Secure.LOCK_SCREEN_SHOW_NOTIFICATIONS);
+                        if (showNotifications != null) {
+                            final SettingsState secureSettings = getSecureSettingsLocked(userId);
+                            secureSettings.insertSettingLocked(
+                                    Settings.Secure.LOCK_SCREEN_SHOW_NOTIFICATIONS,
+                                    showNotifications.getValue(),
+                                    SettingsState.SYSTEM_PACKAGE_NAME);
+                        }
+
+                        final Setting allowPrivate = systemSecureSettings.getSettingLocked(
+                                Settings.Secure.LOCK_SCREEN_ALLOW_PRIVATE_NOTIFICATIONS);
+                        if (allowPrivate != null) {
+                            final SettingsState secureSettings = getSecureSettingsLocked(userId);
+                            secureSettings.insertSettingLocked(
+                                    Settings.Secure.LOCK_SCREEN_ALLOW_PRIVATE_NOTIFICATIONS,
+                                    allowPrivate.getValue(),
+                                    SettingsState.SYSTEM_PACKAGE_NAME);
+                        }
+                    }
+                    currentVersion = 127;
+                }
+
                 // vXXX: Add new settings above this point.
 
                 // Return the current version.
diff --git a/packages/Shell/src/com/android/shell/BugreportProgressService.java b/packages/Shell/src/com/android/shell/BugreportProgressService.java
index 7ca7614..796dff5 100644
--- a/packages/Shell/src/com/android/shell/BugreportProgressService.java
+++ b/packages/Shell/src/com/android/shell/BugreportProgressService.java
@@ -220,6 +220,7 @@
 
     @Override
     public int onStartCommand(Intent intent, int flags, int startId) {
+        Log.v(TAG, "onStartCommand(): " + dumpIntent(intent));
         if (intent != null) {
             // Handle it in a separate thread.
             final Message msg = mMainHandler.obtainMessage();
@@ -297,6 +298,7 @@
                 return;
             }
             final Parcelable parcel = ((Intent) msg.obj).getParcelableExtra(EXTRA_ORIGINAL_INTENT);
+            Log.v(TAG, "handleMessage(): " + dumpIntent((Intent) parcel));
             final Intent intent;
             if (parcel instanceof Intent) {
                 // The real intent was passed to BugreportReceiver, which delegated to the service.
@@ -707,7 +709,8 @@
             for (int i = 0; i < mProcesses.size(); i++) {
                 final BugreportInfo info = mProcesses.valueAt(i);
                 if (info.finished) {
-                    Log.d(TAG, "Not updating progress because share notification was already sent");
+                    Log.d(TAG, "Not updating progress for " + info.id + " while taking screenshot"
+                            + " because share notification was already sent");
                     continue;
                 }
                 updateProgress(info);
@@ -846,7 +849,15 @@
     private static Intent buildSendIntent(Context context, BugreportInfo info) {
         // Files are kept on private storage, so turn into Uris that we can
         // grant temporary permissions for.
-        final Uri bugreportUri = getUri(context, info.bugreportFile);
+        final Uri bugreportUri;
+        try {
+            bugreportUri = getUri(context, info.bugreportFile);
+        } catch (IllegalArgumentException e) {
+            // Should not happen on production, but happens when a Shell is sideloaded and
+            // FileProvider cannot find a configured root for it.
+            Log.wtf(TAG, "Could not get URI for " + info.bugreportFile, e);
+            return null;
+        }
 
         final Intent intent = new Intent(Intent.ACTION_SEND_MULTIPLE);
         final String mimeType = "application/vnd.android.bugreport";
@@ -907,6 +918,12 @@
         addDetailsToZipFile(mContext, info);
 
         final Intent sendIntent = buildSendIntent(mContext, info);
+        if (sendIntent == null) {
+            Log.w(TAG, "Stopping progres on ID " + id + " because share intent could not be built");
+            stopProgress(id);
+            return;
+        }
+
         final Intent notifIntent;
 
         // Send through warning dialog by default
@@ -1165,6 +1182,52 @@
         }
     }
 
+    /**
+     * Dumps an intent, extracting the relevant extras.
+     */
+    static String dumpIntent(Intent intent) {
+        if (intent == null) {
+            return "NO INTENT";
+        }
+        String action = intent.getAction();
+        if (action == null) {
+            // Happens when BugreportReceiver calls startService...
+            action = "no action";
+        }
+        final StringBuilder buffer = new StringBuilder(action).append(" extras: ");
+        addExtra(buffer, intent, EXTRA_ID);
+        addExtra(buffer, intent, EXTRA_PID);
+        addExtra(buffer, intent, EXTRA_MAX);
+        addExtra(buffer, intent, EXTRA_NAME);
+        addExtra(buffer, intent, EXTRA_DESCRIPTION);
+        addExtra(buffer, intent, EXTRA_BUGREPORT);
+        addExtra(buffer, intent, EXTRA_SCREENSHOT);
+        addExtra(buffer, intent, EXTRA_INFO);
+
+        if (intent.hasExtra(EXTRA_ORIGINAL_INTENT)) {
+            buffer.append(SHORT_EXTRA_ORIGINAL_INTENT).append(": ");
+            final Intent originalIntent = intent.getParcelableExtra(EXTRA_ORIGINAL_INTENT);
+            buffer.append(dumpIntent(originalIntent));
+        } else {
+            buffer.append("no ").append(SHORT_EXTRA_ORIGINAL_INTENT);
+        }
+
+        return buffer.toString();
+    }
+
+    private static final String SHORT_EXTRA_ORIGINAL_INTENT =
+            EXTRA_ORIGINAL_INTENT.substring(EXTRA_ORIGINAL_INTENT.lastIndexOf('.') + 1);
+
+    private static void addExtra(StringBuilder buffer, Intent intent, String name) {
+        final String shortName = name.substring(name.lastIndexOf('.') + 1);
+        if (intent.hasExtra(name)) {
+            buffer.append(shortName).append('=').append(intent.getExtra(name));
+        } else {
+            buffer.append("no ").append(shortName);
+        }
+        buffer.append(", ");
+    }
+
     private static boolean setSystemProperty(String key, String value) {
         try {
             if (DEBUG) Log.v(TAG, "Setting system property " + key + " to " + value);
diff --git a/packages/Shell/src/com/android/shell/BugreportReceiver.java b/packages/Shell/src/com/android/shell/BugreportReceiver.java
index cbd17bf..f6e558f 100644
--- a/packages/Shell/src/com/android/shell/BugreportReceiver.java
+++ b/packages/Shell/src/com/android/shell/BugreportReceiver.java
@@ -20,6 +20,7 @@
 import static com.android.shell.BugreportProgressService.EXTRA_ORIGINAL_INTENT;
 import static com.android.shell.BugreportProgressService.INTENT_BUGREPORT_FINISHED;
 import static com.android.shell.BugreportProgressService.getFileExtra;
+import static com.android.shell.BugreportProgressService.dumpIntent;
 
 import java.io.File;
 
@@ -51,7 +52,7 @@
 
     @Override
     public void onReceive(Context context, Intent intent) {
-        Log.d(TAG, "onReceive: " + intent);
+        Log.d(TAG, "onReceive(): " + dumpIntent(intent));
         // Clean up older bugreports in background
         cleanupOldFiles(this, intent, INTENT_BUGREPORT_FINISHED, MIN_KEEP_COUNT, MIN_KEEP_AGE);
 
diff --git a/packages/Shell/tests/src/com/android/shell/BugreportReceiverTest.java b/packages/Shell/tests/src/com/android/shell/BugreportReceiverTest.java
index e1e0c3b..3b53055 100644
--- a/packages/Shell/tests/src/com/android/shell/BugreportReceiverTest.java
+++ b/packages/Shell/tests/src/com/android/shell/BugreportReceiverTest.java
@@ -179,42 +179,37 @@
         sendBugreportStarted(1000);
         waitForScreenshotButtonEnabled(true);
 
-        final NumberFormat nf = NumberFormat.getPercentInstance();
-        nf.setMinimumFractionDigits(2);
-        nf.setMaximumFractionDigits(2);
-
-        assertProgressNotification(NAME, nf.format(0));
+        assertProgressNotification(NAME, 0f);
 
         SystemProperties.set(PROGRESS_PROPERTY, "108");
-        assertProgressNotification(NAME, nf.format(0.108));
+        assertProgressNotification(NAME, 10.80f);
 
-        SystemProperties.set(PROGRESS_PROPERTY, "500");
-        assertProgressNotification(NAME, nf.format(0.50));
+        assertProgressNotification(NAME, 50.00f);
 
         SystemProperties.set(PROGRESS_PROPERTY, "950");
-        assertProgressNotification(NAME, nf.format(0.95));
+        assertProgressNotification(NAME, 95.00f);
 
         // Make sure progress never goes back...
         SystemProperties.set(MAX_PROPERTY, "2000");
         Thread.sleep(POLLING_FREQUENCY + DateUtils.SECOND_IN_MILLIS);
-        assertProgressNotification(NAME, nf.format(0.95));
+        assertProgressNotification(NAME, 95.00f);
 
         SystemProperties.set(PROGRESS_PROPERTY, "1000");
-        assertProgressNotification(NAME, nf.format(0.95));
+        assertProgressNotification(NAME, 95.00f);
 
         // ...only forward...
         SystemProperties.set(PROGRESS_PROPERTY, "1902");
-        assertProgressNotification(NAME, nf.format(0.9510));
+        assertProgressNotification(NAME, 95.10f);
 
         SystemProperties.set(PROGRESS_PROPERTY, "1960");
-        assertProgressNotification(NAME, nf.format(0.98));
+        assertProgressNotification(NAME, 98.00f);
 
         // ...but never more than the capped value.
         SystemProperties.set(PROGRESS_PROPERTY, "2000");
-        assertProgressNotification(NAME, nf.format(0.99));
+        assertProgressNotification(NAME, 99.00f);
 
         SystemProperties.set(PROGRESS_PROPERTY, "3000");
-        assertProgressNotification(NAME, nf.format(0.99));
+        assertProgressNotification(NAME, 99.00f);
 
         Bundle extras =
                 sendBugreportFinishedAndGetSharedIntent(ID, mPlainTextPath, mScreenshotPath);
@@ -233,7 +228,7 @@
         nf.setMinimumFractionDigits(2);
         nf.setMaximumFractionDigits(2);
 
-        assertProgressNotification(NAME, nf.format(0));
+        assertProgressNotification(NAME, 00.00f);
 
         openProgressNotification(ID);
         UiObject cancelButton = mUiBot.getVisibleObject(mContext.getString(
@@ -338,7 +333,7 @@
         detailsUi.clickOk();
 
         assertPropertyValue(NAME_PROPERTY, NEW_NAME);
-        assertProgressNotification(NEW_NAME, "0.00%");
+        assertProgressNotification(NEW_NAME, 00.00f);
 
         Bundle extras = sendBugreportFinishedAndGetSharedIntent(ID, mPlainTextPath,
                 mScreenshotPath);
@@ -375,7 +370,7 @@
         detailsUi.clickOk();
 
         assertPropertyValue(NAME_PROPERTY, NEW_NAME);
-        assertProgressNotification(NEW_NAME, "0.00%");
+        assertProgressNotification(NEW_NAME, 00.00f);
 
         Bundle extras = sendBugreportFinishedAndGetSharedIntent(ID,
                 plainText? mPlainTextPath : mZipPath, mScreenshotPath);
@@ -571,13 +566,13 @@
         }
     }
 
-    private void assertProgressNotification(String name, String percent) {
+    private void assertProgressNotification(String name, float percent) {
         // TODO: it currently looks for 3 distinct objects, without taking advantage of their
         // relationship.
         openProgressNotification(ID);
         Log.v(TAG, "Looking for progress notification details: '" + name + "-" + percent + "'");
         mUiBot.getObject(name);
-        mUiBot.getObject(percent);
+        // TODO: need a way to get the ProgresBar from the "android:id/progress" UIObject...
     }
 
     private UiObject openProgressNotification(int id) {
diff --git a/packages/SystemUI/AndroidManifest.xml b/packages/SystemUI/AndroidManifest.xml
index 9e2442c..c248adf 100644
--- a/packages/SystemUI/AndroidManifest.xml
+++ b/packages/SystemUI/AndroidManifest.xml
@@ -159,6 +159,9 @@
     <!-- DND access -->
     <uses-permission android:name="android.permission.MANAGE_NOTIFICATIONS" />
 
+    <!-- It's like, reality, but, you know, virtual -->
+    <uses-permission android:name="android.permission.ACCESS_VR_MANAGER" />
+
     <application
         android:name=".SystemUIApplication"
         android:persistent="true"
@@ -235,6 +238,19 @@
                     android:value="com.android.settings.category.system" />
         </activity>
 
+        <activity-alias android:name=".DemoMode"
+                  android:targetActivity=".tuner.TunerActivity"
+                  android:icon="@drawable/tuner"
+                  android:theme="@style/TunerSettings"
+                  android:label="@string/demo_mode"
+                  android:process=":tuner"
+                  android:exported="true">
+            <intent-filter>
+                <action android:name="com.android.settings.action.DEMO_MODE" />
+                <category android:name="android.intent.category.DEFAULT" />
+            </intent-filter>
+        </activity-alias>
+
         <!-- Service used by secondary users to register themselves with the system user. -->
         <service android:name=".recents.RecentsSystemUserService"
             android:exported="false"
@@ -488,5 +504,12 @@
                 <action android:name="com.android.systemui.action.CLEAR_TUNER" />
             </intent-filter>
         </receiver>
+
+        <receiver
+            android:name=".statusbar.KeyboardShortcutsReceiver">
+            <intent-filter>
+                <action android:name="android.intent.action.SHOW_KEYBOARD_SHORTCUTS" />
+            </intent-filter>
+        </receiver>
     </application>
 </manifest>
diff --git a/packages/SystemUI/res/anim/tv_pip_overlay_fade_in_animation.xml b/packages/SystemUI/res/anim/tv_pip_overlay_fade_in_animation.xml
new file mode 100644
index 0000000..33bceaa
--- /dev/null
+++ b/packages/SystemUI/res/anim/tv_pip_overlay_fade_in_animation.xml
@@ -0,0 +1,21 @@
+<?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.
+-->
+
+<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
+    android:propertyName="alpha"
+    android:valueTo="1"
+    android:interpolator="@android:interpolator/fast_out_slow_in"
+    android:duration="350" />
diff --git a/packages/SystemUI/res/anim/tv_pip_overlay_fade_out_animation.xml b/packages/SystemUI/res/anim/tv_pip_overlay_fade_out_animation.xml
new file mode 100644
index 0000000..a12ddff
--- /dev/null
+++ b/packages/SystemUI/res/anim/tv_pip_overlay_fade_out_animation.xml
@@ -0,0 +1,21 @@
+<?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.
+-->
+
+<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
+    android:propertyName="alpha"
+    android:valueTo="0"
+    android:interpolator="@android:interpolator/fast_out_slow_in"
+    android:duration="500" />
diff --git a/packages/SystemUI/res/color/qs_user_detail_avatar_frame.xml b/packages/SystemUI/res/color/qs_user_detail_avatar_frame.xml
new file mode 100644
index 0000000..20251c2
--- /dev/null
+++ b/packages/SystemUI/res/color/qs_user_detail_avatar_frame.xml
@@ -0,0 +1,22 @@
+<?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
+  -->
+
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:state_activated="true" android:color="@color/current_user_border_color" />
+    <item android:color="@android:color/transparent" />
+</selector>
\ No newline at end of file
diff --git a/packages/SystemUI/res/color/qs_user_detail_avatar_tint.xml b/packages/SystemUI/res/color/qs_user_detail_avatar_tint.xml
new file mode 100644
index 0000000..2b75c36
--- /dev/null
+++ b/packages/SystemUI/res/color/qs_user_detail_avatar_tint.xml
@@ -0,0 +1,22 @@
+<?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
+  -->
+
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:state_enabled="false" android:color="@color/qs_tile_disabled_color" />
+    <item android:color="@android:color/transparent" />
+</selector>
\ No newline at end of file
diff --git a/packages/SystemUI/res/drawable/ksh_key_item_background.xml b/packages/SystemUI/res/drawable/ksh_key_item_background.xml
new file mode 100644
index 0000000..75ff30d
--- /dev/null
+++ b/packages/SystemUI/res/drawable/ksh_key_item_background.xml
@@ -0,0 +1,21 @@
+<?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
+  -->
+<shape xmlns:android="http://schemas.android.com/apk/res/android"
+        android:shape="rectangle">
+    <solid android:color="@color/ksh_key_item_background" />
+    <corners android:radius="2dp" />
+</shape>
diff --git a/packages/SystemUI/res/drawable/recents_info_dark.xml b/packages/SystemUI/res/drawable/recents_info_dark.xml
index b1a2242..555a69a 100644
--- a/packages/SystemUI/res/drawable/recents_info_dark.xml
+++ b/packages/SystemUI/res/drawable/recents_info_dark.xml
@@ -14,8 +14,8 @@
     limitations under the License.
 -->
 <vector xmlns:android="http://schemas.android.com/apk/res/android"
-        android:width="48.0dp"
-        android:height="48.0dp"
+        android:width="24.0dp"
+        android:height="24.0dp"
         android:viewportWidth="24.0"
         android:viewportHeight="24.0">
     <path
diff --git a/packages/SystemUI/res/drawable/recents_info_light.xml b/packages/SystemUI/res/drawable/recents_info_light.xml
index bc58c3b..65e7bf5 100644
--- a/packages/SystemUI/res/drawable/recents_info_light.xml
+++ b/packages/SystemUI/res/drawable/recents_info_light.xml
@@ -14,8 +14,8 @@
     limitations under the License.
 -->
 <vector xmlns:android="http://schemas.android.com/apk/res/android"
-        android:width="48.0dp"
-        android:height="48.0dp"
+        android:width="24.0dp"
+        android:height="24.0dp"
         android:viewportWidth="24.0"
         android:viewportHeight="24.0">
     <path
diff --git a/packages/SystemUI/res/layout/battery_detail.xml b/packages/SystemUI/res/layout/battery_detail.xml
index 8e7feec94..1f24ab0 100644
--- a/packages/SystemUI/res/layout/battery_detail.xml
+++ b/packages/SystemUI/res/layout/battery_detail.xml
@@ -26,7 +26,7 @@
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
         android:paddingStart="72dp"
-        android:textAppearance="?android:attr/textAppearanceMedium"
+        android:textAppearance="?android:attr/textAppearanceSmall"
         android:textColor="?android:attr/colorAccent" />
 
     <com.android.systemui.ResizingSpace
diff --git a/packages/SystemUI/res/layout/forced_resizable_activity.xml b/packages/SystemUI/res/layout/forced_resizable_activity.xml
index df245bc..3c778c4 100644
--- a/packages/SystemUI/res/layout/forced_resizable_activity.xml
+++ b/packages/SystemUI/res/layout/forced_resizable_activity.xml
@@ -18,10 +18,9 @@
     android:layout_width="match_parent"
     android:layout_height="match_parent">
 
-    <TextView
+    <include
+        layout="@*android:layout/transient_notification"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
-        android:layout_gravity="center"
-        android:text="@string/forced_resizable_info_text"
-        android:textColor="#ffffff"/>
+        android:layout_gravity="center"/>
 </FrameLayout>
\ No newline at end of file
diff --git a/packages/SystemUI/res/layout/keyboard_shortcut_app_item.xml b/packages/SystemUI/res/layout/keyboard_shortcut_app_item.xml
index 9c2c0ab..63b759b 100644
--- a/packages/SystemUI/res/layout/keyboard_shortcut_app_item.xml
+++ b/packages/SystemUI/res/layout/keyboard_shortcut_app_item.xml
@@ -15,15 +15,25 @@
   ~ limitations under the License
   -->
 <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
-        android:id="@+id/keyboard_shortcuts_keyword_wrapper"
         android:orientation="horizontal"
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
+        android:minHeight="48dp"
         android:paddingStart="24dp"
         android:paddingEnd="24dp"
         android:paddingBottom="8dp">
+    <ImageView
+            android:id="@+id/keyboard_shortcuts_icon"
+            android:layout_width="24dp"
+            android:layout_height="24dp"
+            android:layout_marginEnd="32dp"
+            android:layout_gravity="center_vertical"
+            android:visibility="gone"
+            android:layout_alignParentStart="true"
+            android:layout_centerVertical="true"/>
     <TextView
             android:id="@+id/keyboard_shortcuts_keyword"
+            android:layout_toEndOf="@+id/keyboard_shortcuts_icon"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
             android:paddingEnd="12dp"
@@ -32,7 +42,8 @@
             android:maxLines="5"
             android:singleLine="false"
             android:scrollHorizontally="false"
-            android:layout_alignParentStart="true"/>
+            android:layout_alignParentStart="true"
+            android:layout_centerVertical="true"/>
     <com.android.systemui.statusbar.KeyboardShortcutKeysLayout
             android:id="@+id/keyboard_shortcuts_item_container"
             android:layout_toEndOf="@+id/keyboard_shortcuts_keyword"
@@ -41,5 +52,6 @@
             android:layout_height="wrap_content"
             android:layout_alignParentEnd="true"
             android:textSize="14sp"
-            android:scrollHorizontally="false"/>
+            android:scrollHorizontally="false"
+            android:layout_centerVertical="true"/>
 </RelativeLayout>
diff --git a/packages/SystemUI/res/layout/keyboard_shortcuts_key_icon_view.xml b/packages/SystemUI/res/layout/keyboard_shortcuts_key_icon_view.xml
index 0cecb96..5db6789 100644
--- a/packages/SystemUI/res/layout/keyboard_shortcuts_key_icon_view.xml
+++ b/packages/SystemUI/res/layout/keyboard_shortcuts_key_icon_view.xml
@@ -21,4 +21,4 @@
         android:padding="@dimen/ksh_item_padding"
         android:layout_marginStart="@dimen/ksh_item_margin_start"
         android:scaleType="fitXY"
-        android:background="@color/ksh_key_item_background"/>
+        android:background="@drawable/ksh_key_item_background"/>
diff --git a/packages/SystemUI/res/layout/keyboard_shortcuts_key_view.xml b/packages/SystemUI/res/layout/keyboard_shortcuts_key_view.xml
index 1215029..31a8773 100644
--- a/packages/SystemUI/res/layout/keyboard_shortcuts_key_view.xml
+++ b/packages/SystemUI/res/layout/keyboard_shortcuts_key_view.xml
@@ -19,7 +19,8 @@
           android:layout_height="wrap_content"
           android:padding="@dimen/ksh_item_padding"
           android:layout_marginStart="@dimen/ksh_item_margin_start"
-          android:background="@color/ksh_key_item_background"
+          android:background="@drawable/ksh_key_item_background"
           android:textColor="@color/ksh_key_item_color"
           android:singleLine="true"
+          android:gravity="center"
           android:textSize="@dimen/ksh_item_text_size"/>
diff --git a/packages/SystemUI/res/layout/keyguard_user_switcher_item.xml b/packages/SystemUI/res/layout/keyguard_user_switcher_item.xml
index c6e453a..d685528 100644
--- a/packages/SystemUI/res/layout/keyguard_user_switcher_item.xml
+++ b/packages/SystemUI/res/layout/keyguard_user_switcher_item.xml
@@ -33,14 +33,18 @@
     <TextView android:id="@+id/user_name"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
-            android:layout_marginEnd="16dp"
+            android:layout_marginEnd="13dp"
             android:textAppearance="@style/TextAppearance.StatusBar.Expanded.UserSwitcher.UserName"
             />
     <com.android.systemui.statusbar.phone.UserAvatarView android:id="@+id/user_picture"
-            android:layout_width="@dimen/max_avatar_size"
-            android:layout_height="@dimen/max_avatar_size"
+            android:layout_width="@dimen/framed_avatar_size"
+            android:layout_height="@dimen/framed_avatar_size"
             android:contentDescription="@null"
+            android:backgroundTint="@color/qs_user_detail_avatar_tint"
+            android:backgroundTintMode="src_atop"
             sysui:frameWidth="@dimen/keyguard_user_switcher_border_thickness"
-            sysui:framePadding="6dp"
-            sysui:activeFrameColor="@color/current_user_border_color" />
+            sysui:framePadding="2.5dp"
+            sysui:badgeDiameter="18dp"
+            sysui:badgeMargin="1dp"
+            sysui:frameColor="@color/qs_user_detail_avatar_frame" />
 </com.android.systemui.qs.tiles.UserDetailItemView>
diff --git a/packages/SystemUI/res/layout/qs_user_detail_item.xml b/packages/SystemUI/res/layout/qs_user_detail_item.xml
index 661d74a..58fc069 100644
--- a/packages/SystemUI/res/layout/qs_user_detail_item.xml
+++ b/packages/SystemUI/res/layout/qs_user_detail_item.xml
@@ -33,12 +33,16 @@
 
     <com.android.systemui.statusbar.phone.UserAvatarView
             android:id="@+id/user_picture"
-            android:layout_width="@dimen/max_avatar_size"
-            android:layout_height="@dimen/max_avatar_size"
-            android:layout_marginBottom="10dp"
+            android:layout_width="@dimen/framed_avatar_size"
+            android:layout_height="@dimen/framed_avatar_size"
+            android:layout_marginBottom="7dp"
+            android:backgroundTint="@color/qs_user_detail_avatar_tint"
+            android:backgroundTintMode="src_atop"
             systemui:frameWidth="2dp"
-            systemui:framePadding="6dp"
-            systemui:activeFrameColor="@color/current_user_border_color"/>
+            systemui:framePadding="2.5dp"
+            systemui:badgeDiameter="18dp"
+            systemui:badgeMargin="1dp"
+            systemui:frameColor="@color/qs_user_detail_avatar_frame"/>
 
     <LinearLayout
             android:layout_width="wrap_content"
diff --git a/packages/SystemUI/res/layout/quick_status_bar_expanded_header.xml b/packages/SystemUI/res/layout/quick_status_bar_expanded_header.xml
index b88846b..5d3b5ff 100644
--- a/packages/SystemUI/res/layout/quick_status_bar_expanded_header.xml
+++ b/packages/SystemUI/res/layout/quick_status_bar_expanded_header.xml
@@ -84,6 +84,7 @@
             android:clickable="true"
             android:focusable="true"
             android:background="?android:attr/selectableItemBackgroundBorderless"
+            android:contentDescription="@string/accessibility_quick_settings_expand"
             android:padding="12dp" />
 
     </LinearLayout>
diff --git a/packages/SystemUI/res/layout/recents.xml b/packages/SystemUI/res/layout/recents.xml
index 186aaf6..ae89631 100644
--- a/packages/SystemUI/res/layout/recents.xml
+++ b/packages/SystemUI/res/layout/recents.xml
@@ -25,6 +25,14 @@
         android:layout_height="match_parent">
     </com.android.systemui.recents.views.RecentsView>
 
+    <!-- Incompatible task overlay -->
+    <ViewStub android:id="@+id/incompatible_app_overlay_stub"
+        android:inflatedId="@+id/incompatible_app_overlay"
+        android:layout="@layout/recents_incompatible_app_overlay"
+        android:layout_width="match_parent"
+        android:layout_height="128dp"
+        android:layout_gravity="center_horizontal|top" />
+
     <!-- Nav Bar Scrim View -->
     <ImageView
         android:id="@+id/nav_bar_scrim"
diff --git a/packages/SystemUI/res/layout/recents_incompatible_app_overlay.xml b/packages/SystemUI/res/layout/recents_incompatible_app_overlay.xml
new file mode 100644
index 0000000..2b49dd3
--- /dev/null
+++ b/packages/SystemUI/res/layout/recents_incompatible_app_overlay.xml
@@ -0,0 +1,30 @@
+<?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.
+-->
+<FrameLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:alpha="0"
+    android:background="#88000000"
+    android:forceHasOverlappingRendering="false">
+    <TextView
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_gravity="center"
+        android:drawableTop="@drawable/recents_info_light"
+        android:drawablePadding="8dp"
+        android:text="@string/recents_incompatible_app_message" />
+</FrameLayout>
\ No newline at end of file
diff --git a/packages/SystemUI/res/layout/recents_task_view.xml b/packages/SystemUI/res/layout/recents_task_view.xml
index c813818..b1b2f1e 100644
--- a/packages/SystemUI/res/layout/recents_task_view.xml
+++ b/packages/SystemUI/res/layout/recents_task_view.xml
@@ -26,7 +26,9 @@
             android:id="@+id/task_view_thumbnail"
             android:layout_width="match_parent"
             android:layout_height="match_parent" />
+
         <include layout="@layout/recents_task_view_header" />
+
         <com.android.systemui.statusbar.AlphaOptimizedFrameLayout
             android:id="@+id/lock_to_app_fab"
             android:layout_width="@dimen/recents_lock_to_app_size"
@@ -45,6 +47,17 @@
                 android:layout_gravity="center"
                 android:src="@drawable/recents_lock_to_app_pin" />
         </com.android.systemui.statusbar.AlphaOptimizedFrameLayout>
+
+        <!-- The incompatible app toast -->
+        <ViewStub android:id="@+id/incompatible_app_toast_stub"
+                    android:inflatedId="@+id/incompatible_app_toast"
+                    android:layout="@*android:layout/transient_notification"
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:layout_gravity="top|center_horizontal"
+                    android:layout_marginTop="48dp"
+                    android:layout_marginLeft="16dp"
+                    android:layout_marginRight="16dp" />
     </FrameLayout>
 </com.android.systemui.recents.views.TaskView>
 
diff --git a/packages/SystemUI/res/layout/recents_task_view_header.xml b/packages/SystemUI/res/layout/recents_task_view_header.xml
index 2b3c5df..2df57bf 100644
--- a/packages/SystemUI/res/layout/recents_task_view_header.xml
+++ b/packages/SystemUI/res/layout/recents_task_view_header.xml
@@ -31,40 +31,19 @@
         android:paddingBottom="8dp"
         android:paddingStart="16dp"
         android:paddingEnd="12dp" />
-    <LinearLayout
-        android:id="@+id/title_container"
+    <TextView
+        android:id="@+id/title"
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
         android:layout_gravity="center_vertical|start"
-        android:orientation="vertical">
-        <TextView
-            android:id="@+id/title"
-            android:layout_width="match_parent"
-            android:layout_height="wrap_content"
-            android:layout_gravity="start"
-            android:textSize="16sp"
-            android:textColor="#ffffffff"
-            android:text="@string/recents_empty_message"
-            android:fontFamily="sans-serif-medium"
-            android:singleLine="true"
-            android:maxLines="1"
-            android:ellipsize="marquee"
-            android:fadingEdge="horizontal" />
-        <TextView
-            android:id="@+id/sub_title"
-            android:layout_width="match_parent"
-            android:layout_height="wrap_content"
-            android:layout_gravity="start"
-            android:textSize="11sp"
-            android:textColor="#ffffffff"
-            android:text="@string/recents_launch_non_dockable_task_label"
-            android:fontFamily="sans-serif-medium"
-            android:singleLine="true"
-            android:maxLines="1"
-            android:ellipsize="marquee"
-            android:fadingEdge="horizontal"
-            android:visibility="gone" />
-    </LinearLayout>
+        android:textSize="16sp"
+        android:textColor="#ffffffff"
+        android:text="@string/recents_empty_message"
+        android:fontFamily="sans-serif-medium"
+        android:singleLine="true"
+        android:maxLines="1"
+        android:ellipsize="marquee"
+        android:fadingEdge="horizontal" />
     <com.android.systemui.recents.views.FixedSizeImageView
         android:id="@+id/move_task"
         android:layout_width="wrap_content"
diff --git a/packages/SystemUI/res/layout/super_status_bar.xml b/packages/SystemUI/res/layout/super_status_bar.xml
index 3dca77d..7c4ce15 100644
--- a/packages/SystemUI/res/layout/super_status_bar.xml
+++ b/packages/SystemUI/res/layout/super_status_bar.xml
@@ -55,6 +55,7 @@
         android:layout_width="match_parent"
         android:layout_height="@dimen/heads_up_scrim_height"
         android:background="@drawable/heads_up_scrim"
+        sysui:ignoreRightInset="true"
         android:importantForAccessibility="no"/>
 
     <include layout="@layout/status_bar"
diff --git a/packages/SystemUI/res/values-af/strings.xml b/packages/SystemUI/res/values-af/strings.xml
index 3fa6245..8dff1c7 100644
--- a/packages/SystemUI/res/values-af/strings.xml
+++ b/packages/SystemUI/res/values-af/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Maak <xliff:g id="APP">%s</xliff:g> toe."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> verwerp."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Alle onlangse programme is toegemaak."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Maak <xliff:g id="APP">%s</xliff:g>-programinligting oop."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Begin tans <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Kennisgewing is toegemaak."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> is die volumedialoog"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Raak om die oorspronklike terug te stel."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Jy gebruik tans jou werkprofiel"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Stelsel-UI-ontvanger"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Wys persentasie van ingebedde battery"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Wys batteryvlakpersentasie binne die statusbalkikoon wanneer dit nie laai nie"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Skuif op"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Skuif links"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Skuif regs"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Program sal dalk nie met multivenster werk nie"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posisie <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dubbeltik om te wysig."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dubbeltik om by te voeg."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posisie <xliff:g id="POSITION">%1$d</xliff:g>. Dubbeltik om te kies."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is verwyder"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is na posisie <xliff:g id="POSITION">%2$d</xliff:g> geskuif"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Kitsinstellingswysiger."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Program sal dalk nie met verdeelde skerm werk nie."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Program steun nie verdeelde skerm nie."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-am/strings.xml b/packages/SystemUI/res/values-am/strings.xml
index eb5d256..7f6c6b2 100644
--- a/packages/SystemUI/res/values-am/strings.xml
+++ b/packages/SystemUI/res/values-am/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> አስወግድ።"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ተሰናብቷል::"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"ሁሉም የቅርብ ጊዜ ማመልከቻዎች ተሰናብተዋል።"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"የ<xliff:g id="APP">%s</xliff:g> መተግበሪያ መረጃውን ይክፈቱ።"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> በመጀመር ላይ።"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"ማሳወቂያ ተወግዷል።"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> የድምጽ መጠን መገናኛው ነው"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"የመጀመሪያውን ወደነበረበት ለመመለስ ይንኩ።"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"የስራ መገለጫዎን እየተጠቀሙ ነው"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"የስርዓት በይነገጽ መቃኛ"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"የተቀላቀለ የባትሪ አጠቃቀም መቶኛ አሳይ"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ኃይል በማይሞላበት ጊዜ በሁነታ አሞሌ አዶ ውስጥ የባትሪ ደረጃ መቶኛን አሳይ"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ወደ ላይ ሂድ"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ወደ ግራ ሂድ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ወደ ቀኝ ሂድ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"መተግበሪያ ከብዝሃ-መስኮት ጋር ላይሠራ ይችላል"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ቦታ <xliff:g id="POSITION">%1$d</xliff:g>፣ <xliff:g id="TILE_NAME">%2$s</xliff:g>። ለማርትዕ ሁለቴ መታ ያድርጉ።"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>። ለማከል ሁለቴ መታ ያድርጉ።"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ቦታ <xliff:g id="POSITION">%1$d</xliff:g>። ለመምረጥ ሁለቴ መታ ያድርጉ።"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ተወግዷል"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ወደ ቦታ <xliff:g id="POSITION">%2$d</xliff:g> ተወስዷል"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"የፈጣን ቅንብሮች አርታዒ።"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"መተግበሪያ ከተከፈለ ማያ ገጽ ጋር ላይሠራ ይችላል"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"መተግበሪያው የተከፈለ ማያ ገጽን አይደግፍም።"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ar/strings.xml b/packages/SystemUI/res/values-ar/strings.xml
index 82a772c..1b1d280 100644
--- a/packages/SystemUI/res/values-ar/strings.xml
+++ b/packages/SystemUI/res/values-ar/strings.xml
@@ -172,8 +172,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"إزالة <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"تمت إزالة <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"تم تجاهل كل التطبيقات المستخدمة مؤخرًا."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"فتح معلومات تطبيق <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"جارٍ بدء <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"تم تجاهل الإشعار."</string>
@@ -425,6 +424,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> هو مربع حوار مستوى الصوت"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"المس لاستعادة الإعداد الأصلي."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"أنت تستخدم ملفك الشخصي للعمل"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"أداة ضبط واجهة مستخدم النظام"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"عرض نسبة البطارية المدمجة"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"عرض نسبة مستوى البطارية داخل رمز شريط الحالة أثناء عدم الشحن"</string>
@@ -499,7 +504,7 @@
     <string name="night_mode_disclaimer" msgid="598914896926759578">"‏يتم تطبيق المظهر المعتم على المناطق الأساسية في نظام التشغيل Android والتي يتم عرضها عادة في مظهر مضيء، مثل الإعدادات."</string>
     <string name="color_apply" msgid="9212602012641034283">"تطبيق"</string>
     <string name="color_revert_title" msgid="4746666545480534663">"تأكيد الإعدادات"</string>
-    <string name="color_revert_message" msgid="9116001069397996691">"يمكن أن تتسبب بعض إعدادات الألوان في تعطيل إمكانية استخدام الجهاز. يمكنك النقر على \"موافق\" لتأكيد إعدادات الألوان هذه، وإلا فستتم إعادة تعيين هذه الإعدادات بعد 10 ثوانٍ."</string>
+    <string name="color_revert_message" msgid="9116001069397996691">"يمكن أن تتسبب بعض إعدادات الألوان في تعطيل إمكانية استخدام الجهاز. يمكنك النقر على \"موافق\" لتأكيد إعدادات الألوان هذه، وإلا فستتم إعادة تعيين هذه الإعدادات بعد ۱۰ ثوانٍ."</string>
     <string name="battery_panel_title" msgid="7944156115535366613">"استخدام البطارية"</string>
     <string name="battery_detail_charging_summary" msgid="1279095653533044008">"وضع توفير شحن البطارية غير متاح أثناء الشحن."</string>
     <string name="battery_detail_switch_title" msgid="6285872470260795421">"توفير شحن البطارية"</string>
@@ -600,7 +605,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"نقل لأعلى"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"نقل لليسار"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"نقل لليمين"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"يمكن ألا يعمل التطبيق مع وضع النوافذ المتعددة."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"الموضع <xliff:g id="POSITION">%1$d</xliff:g>، <xliff:g id="TILE_NAME">%2$s</xliff:g>. انقر نقرًا مزدوجًا للتعديل."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. انقر نقرًا مزدوجًا للإضافة."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"الموضع <xliff:g id="POSITION">%1$d</xliff:g>. انقر نقرًا مزدوجًا للتحديد."</string>
@@ -610,4 +614,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"تمت إزالة <xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"تم نقل <xliff:g id="TILE_NAME">%1$s</xliff:g> إلى الموضع <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"برنامج تعديل الإعدادات السريعة."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"يمكن ألا يعمل التطبيق مع وضع تقسيم الشاشة."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"التطبيق لا يتيح تقسيم الشاشة."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-az-rAZ/strings.xml b/packages/SystemUI/res/values-az-rAZ/strings.xml
index 59b3141..4fee4ec 100644
--- a/packages/SystemUI/res/values-az-rAZ/strings.xml
+++ b/packages/SystemUI/res/values-az-rAZ/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> kənarlaşdırın."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> çıxarıldı."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Bütün son tətbiqlər kənarlaşdırıldı."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> tətbiqi haqqında məlumatı açın."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> başlanır."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Bildiriş uzaqlaşdırıldı."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> proqramı səs səviyyəsi dialoqudur"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Orijinalı bərpa etmək üçün toxun."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"İş profilinizi istifadə edirsiniz"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Daxil batareya faizini göstərin"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Elektrik şəbəsinə qoşulu olmayan zaman batareya səviyyəsini status paneli ikonası daxilində göstərin"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Yuxarıya keçin"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Sola köçürün"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Sağa köçürün"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Tətbiq çoxsaylı pəncərə ilə işləməyə bilər."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g> mövqeyi, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Redaktə etmək üçün iki dəfə tıklayın."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Əlavə etmək üçün iki dəfə tıklayın."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g> mövqeyi. Seçmək üçün iki dəfə tıklayın."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> silindi"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g> mövqeyinə köçürüldü"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Sürətli ayarlar redaktoru."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Tətbiq bölünmüş ekran ilə işləməyə bilər."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Tətbiq ekran bölünməsini dəstəkləmir."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-b+sr+Latn/strings.xml b/packages/SystemUI/res/values-b+sr+Latn/strings.xml
index 0945885..4d22d2e 100644
--- a/packages/SystemUI/res/values-b+sr+Latn/strings.xml
+++ b/packages/SystemUI/res/values-b+sr+Latn/strings.xml
@@ -169,8 +169,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Odbacite <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Aplikacija <xliff:g id="APP">%s</xliff:g> je odbačena."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Sve nedavno korišćene aplikacije su odbačene."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Otvorite informacije o aplikaciji <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Pokrećemo <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Obaveštenje je odbačeno."</string>
@@ -422,6 +421,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> je dijalog za jačinu zvuka"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Dodirnite da biste vratili original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Koristite profil za Work"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Tjuner za korisnički interfejs sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Prikazuj ugrađeni procenat baterije"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Prikazivanje nivoa napunjenosti baterije u procentima unutar ikone na statusnoj traci kada se baterija ne puni"</string>
@@ -597,7 +602,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Pomeri nagore"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Pomeri ulevo"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Pomeri udesno"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikacija možda neće funkcionisati sa više prozora"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>. pozicija, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dvaput dodirnite da biste izmenili."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dvaput dodirnite da biste dodali."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g>. pozicija. Dvaput dodirnite da biste izabrali."</string>
@@ -607,4 +611,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Pločica <xliff:g id="TILE_NAME">%1$s</xliff:g> je uklonjena"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Pločica <xliff:g id="TILE_NAME">%1$s</xliff:g> je premeštena na <xliff:g id="POSITION">%2$d</xliff:g>. poziciju"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Uređivač za Brza podešavanja."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija možda neće funkcionisati sa podeljenim ekranom."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podržava podeljeni ekran."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-be-rBY/strings.xml b/packages/SystemUI/res/values-be-rBY/strings.xml
index 726a0e7..5f3aa55 100644
--- a/packages/SystemUI/res/values-be-rBY/strings.xml
+++ b/packages/SystemUI/res/values-be-rBY/strings.xml
@@ -172,8 +172,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Выдаліць <xliff:g id="APP">%s</xliff:g> са спіса апошніх."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> выдалены."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Усе апошнія праграмы адхілены."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Адкрыць інфармацыю пра праграму <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Запускаецца <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Апавяшчэнне прапушчана."</string>
@@ -425,6 +424,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> з\'яўляецца дыялогам гучнасці"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Націсніце, каб аднавіць арыгінал."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Вы выкарыстоўваеце свой працоўны профіль"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Наладка сістэмнага інтэрфейсу карыстальніка"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Паказваць працэнт зараду акумулятара"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Паказваць працэнт узроўню акумулятара ўнутры значка панэлі стану, калі ён не зараджаецца"</string>
@@ -535,7 +540,7 @@
     <string name="keyboard_shortcut_group_system_recents" msgid="3154851905021926744">"Апошнія"</string>
     <string name="keyboard_shortcut_group_system_back" msgid="2207004531216446378">"Назад"</string>
     <string name="keyboard_shortcut_group_system_notifications" msgid="8366964080041773224">"Апавяшчэнні"</string>
-    <string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"Спалучэнні клавіш для хуткага доступу"</string>
+    <string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"Спалучэнні клавіш"</string>
     <string name="keyboard_shortcut_group_system_switch_input" msgid="2334164096341310324">"Пераключэнне рэжыму ўводу"</string>
     <string name="keyboard_shortcut_group_applications" msgid="9129465955073449206">"Праграмы"</string>
     <string name="keyboard_shortcut_group_applications_assist" msgid="9095441910537146013">"Памочнік"</string>
@@ -600,7 +605,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Перамясціць уверх"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Перамясціць улева"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Перамясціць управа"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Праграма можа не працаваць у рэжыме некалькіх вокнаў"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Месца: <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Краніце двойчы, каб рэдагаваць."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Краніце двойчы, каб дадаць."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Месца: <xliff:g id="POSITION">%1$d</xliff:g>. Краніце двойчы, каб выбраць."</string>
@@ -610,4 +614,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Плітка <xliff:g id="TILE_NAME">%1$s</xliff:g> выдалена"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> перамешчана ў наступнае месца: <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Рэдактар хуткіх налад."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Праграма можа не працаваць у рэжыме дзялення экрана."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Праграма не падтрымлівае функцыю дзялення экрана."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-bg/strings.xml b/packages/SystemUI/res/values-bg/strings.xml
index 479087a..7aa52fe 100644
--- a/packages/SystemUI/res/values-bg/strings.xml
+++ b/packages/SystemUI/res/values-bg/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Отхвърляне на <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Приложението <xliff:g id="APP">%s</xliff:g> е отхвърлено."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Всички скорошни приложения са отхвърлени."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Отворете информацията за приложението <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> се стартира."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Известието е отхвърлено."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> изпълнява ролята на диалоговия прозорец за силата на звука"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Докоснете, за да възстановите оригинала."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Използвате служебния си потребителски профил"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Тунер на системния потребителски интерфейс"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Показване на процента на вградената батерия"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Показване на процента на нивото на батерията в иконата на лентата на състоянието, когато не се зарежда"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Преместване нагоре"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Преместване наляво"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Преместване надясно"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Приложението може да не работи в режим за няколко прозореца"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Позиция <xliff:g id="POSITION">%1$d</xliff:g>, „<xliff:g id="TILE_NAME">%2$s</xliff:g>“. Докоснете двукратно, за да редактирате."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"„<xliff:g id="TILE_NAME">%1$s</xliff:g>“. Докоснете двукратно, за да добавите."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Позиция <xliff:g id="POSITION">%1$d</xliff:g>. Докоснете двукратно, за да изберете."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Премахнахте „<xliff:g id="TILE_NAME">%1$s</xliff:g>“"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Преместихте „<xliff:g id="TILE_NAME">%1$s</xliff:g>“ на позиция <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Редактор за бързи настройки."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Приложението може да не работи в режим на разделен екран."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Приложението не поддържа разделен екран."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-bn-rBD/strings.xml b/packages/SystemUI/res/values-bn-rBD/strings.xml
index ccbcb6e..6bf0cae 100644
--- a/packages/SystemUI/res/values-bn-rBD/strings.xml
+++ b/packages/SystemUI/res/values-bn-rBD/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> খারিজ করুন।"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> খারিজ করা হয়েছে৷"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"সমস্ত সাম্প্রতিক অ্যাপ্লিকেশন খারিজ করা হয়েছে।"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> অ্যাপ্লিকেশানের তথ্য খুলবে৷"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> তারাঙ্কিত করা হচ্ছে।"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"বিজ্ঞপ্তি খারিজ করা হয়েছে৷"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> হল ভলিউম ডায়লগ"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"আসলটি পুনঃস্থাপন করতে স্পর্শ করুন৷"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"আপনি আপনার কাজের প্রোফাইল ব্যবহার করছেন"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"সিস্টেম UI টিউনার"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"এম্বেড করা ব্যাটারির শতকরা হার দেখায়"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"যখন চার্জ করা হবে না তখন স্থিতি দন্ডের আইকনের ভিতরে ব্যাটারি স্তরের শতকার হার দেখায়"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"উপরে সরান"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"বাঁয়ে সরান"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ডানে সরান"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"একাধিক-উইন্ডো দিয়ে অ্যাপ কাজ নাও করতে পারে"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g> অবস্থান, <xliff:g id="TILE_NAME">%2$s</xliff:g>৷ সম্পাদনা করতে দুবার আলতো চাপুন৷"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>৷ যোগ করতে দুবার আলতো চাপুন৷"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g> অবস্থান৷ নির্বাচন করতে দুবার আলতো চাপুন৷"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> মোছা হয়েছে"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g> এ সরানো হয়েছে"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"দ্রুত সেটিংস সম্পাদক৷"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"অ্যাপ্লিকেশানটি বিভক্ত স্ক্রীনে কাজ নাও করতে পারে৷"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"অ্যাপ্লিকেশান বিভক্ত-স্ক্রীন সমর্থন করে না৷"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-bs-rBA/strings.xml b/packages/SystemUI/res/values-bs-rBA/strings.xml
index c5398a2..3b438d6 100644
--- a/packages/SystemUI/res/values-bs-rBA/strings.xml
+++ b/packages/SystemUI/res/values-bs-rBA/strings.xml
@@ -169,8 +169,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Odbaci aplikaciju <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Aplikacija <xliff:g id="APP">%s</xliff:g> uklonjena."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Sve nedavno korištene aplikacije su odbačene."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Otvaranje informacija o aplikaciji <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Pokrećem aplikaciju <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Obavještenje je uklonjeno."</string>
@@ -422,6 +421,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> je dijaloški okvir za jačinu zvuka"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Dodirnite da vratite original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Koristite svoj profil za posao"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Podešavač za korisničko sučelje sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Prikaži ugrađeni postotak baterije"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Prikazuje postotak nivoa baterije unutar ikone na statusnoj traci kada se baterija ne puni"</string>
@@ -597,7 +602,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Pomjeri gore"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Pomjeri lijevo"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Pomjeri desno"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikacija možda neće raditi s višestrukim prozorom"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Pozicija <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dvaput dodirnite za uređivanje."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g> Dvaput dodirnite za dodavanje."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Pozicija <xliff:g id="POSITION">%1$d</xliff:g>. Dvaput dodirnite za odabir."</string>
@@ -607,4 +611,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> je uklonjen"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> je premješten na poziciju <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Uređivanje brzih postavki"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija možda neće raditi na podijeljenom ekranu"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podržava dijeljenje ekrana."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ca/strings.xml b/packages/SystemUI/res/values-ca/strings.xml
index b7fffb7..99cc5a9 100644
--- a/packages/SystemUI/res/values-ca/strings.xml
+++ b/packages/SystemUI/res/values-ca/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Ignora <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"S\'ha omès <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"S\'han descartat totes les aplicacions recents."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Obre la informació sobre l\'aplicació <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"S\'està iniciant <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificació omesa."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> és el diàleg de volum"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toca per restaurar l\'original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Estàs utilitzant el perfil professional"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Personalitzador d\'interfície d\'usuari"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostra el percentatge de la bateria inserit"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostra el percentatge del nivell de bateria dins de la icona de la barra d\'estat quan no s\'estigui carregant"</string>
@@ -539,7 +544,7 @@
     <string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"Contactes"</string>
     <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"Correu electrònic"</string>
     <string name="keyboard_shortcut_group_applications_im" msgid="1892749399083161405">"MI"</string>
-    <string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Music"</string>
+    <string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Música"</string>
     <string name="keyboard_shortcut_group_applications_youtube" msgid="6555453761294723317">"YouTube"</string>
     <string name="keyboard_shortcut_group_applications_calendar" msgid="9043614299194991263">"Calendari"</string>
     <string name="tuner_full_zen_title" msgid="4540823317772234308">"Mostra amb els controls de volum"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mou amunt"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mou a l\'esquerra"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mou a la dreta"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"És possible que l\'aplicació no funcioni amb el Mode multifinestra"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posició <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Fes doble toc per editar-la."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Fes doble toc per afegir-ho."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posició <xliff:g id="POSITION">%1$d</xliff:g>. Fes doble toc per seleccionar-la."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> s\'ha suprimit"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> s\'ha mogut a la posició <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de la configuració ràpida."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"És possible que l\'aplicació no funcioni amb la pantalla dividida."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"L\'aplicació no admet la pantalla dividida."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-cs/strings.xml b/packages/SystemUI/res/values-cs/strings.xml
index b707ece..3bc73f6 100644
--- a/packages/SystemUI/res/values-cs/strings.xml
+++ b/packages/SystemUI/res/values-cs/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Zavřít aplikaci <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Aplikace <xliff:g id="APP">%s</xliff:g> byla odebrána."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Všechny naposledy použité aplikace byly odstraněny."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Otevře informace o aplikaci <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Spouštění aplikace <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Oznámení je zavřeno."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> je dialog hlasitosti"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Klepnutím obnovíte originál."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Používáte pracovní profil"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Nástroj na ladění uživatelského rozhraní systému"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Zobrazovat vložené procento nabití baterie"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Když neprobíhá nabíjení, zobrazit v ikoně na stavovém řádku procento nabití baterie"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Přesunout nahoru"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Přesunout vlevo"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Přesunout vpravo"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikace nemusí v režimu několika oken fungovat."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Pozice <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dvojitým klepnutím ji upravíte."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dlaždici přidáte dvojitým klepnutím."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Pozice <xliff:g id="POSITION">%1$d</xliff:g>. Dvojitým klepnutím ji vyberete."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Dlaždice <xliff:g id="TILE_NAME">%1$s</xliff:g> byla odstraněna"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Dlaždice <xliff:g id="TILE_NAME">%1$s</xliff:g> byla přesunuta na pozici <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor rychlého nastavení"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikace v režimu rozdělené obrazovky nemusí fungovat."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikace nepodporuje režim rozdělené obrazovky."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-da/strings.xml b/packages/SystemUI/res/values-da/strings.xml
index 7a25141..3b47e24 100644
--- a/packages/SystemUI/res/values-da/strings.xml
+++ b/packages/SystemUI/res/values-da/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Afvis <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> er annulleret."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Alle de seneste applikationer er lukket."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Åbn appoplysningerne for <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> startes."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Underretningen er annulleret."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> er dialogboksen for lydstyrke"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Tryk for at gendanne originalen."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Du bruger din arbejdsprofil"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Vis procent for det indbyggede batteri"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Vis procenttallet for batteriniveauet i ikonet for statusbjælken, når der ikke oplades"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Flyt op"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Flyt til venstre"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Flyt til højre"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Appen fungerer muligvis ikke i Multivindue"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Tryk to gange for at redigere."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Tryk to gange for at tilføje."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Tryk to gange for at vælge."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> fjernes"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> blev flyttet til position <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Redigeringsværktøj for Hurtige indstillinger."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Appen fungerer muligvis ikke i delt skærm."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Appen understøtter ikke delt skærm."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-de/strings.xml b/packages/SystemUI/res/values-de/strings.xml
index e10eb64..436e7c4 100644
--- a/packages/SystemUI/res/values-de/strings.xml
+++ b/packages/SystemUI/res/values-de/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> beenden"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> entfernt"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Alle kürzlich verwendeten Apps wurden entfernt."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Infos zur App \"<xliff:g id="APP">%s</xliff:g>\" öffnen."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> wird gestartet."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Benachrichtigung geschlossen"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> regelt die Lautstärke."</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Zum Wiederherstellen des Originals hier tippen"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Du verwendest dein Arbeitsprofil."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Eingebettete Akku-Prozentzahl anzeigen"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Prozentzahl für Akkustand in Statusleistensymbol anzeigen, wenn das Gerät nicht geladen wird"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Nach oben verschieben"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Nach links verschieben"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Nach rechts verschieben"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"App funktioniert im Mehrfenstermodus möglicherweise nicht"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Zum Bearbeiten doppeltippen."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Zum Hinzufügen doppeltippen."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Zum Auswählen doppeltippen."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> wurde entfernt"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> an Position <xliff:g id="POSITION">%2$d</xliff:g> verschoben"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor für Schnelleinstellungen."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Die App funktioniert unter Umständen bei geteiltem Bildschirm nicht."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Das Teilen des Bildschirms wird in dieser App nicht unterstützt."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-el/strings.xml b/packages/SystemUI/res/values-el/strings.xml
index 5ec3133..8809cdf 100644
--- a/packages/SystemUI/res/values-el/strings.xml
+++ b/packages/SystemUI/res/values-el/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Παράβλεψη <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Απορρίφθηκαν <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Έγινε παράβλεψη όλων των πρόσφατων εφαρμογών."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Άνοιγμα πληροφοριών εφαρμογής <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Έναρξη <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Η ειδοποίηση έχει απορριφθεί."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"Η εφαρμογή <xliff:g id="APP_NAME">%1$s</xliff:g> αποτελεί το παράθυρο διαλόγου ελέγχου έντασης"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Αγγίξτε για επαναφορά αρχικού."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Χρησιμοποιείτε το προφίλ εργασίας σας"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Εμφάνιση ποσοστού ενσωματωμένης μπαταρίας"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Εμφάνιση ποσοστού επιπέδου μπαταρίας μέσα στο εικονίδιο της γραμμής κατάστασης όταν δεν γίνεται φόρτιση"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Μετακίνηση προς τα επάνω"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Μετακίνηση αριστερά"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Μετακίνηση δεξιά"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Η εφαρμογή ενδέχεται να μη λειτουργεί με τη λειτουργία πολλαπλών παραθύρων"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Θέση <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Πατήστε δύο φορές για επεξεργασία."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Πατήστε δύο φορές για προσθήκη."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Θέση <xliff:g id="POSITION">%1$d</xliff:g>. Πατήστε δύο φορές για επιλογή."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Το <xliff:g id="TILE_NAME">%1$s</xliff:g> καταργείται"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Το <xliff:g id="TILE_NAME">%1$s</xliff:g> μετακινήθηκε στη θέση <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Επεξεργασία γρήγορων ρυθμίσεων."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Δεν είναι δυνατή η λειτουργία της εφαρμογής με διαχωρισμό οθόνης."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Η εφαρμογή δεν υποστηρίζει διαχωρισμό οθόνης."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-en-rAU/strings.xml b/packages/SystemUI/res/values-en-rAU/strings.xml
index f08894f..218cbbd 100644
--- a/packages/SystemUI/res/values-en-rAU/strings.xml
+++ b/packages/SystemUI/res/values-en-rAU/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Dismiss <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> dismissed."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"All recent applications dismissed."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Open <xliff:g id="APP">%s</xliff:g> application info."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Starting <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notification dismissed."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> is the volume dialogue"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Touch to restore the original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"You\'re using your work profile"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Show embedded battery percentage"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Show battery level percentage inside the status bar icon when not charging"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Move up"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Move to the left"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Move to the right"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"App may not work with multi-window"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Double tap to edit."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Double tap to add."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Double tap to select."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is removed"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> moved to position <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Quick settings editor."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"App may not work with split-screen."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App does not support split-screen."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-en-rGB/strings.xml b/packages/SystemUI/res/values-en-rGB/strings.xml
index f08894f..218cbbd 100644
--- a/packages/SystemUI/res/values-en-rGB/strings.xml
+++ b/packages/SystemUI/res/values-en-rGB/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Dismiss <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> dismissed."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"All recent applications dismissed."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Open <xliff:g id="APP">%s</xliff:g> application info."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Starting <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notification dismissed."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> is the volume dialogue"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Touch to restore the original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"You\'re using your work profile"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Show embedded battery percentage"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Show battery level percentage inside the status bar icon when not charging"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Move up"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Move to the left"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Move to the right"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"App may not work with multi-window"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Double tap to edit."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Double tap to add."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Double tap to select."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is removed"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> moved to position <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Quick settings editor."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"App may not work with split-screen."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App does not support split-screen."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-en-rIN/strings.xml b/packages/SystemUI/res/values-en-rIN/strings.xml
index f08894f..218cbbd 100644
--- a/packages/SystemUI/res/values-en-rIN/strings.xml
+++ b/packages/SystemUI/res/values-en-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Dismiss <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> dismissed."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"All recent applications dismissed."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Open <xliff:g id="APP">%s</xliff:g> application info."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Starting <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notification dismissed."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> is the volume dialogue"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Touch to restore the original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"You\'re using your work profile"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Show embedded battery percentage"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Show battery level percentage inside the status bar icon when not charging"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Move up"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Move to the left"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Move to the right"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"App may not work with multi-window"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Double tap to edit."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Double tap to add."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Double tap to select."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is removed"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> moved to position <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Quick settings editor."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"App may not work with split-screen."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App does not support split-screen."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-es-rUS/strings.xml b/packages/SystemUI/res/values-es-rUS/strings.xml
index b5a10e1..c612431 100644
--- a/packages/SystemUI/res/values-es-rUS/strings.xml
+++ b/packages/SystemUI/res/values-es-rUS/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Rechazar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> descartada."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Se descartaron todas las aplicaciones recientes."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Abre la información de la aplicación de <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Iniciando <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificación ignorada"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> es el cuadro de diálogo de volumen."</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toca para restaurar el original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Estás usando tu perfil de trabajo"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sintonizador de IU del sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostrar porcentaje de la batería integrada"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostrar porcentaje del nivel de batería en el ícono de la barra de estado cuando no se está cargando"</string>
@@ -538,7 +543,7 @@
     <string name="keyboard_shortcut_group_applications_browser" msgid="6465985474000766533">"Navegador"</string>
     <string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"Contactos"</string>
     <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"Correo electrónico"</string>
-    <string name="keyboard_shortcut_group_applications_im" msgid="1892749399083161405">"MI"</string>
+    <string name="keyboard_shortcut_group_applications_im" msgid="1892749399083161405">"IM"</string>
     <string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Música"</string>
     <string name="keyboard_shortcut_group_applications_youtube" msgid="6555453761294723317">"YouTube"</string>
     <string name="keyboard_shortcut_group_applications_calendar" msgid="9043614299194991263">"Calendario"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mover hacia arriba"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mover a la izquierda"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mover a la derecha"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Es posible que la app no se ejecute con la función Multiventana"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posición <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Presiona dos veces para editarla."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Presiona dos veces para agregarlo."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posición <xliff:g id="POSITION">%1$d</xliff:g>. Presiona dos veces para seleccionarla."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Se quitó <xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Se movió <xliff:g id="TILE_NAME">%1$s</xliff:g> a la posición <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de Configuración rápida"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Es posible que la app no funcione en el modo de pantalla dividida."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"La app no es compatible con la función de pantalla dividida."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-es/strings.xml b/packages/SystemUI/res/values-es/strings.xml
index d8affc9..c6ef4cc 100644
--- a/packages/SystemUI/res/values-es/strings.xml
+++ b/packages/SystemUI/res/values-es/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Ignorar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Se ha eliminado <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Se han ignorado todas las aplicaciones recientes."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Abre la información de la aplicación <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Iniciando <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificación ignorada"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> es el cuadro de diálogo de volumen"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toca para restaurar la versión original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Estás usando tu perfil de trabajo"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Configurador de IU del sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostrar porcentaje de batería insertado"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostrar el porcentaje del nivel de batería en el icono de la barra de estado cuando no se esté cargando"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Subir"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mover a la izquierda"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mover a la derecha"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Es posible que la aplicación no funcione con el modo multiventana"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posición <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Toca dos veces para cambiarla."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Toca dos veces para añadirlo."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posición <xliff:g id="POSITION">%1$d</xliff:g>. Toca dos veces para seleccionarla."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> se ha quitado"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> se ha movido a la posición <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de ajustes rápidos."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Es posible que la aplicación no funcione con la pantalla dividida."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"La aplicación no admite la pantalla dividida."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-et-rEE/strings.xml b/packages/SystemUI/res/values-et-rEE/strings.xml
index f18bf05..664748b 100644
--- a/packages/SystemUI/res/values-et-rEE/strings.xml
+++ b/packages/SystemUI/res/values-et-rEE/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Rakendusest <xliff:g id="APP">%s</xliff:g> loobumine."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Loobusite rakendusest <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Kõikidest hiljutistest rakendustest on loobutud"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Rakenduse <xliff:g id="APP">%s</xliff:g> teabe avamine."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Rakenduse <xliff:g id="APP">%s</xliff:g> käivitamine."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g>, <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Märguandest on loobutud."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> on helitugevuse dialoog"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Originaali taastamiseks puudutage."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Kasutate oma tööprofiili"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Süsteemi kasutajaliidese tuuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Kuva lisatud akutaseme protsent"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Akutaseme protsendi kuvamine olekuriba ikoonil, kui akut ei laeta"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Liigu üles"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Liigu vasakule"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Liigu paremale"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Rakendus ei pruugi mitme akna režiimis töötada"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Asend <xliff:g id="POSITION">%1$d</xliff:g>, paan <xliff:g id="TILE_NAME">%2$s</xliff:g>. Topeltpuudutage muutmiseks."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Topeltpuudutage lisamiseks."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Asend <xliff:g id="POSITION">%1$d</xliff:g>. Topeltpuudutage valimiseks."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Paan <xliff:g id="TILE_NAME">%1$s</xliff:g> eemaldati"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Paan <xliff:g id="TILE_NAME">%1$s</xliff:g> teisaldati asendisse <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Kiirseadete redigeerija."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Rakendus ei pruugi poolitatud ekraaniga töötada."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Rakendus ei toeta jagatud ekraani."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-eu-rES/strings.xml b/packages/SystemUI/res/values-eu-rES/strings.xml
index 575f8749..287f73f 100644
--- a/packages/SystemUI/res/values-eu-rES/strings.xml
+++ b/packages/SystemUI/res/values-eu-rES/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Baztertu <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> baztertu da."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Azken aplikazio guztiak baztertu da."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Ireki <xliff:g id="APP">%s</xliff:g> aplikazioari buruzko informazioa."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> hasten."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Jakinarazpena baztertu da."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> da bolumenaren leihoa"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Ukitu jatorrizkora leheneratzeko"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Work profila erabiltzen ari zara"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sistemako erabiltzaile-interfazearen konfiguratzailea"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Erakutsi txertatutako bateriaren ehunekoa"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Erakutsi bateria-mailaren ehunekoa egoera-barraren ikonoan, kargatzen ari ez denean"</string>
@@ -537,11 +542,11 @@
     <string name="keyboard_shortcut_group_applications_assist" msgid="9095441910537146013">"Laguntzailea"</string>
     <string name="keyboard_shortcut_group_applications_browser" msgid="6465985474000766533">"Arakatzailea"</string>
     <string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"Kontaktuak"</string>
-    <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"Helbide elektronikoa"</string>
+    <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"Posta"</string>
     <string name="keyboard_shortcut_group_applications_im" msgid="1892749399083161405">"Istanteko mezularitza"</string>
     <string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Musika"</string>
     <string name="keyboard_shortcut_group_applications_youtube" msgid="6555453761294723317">"YouTube"</string>
-    <string name="keyboard_shortcut_group_applications_calendar" msgid="9043614299194991263">"Egutegia"</string>
+    <string name="keyboard_shortcut_group_applications_calendar" msgid="9043614299194991263">"Calendar"</string>
     <string name="tuner_full_zen_title" msgid="4540823317772234308">"Erakutsi bolumena kontrolatzeko aukerekin"</string>
     <string name="volume_and_do_not_disturb" msgid="3373784330208603030">"Ez molestatu"</string>
     <string name="volume_dnd_silent" msgid="4363882330723050727">"Bolumen-botoietarako lasterbidea"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Eraman gora"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Eraman ezkerrera"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Eraman eskuinera"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Baliteke aplikazioak ez funtzionatzea leiho anitzetan."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>. posizioa, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Editatzeko, sakatu birritan."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Gehitzeko, sakatu birritan."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g>. posizioa. Hautatzeko, sakatu birritan."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Kendu da <xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g>. posiziora eraman da"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Ezarpen bizkorren editorea."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Baliteke aplikazioak ez funtzionatzea pantaila zatituan."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikazioak ez du onartzen pantaila zatitua"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-fa/strings.xml b/packages/SystemUI/res/values-fa/strings.xml
index 322197e..5020bd8 100644
--- a/packages/SystemUI/res/values-fa/strings.xml
+++ b/packages/SystemUI/res/values-fa/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"رد کردن <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> نادیده گرفته شد."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"همه برنامه‌های اخیر رد شدند."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"باز کردن اطلاعات برنامه <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> در حال شروع به کار است."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"اعلان ردشد."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> کنترل‌کننده صدا است"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"برای بازیابی کنترل‌کننده اصلی، لمس کنید."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"درحال استفاده از نمایه کاری‌تان هستید"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"تنظیم‌کننده واسط کاربری سیستم"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"نمایش درصد شارژ باتری جاسازی شده"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"نمایش درصد سطح باتری در نماد نوار وضعیت، هنگامی که باتری شارژ نمی‌شود"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"انتقال به بالا"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"انتقال به چپ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"انتقال به راست"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"برنامه ممکن است با چندپنجره کار نکند"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"موقعیت <xliff:g id="POSITION">%1$d</xliff:g>، <xliff:g id="TILE_NAME">%2$s</xliff:g>. برای ویرایش دو ضربه سریع بزنید."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. برای افزودن دو ضربه سریع بزنید."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"موقعیت <xliff:g id="POSITION">%1$d</xliff:g>. برای انتخاب دو ضربه سریع بزنید."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> حذف می‌شود"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> به موقعیت <xliff:g id="POSITION">%2$d</xliff:g> منتقل شد"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ویرایشگر تنظیمات سریع."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"ممکن است برنامه با تقسیم صفحه کار نکند."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"برنامه از تقسیم صفحه پشتیبانی نمی‌کند."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-fi/strings.xml b/packages/SystemUI/res/values-fi/strings.xml
index 6db0a3e..dca5b12 100644
--- a/packages/SystemUI/res/values-fi/strings.xml
+++ b/packages/SystemUI/res/values-fi/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Hylätään <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> hylättiin."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Kaikki viimeisimmät sovellukset on hylätty."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Avaa sovelluksen <xliff:g id="APP">%s</xliff:g> tiedot."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Käynnistetään <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Ilmoitus hylätty."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> on äänenvoimakkuusvalinta."</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Palauta alkuperäinen koskettamalla."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Käytät työprofiilia."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Näytä akun varaus kuvakkeessa"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Näyttää akun varausprosentin tilapalkin kuvakkeessa, kun laitetta ei ladata."</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Siirrä ylöspäin"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Siirrä vasemmalle"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Siirrä oikealle"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Sovellus ei ehkä toimi usean ikkunan tilassa."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Paikka <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Muokkaa kaksoisnapauttamalla."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Lisää kaksoisnapauttamalla."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Paikka <xliff:g id="POSITION">%1$d</xliff:g>. Valitse kaksoisnapauttamalla."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> poistettiin."</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> siirrettiin paikkaan <xliff:g id="POSITION">%2$d</xliff:g>."</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Pika-asetusten muokkausnäkymä"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Sovellus ei ehkä toimi jaetulla näytöllä."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Sovellus ei tue jaetun näytön tilaa."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-fr-rCA/strings.xml b/packages/SystemUI/res/values-fr-rCA/strings.xml
index 89c6826..76a3438 100644
--- a/packages/SystemUI/res/values-fr-rCA/strings.xml
+++ b/packages/SystemUI/res/values-fr-rCA/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Supprimer <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Application \"<xliff:g id="APP">%s</xliff:g>\" ignorée."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Toutes les applications récentes ont été supprimées."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Ouvre les détails de l\'application <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Lancement de <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notification masquée"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> correspond à la boîte de dialogue du volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Touchez pour restaurer l\'original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Vous utilisez votre profil professionnel."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Afficher le pourcentage intégré de charge"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Afficher le pourcentage correspondant au niveau de la pile dans l\'icône de la barre d\'état lorsque l\'appareil n\'est pas en charge."</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Déplacer vers le haut"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Déplacer vers la gauche"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Déplacer vers la droite"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Il est possible que l\'application ne fonctionne pas en mode Multi-fenêtre."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Touchez deux fois pour modifier."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Touchez deux fois pour ajouter."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position : <xliff:g id="POSITION">%1$d</xliff:g>. Touchez deux fois pour sélectionner."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> a été supprimé"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> a été déplacé à la position <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Éditeur de paramètres rapides."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Il est possible que l\'application ne fonctionne pas en mode Écran partagé."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"L\'application n\'est pas compatible avec l\'écran partagé."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-fr/strings.xml b/packages/SystemUI/res/values-fr/strings.xml
index 2f99b94..d1ba9e3 100644
--- a/packages/SystemUI/res/values-fr/strings.xml
+++ b/packages/SystemUI/res/values-fr/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Supprimer <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Application \"<xliff:g id="APP">%s</xliff:g>\" ignorée."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Toutes les applications récentes ont été supprimées."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Ouvre les informations sur l\'application <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Lancement de <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> : <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notification masquée"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> correspond à la boîte de dialogue du volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Appuyez pour restaurer l\'interface d\'origine."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Vous utilisez votre profil professionnel."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Afficher le pourcentage intégré de la batterie"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Affichez le pourcentage correspondant au niveau de la batterie dans l\'icône de la barre d\'état lorsque l\'appareil n\'est pas en charge."</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Déplacer vers le haut"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Déplacer vers la gauche"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Déplacer vers la droite"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Il est possible que l\'application ne fonctionne pas en mode multifenêtre."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, \"<xliff:g id="TILE_NAME">%2$s</xliff:g>\". Appuyer deux fois pour modifier."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Appuyer deux fois pour ajouter."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Appuyer deux fois pour sélectionner."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Le bloc \"<xliff:g id="TILE_NAME">%1$s</xliff:g>\" a bien été supprimé."</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Le bloc \"<xliff:g id="TILE_NAME">%1$s</xliff:g>\" a bien été déplacé à la position <xliff:g id="POSITION">%2$d</xliff:g>."</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Éditeur de configuration rapide."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Il est possible que l\'application ne fonctionne pas en mode Écran partagé."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Application incompatible avec l\'écran partagé."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-gl-rES/strings.xml b/packages/SystemUI/res/values-gl-rES/strings.xml
index 45c3626..0f6bedc 100644
--- a/packages/SystemUI/res/values-gl-rES/strings.xml
+++ b/packages/SystemUI/res/values-gl-rES/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Rexeitar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Rexeitouse <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Rexeitáronse todas as aplicacións recentes."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Abre a información da aplicación <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Iniciando <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificación rexeitada"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> é o cadro de diálogo de volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toca para restaurar o orixinal."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Estás usando o perfil de traballo"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Configurador da IU do sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostrar porcentaxe de batería inserida"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostrar porcentaxe do nivel de batería na icona da barra de estado cando non está en carga"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Subir"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mover á esquerda"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mover á dereita"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Pode que a aplicación non funcione con varias ventás."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posición <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Toca dúas veces o elemento para editalo."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Toca dúas veces o elemento para engadilo"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posición <xliff:g id="POSITION">%1$d</xliff:g>. Toca dúas veces o elemento para seleccionalo."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Eliminouse <xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> moveuse á posición <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de configuración rápida."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Pode que a aplicación non funcione coa pantalla dividida."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"A aplicación non é compatible coa función de pantalla dividida."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-gu-rIN/strings.xml b/packages/SystemUI/res/values-gu-rIN/strings.xml
index ef6a49c..f937362 100644
--- a/packages/SystemUI/res/values-gu-rIN/strings.xml
+++ b/packages/SystemUI/res/values-gu-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> કાઢી નાખો."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> કાઢી નાખી."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"તમામ તાજેતરની એપ્લિકેશનો કાઢી નાખી."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ઍપ્લિકેશન માહિતી ખોલો."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> પ્રારંભ કરી રહ્યું છે."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"સૂચના કાઢી નાખી."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> એ વૉલ્યૂમ સંવાદ છે"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"મૂળને પુનઃસ્થાપિત કરવા માટે ટચ કરો."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"તમે તમારી કાર્ય પ્રોફાઇલનો ઉપયોગ કરી રહ્યાં છો"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"સિસ્ટમ UI ટ્યૂનર"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"એમ્બેડ કરેલ બૅટરી ટકા બતાવો"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"જ્યારે ચાર્જ ન થઈ રહ્યું હોય ત્યારે સ્થિતિ બાર આયકનની અંદર બૅટરી સ્તર ટકા બતાવો"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ઉપર ખસેડો"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ડાબે ખસેડો"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"જમણે ખસેડો"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"બહુ-વિંડો સાથે અ‍ૅપ્લિકેશન કદાચ કામ ન કરે"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"સ્થિતિ <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. સંપાદિત કરવા માટે બે વાર ટૅપ કરો."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. ઉમેરવા માટે બે વાર ટૅપ કરો."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"સ્થિતિ <xliff:g id="POSITION">%1$d</xliff:g>. પસંદ કરવા માટે બે વાર ટૅપ કરો."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> દૂર કરવામાં આવ્યું છે"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ને <xliff:g id="POSITION">%2$d</xliff:g> સ્થિતિ પર ખસેડ્યું"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ઝડપી સેટિંગ્સ સંપાદક."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"વિભાજિત-સ્ક્રીન સાથે ઍપ્લિકેશન કદાચ કામ ન કરે."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ઍપ્લિકેશન સ્ક્રીન-વિભાજનનું સમર્થન કરતી નથી."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-hi/strings.xml b/packages/SystemUI/res/values-hi/strings.xml
index 1ba0caf..b30d7a6 100644
--- a/packages/SystemUI/res/values-hi/strings.xml
+++ b/packages/SystemUI/res/values-hi/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> को ख़ारिज करें."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> खा़रिज कर दिया गया."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"हाल ही के सभी ऐप्लिकेशन ख़ारिज कर दिए गए."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ऐप्लिकेशन जानकारी खोलें."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> प्रारंभ हो रहा है."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"नोटिफिकेशन खारिज की गई."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> वॉल्यूम संवाद है"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"मूल वॉल्यूम को फिर से लाने के लिए स्पर्श करें."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"आप अपनी कार्य प्रोफ़ाइल का उपयोग कर रहे हैं"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"सिस्टम UI ट्यूनर"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"एम्बेड किया गया बैटरी प्रतिशत दिखाएं"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"जब चार्ज नहीं किया जा रहा हो तब स्थिति बार आइकन में बैटरी स्तर का प्रतिशत दिखाएं"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ऊपर ले जाएं"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"बाएं ले जाएं"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"दाएं ले जाएं"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"हो सकता है कि ऐप्लिकेशन एकाधिक विंडो के साथ काम ना करे"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"स्थिति <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. संपादित करने के लिए डबल टैप करें."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. जोड़ने के लिए डबल टैप करें."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"स्थिति <xliff:g id="POSITION">%1$d</xliff:g>. चुनने के लिए डबल टैप करें."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> निकाल दिया गया है"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> को <xliff:g id="POSITION">%2$d</xliff:g> स्थिति में ले जाया गया"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"त्वरित सेटिंग संपादक."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"हो सकता है कि ऐप्लिकेशन विभाजित स्क्रीन के साथ काम ना करे."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ऐप विभाजित स्‍क्रीन का समर्थन नहीं करता है."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-hr/strings.xml b/packages/SystemUI/res/values-hr/strings.xml
index 81c6276..24e8f8d 100644
--- a/packages/SystemUI/res/values-hr/strings.xml
+++ b/packages/SystemUI/res/values-hr/strings.xml
@@ -169,8 +169,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Odbacivanje aplikacije <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Aplikacija <xliff:g id="APP">%s</xliff:g> odbačena je."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Odbačene su sve nedavne aplikacije."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Otvaranje informacija o aplikaciji <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Pokretanje aplikacije <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Obavijest je odbačena."</string>
@@ -422,6 +421,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> predstavlja dijaloški okvir za upravljanje glasnoćom"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Dodirnite da biste vratili izvorno."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Upotrebljavate radni profil"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Ugađanje korisničkog sučelja sustava"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Prikaži ugrađeni postotak baterije"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Prikazivanje postotka razine baterije na ikoni trake statusa kada se ne puni"</string>
@@ -597,7 +602,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Pomakni prema gore"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Pomakni ulijevo"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Pomakni udesno"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikacija možda neće funkcionirati uz više prozora"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Položaj <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dodirnite dvaput da biste uredili."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dodirnite dvaput da biste dodali."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Položaj <xliff:g id="POSITION">%1$d</xliff:g>. Dodirnite dvaput da biste odabrali."</string>
@@ -607,4 +611,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Pločica <xliff:g id="TILE_NAME">%1$s</xliff:g> uklonjena"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Pločica <xliff:g id="TILE_NAME">%1$s</xliff:g> premještena je na položaj <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Uređivač brzih postavki."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija možda neće funkcionirati s podijeljenim zaslonom."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podržava podijeljeni zaslon."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-hu/strings.xml b/packages/SystemUI/res/values-hu/strings.xml
index b7ac8a4..cf69932 100644
--- a/packages/SystemUI/res/values-hu/strings.xml
+++ b/packages/SystemUI/res/values-hu/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"A(z) <xliff:g id="APP">%s</xliff:g> elvetése."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> eltávolítva."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Az összes alkalmazás eltávolítva a nemrég használtak közül."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"A(z) <xliff:g id="APP">%s</xliff:g> alkalmazás adatainak megnyitása."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"A(z) <xliff:g id="APP">%s</xliff:g> indítása."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Értesítés elvetve."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"A(z) <xliff:g id="APP_NAME">%1$s</xliff:g> alkalmazás kezeli a hangerőt"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Érintse meg az eredeti érték visszaállításához."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"A munkaprofilt használja"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Kezelőfelület-hangoló"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"A beépített akkumulátor töltöttségi szintjének megjelenítése"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Az akkumulátor töltöttségi szintjének megjelenítése az állapotsori ikonban, amikor az eszköz nem töltődik"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mozgatás felfelé"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mozgatás balra"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mozgatás jobbra"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Lehet, hogy az alkalmazás nem működik többablakos nézetben"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>. pozíció: <xliff:g id="TILE_NAME">%2$s</xliff:g>. Koppintson duplán a szerkesztéshez."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Koppintson duplán a hozzáadáshoz."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g>. pozíció. Koppintson duplán a kiválasztáshoz."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"A(z) <xliff:g id="TILE_NAME">%1$s</xliff:g> eltávolítva"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"A(z) <xliff:g id="TILE_NAME">%1$s</xliff:g> áthelyezve a(z) <xliff:g id="POSITION">%2$d</xliff:g>. pozícióba"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Gyorsbeállítások szerkesztője"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Lehet, hogy az alkalmazás nem működik osztott képernyős nézetben."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Az alkalmazás nem támogatja az osztott képernyős nézetet."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-hy-rAM/strings.xml b/packages/SystemUI/res/values-hy-rAM/strings.xml
index 7e4e01a..d58b63e 100644
--- a/packages/SystemUI/res/values-hy-rAM/strings.xml
+++ b/packages/SystemUI/res/values-hy-rAM/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Անտեսել <xliff:g id="APP">%s</xliff:g>-ը:"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g>-ը անտեսված է:"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Բոլոր վերջին հավելվածները հեռացվել են ցուցակից:"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Բացել <xliff:g id="APP">%s</xliff:g> հավելվածի մասին տեղեկությունները"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Մեկնարկել <xliff:g id="APP">%s</xliff:g>-ը:"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Ծանուցումը անտեսվեց:"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g>-ը ձայնի ուժգնության երկխոսության հավելված է"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Դիպչեք՝ սկզբնօրինակը վերականգնելու համար:"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Դուք օգտագործում եք ձեր աշխատանքային պրոֆիլը"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Համակարգի ՕՄ-ի կարգավորիչ"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Ցուցադրել ներկառուցված մարտկոցի տոկոսայնությունը"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Ցուցադրել մարտկոցի լիցքավորման տոկոսայնությունը կարգավիճակի գոտու պատկերակի վրա, երբ այն չի լիցքավորվում"</string>
@@ -533,7 +538,7 @@
     <string name="keyboard_shortcut_group_system_notifications" msgid="8366964080041773224">"Ծանուցումներ"</string>
     <string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"Ստեղնային դյուրանցումներ"</string>
     <string name="keyboard_shortcut_group_system_switch_input" msgid="2334164096341310324">"Փոխարկել մուտքագրման եղանակը"</string>
-    <string name="keyboard_shortcut_group_applications" msgid="9129465955073449206">"Գործադիրներ"</string>
+    <string name="keyboard_shortcut_group_applications" msgid="9129465955073449206">"Հավելվածներ"</string>
     <string name="keyboard_shortcut_group_applications_assist" msgid="9095441910537146013">"Օգնություն"</string>
     <string name="keyboard_shortcut_group_applications_browser" msgid="6465985474000766533">"Դիտարկիչ"</string>
     <string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"Կոնտակտներ"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Տեղափոխել վերև"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Տեղափոխել ձախ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Տեղափոխել աջ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Հավելվածը չի կարող աշխատել բազմապատուհան ռեժիմում"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Դիրք <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>: Կրկնակի հպեք՝ փոխելու համար:"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>: Կրկնակի հպեք՝ ավելացնելու համար:"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Դիրք <xliff:g id="POSITION">%1$d</xliff:g>: Կրկնակի հպեք՝ ընտրելու համար:"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> սալիկը հեռացվել է"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> սալիկը տեղափոխվել է դեպի <xliff:g id="POSITION">%2$d</xliff:g> դիրք"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Արագ կարգավորումների խմբագրիչ:"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Հավելվածը չի կարող աշխատել տրոհված էկրանի ռեժիմում:"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Հավելվածը չի աջակցում էկրանի տրոհումը:"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-in/strings.xml b/packages/SystemUI/res/values-in/strings.xml
index 2b51426..cab43c1 100644
--- a/packages/SystemUI/res/values-in/strings.xml
+++ b/packages/SystemUI/res/values-in/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Menyingkirkan <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> disingkirkan."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Semua aplikasi terbaru telah ditutup."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Buka info aplikasi <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Memulai <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notifikasi disingkirkan."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> adalah dialog volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Sentuh untuk memulihkan aslinya."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Anda menggunakan profil kerja"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Penyetel Antarmuka Pengguna Sistem"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Tampilkan persentase baterai yang tersemat"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Tampilkan persentase tingkat baterai dalam ikon bilah status saat tidak mengisi daya"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Naikkan"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Pindahkan ke kiri"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Pindahkan ke kanan"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikasi mungkin tidak berfungsi dengan multi-jendela"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posisi <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Ketuk dua kali untuk mengedit."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Ketuk dua kali untuk menambahkan."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posisi <xliff:g id="POSITION">%1$d</xliff:g>. Ketuk dua kali untuk memilih."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> dihapus"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> dpindahkan ke posisi <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor setelan cepat."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikasi mungkin tidak berfungsi dengan layar terpisah."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App tidak mendukung layar terpisah."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-is-rIS/strings.xml b/packages/SystemUI/res/values-is-rIS/strings.xml
index 1dc37df..f67f4c1 100644
--- a/packages/SystemUI/res/values-is-rIS/strings.xml
+++ b/packages/SystemUI/res/values-is-rIS/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Hunsa <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> vísað frá."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Öll nýleg forrit fjarlægð."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Opna forritsupplýsingar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Ræsir <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Tilkynningu lokað."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> er hljóðstyrksvalmyndin"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Snertu til að færa í upprunalegt horf."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Þú ert að nota vinnusniðið"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Fínstillingar kerfisviðmóts"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Sýna innfellda rafhlöðustöðu"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Sýna rafhlöðustöðuna í stöðustikunni þegar tækið er ekki í hleðslu"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Færa upp"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Færa til vinstri"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Færa til hægri"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Hugsanlegt er að forritið virki ekki í mörgum gluggum"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Staða <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Ýttu tvisvar til að breyta."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Ýttu tvisvar til að bæta við."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Staða <xliff:g id="POSITION">%1$d</xliff:g>. Ýttu tvisvar til að velja."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> var fjarlægð"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> færð í stöðu <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Flýtistillingaritill."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Hugsanlega virkar forritið ekki ef skjánum er skipt upp."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Forritið styður ekki að skjánum sé skipt."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-it/strings.xml b/packages/SystemUI/res/values-it/strings.xml
index 4a8ba99..ea1bb00 100644
--- a/packages/SystemUI/res/values-it/strings.xml
+++ b/packages/SystemUI/res/values-it/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Elimina <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> eliminata."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Tutte le applicazioni recenti sono state rimosse."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Mostra informazioni sull\'applicazione <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Avvio di <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notifica eliminata."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> rappresenta la finestra di dialogo relativa al volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Tocca per ripristinare l\'originale."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Stai utilizzando il profilo di lavoro"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sintetizzatore interfaccia utente di sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostra percentuale batteria incorporata"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostra la percentuale di carica della batteria nell\'icona della barra di stato quando non è in carica"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Sposta su"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Sposta a sinistra"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Sposta a destra"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"L\'app potrebbe non funzionare con la modalità multi-finestra"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posizione <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Tocca due volte per modificare."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Tocca due volte per aggiungere."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posizione <xliff:g id="POSITION">%1$d</xliff:g>. Tocca due volte per selezionare."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Il riquadro <xliff:g id="TILE_NAME">%1$s</xliff:g> è stato rimosso"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Il riquadro <xliff:g id="TILE_NAME">%1$s</xliff:g> è stato spostato nella posizione <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor di impostazioni rapide."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"L\'app potrebbe non funzionare con lo schermo diviso."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"L\'app non supporta la modalità Schermo diviso."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-iw/strings.xml b/packages/SystemUI/res/values-iw/strings.xml
index d41d50d..88bfafc 100644
--- a/packages/SystemUI/res/values-iw/strings.xml
+++ b/packages/SystemUI/res/values-iw/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"סגור את <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> נדחה."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"כל האפליקציות האחרונות נסגרו."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"פתח מידע על האפליקציה <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"מפעיל את <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"הודעה נדחתה."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> הוא תיבת הדו-שיח של עוצמת הקול"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"גע כדי לשחזר את עוצמת הקול המקורית."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"אתה משתמש בפרופיל העבודה שלך"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"הצג בשורת הסטטוס את אחוז עוצמת הסוללה"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"הצג את אחוז עוצמת הסוללה בתוך הסמל שבשורת הסטטוס כשהמכשיר אינו בטעינה"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"הזז למעלה"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"הזז שמאלה"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"הזז ימינה"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"ייתכן שהאפליקציה לא תפעל עם ריבוי חלונות"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"מיקום <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. הקש פעמיים כדי לערוך."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. הקש פעמיים כדי להוסיף."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"מיקום <xliff:g id="POSITION">%1$d</xliff:g>. הקש פעמיים כדי לבחור."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> הוסר"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> הועבר למיקום <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"עורך הגדרות מהירות."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"ייתכן שהיישום לא יפעל עם מסך מפוצל."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"האפליקציה אינה תומכת במסך מפוצל."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ja/strings.xml b/packages/SystemUI/res/values-ja/strings.xml
index 83a9888..04a392c 100644
--- a/packages/SystemUI/res/values-ja/strings.xml
+++ b/packages/SystemUI/res/values-ja/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g>を削除します。"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g>は削除されました。"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"最近のアプリケーションをすべて消去しました。"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"「<xliff:g id="APP">%s</xliff:g>」のアプリ情報を開きます。"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g>を開始しています。"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"通知が削除されました。"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g>を音量ダイアログとして使用"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"タップすると元の音量ダイアログが復元されます。"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"仕事用プロファイルを使用しています"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"システムUI調整ツール"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"内蔵電池の残量の割合を表示する"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"充電していないときには電池残量の割合をステータスバーアイコンに表示する"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"上に移動"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"左に移動"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"右に移動"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"アプリはマルチウィンドウでは動作しないことがあります"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ポジション <xliff:g id="POSITION">%1$d</xliff:g> の <xliff:g id="TILE_NAME">%2$s</xliff:g> を編集するにはダブルタップします。"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g> を追加するにはダブルタップします。"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ポジション <xliff:g id="POSITION">%1$d</xliff:g> に配置します。選択するにはダブルタップします。"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> を削除しました"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> をポジション <xliff:g id="POSITION">%2$d</xliff:g> に移動しました"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"クイック設定エディタ"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"アプリは分割画面では動作しないことがあります。"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"アプリで分割画面がサポートされていません。"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ka-rGE/strings.xml b/packages/SystemUI/res/values-ka-rGE/strings.xml
index 5008fe0..fbd97f0 100644
--- a/packages/SystemUI/res/values-ka-rGE/strings.xml
+++ b/packages/SystemUI/res/values-ka-rGE/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g>-ის უგულებელყოფა."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ამოშლილია სიიდან."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"ყველა ბოლო აპლიკაცია გაუქმდა."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> აპლიკაციის ინფორმაციის გახსნა."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> იწყება."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"შეტყობინება წაიშალა."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ხმოვან დიალოგშია"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"ორიგინალის აღდგენისათვის, შეეხეთ."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"თქვენ სამსახურის პროფილს იყენებთ"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"სისტემის UI ტუნერი"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"ჩამაგრებული ბატარეის პროცენტის ჩვენება"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ბატარეის დონის პროცენტის ჩვენება სტატუსის ზოლის ხატულას შიგნით, როდესაც არ იტენება"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ზემოთ გადატანა"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"მარცხნივ გადატანა"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"მარჯვნივ გადატანა"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"აპმა შეიძლება არ იმუშაოს მრავალი ფანჯრის რეჟიმში"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"პოზიცია <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. რედაქტირებისთვის, შეეხეთ ორმაგად."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. დასამატებლად, შეეხეთ ორმაგად."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"პოზიცია <xliff:g id="POSITION">%1$d</xliff:g>. ასარჩევად, შეეხეთ ორმაგად."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ამოიშალა"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> გადატანილია პოზიციაზე <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"სწრაფი პარამეტრების რედაქტორი."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"აპმა შეიძლება არ იმუშაოს გაყოფილი ეკრანის რეჟიმში."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ეკრანის გაყოფა არ არის მხარდაჭერილი აპის მიერ."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-kk-rKZ/strings.xml b/packages/SystemUI/res/values-kk-rKZ/strings.xml
index ff33f05..4bc585a 100644
--- a/packages/SystemUI/res/values-kk-rKZ/strings.xml
+++ b/packages/SystemUI/res/values-kk-rKZ/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> қолданбасынан бас тарту."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> алынып тасталған."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Барлық жақындағы қабылданбаған қолданбалар."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> қолданбасы туралы ақпаратты ашады."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> іске қосылуда."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Хабар алынып тасталды."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> — көлем диалогтық терезесі"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Түпнұсқаны қалпына келтіру үшін түртіңіз."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Сіз жұмыс профиліңізді пайдаланып жатырсыз"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Жүйелік пайдаланушылық интерфейс тюнері"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Ендірілген батарея пайыздық шамасын көрсету"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Зарядталмай тұрғанда, күй жолағы белгішесінің ішінде батарея деңгейінің пайыздық шамасын көрсетеді"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Жоғары қарай жылжыту"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Солға жылжыту"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Оңға жылжыту"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Қолданба көп тереземен жұмыс істемеуі мүмкін"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g> орны, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Өңдеу үшін екі рет түртіңіз."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Қосу үшін екі рет түртіңіз."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g> орны. Таңдау үшін екі рет түртіңіз."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> жойылды"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g> орнына жылжытылды"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Жылдам параметрлер өңдегіші."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Қолданба бөлінген экранда жұмыс істемеуі мүмкін."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Қодланба бөлінген экранды қолдамайды."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-km-rKH/strings.xml b/packages/SystemUI/res/values-km-rKH/strings.xml
index b69f893..9f66f3b 100644
--- a/packages/SystemUI/res/values-km-rKH/strings.xml
+++ b/packages/SystemUI/res/values-km-rKH/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"បោះបង់ <xliff:g id="APP">%s</xliff:g> ។"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> បដិសេធ។"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"កម្មវិធីថ្មីៗទាំងអស់ត្រូវបានបោះបង់។"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"បើកព័ត៌មានកម្មវិធី <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"ចាប់ផ្ដើម <xliff:g id="APP">%s</xliff:g> ។"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"បាន​បដិសេធ​ការ​ជូនដំណឹង"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> គឺជាប្រអប់សម្លេង"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"ប៉ះដើម្បីស្តារច្បាប់ដើម។"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"អ្នកកំពុងប្រើប្រវត្តិរូបការងាររបស់អ្នក"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"កម្មវិធីសម្រួល UI ប្រព័ន្ធ"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"បង្ហាញភាគរយថាមពលថ្មដែលបានបង្កប់"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"បង្ហាញភាគរយនៃកម្រិតថាមពលថ្មនៅក្នុងរូបតំណាងរបារស្ថានភាពនៅពេលមិនសាកថ្ម"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ផ្លាស់ទីឡើងលើ"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ផ្លាស់ទីទៅឆ្វេង"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ផ្លាស់ទីទៅស្តាំ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"កម្មវិធីអាចនឹងមិនដំណើរការជាមួយពហុវិនដូទេ"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ទីតាំង <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>, ប៉ះពីរដងដើម្បីកែ"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>, ប៉ះពីរដងដើម្បីបន្ថែម"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ទីតាំង <xliff:g id="POSITION">%1$d</xliff:g>, ប៉ះពីរដងដើម្បីជ្រើស"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ត្រូវបានយកចេញ"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> បានផ្លាស់ទីទៅទីតាំង <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"កម្មវិធីកែការកំណត់រហ័ស"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"កម្មវិធីអាចនឹងមិនដំណើរការនៅលើអេក្រង់បំបែកទេ"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"កម្មវិធីមិនគាំទ្រអេក្រង់បំបែកជាពីរទេ"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-kn-rIN/strings.xml b/packages/SystemUI/res/values-kn-rIN/strings.xml
index 1ce14dd5..41537a39 100644
--- a/packages/SystemUI/res/values-kn-rIN/strings.xml
+++ b/packages/SystemUI/res/values-kn-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> ವಜಾಗೊಳಿಸು."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ವಜಾಗೊಳಿಸಲಾಗಿದೆ."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"ಇತ್ತೀಚಿನ ಎಲ್ಲಾ ಅಪ್ಲಿಕೇಶನ್‌ಗಳನ್ನು ವಜಾಗೊಳಿಸಲಾಗಿದೆ."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ಅಪ್ಲಿಕೇಶನ್ ಮಾಹಿತಿ ತೆರೆಯಿರಿ."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> ಪ್ರಾರಂಭಿಸಲಾಗುತ್ತಿದೆ."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"ಅಧಿಸೂಚನೆ ವಜಾಗೊಂಡಿದೆ."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ವಾಲ್ಯೂಮ್ ಸಂವಾದವಾಗಿದೆ"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"ಮೂಲ ಮರುಸ್ಥಾಪಿಸಲು ಸ್ಪರ್ಶಿಸಿ."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"ನಿಮ್ಮ ಕೆಲಸದ ಪ್ರೊಫೈಲ್‌ ಅನ್ನು ನೀವು ಬಳಸುತ್ತಿರುವಿರಿ"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"ಸಿಸ್ಟಮ್ UI ಟ್ಯೂನರ್"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"ಎಂಬೆಡ್ ಮಾಡಲಾದ ಬ್ಯಾಟರಿ ಶೇಕಡಾ ತೋರಿಸಿ"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ಚಾರ್ಜ್ ಮಾಡದಿರುವಾಗ ಸ್ಥಿತಿ ಪಟ್ಟಿ ಐಕಾನ್ ಒಳಗೆ ಬ್ಯಾಟರಿ ಮಟ್ಟದ ಶೇಕಡಾವನ್ನು ತೋರಿಸಿ"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ಮೇಲೆ ಸರಿಸಿ"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ಎಡಕ್ಕೆ ಸರಿಸಿ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ಬಲಕ್ಕೆ ಸರಿಸಿ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"ಬಹು ವಿಂಡೋದಲ್ಲಿ ಅಪ್ಲಿಕೇಶನ್ ಕೆಲಸ ಮಾಡದೇ ಇರಬಹುದು"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ಸ್ಥಾನ <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. ಸಂಪಾದಿಸಲು ಡಬಲ್ ಟ್ಯಾಪ್ ಮಾಡಿ."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. ಸೇರಿಸಲು ಡಬಲ್ ಟ್ಯಾಪ್ ಮಾಡಿ."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ಸ್ಥಾನ <xliff:g id="POSITION">%1$d</xliff:g>. ಆಯ್ಕೆಮಾಡಲು ಡಬಲ್ ಟ್ಯಾಪ್ ಮಾಡಿ."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ತೆಗೆದುಹಾಕಲಾಗಿದೆ"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="POSITION">%2$d</xliff:g> ಸ್ಥಾನಕ್ಕೆ <xliff:g id="TILE_NAME">%1$s</xliff:g> ಸೇರಿಸಲಾಗಿದೆ"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ತ್ವರಿತ ಸೆಟ್ಟಿಂಗ್‍ಗಳ ಸಂಪಾದಕ."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"ವಿಭಜಿಸಿದ ಪರದೆಯಲ್ಲಿ ಅಪ್ಲಿಕೇಶನ್ ಕೆಲಸ ಮಾಡದೇ ಇರಬಹುದು."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ಅಪ್ಲಿಕೇಶನ್ ಸ್ಪ್ಲಿಟ್ ಸ್ಕ್ರೀನ್ ಅನ್ನು ಬೆಂಬಲಿಸುವುದಿಲ್ಲ."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ko/strings.xml b/packages/SystemUI/res/values-ko/strings.xml
index a8a2a0a..702c489 100644
--- a/packages/SystemUI/res/values-ko/strings.xml
+++ b/packages/SystemUI/res/values-ko/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g>을(를) 숨깁니다."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g>이(가) 제거되었습니다."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"최근 사용한 애플리케이션을 모두 닫았습니다."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> 애플리케이션 정보를 엽니다."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g>을(를) 시작하는 중입니다."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"알림이 제거되었습니다."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g>은(는) 볼륨 대화입니다."</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"원본을 복원하려면 터치하세요."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"직장 프로필을 사용하고 있습니다."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"시스템 UI 튜너"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"내장형 배터리 잔량 비율 표시"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"충전 중이 아닌 경우 상태 표시줄 아이콘 내에 배터리 잔량 비율 표시"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"위로 이동"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"왼쪽으로 이동"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"오른쪽으로 이동"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"앱이 멀티 윈도우에서 작동하지 않을 수 있습니다."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"위치 <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. 수정하려면 두 번 탭하세요."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. 추가하려면 두 번 탭하세요."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"위치 <xliff:g id="POSITION">%1$d</xliff:g>. 선택하려면 두 번 탭하세요."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> 타일이 삭제되었습니다."</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> 타일을 위치 <xliff:g id="POSITION">%2$d</xliff:g>(으)로 이동함"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"빠른 설정 편집기"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"앱이 분할 화면에서 작동하지 않을 수 있습니다."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"앱이 화면 분할을 지원하지 않습니다."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ky-rKG/strings.xml b/packages/SystemUI/res/values-ky-rKG/strings.xml
index 6a2d77f..23349eb 100644
--- a/packages/SystemUI/res/values-ky-rKG/strings.xml
+++ b/packages/SystemUI/res/values-ky-rKG/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> этибарга албоо."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> жок болду."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Акыркы колдонмолордун баары көз жаздымда калтырылды."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> колдонмосу жөнүндө маалыматты ачыңыз."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> иштеп баштоодо."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Эскертме жок кылынды."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> үндү катуулатуу диалогу"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Түпнусканы калыбына келтирүү үчүн тийип коюңуз."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Жумуш профилиңизди колдонуп жатасыз"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Батарянын кубатнын деңгээли пайыз менен көрсөтлсүн"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Түзмөк кубаттанбай турганда, батареянын деңгээли статус тилкесинде көрүнүп турат"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Жогору жылдыруу"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Солго жылдыруу"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Оңго жылдыруу"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Бир нече терезе режиминде колдонмо иштебей калышы мүмкүн"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Орду - <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Түзөтүү үчүн эки жолу таптаңыз."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Кошуу үчүн эки жолу таптаңыз."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Орду - <xliff:g id="POSITION">%1$d</xliff:g>. Тандоо үчүн эки жолу таптаңыз."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> алынып салынды"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> деген <xliff:g id="POSITION">%2$d</xliff:g>-орунга жылдырылды"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Ыкчам жөндөөлөр түзөткүчү."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Колдонмодо экран бөлүнбөшү мүмкүн."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Колдонмодо экран бөлүнбөйт."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-lo-rLA/strings.xml b/packages/SystemUI/res/values-lo-rLA/strings.xml
index 601cc2a..22acd02 100644
--- a/packages/SystemUI/res/values-lo-rLA/strings.xml
+++ b/packages/SystemUI/res/values-lo-rLA/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"ປິດ <xliff:g id="APP">%s</xliff:g> ໄວ້."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"ປິດ <xliff:g id="APP">%s</xliff:g> ແລ້ວ."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"ທຸກ​ແອັບ​ພ​ລິ​ເຄ​ຊັນ​ບໍ່​ດົນ​ມາ​ນີ້​ຖືກ​ປ່ອຍ​ໄປ."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"ເປີດຂໍ້ມູນແອັບພລິເຄຊັນ <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"ກຳ​ລັງ​ເປີດ <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"ປິດການແຈ້ງເຕືອນແລ້ວ."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ແມ່ນ​ໜ້າ​ຕ່າງ​ລະ​ດັບ​ສຽງ"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"ສໍາ​ຜັດ​ເພື່ອກູ້​ຄືນ​ຕົ້ນ​ສະ​ບັບ​."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"ທ່ານກຳລັງໃຊ້ໂປຣໄຟລ໌ບ່ອນເຮັດວຽກຂອງທ່ານ"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"ສະ​ແດງ​ເປີ​ເຊັນ​ແບັດ​ເຕີ​ຣີ​ທີ່​ຕິດ​ມາ"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ສະ​ແດງ​ເປີ​ເຊັນ​ລະ​ດັບ​ແບັດ​ເຕີ​ຣີ​ຢູ່​ດ້ານ​ໃນ​ໄອ​ຄອນ​ແຖບ​ສະ​ຖາ​ນະ ເມື່ອ​ບໍ່​ສາກ​ຢູ່"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ເລື່ອນຂຶ້ນ"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ເລື່ອນຊ້າຍ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ເລື່ອນຂວາ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"ແອັບອາດບໍ່ສາມາດໃຊ້ໄດ້ກັບຫຼາຍໜ້າຈໍ"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ຕຳແໜ່ງ <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. ແຕະສອງເທື່ອເພື່ອແກ້ໄຂ."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. ແຕະສອງເທື່ອເພື່ອເພີ່ມ."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ຕຳແໜ່ງ <xliff:g id="POSITION">%1$d</xliff:g>. ແຕະສອງເທື່ອເພື່ອເລືອກ."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"ລຶບ <xliff:g id="TILE_NAME">%1$s</xliff:g> ອອກແລ້ວ"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ຍ້າຍໄປຕຳແໜ່ງ <xliff:g id="POSITION">%2$d</xliff:g> ແລ້ວ"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ຕົວແກ້ໄຂການຕັ້ງຄ່າດ່ວນ"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"ແອັບອາດໃຊ້ບໍ່ໄດ້ກັບການແບ່ງໜ້າຈໍ."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ແອັບບໍ່ຮອງຮັບໜ້າຈໍແບບແຍກກັນ."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-lt/strings.xml b/packages/SystemUI/res/values-lt/strings.xml
index 866abf3..ac32b30 100644
--- a/packages/SystemUI/res/values-lt/strings.xml
+++ b/packages/SystemUI/res/values-lt/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Atsisakyti <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Atsisakyta programos „<xliff:g id="APP">%s</xliff:g>“."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Atsisakyta visų naujausių programų."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Atidaryti programos „<xliff:g id="APP">%s</xliff:g>“ informaciją."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Paleidžiama <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"„<xliff:g id="APP">%1$s</xliff:g>“ <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Pranešimo atsisakyta."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"„<xliff:g id="APP_NAME">%1$s</xliff:g>“ yra garsumo valdymo dialogo langas"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Palieskite, kad atkurtumėte originalą."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Naudojate darbo profilį"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sistemos naudotojo sąsajos derinimo priemonė"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Rodyti įterptą akumuliat. įkrovos procentinę vertę"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Rodyti akumuliatoriaus įkrovos lygio procentinę vertę būsenos juostos piktogramoje, kai įrenginys nėra įkraunamas"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Perkelti aukštyn"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Perkelti kairėn"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Perkelti dešinėn"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Naudojant kelių langų funkciją programa gali neveikti"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g> padėtis, išklotinės elementas „<xliff:g id="TILE_NAME">%2$s</xliff:g>“. Dukart palieskite, kad redaguotumėte."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"Išklotinės elementas „<xliff:g id="TILE_NAME">%1$s</xliff:g>“. Dukart palieskite, kad pridėtumėte."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g> padėtis. Dukart palieskite, kad pasirinktumėte."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Išklotinės elementas „<xliff:g id="TILE_NAME">%1$s</xliff:g>“ pašalintas"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Išklotinės elementas „<xliff:g id="TILE_NAME">%1$s</xliff:g>“ perkeltas į <xliff:g id="POSITION">%2$d</xliff:g> padėtį"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Sparčiųjų nustatymų redagavimo priemonė."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Programa gali neveikti naudojant skaidytą ekraną."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Programoje nepalaikomas skaidytas ekranas."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-lv/strings.xml b/packages/SystemUI/res/values-lv/strings.xml
index 9c32b31..218178a 100644
--- a/packages/SystemUI/res/values-lv/strings.xml
+++ b/packages/SystemUI/res/values-lv/strings.xml
@@ -169,8 +169,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Nerādīt lietotni <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Lietotne <xliff:g id="APP">%s</xliff:g> vairs netiek rādīta."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Visas nesen izmantotās lietojumprogrammas tika noņemtas."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Atveriet lietojumprogrammas <xliff:g id="APP">%s</xliff:g> informāciju."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Notiek lietotnes <xliff:g id="APP">%s</xliff:g> palaišana."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Paziņojums netiek rādīts."</string>
@@ -422,6 +421,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ir skaļuma dialoglodziņš"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Pieskarieties, lai atjaunotu sākotnējo."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Jūs izmantojat darba profilu."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sistēmas saskarnes regulators"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Rādīt akumulatora uzlādes līmeni procentos"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Rādīt akumulatora uzlādes līmeni procentos statusa joslas ikonā, kad netiek veikta uzlāde"</string>
@@ -597,7 +602,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Pārvietot uz augšu"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Pārvietot pa kreisi"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Pārvietot pa labi"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Iespējams, lietotnē nedarbosies vairāku logu režīms."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>. pozīcija, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Lai rediģētu, veiciet dubultskārienu."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Lai pievienotu, veiciet dubultskārienu."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g>. pozīcija. Lai atlasītu, veiciet dubultskārienu."</string>
@@ -607,4 +611,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Elements <xliff:g id="TILE_NAME">%1$s</xliff:g> ir noņemts"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Elements <xliff:g id="TILE_NAME">%1$s</xliff:g> ir pārvietots uz <xliff:g id="POSITION">%2$d</xliff:g>. pozīciju"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Ātro iestatījumu redaktors."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Iespējams, lietotnē nedarbosies ekrāna sadalīšana."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Lietotnē netiek atbalstīta ekrāna sadalīšana."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-mk-rMK/strings.xml b/packages/SystemUI/res/values-mk-rMK/strings.xml
index 7f2fc15..8d25796 100644
--- a/packages/SystemUI/res/values-mk-rMK/strings.xml
+++ b/packages/SystemUI/res/values-mk-rMK/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Отфрли <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> е отфрлена."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Сите неодамнешни апликации се отфрлени."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Отвори информации за апликацијата <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Се стартува <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Известувањето е отфрлено."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> е дијалог за јачина на звук"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Допрете за да го вратите оригиналот."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Го користите работниот профил"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Адаптер на УИ на системот"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Прикажи вграден процент на батеријата"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Прикажи процент на ниво на батеријата во внатрешноста на иконата со статусна лента кога не се полни"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Преместете нагоре"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Преместете налево"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Преместете надесно"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Апликацијата може да не работи со повеќе прозорци"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Место <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Допрете двапати за уредување."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Допрете двапати за додавање."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Место <xliff:g id="POSITION">%1$d</xliff:g>. Допрете двапати за избирање."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> е отстранета"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> е преместена на место <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Уредник за брзи поставки."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Апликацијата можеби нема да работи во поделен екран."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Апликацијата не поддржува поделен екран."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ml-rIN/strings.xml b/packages/SystemUI/res/values-ml-rIN/strings.xml
index dfe992c..e44642d 100644
--- a/packages/SystemUI/res/values-ml-rIN/strings.xml
+++ b/packages/SystemUI/res/values-ml-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> നിരസിക്കുക."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> നിരസിച്ചു."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"അടുത്തിടെയുള്ള എല്ലാ അപ്ലിക്കേഷനും നിരസിച്ചു."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ആപ്പ് വിവരങ്ങൾ തുറക്കുക."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> ആരംഭിക്കുന്നു."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"അറിയിപ്പ് നിരസിച്ചു."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g>, വോളിയം ഡയലോഗാണ്"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"ആദ്യത്തേത് പുനഃസ്ഥാപിക്കാൻ സ്‌പർശിക്കുക."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"നിങ്ങൾ ഉപയോഗിക്കുന്നത് ഔദ്യോഗിക പ്രൊഫൈലാണ്"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"സിസ്റ്റം UI ട്യൂണർ"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"എംബഡ് ചെയ്‌ത ബാറ്ററി ശതമാനം കാണിക്കുക"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ചാർജ്ജുചെയ്യാതിരിക്കുമ്പോൾ സ്റ്റാറ്റസ് ബാർ ഐക്കണിൽ ബാറ്ററി ലെവൽ ശതമാനം കാണിക്കുക"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"മുകളിലേക്ക് നീക്കുക"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ഇടത്തേക്ക് നീക്കുക"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"വലത്തേക്ക് നീക്കുക"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"മൾട്ടി-വിൻഡോയിൽ ആപ്പ് പ്രവർത്തിച്ചേക്കില്ല"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"സ്ഥാനം <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. എഡിറ്റുചെയ്യുന്നതിന് രണ്ടുതവണ ടാപ്പുചെയ്യുക."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. ചേർക്കാൻ രണ്ടുതവണ ടാപ്പുചെയ്യുക."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"സ്ഥാനം <xliff:g id="POSITION">%1$d</xliff:g>. തിരഞ്ഞെടുക്കാൻ രണ്ടുതവണ ടാപ്പുചെയ്യുക."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> നീക്കംചെയ്യുന്നു"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"സ്ഥാനം <xliff:g id="POSITION">%2$d</xliff:g>-ലേക്ക് <xliff:g id="TILE_NAME">%1$s</xliff:g> നീക്കി"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ദ്രുത ക്രമീകരണ എഡിറ്റർ."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"സ്പ്ലിറ്റ്-സ്ക്രീനിനൊപ്പം ആപ്പ് പ്രവർത്തിച്ചേക്കില്ല."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"സ്പ്ലിറ്റ്-സ്ക്രീനിനെ ആപ്പ് പിന്തുണയ്ക്കുന്നില്ല."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-mn-rMN/strings.xml b/packages/SystemUI/res/values-mn-rMN/strings.xml
index 80cb8f2..e3fd349 100644
--- a/packages/SystemUI/res/values-mn-rMN/strings.xml
+++ b/packages/SystemUI/res/values-mn-rMN/strings.xml
@@ -166,8 +166,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g>-г хаах."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> байхгүй."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Хамгийн сүүлийн бүх програмыг арилгасан байна."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> апп-н мэдээллийг нээнэ үү."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g>-г эхлүүлж байна."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Мэдэгдэл хаагдсан."</string>
@@ -419,6 +418,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> нь дууны диалог юм."</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Анхны хувилбарыг эргүүлэн хадгалахыг хүсвэл хүрнэ үү."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Та өөрийн ажлын профайлыг ашиглаж байна"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Системийн UI Тохируулагч"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Залгаатай тэжээлийн хувийг харуулах"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Тэжээлийн хувийг цэнэглээгүй байх үед статусын хэсэгт харуулна уу"</string>
@@ -594,7 +599,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Дээш зөөх"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Зүүн тийш зөөх"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Баруун тийш зөөх"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Олон цонхтой үед апп ажиллахгүй байж болзошгүй"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Байршил <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Засахын тулд 2 удаа дарна уу."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Нэмэхийн тулд 2 удаа дарна уу."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Албан тушаал <xliff:g id="POSITION">%1$d</xliff:g>. Сонгохын тулд 2 удаа дарна уу."</string>
@@ -604,4 +608,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g>-г устгасан"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g>-г <xliff:g id="POSITION">%2$d</xliff:g> байршилд зөөсөн"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Түргэн тохиргоо засварлагч."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Апп хуваагдсан дэлгэцэд ажиллахгүй."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Энэ апп нь дэлгэц хуваах тохиргоог дэмждэггүй."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-mr-rIN/strings.xml b/packages/SystemUI/res/values-mr-rIN/strings.xml
index 76dfcd5..2cd5ed8 100644
--- a/packages/SystemUI/res/values-mr-rIN/strings.xml
+++ b/packages/SystemUI/res/values-mr-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> डिसमिस करा."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> डिसमिस केला."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"अलीकडील सर्व अनुप्रयोग डिसमिस झाले."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> अनुप्रयोग माहिती उघडा."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> प्रारंभ करीत आहे."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"सूचना डिसमिस केल्या."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> हा व्हॉल्यूम संवाद आहे"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"मूळ पुनर्संचयित करण्यासाठी स्पर्श करा."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"आपण आपले कार्य प्रोफाईल वापरत आहात"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"सिस्टीम UI ट्यूनर"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"एम्बेडेड बॅटरी टक्केवारी दर्शवा"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"चार्ज होत नसताना स्टेटस बार चिन्हामध्‍ये बॅटरी पातळी टक्केवारी दर्शवा"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"वर हलवा"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"डावीकडे हलवा"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"उजवीकडे हलवा"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"एकाधिक-विंडो सह अॅप कार्य करू शकत नाही"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"स्थिती <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. संपादित करण्यासाठी दोनदा टॅप करा."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g> . जोडण्यासाठी दोनदा टॅप करा."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"स्थिती <xliff:g id="POSITION">%1$d</xliff:g>. निवडण्यासाठी दोनदा टॅप करा."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ला काढले आहे"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ला <xliff:g id="POSITION">%2$d</xliff:g> स्थितीवर हलविले"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"द्रुत सेटिंग्ज संपादक."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"अॅप कदाचित विभाजित-स्क्रीनसह कार्य करू शकत नाही."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"अॅप स्क्रीन-विभाजनास समर्थन देत नाही."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ms-rMY/strings.xml b/packages/SystemUI/res/values-ms-rMY/strings.xml
index 9401198..e11f7ff 100644
--- a/packages/SystemUI/res/values-ms-rMY/strings.xml
+++ b/packages/SystemUI/res/values-ms-rMY/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Ketepikan <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ditolak."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Semua aplikasi terbaharu diketepikan."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Buka maklumat aplikasi <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Memulakan <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Pemberitahuan diketepikan."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ialah dialog kelantangan"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Sentuh untuk memulihkan yang asal."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Anda sedang menggunakan profil kerja"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Penala UI Sistem"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Tunjukkan peratusan bateri terbenam"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Tunjukkan peratusan aras bateri dalam ikon bar status semasa tidak mengecas"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Alih ke atas"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Alih ke kiri"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Alih ke kanan"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Apl mungkin tidak berfungsi dengan berbilang tetingkap"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Kedudukan <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dwiketik untuk mengedit."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dwiketik untuk menambah."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Kedudukan <xliff:g id="POSITION">%1$d</xliff:g>. Dwiketik untuk memilih."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> dialih keluar"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> dialihkan ke kedudukan <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor tetapan pantas."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Apl mungkin tidak berfungsi dengan skrin pisah."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Apl tidak menyokong skrin pisah."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-my-rMM/strings.xml b/packages/SystemUI/res/values-my-rMM/strings.xml
index 6964750..67ce1fc 100644
--- a/packages/SystemUI/res/values-my-rMM/strings.xml
+++ b/packages/SystemUI/res/values-my-rMM/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g>ကို ပယ်လိုက်ရန်"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ထုတ်ထားသည်။"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"မကြာသေးမီက အပလီကေးရှင်းများအားလုံး ဖယ်ထုတ်ပြီးပါပြီ။"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> အက်ပ်အချက်အလက်ကို ဖွင့်ပါ။"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g>ကို စတင်နေသည်။"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g><xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"အကြောင်းကြားချက်ကိုဖယ်ရှားပြီး"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> သည် အသံဒိုင်ယာလော့ခ်ဖြစ်သည်"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"မူရင်းအားပြန်လည်သိမ်းဆည်းရန် ထိပါ။"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"သင်သည် အလုပ်ပရိုဖိုင်းအား သုံးနေသည်"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"စနစ် UI ဖမ်းစက်"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"မြုတ်ထားသည့် ဘတ်ထရီ ရာခိုင်နှုန်းကို ပြပါ"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"အားမသွင်းနေစဉ်တွင် ဘတ်ထရီအဆင့် ရာခိုင်နှုန်းကို အခြေနေပြဘား အိုင်ကွန်တွင် ပြပါ"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"အပေါ်သို့ရွှေ့ပါ"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ဘယ်ဘက်သို့ရွှေ့ပါ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ညာဘက်သို့ရွှေ့ပါ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"အက်ပ်သည် ဝင်းဒိုးများတပြိုင်နက်ဖွင့်ခြင်းကို မပံ့ပိုးပါ"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>၊ <xliff:g id="TILE_NAME">%2$s</xliff:g> နေရာ။ တည်းဖြတ်ရန် နှစ်ချက်တို့ပါ။"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>။ ပေါင်းထည့်ရန် နှစ်ချက်တို့ပါ။"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g> နေရာ။ ရွေးချယ်ရန် နှစ်ချက်တို့ပါ။"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ကိုဖယ်ရှားလိုက်ပါပြီ"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ကို <xliff:g id="POSITION">%2$d</xliff:g> နေရာသို့ ရွှေ့လိုက်ပါပြီ"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"မြန်ဆန်သည့် ဆက်တင်တည်းဖြတ်စနစ်"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"မျက်နှာပြင် ခွဲခြမ်းပြသမှုဖြင့် အက်ပ်သည် အလုပ်လုပ်မည် မဟုတ်ပါ။"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"အက်ပ်သည် မျက်နှာပြင်ခွဲပြရန် ပံ့ပိုးထားခြင်းမရှိပါ။"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-nb/strings.xml b/packages/SystemUI/res/values-nb/strings.xml
index eed5f36..6d68342 100644
--- a/packages/SystemUI/res/values-nb/strings.xml
+++ b/packages/SystemUI/res/values-nb/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Avvis <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> avvist."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Alle nylig brukte apper er avvist."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Åpne appinformasjonen for <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Starter <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Varselet ble skjult."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> er volumdialogen"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Trykk for å gå tilbake til den opprinnelige volumdialogen."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Du bruker jobbprofilen din"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Vis prosent for det innebygde batteriet"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Vis batterinivåprosenten inni statusfeltikonet når du ikke lader"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Flytt opp"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Flytt mot venstre"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Flytt mot høyre"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Appen fungerer kanskje ikke i Flervindusmodus"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Plassering <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dobbelttrykk for å endre."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dobbelttrykk for å legge til."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Plassering <xliff:g id="POSITION">%1$d</xliff:g>. Dobbelttrykk for å velge."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> er fjernet"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> er flyttet til plassering <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Redigeringsvindu for hurtiginnstillinger."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Det kan hende at appen ikke fungerer med delt skjerm."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Appen støtter ikke delt skjerm."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ne-rNP/strings.xml b/packages/SystemUI/res/values-ne-rNP/strings.xml
index 836dc4b..231a28a 100644
--- a/packages/SystemUI/res/values-ne-rNP/strings.xml
+++ b/packages/SystemUI/res/values-ne-rNP/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> खारेज गर्नुहोस्।"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> खारेज गरिएको छ।"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"सबै हालका अनुप्रयोगहरू खारेज गरियो।"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> अनुप्रयोग सम्बन्धी जानकारी खोल्नुहोस्।"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g>सुरु गर्दै।"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"सूचना खारेज।"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> भोल्यूम संवाद हो"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"मूल पुनर्स्थापना गर्न छुनुहोस्।"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"तपाईँले कार्य प्रोफाइल प्रयोग गर्दै हुनुहुन्छ"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"प्रणाली UI ट्युनर"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"इम्बेड गरिएको ब्याट्री प्रतिशत देखाउनुहोस्"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"चार्ज नगरेको बेला वस्तुस्थिति पट्टी आइकन भित्र ब्याट्री प्रतिशत स्तर देखाउनुहोस्"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"माथि सार्नुहोस्"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"बाँया सार्नुहोस्"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"दायाँ सार्नुहोस्"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"अनुप्रयोग बहु-विन्डोमा काम नगर्न सक्छ"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"स्थिति <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>। सम्पादन गर्नका लागि डबल ट्याप गर्नुहोस्।"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>। थप्नका लागि डबल ट्याप गर्नुहोस्।"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"स्थिति <xliff:g id="POSITION">%1$d</xliff:g>। चयन गर्नका लागि डबल ट्याप गर्नुहोस्।"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> लाई हटाइयो"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> लाई स्थिति <xliff:g id="POSITION">%2$d</xliff:g> मा सारियो"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"द्रुत सेटिङ सम्पादक।"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"अनुप्रयोगले विभाजित-स्क्रिनमा काम नगर्न सक्छ।"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"अनुप्रयोगले विभाजित-स्क्रिनलाई समर्थन गर्दैन।"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-nl/strings.xml b/packages/SystemUI/res/values-nl/strings.xml
index 41075e3..700fd88 100644
--- a/packages/SystemUI/res/values-nl/strings.xml
+++ b/packages/SystemUI/res/values-nl/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> sluiten."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> verwijderd."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Alle recente apps gesloten."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"App-gegevens voor <xliff:g id="APP">%s</xliff:g> openen."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> starten."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Melding verwijderd."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> is het volumedialoogvenster"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Tik hierop om het origineel te herstellen."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"U gebruikt je werkprofiel"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Systeem-UI-tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Percentage ingebouwde accu weergeven"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Accupercentage weergeven in het pictogram op de statusbalk wanneer er niet wordt opgeladen"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Omhoog"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Naar links"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Naar rechts"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"De app werkt mogelijk niet met meerdere vensters"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Positie <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Dubbeltik om te bewerken."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Dubbeltik om toe te voegen."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Positie <xliff:g id="POSITION">%1$d</xliff:g>. Dubbeltik om te selecteren."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is verwijderd"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> is verplaatst naar positie <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor voor \'Snelle instellingen\'."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"App werkt mogelijk niet met gesplitst scherm."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"App biedt geen ondersteuning voor gesplitst scherm."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-pa-rIN/strings.xml b/packages/SystemUI/res/values-pa-rIN/strings.xml
index 1703a2f..d2166a4a 100644
--- a/packages/SystemUI/res/values-pa-rIN/strings.xml
+++ b/packages/SystemUI/res/values-pa-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> ਨੂੰ ਰੱਦ ਕਰੋ।"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ਰੱਦ ਕੀਤਾ।"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"ਸਾਰੀਆਂ ਹਾਲੀਆ ਐਪਲੀਕੇਸ਼ਨਾਂ ਰੱਦ ਕੀਤੀਆਂ।"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ਐਪਲੀਕੇਸ਼ਨਾਂ ਜਾਣਕਾਰੀ ਖੋਲ੍ਹੋ।"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> ਚਾਲੂ ਕਰ ਰਿਹਾ ਹੈ।"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"ਸੂਚਨਾ ਰੱਦ ਕੀਤੀ।"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ਵੋਲਯੂਮ ਡਾਇਲੌਗ ਹੈ"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"ਅਸਲੀ ਨੂੰ ਰੀਸਟੋਰ ਕਰਨ ਲਈ ਛੋਹਵੋ।"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"ਤੁਸੀਂ ਆਪਣੀ ਕੰਮ ਪ੍ਰੋਫਾਈਲ ਵਰਤ ਰਹੇ ਹੋ"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI ਟਿਊਨਰ"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"ਜੋਡ਼ੀ ਗਈ ਬੈਟਰੀ ਪ੍ਰਤਿਸ਼ਤਤਾ ਦਿਖਾਓ"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ਜਦੋਂ ਚਾਰਜ ਨਾ ਹੋ ਰਹੀ ਹੋਵੇ ਤਾਂ ਸਥਿਤੀ ਬਾਰ ਦੇ ਅੰਦਰ ਬੈਟਰੀ ਪੱਧਰ ਪ੍ਰਤਿਸ਼ਤਤਾ ਦਿਖਾਓ"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ਉੱਪਰ ਲੈ ਜਾਓ"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ਖੱਬੇ ਲੈ ਜਾਓ"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"ਸੱਜੇ ਲੈ ਜਾਓ"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"ਹੋ ਸਕਦਾ ਹੈ ਕਿ ਐਪ ਮਲਟੀ-ਵਿੰਡੋ ਨਾਲ ਕੰਮ ਨਾ ਕਰੇ"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ਸਥਿਤੀ <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>। ਸੰਪਾਦਨ ਲਈ ਦੋ ਵਾਰ ਟੈਪ ਕਰੋ।"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>। ਸ਼ਾਮਲ ਕਰਨ ਲਈ ਦੋ ਵਾਰ ਟੈਪ ਕਰੋ।"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ਸਥਿਤੀ <xliff:g id="POSITION">%1$d</xliff:g>। ਚੁਣਨ ਲਈ ਦੋ ਵਾਰ ਟੈਪ ਕਰੋ।"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ਨੂੰ ਹਟਾਇਆ ਗਿਆ"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ਨੂੰ <xliff:g id="POSITION">%2$d</xliff:g> ਸਥਿਤੀ \'ਤੇ ਤਬਦੀਲ ਕੀਤਾ ਗਿਆ"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ਤਤਕਾਲ ਸੈਟਿੰਗਾਂ ਸੰਪਾਦਕ।"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"ਹੋ ਸਕਦਾ ਹੈ ਕਿ ਐਪ ਸਪਲਿਟ-ਸਕ੍ਰੀਨ ਨਾਲ ਕੰਮ ਨਾ ਕਰੇ।"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ਐਪ ਸਪਲਿਟ-ਸਕ੍ਰੀਨ ਨੂੰ ਸਮਰਥਨ ਨਹੀਂ ਕਰਦੀ।"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-pl/strings.xml b/packages/SystemUI/res/values-pl/strings.xml
index 297b849..2f1f889 100644
--- a/packages/SystemUI/res/values-pl/strings.xml
+++ b/packages/SystemUI/res/values-pl/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Usuń stąd <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g>: zamknięto."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Wszystkie ostatnie aplikacje zostały zamknięte."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Otwórz informacje o aplikacji <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Uruchamiam <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Zamknięto powiadomienie."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> steruje głośnością"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Dotknij, by przywrócić pierwotną."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Używasz profilu do pracy"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Kalibrator System UI"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Pokaż procent naładowania baterii"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Pokaż procent naładowania baterii w ikonie na pasku stanu, gdy telefon się nie ładuje"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Przesuń w górę"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Przesuń w lewo"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Przesuń w prawo"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikacja może nie działać w trybie wielu okien"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Położenie <xliff:g id="POSITION">%1$d</xliff:g>, kafelek <xliff:g id="TILE_NAME">%2$s</xliff:g>. Kliknij dwukrotnie, by edytować."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"Kafelek <xliff:g id="TILE_NAME">%1$s</xliff:g>. Kliknij dwukrotnie, by dodać."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Położenie <xliff:g id="POSITION">%1$d</xliff:g>. Kliknij dwukrotnie, by wybrać."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Kafelek <xliff:g id="TILE_NAME">%1$s</xliff:g> został usunięty"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Kafelek <xliff:g id="TILE_NAME">%1$s</xliff:g> przeniesiony w położenie <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Edytor szybkich ustawień."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacja może nie działać przy podzielonym ekranie."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacja nie obsługuje dzielonego ekranu."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-pt-rBR/strings.xml b/packages/SystemUI/res/values-pt-rBR/strings.xml
index eb08d99..9b778cc 100644
--- a/packages/SystemUI/res/values-pt-rBR/strings.xml
+++ b/packages/SystemUI/res/values-pt-rBR/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Descartar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> descartado."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Todos os apps recentes foram dispensados."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Abre informações do app <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Iniciando <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificação dispensada."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> é a caixa de diálogo referente ao volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toque para restaurar o original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Você está usando seu perfil de trabalho"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sintonizador System UI"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostrar porcentagem de bateria incorporada"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostrar porcentagem de nível de bateria dentro do ícone da barra de status quando não estiver carregando"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mover para cima"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mover para a esquerda"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mover para a direita"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"É possível que o app não funcione com várias janelas"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posição <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Toque duas vezes para editar."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Toque duas vezes para adicionar."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posição <xliff:g id="POSITION">%1$d</xliff:g>. Toque duas vezes para selecionar."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> é removido"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> movido para a posição <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de configurações rápidas."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"É possível que o app não funcione com o recurso de divisão de tela."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"O app não é compatível com a divisão de tela."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-pt-rPT/strings.xml b/packages/SystemUI/res/values-pt-rPT/strings.xml
index bba2f3e..69a4dad 100644
--- a/packages/SystemUI/res/values-pt-rPT/strings.xml
+++ b/packages/SystemUI/res/values-pt-rPT/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Ignorar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ignorado."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Todas as aplicações recentes foram ignoradas."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Abrir as informações da aplicação <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"A iniciar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificação ignorada."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> é a caixa de diálogo do volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toque para restaurar o original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Está a utilizar o seu perfil de trabalho"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sintonizador da interface do sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostrar percentagem da bateria incorporada"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostrar a percentagem do nível da bateria no ícone da barra de estado quando não estiver a carregar"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mover para cima"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mover para a esquerda"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mover para a direita"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"A aplicação pode não funcionar com multijanelas"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posição <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Toque duas vezes para editar."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Toque duas vezes para adicionar."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posição <xliff:g id="POSITION">%1$d</xliff:g>. Toque duas vezes para selecionar."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> removido"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> movido para a posição <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de definições rápidas."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"A aplicação pode não funcionar com o ecrã dividido."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"A aplicação não é compatível com o ecrã dividido."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-pt/strings.xml b/packages/SystemUI/res/values-pt/strings.xml
index eb08d99..9b778cc 100644
--- a/packages/SystemUI/res/values-pt/strings.xml
+++ b/packages/SystemUI/res/values-pt/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Descartar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> descartado."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Todos os apps recentes foram dispensados."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Abre informações do app <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Iniciando <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificação dispensada."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> é a caixa de diálogo referente ao volume"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Toque para restaurar o original."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Você está usando seu perfil de trabalho"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sintonizador System UI"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Mostrar porcentagem de bateria incorporada"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Mostrar porcentagem de nível de bateria dentro do ícone da barra de status quando não estiver carregando"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mover para cima"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mover para a esquerda"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mover para a direita"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"É possível que o app não funcione com várias janelas"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posição <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Toque duas vezes para editar."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Toque duas vezes para adicionar."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posição <xliff:g id="POSITION">%1$d</xliff:g>. Toque duas vezes para selecionar."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> é removido"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> movido para a posição <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor de configurações rápidas."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"É possível que o app não funcione com o recurso de divisão de tela."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"O app não é compatível com a divisão de tela."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ro/strings.xml b/packages/SystemUI/res/values-ro/strings.xml
index 81d0456..50289f3 100644
--- a/packages/SystemUI/res/values-ro/strings.xml
+++ b/packages/SystemUI/res/values-ro/strings.xml
@@ -169,8 +169,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Închideți <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> a fost eliminată."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Toate aplicațiile recente au fost închise."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Deschideți informațiile despre aplicația <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Se inițiază <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Notificarea a fost închisă."</string>
@@ -422,6 +421,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> afișează caseta de dialog pentru volum"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Atingeți pentru a reveni la setarea inițială."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Acum folosiți profilul de serviciu"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Afișați procentajul bateriei încorporat"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Afișați procentajul cu nivelul bateriei în interiorul pictogramei din bara de stare, atunci când nu se încarcă"</string>
@@ -597,7 +602,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Mutați în sus"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Mutați spre stânga"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Mutați spre dreapta"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Este posibil ca aplicația să nu funcționeze cu ferestre multiple"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Poziția <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Atingeți de două ori pentru a edita."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Atingeți de două ori pentru a adăuga."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Poziția <xliff:g id="POSITION">%1$d</xliff:g>. Atingeți de două ori pentru a selecta."</string>
@@ -607,4 +611,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Caseta <xliff:g id="TILE_NAME">%1$s</xliff:g> este eliminată"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Caseta <xliff:g id="TILE_NAME">%1$s</xliff:g> a fost mutată pe poziția <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editorul pentru setări rapide."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Este posibil ca aplicația să nu funcționeze cu ecranul împărțit."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplicația nu acceptă ecranul împărțit."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ru/strings.xml b/packages/SystemUI/res/values-ru/strings.xml
index 86f0ec4..0347b03 100644
--- a/packages/SystemUI/res/values-ru/strings.xml
+++ b/packages/SystemUI/res/values-ru/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Удаление приложения <xliff:g id="APP">%s</xliff:g> из списка."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Приложение \"<xliff:g id="APP">%s</xliff:g>\" удалено из списка."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Все недавние приложения закрыты."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Открыть информацию о приложении \"<xliff:g id="APP">%s</xliff:g>\""</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Запуск приложения <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Уведомление закрыто"</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"Приложение <xliff:g id="APP_NAME">%1$s</xliff:g> назначено регулятором громкости"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Нажмите, чтобы восстановить приложение по умолчанию."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Вы перешли в рабочий профиль"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Показывать уровень заряда батареи в процентах"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Когда устройство работает в автономном режиме, процент заряда батареи показан в строке состояния"</string>
@@ -541,7 +546,7 @@
     <string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"Контакты"</string>
     <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"Эл. почта"</string>
     <string name="keyboard_shortcut_group_applications_im" msgid="1892749399083161405">"Чат"</string>
-    <string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Музыка."</string>
+    <string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Музыка"</string>
     <string name="keyboard_shortcut_group_applications_youtube" msgid="6555453761294723317">"YouTube"</string>
     <string name="keyboard_shortcut_group_applications_calendar" msgid="9043614299194991263">"Календарь"</string>
     <string name="tuner_full_zen_title" msgid="4540823317772234308">"Показывать при нажатии кнопок регулировки громкости"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Поднять"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Сдвинуть влево"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Сдвинуть вправо"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Приложение не поддерживает многооконный режим"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Позиция <xliff:g id="POSITION">%1$d</xliff:g>, кнопка \"<xliff:g id="TILE_NAME">%2$s</xliff:g>\". Чтобы изменить, нажмите дважды."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"Кнопка \"<xliff:g id="TILE_NAME">%1$s</xliff:g>\". Чтобы добавить, нажмите дважды."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Позиция <xliff:g id="POSITION">%1$d</xliff:g>. Чтобы выбрать, нажмите дважды."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Кнопка \"<xliff:g id="TILE_NAME">%1$s</xliff:g>\" удалена"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Кнопка \"<xliff:g id="TILE_NAME">%1$s</xliff:g>\" теперь занимает позицию <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Редактор быстрых настроек."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Приложение не поддерживает разделение экрана."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Приложение не поддерживает разделение экрана."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-si-rLK/strings.xml b/packages/SystemUI/res/values-si-rLK/strings.xml
index 5a2f849..d92b0e8 100644
--- a/packages/SystemUI/res/values-si-rLK/strings.xml
+++ b/packages/SystemUI/res/values-si-rLK/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> ඉවතලන්න."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> අස් කර ඇත."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"සියලුම මෑත යෙඳුම් අස් කරන ලදි."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> යෙදුම් තොරතුරු විවෘත කරයි."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> ආරම්භ කරමින්."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"දැනුම්දීම නිෂ්ප්‍රභා කරඇත."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ධාරිතා සංවාදයයි"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"මුල් තත්ත්වය නැවත ප්‍රතිසාධනය කිරීමට ස්පර්ශ කරන්න."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"ඔබ ඔබේ කාර්යාල පැතිකඩ භාවිත කරමින් සිටී"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"පද්ධති UI සුසරකය"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"කාවද්දන ලද බැටරි ප්‍රතිශතය පෙන්වන්න"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ආරෝපණය නොවන විට තත්ත්ව තීරු නිරූපකය ඇතුළත බැටරි මට්ටම් ප්‍රතිශතය පෙන්වන්න"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"ඉහළට ගෙන යන්න"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"වමට ගෙන යන්න"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"දකුණට ගෙන යන්න"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"යෙදුම බහු-කවුළුව සමඟ ක්‍රියා නොකළ හැකිය."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ස්ථානය <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. වෙනස් කිරීමට දෙවරක් තට්ටු කරන්න."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. එක් කිරීමට දෙවරක් තට්ටු කරන්න."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ස්ථානය <xliff:g id="POSITION">%1$d</xliff:g>. තෝරා ගැනීමට දෙවරක් තට්ටු කරන්න."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ඉවත් කරන ලදි"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g> වන ස්ථානයට ගෙන යන ලදි"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ඉක්මන් සැකසුම් සංස්කාරකය."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"යෙදුම බෙදුම්-තිරය සමග ක්‍රියා නොකළ හැකිය."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"යෙදුම බෙදුණු-තිරය සඳහා සහාය නොදක්වයි."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-sk/strings.xml b/packages/SystemUI/res/values-sk/strings.xml
index 9468fcf..b606d01 100644
--- a/packages/SystemUI/res/values-sk/strings.xml
+++ b/packages/SystemUI/res/values-sk/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Zrušiť aplikáciu <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Aplikácia <xliff:g id="APP">%s</xliff:g> bola zrušená."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Všetky nedávne aplikácie boli odmietnuté."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Otvoriť informácie o aplikácii <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Spúšťa sa aplikácia <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Upozornenie bolo zrušené."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> je dialóg hlasitosti"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Klepnutím obnovíte originál."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Používate svoj pracovný profil."</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Tuner používateľského rozhrania systému"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Zobraziť percentá vloženej batérie"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Percentuálne zobrazenie nabitia batérie vnútri ikony v stavovom riadku, keď neprebieha nabíjanie"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Posunúť nahor"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Posunúť doľava"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Posunúť doprava"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikácia nemusí fungovať v režime viacerých okien"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Pozícia <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Upravíte ju dvojitým klepnutím."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Pridáte ju dvojitým klepnutím."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Pozícia <xliff:g id="POSITION">%1$d</xliff:g>. Vyberiete ju dvojitým klepnutím."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Dlaždica <xliff:g id="TILE_NAME">%1$s</xliff:g> bola odstránená"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Dlaždica <xliff:g id="TILE_NAME">%1$s</xliff:g> bola presunutá na pozíciu <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor rýchlych nastavení"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikácia nemusí fungovať so zapnutou rozdelenou obrazovkou."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikácia nepodporuje rozdelenú obrazovku."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-sl/strings.xml b/packages/SystemUI/res/values-sl/strings.xml
index c5a43f9..3c71c09 100644
--- a/packages/SystemUI/res/values-sl/strings.xml
+++ b/packages/SystemUI/res/values-sl/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Opusti aplikacijo <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Aplikacija <xliff:g id="APP">%s</xliff:g> je bila odstranjena."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Vse nedavne aplikacije so bile opuščene."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Odpiranje podatkov o aplikaciji <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Zaganjanje aplikacije <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Obvestilo je bilo odstranjeno."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> je pogovorno okno glede prostornine"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Dotaknite se, če želite obnoviti izvirnik."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Uporabljate delovni profil"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Uglaševalnik uporabniškega vmesnika sistema"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Prikaži odstotek napolnjenosti vgraj. akumulatorja"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Prikaz odstotka napolnjenosti akumulatorja znotraj ikone v vrstici stanja, ko se ne polni"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Premakni navzgor"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Premakni levo"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Premakni desno"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikacija morda ne deluje v načinu z več okni"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Položaj <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Če želite urediti, se dvakrat dotaknite."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Če želite dodati, se dvakrat dotaknite."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Položaj: <xliff:g id="POSITION">%1$d</xliff:g>. Če želite izbrati, se dvakrat dotaknite."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> je odstranjeno"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> premaknjeno na položaj <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Urejevalnik hitrih nastavitev."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacija morda ne deluje v načinu razdeljenega zaslona."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacija ne podpira načina razdeljenega zaslona."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-sq-rAL/strings.xml b/packages/SystemUI/res/values-sq-rAL/strings.xml
index 0188e5b..fe79425 100644
--- a/packages/SystemUI/res/values-sq-rAL/strings.xml
+++ b/packages/SystemUI/res/values-sq-rAL/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Largo <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> është hequr."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Të gjitha aplikacionet e fundit u larguan."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Hap informacionin e aplikacionit <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Po nis <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Njoftimi është hequr."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> është dialogu i volumit"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Prek për të restauruar origjinalin."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Po përdor profilin tënd të punës"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sintonizuesi i Sistemit të Ndërfaqes së Përdoruesit"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Shfaq përqindjen e baterisë së integruar"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Shfaq përqindjen e nivelit të baterisë brenda ikonës së shiritit të statusit kur nuk është duke u ngarkuar."</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Lëviz lart"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Lëviz majtas"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Lëviz djathtas"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Aplikacioni mund të mos punojë me funksionin me shumë dritare."</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Pozicioni <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Trokit dy herë për ta redaktuar."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Trokit dy herë për ta shtuar."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Pozicioni <xliff:g id="POSITION">%1$d</xliff:g>. Trokit dy herë për ta zgjedhur."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> u hoq"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> u zhvendos te pozicioni <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Redaktori i cilësimeve të shpejta."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Aplikacioni mund të mos funksionojë me ekranin e ndarë."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Aplikacioni nuk mbështet ekranin e ndarë."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-sr/strings.xml b/packages/SystemUI/res/values-sr/strings.xml
index 501a3e3..772aca4 100644
--- a/packages/SystemUI/res/values-sr/strings.xml
+++ b/packages/SystemUI/res/values-sr/strings.xml
@@ -169,8 +169,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Одбаците <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Апликација <xliff:g id="APP">%s</xliff:g> је одбачена."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Све недавно коришћене апликације су одбачене."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Отворите информације о апликацији <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Покрећемо <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Обавештење је одбачено."</string>
@@ -422,6 +421,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> је дијалог за јачину звука"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Додирните да бисте вратили оригинал."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Користите профил за Work"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Тјунер за кориснички интерфејс система"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Приказуј уграђени проценат батерије"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Приказивање нивоа напуњености батерије у процентима унутар иконе на статусној траци када се батерија не пуни"</string>
@@ -597,7 +602,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Помери нагоре"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Помери улево"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Помери удесно"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Апликација можда неће функционисати са више прозора"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>. позиција, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Двапут додирните да бисте изменили."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Двапут додирните да бисте додали."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g>. позиција. Двапут додирните да бисте изабрали."</string>
@@ -607,4 +611,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Плочица <xliff:g id="TILE_NAME">%1$s</xliff:g> је уклоњена"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Плочица <xliff:g id="TILE_NAME">%1$s</xliff:g> је премештена на <xliff:g id="POSITION">%2$d</xliff:g>. позицију"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Уређивач за Брза подешавања."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Апликација можда неће функционисати са подељеним екраном."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Апликација не подржава подељени екран."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-sv/strings.xml b/packages/SystemUI/res/values-sv/strings.xml
index 959128e..5acbc61 100644
--- a/packages/SystemUI/res/values-sv/strings.xml
+++ b/packages/SystemUI/res/values-sv/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Ta bort <xliff:g id="APP">%s</xliff:g> från listan."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> togs bort permanent."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Alla appar har tagits bort från listan Senaste."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Öppna appinformation för <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Startar <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Meddelandet ignorerades."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> används som volymkontroll"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Tryck här om du vill återställa den ursprungliga appen."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Du använder din jobbprofil"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Inställningar för systemgränssnitt"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Visa inbäddad batteriprocent"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Visa batterinivå i procent i statusfältsikonen när enheten inte laddas"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Flytta uppåt"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Flytta åt vänster"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Flytta åt höger"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Appen fungerar eventuellt inte i flerfönsterläge"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Position <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Tryck snabbt två gånger om du vill redigera positionen."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Lägg till genom att trycka snabbt två gånger."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Position <xliff:g id="POSITION">%1$d</xliff:g>. Välj den genom att trycka snabbt två gånger."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> har tagits bort"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> har flyttats till position <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Redigerare för snabbinställningar."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Appen kanske inte fungerar med delad skärm."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Appen har inte stöd för delad skärm."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-sw/strings.xml b/packages/SystemUI/res/values-sw/strings.xml
index 4b936c9..d4d278d 100644
--- a/packages/SystemUI/res/values-sw/strings.xml
+++ b/packages/SystemUI/res/values-sw/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Ondoa <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> imeondolewa."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Programu za hivi majuzi zimeondolewa."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Fungua maelezo kuhusu programu ya <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Inaanzisha <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Arifa imetupwa."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ni mazungumzo ya sauti"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Gusa ili urejeshe ya awali."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Unatumia wasifu wako wa kazini"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Kipokea Ishara cha SystemUI"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Onyesha asilimia ya betri iliyopachikwa"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Onyesha asilimia ya kiwango cha betri ndani ya aikoni ya sehemu ya arifa inapokuwa haichaji"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Sogeza juu"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Sogeza kushoto"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Sogeza kulia"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Huenda programu isifanye kazi kwenye madirisha mengi"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Nafasi ya <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Gonga mara mbili ili ubadilishe."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Gonga mara mbili ili uongeze."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Nafasi ya <xliff:g id="POSITION">%1$d</xliff:g>. Gonga mara mbili ili uchague."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> imeondolewa"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> imehamishiwa kwenye nafasi ya <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Kihariri cha Mipangilio ya haraka."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Huenda programu isifanye kazi kwenye skrini inayogawanywa."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Programu haiwezi kutumia skrini iliyogawanywa."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ta-rIN/strings.xml b/packages/SystemUI/res/values-ta-rIN/strings.xml
index 5489be9..3714c06 100644
--- a/packages/SystemUI/res/values-ta-rIN/strings.xml
+++ b/packages/SystemUI/res/values-ta-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> ஐ நிராகரி."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> விலக்கப்பட்டது."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"எல்லா சமீபத்திய பயன்பாடுகளும் விலக்கப்பட்டன."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> பயன்பாட்டின் தகவலைத் திற."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> ஐத் தொடங்குகிறது."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"அறிவிப்பு நிராகரிக்கப்பட்டது."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"ஒலியளவு செய்தி: <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"அசலை மீட்டமைக்கத் தொடவும்."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"பணி சுயவிவரத்தைப் பயன்படுத்துகிறீர்கள்"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"உள்ளிணைந்த பேட்டரி சதவீதத்தைக் காட்டு"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"சார்ஜ் செய்யாத போது, நிலைப் பட்டி ஐகானின் உள்ளே பேட்டரி அளவு சதவீதத்தைக் காட்டும்"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"மேலே நகர்த்து"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"இடப்புறம் நகர்த்து"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"வலப்புறம் நகர்த்து"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"பல சாளர அம்சத்தில் பயன்பாடு வேலைசெய்யாமல் போகக்கூடும்"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"நிலை <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. திருத்த, இருமுறை தட்டவும்."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. சேர்க்க, இருமுறை தட்டவும்."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"நிலை <xliff:g id="POSITION">%1$d</xliff:g>. தேர்ந்தெடுக்க, இருமுறை தட்டவும்."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> அகற்றப்பட்டது"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> நிலை <xliff:g id="POSITION">%2$d</xliff:g>க்கு நகர்த்தப்பட்டது"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"விரைவு அமைப்புகள் திருத்தி."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"திரைப் பிரிப்பில் பயன்பாடு வேலைசெய்யாமல் போகக்கூடும்."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"திரையைப் பிரிப்பதைப் பயன்பாடு ஆதரிக்கவில்லை."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-te-rIN/strings.xml b/packages/SystemUI/res/values-te-rIN/strings.xml
index 3a72809..1dd7254 100644
--- a/packages/SystemUI/res/values-te-rIN/strings.xml
+++ b/packages/SystemUI/res/values-te-rIN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g>ని తీసివేయండి."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> తీసివేయబడింది."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"అన్ని ఇటీవలి అనువర్తనాలు తీసివేయబడ్డాయి."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> అనువర్తన సమాచారాన్ని తెరుస్తుంది."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g>ని ప్రారంభిస్తోంది."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"నోటిఫికేషన్ తీసివేయబడింది."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> అనేది వాల్యూమ్ డైలాగ్"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"అసలుదాన్ని పునరుద్ధరించడానికి తాకండి."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"మీరు మీ కార్యాలయ ప్రొఫైల్‌ను ఉపయోగిస్తున్నారు"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"సిస్టమ్ UI ట్యూనర్"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"పొందుపరిచిన బ్యాటరీ శాతం చూపు"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"ఛార్జింగ్‌లో లేనప్పుడు స్థితి పట్టీ చిహ్నం లోపల బ్యాటరీ స్థాయి శాతం చూపుతుంది"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"పైకి తరలించు"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"ఎడమవైపుకు తరలించు"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"కుడివైపుకు తరలించు"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"అనువర్తనం బహుళ విండోల రూపంలో పని చేయకపోవచ్చు"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"స్థానం <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. సవరించడానికి రెండుసార్లు నొక్కండి."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. జోడించడానికి రెండుసార్లు నొక్కండి."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"స్థానం <xliff:g id="POSITION">%1$d</xliff:g>. ఎంచుకోవడానికి రెండుసార్లు నొక్కండి."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> తీసివేయబడింది"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g>వ స్థానానికి తరలించబడింది"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"శీఘ్ర సెట్టింగ్‌ల ఎడిటర్."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"స్క్రీన్ విభజనతో అనువర్తనం పని చేయకపోవచ్చు."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"అనువర్తనంలో స్క్రీన్ విభజనకు మద్దతు లేదు."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-th/strings.xml b/packages/SystemUI/res/values-th/strings.xml
index 4844c84..59b420d 100644
--- a/packages/SystemUI/res/values-th/strings.xml
+++ b/packages/SystemUI/res/values-th/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"ยกเลิก <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ถูกลบไปแล้ว"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"ปิดแอปพลิเคชันล่าสุดทั้งหมดแล้ว"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"เปิดข้อมูลแอปพลิเคชัน <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"กำลังเริ่มต้น <xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"ปิดการแจ้งเตือนแล้ว"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> เป็นช่องโต้ตอบระดับเสียง"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"แตะเพื่อคืนค่าดั้งเดิม"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"คุณกำลังใช้โปรไฟล์งานของคุณ"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"ตัวรับสัญญาณ UI ระบบ"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"แสดงเปอร์เซ็นต์ของแบตเตอรี่ในตัว"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"แสดงเปอร์เซ็นต์ของระดับแบตเตอรี่ภายในไอคอนแถบสถานะเมื่อไม่มีการชาร์จ"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"เลื่อนขึ้น"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"เลื่อนไปทางซ้าย"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"เลื่อนไปทางขวา"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"แอปอาจทำงานกับหลายหน้าต่างไม่ได้"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"ตำแหน่ง <xliff:g id="POSITION">%1$d</xliff:g> <xliff:g id="TILE_NAME">%2$s</xliff:g> แตะ 2 ครั้งเพื่อแก้ไข"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g> แตะ 2 ครั้งเพื่อเพิ่ม"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"ตำแหน่ง <xliff:g id="POSITION">%1$d</xliff:g> แตะ 2 ครั้งเพื่อเลือก"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"นำ <xliff:g id="TILE_NAME">%1$s</xliff:g> ออกแล้ว"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"ย้าย <xliff:g id="TILE_NAME">%1$s</xliff:g> ไปยังตำแหน่ง <xliff:g id="POSITION">%2$d</xliff:g> แล้ว"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"ตัวแก้ไขการตั้งค่าด่วน"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"แอปอาจใช้ไม่ได้กับโหมดแยกหน้าจอ"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"แอปไม่สนับสนุนการแยกหน้าจอ"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-tl/strings.xml b/packages/SystemUI/res/values-tl/strings.xml
index 0672959..629963d 100644
--- a/packages/SystemUI/res/values-tl/strings.xml
+++ b/packages/SystemUI/res/values-tl/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"I-dismiss ang <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Hindi pinansin ang <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Na-dismiss ang lahat ng kamakailang application."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Buksan ang impormasyon ng <xliff:g id="APP">%s</xliff:g> application."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Sinisimulan ang <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Na-dismiss ang notification."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"Ang <xliff:g id="APP_NAME">%1$s</xliff:g> ang volume dialog"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Pindutin upang ibalik ang orihinal."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Ginagamit mo ang iyong profile sa trabaho"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Tuner ng System UI"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Ipakita ang naka-embed na porsyento ng baterya"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Ipakita ang porsyento ng antas ng baterya na nasa icon ng status bar kapag nagcha-charge"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Ilipat pataas"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Ilipat pakaliwa"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Ilipat pakanan"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Maaaring hindi gumana ang app sa maraming window"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Posisyon <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. I-double tap upang i-edit."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. I-double tap upang idagdag."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Posisyon <xliff:g id="POSITION">%1$d</xliff:g>. I-double tap upang piliin."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"Inalis ang <xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"Inilipat ang <xliff:g id="TILE_NAME">%1$s</xliff:g> sa posisyon <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Editor ng Mga mabilisang setting."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Maaaring hindi gumana ang app sa split-screen."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Hindi sinusuportahan ng app ang split-screen."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-tr/strings.xml b/packages/SystemUI/res/values-tr/strings.xml
index 58d488c..02c0d59 100644
--- a/packages/SystemUI/res/values-tr/strings.xml
+++ b/packages/SystemUI/res/values-tr/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> uygulamasını kapat."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> kaldırıldı."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Tüm son uygulamalar kapatıldı."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> uygulaması bilgilerini açın."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> başlatılıyor."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Bildirim kapatıldı."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ses denetimi iletişim kutusu olarak ayarlandı"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Orijinali geri yüklemek için dokunun."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"İş profilinizi kullanıyorsunuz"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Sistem Arayüzü Ayarlayıcısı"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Yerleşik pil yüzdesini göster"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Şarj olmazken durum çubuğu simgesinin içinde pil düzeyi yüzdesini göster"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Yukarı taşı"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Sola taşı"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Sağa taşı"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Uygulama birden fazla pencerede çalışmayabilir"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>. konum, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Düzenlemek için iki kez hafifçe dokunun."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Eklemek için iki kez hafifçe dokunun."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"<xliff:g id="POSITION">%1$d</xliff:g>. konum. Seçmek için iki kez hafifçe dokunun."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> kaldırıldı"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> <xliff:g id="POSITION">%2$d</xliff:g>. konumuna taşındı"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Hızlı ayar düzenleyicisi."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Uygulama bölünmüş ekranda çalışmayabilir."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Uygulama bölünmüş ekranı desteklemiyor."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-uk/strings.xml b/packages/SystemUI/res/values-uk/strings.xml
index c75891c..a1b2ee1 100644
--- a/packages/SystemUI/res/values-uk/strings.xml
+++ b/packages/SystemUI/res/values-uk/strings.xml
@@ -170,8 +170,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Видалити додаток <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"Програму <xliff:g id="APP">%s</xliff:g> закрито."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Усі останні додатки закрито."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Відкрити інформацію про додаток <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Запуск додатка <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Сповіщення відхилено."</string>
@@ -423,6 +422,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> призначено регулятором гучності"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Торкніться, щоб відновити оригінал."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Ви в робочому профілі"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"System UI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Показувати заряд акумулятора у відсотках"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Показувати заряд акумулятора у відсотках в рядку стану, коли пристрій не заряджається"</string>
@@ -598,7 +603,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Перемістити вгору"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Перемістити ліворуч"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Перемістити праворуч"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Додаток може не працювати в багатовіконному режимі"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Позиція <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Двічі торкніться, щоб змінити."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Двічі торкніться, щоб додати."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Позиція <xliff:g id="POSITION">%1$d</xliff:g>. Двічі торкніться, щоб вибрати."</string>
@@ -608,4 +612,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> видалено"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> переміщено на позицію <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Редактор швидких налаштувань."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Додаток може не працювати в режимі розділеного екрана."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Додаток не підтримує розділення екрана."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-ur-rPK/strings.xml b/packages/SystemUI/res/values-ur-rPK/strings.xml
index 807a923..5c4ae9a 100644
--- a/packages/SystemUI/res/values-ur-rPK/strings.xml
+++ b/packages/SystemUI/res/values-ur-rPK/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"<xliff:g id="APP">%s</xliff:g> کو مسترد کریں۔"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> کو ہٹا دیا گیا۔"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"سبھی حالیہ ایپلیکیشنز کو برخاست کر دیا گیا۔"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ایپلیکیشن معلومات کھولیں۔"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> شروع ہو رہی ہے۔"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"اطلاع مسترد ہوگئی۔"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> والیوم ڈائلاگ ہے"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"اصل کو بحال کرنے کیلئے ٹچ کریں۔"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"آپ اپنا دفتری پروفائل استعمال کر رہے ہیں۔"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"‏سسٹم UI ٹیونر"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"سرایت کردہ بیٹری کی فیصد دکھائیں"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"جب چارج نہ ہو رہا ہو تو بیٹری کی سطح کی فیصد اسٹیٹس بار آئیکن کے اندر دکھائیں"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"اوپر منتقل کریں"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"بائیں منتقل کریں"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"دائیں منتقل کریں"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"ایپ شاید ملٹی ونڈو کے ساتھ کام نہ کرے"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"پوزیشن <xliff:g id="POSITION">%1$d</xliff:g>، <xliff:g id="TILE_NAME">%2$s</xliff:g>۔ ترمیم کرنے کیلئے دو بار تھپتھپائیں۔"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>۔ شامل کرنے کیلئے دو بار تھپتھپائیں۔"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"پوزیشن <xliff:g id="POSITION">%1$d</xliff:g>۔ منتخب کرنے کیلئے دو بار تھپتھپائیں۔"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> ہٹا دیا گیا"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="POSITION">%2$d</xliff:g> پوزیشن پر <xliff:g id="TILE_NAME">%1$s</xliff:g> منتقل ہو گیا ہے"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"فوری ترتیبات کا ایڈیٹر۔"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"ممکن ہے کہ ایپ سپلٹ اسکرین کے ساتھ کام نہ کرے۔"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"ایپ سپلٹ اسکرین کو سپورٹ نہیں کرتی۔"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-uz-rUZ/strings.xml b/packages/SystemUI/res/values-uz-rUZ/strings.xml
index fe67b52..27039d6 100644
--- a/packages/SystemUI/res/values-uz-rUZ/strings.xml
+++ b/packages/SystemUI/res/values-uz-rUZ/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Olib tashlash: <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> olib tashlangan."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Yaqinda ishlatilgan barcha ilovalar olib tashlandi."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"<xliff:g id="APP">%s</xliff:g> ilovasi haqidagi ma’lumotlarni ochadi."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"<xliff:g id="APP">%s</xliff:g> ishga tushirilmoqda."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Xabarnoma e‘tiborsiz qoldirildi."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> ovoz balandligini boshqaradi"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Aslini tiklash uchun bosing."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Siz ishchi profildan foydalanmoqdasiz"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"SystemUI Tuner"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Batareya foizi ko‘rsatilsin"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Batareya quvvat olmayotgan vaqtda uning foizi holat qatorida ko‘rsatilsin"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Tepaga siljitish"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Chapga siljitish"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"O‘ngga siljitish"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Ilova ko‘p oynali rejimni qo‘llab-quvvatlamaydi"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"<xliff:g id="POSITION">%1$d</xliff:g>-joy, “<xliff:g id="TILE_NAME">%2$s</xliff:g>” tugmasi. Tahrirlash uchun ustiga ikki marta bosing."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"“<xliff:g id="TILE_NAME">%1$s</xliff:g>” tugmasi. Qo‘shish uchun ustiga ikki marta bosing."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Joylashuv: <xliff:g id="POSITION">%1$d</xliff:g>. Belgilash uchun ustiga ikki marta bosing."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"“<xliff:g id="TILE_NAME">%1$s</xliff:g>” tugmasi o‘chirildi"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"“<xliff:g id="TILE_NAME">%1$s</xliff:g>” tugmasi endi <xliff:g id="POSITION">%2$d</xliff:g>-joyni egallanmoqda"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Tezkor sozlamalar muharriri"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Ilova ekranni ikkiga bo‘lish rejimini qo‘llab-quvvatlamaydi."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Bu ilova ekranni bo‘lish xususiyatini qo‘llab-quvvatlamaydi."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-vi/strings.xml b/packages/SystemUI/res/values-vi/strings.xml
index ca7c59b..ef87f01 100644
--- a/packages/SystemUI/res/values-vi/strings.xml
+++ b/packages/SystemUI/res/values-vi/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Xóa bỏ <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> đã bị loại bỏ."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Đã bỏ qua tất cả các ứng dụng gần đây."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Mở thông tin ứng dụng <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Bắt đầu <xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Đã loại bỏ thông báo."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"<xliff:g id="APP_NAME">%1$s</xliff:g> là hộp thoại khối lượng"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Chạm để khôi phục bản gốc."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Bạn đang sử dụng hồ sơ công việc của mình"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Bộ điều hướng giao diện người dùng hệ thống"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Hiển thị tỷ lệ phần trăm pin được nhúng"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Hiển thị tỷ lệ phần trăm mức pin bên trong biểu tượng thanh trạng thái khi không sạc"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Chuyển lên"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Di chuyển sang trái"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Di chuyển sang phải"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Ứng dụng có thể không hoạt động với nhiều cửa sổ"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Vị trí <xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Nhấn đúp để chỉnh sửa."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Nhấn đúp để thêm."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Vị trí <xliff:g id="POSITION">%1$d</xliff:g>. Nhấn đúp để chọn."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> được di chuyển"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> được di chuyển sang vị trí <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Trình chỉnh sửa cài đặt nhanh."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Ứng dụng có thể không hoạt động với tính năng chia đôi màn hình."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Ứng dụng không hỗ trợ chia đôi màn hình."</string>
 </resources>
diff --git a/packages/SystemUI/res/values-zh-rCN/strings.xml b/packages/SystemUI/res/values-zh-rCN/strings.xml
index a25b9f1..85c8bf6 100644
--- a/packages/SystemUI/res/values-zh-rCN/strings.xml
+++ b/packages/SystemUI/res/values-zh-rCN/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"移除<xliff:g id="APP">%s</xliff:g>。"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"已删除<xliff:g id="APP">%s</xliff:g>"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"已关闭所有最近用过的应用。"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"打开<xliff:g id="APP">%s</xliff:g>应用信息。"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"正在启动<xliff:g id="APP">%s</xliff:g>。"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"已关闭通知。"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"“<xliff:g id="APP_NAME">%1$s</xliff:g>”已用作音量控制对话框"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"触摸即可恢复原始设置。"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"您当前正在使用工作资料"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"系统界面调谐器"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"嵌入式显示电池电量百分比 显示嵌入的电池电量百分比"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"未充电时在状态栏图标内显示电池电量百分比"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"上移"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"左移"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"右移"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"应用可能无法在多窗口模式下正常运行"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"位置 <xliff:g id="POSITION">%1$d</xliff:g>,<xliff:g id="TILE_NAME">%2$s</xliff:g>。点按两次即可修改。"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>。点按两次即可添加。"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"位置 <xliff:g id="POSITION">%1$d</xliff:g>。点按两次即可选择。"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"已移除<xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"已将<xliff:g id="TILE_NAME">%1$s</xliff:g>移至位置 <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"快捷设置编辑器。"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"应用可能无法在分屏模式下正常运行。"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"应用不支持分屏。"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-zh-rHK/strings.xml b/packages/SystemUI/res/values-zh-rHK/strings.xml
index 083cd5e..4d5e495 100644
--- a/packages/SystemUI/res/values-zh-rHK/strings.xml
+++ b/packages/SystemUI/res/values-zh-rHK/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"關閉「<xliff:g id="APP">%s</xliff:g>」。"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"「<xliff:g id="APP">%s</xliff:g>」已關閉。"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"所有最近使用的應用程式均已關閉。"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"開啟「<xliff:g id="APP">%s</xliff:g>」應用程式的資料。"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"正在啟動「<xliff:g id="APP">%s</xliff:g>」。"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g><xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"通知已關閉。"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"「<xliff:g id="APP_NAME">%1$s</xliff:g>」為音量對話框"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"輕觸即可復原。"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"您正在使用工作設定檔"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"系統使用者介面調諧器"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"顯示嵌入的電池百分比"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"非充電時,在狀態列圖示顯示電量百分比"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"向上移"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"向左移"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"向右移"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"應用程式可能無法在多重視窗下運作"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"位置 <xliff:g id="POSITION">%1$d</xliff:g>,<xliff:g id="TILE_NAME">%2$s</xliff:g>。輕按兩下即可編輯。"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>。輕按兩下即可新增。"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"位置 <xliff:g id="POSITION">%1$d</xliff:g>。輕按兩下即可選取。"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"<xliff:g id="TILE_NAME">%1$s</xliff:g> 已移除"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"<xliff:g id="TILE_NAME">%1$s</xliff:g> 已移至位置 <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"快速設定編輯工具。"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"應用程式可能無法在分割畫面中運作。"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"應用程式不支援分割畫面。"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-zh-rTW/strings.xml b/packages/SystemUI/res/values-zh-rTW/strings.xml
index 3c95a93..6d15234 100644
--- a/packages/SystemUI/res/values-zh-rTW/strings.xml
+++ b/packages/SystemUI/res/values-zh-rTW/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"關閉「<xliff:g id="APP">%s</xliff:g>」。"</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"「<xliff:g id="APP">%s</xliff:g>」已關閉。"</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"最近使用的應用程式已全部關閉。"</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"開啟「<xliff:g id="APP">%s</xliff:g>」應用程式資訊。"</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"正在啟動「<xliff:g id="APP">%s</xliff:g>」。"</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"已關閉通知。"</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"「<xliff:g id="APP_NAME">%1$s</xliff:g>」現在是預設的音量控制對話方塊。"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"輕觸這裡即可恢復原始設定。"</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"您正在使用 Work 設定檔"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"系統使用者介面調整精靈"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"顯示嵌入式電池百分比"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"未充電時在狀態列圖示中顯示電量百分比"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"向上移"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"向左移"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"向右移"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"應用程式可能無法在多視窗模式下運作"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"位置 <xliff:g id="POSITION">%1$d</xliff:g>,<xliff:g id="TILE_NAME">%2$s</xliff:g>。輕按兩下即可編輯。"</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>。輕按兩下即可新增。"</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"位置 <xliff:g id="POSITION">%1$d</xliff:g>。輕按兩下即可選取。"</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"已移除 <xliff:g id="TILE_NAME">%1$s</xliff:g>"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"已將 <xliff:g id="TILE_NAME">%1$s</xliff:g> 移到位置 <xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"快速設定編輯器。"</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"應用程式可能無法在分割畫面中運作。"</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"這個應用程式不支援分割畫面。"</string>
 </resources>
diff --git a/packages/SystemUI/res/values-zu/strings.xml b/packages/SystemUI/res/values-zu/strings.xml
index e03e642..4d63511 100644
--- a/packages/SystemUI/res/values-zu/strings.xml
+++ b/packages/SystemUI/res/values-zu/strings.xml
@@ -168,8 +168,7 @@
     <string name="accessibility_recents_item_will_be_dismissed" msgid="395770242498031481">"Cashisa i-<xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_dismissed" msgid="6803574935084867070">"<xliff:g id="APP">%s</xliff:g> ivaliwe."</string>
     <string name="accessibility_recents_all_items_dismissed" msgid="4464697366179168836">"Zonke izinhlelo zokusebenza zakamuva zicashisiwe."</string>
-    <!-- no translation found for accessibility_recents_item_open_app_info (5107479759905883540) -->
-    <skip />
+    <string name="accessibility_recents_item_open_app_info" msgid="5107479759905883540">"Vula ulwazi lohlelo lokusebenza le-<xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_item_launched" msgid="7616039892382525203">"Iqala i-<xliff:g id="APP">%s</xliff:g>."</string>
     <string name="accessibility_recents_task_header" msgid="1437183540924535457">"<xliff:g id="APP">%1$s</xliff:g> <xliff:g id="ACTIVITY_LABEL">%2$s</xliff:g>"</string>
     <string name="accessibility_notification_dismissed" msgid="854211387186306927">"Isaziso sichithiwe."</string>
@@ -421,6 +420,12 @@
     <string name="volumeui_notification_title" msgid="4906770126345910955">"I-<xliff:g id="APP_NAME">%1$s</xliff:g> yingxoxo yevolumu"</string>
     <string name="volumeui_notification_text" msgid="1826889705095768656">"Thinta ukuze ubuyisele kokwangempela."</string>
     <string name="managed_profile_foreground_toast" msgid="5421487114739245972">"Usebenzisa iphrofayela yakho yomsebenzi"</string>
+    <!-- no translation found for volume_stream_content_description_unmute (4436631538779230857) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_vibrate (1187944970457807498) -->
+    <skip />
+    <!-- no translation found for volume_stream_content_description_mute (3625049841390467354) -->
+    <skip />
     <string name="system_ui_tuner" msgid="708224127392452018">"Isishuni se-UI yesistimu"</string>
     <string name="show_battery_percentage" msgid="5444136600512968798">"Bonisa amaphesenti ebhethri elinamathiselwe"</string>
     <string name="show_battery_percentage_summary" msgid="3215025775576786037">"Bonisa amaphesenti eleveli yebhethri ngaphakathi kwesithonjana sebha yesimo uma kungashajwa"</string>
@@ -596,7 +601,6 @@
     <string name="accessibility_action_divider_move_up" msgid="4580103171609248006">"Iya phezulu"</string>
     <string name="accessibility_action_divider_move_left" msgid="9218189832115847253">"Iya kwesokunxele"</string>
     <string name="accessibility_action_divider_move_right" msgid="4671522715182567972">"Iya kwesokudla"</string>
-    <string name="forced_resizable_info_text" msgid="7591061837558867999">"Uhlelo lokusebenza kungenzeka lungasebenzi namawindi amaningi"</string>
     <string name="accessibility_qs_edit_tile_label" msgid="8374924053307764245">"Isimo esingu-<xliff:g id="POSITION">%1$d</xliff:g>, <xliff:g id="TILE_NAME">%2$s</xliff:g>. Thepha kabili ukuze uhlele."</string>
     <string name="accessibility_qs_edit_add_tile_label" msgid="8133209638023882667">"<xliff:g id="TILE_NAME">%1$s</xliff:g>. Thepha kabili ukuze ungeze."</string>
     <string name="accessibility_qs_edit_position_label" msgid="5055306305919289819">"Isimo esingu-<xliff:g id="POSITION">%1$d</xliff:g>. Thepha kabili ukuze ukhethe."</string>
@@ -606,4 +610,6 @@
     <string name="accessibility_qs_edit_tile_removed" msgid="8584304916627913440">"I-<xliff:g id="TILE_NAME">%1$s</xliff:g> isusiwe"</string>
     <string name="accessibility_qs_edit_tile_moved" msgid="4343693412689365038">"I-<xliff:g id="TILE_NAME">%1$s</xliff:g> ihanjiswe kusimo esingu-<xliff:g id="POSITION">%2$d</xliff:g>"</string>
     <string name="accessibility_desc_quick_settings_edit" msgid="8073587401747016103">"Isihleli sezilungiselelo ezisheshayo."</string>
+    <string name="dock_forced_resizable" msgid="5914261505436217520">"Izinhlelo zokusebenza kungenzeka zingasebenzi ngesikrini esihlukanisiwe."</string>
+    <string name="dock_non_resizeble_failed_to_dock_text" msgid="3871617304250207291">"Uhlelo lokusebenza alusekeli isikrini esihlukanisiwe."</string>
 </resources>
diff --git a/packages/SystemUI/res/values/attrs.xml b/packages/SystemUI/res/values/attrs.xml
index 6dd8c52..1543360 100644
--- a/packages/SystemUI/res/values/attrs.xml
+++ b/packages/SystemUI/res/values/attrs.xml
@@ -53,10 +53,14 @@
         <enum name="vertical" value="1" />
     </attr>
     <declare-styleable name="UserAvatarView">
+        <attr name="avatarPadding" format="dimension" />
         <attr name="frameWidth" format="dimension" />
         <attr name="framePadding" format="dimension" />
+        <!-- {@deprecated Use a statelist in frameColor instead.} -->
         <attr name="activeFrameColor" format="color" />
-        <attr name="frameColor" />
+        <attr name="frameColor" format="color" />
+        <attr name="badgeDiameter" format="dimension" />
+        <attr name="badgeMargin" format="dimension" />
     </declare-styleable>
     <declare-styleable name="UserDetailItemView">
         <attr name="regularFontFamily" format="string" />
diff --git a/packages/SystemUI/res/values/colors.xml b/packages/SystemUI/res/values/colors.xml
index b874e7c..18fc419 100644
--- a/packages/SystemUI/res/values/colors.xml
+++ b/packages/SystemUI/res/values/colors.xml
@@ -151,7 +151,7 @@
 
     <color name="docked_divider_background">#ff000000</color>
     <color name="docked_divider_handle">#ffffff</color>
-    <drawable name="forced_resizable_background">#80000000</drawable>
+    <drawable name="forced_resizable_background">#40000000</drawable>
 
     <color name="default_remote_input_background">@*android:color/notification_default_color</color>
     <color name="remote_input_hint">#99ffffff</color>
@@ -166,11 +166,11 @@
     <color name="switch_accent_color">#ff7fcac3</color>
 
     <!-- Keyboard shortcuts colors -->
-    <color name="ksh_system_group_color">#ff00bcd4</color>
+    <color name="ksh_system_group_color">@color/material_deep_teal_500</color>
     <color name="ksh_application_group_color">#fff44336</color>
     <color name="ksh_keyword_color">#d9000000</color>
     <color name="ksh_key_item_color">@color/material_grey_600</color>
-    <color name="ksh_key_item_background">#eeeeee</color>
+    <color name="ksh_key_item_background">@color/material_grey_100</color>
 
     <!-- Background color of edit overflow -->
     <color name="qs_edit_overflow_bg">#455A64</color>
diff --git a/packages/SystemUI/res/values/config_tv.xml b/packages/SystemUI/res/values/config_tv.xml
index 22b7578..40e3b12 100644
--- a/packages/SystemUI/res/values/config_tv.xml
+++ b/packages/SystemUI/res/values/config_tv.xml
@@ -16,6 +16,10 @@
 
 <resources>
     <!-- Bounds [left top right bottom] on screen for picture-in-picture (PIP) windows,
+         when the PIP menu is shown with settings. -->
+    <string translatable="false" name="pip_settings_bounds">"662 54 1142 324"</string>
+
+    <!-- Bounds [left top right bottom] on screen for picture-in-picture (PIP) windows,
          when the PIP menu is shown in center. -->
     <string translatable="false" name="pip_menu_bounds">"596 280 1324 690"</string>
 
diff --git a/packages/SystemUI/res/values/dimens.xml b/packages/SystemUI/res/values/dimens.xml
index a4eadbf..cf2e338 100644
--- a/packages/SystemUI/res/values/dimens.xml
+++ b/packages/SystemUI/res/values/dimens.xml
@@ -388,6 +388,9 @@
          quick settings header -->
     <dimen name="max_avatar_size">48dp</dimen>
 
+    <!-- Size of user icon + frame in the qs/keyguard user picker (incl. frame) -->
+    <dimen name="framed_avatar_size">54dp</dimen>
+
     <!-- Margin on the left side of the carrier text on Keyguard -->
     <dimen name="keyguard_carrier_text_margin">16dp</dimen>
 
diff --git a/packages/SystemUI/res/values/strings.xml b/packages/SystemUI/res/values/strings.xml
index 060e050..dc9ffa9 100644
--- a/packages/SystemUI/res/values/strings.xml
+++ b/packages/SystemUI/res/values/strings.xml
@@ -735,10 +735,8 @@
     <string name="recents_launch_disabled_message"><xliff:g id="app" example="Calendar">%s</xliff:g> is disabled in safe-mode.</string>
     <!-- Recents: Stack action button string. [CHAR LIMIT=NONE] -->
     <string name="recents_stack_action_button_label">Clear all</string>
-    <!-- Recents: Non-dockable task drag message. [CHAR LIMIT=NONE] -->
-    <string name="recents_drag_non_dockable_task_message">This app does not support multi-window</string>
-    <!-- Recents: Non-dockable task launch sub header. [CHAR LIMIT=NONE] -->
-    <string name="recents_launch_non_dockable_task_label">App does not support multi-window</string>
+    <!-- Recents: Incompatible task message. [CHAR LIMIT=NONE] -->
+    <string name="recents_incompatible_app_message">App doesn\'t support split screen</string>
 
     <!-- Recents: MultiStack add stack split horizontal radio button. [CHAR LIMIT=NONE] -->
     <string name="recents_multistack_add_stack_dialog_split_horizontal">Split Horizontal</string>
@@ -1082,6 +1080,10 @@
     <string name="volume_stream_limited_dnd" translatable="false">%s — Priority only</string>
     <string name="volume_stream_vibrate_dnd" translatable="false">%s vibrate — Priority only</string>
 
+    <string name="volume_stream_content_description_unmute">%1$s. Tap to unmute.</string>
+    <string name="volume_stream_content_description_vibrate">%1$s. Tap to set to vibrate. Accessibility services may be muted.</string>
+    <string name="volume_stream_content_description_mute">%1$s. Tap to mute. Accessibility services may be muted.</string>
+
     <!-- Name of special SystemUI debug settings -->
     <string name="system_ui_tuner">System UI Tuner</string>
 
@@ -1557,9 +1559,6 @@
     <!-- Accessibility action for moving down the docked stack divider [CHAR LIMIT=NONE] -->
     <string name="accessibility_action_divider_move_right">Move right</string>
 
-    <!-- Text that gets shown on top of current activity to inform the user that the system force-resized the current activity and that things might crash/not work properly [CHAR LIMIT=NONE] -->
-    <string name="forced_resizable_info_text">App may not work with multi-window</string>
-
     <!-- Accessibility description of a QS tile while editing positions [CHAR LIMIT=NONE] -->
     <string name="accessibility_qs_edit_tile_label">Position <xliff:g id="position" example="2">%1$d</xliff:g>, <xliff:g id="tile_name" example="Wi-Fi">%2$s</xliff:g>. Double tap to edit.</string>
 
@@ -1587,4 +1586,13 @@
     <!-- Accessibility label for window when QS editing is happening [CHAR LIMIT=NONE] -->
     <string name="accessibility_desc_quick_settings_edit">Quick settings editor.</string>
 
+    <!-- Multi-Window strings -->
+    <!-- Text that gets shown on top of current activity to inform the user that the system force-resized the current activity and that things might crash/not work properly [CHAR LIMIT=NONE] -->
+    <string name="dock_forced_resizable">App may not work with split-screen.</string>
+    <!-- Warning message when we try to dock a non-resizeble tasks and launch it in fullscreen instead. -->
+    <string name="dock_non_resizeble_failed_to_dock_text">App does not support split-screen.</string>
+
+    <!-- accessibility label for button to expand quick settings [CHAR LIMIT=NONE] -->
+    <string name="accessibility_quick_settings_expand">Expand quick settings.</string>
+
 </resources>
diff --git a/packages/SystemUI/res/values/styles.xml b/packages/SystemUI/res/values/styles.xml
index 5db35b1..f560a13 100644
--- a/packages/SystemUI/res/values/styles.xml
+++ b/packages/SystemUI/res/values/styles.xml
@@ -49,6 +49,9 @@
 
     <style name="Animation.ForcedResizable" parent="@android:style/Animation">
         <item name="android:activityOpenEnterAnimation">@anim/forced_resizable_enter</item>
+
+        <!-- If the target stack doesn't have focus, we do a task to front animation. -->
+        <item name="android:taskToFrontEnterAnimation">@anim/forced_resizable_enter</item>
         <item name="android:activityCloseExitAnimation">@anim/forced_resizable_exit</item>
     </style>
 
diff --git a/packages/SystemUI/src/com/android/systemui/BatteryMeterDrawable.java b/packages/SystemUI/src/com/android/systemui/BatteryMeterDrawable.java
index 087f61e..076b5bc 100755
--- a/packages/SystemUI/src/com/android/systemui/BatteryMeterDrawable.java
+++ b/packages/SystemUI/src/com/android/systemui/BatteryMeterDrawable.java
@@ -37,7 +37,7 @@
 
 import com.android.systemui.statusbar.policy.BatteryController;
 
-public class BatteryMeterDrawable extends Drawable implements DemoMode,
+public class BatteryMeterDrawable extends Drawable implements
         BatteryController.BatteryStateChangeCallback {
 
     private static final float ASPECT_RATIO = 9.5f / 14.5f;
@@ -184,14 +184,12 @@
         mContext.getContentResolver().registerContentObserver(
                 Settings.System.getUriFor(SHOW_PERCENT_SETTING), false, mSettingObserver);
         updateShowPercent();
-        if (mDemoMode) return;
         mBatteryController.addStateChangedCallback(this);
     }
 
     public void stopListening() {
         mListening = false;
         mContext.getContentResolver().unregisterContentObserver(mSettingObserver);
-        if (mDemoMode) return;
         mBatteryController.removeStateChangedCallback(this);
     }
 
@@ -507,35 +505,6 @@
         return 0;
     }
 
-    private boolean mDemoMode;
-
-    @Override
-    public void dispatchDemoCommand(String command, Bundle args) {
-        if (!mDemoMode && command.equals(COMMAND_ENTER)) {
-            mBatteryController.removeStateChangedCallback(this);
-            mDemoMode = true;
-            if (mListening) {
-                mBatteryController.removeStateChangedCallback(this);
-            }
-        } else if (mDemoMode && command.equals(COMMAND_EXIT)) {
-            mDemoMode = false;
-            postInvalidate();
-            if (mListening) {
-                mBatteryController.addStateChangedCallback(this);
-            }
-        } else if (mDemoMode && command.equals(COMMAND_BATTERY)) {
-           String level = args.getString("level");
-           String plugged = args.getString("plugged");
-           if (level != null) {
-               mLevel = Math.min(Math.max(Integer.parseInt(level), 0), 100);
-           }
-           if (plugged != null) {
-               mPluggedIn = Boolean.parseBoolean(plugged);
-           }
-           postInvalidate();
-        }
-    }
-
     private final class SettingObserver extends ContentObserver {
         public SettingObserver() {
             super(new Handler());
diff --git a/packages/SystemUI/src/com/android/systemui/BitmapHelper.java b/packages/SystemUI/src/com/android/systemui/BitmapHelper.java
deleted file mode 100644
index 1933bbc..0000000
--- a/packages/SystemUI/src/com/android/systemui/BitmapHelper.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.systemui;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapShader;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.RectF;
-import android.graphics.Shader;
-
-public class BitmapHelper {
-    /**
-     * Generate a new bitmap (width x height pixels, ARGB_8888) with the input bitmap scaled
-     * to fit and clipped to an inscribed circle.
-     * @param input Bitmap to resize and clip
-     * @param width Width of output bitmap (and diameter of circle)
-     * @param height Height of output bitmap
-     * @return A shiny new bitmap for you to use
-     */
-    public static Bitmap createCircularClip(Bitmap input, int width, int height) {
-        if (input == null) return null;
-
-        final int inWidth = input.getWidth();
-        final int inHeight = input.getHeight();
-        final Bitmap output = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
-        final Canvas canvas = new Canvas(output);
-        final Paint paint = new Paint();
-        paint.setShader(new BitmapShader(input, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP));
-        paint.setAntiAlias(true);
-        final RectF srcRect = new RectF(0, 0, inWidth, inHeight);
-        final RectF dstRect = new RectF(0, 0, width, height);
-        final Matrix m = new Matrix();
-        m.setRectToRect(srcRect, dstRect, Matrix.ScaleToFit.CENTER);
-        canvas.setMatrix(m);
-        canvas.drawCircle(inWidth / 2, inHeight / 2, inWidth / 2, paint);
-        return output;
-    }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/classifier/FalsingManager.java b/packages/SystemUI/src/com/android/systemui/classifier/FalsingManager.java
index 0d822cb..0798590 100644
--- a/packages/SystemUI/src/com/android/systemui/classifier/FalsingManager.java
+++ b/packages/SystemUI/src/com/android/systemui/classifier/FalsingManager.java
@@ -250,7 +250,6 @@
             FalsingLog.i("onSucccessfulUnlock", "");
         }
         mDataCollector.onSucccessfulUnlock();
-        sessionExitpoint(true /* force */);
     }
 
     public void onBouncerShown() {
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java
index 66754a7..f892fd6 100644
--- a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java
+++ b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java
@@ -847,17 +847,16 @@
 
     private void doKeyguardLaterForChildProfilesLocked() {
         UserManager um = UserManager.get(mContext);
-        List<UserInfo> profiles = um.getEnabledProfiles(UserHandle.myUserId());
-        for (UserInfo info : profiles) {
-            if (mLockPatternUtils.isSeparateProfileChallengeEnabled(info.id)) {
-                long userTimeout = getLockTimeout(info.id);
+        for (int profileId : um.getEnabledProfileIds(UserHandle.myUserId())) {
+            if (mLockPatternUtils.isSeparateProfileChallengeEnabled(profileId)) {
+                long userTimeout = getLockTimeout(profileId);
                 if (userTimeout == 0) {
                     doKeyguardForChildProfilesLocked();
                 } else {
                     long userWhen = SystemClock.elapsedRealtime() + userTimeout;
                     Intent lockIntent = new Intent(DELAYED_LOCK_PROFILE_ACTION);
                     lockIntent.putExtra("seq", mDelayedProfileShowingSequence);
-                    lockIntent.putExtra(Intent.EXTRA_USER_ID, info.id);
+                    lockIntent.putExtra(Intent.EXTRA_USER_ID, profileId);
                     PendingIntent lockSender = PendingIntent.getBroadcast(
                             mContext, 0, lockIntent, PendingIntent.FLAG_CANCEL_CURRENT);
                     mAlarmManager.setExactAndAllowWhileIdle(AlarmManager.ELAPSED_REALTIME_WAKEUP,
@@ -869,10 +868,9 @@
 
     private void doKeyguardForChildProfilesLocked() {
         UserManager um = UserManager.get(mContext);
-        List<UserInfo> profiles = um.getEnabledProfiles(UserHandle.myUserId());
-        for (UserInfo info : profiles) {
-            if (mLockPatternUtils.isSeparateProfileChallengeEnabled(info.id)) {
-                lockProfile(info.id);
+        for (int profileId : um.getEnabledProfileIds(UserHandle.myUserId())) {
+            if (mLockPatternUtils.isSeparateProfileChallengeEnabled(profileId)) {
+                lockProfile(profileId);
             }
         }
     }
@@ -1482,9 +1480,8 @@
                 final UserHandle currentUser = new UserHandle(KeyguardUpdateMonitor.getCurrentUser());
                 final UserManager um = (UserManager) mContext.getSystemService(
                         Context.USER_SERVICE);
-                List <UserInfo> userHandles = um.getProfiles(currentUser.getIdentifier());
-                for (UserInfo ui : userHandles) {
-                    mContext.sendBroadcastAsUser(USER_PRESENT_INTENT, ui.getUserHandle());
+                for (int profileId : um.getProfileIdsWithDisabled(currentUser.getIdentifier())) {
+                    mContext.sendBroadcastAsUser(USER_PRESENT_INTENT, UserHandle.of(profileId));
                 }
             } else {
                 mBootSendUserPresent = true;
diff --git a/packages/SystemUI/src/com/android/systemui/qs/PageIndicator.java b/packages/SystemUI/src/com/android/systemui/qs/PageIndicator.java
index ba07bf4..5cb46ac 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/PageIndicator.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/PageIndicator.java
@@ -118,6 +118,10 @@
         }
         ImageView first = (ImageView) getChildAt(firstIndex);
         ImageView second = (ImageView) getChildAt(secondIndex);
+        if (second == null) {
+            // Weird state where number of pages must not have propagated yet.
+            return;
+        }
         // Lay the two views on top of each other.
         second.setTranslationX(first.getX() - second.getX());
 
diff --git a/packages/SystemUI/src/com/android/systemui/qs/QSAnimator.java b/packages/SystemUI/src/com/android/systemui/qs/QSAnimator.java
index 4d959d8..af81c19 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/QSAnimator.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/QSAnimator.java
@@ -87,6 +87,7 @@
 
     public void setOnKeyguard(boolean onKeyguard) {
         mOnKeyguard = onKeyguard;
+        mQuickQsPanel.setVisibility(mOnKeyguard ? View.INVISIBLE : View.VISIBLE);
         if (mOnKeyguard) {
             clearAnimationState();
         }
@@ -290,7 +291,7 @@
 
     @Override
     public void onAnimationStarted() {
-        mQuickQsPanel.setVisibility(View.VISIBLE);
+        mQuickQsPanel.setVisibility(mOnKeyguard ? View.INVISIBLE : View.VISIBLE);
         if (mOnFirstPage) {
             final int N = mTopFiveQs.size();
             for (int i = 0; i < N; i++) {
@@ -302,12 +303,11 @@
     private void clearAnimationState() {
         final int N = mAllViews.size();
         mQuickQsPanel.setAlpha(0);
-        mQuickQsPanel.setVisibility(View.VISIBLE);
         for (int i = 0; i < N; i++) {
             View v = mAllViews.get(i);
             v.setAlpha(1);
-            v.setTranslationX(1);
-            v.setTranslationY(1);
+            v.setTranslationX(0);
+            v.setTranslationY(0);
         }
         final int N2 = mTopFiveQs.size();
         for (int i = 0; i < N2; i++) {
diff --git a/packages/SystemUI/src/com/android/systemui/qs/QSContainer.java b/packages/SystemUI/src/com/android/systemui/qs/QSContainer.java
index e3a4909..ef75562 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/QSContainer.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/QSContainer.java
@@ -70,8 +70,8 @@
         super.onFinishInflate();
         mQSPanel = (QSPanel) findViewById(R.id.quick_settings_panel);
         mQSDetail = (QSDetail) findViewById(R.id.qs_detail);
-        mQSDetail.setQsPanel(mQSPanel);
         mHeader = (BaseStatusBarHeader) findViewById(R.id.header);
+        mQSDetail.setQsPanel(mQSPanel, mHeader);
         mQSAnimator = new QSAnimator(this, (QuickQSPanel) mHeader.findViewById(R.id.quick_qs_panel),
                 mQSPanel);
         mQSCustomizer = (QSCustomizer) findViewById(R.id.qs_customize);
diff --git a/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java b/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java
index 50c0cca..0cf7e479 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/QSDetail.java
@@ -35,6 +35,7 @@
 import com.android.systemui.FontSizeUtils;
 import com.android.systemui.R;
 import com.android.systemui.qs.QSTile.DetailAdapter;
+import com.android.systemui.statusbar.phone.BaseStatusBarHeader;
 import com.android.systemui.statusbar.phone.QSTileHost;
 
 public class QSDetail extends LinearLayout {
@@ -62,6 +63,7 @@
     private boolean mClosingDetail;
     private boolean mFullyExpanded;
     private View mQsDetailHeaderBack;
+    private BaseStatusBarHeader mHeader;
 
     public QSDetail(Context context, @Nullable AttributeSet attrs) {
         super(context, attrs);
@@ -107,8 +109,9 @@
         mDetailDoneButton.setOnClickListener(doneListener);
     }
 
-    public void setQsPanel(QSPanel panel) {
+    public void setQsPanel(QSPanel panel, BaseStatusBarHeader header) {
         mQsPanel = panel;
+        mHeader = header;
         mQsPanel.setCallback(mQsPanelCallback);
     }
 
@@ -195,6 +198,7 @@
             mClosingDetail = true;
             mDetailAdapter = null;
             listener = mTeardownDetailWhenDone;
+            mHeader.setVisibility(View.VISIBLE);
             mQsPanel.setGridContentVisibility(true);
             mQsPanelCallback.onScanStateChanged(false);
         }
@@ -273,6 +277,7 @@
             // Only hide content if still in detail state.
             if (mDetailAdapter != null) {
                 mQsPanel.setGridContentVisibility(false);
+                mHeader.setVisibility(View.INVISIBLE);
             }
         }
     };
diff --git a/packages/SystemUI/src/com/android/systemui/qs/QSTileBaseView.java b/packages/SystemUI/src/com/android/systemui/qs/QSTileBaseView.java
index 9e40cfd..44b38f1 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/QSTileBaseView.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/QSTileBaseView.java
@@ -93,6 +93,12 @@
         }
     }
 
+    @Override
+    public boolean hasOverlappingRendering() {
+        // Avoid layers for this layout - we don't need them.
+        return false;
+    }
+
     /**
      * Update the accessibility order for this view.
      *
diff --git a/packages/SystemUI/src/com/android/systemui/qs/external/CustomTile.java b/packages/SystemUI/src/com/android/systemui/qs/external/CustomTile.java
index 6114573..6b20681 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/external/CustomTile.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/external/CustomTile.java
@@ -138,7 +138,7 @@
         mListening = listening;
         try {
             if (listening) {
-                if (mServiceManager.getType() == TileService.TILE_MODE_PASSIVE) {
+                if (!mServiceManager.isActiveTile()) {
                     mServiceManager.setBindRequested(true);
                     mService.onStartListening();
                 }
@@ -209,7 +209,7 @@
         } catch (RemoteException e) {
         }
         try {
-            if (mServiceManager.getType() == TileService.TILE_MODE_ACTIVE) {
+            if (mServiceManager.isActiveTile()) {
                 mServiceManager.setBindRequested(true);
                 mService.onStartListening();
             }
diff --git a/packages/SystemUI/src/com/android/systemui/qs/external/TileLifecycleManager.java b/packages/SystemUI/src/com/android/systemui/qs/external/TileLifecycleManager.java
index 8910d44..5a26a4a 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/external/TileLifecycleManager.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/external/TileLifecycleManager.java
@@ -15,8 +15,6 @@
  */
 package com.android.systemui.qs.external;
 
-import libcore.util.Objects;
-
 import android.app.AppGlobals;
 import android.content.BroadcastReceiver;
 import android.content.ComponentName;
@@ -25,6 +23,7 @@
 import android.content.IntentFilter;
 import android.content.ServiceConnection;
 import android.content.pm.PackageManager;
+import android.content.pm.PackageManager.NameNotFoundException;
 import android.content.pm.ServiceInfo;
 import android.net.Uri;
 import android.os.Handler;
@@ -34,9 +33,11 @@
 import android.service.quicksettings.IQSService;
 import android.service.quicksettings.IQSTileService;
 import android.service.quicksettings.Tile;
+import android.service.quicksettings.TileService;
 import android.support.annotation.VisibleForTesting;
 import android.util.ArraySet;
 import android.util.Log;
+import libcore.util.Objects;
 
 import java.util.Set;
 
@@ -98,6 +99,17 @@
         }
     }
 
+    public boolean isActiveTile() {
+        try {
+            ServiceInfo info = mContext.getPackageManager().getServiceInfo(mIntent.getComponent(),
+                    PackageManager.MATCH_UNINSTALLED_PACKAGES | PackageManager.GET_META_DATA);
+            return info.metaData != null
+                    && info.metaData.getBoolean(TileService.META_DATA_ACTIVE_TILE, false);
+        } catch (NameNotFoundException e) {
+            return false;
+        }
+    }
+
     /**
      * Binds just long enough to send any queued messages, then unbinds.
      */
diff --git a/packages/SystemUI/src/com/android/systemui/qs/external/TileServiceManager.java b/packages/SystemUI/src/com/android/systemui/qs/external/TileServiceManager.java
index 664ddd6..f34df75 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/external/TileServiceManager.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/external/TileServiceManager.java
@@ -16,14 +16,18 @@
 package com.android.systemui.qs.external;
 
 import android.app.ActivityManager;
+import android.content.BroadcastReceiver;
 import android.content.ComponentName;
+import android.content.Context;
 import android.content.Intent;
+import android.content.IntentFilter;
+import android.net.Uri;
 import android.os.Handler;
 import android.os.UserHandle;
 import android.service.quicksettings.IQSTileService;
-import android.service.quicksettings.TileService;
 import android.support.annotation.VisibleForTesting;
 import android.util.Log;
+import libcore.util.Objects;
 
 /**
  * Manages the priority which lets {@link TileServices} make decisions about which tiles
@@ -51,7 +55,6 @@
     private int mPriority;
     private boolean mJustBound;
     private long mLastUpdate;
-    private int mType;
     private boolean mShowingDialog;
     // Whether we have a pending bind going out to the service without a response yet.
     // This defaults to true to ensure tiles start out unavailable.
@@ -69,25 +72,17 @@
         mServices = tileServices;
         mHandler = handler;
         mStateManager = tileLifecycleManager;
-        mType = tileServices.getContext().getSharedPreferences(PREFS_FILE, 0)
-                .getInt(tileLifecycleManager.getComponent().flattenToString(),
-                        TileService.TILE_MODE_UNSET);
         mStateManager.setQSService(tileServices);
-        if (mType == TileService.TILE_MODE_UNSET) {
-            bindService();
-            mStateManager.onTileAdded();
-        }
+
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
+        filter.addDataScheme("package");
+        mServices.getContext().registerReceiverAsUser(mUninstallReceiver,
+                new UserHandle(ActivityManager.getCurrentUser()), filter, null, mHandler);
     }
 
-    public int getType() {
-        return mType;
-    }
-
-    public void setType(int type) {
-        mServices.getContext().getSharedPreferences(PREFS_FILE, 0).edit()
-                .putInt(mStateManager.getComponent().flattenToString(), type).commit();
-        mType = type;
-        mServices.recalculateBindAllowance();
+    public boolean isActiveTile() {
+        return mStateManager.isActiveTile();
     }
 
     public void setShowingDialog(boolean dialog) {
@@ -114,7 +109,7 @@
 
     public void setLastUpdate(long lastUpdate) {
         mLastUpdate = lastUpdate;
-        if (mBound && mType == TileService.TILE_MODE_ACTIVE) {
+        if (mBound && isActiveTile()) {
             mStateManager.onStopListening();
             setBindRequested(false);
         }
@@ -122,6 +117,7 @@
     }
 
     public void handleDestroy() {
+        mServices.getContext().unregisterReceiver(mUninstallReceiver);
         mStateManager.handleDestroy();
     }
 
@@ -214,4 +210,23 @@
             mServices.recalculateBindAllowance();
         }
     };
+
+    private final BroadcastReceiver mUninstallReceiver = new BroadcastReceiver() {
+        @Override
+        public void onReceive(Context context, Intent intent) {
+            if (!Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction())) {
+                return;
+            }
+            if (intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) {
+                return;
+            }
+            Uri data = intent.getData();
+            String pkgName = data.getEncodedSchemeSpecificPart();
+            final ComponentName component = mStateManager.getComponent();
+            if (!Objects.equal(pkgName, component.getPackageName())) {
+                return;
+            }
+            mServices.getHost().removeTile(component);
+        }
+    };
 }
diff --git a/packages/SystemUI/src/com/android/systemui/qs/external/TileServices.java b/packages/SystemUI/src/com/android/systemui/qs/external/TileServices.java
index 5bb2a35..2ab6b5f 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/external/TileServices.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/external/TileServices.java
@@ -72,6 +72,10 @@
         return mContext;
     }
 
+    public QSTileHost getHost() {
+        return mHost;
+    }
+
     public TileServiceManager getTileWrapper(CustomTile tile) {
         ComponentName component = tile.getComponent();
         TileServiceManager service = onCreateTileService(component);
@@ -89,6 +93,7 @@
     public void freeService(CustomTile tile, TileServiceManager service) {
         synchronized (mServices) {
             service.setBindAllowed(false);
+            service.handleDestroy();
             mServices.remove(tile);
             mTiles.remove(tile.getComponent());
             final String slot = tile.getComponent().getClassName();
@@ -153,7 +158,7 @@
                 return;
             }
             TileServiceManager service = mServices.get(customTile);
-            if (service.getType() != TileService.TILE_MODE_ACTIVE) {
+            if (!service.isActiveTile()) {
                 return;
             }
             service.setBindRequested(true);
@@ -165,17 +170,6 @@
     }
 
     @Override
-    public void setTileMode(ComponentName component, int mode) {
-        verifyCaller(component.getPackageName());
-        CustomTile customTile = getTileForComponent(component);
-        if (customTile != null) {
-            synchronized (mServices) {
-                mServices.get(customTile).setType(mode);
-            }
-        }
-    }
-
-    @Override
     public void updateQsTile(Tile tile) {
         ComponentName componentName = tile.getComponentName();
         verifyCaller(componentName.getPackageName());
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/BatteryTile.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/BatteryTile.java
index 2032783..77eaa3b 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/BatteryTile.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/BatteryTile.java
@@ -25,6 +25,7 @@
 import android.text.SpannableStringBuilder;
 import android.text.Spanned;
 import android.text.style.RelativeSizeSpan;
+import android.util.TypedValue;
 import android.view.LayoutInflater;
 import android.view.View;
 import android.view.View.OnAttachStateChangeListener;
@@ -129,6 +130,8 @@
             }
         };
         state.label = percentage;
+        state.contentDescription = mContext.getString(R.string.accessibility_quick_settings_battery,
+                percentage);
     }
 
     @Override
@@ -207,18 +210,21 @@
                     }
                 }
             });
+            final TextView batterySaverTitle =
+                    (TextView) mCurrentView.findViewById(android.R.id.title);
+            final TextView batterySaverSummary =
+                    (TextView) mCurrentView.findViewById(android.R.id.summary);
             if (mCharging) {
-                ((TextView) mCurrentView.findViewById(android.R.id.title)).setText(
-                        R.string.battery_detail_charging_summary);
-                mCurrentView.findViewById(android.R.id.icon).setVisibility(View.INVISIBLE);
+                mCurrentView.findViewById(R.id.switch_container).setAlpha(.7f);
+                batterySaverTitle.setTextSize(TypedValue.COMPLEX_UNIT_SP, 14);
+                batterySaverTitle.setText(R.string.battery_detail_charging_summary);
                 mCurrentView.findViewById(android.R.id.toggle).setVisibility(View.GONE);
                 mCurrentView.findViewById(R.id.switch_container).setClickable(false);
             } else {
-                ((TextView) mCurrentView.findViewById(android.R.id.title)).setText(
-                        R.string.battery_detail_switch_title);
-                ((TextView) mCurrentView.findViewById(android.R.id.summary)).setText(
-                        R.string.battery_detail_switch_summary);
-                mCurrentView.findViewById(android.R.id.icon).setVisibility(View.VISIBLE);
+                mCurrentView.findViewById(R.id.switch_container).setAlpha(1);
+                batterySaverTitle.setTextSize(TypedValue.COMPLEX_UNIT_SP, 16);
+                batterySaverTitle.setText(R.string.battery_detail_switch_title);
+                batterySaverSummary.setText(R.string.battery_detail_switch_summary);
                 mCurrentView.findViewById(android.R.id.toggle).setVisibility(View.VISIBLE);
                 mCurrentView.findViewById(R.id.switch_container).setClickable(true);
                 mCurrentView.findViewById(R.id.switch_container).setOnClickListener(this);
@@ -227,7 +233,7 @@
 
         private void bindBatteryInfo(BatteryInfo info) {
             SpannableStringBuilder builder = new SpannableStringBuilder();
-            builder.append(info.batteryPercentString, new RelativeSizeSpan(2),
+            builder.append(info.batteryPercentString, new RelativeSizeSpan(2.6f),
                     Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
             if (info.remainingLabel != null) {
                 if (mContext.getResources().getBoolean(R.bool.quick_settings_wide)) {
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java
index fcf758b..99eae02 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailItemView.java
@@ -30,6 +30,7 @@
 import android.widget.TextView;
 
 import com.android.internal.util.ArrayUtils;
+import com.android.settingslib.drawable.UserIconDrawable;
 import com.android.systemui.FontSizeUtils;
 import com.android.systemui.R;
 import com.android.systemui.statusbar.phone.UserAvatarView;
@@ -87,25 +88,29 @@
         return (UserDetailItemView) convertView;
     }
 
-    public void bind(String name, Bitmap picture) {
+    public void bind(String name, Bitmap picture, int userId) {
         mName.setText(name);
-        mAvatar.setBitmap(picture);
+        mAvatar.setAvatarWithBadge(picture, userId);
     }
 
-    public void bind(String name, Drawable picture) {
+    public void bind(String name, Drawable picture, int userId) {
         mName.setText(name);
-        mAvatar.setDrawable(picture);
+        mAvatar.setDrawableWithBadge(picture, userId);
+    }
+
+    public void setAvatarEnabled(boolean enabled) {
+        mAvatar.setEnabled(enabled);
     }
 
     public void setDisabledByAdmin(boolean disabled) {
         mRestrictedPadlock.setVisibility(disabled ? View.VISIBLE : View.GONE);
         mName.setEnabled(!disabled);
-        mAvatar.setDisabled(disabled);
+        mAvatar.setEnabled(!disabled);
     }
 
     public void setEnabled(boolean enabled) {
         mName.setEnabled(enabled);
-        mAvatar.setDisabled(!enabled);
+        mAvatar.setEnabled(enabled);
     }
 
     @Override
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java
index da98762..d4fa765 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/UserDetailView.java
@@ -76,9 +76,9 @@
             }
             String name = getName(mContext, item);
             if (item.picture == null) {
-                v.bind(name, getDrawable(mContext, item));
+                v.bind(name, getDrawable(mContext, item), item.resolveId());
             } else {
-                v.bind(name, item.picture);
+                v.bind(name, item.picture, item.info.id);
             }
             v.setActivated(item.isCurrent);
             v.setDisabledByAdmin(item.isDisabledByAdmin);
diff --git a/packages/SystemUI/src/com/android/systemui/recents/Recents.java b/packages/SystemUI/src/com/android/systemui/recents/Recents.java
index 287bb22..82daaa6 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/Recents.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/Recents.java
@@ -435,7 +435,7 @@
                 mDraggingInRecentsCurrentUser = currentUser;
                 return true;
             } else {
-                Toast.makeText(mContext, R.string.recents_drag_non_dockable_task_message,
+                Toast.makeText(mContext, R.string.recents_incompatible_app_message,
                         Toast.LENGTH_SHORT).show();
                 return false;
             }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java b/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java
index b1d9555..6b476ee 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java
@@ -38,6 +38,7 @@
 
 import com.android.internal.logging.MetricsLogger;
 import com.android.internal.logging.MetricsProto.MetricsEvent;
+import com.android.systemui.Interpolators;
 import com.android.systemui.R;
 import com.android.systemui.recents.events.EventBus;
 import com.android.systemui.recents.events.activity.CancelEnterRecentsWindowAnimationEvent;
@@ -58,8 +59,10 @@
 import com.android.systemui.recents.events.component.ScreenPinningRequestEvent;
 import com.android.systemui.recents.events.ui.AllTaskViewsDismissedEvent;
 import com.android.systemui.recents.events.ui.DeleteTaskDataEvent;
+import com.android.systemui.recents.events.ui.HideIncompatibleAppOverlayEvent;
 import com.android.systemui.recents.events.ui.RecentsDrawnEvent;
 import com.android.systemui.recents.events.ui.ShowApplicationInfoEvent;
+import com.android.systemui.recents.events.ui.ShowIncompatibleAppOverlayEvent;
 import com.android.systemui.recents.events.ui.StackViewScrolledEvent;
 import com.android.systemui.recents.events.ui.UpdateFreeformTaskViewVisibilityEvent;
 import com.android.systemui.recents.events.ui.UserInteractionEvent;
@@ -68,12 +71,12 @@
 import com.android.systemui.recents.events.ui.focus.FocusPreviousTaskViewEvent;
 import com.android.systemui.recents.misc.DozeTrigger;
 import com.android.systemui.recents.misc.SystemServicesProxy;
+import com.android.systemui.recents.misc.Utilities;
 import com.android.systemui.recents.model.RecentsPackageMonitor;
 import com.android.systemui.recents.model.RecentsTaskLoadPlan;
 import com.android.systemui.recents.model.RecentsTaskLoader;
 import com.android.systemui.recents.model.Task;
 import com.android.systemui.recents.model.TaskStack;
-import com.android.systemui.recents.views.AnimationProps;
 import com.android.systemui.recents.views.RecentsView;
 import com.android.systemui.recents.views.SystemBarScrimViews;
 import com.android.systemui.statusbar.BaseStatusBar;
@@ -90,6 +93,7 @@
     private final static boolean DEBUG = false;
 
     public final static int EVENT_BUS_PRIORITY = Recents.EVENT_BUS_PRIORITY + 1;
+    public final static int INCOMPATIBLE_APP_ALPHA_DURATION = 150;
 
     private RecentsPackageMonitor mPackageMonitor;
     private long mLastTabKeyEventTime;
@@ -101,6 +105,7 @@
     // Top level views
     private RecentsView mRecentsView;
     private SystemBarScrimViews mScrimViews;
+    private View mIncompatibleAppOverlay;
 
     // Runnables to finish the Recents activity
     private Intent mHomeIntent;
@@ -674,6 +679,30 @@
         MetricsLogger.count(this, "overview_app_info", 1);
     }
 
+    public final void onBusEvent(ShowIncompatibleAppOverlayEvent event) {
+        if (mIncompatibleAppOverlay == null) {
+            mIncompatibleAppOverlay = Utilities.findViewStubById(this,
+                    R.id.incompatible_app_overlay_stub).inflate();
+            mIncompatibleAppOverlay.setWillNotDraw(false);
+            mIncompatibleAppOverlay.setVisibility(View.VISIBLE);
+        }
+        mIncompatibleAppOverlay.animate()
+                .alpha(1f)
+                .setDuration(INCOMPATIBLE_APP_ALPHA_DURATION)
+                .setInterpolator(Interpolators.ALPHA_IN)
+                .start();
+    }
+
+    public final void onBusEvent(HideIncompatibleAppOverlayEvent event) {
+        if (mIncompatibleAppOverlay != null) {
+            mIncompatibleAppOverlay.animate()
+                    .alpha(0f)
+                    .setDuration(INCOMPATIBLE_APP_ALPHA_DURATION)
+                    .setInterpolator(Interpolators.ALPHA_OUT)
+                    .start();
+        }
+    }
+
     public final void onBusEvent(DeleteTaskDataEvent event) {
         // Remove any stored data from the loader
         RecentsTaskLoader loader = Recents.getTaskLoader();
diff --git a/packages/SystemUI/src/com/android/systemui/recents/RecentsImpl.java b/packages/SystemUI/src/com/android/systemui/recents/RecentsImpl.java
index 957c94b..fda340d 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/RecentsImpl.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/RecentsImpl.java
@@ -45,7 +45,6 @@
 import com.android.systemui.recents.events.EventBus;
 import com.android.systemui.recents.events.activity.DockedTopTaskEvent;
 import com.android.systemui.recents.events.activity.EnterRecentsWindowLastAnimationFrameEvent;
-import com.android.systemui.recents.events.activity.ForcedResizableEvent;
 import com.android.systemui.recents.events.activity.HideRecentsEvent;
 import com.android.systemui.recents.events.activity.IterateRecentsEvent;
 import com.android.systemui.recents.events.activity.LaunchNextTaskRequestEvent;
@@ -125,13 +124,6 @@
                 loader.loadTasks(mContext, plan, launchOpts);
             }
         }
-
-        @Override
-        public void onActivityForcedResizable(String packageName, int taskId) {
-            EventBus.getDefault().sendOntoMainThread(
-                    new ForcedResizableEvent(packageName, taskId));
-
-        }
     }
 
     protected static RecentsTaskLoadPlan sInstanceLoadPlan;
diff --git a/packages/SystemUI/src/com/android/systemui/recents/events/activity/ForcedResizableEvent.java b/packages/SystemUI/src/com/android/systemui/recents/events/activity/ForcedResizableEvent.java
deleted file mode 100644
index cdcabf0..0000000
--- a/packages/SystemUI/src/com/android/systemui/recents/events/activity/ForcedResizableEvent.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * 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 com.android.systemui.recents.events.activity;
-
-import com.android.systemui.recents.events.EventBus;
-
-/**
- * Sent when recents received the information that an activity got forced resizable, and we need
- * to inform the user about that.
- */
-public class ForcedResizableEvent extends EventBus.Event {
-
-    public final String packageName;
-    public final int taskId;
-
-    public ForcedResizableEvent(String packageName, int taskId) {
-        this.packageName = packageName;
-        this.taskId = taskId;
-    }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/recents/events/ui/HideIncompatibleAppOverlayEvent.java b/packages/SystemUI/src/com/android/systemui/recents/events/ui/HideIncompatibleAppOverlayEvent.java
new file mode 100644
index 0000000..d6ef636
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/recents/events/ui/HideIncompatibleAppOverlayEvent.java
@@ -0,0 +1,26 @@
+/*
+ * 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 com.android.systemui.recents.events.ui;
+
+import com.android.systemui.recents.events.EventBus;
+
+/**
+ * This is sent when a user stops draggin an incompatible app task.
+ */
+public class HideIncompatibleAppOverlayEvent extends EventBus.Event {
+    // Simple event
+}
diff --git a/packages/SystemUI/src/com/android/systemui/recents/events/ui/ShowIncompatibleAppOverlayEvent.java b/packages/SystemUI/src/com/android/systemui/recents/events/ui/ShowIncompatibleAppOverlayEvent.java
new file mode 100644
index 0000000..3a4350e
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/recents/events/ui/ShowIncompatibleAppOverlayEvent.java
@@ -0,0 +1,26 @@
+/*
+ * 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 com.android.systemui.recents.events.ui;
+
+import com.android.systemui.recents.events.EventBus;
+
+/**
+ * This is sent when a user starts dragging an incompatible app task.
+ */
+public class ShowIncompatibleAppOverlayEvent extends EventBus.Event {
+    // Simple event
+}
diff --git a/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java b/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java
index 1a4b40f..2d5addb 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java
@@ -144,6 +144,7 @@
         public void onPinnedActivityRestartAttempt() { }
         public void onPinnedStackAnimationEnded() { }
         public void onActivityForcedResizable(String packageName, int taskId) { }
+        public void onActivityDismissingDockedStack() { }
     }
 
     /**
@@ -182,6 +183,11 @@
             mHandler.obtainMessage(H.ON_ACTIVITY_FORCED_RESIZABLE, taskId, 0, packageName)
                     .sendToTarget();
         }
+
+        @Override
+        public void onActivityDismissingDockedStack() throws RemoteException {
+            mHandler.sendEmptyMessage(H.ON_ACTIVITY_DISMISSING_DOCKED_STACK);
+        }
     };
 
     /**
@@ -1091,6 +1097,7 @@
         private static final int ON_PINNED_ACTIVITY_RESTART_ATTEMPT = 3;
         private static final int ON_PINNED_STACK_ANIMATION_ENDED = 4;
         private static final int ON_ACTIVITY_FORCED_RESIZABLE = 5;
+        private static final int ON_ACTIVITY_DISMISSING_DOCKED_STACK = 6;
 
         @Override
         public void handleMessage(Message msg) {
@@ -1126,6 +1133,12 @@
                     }
                     break;
                 }
+                case ON_ACTIVITY_DISMISSING_DOCKED_STACK: {
+                    for (int i = mTaskStackListeners.size() - 1; i >= 0; i--) {
+                        mTaskStackListeners.get(i).onActivityDismissingDockedStack();
+                    }
+                    break;
+                }
             }
         }
     }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/misc/Utilities.java b/packages/SystemUI/src/com/android/systemui/recents/misc/Utilities.java
index 69d98af..4ecda54 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/misc/Utilities.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/misc/Utilities.java
@@ -19,17 +19,20 @@
 import android.animation.Animator;
 import android.animation.AnimatorSet;
 import android.annotation.FloatRange;
+import android.app.Activity;
 import android.content.res.Resources;
 import android.graphics.Color;
 import android.graphics.Rect;
 import android.graphics.RectF;
 import android.graphics.drawable.Drawable;
+import android.os.Trace;
 import android.util.ArraySet;
 import android.util.IntProperty;
 import android.util.Property;
 import android.util.TypedValue;
 import android.view.View;
 import android.view.ViewParent;
+import android.view.ViewStub;
 
 import com.android.systemui.recents.model.Task;
 import com.android.systemui.recents.views.TaskViewTransform;
@@ -220,6 +223,20 @@
     }
 
     /**
+     * Returns a view stub for the given view id.
+     */
+    public static ViewStub findViewStubById(View v, int stubId) {
+        return (ViewStub) v.findViewById(stubId);
+    }
+
+    /**
+     * Returns a view stub for the given view id.
+     */
+    public static ViewStub findViewStubById(Activity a, int stubId) {
+        return (ViewStub) a.findViewById(stubId);
+    }
+
+    /**
      * Updates {@param transforms} to be the same size as {@param tasks}.
      */
     public static void matchTaskListSize(List<Task> tasks, List<TaskViewTransform> transforms) {
@@ -245,6 +262,14 @@
     }
 
     /**
+     * Adds a trace event for debugging.
+     */
+    public static void addTraceEvent(String event) {
+        Trace.traceBegin(Trace.TRACE_TAG_VIEW, event);
+        Trace.traceEnd(Trace.TRACE_TAG_VIEW);
+    }
+
+    /**
      * Returns a lightweight dump of a rect.
      */
     public static String dumpRect(Rect r) {
diff --git a/packages/SystemUI/src/com/android/systemui/recents/tv/RecentsTvActivity.java b/packages/SystemUI/src/com/android/systemui/recents/tv/RecentsTvActivity.java
index bdc1426..60a85df 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/tv/RecentsTvActivity.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/tv/RecentsTvActivity.java
@@ -55,6 +55,7 @@
 import com.android.systemui.recents.tv.views.RecentsTvView;
 import com.android.systemui.recents.tv.views.TaskStackHorizontalGridView;
 import com.android.systemui.recents.tv.views.TaskStackHorizontalViewAdapter;
+import com.android.systemui.recents.views.AnimationProps;
 import com.android.systemui.statusbar.BaseStatusBar;
 import com.android.systemui.tv.pip.PipManager;
 import com.android.systemui.tv.pip.PipRecentsOverlayManager;
@@ -246,7 +247,7 @@
         dismissEvent.addPostAnimationCallback(mFinishLaunchHomeRunnable);
         dismissEvent.addPostAnimationCallback(closeSystemWindows);
 
-        if(mTaskStackHorizontalGridView.getChildCount() > 0) {
+        if(mTaskStackHorizontalGridView.getChildCount() > 0 && animateTaskViews) {
             mHomeRecentsEnterExitAnimationHolder.startExitAnimation(dismissEvent);
         } else {
             closeSystemWindows.run();
@@ -501,12 +502,10 @@
     }
 
     public final void onBusEvent(AllTaskViewsDismissedEvent event) {
-        SystemServicesProxy ssp = Recents.getSystemServices();
-        if (ssp.hasDockedTask()) {
+        if (mPipManager.isPipShown()) {
             mRecentsView.showEmptyView();
         } else {
-            // Just go straight home (no animation necessary because there are no more task views)
-            dismissRecentsToHome(false /* animateTaskViews */);
+            dismissRecentsToHome(false);
         }
     }
 
diff --git a/packages/SystemUI/src/com/android/systemui/recents/tv/animations/DismissAnimationsHolder.java b/packages/SystemUI/src/com/android/systemui/recents/tv/animations/DismissAnimationsHolder.java
index fbcfa97..3e668af 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/tv/animations/DismissAnimationsHolder.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/tv/animations/DismissAnimationsHolder.java
@@ -26,13 +26,13 @@
 
 public class DismissAnimationsHolder {
     private LinearLayout mDismissArea;
-    private LinearLayout mTaskCardView;
+    private LinearLayout mRecentsTvCard;
     private int mCardYDelta;
     private long mShortDuration;
     private long mLongDuration;
 
     public DismissAnimationsHolder(TaskCardView taskCardView) {
-        mTaskCardView = (LinearLayout) taskCardView.findViewById(R.id.recents_tv_card);
+        mRecentsTvCard = (LinearLayout) taskCardView.findViewById(R.id.recents_tv_card);
         mDismissArea = (LinearLayout) taskCardView.findViewById(R.id.card_dismiss);
 
         Resources res = taskCardView.getResources();
@@ -47,7 +47,7 @@
                 .setInterpolator(Interpolators.FAST_OUT_SLOW_IN)
                 .alpha(1.0f);
 
-        mTaskCardView.animate()
+        mRecentsTvCard.animate()
                 .setDuration(mShortDuration)
                 .setInterpolator(Interpolators.FAST_OUT_SLOW_IN)
                 .translationYBy(mCardYDelta)
@@ -60,7 +60,7 @@
                 .setInterpolator(Interpolators.FAST_OUT_SLOW_IN)
                 .alpha(0.0f);
 
-        mTaskCardView.animate()
+        mRecentsTvCard.animate()
                 .setDuration(mShortDuration)
                 .setInterpolator(Interpolators.FAST_OUT_SLOW_IN)
                 .translationYBy(-mCardYDelta)
@@ -73,11 +73,17 @@
                 .setInterpolator(Interpolators.FAST_OUT_SLOW_IN)
                 .alpha(0.0f);
 
-        mTaskCardView.animate()
+        mRecentsTvCard.animate()
                 .setDuration(mLongDuration)
                 .setInterpolator(Interpolators.FAST_OUT_SLOW_IN)
                 .translationYBy(mCardYDelta)
                 .alpha(0.0f)
                 .setListener(listener);
     }
+
+    public void reset() {
+        mRecentsTvCard.setAlpha(1.0f);
+        mRecentsTvCard.setTranslationY(0);
+        mRecentsTvCard.animate().setListener(null);
+    }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/tv/views/RecentsTvView.java b/packages/SystemUI/src/com/android/systemui/recents/tv/views/RecentsTvView.java
index 53fdf62..b876fc70 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/tv/views/RecentsTvView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/tv/views/RecentsTvView.java
@@ -250,8 +250,9 @@
 
     public TaskStackHorizontalGridView setTaskStackViewAdapter(
             TaskStackHorizontalViewAdapter taskStackViewAdapter) {
-        if(mTaskStackHorizontalView != null) {
+        if (mTaskStackHorizontalView != null) {
             mTaskStackHorizontalView.setAdapter(taskStackViewAdapter);
+            taskStackViewAdapter.setTaskStackHorizontalGridView(mTaskStackHorizontalView);
         }
         return mTaskStackHorizontalView;
     }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskCardView.java b/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskCardView.java
index 08d5cb0..d3bc4b6 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskCardView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskCardView.java
@@ -219,6 +219,7 @@
     }
 
     public void startDismissTaskAnimation(Animator.AnimatorListener listener) {
+        mDismissState = false;
         mDismissAnimationsHolder.startDismissAnimation(listener);
     }
 
@@ -231,4 +232,10 @@
         super.onDetachedFromWindow();
         setDismissState(false);
     }
+
+    public void reset() {
+        mDismissState = false;
+        mRecentsRowFocusAnimationHolder.reset();
+        mDismissAnimationsHolder.reset();
+    }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalGridView.java b/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalGridView.java
index 603721a..77ab8c1 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalGridView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalGridView.java
@@ -179,13 +179,14 @@
 
     @Override
     public void onStackTaskAdded(TaskStack stack, Task newTask) {
-        getAdapter().notifyItemInserted(stack.getStackTasks().indexOf(newTask));
+        ((TaskStackHorizontalViewAdapter) getAdapter()).addTaskAt(newTask,
+                stack.indexOfStackTask(newTask));
     }
 
     @Override
     public void onStackTaskRemoved(TaskStack stack, Task removedTask, boolean wasFrontMostTask,
             Task newFrontMostTask, AnimationProps animation, boolean fromDockGesture) {
-        getAdapter().notifyItemRemoved(stack.getStackTasks().indexOf(removedTask));
+        ((TaskStackHorizontalViewAdapter) getAdapter()).removeTask(removedTask);
         if (mFocusedTask == removedTask) {
             resetFocusedTask(removedTask);
         }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalViewAdapter.java b/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalViewAdapter.java
index 97712ea..eff1845 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalViewAdapter.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/tv/views/TaskStackHorizontalViewAdapter.java
@@ -27,7 +27,9 @@
 import com.android.systemui.recents.events.EventBus;
 import com.android.systemui.recents.events.activity.LaunchTvTaskEvent;
 import com.android.systemui.recents.events.ui.DeleteTaskDataEvent;
+import com.android.systemui.recents.events.ui.TaskViewDismissedEvent;
 import com.android.systemui.recents.model.Task;
+import com.android.systemui.recents.views.AnimationProps;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -40,6 +42,7 @@
     //Full class name is 30 characters
     private static final String TAG = "TaskStackViewAdapter";
     private List<Task> mTaskList;
+    private TaskStackHorizontalGridView mGridView;
 
     public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener{
         private TaskCardView mTaskCardView;
@@ -62,7 +65,7 @@
             try {
                 if (mTaskCardView.isInDismissState()) {
                     mTaskCardView.startDismissTaskAnimation(
-                            getRemoveAtListener(getAdapterPosition(), mTaskCardView));
+                            getRemoveAtListener(getAdapterPosition(), mTaskCardView.getTask()));
                 } else {
                     EventBus.getDefault().send(new LaunchTvTaskEvent(mTaskCardView, mTask,
                             null, INVALID_STACK_ID));
@@ -74,6 +77,28 @@
             }
 
         }
+
+        private Animator.AnimatorListener getRemoveAtListener(final int position,
+                                                              final Task task) {
+            return new Animator.AnimatorListener() {
+
+                @Override
+                public void onAnimationStart(Animator animation) { }
+
+                @Override
+                public void onAnimationEnd(Animator animation) {
+                    removeAt(position);
+                    EventBus.getDefault().send(new DeleteTaskDataEvent(task));
+                }
+
+                @Override
+                public void onAnimationCancel(Animator animation) { }
+
+                @Override
+                public void onAnimationRepeat(Animator animation) { }
+            };
+
+        }
     }
 
     public TaskStackHorizontalViewAdapter(List tasks) {
@@ -101,39 +126,43 @@
     }
 
     @Override
+    public void onViewDetachedFromWindow(ViewHolder holder) {
+        holder.mTaskCardView.reset();
+    }
+
+    @Override
     public int getItemCount() {
         return mTaskList.size();
     }
 
-    private Animator.AnimatorListener getRemoveAtListener(final int position,
-                                                          final TaskCardView taskCardView) {
-        return new Animator.AnimatorListener() {
-
-            @Override
-            public void onAnimationStart(Animator animation) { }
-
-            @Override
-            public void onAnimationEnd(Animator animation) {
-                removeAt(position);
-                EventBus.getDefault().send(new DeleteTaskDataEvent(taskCardView.getTask()));
-            }
-
-            @Override
-            public void onAnimationCancel(Animator animation) { }
-
-            @Override
-            public void onAnimationRepeat(Animator animation) { }
-        };
-
+    private void removeAt(int position) {
+        Task removedTask = mTaskList.remove(position);
+        if (mGridView != null) {
+            mGridView.getStack().removeTask(removedTask, AnimationProps.IMMEDIATE,
+                    false);
+        }
+        notifyItemRemoved(position);
     }
 
-    private void removeAt(int position) {
-        mTaskList.remove(position);
-        notifyItemRemoved(position);
+    public void removeTask(Task task) {
+        int position = mTaskList.indexOf(task);
+        if (position >= 0) {
+            mTaskList.remove(position);
+            notifyItemRemoved(position);
+        }
     }
 
     public int getPositionOfTask(Task task) {
         int position = mTaskList.indexOf(task);
         return (position >= 0) ? position : 0;
     }
+
+    public void setTaskStackHorizontalGridView(TaskStackHorizontalGridView gridView) {
+        mGridView = gridView;
+    }
+
+    public void addTaskAt(Task task, int position) {
+        mTaskList.add(position, task);
+        notifyItemInserted(position);
+    }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/RecentsTransitionHelper.java b/packages/SystemUI/src/com/android/systemui/recents/views/RecentsTransitionHelper.java
index 9eec2ce..fd8df99 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/RecentsTransitionHelper.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/RecentsTransitionHelper.java
@@ -116,6 +116,7 @@
                     // window transition
                     EventBus.getDefault().send(new CancelEnterRecentsWindowAnimationEvent(task));
                     EventBus.getDefault().send(new ExitRecentsWindowFirstAnimationFrameEvent());
+                    stackView.cancelAllTaskViewAnimations();
 
                     if (screenPinningRequested) {
                         // Request screen pinning after the animation runs
@@ -133,6 +134,7 @@
                     // window transition
                     EventBus.getDefault().send(new CancelEnterRecentsWindowAnimationEvent(task));
                     EventBus.getDefault().send(new ExitRecentsWindowFirstAnimationFrameEvent());
+                    stackView.cancelAllTaskViewAnimations();
                 }
             };
         }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/RecentsViewTouchHandler.java b/packages/SystemUI/src/com/android/systemui/recents/views/RecentsViewTouchHandler.java
index 33d5bb7..22acb88 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/RecentsViewTouchHandler.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/RecentsViewTouchHandler.java
@@ -19,15 +19,18 @@
 import android.app.ActivityManager;
 import android.content.res.Configuration;
 import android.graphics.Point;
+import android.graphics.Rect;
 import android.view.MotionEvent;
 import android.view.ViewConfiguration;
 import android.view.ViewDebug;
-import android.widget.Toast;
 
-import com.android.systemui.R;
+import com.android.internal.policy.DividerSnapAlgorithm;
 import com.android.systemui.recents.Recents;
 import com.android.systemui.recents.RecentsConfiguration;
 import com.android.systemui.recents.events.EventBus;
+import com.android.systemui.recents.events.activity.ConfigurationChangedEvent;
+import com.android.systemui.recents.events.ui.HideIncompatibleAppOverlayEvent;
+import com.android.systemui.recents.events.ui.ShowIncompatibleAppOverlayEvent;
 import com.android.systemui.recents.events.ui.dragndrop.DragDropTargetChangedEvent;
 import com.android.systemui.recents.events.ui.dragndrop.DragEndEvent;
 import com.android.systemui.recents.events.ui.dragndrop.DragStartEvent;
@@ -81,12 +84,20 @@
     private float mDragSlop;
 
     private DropTarget mLastDropTarget;
+    private DividerSnapAlgorithm mDividerSnapAlgorithm;
     private ArrayList<DropTarget> mDropTargets = new ArrayList<>();
     private ArrayList<TaskStack.DockState> mVisibleDockStates = new ArrayList<>();
 
     public RecentsViewTouchHandler(RecentsView rv) {
         mRv = rv;
         mDragSlop = ViewConfiguration.get(rv.getContext()).getScaledTouchSlop();
+        updateSnapAlgorithm();
+    }
+
+    private void updateSnapAlgorithm() {
+        Rect insets = new Rect();
+        SystemServicesProxy.getInstance(mRv.getContext()).getStableInsets(insets);
+        mDividerSnapAlgorithm = DividerSnapAlgorithm.create(mRv.getContext(), insets);
     }
 
     /**
@@ -150,10 +161,10 @@
         mTaskView.setTranslationY(y);
 
         mVisibleDockStates.clear();
-        if (ActivityManager.supportsMultiWindow() && !ssp.hasDockedTask()) {
+        if (ActivityManager.supportsMultiWindow() && !ssp.hasDockedTask()
+                && mDividerSnapAlgorithm.isSplitScreenFeasible()) {
             if (!event.task.isDockable) {
-                Toast.makeText(mRv.getContext(), R.string.recents_drag_non_dockable_task_message,
-                        Toast.LENGTH_SHORT).show();
+                EventBus.getDefault().send(new ShowIncompatibleAppOverlayEvent());
             } else {
                 // Add the dock state drop targets (these take priority)
                 TaskStack.DockState[] dockStates = getDockStatesForCurrentOrientation();
@@ -170,12 +181,19 @@
     }
 
     public final void onBusEvent(DragEndEvent event) {
+        if (!mDragTask.isDockable) {
+            EventBus.getDefault().send(new HideIncompatibleAppOverlayEvent());
+        }
         mDragRequested = false;
         mDragTask = null;
         mTaskView = null;
         mLastDropTarget = null;
     }
 
+    public final void onBusEvent(ConfigurationChangedEvent event) {
+        updateSnapAlgorithm();
+    }
+
     /**
      * Handles dragging touch events
      */
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackLayoutAlgorithm.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackLayoutAlgorithm.java
index b75a91e..e4da8b3 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackLayoutAlgorithm.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackLayoutAlgorithm.java
@@ -23,13 +23,13 @@
 import android.graphics.Path;
 import android.graphics.Rect;
 import android.util.ArraySet;
+import android.util.MutableFloat;
 import android.util.SparseArray;
 import android.util.SparseIntArray;
 import android.view.ViewDebug;
 
 import com.android.systemui.R;
 import com.android.systemui.recents.Recents;
-import com.android.systemui.recents.RecentsActivity;
 import com.android.systemui.recents.RecentsActivityLaunchState;
 import com.android.systemui.recents.RecentsConfiguration;
 import com.android.systemui.recents.RecentsDebugFlags;
@@ -628,22 +628,24 @@
 
     /**
      * Updates this stack when a scroll happens.
+     *
      */
-    public void updateFocusStateOnScroll(float stackScroll, float deltaScroll) {
-        if (deltaScroll == 0f) {
-            return;
+    public float updateFocusStateOnScroll(float lastTargetStackScroll, float targetStackScroll,
+            float lastStackScroll) {
+        if (targetStackScroll == lastStackScroll) {
+            return targetStackScroll;
         }
 
+        float deltaScroll = targetStackScroll - lastStackScroll;
+        float deltaTargetScroll = targetStackScroll - lastTargetStackScroll;
+        float newScroll = targetStackScroll;
+        mUnfocusedRange.offset(targetStackScroll);
         for (int i = mTaskIndexOverrideMap.size() - 1; i >= 0; i--) {
             int taskId = mTaskIndexOverrideMap.keyAt(i);
             float x = mTaskIndexMap.get(taskId);
             float overrideX = mTaskIndexOverrideMap.get(taskId, 0f);
             float newOverrideX = overrideX + deltaScroll;
-            mUnfocusedRange.offset(stackScroll);
-            boolean outOfBounds = mUnfocusedRange.getNormalizedX(newOverrideX) < 0f ||
-                    mUnfocusedRange.getNormalizedX(newOverrideX) > 1f;
-            if (outOfBounds || (overrideX >= x && x >= newOverrideX) ||
-                    (overrideX <= x && x <= newOverrideX)) {
+            if (isInvalidOverrideX(x, overrideX, newOverrideX)) {
                 // Remove the override once we reach the original task index
                 mTaskIndexOverrideMap.removeAt(i);
             } else if ((overrideX >= x && deltaScroll <= 0f) ||
@@ -652,11 +654,23 @@
                 mTaskIndexOverrideMap.put(taskId, newOverrideX);
             } else {
                 // Scrolling override x away from x, we should still move the scroll towards x
-                float deltaX = overrideX - x;
-                newOverrideX = Math.signum(deltaX) * (Math.abs(deltaX) - Math.abs(deltaScroll));
-                mTaskIndexOverrideMap.put(taskId, x + newOverrideX);
+                newScroll = lastStackScroll;
+                newOverrideX = overrideX - deltaTargetScroll;
+                if (isInvalidOverrideX(x, overrideX, newOverrideX)) {
+                    mTaskIndexOverrideMap.removeAt(i);
+                } else{
+                    mTaskIndexOverrideMap.put(taskId, newOverrideX);
+                }
             }
         }
+        return newScroll;
+    }
+
+    private boolean isInvalidOverrideX(float x, float overrideX, float newOverrideX) {
+        boolean outOfBounds = mUnfocusedRange.getNormalizedX(newOverrideX) < 0f ||
+                mUnfocusedRange.getNormalizedX(newOverrideX) > 1f;
+        return outOfBounds || (overrideX >= x && x >= newOverrideX) ||
+                (overrideX <= x && x <= newOverrideX);
     }
 
     /**
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java
index 13c8403..0fc45ed 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java
@@ -1618,7 +1618,6 @@
         if (animation != null) {
             relayoutTaskViewsOnNextFrame(animation);
         }
-        mLayoutAlgorithm.updateFocusStateOnScroll(curScroll, curScroll - prevScroll);
 
         if (mEnterAnimationComplete) {
             if (prevScroll > SHOW_STACK_ACTION_BUTTON_SCROLL_THRESHOLD &&
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewScroller.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewScroller.java
index 19b3c94..1fa73c6 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewScroller.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewScroller.java
@@ -22,6 +22,7 @@
 import android.content.Context;
 import android.util.FloatProperty;
 import android.util.Log;
+import android.util.MutableFloat;
 import android.util.Property;
 import android.view.ViewDebug;
 import android.widget.OverScroller;
@@ -66,6 +67,8 @@
 
     @ViewDebug.ExportedProperty(category="recents")
     float mStackScrollP;
+    @ViewDebug.ExportedProperty(category="recents")
+    float mLastDeltaP = 0f;
     float mFlingDownScrollP;
     int mFlingDownY;
 
@@ -84,6 +87,11 @@
     /** Resets the task scroller. */
     void reset() {
         mStackScrollP = 0f;
+        mLastDeltaP = 0f;
+    }
+
+    void resetDeltaScroll() {
+        mLastDeltaP = 0f;
     }
 
     /** Gets the current stack scroll */
@@ -99,14 +107,27 @@
     }
 
     /**
+     * Sets the current stack scroll immediately, and returns the difference between the target
+     * scroll and the actual scroll after accounting for the effect on the focus state.
+     */
+    public float setDeltaStackScroll(float downP, float deltaP) {
+        float targetScroll = downP + deltaP;
+        float newScroll = mLayoutAlgorithm.updateFocusStateOnScroll(downP + mLastDeltaP, targetScroll,
+                mStackScrollP);
+        setStackScroll(newScroll, AnimationProps.IMMEDIATE);
+        mLastDeltaP = deltaP;
+        return newScroll - targetScroll;
+    }
+
+    /**
      * Sets the current stack scroll, but indicates to the callback the preferred animation to
      * update to this new scroll.
      */
-    public void setStackScroll(float s, AnimationProps animation) {
-        float prevStackScroll = mStackScrollP;
-        mStackScrollP = s;
+    public void setStackScroll(float newScroll, AnimationProps animation) {
+        float prevScroll = mStackScrollP;
+        mStackScrollP = newScroll;
         if (mCb != null) {
-            mCb.onStackScrollChanged(prevStackScroll, mStackScrollP, animation);
+            mCb.onStackScrollChanged(prevScroll, mStackScrollP, animation);
         }
     }
 
@@ -115,9 +136,9 @@
      * @return whether the stack progress changed.
      */
     public boolean setStackScrollToInitialState() {
-        float prevStackScrollP = mStackScrollP;
+        float prevScroll = mStackScrollP;
         setStackScroll(mLayoutAlgorithm.mInitialScrollP);
-        return Float.compare(prevStackScrollP, mStackScrollP) != 0;
+        return Float.compare(prevScroll, mStackScrollP) != 0;
     }
 
     /**
@@ -227,10 +248,9 @@
     boolean computeScroll() {
         if (mScroller.computeScrollOffset()) {
             float deltaP = mLayoutAlgorithm.getDeltaPForY(mFlingDownY, mScroller.getCurrY());
-            float scroll = mFlingDownScrollP + deltaP;
-            setStackScroll(scroll);
+            mFlingDownScrollP += setDeltaStackScroll(mFlingDownScrollP, deltaP);
             if (DEBUG) {
-                Log.d(TAG, "computeScroll: " + scroll);
+                Log.d(TAG, "computeScroll: " + (mFlingDownScrollP + deltaP));
             }
             return true;
         }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewTouchHandler.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewTouchHandler.java
index ee0de1a..3cdb1fb 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewTouchHandler.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackViewTouchHandler.java
@@ -200,6 +200,7 @@
                 // Stop the current scroll if it is still flinging
                 mScroller.stopScroller();
                 mScroller.stopBoundScrollAnimation();
+                mScroller.resetDeltaScroll();
                 Utilities.cancelAnimationWithoutCallbacks(mScrollFlingAnimator);
 
                 // Finish any existing task animations from the delete
@@ -223,6 +224,7 @@
                 mDownY = (int) ev.getY(index);
                 mLastY = mDownY;
                 mDownScrollP = mScroller.getStackScroll();
+                mScroller.resetDeltaScroll();
                 mVelocityTracker.addMovement(ev);
                 break;
             }
@@ -256,20 +258,21 @@
                     // If we just move linearly on the screen, then that would map to 1/arclength
                     // of the curve, so just move the scroll proportional to that
                     float deltaP = layoutAlgorithm.getDeltaPForY(mDownY, y);
-                    float curScrollP = mDownScrollP + deltaP;
 
                     // Modulate the overscroll to prevent users from pulling the stack too far
                     float minScrollP = layoutAlgorithm.mMinScrollP;
                     float maxScrollP = layoutAlgorithm.mMaxScrollP;
+                    float curScrollP = mDownScrollP + deltaP;
                     if (curScrollP < minScrollP || curScrollP > maxScrollP) {
                         float clampedScrollP = Utilities.clamp(curScrollP, minScrollP, maxScrollP);
                         float overscrollP = (curScrollP - clampedScrollP);
                         float overscrollX = Math.abs(overscrollP) / MAX_OVERSCROLL;
-                        curScrollP = clampedScrollP + (Math.signum(overscrollP) *
-                                (OVERSCROLL_INTERP.getInterpolation(overscrollX) * MAX_OVERSCROLL));
+                        float interpX = OVERSCROLL_INTERP.getInterpolation(overscrollX);
+                        curScrollP = clampedScrollP + Math.signum(overscrollP) *
+                                (interpX * MAX_OVERSCROLL);
                     }
-
-                    mScroller.setStackScroll(curScrollP);
+                    mDownScrollP += mScroller.setDeltaStackScroll(mDownScrollP,
+                            curScrollP - mDownScrollP);
                     mStackViewScrolledEvent.updateY(y - mLastY);
                     EventBus.getDefault().send(mStackViewScrolledEvent);
                 }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java
index f8ed700..6be8a4a 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskView.java
@@ -39,6 +39,7 @@
 import android.view.View;
 import android.view.ViewDebug;
 import android.view.ViewOutlineProvider;
+import android.widget.TextView;
 import android.widget.Toast;
 
 import com.android.internal.logging.MetricsLogger;
@@ -146,6 +147,8 @@
     AnimateableViewBounds mViewBounds;
 
     private AnimatorSet mTransformAnimation;
+    private ObjectAnimator mDimAnimator;
+    private ObjectAnimator mOutlineAnimator;
     private final TaskViewTransform mTargetAnimationTransform = new TaskViewTransform();
     private ArrayList<Animator> mTmpAnimators = new ArrayList<>();
 
@@ -155,6 +158,7 @@
     @ViewDebug.ExportedProperty(deepExport=true, prefix="header_")
     TaskViewHeader mHeaderView;
     View mActionButtonView;
+    View mIncompatibleAppToastView;
     TaskViewCallbacks mCb;
 
     @ViewDebug.ExportedProperty(category="recents")
@@ -308,14 +312,14 @@
         } else {
             // Both the progress and the update are a function of the bounds movement of the task
             if (Float.compare(getDimAlpha(), toTransform.dimAlpha) != 0) {
-                ObjectAnimator anim = ObjectAnimator.ofFloat(this, DIM_ALPHA, getDimAlpha(),
+                mDimAnimator = ObjectAnimator.ofFloat(this, DIM_ALPHA, getDimAlpha(),
                         toTransform.dimAlpha);
-                mTmpAnimators.add(toAnimation.apply(AnimationProps.BOUNDS, anim));
+                mTmpAnimators.add(toAnimation.apply(AnimationProps.BOUNDS, mDimAnimator));
             }
             if (Float.compare(mViewBounds.getAlpha(), toTransform.viewOutlineAlpha) != 0) {
-                ObjectAnimator anim = ObjectAnimator.ofFloat(this, VIEW_OUTLINE_ALPHA,
+                mOutlineAnimator = ObjectAnimator.ofFloat(this, VIEW_OUTLINE_ALPHA,
                         mViewBounds.getAlpha(), toTransform.viewOutlineAlpha);
-                mTmpAnimators.add(toAnimation.apply(AnimationProps.BOUNDS, anim));
+                mTmpAnimators.add(toAnimation.apply(AnimationProps.BOUNDS, mOutlineAnimator));
             }
             if (updateCallback != null) {
                 ValueAnimator updateCallbackAnim = ValueAnimator.ofInt(0, 1);
@@ -343,6 +347,9 @@
         mActionButtonView.setScaleY(1f);
         mActionButtonView.setAlpha(0f);
         mActionButtonView.setTranslationZ(mActionButtonTranslationZ);
+        if (mIncompatibleAppToastView != null) {
+            mIncompatibleAppToastView.setVisibility(View.INVISIBLE);
+        }
     }
 
     /**
@@ -358,6 +365,8 @@
      */
     public void cancelTransformAnimation() {
         Utilities.cancelAnimationWithoutCallbacks(mTransformAnimation);
+        Utilities.cancelAnimationWithoutCallbacks(mDimAnimator);
+        Utilities.cancelAnimationWithoutCallbacks(mOutlineAnimator);
     }
 
     /** Enables/disables handling touch on this task view. */
@@ -532,32 +541,49 @@
         // These values will be animated in when onStartLaunchTargetEnterAnimation() is called
         setDimAlphaWithoutHeader(0);
         mActionButtonView.setAlpha(0f);
+        if (mIncompatibleAppToastView != null &&
+                mIncompatibleAppToastView.getVisibility() == View.VISIBLE) {
+            mIncompatibleAppToastView.setAlpha(0f);
+        }
     }
 
     @Override
     public void onStartLaunchTargetEnterAnimation(TaskViewTransform transform, int duration,
             boolean screenPinningEnabled, ReferenceCountedTrigger postAnimationTrigger) {
+        Utilities.cancelAnimationWithoutCallbacks(mDimAnimator);
+
         // Dim the view after the app window transitions down into recents
         postAnimationTrigger.increment();
         AnimationProps animation = new AnimationProps(duration, Interpolators.ALPHA_OUT);
-        Animator anim = animation.apply(AnimationProps.DIM_ALPHA, ObjectAnimator.ofFloat(this,
+        mDimAnimator = animation.apply(AnimationProps.DIM_ALPHA, ObjectAnimator.ofFloat(this,
                 DIM_ALPHA_WITHOUT_HEADER, getDimAlpha(), transform.dimAlpha));
-        anim.addListener(postAnimationTrigger.decrementOnAnimationEnd());
-        anim.start();
+        mDimAnimator.addListener(postAnimationTrigger.decrementOnAnimationEnd());
+        mDimAnimator.start();
 
         if (screenPinningEnabled) {
             showActionButton(true /* fadeIn */, duration /* fadeInDuration */);
         }
+
+        if (mIncompatibleAppToastView != null &&
+                mIncompatibleAppToastView.getVisibility() == View.VISIBLE) {
+            mIncompatibleAppToastView.animate()
+                    .alpha(1f)
+                    .setDuration(duration)
+                    .setInterpolator(Interpolators.ALPHA_IN)
+                    .start();
+        }
     }
 
     @Override
     public void onStartLaunchTargetLaunchAnimation(int duration, boolean screenPinningRequested,
             ReferenceCountedTrigger postAnimationTrigger) {
+        Utilities.cancelAnimationWithoutCallbacks(mDimAnimator);
+
         // Un-dim the view before/while launching the target
         AnimationProps animation = new AnimationProps(duration, Interpolators.ALPHA_OUT);
-        Animator anim = animation.apply(AnimationProps.DIM_ALPHA, ObjectAnimator.ofFloat(this,
+        mDimAnimator = animation.apply(AnimationProps.DIM_ALPHA, ObjectAnimator.ofFloat(this,
                 DIM_ALPHA, getDimAlpha(), 0));
-        anim.start();
+        mDimAnimator.start();
 
         postAnimationTrigger.increment();
         hideActionButton(true /* fadeOut */, duration,
@@ -579,6 +605,18 @@
         mTask = t;
         mTask.addCallback(this);
         mIsDisabledInSafeMode = !mTask.isSystemApp && ssp.isInSafeMode();
+
+        if (!t.isDockable && ssp.hasDockedTask()) {
+            if (mIncompatibleAppToastView == null) {
+                mIncompatibleAppToastView = Utilities.findViewStubById(this,
+                        R.id.incompatible_app_toast_stub).inflate();
+                TextView msg = (TextView) findViewById(com.android.internal.R.id.message);
+                msg.setText(R.string.recents_incompatible_app_message);
+            }
+            mIncompatibleAppToastView.setVisibility(View.VISIBLE);
+        } else if (mIncompatibleAppToastView != null) {
+            mIncompatibleAppToastView.setVisibility(View.INVISIBLE);
+        }
     }
 
     @Override
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java
index 570ff8a..16d8e53 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java
@@ -39,7 +39,6 @@
 import android.view.ViewAnimationUtils;
 import android.view.ViewDebug;
 import android.view.ViewGroup;
-import android.view.ViewStub;
 import android.widget.FrameLayout;
 import android.widget.ImageView;
 import android.widget.ProgressBar;
@@ -141,15 +140,12 @@
     // Header views
     ImageView mIconView;
     TextView mTitleView;
-    TextView mSubTitleView;
     ImageView mMoveTaskButton;
     ImageView mDismissButton;
-    ViewStub mAppOverlayViewStub;
     FrameLayout mAppOverlayView;
     ImageView mAppIconView;
     ImageView mAppInfoView;
     TextView mAppTitleView;
-    ViewStub mFocusTimerIndicatorStub;
     ProgressBar mFocusTimerIndicator;
 
     // Header drawables
@@ -242,13 +238,10 @@
         mIconView.setClickable(false);
         mIconView.setOnLongClickListener(this);
         mTitleView = (TextView) findViewById(R.id.title);
-        mSubTitleView = (TextView) findViewById(R.id.sub_title);
         mDismissButton = (ImageView) findViewById(R.id.dismiss_task);
         if (ssp.hasFreeformWorkspaceSupport()) {
             mMoveTaskButton = (ImageView) findViewById(R.id.move_task);
         }
-        mFocusTimerIndicatorStub = (ViewStub) findViewById(R.id.focus_timer_indicator_stub);
-        mAppOverlayViewStub = (ViewStub) findViewById(R.id.app_overlay_stub);
 
         onConfigurationChanged();
     }
@@ -305,8 +298,7 @@
                 R.dimen.recents_task_view_header_button_padding_tablet_land,
                 R.dimen.recents_task_view_header_button_padding,
                 R.dimen.recents_task_view_header_button_padding_tablet_land);
-        updateLayoutParams(mIconView, findViewById(R.id.title_container), mMoveTaskButton,
-                mDismissButton);
+        updateLayoutParams(mIconView, mTitleView, mMoveTaskButton, mDismissButton);
         if (mAppOverlayView != null) {
             updateLayoutParams(mAppIconView, mAppTitleView, null, mAppInfoView);
         }
@@ -462,13 +454,6 @@
         mTitleView.setContentDescription(t.titleDescription);
         mTitleView.setTextColor(t.useLightOnPrimaryColor ?
                 mTaskBarViewLightTextColor : mTaskBarViewDarkTextColor);
-        if (!t.isDockable && ssp.hasDockedTask()) {
-            mSubTitleView.setVisibility(View.VISIBLE);
-            mSubTitleView.setTextColor(t.useLightOnPrimaryColor ?
-                    mTaskBarViewLightTextColor : mTaskBarViewDarkTextColor);
-        } else {
-            mSubTitleView.setVisibility(View.GONE);
-        }
         mDismissButton.setImageDrawable(t.useLightOnPrimaryColor ?
                 mLightDismissDrawable : mDarkDismissDrawable);
         mDismissButton.setContentDescription(t.dismissDescription);
@@ -491,7 +476,8 @@
 
         if (Recents.getDebugFlags().isFastToggleRecentsEnabled()) {
             if (mFocusTimerIndicator == null) {
-                mFocusTimerIndicator = (ProgressBar) mFocusTimerIndicatorStub.inflate();
+                mFocusTimerIndicator = (ProgressBar) Utilities.findViewStubById(this,
+                        R.id.focus_timer_indicator_stub).inflate();
             }
             mFocusTimerIndicator.getProgressDrawable()
                     .setColorFilter(
@@ -637,7 +623,8 @@
 
         // Inflate the overlay if necessary
         if (mAppOverlayView == null) {
-            mAppOverlayView = (FrameLayout) mAppOverlayViewStub.inflate();
+            mAppOverlayView = (FrameLayout) Utilities.findViewStubById(this,
+                    R.id.app_overlay_stub).inflate();
             mAppOverlayView.setBackground(mOverlayBackground);
             mAppIconView = (ImageView) mAppOverlayView.findViewById(R.id.app_icon);
             mAppIconView.setOnClickListener(this);
diff --git a/packages/SystemUI/src/com/android/systemui/stackdivider/DividerView.java b/packages/SystemUI/src/com/android/systemui/stackdivider/DividerView.java
index 3005535..8461d8e 100644
--- a/packages/SystemUI/src/com/android/systemui/stackdivider/DividerView.java
+++ b/packages/SystemUI/src/com/android/systemui/stackdivider/DividerView.java
@@ -31,12 +31,13 @@
 import android.graphics.Region.Op;
 import android.hardware.display.DisplayManager;
 import android.os.Bundle;
+import android.os.Vibrator;
 import android.util.AttributeSet;
 import android.view.Display;
 import android.view.DisplayInfo;
 import android.view.GestureDetector;
-import android.view.GestureDetector.OnDoubleTapListener;
 import android.view.GestureDetector.SimpleOnGestureListener;
+import android.view.HapticFeedbackConstants;
 import android.view.MotionEvent;
 import android.view.PointerIcon;
 import android.view.VelocityTracker;
@@ -45,7 +46,6 @@
 import android.view.ViewConfiguration;
 import android.view.ViewTreeObserver.InternalInsetsInfo;
 import android.view.ViewTreeObserver.OnComputeInternalInsetsListener;
-import android.view.ViewTreeObserver.OnGlobalLayoutListener;
 import android.view.WindowInsets;
 import android.view.WindowManager;
 import android.view.accessibility.AccessibilityNodeInfo;
@@ -133,6 +133,8 @@
     private boolean mGrowRecents;
     private ValueAnimator mCurrentAnimator;
     private boolean mEntranceAnimationRunning;
+    private boolean mExitAnimationRunning;
+    private int mExitStartPosition;
     private GestureDetector mGestureDetector;
     private boolean mDockedStackMinimized;
 
@@ -445,6 +447,7 @@
                 mDockSide = WindowManager.DOCKED_INVALID;
                 mCurrentAnimator = null;
                 mEntranceAnimationRunning = false;
+                mExitAnimationRunning = false;
                 EventBus.getDefault().send(new StoppedDragingEvent());
             }
         });
@@ -654,6 +657,13 @@
                     mOtherTaskRect);
             mWindowManagerProxy.resizeDockedStack(mDockedRect, mDockedTaskRect, null,
                     mOtherTaskRect, null);
+        } else if (mExitAnimationRunning && taskPosition != TASK_POSITION_SAME) {
+            calculateBoundsForPosition(taskPosition,
+                    mDockSide, mDockedTaskRect);
+            calculateBoundsForPosition(mExitStartPosition,
+                    DockedDividerUtils.invertDockSide(mDockSide), mOtherTaskRect);
+            mWindowManagerProxy.resizeDockedStack(mDockedRect, mDockedTaskRect, null,
+                    mOtherTaskRect, null);
         } else if (taskPosition != TASK_POSITION_SAME) {
             calculateBoundsForPosition(position, DockedDividerUtils.invertDockSide(mDockSide),
                     mOtherRect);
@@ -866,6 +876,9 @@
         mEntranceAnimationRunning = true;
         resizeStack(position, mSnapAlgorithm.getMiddleTarget().position,
                 mSnapAlgorithm.getMiddleTarget());
+
+        // Vibrate after docking
+        performHapticFeedback(HapticFeedbackConstants.VIRTUAL_KEY);
     }
 
     public final void onBusEvent(RecentsDrawnEvent drawnEvent) {
@@ -892,8 +905,13 @@
                     : mSnapAlgorithm.getDismissStartTarget();
 
             // Don't start immediately - give a little bit time to settle the drag resize change.
-            stopDragging(getCurrentPosition(), target, 336 /* duration */, 100 /* startDelay */,
+            mExitAnimationRunning = true;
+            mExitStartPosition = getCurrentPosition();
+            stopDragging(mExitStartPosition, target, 336 /* duration */, 100 /* startDelay */,
                     Interpolators.TOUCH_RESPONSE);
+
+            // Vibrate after undocking
+            performHapticFeedback(HapticFeedbackConstants.VIRTUAL_KEY);
         }
     }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivity.java b/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivity.java
index f728dab..177296b 100644
--- a/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivity.java
+++ b/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivity.java
@@ -23,6 +23,7 @@
 import android.view.MotionEvent;
 import android.view.View;
 import android.view.View.OnTouchListener;
+import android.widget.TextView;
 
 import com.android.systemui.R;
 
@@ -45,6 +46,9 @@
     protected void onCreate(@Nullable Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
         setContentView(R.layout.forced_resizable_activity);
+        TextView tv = (TextView) findViewById(com.android.internal.R.id.message);
+        tv.setText(R.string.dock_forced_resizable);
+        getWindow().setTitle(getString(R.string.dock_forced_resizable));
         getWindow().getDecorView().setOnTouchListener(this);
     }
 
diff --git a/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivityController.java b/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivityController.java
index 9b56037..9294ecd 100644
--- a/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivityController.java
+++ b/packages/SystemUI/src/com/android/systemui/stackdivider/ForcedResizableInfoActivityController.java
@@ -20,12 +20,14 @@
 import android.content.Context;
 import android.content.Intent;
 import android.os.Handler;
-import android.util.ArrayMap;
 import android.util.ArraySet;
+import android.widget.Toast;
 
+import com.android.systemui.R;
 import com.android.systemui.recents.events.EventBus;
 import com.android.systemui.recents.events.activity.AppTransitionFinishedEvent;
-import com.android.systemui.recents.events.activity.ForcedResizableEvent;
+import com.android.systemui.recents.misc.SystemServicesProxy;
+import com.android.systemui.recents.misc.SystemServicesProxy.TaskStackListener;
 import com.android.systemui.stackdivider.events.StartedDragingEvent;
 import com.android.systemui.stackdivider.events.StoppedDragingEvent;
 
@@ -53,6 +55,18 @@
     public ForcedResizableInfoActivityController(Context context) {
         mContext = context;
         EventBus.getDefault().register(this);
+        SystemServicesProxy.getInstance(context).registerTaskStackListener(
+                new TaskStackListener() {
+                    @Override
+                    public void onActivityForcedResizable(String packageName, int taskId) {
+                        activityForcedResizable(packageName, taskId);
+                    }
+
+                    @Override
+                    public void onActivityDismissingDockedStack() {
+                        activityDismissingDockedStack();
+                    }
+                });
     }
 
     public void notifyDockedStackExistsChanged(boolean exists) {
@@ -61,14 +75,6 @@
         }
     }
 
-    public final void onBusEvent(ForcedResizableEvent forcedResizableEvent) {
-        if (debounce(forcedResizableEvent.packageName)) {
-            return;
-        }
-        mPendingTaskIds.add(forcedResizableEvent.taskId);
-        postTimeout();
-    }
-
     public final void onBusEvent(AppTransitionFinishedEvent event) {
         if (!mDividerDraging) {
             showPending();
@@ -85,6 +91,20 @@
         showPending();
     }
 
+    private void activityForcedResizable(String packageName, int taskId) {
+        if (debounce(packageName)) {
+            return;
+        }
+        mPendingTaskIds.add(taskId);
+        postTimeout();
+    }
+
+    private void activityDismissingDockedStack() {
+        Toast toast = Toast.makeText(mContext, R.string.dock_non_resizeble_failed_to_dock_text,
+                Toast.LENGTH_SHORT);
+        toast.show();
+    }
+
     private void showPending() {
         mHandler.removeCallbacks(mTimeoutRunnable);
         for (int i = mPendingTaskIds.size() - 1; i >= 0; i--) {
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/BaseStatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/BaseStatusBar.java
index 1b2393a..3ac7b26 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/BaseStatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/BaseStatusBar.java
@@ -63,6 +63,8 @@
 import android.service.notification.NotificationListenerService;
 import android.service.notification.NotificationListenerService.RankingMap;
 import android.service.notification.StatusBarNotification;
+import android.service.vr.IVrManager;
+import android.service.vr.IVrStateCallbacks;
 import android.text.TextUtils;
 import android.util.ArraySet;
 import android.util.Log;
@@ -262,11 +264,24 @@
 
     protected AssistManager mAssistManager;
 
+    protected boolean mVrMode;
+
     @Override  // NotificationData.Environment
     public boolean isDeviceProvisioned() {
         return mDeviceProvisioned;
     }
 
+    private final IVrStateCallbacks mVrStateCallbacks = new IVrStateCallbacks.Stub() {
+        @Override
+        public void onVrStateChanged(boolean enabled) {
+            mVrMode = enabled;
+        }
+    };
+
+    public boolean isDeviceInVrMode() {
+        return mVrMode;
+    }
+
     protected final ContentObserver mSettingsObserver = new ContentObserver(mHandler) {
         @Override
         public void onChange(boolean selfChange) {
@@ -776,6 +791,14 @@
         mContext.registerReceiverAsUser(mAllUsersReceiver, UserHandle.ALL, allUsersFilter,
                 null, null);
         updateCurrentProfilesCache();
+
+        IVrManager vrManager = IVrManager.Stub.asInterface(ServiceManager.getService("vrmanager"));
+        try {
+            vrManager.registerListener(mVrStateCallbacks);
+        } catch (RemoteException e) {
+            Slog.e(TAG, "Failed to register VR mode state listener: " + e);
+        }
+
     }
 
     protected void notifyUserAboutHiddenNotifications() {
@@ -2353,6 +2376,10 @@
     }
 
     protected boolean shouldPeek(Entry entry, StatusBarNotification sbn) {
+        if (isDeviceInVrMode()) {
+            return false;
+        }
+
         if (mNotificationData.shouldFilterOut(sbn)) {
             if (DEBUG) Log.d(TAG, "No peeking: filtered notification: " + sbn.getKey());
             return false;
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/DismissView.java b/packages/SystemUI/src/com/android/systemui/statusbar/DismissView.java
index 3067714..2045ec8 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/DismissView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/DismissView.java
@@ -17,6 +17,7 @@
 package com.android.systemui.statusbar;
 
 import android.content.Context;
+import android.content.res.Configuration;
 import android.util.AttributeSet;
 import android.view.View;
 
@@ -51,6 +52,12 @@
                 || touchY > mContent.getY() + mContent.getHeight();
     }
 
+    @Override
+    protected void onConfigurationChanged(Configuration newConfig) {
+        super.onConfigurationChanged(newConfig);
+        mDismissButton.setText(R.string.clear_all_notifications_text);
+    }
+
     public boolean isButtonVisible() {
         return mDismissButton.getAlpha() != 0.0f;
     }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/ExpandableNotificationRow.java b/packages/SystemUI/src/com/android/systemui/statusbar/ExpandableNotificationRow.java
index 7ca7d12..e25f9de 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/ExpandableNotificationRow.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/ExpandableNotificationRow.java
@@ -618,6 +618,19 @@
         return mOnKeyguard;
     }
 
+    public void removeAllChildren() {
+        List<ExpandableNotificationRow> notificationChildren
+                = mChildrenContainer.getNotificationChildren();
+        ArrayList<ExpandableNotificationRow> clonedList = new ArrayList<>(notificationChildren);
+        for (int i = 0; i < clonedList.size(); i++) {
+            ExpandableNotificationRow row = clonedList.get(i);
+            mChildrenContainer.removeNotification(row);
+            mHeaderUtil.restoreNotificationHeader(row);
+            row.setIsChildInGroup(false, null);
+        }
+        onChildrenCountChanged();
+    }
+
     public interface ExpansionLogger {
         public void logNotificationExpansion(String key, boolean userAction, boolean expanded);
     }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcuts.java b/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcuts.java
index 977a77d..c2521b3 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcuts.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcuts.java
@@ -17,16 +17,24 @@
 package com.android.systemui.statusbar;
 
 import android.app.AlertDialog;
+import android.app.AppGlobals;
 import android.app.Dialog;
+import android.content.ComponentName;
 import android.content.Context;
 import android.content.DialogInterface;
 import android.content.DialogInterface.OnClickListener;
+import android.content.Intent;
+import android.content.pm.IPackageManager;
+import android.content.pm.PackageInfo;
+import android.content.pm.ResolveInfo;
+import android.graphics.drawable.Icon;
 import android.graphics.Bitmap;
 import android.graphics.Canvas;
 import android.graphics.drawable.Drawable;
 import android.hardware.input.InputManager;
 import android.os.Handler;
 import android.os.Looper;
+import android.os.RemoteException;
 import android.util.Log;
 import android.util.SparseArray;
 import android.view.ContextThemeWrapper;
@@ -42,12 +50,16 @@
 import android.view.WindowManager.KeyboardShortcutsReceiver;
 import android.widget.ImageView;
 import android.widget.LinearLayout;
+import android.widget.RelativeLayout;
 import android.widget.TextView;
 
+import com.android.internal.app.AssistUtils;
 import com.android.systemui.R;
 import com.android.systemui.recents.Recents;
 
 import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
 import java.util.List;
 
 import static android.content.Context.LAYOUT_INFLATER_SERVICE;
@@ -58,7 +70,6 @@
  */
 public final class KeyboardShortcuts {
     private static final String TAG = KeyboardShortcuts.class.getSimpleName();
-
     private final SparseArray<String> mSpecialCharacterNames = new SparseArray<>();
     private final SparseArray<String> mModifierNames = new SparseArray<>();
     private final SparseArray<Drawable> mSpecialCharacterDrawables = new SparseArray<>();
@@ -66,17 +77,40 @@
 
     private final Handler mHandler = new Handler(Looper.getMainLooper());
     private final Context mContext;
-    private final OnClickListener dialogCloseListener =  new DialogInterface.OnClickListener() {
+    private final IPackageManager mPackageManager;
+    private final OnClickListener mDialogCloseListener = new DialogInterface.OnClickListener() {
         public void onClick(DialogInterface dialog, int id) {
             dismissKeyboardShortcutsDialog();
         }
     };
+    private final Comparator<KeyboardShortcutInfo> mApplicationItemsComparator =
+            new Comparator<KeyboardShortcutInfo>() {
+                @Override
+                public int compare(KeyboardShortcutInfo ksh1, KeyboardShortcutInfo ksh2) {
+                    boolean ksh1ShouldBeLast = ksh1.getLabel() == null
+                            || ksh1.getLabel().toString().isEmpty();
+                    boolean ksh2ShouldBeLast = ksh2.getLabel() == null
+                            || ksh2.getLabel().toString().isEmpty();
+                    if (ksh1ShouldBeLast && ksh2ShouldBeLast) {
+                        return 0;
+                    }
+                    if (ksh1ShouldBeLast) {
+                        return 1;
+                    }
+                    if (ksh2ShouldBeLast) {
+                        return -1;
+                    }
+                    return (ksh1.getLabel().toString()).compareToIgnoreCase(
+                            ksh2.getLabel().toString());
+                }
+            };
 
     private Dialog mKeyboardShortcutsDialog;
     private KeyCharacterMap mKeyCharacterMap;
 
     public KeyboardShortcuts(Context context) {
         this.mContext = new ContextThemeWrapper(context, android.R.style.Theme_Material_Light);
+        this.mPackageManager = AppGlobals.getPackageManager();
         loadResources(context);
     }
 
@@ -244,78 +278,18 @@
     }
 
     public void toggleKeyboardShortcuts(int deviceId) {
-        InputDevice inputDevice = InputManager.getInstance().getInputDevice(deviceId);
-        if (inputDevice != null) {
-            mKeyCharacterMap = inputDevice.getKeyCharacterMap();
-        }
+        retrieveKeyCharacterMap(deviceId);
         if (mKeyboardShortcutsDialog == null) {
             Recents.getSystemServices().requestKeyboardShortcuts(mContext,
                 new KeyboardShortcutsReceiver() {
                     @Override
                     public void onKeyboardShortcutsReceived(
                             final List<KeyboardShortcutGroup> result) {
-                        KeyboardShortcutGroup systemGroup = new KeyboardShortcutGroup(
-                                mContext.getString(R.string.keyboard_shortcut_group_system), true);
-                        systemGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(R.string.keyboard_shortcut_group_system_home),
-                                KeyEvent.KEYCODE_ENTER, KeyEvent.META_META_ON));
-                        systemGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(R.string.keyboard_shortcut_group_system_back),
-                                KeyEvent.KEYCODE_DEL, KeyEvent.META_META_ON));
-                        systemGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(R.string.keyboard_shortcut_group_system_recents),
-                                KeyEvent.KEYCODE_TAB, KeyEvent.META_ALT_ON));
-                        systemGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_system_notifications),
-                                KeyEvent.KEYCODE_N, KeyEvent.META_META_ON));
-                        systemGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_system_shortcuts_helper),
-                                KeyEvent.KEYCODE_SLASH, KeyEvent.META_META_ON));
-                        systemGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_system_switch_input),
-                                KeyEvent.KEYCODE_SPACE, KeyEvent.META_META_ON));
-                        result.add(systemGroup);
-
-                        KeyboardShortcutGroup applicationGroup = new KeyboardShortcutGroup(
-                                mContext.getString(R.string.keyboard_shortcut_group_applications),
-                                true);
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_assist),
-                                KeyEvent.KEYCODE_UNKNOWN, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_browser),
-                                KeyEvent.KEYCODE_B, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_contacts),
-                                KeyEvent.KEYCODE_C, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_email),
-                                KeyEvent.KEYCODE_E, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_im),
-                                KeyEvent.KEYCODE_T, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_music),
-                                KeyEvent.KEYCODE_P, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_youtube),
-                                KeyEvent.KEYCODE_Y, KeyEvent.META_META_ON));
-                        applicationGroup.addItem(new KeyboardShortcutInfo(
-                                mContext.getString(
-                                        R.string.keyboard_shortcut_group_applications_calendar),
-                                KeyEvent.KEYCODE_L, KeyEvent.META_META_ON));
-                        result.add(applicationGroup);
-
+                        result.add(getSystemShortcuts());
+                        final KeyboardShortcutGroup appShortcuts = getDefaultApplicationShortcuts();
+                        if (appShortcuts != null) {
+                            result.add(appShortcuts);
+                        }
                         showKeyboardShortcutsDialog(result);
                     }
                 }, deviceId);
@@ -324,6 +298,35 @@
         }
     }
 
+    /**
+     * Retrieves a {@link KeyCharacterMap} and assigns it to mKeyCharacterMap. If the given id is an
+     * existing device, that device's map is used. Otherwise, it checks first all available devices
+     * and if there is a full keyboard it uses that map, otherwise falls back to the Virtual
+     * Keyboard with its default map.
+     */
+    private void retrieveKeyCharacterMap(int deviceId) {
+        final InputManager inputManager = InputManager.getInstance();
+        if (deviceId != -1) {
+            final InputDevice inputDevice = inputManager.getInputDevice(deviceId);
+            if (inputDevice != null) {
+                mKeyCharacterMap = inputDevice.getKeyCharacterMap();
+                return;
+            }
+        }
+        final int[] deviceIds = inputManager.getInputDeviceIds();
+        for (int i = 0; i < deviceIds.length; ++i) {
+            final InputDevice inputDevice = inputManager.getInputDevice(deviceIds[i]);
+            // -1 is the Virtual Keyboard, with the default key map. Use that one only as last
+            // resort.
+            if (inputDevice.getId() != -1 && inputDevice.isFullKeyboard()) {
+                mKeyCharacterMap = inputDevice.getKeyCharacterMap();
+                return;
+            }
+        }
+        final InputDevice inputDevice = inputManager.getInputDevice(-1);
+        mKeyCharacterMap = inputDevice.getKeyCharacterMap();
+    }
+
     public void dismissKeyboardShortcutsDialog() {
         if (mKeyboardShortcutsDialog != null) {
             mKeyboardShortcutsDialog.dismiss();
@@ -331,6 +334,168 @@
         }
     }
 
+    private KeyboardShortcutGroup getSystemShortcuts() {
+        final KeyboardShortcutGroup systemGroup = new KeyboardShortcutGroup(
+                mContext.getString(R.string.keyboard_shortcut_group_system), true);
+        systemGroup.addItem(new KeyboardShortcutInfo(
+                mContext.getString(R.string.keyboard_shortcut_group_system_home),
+                KeyEvent.KEYCODE_ENTER,
+                KeyEvent.META_META_ON));
+        systemGroup.addItem(new KeyboardShortcutInfo(
+                mContext.getString(R.string.keyboard_shortcut_group_system_back),
+                KeyEvent.KEYCODE_DEL,
+                KeyEvent.META_META_ON));
+        systemGroup.addItem(new KeyboardShortcutInfo(
+                mContext.getString(R.string.keyboard_shortcut_group_system_recents),
+                KeyEvent.KEYCODE_TAB,
+                KeyEvent.META_ALT_ON));
+        systemGroup.addItem(new KeyboardShortcutInfo(
+                mContext.getString(
+                        R.string.keyboard_shortcut_group_system_notifications),
+                KeyEvent.KEYCODE_N,
+                KeyEvent.META_META_ON));
+        systemGroup.addItem(new KeyboardShortcutInfo(
+                mContext.getString(
+                        R.string.keyboard_shortcut_group_system_shortcuts_helper),
+                KeyEvent.KEYCODE_SLASH,
+                KeyEvent.META_META_ON));
+        systemGroup.addItem(new KeyboardShortcutInfo(
+                mContext.getString(
+                        R.string.keyboard_shortcut_group_system_switch_input),
+                KeyEvent.KEYCODE_SPACE,
+                KeyEvent.META_META_ON));
+        return systemGroup;
+    }
+
+    private KeyboardShortcutGroup getDefaultApplicationShortcuts() {
+        final int userId = mContext.getUserId();
+        List<KeyboardShortcutInfo> keyboardShortcutInfoAppItems = new ArrayList<>();
+
+        // Assist.
+        final AssistUtils assistUtils = new AssistUtils(mContext);
+        final ComponentName assistComponent = assistUtils.getAssistComponentForUser(userId);
+        PackageInfo assistPackageInfo = null;
+        try {
+            assistPackageInfo = mPackageManager.getPackageInfo(
+                    assistComponent.getPackageName(), 0, userId);
+        } catch (RemoteException e) {
+            Log.e(TAG, "PackageManagerService is dead");
+        }
+
+        if (assistPackageInfo != null) {
+            final Icon assistIcon = Icon.createWithResource(
+                    assistPackageInfo.applicationInfo.packageName,
+                    assistPackageInfo.applicationInfo.icon);
+
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_assist),
+                    assistIcon,
+                    KeyEvent.KEYCODE_UNKNOWN,
+                    KeyEvent.META_META_ON));
+        }
+
+        // Browser.
+        final Icon browserIcon = getIconForIntentCategory(Intent.CATEGORY_APP_BROWSER, userId);
+        if (browserIcon != null) {
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_browser),
+                    browserIcon,
+                    KeyEvent.KEYCODE_B,
+                    KeyEvent.META_META_ON));
+        }
+
+
+        // Contacts.
+        final Icon contactsIcon = getIconForIntentCategory(Intent.CATEGORY_APP_CONTACTS, userId);
+        if (contactsIcon != null) {
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_contacts),
+                    contactsIcon,
+                    KeyEvent.KEYCODE_C,
+                    KeyEvent.META_META_ON));
+        }
+
+        // Email.
+        final Icon emailIcon = getIconForIntentCategory(Intent.CATEGORY_APP_EMAIL, userId);
+        if (emailIcon != null) {
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_email),
+                    emailIcon,
+                    KeyEvent.KEYCODE_E,
+                    KeyEvent.META_META_ON));
+        }
+
+        // Messaging.
+        final Icon messagingIcon = getIconForIntentCategory(Intent.CATEGORY_APP_MESSAGING, userId);
+        if (messagingIcon != null) {
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_im),
+                    messagingIcon,
+                    KeyEvent.KEYCODE_T,
+                    KeyEvent.META_META_ON));
+        }
+
+        // Music.
+        final Icon musicIcon = getIconForIntentCategory(Intent.CATEGORY_APP_MUSIC, userId);
+        if (musicIcon != null) {
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_music),
+                    musicIcon,
+                    KeyEvent.KEYCODE_P,
+                    KeyEvent.META_META_ON));
+        }
+
+        // Calendar.
+        final Icon calendarIcon = getIconForIntentCategory(Intent.CATEGORY_APP_CALENDAR, userId);
+        if (calendarIcon != null) {
+            keyboardShortcutInfoAppItems.add(new KeyboardShortcutInfo(
+                    mContext.getString(R.string.keyboard_shortcut_group_applications_calendar),
+                    calendarIcon,
+                    KeyEvent.KEYCODE_L,
+                    KeyEvent.META_META_ON));
+        }
+
+        final int itemsSize = keyboardShortcutInfoAppItems.size();
+        if (itemsSize == 0) {
+            return null;
+        }
+
+        // Sorts by label, case insensitive with nulls and/or empty labels last.
+        Collections.sort(keyboardShortcutInfoAppItems, mApplicationItemsComparator);
+        return new KeyboardShortcutGroup(
+                mContext.getString(R.string.keyboard_shortcut_group_applications),
+                keyboardShortcutInfoAppItems,
+                true);
+    }
+
+    private Icon getIconForIntentCategory(String intentCategory, int userId) {
+        final Intent intent = new Intent(Intent.ACTION_MAIN);
+        intent.addCategory(intentCategory);
+
+        final PackageInfo packageInfo = getPackageInfoForIntent(intent, userId);
+        if (packageInfo != null && packageInfo.applicationInfo.icon != 0) {
+            return Icon.createWithResource(
+                    packageInfo.applicationInfo.packageName,
+                    packageInfo.applicationInfo.icon);
+        }
+        return null;
+    }
+
+    private PackageInfo getPackageInfoForIntent(Intent intent, int userId) {
+        try {
+            ResolveInfo handler;
+            handler = mPackageManager.resolveIntent(
+                    intent, intent.resolveTypeIfNeeded(mContext.getContentResolver()), 0, userId);
+            if (handler == null || handler.activityInfo == null) {
+                return null;
+            }
+            return mPackageManager.getPackageInfo(handler.activityInfo.packageName, 0, userId);
+        } catch (RemoteException e) {
+            Log.e(TAG, "PackageManagerService is dead", e);
+            return null;
+        }
+    }
+
     private void showKeyboardShortcutsDialog(
             final List<KeyboardShortcutGroup> keyboardShortcutGroups) {
         // Need to post on the main thread.
@@ -351,7 +516,7 @@
         populateKeyboardShortcuts((LinearLayout) keyboardShortcutsView.findViewById(
                 R.id.keyboard_shortcuts_container), keyboardShortcutGroups);
         dialogBuilder.setView(keyboardShortcutsView);
-        dialogBuilder.setPositiveButton(R.string.quick_settings_done, dialogCloseListener);
+        dialogBuilder.setPositiveButton(R.string.quick_settings_done, mDialogCloseListener);
         mKeyboardShortcutsDialog = dialogBuilder.create();
         mKeyboardShortcutsDialog.setCanceledOnTouchOutside(true);
         Window keyboardShortcutsWindow = mKeyboardShortcutsDialog.getWindow();
@@ -363,8 +528,15 @@
             List<KeyboardShortcutGroup> keyboardShortcutGroups) {
         LayoutInflater inflater = LayoutInflater.from(mContext);
         final int keyboardShortcutGroupsSize = keyboardShortcutGroups.size();
+        TextView shortcutsKeyView = (TextView) inflater.inflate(
+                R.layout.keyboard_shortcuts_key_view, null, false);
+        shortcutsKeyView.measure(
+                View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED);
+        final int shortcutKeyTextItemMinWidth = shortcutsKeyView.getMeasuredHeight();
         // Needed to be able to scale the image items to the same height as the text items.
-        final int shortcutTextItemHeight = getShortcutTextItemHeight(inflater);
+        final int shortcutKeyIconItemHeightWidth = shortcutsKeyView.getMeasuredHeight()
+                - shortcutsKeyView.getPaddingTop()
+                - shortcutsKeyView.getPaddingBottom();
         for (int i = 0; i < keyboardShortcutGroupsSize; i++) {
             KeyboardShortcutGroup group = keyboardShortcutGroups.get(i);
             TextView categoryTitle = (TextView) inflater.inflate(
@@ -380,12 +552,6 @@
             final int itemsSize = group.getItems().size();
             for (int j = 0; j < itemsSize; j++) {
                 KeyboardShortcutInfo info = group.getItems().get(j);
-                if (info.getKeycode() != KeyEvent.KEYCODE_UNKNOWN
-                        && !KeyCharacterMap.deviceHasKey(info.getKeycode())) {
-                    // The user can't achieve this shortcut, so skipping.
-                    Log.w(TAG, "Keyboard Shortcut contains key not on device, skipping.");
-                    continue;
-                }
                 List<StringOrDrawable> shortcutKeys = getHumanReadableShortcutKeys(info);
                 if (shortcutKeys == null) {
                     // Ignore shortcuts we can't display keys for.
@@ -394,9 +560,23 @@
                 }
                 View shortcutView = inflater.inflate(R.layout.keyboard_shortcut_app_item,
                         shortcutContainer, false);
-                TextView textView = (TextView) shortcutView
+
+                if (info.getIcon() != null) {
+                    ImageView shortcutIcon = (ImageView) shortcutView
+                            .findViewById(R.id.keyboard_shortcuts_icon);
+                    shortcutIcon.setImageIcon(info.getIcon());
+                    shortcutIcon.setVisibility(View.VISIBLE);
+                }
+
+                TextView shortcutKeyword = (TextView) shortcutView
                         .findViewById(R.id.keyboard_shortcuts_keyword);
-                textView.setText(info.getLabel());
+                shortcutKeyword.setText(info.getLabel());
+                if (info.getIcon() != null) {
+                    RelativeLayout.LayoutParams lp =
+                            (RelativeLayout.LayoutParams) shortcutKeyword.getLayoutParams();
+                    lp.removeRule(RelativeLayout.ALIGN_PARENT_START);
+                    shortcutKeyword.setLayoutParams(lp);
+                }
 
                 ViewGroup shortcutItemsContainer = (ViewGroup) shortcutView
                         .findViewById(R.id.keyboard_shortcuts_item_container);
@@ -407,8 +587,8 @@
                         ImageView shortcutKeyIconView = (ImageView) inflater.inflate(
                                 R.layout.keyboard_shortcuts_key_icon_view, shortcutItemsContainer,
                                 false);
-                        Bitmap bitmap = Bitmap.createBitmap(shortcutTextItemHeight,
-                                shortcutTextItemHeight, Bitmap.Config.ARGB_8888);
+                        Bitmap bitmap = Bitmap.createBitmap(shortcutKeyIconItemHeightWidth,
+                                shortcutKeyIconItemHeightWidth, Bitmap.Config.ARGB_8888);
                         Canvas canvas = new Canvas(bitmap);
                         shortcutRepresentation.drawable.setBounds(0, 0, canvas.getWidth(),
                                 canvas.getHeight());
@@ -419,6 +599,7 @@
                         TextView shortcutKeyTextView = (TextView) inflater.inflate(
                                 R.layout.keyboard_shortcuts_key_view, shortcutItemsContainer,
                                 false);
+                        shortcutKeyTextView.setMinimumWidth(shortcutKeyTextItemMinWidth);
                         shortcutKeyTextView.setText(shortcutRepresentation.string);
                         shortcutItemsContainer.addView(shortcutKeyTextView);
                     }
@@ -435,16 +616,6 @@
         }
     }
 
-    private int getShortcutTextItemHeight(LayoutInflater inflater) {
-        TextView shortcutKeyTextView = (TextView) inflater.inflate(
-                R.layout.keyboard_shortcuts_key_view, null, false);
-        shortcutKeyTextView.measure(
-                View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED);
-        return shortcutKeyTextView.getMeasuredHeight()
-                - shortcutKeyTextView.getPaddingTop()
-                - shortcutKeyTextView.getPaddingBottom();
-    }
-
     private List<StringOrDrawable> getHumanReadableShortcutKeys(KeyboardShortcutInfo info) {
         List<StringOrDrawable> shortcutKeys = getHumanReadableModifiers(info);
         if (shortcutKeys == null) {
@@ -463,9 +634,7 @@
             if (info.getKeycode() == KeyEvent.KEYCODE_UNKNOWN) {
                 return shortcutKeys;
             }
-            // TODO: Have a generic map for when we don't have the device's.
-            char displayLabel = mKeyCharacterMap == null
-                    ? 0 : mKeyCharacterMap.getDisplayLabel(info.getKeycode());
+            char displayLabel = mKeyCharacterMap.getDisplayLabel(info.getKeycode());
             if (displayLabel != 0) {
                 displayLabelString = String.valueOf(displayLabel);
             } else {
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcutsReceiver.java b/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcutsReceiver.java
new file mode 100644
index 0000000..5d22faf
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/KeyboardShortcutsReceiver.java
@@ -0,0 +1,33 @@
+/*
+ * 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 com.android.systemui.statusbar;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+
+/**
+ * Receiver for the Keyboard Shortcuts Helper.
+ */
+public class KeyboardShortcutsReceiver extends BroadcastReceiver {
+    @Override
+    public void onReceive(Context context, Intent intent) {
+        if (Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS.equals(intent.getAction())) {
+            final KeyboardShortcuts keyboardShortcuts = new KeyboardShortcuts(context);
+            keyboardShortcuts.toggleKeyboardShortcuts(-1 /* deviceId unknown */);
+        }
+    }
+}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationContentView.java b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationContentView.java
index 5b00523..491ffde 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationContentView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationContentView.java
@@ -348,6 +348,12 @@
         setVisible(isShown());
     }
 
+    @Override
+    protected void onDetachedFromWindow() {
+        super.onDetachedFromWindow();
+        getViewTreeObserver().removeOnPreDrawListener(mEnableAnimationPredrawListener);
+    }
+
     private void setVisible(final boolean isVisible) {
         if (isVisible) {
 
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationData.java b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationData.java
index c9fe2bd..6570221 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationData.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationData.java
@@ -34,6 +34,7 @@
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Comparator;
+import java.util.Map;
 import java.util.Objects;
 
 /**
@@ -257,16 +258,21 @@
     }
 
     public void add(Entry entry, RankingMap ranking) {
-        mEntries.put(entry.notification.getKey(), entry);
-        updateRankingAndSort(ranking);
+        synchronized (mEntries) {
+            mEntries.put(entry.notification.getKey(), entry);
+        }
         mGroupManager.onEntryAdded(entry);
+        updateRankingAndSort(ranking);
     }
 
     public Entry remove(String key, RankingMap ranking) {
-        Entry removed = mEntries.remove(key);
+        Entry removed = null;
+        synchronized (mEntries) {
+            removed = mEntries.remove(key);
+        }
         if (removed == null) return null;
-        updateRankingAndSort(ranking);
         mGroupManager.onEntryRemoved(removed);
+        updateRankingAndSort(ranking);
         return removed;
     }
 
@@ -316,9 +322,30 @@
         return Ranking.IMPORTANCE_UNSPECIFIED;
     }
 
+    public String getOverrideGroupKey(String key) {
+        if (mRankingMap != null) {
+            mRankingMap.getRanking(key, mTmpRanking);
+            return mTmpRanking.getOverrideGroupKey();
+        }
+         return null;
+    }
+
     private void updateRankingAndSort(RankingMap ranking) {
         if (ranking != null) {
             mRankingMap = ranking;
+            synchronized (mEntries) {
+                final int N = mEntries.size();
+                for (int i = 0; i < N; i++) {
+                    Entry entry = mEntries.valueAt(i);
+                    final StatusBarNotification oldSbn = entry.notification.clone();
+                    final String overrideGroupKey = getOverrideGroupKey(entry.key);
+                    if (!Objects.equals(oldSbn.getOverrideGroupKey(), overrideGroupKey)) {
+                        entry.notification.setOverrideGroupKey(overrideGroupKey);
+                        mGroupManager.onEntryUpdated(entry, oldSbn);
+                    }
+                    //mGroupManager.onEntryBundlingUpdated(entry, getOverrideGroupKey(entry.key));
+                }
+            }
         }
         filterAndSort();
     }
@@ -328,16 +355,18 @@
     public void filterAndSort() {
         mSortedAndFiltered.clear();
 
-        final int N = mEntries.size();
-        for (int i = 0; i < N; i++) {
-            Entry entry = mEntries.valueAt(i);
-            StatusBarNotification sbn = entry.notification;
+        synchronized (mEntries) {
+            final int N = mEntries.size();
+            for (int i = 0; i < N; i++) {
+                Entry entry = mEntries.valueAt(i);
+                StatusBarNotification sbn = entry.notification;
 
-            if (shouldFilterOut(sbn)) {
-                continue;
+                if (shouldFilterOut(sbn)) {
+                    continue;
+                }
+
+                mSortedAndFiltered.add(entry);
             }
-
-            mSortedAndFiltered.add(entry);
         }
 
         Collections.sort(mSortedAndFiltered, mRankingComparator);
@@ -398,16 +427,17 @@
             NotificationData.Entry e = mSortedAndFiltered.get(active);
             dumpEntry(pw, indent, active, e);
         }
-
-        int M = mEntries.size();
-        pw.print(indent);
-        pw.println("inactive notifications: " + (M - active));
-        int inactiveCount = 0;
-        for (int i = 0; i < M; i++) {
-            Entry entry = mEntries.valueAt(i);
-            if (!mSortedAndFiltered.contains(entry)) {
-                dumpEntry(pw, indent, inactiveCount, entry);
-                inactiveCount++;
+        synchronized (mEntries) {
+            int M = mEntries.size();
+            pw.print(indent);
+            pw.println("inactive notifications: " + (M - active));
+            int inactiveCount = 0;
+            for (int i = 0; i < M; i++) {
+                Entry entry = mEntries.valueAt(i);
+                if (!mSortedAndFiltered.contains(entry)) {
+                    dumpEntry(pw, indent, inactiveCount, entry);
+                    inactiveCount++;
+                }
             }
         }
     }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationSettingsIconRow.java b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationSettingsIconRow.java
index a5ebbba..9ed5022 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationSettingsIconRow.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationSettingsIconRow.java
@@ -232,8 +232,9 @@
             return;
         }
         final boolean isRtl = mParent.isLayoutRtl();
-        final float left = isRtl ? -(mParent.getWidth() - mHorizSpaceForGear) : 0;
-        final float right = isRtl ? 0 : (mParent.getWidth() - mHorizSpaceForGear);
+        // TODO No need to cast to float here once b/28050538 is fixed.
+        final float left = (float) (isRtl ? -(mParent.getWidth() - mHorizSpaceForGear) : 0);
+        final float right = (float) (isRtl ? 0 : (mParent.getWidth() - mHorizSpaceForGear));
         setTranslationX(onLeft ? left : right);
         mOnLeft = onLeft;
     }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/car/CarBatteryController.java b/packages/SystemUI/src/com/android/systemui/statusbar/car/CarBatteryController.java
new file mode 100644
index 0000000..244536d
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/car/CarBatteryController.java
@@ -0,0 +1,276 @@
+/*
+ * 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 com.android.systemui.statusbar.car;
+
+import android.bluetooth.BluetoothAdapter;
+import android.bluetooth.BluetoothDevice;
+import android.bluetooth.BluetoothHeadsetClient;
+import android.bluetooth.BluetoothProfile;
+import android.bluetooth.BluetoothProfile.ServiceListener;
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.os.Bundle;
+import android.util.Log;
+
+import com.android.systemui.statusbar.policy.BatteryController;
+
+import java.io.FileDescriptor;
+import java.io.PrintWriter;
+import java.util.ArrayList;
+
+/**
+ * A {@link BatteryController} that is specific to the Auto use-case. For Auto, the battery icon
+ * displays the battery status of a device that is connected via bluetooth and not the system's
+ * battery.
+ */
+public class CarBatteryController extends BroadcastReceiver implements BatteryController {
+    private static final String TAG = "CarBatteryController";
+
+    // According to the Bluetooth HFP 1.5 specification, battery levels are indicated by a
+    // value from 1-5, where these values represent the following:
+    // 0%% - 0, 1-25%% - 1, 26-50%% - 2, 51-75%% - 3, 76-99%% - 4, 100%% - 5
+    // As a result, set the level as the average within that range.
+    private static final int BATTERY_LEVEL_EMPTY = 0;
+    private static final int BATTERY_LEVEL_1 = 12;
+    private static final int BATTERY_LEVEL_2 = 28;
+    private static final int BATTERY_LEVEL_3 = 63;
+    private static final int BATTERY_LEVEL_4 = 87;
+    private static final int BATTERY_LEVEL_FULL = 100;
+
+    private static final int INVALID_BATTERY_LEVEL = -1;
+
+    private final Context mContext;
+
+    private final BluetoothAdapter mAdapter = BluetoothAdapter.getDefaultAdapter();
+    private BluetoothHeadsetClient mBluetoothHeadsetClient;
+
+    private final ArrayList<BatteryStateChangeCallback> mChangeCallbacks = new ArrayList<>();
+
+    private int mLevel;
+
+    /**
+     * An interface indicating the container of a View that will display what the information
+     * in the {@link CarBatteryController}.
+     */
+    public interface BatteryViewHandler {
+        void hideBatteryView();
+        void showBatteryView();
+    }
+
+    private BatteryViewHandler mBatteryViewHandler;
+
+    public CarBatteryController(Context context) {
+        mContext = context;
+
+        mAdapter.getProfileProxy(context.getApplicationContext(), mHfpServiceListener,
+                BluetoothProfile.HEADSET_CLIENT);
+    }
+
+    @Override
+    public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
+        pw.println("CarBatteryController state:");
+        pw.print("    mLevel=");
+        pw.println(mLevel);
+    }
+
+    @Override
+    public void setPowerSaveMode(boolean powerSave) {
+        // No-op. No power save mode for the car.
+    }
+
+    @Override
+    public void addStateChangedCallback(BatteryController.BatteryStateChangeCallback cb) {
+        mChangeCallbacks.add(cb);
+
+        // There is no way to know if the phone is plugged in or charging via bluetooth, so pass
+        // false for these values.
+        cb.onBatteryLevelChanged(mLevel, false /* pluggedIn */, false /* charging */);
+        cb.onPowerSaveChanged(false /* isPowerSave */);
+    }
+
+    @Override
+    public void removeStateChangedCallback(BatteryController.BatteryStateChangeCallback cb) {
+        mChangeCallbacks.remove(cb);
+    }
+
+    public void addBatteryViewHandler(BatteryViewHandler batteryViewHandler) {
+        mBatteryViewHandler = batteryViewHandler;
+    }
+
+    public void startListening() {
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(BluetoothHeadsetClient.ACTION_CONNECTION_STATE_CHANGED);
+        filter.addAction(BluetoothHeadsetClient.ACTION_AG_EVENT);
+        mContext.registerReceiver(this, filter);
+    }
+
+    public void stopListening() {
+        mContext.unregisterReceiver(this);
+    }
+
+    @Override
+    public void onReceive(Context context, Intent intent) {
+        String action = intent.getAction();
+
+        if (Log.isLoggable(TAG, Log.DEBUG)) {
+            Log.d(TAG, "onReceive(). action: " + action);
+        }
+
+        if (BluetoothHeadsetClient.ACTION_AG_EVENT.equals(action)) {
+            if (Log.isLoggable(TAG, Log.DEBUG)) {
+                Log.d(TAG, "Received ACTION_AG_EVENT");
+            }
+
+            int batteryLevel = intent.getIntExtra(BluetoothHeadsetClient.EXTRA_BATTERY_LEVEL,
+                    INVALID_BATTERY_LEVEL);
+
+            updateBatteryLevel(batteryLevel);
+
+            if (batteryLevel != INVALID_BATTERY_LEVEL && mBatteryViewHandler != null) {
+                mBatteryViewHandler.showBatteryView();
+            }
+        } else if (BluetoothHeadsetClient.ACTION_CONNECTION_STATE_CHANGED.equals(action)) {
+            int newState = intent.getIntExtra(BluetoothProfile.EXTRA_STATE, -1);
+
+            if (Log.isLoggable(TAG, Log.DEBUG)) {
+                int oldState = intent.getIntExtra(BluetoothProfile.EXTRA_PREVIOUS_STATE, -1);
+                Log.d(TAG, "ACTION_CONNECTION_STATE_CHANGED event: "
+                        + oldState + " -> " + newState);
+
+            }
+            BluetoothDevice device =
+                    (BluetoothDevice)intent.getExtra(BluetoothDevice.EXTRA_DEVICE);
+            updateBatteryIcon(device, newState);
+        }
+    }
+
+    /**
+     * Converts the battery level to a percentage that can be displayed on-screen and notifies
+     * any {@link BatteryStateChangeCallback}s of this.
+     */
+    private void updateBatteryLevel(int batteryLevel) {
+        if (batteryLevel == INVALID_BATTERY_LEVEL) {
+            if (Log.isLoggable(TAG, Log.DEBUG)) {
+                Log.d(TAG, "Battery level invalid. Ignoring.");
+            }
+            return;
+        }
+
+        // The battery level is a value between 0-5. Let the default battery level be 0.
+        switch (batteryLevel) {
+            case 5:
+                mLevel = BATTERY_LEVEL_FULL;
+                break;
+            case 4:
+                mLevel = BATTERY_LEVEL_4;
+                break;
+            case 3:
+                mLevel = BATTERY_LEVEL_3;
+                break;
+            case 2:
+                mLevel = BATTERY_LEVEL_2;
+                break;
+            case 1:
+                mLevel = BATTERY_LEVEL_1;
+                break;
+            case 0:
+            default:
+                mLevel = BATTERY_LEVEL_EMPTY;
+        }
+
+        if (Log.isLoggable(TAG, Log.DEBUG)) {
+            Log.d(TAG, "Battery level: " + batteryLevel + "; setting mLevel as: " + mLevel);
+        }
+
+        notifyBatteryLevelChanged();
+    }
+
+    /**
+     * Updates the display of the battery icon depending on the given connection state from the
+     * given {@link BluetoothDevice}.
+     */
+    private void updateBatteryIcon(BluetoothDevice device, int newState) {
+        if (newState == BluetoothProfile.STATE_CONNECTED) {
+            if (Log.isLoggable(TAG, Log.DEBUG)) {
+                Log.d(TAG, "Device connected");
+            }
+
+            if (mBatteryViewHandler != null) {
+                mBatteryViewHandler.showBatteryView();
+            }
+
+            if (mBluetoothHeadsetClient == null || device == null) {
+                return;
+            }
+
+            // Check if battery information is available and immediately update.
+            Bundle featuresBundle = mBluetoothHeadsetClient.getCurrentAgEvents(device);
+            if (featuresBundle == null) {
+                return;
+            }
+
+            int batteryLevel = featuresBundle.getInt(BluetoothHeadsetClient.EXTRA_BATTERY_LEVEL,
+                    INVALID_BATTERY_LEVEL);
+            updateBatteryLevel(batteryLevel);
+        } else if (newState == BluetoothProfile.STATE_DISCONNECTED) {
+            if (Log.isLoggable(TAG, Log.DEBUG)) {
+                Log.d(TAG, "Device disconnected");
+            }
+
+            if (mBatteryViewHandler != null) {
+                mBatteryViewHandler.hideBatteryView();
+            }
+        }
+    }
+
+    @Override
+    public void dispatchDemoCommand(String command, Bundle args) {
+        // TODO: Car demo mode.
+    }
+
+    @Override
+    public boolean isPowerSave() {
+        // Power save is not valid for the car, so always return false.
+        return false;
+    }
+
+    private void notifyBatteryLevelChanged() {
+        for (int i = 0, size = mChangeCallbacks.size(); i < size; i++) {
+            mChangeCallbacks.get(i)
+                    .onBatteryLevelChanged(mLevel, false /* pluggedIn */, false /* charging */);
+        }
+    }
+
+    private final ServiceListener mHfpServiceListener = new ServiceListener() {
+        @Override
+        public void onServiceConnected(int profile, BluetoothProfile proxy) {
+            if (profile == BluetoothProfile.HEADSET_CLIENT) {
+                mBluetoothHeadsetClient = (BluetoothHeadsetClient) proxy;
+            }
+        }
+
+        @Override
+        public void onServiceDisconnected(int profile) {
+            if (profile == BluetoothProfile.HEADSET_CLIENT) {
+                mBluetoothHeadsetClient = null;
+            }
+        }
+    };
+
+}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java
index 4add3cb..811687c 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java
@@ -22,37 +22,75 @@
 import android.content.Intent;
 import android.content.IntentFilter;
 import android.graphics.PixelFormat;
-import android.os.Handler;
-import android.os.Looper;
-import android.os.RemoteException;
+import android.util.Log;
 import android.view.View;
 import android.view.ViewGroup.LayoutParams;
 import android.view.ViewStub;
 import android.view.WindowManager;
-
+import com.android.systemui.BatteryMeterView;
 import com.android.systemui.R;
 import com.android.systemui.recents.Recents;
 import com.android.systemui.recents.misc.SystemServicesProxy;
 import com.android.systemui.recents.misc.SystemServicesProxy.TaskStackListener;
 import com.android.systemui.statusbar.StatusBarState;
 import com.android.systemui.statusbar.phone.PhoneStatusBar;
+import com.android.systemui.statusbar.phone.PhoneStatusBarView;
+import com.android.systemui.statusbar.policy.BatteryController;
 
 /**
  * A status bar (and navigation bar) tailored for the automotive use case.
  */
-public class CarStatusBar extends PhoneStatusBar {
+public class CarStatusBar extends PhoneStatusBar implements
+        CarBatteryController.BatteryViewHandler {
+    private static final String TAG = "CarStatusBar";
+
     private TaskStackListenerImpl mTaskStackListener;
 
     private CarNavigationBarView mCarNavigationBar;
     private CarNavigationBarController mController;
     private FullscreenUserSwitcher mFullscreenUserSwitcher;
 
+    private CarBatteryController mCarBatteryController;
+    private BatteryMeterView mBatteryMeterView;
+
     @Override
     public void start() {
         super.start();
         mTaskStackListener = new TaskStackListenerImpl();
         SystemServicesProxy.getInstance(mContext).registerTaskStackListener(mTaskStackListener);
         registerPackageChangeReceivers();
+
+        mCarBatteryController.startListening();
+    }
+
+    @Override
+    public void destroy() {
+        mCarBatteryController.stopListening();
+        super.destroy();
+    }
+
+    @Override
+    protected PhoneStatusBarView makeStatusBarView() {
+        PhoneStatusBarView statusBarView = super.makeStatusBarView();
+
+        mBatteryMeterView = ((BatteryMeterView) statusBarView.findViewById(R.id.battery));
+
+        // By default, the BatteryMeterView should not be visible. It will be toggled visible
+        // when a device has connected by bluetooth.
+        mBatteryMeterView.setVisibility(View.GONE);
+
+        if (Log.isLoggable(TAG, Log.DEBUG)) {
+            Log.d(TAG, "makeStatusBarView(). mBatteryMeterView: " + mBatteryMeterView);
+        }
+
+        return statusBarView;
+    }
+
+    @Override
+    protected BatteryController createBatteryController() {
+        mCarBatteryController = new CarBatteryController(mContext);
+        mCarBatteryController.addBatteryViewHandler(this);
+        return mCarBatteryController;
     }
 
     @Override
@@ -85,6 +123,28 @@
 
     }
 
+    @Override
+    public void showBatteryView() {
+        if (Log.isLoggable(TAG, Log.DEBUG)) {
+            Log.d(TAG, "showBatteryView(). mBatteryMeterView: " + mBatteryMeterView);
+        }
+
+        if (mBatteryMeterView != null) {
+            mBatteryMeterView.setVisibility(View.VISIBLE);
+        }
+    }
+
+    @Override
+    public void hideBatteryView() {
+        if (Log.isLoggable(TAG, Log.DEBUG)) {
+            Log.d(TAG, "hideBatteryView(). mBatteryMeterView: " + mBatteryMeterView);
+        }
+
+        if (mBatteryMeterView != null) {
+            mBatteryMeterView.setVisibility(View.GONE);
+        }
+    }
+
     private BroadcastReceiver mPackageChangeReceiver = new BroadcastReceiver() {
         @Override
         public void onReceive(Context context, Intent intent) {
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NotificationGroupManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NotificationGroupManager.java
index f7a6b271..fffb20a 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NotificationGroupManager.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NotificationGroupManager.java
@@ -26,6 +26,8 @@
 
 import java.util.HashMap;
 import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Objects;
 
 /**
  * A class to handle notifications and their corresponding groups.
@@ -36,6 +38,7 @@
     private OnGroupChangeListener mListener;
     private int mBarState = -1;
     private HashMap<String, StatusBarNotification> mIsolatedEntries = new HashMap<>();
+    private HeadsUpManager mHeadsUpManager;
 
     public void setOnGroupChangeListener(OnGroupChangeListener listener) {
         mListener = listener;
@@ -121,6 +124,15 @@
         }
     }
 
+    public void onEntryBundlingUpdated(final NotificationData.Entry updated,
+            final String overrideGroupKey) {
+        final StatusBarNotification oldSbn = updated.notification.clone();
+        if (!Objects.equals(oldSbn.getOverrideGroupKey(), overrideGroupKey)) {
+            updated.notification.setOverrideGroupKey(overrideGroupKey);
+            onEntryUpdated(updated, oldSbn);
+        }
+    }
+
     private void updateSuppression(NotificationGroup group) {
         if (group == null) {
             return;
@@ -129,9 +141,12 @@
         group.suppressed = group.summary != null && !group.expanded
                 && (group.children.size() == 1
                 || (group.children.size() == 0
-                        && !group.summary.notification.getNotification().isGroupChild()
+                        && group.summary.notification.getNotification().isGroupSummary()
                         && hasIsolatedChildren(group)));
         if (prevSuppressed != group.suppressed) {
+            if (group.suppressed) {
+                handleSuppressedSummaryHeadsUpped(group.summary);
+            }
             mListener.onGroupsChanged();
         }
     }
@@ -150,6 +165,15 @@
         return count;
     }
 
+    private NotificationData.Entry getIsolatedChild(String groupKey) {
+        for (StatusBarNotification sbn : mIsolatedEntries.values()) {
+            if (sbn.getGroupKey().equals(groupKey) && isIsolated(sbn)) {
+                return mGroupMap.get(sbn.getKey()).summary;
+            }
+        }
+        return null;
+    }
+
     public void onEntryUpdated(NotificationData.Entry entry,
             StatusBarNotification oldNotification) {
         if (mGroupMap.get(getGroupKey(oldNotification)) != null) {
@@ -173,7 +197,7 @@
 
     public boolean isOnlyChildInSuppressedGroup(StatusBarNotification sbn) {
         return isGroupSuppressed(sbn.getGroupKey())
-                && sbn.getNotification().isGroupChild()
+                && !sbn.getNotification().isGroupSummary()
                 && getTotalNumberOfChildren(sbn) == 1;
     }
 
@@ -278,11 +302,12 @@
         }
         return sbn.getNotification().isGroupSummary();
     }
+
     private boolean isGroupChild(StatusBarNotification sbn) {
         if (isIsolated(sbn)) {
             return false;
         }
-        return sbn.getNotification().isGroupChild();
+        return sbn.isGroup() && !sbn.getNotification().isGroupSummary();
     }
 
     private String getGroupKey(StatusBarNotification sbn) {
@@ -321,6 +346,9 @@
                 // it doesn't lead to an update.
                 updateSuppression(mGroupMap.get(entry.notification.getGroupKey()));
                 mListener.onGroupsChanged();
+            } else {
+                handleSuppressedSummaryHeadsUpped(entry);
+
             }
         } else {
             if (mIsolatedEntries.containsKey(sbn.getKey())) {
@@ -333,9 +361,35 @@
         }
     }
 
+    private void handleSuppressedSummaryHeadsUpped(NotificationData.Entry entry) {
+        StatusBarNotification sbn = entry.notification;
+        if (!isGroupSuppressed(sbn.getGroupKey())
+                || !sbn.getNotification().isGroupSummary()
+                || !entry.row.isHeadsUp()) {
+            return;
+        }
+        // The parent of a suppressed group got huned, lets hun the child!
+        NotificationGroup notificationGroup = mGroupMap.get(sbn.getGroupKey());
+        if (notificationGroup != null) {
+            Iterator<NotificationData.Entry> iterator = notificationGroup.children.iterator();
+            NotificationData.Entry child = iterator.hasNext() ? iterator.next() : null;
+            if (child == null) {
+                child = getIsolatedChild(sbn.getGroupKey());
+            }
+            if (child != null) {
+                if (mHeadsUpManager.isHeadsUp(child.key)) {
+                    mHeadsUpManager.updateNotification(child, true);
+                } else {
+                    mHeadsUpManager.showNotification(child);
+                }
+            }
+        }
+        mHeadsUpManager.releaseImmediately(entry.key);
+    }
+
     private boolean shouldIsolate(StatusBarNotification sbn) {
         NotificationGroup notificationGroup = mGroupMap.get(sbn.getGroupKey());
-        return sbn.getNotification().isGroupChild()
+        return (sbn.isGroup() && !sbn.getNotification().isGroupSummary())
                 && (sbn.getNotification().fullScreenIntent != null
                         || notificationGroup == null
                         || !notificationGroup.expanded
@@ -349,6 +403,10 @@
                 || notificationGroup.summary.row.getTranslationY() < 0;
     }
 
+    public void setHeadsUpManager(HeadsUpManager headsUpManager) {
+        mHeadsUpManager = headsUpManager;
+    }
+
     public static class NotificationGroup {
         public final HashSet<NotificationData.Entry> children = new HashSet<>();
         public NotificationData.Entry summary;
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java
index bf58592..f68b24b 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java
@@ -21,9 +21,7 @@
 import android.animation.AnimatorListenerAdapter;
 import android.annotation.NonNull;
 import android.app.ActivityManager;
-import android.app.ActivityManager.StackId;
 import android.app.ActivityManagerNative;
-import android.app.ActivityOptions;
 import android.app.IActivityManager;
 import android.app.Notification;
 import android.app.PendingIntent;
@@ -147,6 +145,7 @@
 import com.android.systemui.statusbar.policy.AccessibilityController;
 import com.android.systemui.statusbar.policy.BatteryController;
 import com.android.systemui.statusbar.policy.BatteryController.BatteryStateChangeCallback;
+import com.android.systemui.statusbar.policy.BatteryControllerImpl;
 import com.android.systemui.statusbar.policy.BluetoothControllerImpl;
 import com.android.systemui.statusbar.policy.BrightnessMirrorController;
 import com.android.systemui.statusbar.policy.CastControllerImpl;
@@ -730,6 +729,7 @@
         mHeadsUpManager.addListener(mGroupManager);
         mNotificationPanel.setHeadsUpManager(mHeadsUpManager);
         mNotificationData.setHeadsUpManager(mHeadsUpManager);
+        mGroupManager.setHeadsUpManager(mHeadsUpManager);
 
         if (MULTIUSER_DEBUG) {
             mNotificationPanelDebugText = (TextView) mNotificationPanel.findViewById(
@@ -826,7 +826,7 @@
         // Other icons
         mLocationController = new LocationControllerImpl(mContext,
                 mHandlerThread.getLooper()); // will post a notification
-        mBatteryController = new BatteryController(mContext);
+        mBatteryController = createBatteryController();
         mBatteryController.addStateChangedCallback(new BatteryStateChangeCallback() {
             @Override
             public void onPowerSaveChanged(boolean isPowerSave) {
@@ -943,6 +943,10 @@
         return mStatusBarView;
     }
 
+    protected BatteryController createBatteryController() {
+        return new BatteryControllerImpl(mContext);
+    }
+
     @Override
     protected void reInflateViews() {
         super.reInflateViews();
@@ -1167,7 +1171,9 @@
 
         @Override
         public boolean onLongClick(View v) {
-            if (mRecents == null || !ActivityManager.supportsMultiWindow()) {
+            if (mRecents == null || !ActivityManager.supportsMultiWindow()
+                    || !getComponent(Divider.class).getView().getSnapAlgorithm()
+                            .isSplitScreenFeasible()) {
                 return false;
             }
 
@@ -1368,6 +1374,10 @@
     }
 
     private boolean shouldSuppressFullScreenIntent(String key) {
+        if (isDeviceInVrMode()) {
+            return true;
+        }
+
         if (mPowerManager.isInteractive()) {
             return mNotificationData.shouldSuppressScreenOn(key);
         } else {
@@ -1525,6 +1535,9 @@
                 // we are only transfering this notification to its parent, don't generate an animation
                 mStackScroller.setChildTransferInProgress(true);
             }
+            if (remove.isSummaryWithChildren()) {
+                remove.removeAllChildren();
+            }
             mStackScroller.removeView(remove);
             mStackScroller.setChildTransferInProgress(false);
         }
@@ -3461,7 +3474,7 @@
             @Override
             public void run() {
                 mLeaveOpenOnKeyguardHide = true;
-                executeRunnableDismissingKeyguard(runnable, null, false, true);
+                executeRunnableDismissingKeyguard(runnable, null, false, false);
             }
         });
     }
@@ -3582,11 +3595,10 @@
             dispatchDemoCommandToView(command, args, R.id.clock);
         }
         if (modeChange || command.equals(COMMAND_BATTERY)) {
-            dispatchDemoCommandToView(command, args, R.id.battery);
+            mBatteryController.dispatchDemoCommand(command, args);
         }
         if (modeChange || command.equals(COMMAND_STATUS)) {
             mIconController.dispatchDemoCommand(command, args);
-
         }
         if (mNetworkController != null && (modeChange || command.equals(COMMAND_NETWORK))) {
             mNetworkController.dispatchDemoCommand(command, args);
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/QuickStatusBarHeader.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/QuickStatusBarHeader.java
index ea9a5a5..2b03dfb 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/QuickStatusBarHeader.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/QuickStatusBarHeader.java
@@ -125,6 +125,7 @@
         // RenderThread is doing more harm than good when touching the header (to expand quick
         // settings), so disable it for this view
         ((RippleDrawable) mSettingsButton.getBackground()).setForceSoftware(true);
+        ((RippleDrawable) mExpandIndicator.getBackground()).setForceSoftware(true);
 
         updateResources();
     }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/UserAvatarView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/UserAvatarView.java
index 093a827..dc1b35d 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/UserAvatarView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/UserAvatarView.java
@@ -17,69 +17,57 @@
 package com.android.systemui.statusbar.phone;
 
 import android.content.Context;
+import android.content.res.ColorStateList;
 import android.content.res.TypedArray;
 import android.graphics.Bitmap;
-import android.graphics.BitmapShader;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
 import android.graphics.PorterDuff;
-import android.graphics.PorterDuffColorFilter;
-import android.graphics.Shader;
 import android.graphics.drawable.Drawable;
 import android.util.AttributeSet;
 import android.view.View;
 
+import com.android.settingslib.drawable.UserIconDrawable;
 import com.android.systemui.R;
 
 /**
- * A view that displays a user image cropped to a circle with a frame.
+ * A view that displays a user image cropped to a circle with an optional frame.
  */
 public class UserAvatarView extends View {
 
-    private int mActiveFrameColor;
-    private int mFrameColor;
-    private float mFrameWidth;
-    private float mFramePadding;
-    private Bitmap mBitmap;
-    private Drawable mDrawable;
-    private boolean mIsDisabled;
-
-    private final Paint mFramePaint = new Paint();
-    private final Paint mBitmapPaint = new Paint();
-    private final Matrix mDrawMatrix = new Matrix();
-
-    private float mScale = 1;
+    private final UserIconDrawable mDrawable = new UserIconDrawable();
 
     public UserAvatarView(Context context, AttributeSet attrs,
             int defStyleAttr,
             int defStyleRes) {
         super(context, attrs, defStyleAttr, defStyleRes);
+
         final TypedArray a = context.obtainStyledAttributes(
                 attrs, R.styleable.UserAvatarView, defStyleAttr, defStyleRes);
         final int N = a.getIndexCount();
         for (int i = 0; i < N; i++) {
             int attr = a.getIndex(i);
             switch (attr) {
+                case R.styleable.UserAvatarView_avatarPadding:
+                    setAvatarPadding(a.getDimension(attr, 0));
+                    break;
                 case R.styleable.UserAvatarView_frameWidth:
                     setFrameWidth(a.getDimension(attr, 0));
                     break;
                 case R.styleable.UserAvatarView_framePadding:
                     setFramePadding(a.getDimension(attr, 0));
                     break;
-                case R.styleable.UserAvatarView_activeFrameColor:
-                    setActiveFrameColor(a.getColor(attr, 0));
-                    break;
                 case R.styleable.UserAvatarView_frameColor:
-                    setFrameColor(a.getColor(attr, 0));
+                    setFrameColor(a.getColorStateList(attr));
+                    break;
+                case R.styleable.UserAvatarView_badgeDiameter:
+                    setBadgeDiameter(a.getDimension(attr, 0));
+                    break;
+                case R.styleable.UserAvatarView_badgeMargin:
+                    setBadgeMargin(a.getDimension(attr, 0));
                     break;
             }
         }
         a.recycle();
-
-        mFramePaint.setAntiAlias(true);
-        mFramePaint.setStyle(Paint.Style.STROKE);
-        mBitmapPaint.setAntiAlias(true);
+        setBackground(mDrawable);
     }
 
     public UserAvatarView(Context context, AttributeSet attrs, int defStyleAttr) {
@@ -94,180 +82,61 @@
         this(context, null);
     }
 
+    /**
+     * @deprecated use {@link #setAvatar(Bitmap)} instead.
+     */
+    @Deprecated
     public void setBitmap(Bitmap bitmap) {
-        setDrawable(null);
-        mBitmap = bitmap;
-        if (mBitmap != null) {
-            mBitmapPaint.setShader(new BitmapShader(
-                    bitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP));
-        } else {
-            mBitmapPaint.setShader(null);
-        }
-        configureBounds();
-        invalidate();
+        setAvatar(bitmap);
     }
 
-    public void setFrameColor(int frameColor) {
-        mFrameColor = frameColor;
-        invalidate();
-    }
-
-    public void setActiveFrameColor(int activeFrameColor) {
-        mActiveFrameColor = activeFrameColor;
-        invalidate();
+    public void setFrameColor(ColorStateList color) {
+        mDrawable.setFrameColor(color);
     }
 
     public void setFrameWidth(float frameWidth) {
-        mFrameWidth = frameWidth;
-        invalidate();
+        mDrawable.setFrameWidth(frameWidth);
     }
 
     public void setFramePadding(float framePadding) {
-        mFramePadding = framePadding;
-        invalidate();
+        mDrawable.setFramePadding(framePadding);
     }
 
-    @Override
-    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
-        super.onLayout(changed, left, top, right, bottom);
-        configureBounds();
+    public void setAvatarPadding(float avatarPadding) {
+        mDrawable.setPadding(avatarPadding);
     }
 
-    public void configureBounds() {
-        int vwidth = getWidth() - mPaddingLeft - mPaddingRight;
-        int vheight = getHeight() - mPaddingTop - mPaddingBottom;
-
-        int dwidth;
-        int dheight;
-        if (mBitmap != null) {
-            dwidth = mBitmap.getWidth();
-            dheight = mBitmap.getHeight();
-        } else if (mDrawable != null) {
-            vwidth -= 2 * (mFrameWidth - 1);
-            vheight -= 2 * (mFrameWidth - 1);
-            dwidth = vwidth;
-            dheight = vheight;
-            mDrawable.setBounds(0, 0, dwidth, dheight);
-        } else {
-            return;
-        }
-
-        float scale;
-        float dx;
-        float dy;
-
-        scale = Math.min((float) vwidth / (float) dwidth,
-                (float) vheight / (float) dheight);
-
-        dx = (int) ((vwidth - dwidth * scale) * 0.5f + 0.5f);
-        dy = (int) ((vheight - dheight * scale) * 0.5f + 0.5f);
-
-        mDrawMatrix.setScale(scale, scale);
-        mDrawMatrix.postTranslate(dx, dy);
-        mScale = scale;
+    public void setBadgeDiameter(float diameter) {
+        mDrawable.setBadgeRadius(diameter * 0.5f);
     }
 
-    @Override
-    protected void onDraw(Canvas canvas) {
-        int frameColor = isActivated() ? mActiveFrameColor : mFrameColor;
-        float halfW = getWidth() / 2f;
-        float halfH = getHeight() / 2f;
-        float halfSW = Math.min(halfH, halfW);
-        updateDrawableIfDisabled();
-        if (mBitmap != null && mScale > 0) {
-            int saveCount = canvas.getSaveCount();
-            canvas.save();
-            canvas.translate(mPaddingLeft, mPaddingTop);
-            canvas.concat(mDrawMatrix);
-            float halfBW = mBitmap.getWidth() / 2f;
-            float halfBH = mBitmap.getHeight() / 2f;
-            float halfBSW = Math.min(halfBH, halfBW);
-            canvas.drawCircle(halfBW, halfBH, halfBSW - mFrameWidth / mScale + 1, mBitmapPaint);
-            canvas.restoreToCount(saveCount);
-        } else if (mDrawable != null && mScale > 0) {
-            int saveCount = canvas.getSaveCount();
-            canvas.save();
-            canvas.translate(mPaddingLeft, mPaddingTop);
-            canvas.translate(mFrameWidth - 1, mFrameWidth - 1);
-            canvas.concat(mDrawMatrix);
-            mDrawable.draw(canvas);
-            canvas.restoreToCount(saveCount);
-        }
-        if (frameColor != 0) {
-            mFramePaint.setColor(frameColor);
-            mFramePaint.setStrokeWidth(mFrameWidth);
-            canvas.drawCircle(halfW, halfH, halfSW + (mFramePadding - mFrameWidth) / 2f,
-                    mFramePaint);
-        }
+    public void setBadgeMargin(float margin) {
+        mDrawable.setBadgeMargin(margin);
+    }
+
+    public void setAvatar(Bitmap avatar) {
+        mDrawable.setIcon(avatar);
+        mDrawable.setBadge(null);
+    }
+
+    public void setAvatarWithBadge(Bitmap avatar, int userId) {
+        mDrawable.setIcon(avatar);
+        mDrawable.setBadgeIfManagedUser(getContext(), userId);
     }
 
     public void setDrawable(Drawable d) {
-        if (mDrawable != null) {
-            mDrawable.setCallback(null);
-            unscheduleDrawable(mDrawable);
+        if (d instanceof UserIconDrawable) {
+            throw new RuntimeException("Recursively adding UserIconDrawable");
         }
-        mDrawable = d;
-        if (d != null) {
-            d.setCallback(this);
-            if (d.isStateful()) {
-                d.setState(getDrawableState());
-            }
-            d.setLayoutDirection(getLayoutDirection());
-            configureBounds();
-        }
-        if (d != null) {
-            mBitmap = null;
-        }
-        configureBounds();
-        invalidate();
+        mDrawable.setIconDrawable(d);
+        mDrawable.setBadge(null);
     }
 
-    @Override
-    public void invalidateDrawable(Drawable dr) {
-        if (dr == mDrawable) {
-            invalidate();
-        } else {
-            super.invalidateDrawable(dr);
+    public void setDrawableWithBadge(Drawable d, int userId) {
+        if (d instanceof UserIconDrawable) {
+            throw new RuntimeException("Recursively adding UserIconDrawable");
         }
-    }
-
-    @Override
-    protected boolean verifyDrawable(Drawable who) {
-        return who == mDrawable || super.verifyDrawable(who);
-    }
-
-    @Override
-    protected void drawableStateChanged() {
-        super.drawableStateChanged();
-        if (mDrawable != null && mDrawable.isStateful()) {
-            mDrawable.setState(getDrawableState());
-        }
-    }
-
-    public void setDisabled(boolean disabled) {
-        if (mIsDisabled == disabled) {
-            return;
-        }
-        mIsDisabled = disabled;
-        invalidate();
-    }
-
-    private void updateDrawableIfDisabled() {
-        int disabledColor = getContext().getColor(R.color.qs_tile_disabled_color);
-        PorterDuffColorFilter filter = new PorterDuffColorFilter(disabledColor,
-                PorterDuff.Mode.SRC_ATOP);
-        if (mBitmap != null) {
-            if (mIsDisabled) {
-                mBitmapPaint.setColorFilter(filter);
-            } else {
-                mBitmapPaint.setColorFilter(null);
-            }
-        } else if (mDrawable != null) {
-            if (mIsDisabled) {
-                mDrawable.setColorFilter(filter);
-            } else {
-                mDrawable.setColorFilter(null);
-            }
-        }
+        mDrawable.setIconDrawable(d);
+        mDrawable.setBadgeIfManagedUser(getContext(), userId);
     }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryController.java
index bb3e116..559436b 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryController.java
@@ -16,158 +16,35 @@
 
 package com.android.systemui.statusbar.policy;
 
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.os.BatteryManager;
-import android.os.Handler;
-import android.os.PowerManager;
-import android.util.Log;
+import com.android.systemui.DemoMode;
 
 import java.io.FileDescriptor;
 import java.io.PrintWriter;
-import java.util.ArrayList;
 
-public class BatteryController extends BroadcastReceiver {
-    private static final String TAG = "BatteryController";
+public interface BatteryController extends DemoMode {
+    /**
+     * Prints the current state of the {@link BatteryController} to the given {@link PrintWriter}.
+     */
+    void dump(FileDescriptor fd, PrintWriter pw, String[] args);
 
-    public static final String ACTION_LEVEL_TEST = "com.android.systemui.BATTERY_LEVEL_TEST";
+    /**
+     * Sets if the current device is in power save mode.
+     */
+    void setPowerSaveMode(boolean powerSave);
 
-    private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
+    /**
+     * Returns {@code true} if the device is currently in power save mode.
+     */
+    boolean isPowerSave();
 
-    private final ArrayList<BatteryStateChangeCallback> mChangeCallbacks = new ArrayList<>();
-    private final PowerManager mPowerManager;
-    private final Handler mHandler;
+    void addStateChangedCallback(BatteryStateChangeCallback cb);
+    void removeStateChangedCallback(BatteryStateChangeCallback cb);
 
-    private int mLevel;
-    private boolean mPluggedIn;
-    private boolean mCharging;
-    private boolean mCharged;
-    private boolean mPowerSave;
-    private boolean mTestmode = false;
-
-    public BatteryController(Context context) {
-        mHandler = new Handler();
-        mPowerManager = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
-
-        IntentFilter filter = new IntentFilter();
-        filter.addAction(Intent.ACTION_BATTERY_CHANGED);
-        filter.addAction(PowerManager.ACTION_POWER_SAVE_MODE_CHANGED);
-        filter.addAction(PowerManager.ACTION_POWER_SAVE_MODE_CHANGING);
-        filter.addAction(ACTION_LEVEL_TEST);
-        context.registerReceiver(this, filter);
-
-        updatePowerSave();
-    }
-
-    public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
-        pw.println("BatteryController state:");
-        pw.print("  mLevel="); pw.println(mLevel);
-        pw.print("  mPluggedIn="); pw.println(mPluggedIn);
-        pw.print("  mCharging="); pw.println(mCharging);
-        pw.print("  mCharged="); pw.println(mCharged);
-        pw.print("  mPowerSave="); pw.println(mPowerSave);
-    }
-
-    public void setPowerSaveMode(boolean powerSave) {
-        mPowerManager.setPowerSaveMode(powerSave);
-    }
-
-    public void addStateChangedCallback(BatteryStateChangeCallback cb) {
-        mChangeCallbacks.add(cb);
-        cb.onBatteryLevelChanged(mLevel, mPluggedIn, mCharging);
-        cb.onPowerSaveChanged(mPowerSave);
-    }
-
-    public void removeStateChangedCallback(BatteryStateChangeCallback cb) {
-        mChangeCallbacks.remove(cb);
-    }
-
-    public void onReceive(final Context context, Intent intent) {
-        final String action = intent.getAction();
-        if (action.equals(Intent.ACTION_BATTERY_CHANGED)) {
-            if (mTestmode && !intent.getBooleanExtra("testmode", false)) return;
-            mLevel = (int)(100f
-                    * intent.getIntExtra(BatteryManager.EXTRA_LEVEL, 0)
-                    / intent.getIntExtra(BatteryManager.EXTRA_SCALE, 100));
-            mPluggedIn = intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, 0) != 0;
-
-            final int status = intent.getIntExtra(BatteryManager.EXTRA_STATUS,
-                    BatteryManager.BATTERY_STATUS_UNKNOWN);
-            mCharged = status == BatteryManager.BATTERY_STATUS_FULL;
-            mCharging = mCharged || status == BatteryManager.BATTERY_STATUS_CHARGING;
-
-            fireBatteryLevelChanged();
-        } else if (action.equals(PowerManager.ACTION_POWER_SAVE_MODE_CHANGED)) {
-            updatePowerSave();
-        } else if (action.equals(PowerManager.ACTION_POWER_SAVE_MODE_CHANGING)) {
-            setPowerSave(intent.getBooleanExtra(PowerManager.EXTRA_POWER_SAVE_MODE, false));
-        } else if (action.equals(ACTION_LEVEL_TEST)) {
-            mTestmode = true;
-            mHandler.post(new Runnable() {
-                int curLevel = 0;
-                int incr = 1;
-                int saveLevel = mLevel;
-                boolean savePlugged = mPluggedIn;
-                Intent dummy = new Intent(Intent.ACTION_BATTERY_CHANGED);
-                @Override
-                public void run() {
-                    if (curLevel < 0) {
-                        mTestmode = false;
-                        dummy.putExtra("level", saveLevel);
-                        dummy.putExtra("plugged", savePlugged);
-                        dummy.putExtra("testmode", false);
-                    } else {
-                        dummy.putExtra("level", curLevel);
-                        dummy.putExtra("plugged", incr > 0 ? BatteryManager.BATTERY_PLUGGED_AC
-                                : 0);
-                        dummy.putExtra("testmode", true);
-                    }
-                    context.sendBroadcast(dummy);
-
-                    if (!mTestmode) return;
-
-                    curLevel += incr;
-                    if (curLevel == 100) {
-                        incr *= -1;
-                    }
-                    mHandler.postDelayed(this, 200);
-                }
-            });
-        }
-    }
-
-    public boolean isPowerSave() {
-        return mPowerSave;
-    }
-
-    private void updatePowerSave() {
-        setPowerSave(mPowerManager.isPowerSaveMode());
-    }
-
-    private void setPowerSave(boolean powerSave) {
-        if (powerSave == mPowerSave) return;
-        mPowerSave = powerSave;
-        if (DEBUG) Log.d(TAG, "Power save is " + (mPowerSave ? "on" : "off"));
-        firePowerSaveChanged();
-    }
-
-    private void fireBatteryLevelChanged() {
-        final int N = mChangeCallbacks.size();
-        for (int i = 0; i < N; i++) {
-            mChangeCallbacks.get(i).onBatteryLevelChanged(mLevel, mPluggedIn, mCharging);
-        }
-    }
-
-    private void firePowerSaveChanged() {
-        final int N = mChangeCallbacks.size();
-        for (int i = 0; i < N; i++) {
-            mChangeCallbacks.get(i).onPowerSaveChanged(mPowerSave);
-        }
-    }
-
-    public interface BatteryStateChangeCallback {
+    /**
+     * A listener that will be notified whenever a change in battery level or power save mode
+     * has occurred.
+     */
+    interface BatteryStateChangeCallback {
         void onBatteryLevelChanged(int level, boolean pluggedIn, boolean charging);
         void onPowerSaveChanged(boolean isPowerSave);
     }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryControllerImpl.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryControllerImpl.java
new file mode 100644
index 0000000..5d734c6
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BatteryControllerImpl.java
@@ -0,0 +1,210 @@
+/*
+ * 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 com.android.systemui.statusbar.policy;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.os.BatteryManager;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.PowerManager;
+import android.util.Log;
+import com.android.systemui.DemoMode;
+
+import java.io.FileDescriptor;
+import java.io.PrintWriter;
+import java.util.ArrayList;
+
+/**
+ * Default implementation of a {@link BatteryController}. This controller monitors for battery
+ * level change events that are broadcasted by the system.
+ */
+public class BatteryControllerImpl extends BroadcastReceiver implements BatteryController {
+    private static final String TAG = "BatteryController";
+
+    public static final String ACTION_LEVEL_TEST = "com.android.systemui.BATTERY_LEVEL_TEST";
+
+    private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
+
+    private final ArrayList<BatteryController.BatteryStateChangeCallback> mChangeCallbacks = new ArrayList<>();
+    private final PowerManager mPowerManager;
+    private final Handler mHandler;
+    private final Context mContext;
+
+    protected int mLevel;
+    protected boolean mPluggedIn;
+    protected boolean mCharging;
+    protected boolean mCharged;
+    protected boolean mPowerSave;
+    private boolean mTestmode = false;
+
+    public BatteryControllerImpl(Context context) {
+        mContext = context;
+        mHandler = new Handler();
+        mPowerManager = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
+
+        registerReceiver();
+        updatePowerSave();
+    }
+
+    private void registerReceiver() {
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(Intent.ACTION_BATTERY_CHANGED);
+        filter.addAction(PowerManager.ACTION_POWER_SAVE_MODE_CHANGED);
+        filter.addAction(PowerManager.ACTION_POWER_SAVE_MODE_CHANGING);
+        filter.addAction(ACTION_LEVEL_TEST);
+        mContext.registerReceiver(this, filter);
+    }
+
+    @Override
+    public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
+        pw.println("BatteryController state:");
+        pw.print("  mLevel="); pw.println(mLevel);
+        pw.print("  mPluggedIn="); pw.println(mPluggedIn);
+        pw.print("  mCharging="); pw.println(mCharging);
+        pw.print("  mCharged="); pw.println(mCharged);
+        pw.print("  mPowerSave="); pw.println(mPowerSave);
+    }
+
+    @Override
+    public void setPowerSaveMode(boolean powerSave) {
+        mPowerManager.setPowerSaveMode(powerSave);
+    }
+
+    @Override
+    public void addStateChangedCallback(BatteryController.BatteryStateChangeCallback cb) {
+        mChangeCallbacks.add(cb);
+        cb.onBatteryLevelChanged(mLevel, mPluggedIn, mCharging);
+        cb.onPowerSaveChanged(mPowerSave);
+    }
+
+    @Override
+    public void removeStateChangedCallback(BatteryController.BatteryStateChangeCallback cb) {
+        mChangeCallbacks.remove(cb);
+    }
+
+    @Override
+    public void onReceive(final Context context, Intent intent) {
+        final String action = intent.getAction();
+        if (action.equals(Intent.ACTION_BATTERY_CHANGED)) {
+            if (mTestmode && !intent.getBooleanExtra("testmode", false)) return;
+            mLevel = (int)(100f
+                    * intent.getIntExtra(BatteryManager.EXTRA_LEVEL, 0)
+                    / intent.getIntExtra(BatteryManager.EXTRA_SCALE, 100));
+            mPluggedIn = intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, 0) != 0;
+
+            final int status = intent.getIntExtra(BatteryManager.EXTRA_STATUS,
+                    BatteryManager.BATTERY_STATUS_UNKNOWN);
+            mCharged = status == BatteryManager.BATTERY_STATUS_FULL;
+            mCharging = mCharged || status == BatteryManager.BATTERY_STATUS_CHARGING;
+
+            fireBatteryLevelChanged();
+        } else if (action.equals(PowerManager.ACTION_POWER_SAVE_MODE_CHANGED)) {
+            updatePowerSave();
+        } else if (action.equals(PowerManager.ACTION_POWER_SAVE_MODE_CHANGING)) {
+            setPowerSave(intent.getBooleanExtra(PowerManager.EXTRA_POWER_SAVE_MODE, false));
+        } else if (action.equals(ACTION_LEVEL_TEST)) {
+            mTestmode = true;
+            mHandler.post(new Runnable() {
+                int curLevel = 0;
+                int incr = 1;
+                int saveLevel = mLevel;
+                boolean savePlugged = mPluggedIn;
+                Intent dummy = new Intent(Intent.ACTION_BATTERY_CHANGED);
+                @Override
+                public void run() {
+                    if (curLevel < 0) {
+                        mTestmode = false;
+                        dummy.putExtra("level", saveLevel);
+                        dummy.putExtra("plugged", savePlugged);
+                        dummy.putExtra("testmode", false);
+                    } else {
+                        dummy.putExtra("level", curLevel);
+                        dummy.putExtra("plugged", incr > 0 ? BatteryManager.BATTERY_PLUGGED_AC
+                                : 0);
+                        dummy.putExtra("testmode", true);
+                    }
+                    context.sendBroadcast(dummy);
+
+                    if (!mTestmode) return;
+
+                    curLevel += incr;
+                    if (curLevel == 100) {
+                        incr *= -1;
+                    }
+                    mHandler.postDelayed(this, 200);
+                }
+            });
+        }
+    }
+
+    @Override
+    public boolean isPowerSave() {
+        return mPowerSave;
+    }
+
+    private void updatePowerSave() {
+        setPowerSave(mPowerManager.isPowerSaveMode());
+    }
+
+    private void setPowerSave(boolean powerSave) {
+        if (powerSave == mPowerSave) return;
+        mPowerSave = powerSave;
+        if (DEBUG) Log.d(TAG, "Power save is " + (mPowerSave ? "on" : "off"));
+        firePowerSaveChanged();
+    }
+
+    protected void fireBatteryLevelChanged() {
+        final int N = mChangeCallbacks.size();
+        for (int i = 0; i < N; i++) {
+            mChangeCallbacks.get(i).onBatteryLevelChanged(mLevel, mPluggedIn, mCharging);
+        }
+    }
+
+    private void firePowerSaveChanged() {
+        final int N = mChangeCallbacks.size();
+        for (int i = 0; i < N; i++) {
+            mChangeCallbacks.get(i).onPowerSaveChanged(mPowerSave);
+        }
+    }
+
+    private boolean mDemoMode;
+
+    @Override
+    public void dispatchDemoCommand(String command, Bundle args) {
+        if (!mDemoMode && command.equals(COMMAND_ENTER)) {
+            mDemoMode = true;
+            mContext.unregisterReceiver(this);
+        } else if (mDemoMode && command.equals(COMMAND_EXIT)) {
+            mDemoMode = false;
+            registerReceiver();
+            updatePowerSave();
+        } else if (mDemoMode && command.equals(COMMAND_BATTERY)) {
+           String level = args.getString("level");
+           String plugged = args.getString("plugged");
+           if (level != null) {
+               mLevel = Math.min(Math.max(Integer.parseInt(level), 0), 100);
+           }
+           if (plugged != null) {
+               mPluggedIn = Boolean.parseBoolean(plugged);
+           }
+            fireBatteryLevelChanged();
+        }
+    }
+}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/DataSaverController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/DataSaverController.java
index 6dd196b..c4c64e7 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/DataSaverController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/DataSaverController.java
@@ -33,24 +33,29 @@
     }
 
     private void handleRestrictBackgroundChanged(boolean isDataSaving) {
-        final int N = mListeners.size();
-        for (int i = 0; i < N; i++) {
-            mListeners.get(i).onDataSaverChanged(isDataSaving);
+        synchronized (mListeners) {
+            for (int i = 0; i < mListeners.size(); i++) {
+                mListeners.get(i).onDataSaverChanged(isDataSaving);
+            }
         }
     }
 
     public void addListener(Listener listener) {
-        mListeners.add(listener);
-        if (mListeners.size() == 1) {
-            mPolicyManager.registerListener(mPolicyListener);
+        synchronized (mListeners) {
+            mListeners.add(listener);
+            if (mListeners.size() == 1) {
+                mPolicyManager.registerListener(mPolicyListener);
+            }
         }
         listener.onDataSaverChanged(isDataSaverEnabled());
     }
 
     public void remListener(Listener listener) {
-        mListeners.remove(listener);
-        if (mListeners.size() == 0) {
-            mPolicyManager.unregisterListener(mPolicyListener);
+        synchronized (mListeners) {
+            mListeners.remove(listener);
+            if (mListeners.size() == 0) {
+                mPolicyManager.unregisterListener(mPolicyListener);
+            }
         }
     }
 
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/HeadsUpManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/HeadsUpManager.java
index ab81712..ebefdde 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/HeadsUpManager.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/HeadsUpManager.java
@@ -185,6 +185,11 @@
 
         if (alert) {
             HeadsUpEntry headsUpEntry = mHeadsUpEntries.get(headsUp.key);
+            if (headsUpEntry == null) {
+                // the entry was released before this update (i.e by a listener) This can happen
+                // with the groupmanager
+                return;
+            }
             headsUpEntry.updateEntry();
             setEntryPinned(headsUpEntry, shouldHeadsUpBecomePinned(headsUp));
         }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyguardUserSwitcher.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyguardUserSwitcher.java
index fb310a6..c39d718 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyguardUserSwitcher.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyguardUserSwitcher.java
@@ -253,17 +253,13 @@
             UserDetailItemView v = (UserDetailItemView) convertView;
 
             String name = getName(mContext, item);
-            Drawable drawable;
             if (item.picture == null) {
-                drawable = getDrawable(mContext, item).mutate();
+                v.bind(name, getDrawable(mContext, item).mutate(), item.resolveId());
             } else {
-                drawable = new BitmapDrawable(mContext.getResources(), item.picture);
+                v.bind(name, item.picture, item.info.id);
             }
             // Disable the icon if switching is disabled
-            if (!item.isSwitchToEnabled) {
-                drawable.setTint(mContext.getColor(R.color.qs_tile_disabled_color));
-            }
-            v.bind(name, drawable);
+            v.setAvatarEnabled(item.isSwitchToEnabled);
             convertView.setActivated(item.isCurrent);
             convertView.setTag(item);
             return convertView;
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/SecurityControllerImpl.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/SecurityControllerImpl.java
index a85fe0d..5046456 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/SecurityControllerImpl.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/SecurityControllerImpl.java
@@ -114,8 +114,8 @@
 
     @Override
     public String getProfileOwnerName() {
-        for (UserInfo profile : mUserManager.getProfiles(mCurrentUserId)) {
-            String name = mDevicePolicyManager.getProfileOwnerNameAsUser(profile.id);
+        for (int profileId : mUserManager.getProfileIdsWithDisabled(mCurrentUserId)) {
+            String name = mDevicePolicyManager.getProfileOwnerNameAsUser(profileId);
             if (name != null) {
                 return name;
             }
@@ -135,13 +135,13 @@
 
     @Override
     public String getProfileVpnName() {
-        for (UserInfo profile : mUserManager.getProfiles(mVpnUserId)) {
-            if (profile.id == mVpnUserId) {
+        for (int profileId : mUserManager.getProfileIdsWithDisabled(mVpnUserId)) {
+            if (profileId == mVpnUserId) {
                 continue;
             }
-            VpnConfig cfg = mCurrentVpns.get(profile.id);
+            VpnConfig cfg = mCurrentVpns.get(profileId);
             if (cfg != null) {
-                return getNameForVpnConfig(cfg, profile.getUserHandle());
+                return getNameForVpnConfig(cfg, UserHandle.of(profileId));
             }
         }
         return null;
@@ -149,8 +149,8 @@
 
     @Override
     public boolean isVpnEnabled() {
-        for (UserInfo profile : mUserManager.getProfiles(mVpnUserId)) {
-            if (mCurrentVpns.get(profile.id) != null) {
+        for (int profileId : mUserManager.getProfileIdsWithDisabled(mVpnUserId)) {
+            if (mCurrentVpns.get(profileId) != null) {
                 return true;
             }
         }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserInfoController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserInfoController.java
index 85ac755..bae5bda 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserInfoController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserInfoController.java
@@ -26,7 +26,6 @@
 import android.content.res.Resources;
 import android.database.Cursor;
 import android.graphics.Bitmap;
-import android.graphics.drawable.BitmapDrawable;
 import android.graphics.drawable.Drawable;
 import android.os.AsyncTask;
 import android.os.RemoteException;
@@ -37,7 +36,7 @@
 import android.util.Pair;
 
 import com.android.internal.util.UserIcons;
-import com.android.systemui.BitmapHelper;
+import com.android.settingslib.drawable.UserIconDrawable;
 import com.android.systemui.R;
 
 import java.util.ArrayList;
@@ -155,8 +154,8 @@
                 Drawable avatar = null;
                 Bitmap rawAvatar = um.getUserIcon(userId);
                 if (rawAvatar != null) {
-                    avatar = new BitmapDrawable(mContext.getResources(),
-                            BitmapHelper.createCircularClip(rawAvatar, avatarSize, avatarSize));
+                    avatar = new UserIconDrawable(avatarSize)
+                            .setIcon(rawAvatar).setBadgeIfManagedUser(mContext, userId).bake();
                 } else {
                     avatar = UserIcons.getDefaultUserIcon(isGuest? UserHandle.USER_NULL : userId,
                             /* light= */ true);
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
index ea0bdf2..c82ba3b 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
@@ -50,7 +50,6 @@
 import com.android.internal.logging.MetricsProto.MetricsEvent;
 import com.android.internal.util.UserIcons;
 import com.android.settingslib.RestrictedLockUtils;
-import com.android.systemui.BitmapHelper;
 import com.android.systemui.GuestResumeSessionReceiver;
 import com.android.systemui.R;
 import com.android.systemui.SystemUISecondaryUserService;
@@ -197,8 +196,6 @@
                 boolean canSwitchUsers = mUserManager.canSwitchUsers();
                 UserInfo currentUserInfo = null;
                 UserRecord guestRecord = null;
-                int avatarSize = mContext.getResources()
-                        .getDimensionPixelSize(R.dimen.max_avatar_size);
 
                 for (UserInfo info : infos) {
                     boolean isCurrent = currentId == info.id;
@@ -219,8 +216,10 @@
                                 picture = mUserManager.getUserIcon(info.id);
 
                                 if (picture != null) {
-                                    picture = BitmapHelper.createCircularClip(
-                                            picture, avatarSize, avatarSize);
+                                    int avatarSize = mContext.getResources()
+                                            .getDimensionPixelSize(R.dimen.max_avatar_size);
+                                    picture = Bitmap.createScaledBitmap(
+                                            picture, avatarSize, avatarSize, true);
                                 }
                             }
                             int index = isCurrent ? 0 : records.size();
@@ -664,8 +663,7 @@
             if (item.isAddUser) {
                 return context.getDrawable(R.drawable.ic_add_circle_qs);
             }
-            return UserIcons.getDefaultUserIcon(item.isGuest ? UserHandle.USER_NULL : item.info.id,
-                    /* light= */ true);
+            return UserIcons.getDefaultUserIcon(item.resolveId(), /* light= */ true);
         }
 
         public void refresh() {
@@ -718,6 +716,13 @@
                     isSwitchToEnabled);
         }
 
+        public int resolveId() {
+            if (isGuest || info == null) {
+                return UserHandle.USER_NULL;
+            }
+            return info.id;
+        }
+
         public String toString() {
             StringBuilder sb = new StringBuilder();
             sb.append("UserRecord(");
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/stack/NotificationStackScrollLayout.java b/packages/SystemUI/src/com/android/systemui/statusbar/stack/NotificationStackScrollLayout.java
index 7c5cdfb..8b52bf6 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/stack/NotificationStackScrollLayout.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/stack/NotificationStackScrollLayout.java
@@ -3799,6 +3799,7 @@
             } else {
                 getViewTreeObserver().removeOnPreDrawListener(mShadowUpdater);
             }
+            mContinuousShadowUpdate = continuousShadowUpdate;
         }
     }
 
diff --git a/packages/SystemUI/src/com/android/systemui/tuner/TunerActivity.java b/packages/SystemUI/src/com/android/systemui/tuner/TunerActivity.java
index 748ee97..ae104cd 100644
--- a/packages/SystemUI/src/com/android/systemui/tuner/TunerActivity.java
+++ b/packages/SystemUI/src/com/android/systemui/tuner/TunerActivity.java
@@ -36,11 +36,15 @@
         super.onCreate(savedInstanceState);
 
         if (getFragmentManager().findFragmentByTag(TAG_TUNER) == null) {
+            boolean showDemoMode = getIntent().getAction().equals(
+                    "com.android.settings.action.DEMO_MODE");
             boolean showNightMode = getIntent().getBooleanExtra(
                     NightModeFragment.EXTRA_SHOW_NIGHT_MODE, false);
+            final PreferenceFragment fragment = showNightMode ? new NightModeFragment()
+                    : showDemoMode ? new DemoModeFragment()
+                    : new TunerFragment();
             getFragmentManager().beginTransaction().replace(R.id.content_frame,
-                    showNightMode ? new NightModeFragment() : new TunerFragment(),
-                    TAG_TUNER).commit();
+                    fragment, TAG_TUNER).commit();
         }
     }
 
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 fe54090..a445e77 100644
--- a/packages/SystemUI/src/com/android/systemui/tv/pip/PipManager.java
+++ b/packages/SystemUI/src/com/android/systemui/tv/pip/PipManager.java
@@ -36,6 +36,7 @@
 import android.os.RemoteException;
 import android.os.SystemProperties;
 import android.util.Log;
+import android.util.Pair;
 
 import com.android.systemui.Prefs;
 import com.android.systemui.R;
@@ -63,6 +64,20 @@
     private static final int MAX_RUNNING_TASKS_COUNT = 10;
 
     /**
+     * List of package and class name which are considered as Settings,
+     * so PIP location should be adjusted to the left of the side panel.
+     */
+    private static final List<Pair<String, String>> sSettingsPackageAndClassNamePairList;
+    static {
+        sSettingsPackageAndClassNamePairList = new ArrayList<>();
+        sSettingsPackageAndClassNamePairList.add(new Pair<String, String>(
+                "com.android.tv.settings", null));
+        sSettingsPackageAndClassNamePairList.add(new Pair<String, String>(
+                "com.google.android.leanbacklauncher",
+                "com.google.android.leanbacklauncher.settings.HomeScreenSettingsActivity"));
+    }
+
+    /**
      * State when there's no PIP.
      */
     public static final int STATE_NO_PIP = 0;
@@ -108,6 +123,7 @@
     private int mSuspendPipResizingReason;
 
     private Context mContext;
+    private SystemServicesProxy mSystemServiceProxy;
     private PipRecentsOverlayManager mPipRecentsOverlayManager;
     private IActivityManager mActivityManager;
     private MediaSessionManager mMediaSessionManager;
@@ -117,6 +133,8 @@
     private List<MediaListener> mMediaListeners = new ArrayList<>();
     private Rect mCurrentPipBounds;
     private Rect mPipBounds;
+    private Rect mDefaultPipBounds;
+    private Rect mSettingsPipBounds;
     private Rect mMenuModePipBounds;
     private Rect mRecentsPipBounds;
     private Rect mRecentsFocusedPipBounds;
@@ -176,8 +194,10 @@
         mInitialized = true;
         mContext = context;
         Resources res = context.getResources();
-        mPipBounds = Rect.unflattenFromString(res.getString(
+        mDefaultPipBounds = Rect.unflattenFromString(res.getString(
                 com.android.internal.R.string.config_defaultPictureInPictureBounds));
+        mSettingsPipBounds = Rect.unflattenFromString(res.getString(
+                R.string.pip_settings_bounds));
         mMenuModePipBounds = Rect.unflattenFromString(res.getString(
                 R.string.pip_menu_bounds));
         mRecentsPipBounds = Rect.unflattenFromString(res.getString(
@@ -186,9 +206,11 @@
                 R.string.pip_recents_focused_bounds));
         mRecentsFocusChangedAnimationDurationMs = res.getInteger(
                 R.integer.recents_tv_pip_focus_anim_duration);
+        mPipBounds = mDefaultPipBounds;
 
         mActivityManager = ActivityManagerNative.getDefault();
-        SystemServicesProxy.getInstance(context).registerTaskStackListener(mTaskStackListener);
+        mSystemServiceProxy = SystemServicesProxy.getInstance(context);
+        mSystemServiceProxy.registerTaskStackListener(mTaskStackListener);
         IntentFilter intentFilter = new IntentFilter();
         intentFilter.addAction(Intent.ACTION_MEDIA_RESOURCE_GRANTED);
         mContext.registerReceiver(mBroadcastReceiver, intentFilter);
@@ -522,10 +544,25 @@
         return PLAYBACK_STATE_UNAVAILABLE;
     }
 
+    private static boolean isSettingsShown(ComponentName topActivity) {
+        for (Pair<String, String> componentName : sSettingsPackageAndClassNamePairList) {
+            String packageName = componentName.first;
+            if (topActivity.getPackageName().equals(componentName.first)) {
+                String className = componentName.second;
+                if (className == null || topActivity.getClassName().equals(className)) {
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+
     private TaskStackListener mTaskStackListener = new TaskStackListener() {
         @Override
         public void onTaskStackChanged() {
             if (mState != STATE_NO_PIP) {
+                boolean hasPip = false;
+
                 StackInfo stackInfo = null;
                 try {
                     stackInfo = mActivityManager.getStackInfo(PINNED_STACK_ID);
@@ -541,11 +578,32 @@
                 for (int i = stackInfo.taskIds.length - 1; i >= 0; --i) {
                     if (stackInfo.taskIds[i] == mPipTaskId) {
                         // PIP task is still alive.
-                        return;
+                        hasPip = true;
+                        break;
                     }
                 }
-                // PIP task doesn't exist anymore in PINNED_STACK.
-                closePipInternal(true);
+                if (!hasPip) {
+                    // PIP task doesn't exist anymore in PINNED_STACK.
+                    closePipInternal(true);
+                    return;
+                }
+            }
+            if (mState == STATE_PIP_OVERLAY) {
+                try {
+                    List<RunningTaskInfo> runningTasks = mActivityManager.getTasks(1, 0);
+                    if (runningTasks == null || runningTasks.size() == 0) {
+                        return;
+                    }
+                    RunningTaskInfo topTask = runningTasks.get(0);
+                    Rect bounds = isSettingsShown(topTask.topActivity)
+                          ? mSettingsPipBounds : mDefaultPipBounds;
+                    if (mPipBounds != bounds) {
+                        mPipBounds = bounds;
+                        resizePinnedStack(STATE_PIP_OVERLAY);
+                    }
+                } catch (RemoteException e) {
+                    Log.d(TAG, "Failed to detect top activity", e);
+                }
             }
         }
 
diff --git a/packages/SystemUI/src/com/android/systemui/tv/pip/PipOverlayActivity.java b/packages/SystemUI/src/com/android/systemui/tv/pip/PipOverlayActivity.java
index e205ff5..011e159 100644
--- a/packages/SystemUI/src/com/android/systemui/tv/pip/PipOverlayActivity.java
+++ b/packages/SystemUI/src/com/android/systemui/tv/pip/PipOverlayActivity.java
@@ -16,6 +16,8 @@
 
 package com.android.systemui.tv.pip;
 
+import android.animation.Animator;
+import android.animation.AnimatorInflater;
 import android.app.Activity;
 import android.app.ActivityOptions;
 import android.content.Context;
@@ -50,9 +52,11 @@
     private ImageView mGuideButtonPlayPauseImageView;
     private final Runnable mHideGuideOverlayRunnable = new Runnable() {
         public void run() {
-            mGuideOverlayView.setVisibility(View.GONE);
+            mFadeOutAnimation.start();
         }
     };
+    private Animator mFadeInAnimation;
+    private Animator mFadeOutAnimation;
 
     /**
      * Shows PIP overlay UI only if it's not there.
@@ -74,11 +78,18 @@
         setContentView(R.layout.tv_pip_overlay);
         mGuideOverlayView = findViewById(R.id.guide_overlay);
         mPipManager.addListener(this);
+        mFadeInAnimation = AnimatorInflater.loadAnimator(
+                this, R.anim.tv_pip_overlay_fade_in_animation);
+        mFadeInAnimation.setTarget(mGuideOverlayView);
+        mFadeOutAnimation = AnimatorInflater.loadAnimator(
+                this, R.anim.tv_pip_overlay_fade_out_animation);
+        mFadeOutAnimation.setTarget(mGuideOverlayView);
     }
 
     @Override
     protected void onResume() {
         super.onResume();
+        mFadeInAnimation.start();
         mHandler.removeCallbacks(mHideGuideOverlayRunnable);
         mHandler.postDelayed(mHideGuideOverlayRunnable, SHOW_GUIDE_OVERLAY_VIEW_DURATION_MS);
     }
diff --git a/packages/SystemUI/src/com/android/systemui/usb/StorageNotification.java b/packages/SystemUI/src/com/android/systemui/usb/StorageNotification.java
index 180d918..2c53e29 100644
--- a/packages/SystemUI/src/com/android/systemui/usb/StorageNotification.java
+++ b/packages/SystemUI/src/com/android/systemui/usb/StorageNotification.java
@@ -16,6 +16,7 @@
 
 package com.android.systemui.usb;
 
+import android.annotation.NonNull;
 import android.app.Notification;
 import android.app.Notification.Action;
 import android.app.NotificationManager;
@@ -97,6 +98,11 @@
         public void onDiskScanned(DiskInfo disk, int volumeCount) {
             onDiskScannedInternal(disk, volumeCount);
         }
+
+        @Override
+        public void onDiskDestroyed(DiskInfo disk) {
+            onDiskDestroyedInternal(disk);
+        }
     };
 
     private final BroadcastReceiver mSnoozeReceiver = new BroadcastReceiver() {
@@ -238,6 +244,15 @@
         }
     }
 
+    /**
+     * Remove all notifications for a disk when it goes away.
+     *
+     * @param disk The disk that went away.
+     */
+    private void onDiskDestroyedInternal(@NonNull DiskInfo disk) {
+        mNotificationManager.cancelAsUser(disk.getId(), DISK_ID, UserHandle.ALL);
+    }
+
     private void onVolumeStateChangedInternal(VolumeInfo vol) {
         switch (vol.getType()) {
             case VolumeInfo.TYPE_PRIVATE:
diff --git a/packages/SystemUI/src/com/android/systemui/volume/SafetyWarningDialog.java b/packages/SystemUI/src/com/android/systemui/volume/SafetyWarningDialog.java
index 04640a2..d7c4bbf 100644
--- a/packages/SystemUI/src/com/android/systemui/volume/SafetyWarningDialog.java
+++ b/packages/SystemUI/src/com/android/systemui/volume/SafetyWarningDialog.java
@@ -47,6 +47,7 @@
         mAudioManager = audioManager;
 
         getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
+        setShowForAllUsers(true);
         setMessage(mContext.getString(com.android.internal.R.string.safe_media_volume_warning));
         setButton(DialogInterface.BUTTON_POSITIVE,
                 mContext.getString(com.android.internal.R.string.yes), this);
diff --git a/packages/SystemUI/src/com/android/systemui/volume/VolumeDialog.java b/packages/SystemUI/src/com/android/systemui/volume/VolumeDialog.java
index 1d5ca04..91a8493 100644
--- a/packages/SystemUI/src/com/android/systemui/volume/VolumeDialog.java
+++ b/packages/SystemUI/src/com/android/systemui/volume/VolumeDialog.java
@@ -761,7 +761,37 @@
                 : (iconRes == R.drawable.ic_volume_media_bt || iconRes == row.iconRes)
                         ? Events.ICON_STATE_UNMUTE
                 : Events.ICON_STATE_UNKNOWN;
-        row.icon.setContentDescription(ss.name);
+        if (iconEnabled) {
+            if (isRingStream) {
+                if (isRingVibrate) {
+                    row.icon.setContentDescription(mContext.getString(
+                            R.string.volume_stream_content_description_unmute,
+                            ss.name));
+                } else {
+                    if (mController.hasVibrator()) {
+                        row.icon.setContentDescription(mContext.getString(
+                                R.string.volume_stream_content_description_vibrate,
+                                ss.name));
+                    } else {
+                        row.icon.setContentDescription(mContext.getString(
+                                R.string.volume_stream_content_description_mute,
+                                ss.name));
+                    }
+                }
+            } else {
+                if (ss.muted || mAutomute && ss.level == 0) {
+                   row.icon.setContentDescription(mContext.getString(
+                           R.string.volume_stream_content_description_unmute,
+                           ss.name));
+                } else {
+                    row.icon.setContentDescription(mContext.getString(
+                            R.string.volume_stream_content_description_mute,
+                            ss.name));
+                }
+            }
+        } else {
+            row.icon.setContentDescription(ss.name);
+        }
 
         // update slider
         final boolean enableSlider = !zenMuted;
diff --git a/packages/SystemUI/tests/src/com/android/systemui/qs/external/TileServiceManagerTests.java b/packages/SystemUI/tests/src/com/android/systemui/qs/external/TileServiceManagerTests.java
index f24b541..1e27603 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/qs/external/TileServiceManagerTests.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/qs/external/TileServiceManagerTests.java
@@ -18,7 +18,6 @@
 import android.content.ComponentName;
 import android.os.Handler;
 import android.os.HandlerThread;
-import android.service.quicksettings.TileService;
 import android.test.suitebuilder.annotation.SmallTest;
 import com.android.systemui.SysuiTestCase;
 import org.mockito.ArgumentCaptor;
@@ -42,11 +41,10 @@
         mTileServices = Mockito.mock(TileServices.class);
         Mockito.when(mTileServices.getContext()).thenReturn(mContext);
         mTileLifecycle = Mockito.mock(TileLifecycleManager.class);
+        Mockito.when(mTileLifecycle.isActiveTile()).thenReturn(false);
         ComponentName componentName = new ComponentName(mContext,
                 TileServiceManagerTests.class);
         Mockito.when(mTileLifecycle.getComponent()).thenReturn(componentName);
-        mContext.getSharedPreferences(TileServiceManager.PREFS_FILE, 0).edit()
-                .putInt(componentName.flattenToString(), TileService.TILE_MODE_PASSIVE).commit();
         mTileServiceManager = new TileServiceManager(mTileServices, mHandler, mTileLifecycle);
     }
 
diff --git a/preloaded-classes b/preloaded-classes
index be645d2..d854769 100644
--- a/preloaded-classes
+++ b/preloaded-classes
@@ -12,6 +12,7 @@
 [Landroid.animation.Keyframe;
 [Landroid.animation.PropertyValuesHolder;
 [Landroid.app.LoaderManagerImpl;
+[Landroid.app.Notification$Action;
 [Landroid.content.ContentProviderResult;
 [Landroid.content.ContentValues;
 [Landroid.content.Intent;
@@ -29,7 +30,6 @@
 [Landroid.content.res.Configuration;
 [Landroid.content.res.StringBlock;
 [Landroid.content.res.XmlBlock;
-[Landroid.database.Cursor;
 [Landroid.database.CursorWindow;
 [Landroid.database.sqlite.SQLiteConnection$Operation;
 [Landroid.database.sqlite.SQLiteConnectionPool$AcquiredConnectionStatus;
@@ -54,7 +54,6 @@
 [Landroid.graphics.drawable.GradientDrawable$Orientation;
 [Landroid.graphics.drawable.LayerDrawable$ChildDrawable;
 [Landroid.graphics.drawable.RippleForeground;
-[Landroid.hardware.display.WifiDisplay;
 [Landroid.hardware.soundtrigger.SoundTrigger$ConfidenceLevel;
 [Landroid.hardware.soundtrigger.SoundTrigger$Keyphrase;
 [Landroid.hardware.soundtrigger.SoundTrigger$KeyphraseRecognitionExtra;
@@ -83,6 +82,10 @@
 [Landroid.icu.util.ULocale$Category;
 [Landroid.icu.util.ULocale;
 [Landroid.media.AudioGain;
+[Landroid.media.MediaCodecInfo$CodecCapabilities;
+[Landroid.media.MediaCodecInfo$CodecProfileLevel;
+[Landroid.media.MediaCodecInfo$Feature;
+[Landroid.media.MediaCodecInfo;
 [Landroid.net.Network;
 [Landroid.net.NetworkInfo$DetailedState;
 [Landroid.net.NetworkInfo$State;
@@ -109,7 +112,6 @@
 [Landroid.text.method.TextKeyListener;
 [Landroid.text.style.AlignmentSpan;
 [Landroid.text.style.CharacterStyle;
-[Landroid.text.style.ClickableSpan;
 [Landroid.text.style.LeadingMarginSpan;
 [Landroid.text.style.LineBackgroundSpan;
 [Landroid.text.style.LineHeightSpan;
@@ -122,12 +124,11 @@
 [Landroid.text.style.URLSpan;
 [Landroid.text.style.WrapTogetherSpan;
 [Landroid.util.LongSparseArray;
-[Landroid.util.Pair;
+[Landroid.util.Range;
 [Landroid.util.Rational;
 [Landroid.view.Choreographer$CallbackQueue;
 [Landroid.view.Display$ColorTransform;
 [Landroid.view.Display$Mode;
-[Landroid.view.Display;
 [Landroid.view.HandlerActionQueue$HandlerAction;
 [Landroid.view.MenuItem;
 [Landroid.view.View;
@@ -198,11 +199,13 @@
 [Ljava.text.DateFormat$Field;
 [Ljava.text.Normalizer$Form;
 [Ljava.util.ArrayList;
+[Ljava.util.Comparators$NaturalOrderComparator;
 [Ljava.util.Enumeration;
 [Ljava.util.Formatter$Flags;
 [Ljava.util.Formatter$FormatString;
 [Ljava.util.HashMap$HashMapEntry;
 [Ljava.util.Hashtable$HashtableEntry;
+[Ljava.util.List;
 [Ljava.util.Locale$Category;
 [Ljava.util.Locale;
 [Ljava.util.Map$Entry;
@@ -216,11 +219,8 @@
 [Ljava.util.regex.Pattern;
 [Ljavax.crypto.Cipher$InitType;
 [Ljavax.crypto.Cipher$NeedToSet;
-[Ljavax.microedition.khronos.egl.EGLConfig;
 [Ljavax.net.ssl.KeyManager;
-[Ljavax.net.ssl.SSLSession;
 [Ljavax.net.ssl.TrustManager;
-[Ljavax.security.auth.x500.X500Principal;
 [Ljavax.security.cert.X509Certificate;
 [Llibcore.io.ClassPathURLStreamHandler;
 [Llibcore.reflect.AnnotationMember$DefaultValues;
@@ -307,12 +307,10 @@
 android.animation.PathKeyframes$1
 android.animation.PathKeyframes$2
 android.animation.PathKeyframes$FloatKeyframesBase
-android.animation.PathKeyframes$IntKeyframesBase
 android.animation.PathKeyframes$SimpleKeyframes
 android.animation.PropertyValuesHolder
 android.animation.PropertyValuesHolder$FloatPropertyValuesHolder
 android.animation.PropertyValuesHolder$IntPropertyValuesHolder
-android.animation.PropertyValuesHolder$PropertyValues
 android.animation.RectEvaluator
 android.animation.StateListAnimator
 android.animation.StateListAnimator$1
@@ -328,7 +326,6 @@
 android.app.Activity$HostCallbacks
 android.app.ActivityManager
 android.app.ActivityManager$MemoryInfo
-android.app.ActivityManager$RecentTaskInfo
 android.app.ActivityManager$RunningAppProcessInfo
 android.app.ActivityManager$RunningAppProcessInfo$1
 android.app.ActivityManager$StackId
@@ -348,7 +345,6 @@
 android.app.ActivityThread$ApplicationThread
 android.app.ActivityThread$BindServiceData
 android.app.ActivityThread$ContextCleanupInfo
-android.app.ActivityThread$CreateBackupAgentData
 android.app.ActivityThread$CreateServiceData
 android.app.ActivityThread$DropBoxReporter
 android.app.ActivityThread$EventLoggingReporter
@@ -381,7 +377,7 @@
 android.app.ContextImpl
 android.app.ContextImpl$ApplicationContentResolver
 android.app.Dialog
-android.app.Dialog$1
+android.app.Dialog$-void__init__android_content_Context_context_int_themeResId_boolean_createContextThemeWrapper_LambdaImpl0
 android.app.Dialog$ListenersHandler
 android.app.DialogFragment
 android.app.DownloadManager
@@ -402,8 +398,6 @@
 android.app.IAlarmManager$Stub
 android.app.IAlarmManager$Stub$Proxy
 android.app.IApplicationThread
-android.app.IBackupAgent
-android.app.IBackupAgent$Stub
 android.app.IInstrumentationWatcher
 android.app.IInstrumentationWatcher$Stub
 android.app.INotificationManager
@@ -415,6 +409,9 @@
 android.app.ITransientNotification$Stub
 android.app.IUiAutomationConnection
 android.app.IUiAutomationConnection$Stub
+android.app.IUiModeManager
+android.app.IUiModeManager$Stub
+android.app.IUiModeManager$Stub$Proxy
 android.app.Instrumentation
 android.app.IntentReceiverLeaked
 android.app.IntentService
@@ -437,16 +434,21 @@
 android.app.Notification
 android.app.Notification$1
 android.app.Notification$Action
+android.app.Notification$Action$1
 android.app.Notification$BigTextStyle
 android.app.Notification$Builder
+android.app.Notification$BuilderRemoteViews
 android.app.Notification$Style
 android.app.NotificationManager
+android.app.OnActivityPausedListener
 android.app.PendingIntent
 android.app.PendingIntent$1
 android.app.PendingIntent$CanceledException
 android.app.QueuedWork
 android.app.ReceiverRestrictedContext
 android.app.ResourcesManager
+android.app.ResourcesManager$1
+android.app.ResourcesManager$ActivityResources
 android.app.ResultInfo
 android.app.ResultInfo$1
 android.app.Service
@@ -530,11 +532,15 @@
 android.app.SystemServiceRegistry$69
 android.app.SystemServiceRegistry$7
 android.app.SystemServiceRegistry$70
+android.app.SystemServiceRegistry$71
+android.app.SystemServiceRegistry$72
+android.app.SystemServiceRegistry$73
+android.app.SystemServiceRegistry$74
 android.app.SystemServiceRegistry$8
 android.app.SystemServiceRegistry$9
 android.app.SystemServiceRegistry$CachedServiceFetcher
 android.app.SystemServiceRegistry$ServiceFetcher
-android.app.SystemServiceRegistry$StaticOuterContextServiceFetcher
+android.app.SystemServiceRegistry$StaticApplicationContextServiceFetcher
 android.app.SystemServiceRegistry$StaticServiceFetcher
 android.app.UiModeManager
 android.app.WallpaperManager
@@ -542,10 +548,9 @@
 android.app.admin.IDevicePolicyManager
 android.app.admin.IDevicePolicyManager$Stub
 android.app.admin.IDevicePolicyManager$Stub$Proxy
-android.app.backup.BackupAgent
-android.app.backup.BackupAgent$BackupServiceBinder
-android.app.backup.BackupAgent$SharedPrefsSynchronizer
-android.app.backup.BackupAgentHelper
+android.app.admin.SecurityLog
+android.app.admin.SecurityLog$SecurityEvent
+android.app.admin.SecurityLog$SecurityEvent$1
 android.app.backup.BackupDataInput
 android.app.backup.BackupDataInput$EntityHeader
 android.app.backup.BackupDataOutput
@@ -554,9 +559,6 @@
 android.app.backup.FileBackupHelperBase
 android.app.backup.FullBackup
 android.app.backup.FullBackupDataOutput
-android.app.backup.IBackupManager
-android.app.backup.IBackupManager$Stub
-android.app.backup.IBackupManager$Stub$Proxy
 android.app.job.JobScheduler
 android.app.trust.ITrustManager
 android.app.trust.ITrustManager$Stub
@@ -566,9 +568,6 @@
 android.app.usage.UsageStatsManager
 android.appwidget.AppWidgetManager
 android.appwidget.AppWidgetProvider
-android.auditing.SecurityLog
-android.auditing.SecurityLog$SecurityEvent
-android.auditing.SecurityLog$SecurityEvent$1
 android.bluetooth.BluetoothAdapter
 android.bluetooth.BluetoothAdapter$1
 android.bluetooth.BluetoothManager
@@ -585,6 +584,7 @@
 android.content.ActivityNotFoundException
 android.content.BroadcastReceiver
 android.content.BroadcastReceiver$PendingResult
+android.content.BroadcastReceiver$PendingResult$1
 android.content.ClipData
 android.content.ClipData$1
 android.content.ClipData$Item
@@ -600,7 +600,6 @@
 android.content.ContentProviderClient
 android.content.ContentProviderNative
 android.content.ContentProviderOperation
-android.content.ContentProviderOperation$Builder
 android.content.ContentProviderProxy
 android.content.ContentProviderResult
 android.content.ContentResolver
@@ -637,7 +636,6 @@
 android.content.IntentSender
 android.content.IntentSender$SendIntentException
 android.content.OperationApplicationException
-android.content.PeriodicSync
 android.content.RestrictionsManager
 android.content.ServiceConnection
 android.content.SharedPreferences
@@ -646,7 +644,6 @@
 android.content.SyncContext
 android.content.SyncRequest
 android.content.SyncRequest$1
-android.content.SyncRequest$Builder
 android.content.SyncResult
 android.content.SyncResult$1
 android.content.SyncStats
@@ -693,6 +690,7 @@
 android.content.pm.ResolveInfo$1
 android.content.pm.ServiceInfo
 android.content.pm.ServiceInfo$1
+android.content.pm.ShortcutManager
 android.content.pm.Signature
 android.content.pm.Signature$1
 android.content.pm.UserInfo
@@ -721,6 +719,8 @@
 android.content.res.Resources$NotFoundException
 android.content.res.Resources$Theme
 android.content.res.Resources$ThemeKey
+android.content.res.ResourcesImpl
+android.content.res.ResourcesImpl$ThemeImpl
 android.content.res.ResourcesKey
 android.content.res.StringBlock
 android.content.res.StringBlock$StyleIDs
@@ -762,7 +762,6 @@
 android.database.IContentObserver$Stub$Proxy
 android.database.MatrixCursor
 android.database.MatrixCursor$RowBuilder
-android.database.MergeCursor
 android.database.Observable
 android.database.SQLException
 android.database.sqlite.DatabaseObjectNotClosedException
@@ -775,7 +774,6 @@
 android.database.sqlite.SQLiteConnectionPool
 android.database.sqlite.SQLiteConnectionPool$AcquiredConnectionStatus
 android.database.sqlite.SQLiteConnectionPool$ConnectionWaiter
-android.database.sqlite.SQLiteConstraintException
 android.database.sqlite.SQLiteCursor
 android.database.sqlite.SQLiteCursorDriver
 android.database.sqlite.SQLiteCustomFunction
@@ -807,7 +805,6 @@
 android.ddm.DdmHandleThread
 android.ddm.DdmHandleViewDebug
 android.ddm.DdmRegister
-android.graphics.AvoidXfermode
 android.graphics.Bitmap
 android.graphics.Bitmap$1
 android.graphics.Bitmap$CompressFormat
@@ -820,10 +817,10 @@
 android.graphics.Camera
 android.graphics.Canvas
 android.graphics.Canvas$EdgeType
+android.graphics.Canvas$NoImagePreloadHolder
 android.graphics.CanvasProperty
 android.graphics.Color
 android.graphics.ColorFilter
-android.graphics.ColorMatrix
 android.graphics.ColorMatrixColorFilter
 android.graphics.ComposePathEffect
 android.graphics.ComposeShader
@@ -859,6 +856,7 @@
 android.graphics.Paint$FontMetrics
 android.graphics.Paint$FontMetricsInt
 android.graphics.Paint$Join
+android.graphics.Paint$NoImagePreloadHolder
 android.graphics.Paint$Style
 android.graphics.PaintFlagsDrawFilter
 android.graphics.Path
@@ -869,7 +867,6 @@
 android.graphics.PathMeasure
 android.graphics.Picture
 android.graphics.PixelFormat
-android.graphics.PixelXorXfermode
 android.graphics.Point
 android.graphics.Point$1
 android.graphics.PointF
@@ -903,11 +900,14 @@
 android.graphics.drawable.Animatable2
 android.graphics.drawable.AnimatedStateListDrawable
 android.graphics.drawable.AnimatedStateListDrawable$AnimatedStateListState
+android.graphics.drawable.AnimatedStateListDrawable$Transition
 android.graphics.drawable.AnimatedVectorDrawable
 android.graphics.drawable.AnimatedVectorDrawable$1
 android.graphics.drawable.AnimatedVectorDrawable$AnimatedVectorDrawableState
 android.graphics.drawable.AnimatedVectorDrawable$AnimatedVectorDrawableState$PendingAnimator
+android.graphics.drawable.AnimatedVectorDrawable$VectorDrawableAnimator
 android.graphics.drawable.AnimatedVectorDrawable$VectorDrawableAnimatorRT
+android.graphics.drawable.AnimatedVectorDrawable$VectorDrawableAnimatorUI
 android.graphics.drawable.AnimationDrawable
 android.graphics.drawable.AnimationDrawable$AnimationState
 android.graphics.drawable.BitmapDrawable
@@ -976,12 +976,14 @@
 android.hardware.Camera$Face
 android.hardware.ConsumerIrManager
 android.hardware.Sensor
+android.hardware.SensorEvent
 android.hardware.SensorEventListener
 android.hardware.SensorManager
 android.hardware.SerialManager
 android.hardware.SerialPort
 android.hardware.SystemSensorManager
 android.hardware.SystemSensorManager$BaseEventQueue
+android.hardware.SystemSensorManager$SensorEventQueue
 android.hardware.camera2.CameraCharacteristics$Key
 android.hardware.camera2.CameraManager
 android.hardware.camera2.CaptureRequest$Key
@@ -1000,12 +1002,6 @@
 android.hardware.display.IDisplayManager$Stub$Proxy
 android.hardware.display.IDisplayManagerCallback
 android.hardware.display.IDisplayManagerCallback$Stub
-android.hardware.display.WifiDisplay
-android.hardware.display.WifiDisplay$1
-android.hardware.display.WifiDisplaySessionInfo
-android.hardware.display.WifiDisplaySessionInfo$1
-android.hardware.display.WifiDisplayStatus
-android.hardware.display.WifiDisplayStatus$1
 android.hardware.fingerprint.FingerprintManager
 android.hardware.hdmi.HdmiControlManager
 android.hardware.input.IInputDevicesChangedListener
@@ -1021,6 +1017,10 @@
 # android.hardware.location.ActivityRecognitionHardware
 # android.hardware.location.IActivityRecognitionHardware
 # android.hardware.location.IActivityRecognitionHardware$Stub
+android.hardware.location.ContextHubManager
+android.hardware.location.ContextHubService
+android.hardware.location.IContextHubService
+android.hardware.location.IContextHubService$Stub
 android.hardware.radio.RadioManager
 android.hardware.radio.RadioManager$AmBandConfig
 android.hardware.radio.RadioManager$AmBandConfig$1
@@ -1046,6 +1046,7 @@
 android.hardware.soundtrigger.SoundTrigger$ConfidenceLevel
 android.hardware.soundtrigger.SoundTrigger$ConfidenceLevel$1
 android.hardware.soundtrigger.SoundTrigger$GenericRecognitionEvent
+android.hardware.soundtrigger.SoundTrigger$GenericRecognitionEvent$1
 android.hardware.soundtrigger.SoundTrigger$GenericSoundModel
 android.hardware.soundtrigger.SoundTrigger$Keyphrase
 android.hardware.soundtrigger.SoundTrigger$Keyphrase$1
@@ -1070,7 +1071,6 @@
 android.hardware.usb.IUsbManager$Stub$Proxy
 android.hardware.usb.UsbDevice
 android.hardware.usb.UsbDeviceConnection
-android.hardware.usb.UsbInterface
 android.hardware.usb.UsbManager
 android.hardware.usb.UsbRequest
 android.icu.impl.BMPSet
@@ -1396,6 +1396,7 @@
 android.media.AudioDevicePort
 android.media.AudioDevicePortConfig
 android.media.AudioFormat
+android.media.AudioFormat$1
 android.media.AudioGain
 android.media.AudioGainConfig
 android.media.AudioHandle
@@ -1412,8 +1413,6 @@
 android.media.AudioPortConfig
 android.media.AudioPortEventHandler
 android.media.AudioRecord
-android.media.AudioRoutesInfo
-android.media.AudioRoutesInfo$1
 android.media.AudioRouting
 android.media.AudioSystem
 android.media.AudioTimestamp
@@ -1425,21 +1424,13 @@
 android.media.ExifInterface
 android.media.IAudioFocusDispatcher
 android.media.IAudioFocusDispatcher$Stub
-android.media.IAudioRoutesObserver
-android.media.IAudioRoutesObserver$Stub
 android.media.IAudioService
 android.media.IAudioService$Stub
 android.media.IAudioService$Stub$Proxy
 android.media.IMediaHTTPConnection
 android.media.IMediaHTTPConnection$Stub
-android.media.IMediaRouterClient
-android.media.IMediaRouterClient$Stub
-android.media.IMediaRouterService
-android.media.IMediaRouterService$Stub
 android.media.IRecordingConfigDispatcher
 android.media.IRecordingConfigDispatcher$Stub
-android.media.IRemoteVolumeObserver
-android.media.IRemoteVolumeObserver$Stub
 android.media.Image
 android.media.ImageReader
 android.media.ImageReader$SurfaceImage
@@ -1447,10 +1438,18 @@
 android.media.ImageWriter$WriterSurfaceImage
 android.media.JetPlayer
 android.media.MediaCodec
+android.media.MediaCodecInfo
+android.media.MediaCodecInfo$AudioCapabilities
+android.media.MediaCodecInfo$CodecCapabilities
+android.media.MediaCodecInfo$CodecProfileLevel
+android.media.MediaCodecInfo$EncoderCapabilities
+android.media.MediaCodecInfo$Feature
+android.media.MediaCodecInfo$VideoCapabilities
 android.media.MediaCodecList
 android.media.MediaCrypto
 android.media.MediaDrm
 android.media.MediaExtractor
+android.media.MediaFormat
 android.media.MediaHTTPConnection
 android.media.MediaMetadataRetriever
 android.media.MediaMuxer
@@ -1461,17 +1460,6 @@
 android.media.MediaPlayer$OnSeekCompleteListener
 android.media.MediaRecorder
 android.media.MediaRouter
-android.media.MediaRouter$Callback
-android.media.MediaRouter$RouteCategory
-android.media.MediaRouter$RouteInfo
-android.media.MediaRouter$RouteInfo$1
-android.media.MediaRouter$Static
-android.media.MediaRouter$Static$1
-android.media.MediaRouter$Static$Client
-android.media.MediaRouter$VolumeChangeReceiver
-android.media.MediaRouter$WifiDisplayStatusChangedReceiver
-android.media.MediaRouterClientState
-android.media.MediaRouterClientState$1
 android.media.MediaScanner
 android.media.MediaSync
 android.media.PlaybackParams
@@ -1479,9 +1467,10 @@
 android.media.RemoteDisplay
 android.media.ResampleInputStream
 android.media.SubtitleController$Listener
-android.media.ThumbnailUtils
 android.media.ToneGenerator
-android.media.audiofx.AcousticEchoCanceler
+android.media.Utils
+android.media.Utils$1
+android.media.Utils$2
 android.media.audiofx.AudioEffect
 android.media.audiopolicy.AudioMix
 android.media.audiopolicy.AudioMixingRule
@@ -1504,13 +1493,13 @@
 android.net.ConnectivityManager
 android.net.ConnectivityManager$CallbackHandler
 android.net.ConnectivityManager$NetworkCallback
+android.net.ConnectivityThread
 android.net.Credentials
-android.net.DhcpResults
-android.net.DhcpResults$1
 android.net.EthernetManager
 android.net.IConnectivityManager
 android.net.IConnectivityManager$Stub
 android.net.IConnectivityManager$Stub$Proxy
+android.net.INetworkPolicyManager
 android.net.IpPrefix
 android.net.IpPrefix$1
 android.net.LinkAddress
@@ -1545,8 +1534,6 @@
 android.net.SSLCertificateSocketFactory
 android.net.SSLCertificateSocketFactory$1
 android.net.SSLSessionCache
-android.net.StaticIpConfiguration
-android.net.StaticIpConfiguration$1
 android.net.TrafficStats
 android.net.Uri
 android.net.Uri$1
@@ -1584,10 +1571,16 @@
 android.nfc.INfcAdapter$Stub$Proxy
 android.nfc.INfcCardEmulation
 android.nfc.INfcCardEmulation$Stub
+android.nfc.INfcCardEmulation$Stub$Proxy
 android.nfc.INfcFCardEmulation
 android.nfc.INfcFCardEmulation$Stub
+android.nfc.INfcFCardEmulation$Stub$Proxy
 android.nfc.INfcTag
 android.nfc.INfcTag$Stub
+android.nfc.INfcTag$Stub$Proxy
+android.nfc.NfcActivityManager
+android.nfc.NfcAdapter
+android.nfc.NfcAdapter$1
 android.nfc.NfcManager
 android.opengl.EGL14
 android.opengl.EGLConfig
@@ -1631,9 +1624,8 @@
 android.os.CancellationSignal$OnCancelListener
 android.os.CancellationSignal$Transport
 android.os.ConditionVariable
-android.os.CpuUsageInfo
-android.os.CpuUsageInfo$1
 android.os.DeadObjectException
+android.os.DeadSystemException
 android.os.Debug
 android.os.Debug$MemoryInfo
 android.os.Debug$MemoryInfo$1
@@ -1665,6 +1657,8 @@
 android.os.IUserManager
 android.os.IUserManager$Stub
 android.os.IUserManager$Stub$Proxy
+android.os.IVibratorService
+android.os.IVibratorService$Stub
 android.os.Looper
 android.os.MemoryFile
 android.os.Message
@@ -1679,10 +1673,13 @@
 android.os.ParcelFileDescriptor
 android.os.ParcelFileDescriptor$1
 android.os.ParcelFileDescriptor$AutoCloseInputStream
+android.os.ParcelFileDescriptor$AutoCloseOutputStream
 android.os.ParcelUuid
 android.os.Parcelable
 android.os.Parcelable$ClassLoaderCreator
 android.os.Parcelable$Creator
+android.os.ParcelableParcel
+android.os.ParcelableParcel$1
 android.os.PatternMatcher
 android.os.PatternMatcher$1
 android.os.PersistableBundle
@@ -1691,6 +1688,7 @@
 android.os.PowerManager$WakeLock
 android.os.PowerManager$WakeLock$1
 android.os.Process
+android.os.RecoverySystem
 android.os.RemoteException
 android.os.ResultReceiver
 android.os.SELinux
@@ -1726,24 +1724,26 @@
 android.os.StrictMode$VmPolicy$Builder
 android.os.SystemClock
 android.os.SystemProperties
+android.os.SystemVibrator
 android.os.Trace
 android.os.Trace$1
-android.os.TransactionTooLargeException
 android.os.UEventObserver
 android.os.UserHandle
 android.os.UserHandle$1
 android.os.UserManager
 android.os.Vibrator
 android.os.ZygoteStartFailedEx
+android.os.health.SystemHealthManager
 android.os.storage.IMountService
 android.os.storage.IMountService$Stub
 android.os.storage.IMountService$Stub$Proxy
+android.os.storage.IObbActionListener
+android.os.storage.IObbActionListener$Stub
 android.os.storage.StorageManager
+android.os.storage.StorageManager$ObbActionListener
 android.os.storage.StorageVolume
 android.os.storage.StorageVolume$1
-android.preference.Preference$OnPreferenceChangeListener
 android.preference.PreferenceActivity
-android.preference.PreferenceFragment
 android.preference.PreferenceFragment$OnPreferenceStartFragmentCallback
 android.preference.PreferenceManager
 android.preference.PreferenceManager$OnPreferenceTreeClickListener
@@ -1836,7 +1836,6 @@
 android.system.UnixSocketAddress
 android.telecom.TelecomManager
 android.telephony.CarrierConfigManager
-android.telephony.PhoneNumberUtils
 android.telephony.Rlog
 android.telephony.SubscriptionManager
 android.telephony.TelephonyManager
@@ -1852,12 +1851,15 @@
 android.text.GetChars
 android.text.GraphicsOperations
 android.text.Html
+android.text.Html$HtmlParser
+android.text.HtmlToSpannedConverter
 android.text.Hyphenator
 android.text.InputFilter
 android.text.InputType
 android.text.Layout
 android.text.Layout$Alignment
 android.text.Layout$Directions
+android.text.Layout$Ellipsizer
 android.text.MeasuredText
 android.text.NoCopySpan
 android.text.NoCopySpan$Concrete
@@ -1916,7 +1918,6 @@
 android.text.method.SingleLineTransformationMethod
 android.text.method.TextKeyListener
 android.text.method.TextKeyListener$Capitalize
-android.text.method.Touch
 android.text.method.TransformationMethod
 android.text.method.TransformationMethod2
 android.text.style.AlignmentSpan
@@ -1937,6 +1938,7 @@
 android.text.style.StyleSpan
 android.text.style.SuggestionSpan
 android.text.style.TabStopSpan
+android.text.style.TextAppearanceSpan
 android.text.style.URLSpan
 android.text.style.UnderlineSpan
 android.text.style.UpdateAppearance
@@ -1985,7 +1987,6 @@
 android.util.EventLog$Event
 android.util.FloatProperty
 android.util.IntProperty
-android.util.JsonReader
 android.util.LocaleList
 android.util.LocaleList$1
 android.util.Log
@@ -1993,7 +1994,6 @@
 android.util.Log$ImmediateLogWriter
 android.util.Log$TerribleFailureHandler
 android.util.LogPrinter
-android.util.LongArray
 android.util.LongSparseArray
 android.util.LongSparseLongArray
 android.util.LruCache
@@ -2006,15 +2006,16 @@
 android.util.Pair
 android.util.PathParser
 android.util.PathParser$PathData
-android.util.Patterns
 android.util.Pools$Pool
 android.util.Pools$SimplePool
 android.util.Pools$SynchronizedPool
 android.util.Printer
 android.util.Property
+android.util.Range
 android.util.Rational
 android.util.Singleton
 android.util.Size
+android.util.SizeF
 android.util.Slog
 android.util.SparseArray
 android.util.SparseBooleanArray
@@ -2031,6 +2032,7 @@
 android.view.AbsSavedState$2
 android.view.ActionMode
 android.view.ActionMode$Callback
+android.view.ActionMode$Callback2
 android.view.ActionProvider
 android.view.ActionProvider$SubUiVisibilityListener
 android.view.Choreographer
@@ -2135,7 +2137,6 @@
 android.view.RenderNode
 android.view.RenderNodeAnimator
 android.view.RenderNodeAnimator$1
-android.view.RenderNodeAnimatorSetHelper
 android.view.SearchEvent
 android.view.SoundEffectConstants
 android.view.SubMenu
@@ -2151,6 +2152,7 @@
 android.view.SurfaceSession
 android.view.SurfaceView
 android.view.TextureView
+android.view.TextureView$SurfaceTextureListener
 android.view.ThreadedRenderer
 android.view.ThreadedRenderer$HardwareDrawCallbacks
 android.view.ThreadedRenderer$ProcessInitializer
@@ -2174,6 +2176,7 @@
 android.view.View$AttachInfo$Callbacks
 android.view.View$BaseSavedState
 android.view.View$BaseSavedState$1
+android.view.View$CheckForLongPress
 android.view.View$CheckForTap
 android.view.View$ForegroundInfo
 android.view.View$ListenerInfo
@@ -2258,10 +2261,10 @@
 android.view.WindowCallbacks
 android.view.WindowContentFrameStats
 android.view.WindowContentFrameStats$1
-android.view.WindowId
 android.view.WindowInsets
 android.view.WindowLeaked
 android.view.WindowManager
+android.view.WindowManager$BadTokenException
 android.view.WindowManager$LayoutParams
 android.view.WindowManager$LayoutParams$1
 android.view.WindowManagerGlobal
@@ -2280,6 +2283,7 @@
 android.view.accessibility.AccessibilityRecord
 android.view.accessibility.CaptioningManager
 android.view.accessibility.CaptioningManager$1
+android.view.accessibility.CaptioningManager$CaptionStyle
 android.view.accessibility.CaptioningManager$CaptioningChangeListener
 android.view.accessibility.CaptioningManager$MyContentObserver
 android.view.accessibility.IAccessibilityManager
@@ -2295,6 +2299,7 @@
 android.view.animation.Animation$2
 android.view.animation.Animation$3
 android.view.animation.Animation$AnimationListener
+android.view.animation.Animation$Description
 android.view.animation.AnimationSet
 android.view.animation.AnimationUtils
 android.view.animation.BaseInterpolator
@@ -2316,6 +2321,7 @@
 android.view.inputmethod.ExtractedText
 android.view.inputmethod.ExtractedText$1
 android.view.inputmethod.InputConnection
+android.view.inputmethod.InputConnectionInspector
 android.view.inputmethod.InputMethodManager
 android.view.inputmethod.InputMethodManager$1
 android.view.inputmethod.InputMethodManager$ControlledInputConnectionWrapper
@@ -2323,15 +2329,17 @@
 android.view.inputmethod.InputMethodManager$H
 android.view.inputmethod.InputMethodManager$ImeInputEventSender
 android.view.inputmethod.InputMethodManager$PendingEvent
-android.view.inputmethod.InputMethodSubtype
 android.view.textservice.SpellCheckerSession$SpellCheckerSessionListener
 android.view.textservice.SpellCheckerSubtype
 android.view.textservice.SpellCheckerSubtype$1
 android.view.textservice.TextServicesManager
+android.webkit.IWebViewUpdateService
+android.webkit.IWebViewUpdateService$Stub
 android.webkit.MimeTypeMap
 android.webkit.URLUtil
 android.webkit.WebSettings
 android.webkit.WebView
+android.webkit.WebViewClient
 android.webkit.WebViewFactory
 android.webkit.WebViewFactory$MissingWebViewPackageException
 android.widget.AbsListView
@@ -2348,6 +2356,7 @@
 android.widget.AbsListView$WindowRunnnable
 android.widget.AbsSeekBar
 android.widget.AbsSpinner
+android.widget.AbsSpinner$RecycleBin
 android.widget.AbsoluteLayout
 android.widget.ActionMenuPresenter
 android.widget.ActionMenuPresenter$1
@@ -2362,13 +2371,9 @@
 android.widget.AdapterView
 android.widget.AdapterView$AdapterDataSetObserver
 android.widget.AdapterView$OnItemClickListener
-android.widget.AdapterView$OnItemLongClickListener
 android.widget.AdapterView$OnItemSelectedListener
 android.widget.ArrayAdapter
 android.widget.AutoCompleteTextView
-android.widget.AutoCompleteTextView$DropDownItemClickListener
-android.widget.AutoCompleteTextView$MyWatcher
-android.widget.AutoCompleteTextView$PassThroughClickListener
 android.widget.BaseAdapter
 android.widget.Button
 android.widget.CheckBox
@@ -2381,15 +2386,17 @@
 android.widget.Editor
 android.widget.Editor$1
 android.widget.Editor$2
-android.widget.Editor$3
 android.widget.Editor$Blink
 android.widget.Editor$CursorAnchorInfoNotifier
+android.widget.Editor$CursorController
 android.widget.Editor$EditOperation
 android.widget.Editor$EditOperation$1
 android.widget.Editor$InputContentType
 android.widget.Editor$InputMethodState
+android.widget.Editor$InsertionPointCursorController
 android.widget.Editor$PositionListener
 android.widget.Editor$ProcessTextIntentActionsHandler
+android.widget.Editor$SelectionModifierCursorController
 android.widget.Editor$SpanController
 android.widget.Editor$SuggestionHelper
 android.widget.Editor$SuggestionHelper$SuggestionSpanComparator
@@ -2439,6 +2446,19 @@
 android.widget.RelativeLayout$DependencyGraph$Node
 android.widget.RelativeLayout$LayoutParams
 android.widget.RemoteViews
+android.widget.RemoteViews$1
+android.widget.RemoteViews$2
+android.widget.RemoteViews$3
+android.widget.RemoteViews$Action
+android.widget.RemoteViews$ActionException
+android.widget.RemoteViews$BitmapCache
+android.widget.RemoteViews$LayoutParamAction
+android.widget.RemoteViews$MemoryUsageCounter
+android.widget.RemoteViews$MutablePair
+android.widget.RemoteViews$OnClickHandler
+android.widget.RemoteViews$ReflectionAction
+android.widget.RemoteViews$RuntimeAction
+android.widget.RemoteViews$SetDrawableParameters
 android.widget.RemoteViewsAdapter$RemoteAdapterConnectionCallback
 android.widget.RtlSpacingHelper
 android.widget.ScrollBarDrawable
@@ -2451,7 +2471,10 @@
 android.widget.SpellChecker
 android.widget.SpellChecker$SpellParser
 android.widget.Spinner
+android.widget.Spinner$SpinnerPopup
 android.widget.SpinnerAdapter
+android.widget.Switch
+android.widget.Switch$1
 android.widget.TextView
 android.widget.TextView$3
 android.widget.TextView$BufferType
@@ -2460,6 +2483,7 @@
 android.widget.TextView$Drawables
 android.widget.TextView$OnEditorActionListener
 android.widget.TextView$SavedState
+android.widget.TextView$SavedState$1
 android.widget.ThemedSpinnerAdapter
 android.widget.Toast
 android.widget.Toast$TN
@@ -2470,7 +2494,6 @@
 android.widget.Toolbar$2
 android.widget.Toolbar$ExpandedActionViewMenuPresenter
 android.widget.Toolbar$LayoutParams
-android.widget.ViewAnimator
 android.widget.WrapperListAdapter
 com.android.dex.Annotation
 com.android.dex.ClassData
@@ -2511,9 +2534,10 @@
 com.android.internal.app.IAppOpsService
 com.android.internal.app.IAppOpsService$Stub
 com.android.internal.app.IAppOpsService$Stub$Proxy
+com.android.internal.app.IBatteryStats
+com.android.internal.app.IBatteryStats$Stub
 com.android.internal.app.IVoiceInteractor
 com.android.internal.app.IVoiceInteractor$Stub
-com.android.internal.app.WindowDecorActionBar
 com.android.internal.appwidget.IAppWidgetService
 com.android.internal.appwidget.IAppWidgetService$Stub
 com.android.internal.appwidget.IAppWidgetService$Stub$Proxy
@@ -2521,6 +2545,8 @@
 com.android.internal.content.ReferrerIntent
 com.android.internal.content.ReferrerIntent$1
 com.android.internal.inputmethod.InputMethodUtils
+com.android.internal.inputmethod.InputMethodUtils$1
+com.android.internal.inputmethod.LocaleUtils$LocaleExtractor
 com.android.internal.logging.AndroidConfig
 com.android.internal.logging.AndroidHandler
 com.android.internal.logging.AndroidHandler$1
@@ -2575,6 +2601,9 @@
 com.android.internal.util.FastXmlSerializer
 com.android.internal.util.GrowingArrayUtils
 com.android.internal.util.LineBreakBufferedWriter
+com.android.internal.util.MessageUtils
+com.android.internal.util.NotificationColorUtil
+com.android.internal.util.NotificationColorUtil$ColorUtilsFromCompat
 com.android.internal.util.Preconditions
 com.android.internal.util.VirtualRefBasePtr
 com.android.internal.util.XmlUtils
@@ -2613,13 +2642,9 @@
 com.android.internal.view.menu.MenuPresenter$Callback
 com.android.internal.view.menu.MenuView
 com.android.internal.view.menu.ShowableListMenu
-com.android.internal.widget.ActionBarOverlayLayout$ActionBarVisibilityCallback
-com.android.internal.widget.AlertDialogLayout
 com.android.internal.widget.BackgroundFallback
-com.android.internal.widget.ButtonBarLayout
 com.android.internal.widget.DecorContentParent
 com.android.internal.widget.DecorToolbar
-com.android.internal.widget.DialogTitle
 com.android.internal.widget.EditableInputConnection
 com.android.internal.widget.ScrollBarUtils
 com.android.internal.widget.ToolbarWidgetWrapper
@@ -2884,7 +2909,6 @@
 dalvik.system.CloseGuard$DefaultReporter
 dalvik.system.CloseGuard$Reporter
 dalvik.system.DalvikLogHandler
-dalvik.system.DalvikLogging
 dalvik.system.DexClassLoader
 dalvik.system.DexFile
 dalvik.system.DexFile$DFEnum
@@ -2911,6 +2935,7 @@
 java.io.ByteArrayOutputStream
 java.io.CharArrayWriter
 java.io.Closeable
+java.io.Console
 java.io.DataInput
 java.io.DataInputStream
 java.io.DataOutput
@@ -2922,15 +2947,14 @@
 java.io.Externalizable
 java.io.File
 java.io.File$PathStatus
-java.io.File$TempDirectory
 java.io.FileDescriptor
+java.io.FileFilter
 java.io.FileInputStream
 java.io.FileInputStream$UseManualSkipException
 java.io.FileNotFoundException
 java.io.FileOutputStream
 java.io.FileReader
 java.io.FileSystem
-java.io.FileWriter
 java.io.FilenameFilter
 java.io.FilterInputStream
 java.io.FilterOutputStream
@@ -2941,7 +2965,6 @@
 java.io.InputStreamReader
 java.io.InterruptedIOException
 java.io.InvalidObjectException
-java.io.NotSerializableException
 java.io.ObjectInput
 java.io.ObjectInputStream
 java.io.ObjectInputStream$BlockDataInputStream
@@ -3013,6 +3036,7 @@
 java.lang.EnumConstantNotPresentException
 java.lang.Error
 java.lang.Exception
+java.lang.ExceptionInInitializerError
 java.lang.Float
 java.lang.FloatingDecimal
 java.lang.FloatingDecimal$1
@@ -3056,7 +3080,6 @@
 java.lang.RuntimeException
 java.lang.RuntimePermission
 java.lang.SecurityException
-java.lang.SecurityManager
 java.lang.Short
 java.lang.Short$ShortCache
 java.lang.Shutdown
@@ -3133,7 +3156,6 @@
 java.math.BigInt
 java.math.BigInteger
 java.math.BitLevel
-java.math.Multiplication
 java.math.NativeBN
 java.math.RoundingMode
 java.net.AbstractPlainDatagramSocketImpl
@@ -3260,22 +3282,18 @@
 java.security.AlgorithmParameters
 java.security.AlgorithmParametersSpi
 java.security.BasicPermission
-java.security.BasicPermissionCollection
 java.security.CryptoPrimitive
 java.security.GeneralSecurityException
 java.security.Guard
 java.security.InvalidAlgorithmParameterException
 java.security.InvalidKeyException
-java.security.InvalidParameterException
 java.security.Key
 java.security.KeyException
 java.security.KeyFactory
 java.security.KeyFactorySpi
 java.security.KeyManagementException
-java.security.KeyPair
 java.security.KeyStore
 java.security.KeyStore$1
-java.security.KeyStore$LoadStoreParameter
 java.security.KeyStoreException
 java.security.KeyStoreSpi
 java.security.MessageDigest
@@ -3285,6 +3303,7 @@
 java.security.NoSuchProviderException
 java.security.Permission
 java.security.PermissionCollection
+java.security.Permissions
 java.security.Principal
 java.security.PrivateKey
 java.security.PrivilegedAction
@@ -3332,7 +3351,6 @@
 java.security.cert.PKIXRevocationChecker
 java.security.cert.PolicyNode
 java.security.cert.TrustAnchor
-java.security.cert.X509CRL
 java.security.cert.X509CertSelector
 java.security.cert.X509Certificate
 java.security.cert.X509Extension
@@ -3342,7 +3360,6 @@
 java.security.interfaces.ECPrivateKey
 java.security.interfaces.ECPublicKey
 java.security.interfaces.RSAKey
-java.security.interfaces.RSAPrivateCrtKey
 java.security.interfaces.RSAPrivateKey
 java.security.interfaces.RSAPublicKey
 java.security.spec.AlgorithmParameterSpec
@@ -3351,19 +3368,14 @@
 java.security.spec.ECFieldFp
 java.security.spec.ECParameterSpec
 java.security.spec.ECPoint
-java.security.spec.ECPrivateKeySpec
 java.security.spec.ECPublicKeySpec
 java.security.spec.EllipticCurve
 java.security.spec.EncodedKeySpec
 java.security.spec.InvalidKeySpecException
 java.security.spec.InvalidParameterSpecException
 java.security.spec.KeySpec
-java.security.spec.PKCS8EncodedKeySpec
-java.security.spec.RSAPrivateCrtKeySpec
-java.security.spec.RSAPrivateKeySpec
 java.security.spec.RSAPublicKeySpec
 java.security.spec.X509EncodedKeySpec
-java.sql.Timestamp
 java.text.AttributedCharacterIterator$Attribute
 java.text.CalendarBuilder
 java.text.Collator
@@ -3401,7 +3413,9 @@
 java.util.AbstractSequentialList
 java.util.AbstractSet
 java.util.ArrayDeque
+java.util.ArrayDeque$DeqIterator
 java.util.ArrayList
+java.util.ArrayList$ArrayListSpliterator
 java.util.ArrayList$Itr
 java.util.ArrayList$ListItr
 java.util.ArrayList$SubList
@@ -3414,6 +3428,7 @@
 java.util.Collections
 java.util.Collections$1
 java.util.Collections$2
+java.util.Collections$3
 java.util.Collections$AsLIFOQueue
 java.util.Collections$CheckedCollection
 java.util.Collections$CheckedList
@@ -3456,6 +3471,14 @@
 java.util.Collections$UnmodifiableSortedSet
 java.util.ComparableTimSort
 java.util.Comparator
+java.util.Comparator$-java_util_Comparator_comparingDouble_java_util_function_ToDoubleFunction_keyExtractor_LambdaImpl0
+java.util.Comparator$-java_util_Comparator_comparingInt_java_util_function_ToIntFunction_keyExtractor_LambdaImpl0
+java.util.Comparator$-java_util_Comparator_comparingLong_java_util_function_ToLongFunction_keyExtractor_LambdaImpl0
+java.util.Comparator$-java_util_Comparator_comparing_java_util_function_Function_keyExtractor_LambdaImpl0
+java.util.Comparator$-java_util_Comparator_comparing_java_util_function_Function_keyExtractor_java_util_Comparator_keyComparator_LambdaImpl0
+java.util.Comparator$-java_util_Comparator_thenComparing_java_util_Comparator_other_LambdaImpl0
+java.util.Comparators$NaturalOrderComparator
+java.util.Comparators$NullComparator
 java.util.ConcurrentModificationException
 java.util.Currency
 java.util.Date
@@ -3464,7 +3487,6 @@
 java.util.DualPivotQuicksort
 java.util.EnumMap
 java.util.EnumMap$1
-java.util.EnumMap$EnumMapIterator
 java.util.EnumSet
 java.util.Enumeration
 java.util.EventListener
@@ -3497,8 +3519,6 @@
 java.util.Hashtable$KeySet
 java.util.Hashtable$ValueCollection
 java.util.IdentityHashMap
-java.util.IdentityHashMap$EntryIterator
-java.util.IdentityHashMap$EntrySet
 java.util.IdentityHashMap$IdentityHashMapIterator
 java.util.IdentityHashMap$KeySet
 java.util.IllegalFormatException
@@ -3538,7 +3558,6 @@
 java.util.RandomAccess
 java.util.RandomAccessSubList
 java.util.RegularEnumSet
-java.util.RegularEnumSet$EnumSetIterator
 java.util.ResourceBundle
 java.util.ResourceBundle$1
 java.util.ResourceBundle$BundleReference
@@ -3550,7 +3569,6 @@
 java.util.ResourceBundle$LoaderReference
 java.util.ResourceBundle$RBClassLoader
 java.util.ResourceBundle$RBClassLoader$1
-java.util.Scanner
 java.util.ServiceLoader
 java.util.ServiceLoader$1
 java.util.ServiceLoader$LazyIterator
@@ -3558,6 +3576,17 @@
 java.util.SimpleTimeZone
 java.util.SortedMap
 java.util.SortedSet
+java.util.Spliterator
+java.util.Spliterator$OfDouble
+java.util.Spliterator$OfInt
+java.util.Spliterator$OfLong
+java.util.Spliterator$OfPrimitive
+java.util.Spliterators
+java.util.Spliterators$EmptySpliterator
+java.util.Spliterators$EmptySpliterator$OfDouble
+java.util.Spliterators$EmptySpliterator$OfInt
+java.util.Spliterators$EmptySpliterator$OfLong
+java.util.Spliterators$EmptySpliterator$OfRef
 java.util.Stack
 java.util.StringTokenizer
 java.util.SubList
@@ -3569,12 +3598,10 @@
 java.util.TimerTask
 java.util.TimerThread
 java.util.TreeMap
-java.util.TreeMap$AscendingSubMap
 java.util.TreeMap$EntryIterator
 java.util.TreeMap$EntrySet
 java.util.TreeMap$KeyIterator
 java.util.TreeMap$KeySet
-java.util.TreeMap$NavigableSubMap
 java.util.TreeMap$PrivateEntryIterator
 java.util.TreeMap$TreeMapEntry
 java.util.TreeMap$ValueIterator
@@ -3595,14 +3622,12 @@
 java.util.WeakHashMap$Values
 java.util.XMLUtils
 java.util.concurrent.AbstractExecutorService
-java.util.concurrent.ArrayBlockingQueue
 java.util.concurrent.BlockingQueue
 java.util.concurrent.Callable
 java.util.concurrent.CancellationException
 java.util.concurrent.ConcurrentHashMap
 java.util.concurrent.ConcurrentHashMap$BaseIterator
 java.util.concurrent.ConcurrentHashMap$CollectionView
-java.util.concurrent.ConcurrentHashMap$CounterCell
 java.util.concurrent.ConcurrentHashMap$ForwardingNode
 java.util.concurrent.ConcurrentHashMap$KeyIterator
 java.util.concurrent.ConcurrentHashMap$KeySetView
@@ -3611,8 +3636,6 @@
 java.util.concurrent.ConcurrentHashMap$Traverser
 java.util.concurrent.ConcurrentHashMap$TreeBin
 java.util.concurrent.ConcurrentHashMap$TreeNode
-java.util.concurrent.ConcurrentHashMap$ValueIterator
-java.util.concurrent.ConcurrentHashMap$ValuesView
 java.util.concurrent.ConcurrentLinkedQueue
 java.util.concurrent.ConcurrentLinkedQueue$Node
 java.util.concurrent.ConcurrentMap
@@ -3689,6 +3712,16 @@
 java.util.concurrent.locks.ReentrantReadWriteLock$Sync
 java.util.concurrent.locks.ReentrantReadWriteLock$Sync$ThreadLocalHoldCounter
 java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock
+java.util.function.BiConsumer
+java.util.function.BiFunction
+java.util.function.Consumer
+java.util.function.Function
+java.util.function.Predicate
+java.util.function.Supplier
+java.util.function.ToDoubleFunction
+java.util.function.ToIntFunction
+java.util.function.ToLongFunction
+java.util.function.UnaryOperator
 java.util.jar.JarEntry
 java.util.jar.JarFile
 java.util.jar.JarFile$1
@@ -3709,15 +3742,19 @@
 java.util.logging.LogManager$LoggerWeakRef
 java.util.logging.LogManager$RootLogger
 java.util.logging.LogManager$SystemLoggerContext
-java.util.logging.LogRecord
 java.util.logging.Logger
 java.util.logging.LoggingPermission
 java.util.logging.LoggingProxyImpl
+java.util.prefs.AbstractPreferences
+java.util.prefs.Preferences
 java.util.regex.MatchResult
 java.util.regex.Matcher
 java.util.regex.Pattern
 java.util.regex.PatternSyntaxException
 java.util.spi.LocaleServiceProvider
+java.util.stream.BaseStream
+java.util.stream.Stream
+java.util.stream.StreamSupport
 java.util.zip.Adler32
 java.util.zip.CRC32
 java.util.zip.CheckedInputStream
@@ -3748,7 +3785,6 @@
 javax.crypto.CipherSpi
 javax.crypto.IllegalBlockSizeException
 javax.crypto.JceSecurity
-javax.crypto.Mac
 javax.crypto.NoSuchPaddingException
 javax.crypto.NullCipher
 javax.crypto.SecretKey
@@ -3757,10 +3793,6 @@
 javax.crypto.spec.SecretKeySpec
 javax.microedition.khronos.egl.EGL
 javax.microedition.khronos.egl.EGL10
-javax.microedition.khronos.egl.EGLConfig
-javax.microedition.khronos.egl.EGLContext
-javax.microedition.khronos.egl.EGLDisplay
-javax.microedition.khronos.egl.EGLSurface
 javax.microedition.khronos.opengles.GL
 javax.microedition.khronos.opengles.GL10
 javax.microedition.khronos.opengles.GL10Ext
@@ -3771,7 +3803,6 @@
 javax.net.ServerSocketFactory
 javax.net.SocketFactory
 javax.net.ssl.ExtendedSSLSession
-javax.net.ssl.HandshakeCompletedEvent
 javax.net.ssl.HandshakeCompletedListener
 javax.net.ssl.HostnameVerifier
 javax.net.ssl.HttpsURLConnection
@@ -3779,23 +3810,20 @@
 javax.net.ssl.KeyManagerFactory
 javax.net.ssl.KeyManagerFactory$1
 javax.net.ssl.KeyManagerFactorySpi
+javax.net.ssl.SNIHostName
+javax.net.ssl.SNIServerName
 javax.net.ssl.SSLContext
 javax.net.ssl.SSLContextSpi
 javax.net.ssl.SSLEngine
 javax.net.ssl.SSLException
-javax.net.ssl.SSLHandshakeException
 javax.net.ssl.SSLParameters
 javax.net.ssl.SSLPeerUnverifiedException
 javax.net.ssl.SSLProtocolException
-javax.net.ssl.SSLServerSocket
 javax.net.ssl.SSLServerSocketFactory
 javax.net.ssl.SSLSession
-javax.net.ssl.SSLSessionBindingEvent
-javax.net.ssl.SSLSessionBindingListener
 javax.net.ssl.SSLSessionContext
 javax.net.ssl.SSLSocket
 javax.net.ssl.SSLSocketFactory
-javax.net.ssl.SSLSocketFactory$1
 javax.net.ssl.TrustManager
 javax.net.ssl.TrustManagerFactory
 javax.net.ssl.TrustManagerFactory$1
@@ -3841,7 +3869,6 @@
 libcore.io.NioBufferIterator
 libcore.io.Os
 libcore.io.Posix
-libcore.math.MathUtils
 libcore.net.NetworkSecurityPolicy
 libcore.net.NetworkSecurityPolicy$DefaultNetworkSecurityPolicy
 libcore.net.UriCodec
@@ -3857,7 +3884,6 @@
 libcore.reflect.ListOfTypes
 libcore.reflect.ListOfVariables
 libcore.reflect.ParameterizedTypeImpl
-libcore.reflect.TypeVariableImpl
 libcore.reflect.Types
 libcore.util.BasicLruCache
 libcore.util.CharsetUtils
@@ -3866,7 +3892,6 @@
 libcore.util.NativeAllocationRegistry
 libcore.util.NativeAllocationRegistry$CleanerRunner
 libcore.util.NativeAllocationRegistry$CleanerThunk
-libcore.util.Objects
 libcore.util.ZoneInfo
 libcore.util.ZoneInfo$CheckedArithmeticException
 libcore.util.ZoneInfo$WallTime
@@ -3892,11 +3917,8 @@
 org.apache.http.HttpResponse
 org.apache.http.HttpVersion
 org.apache.http.NameValuePair
-org.apache.http.ProtocolException
 org.apache.http.ProtocolVersion
-org.apache.http.ReasonPhraseCatalog
 org.apache.http.StatusLine
-org.apache.http.client.ClientProtocolException
 org.apache.http.client.HttpClient
 org.apache.http.client.ResponseHandler
 org.apache.http.client.methods.AbortableHttpRequest
@@ -3905,26 +3927,15 @@
 org.apache.http.client.methods.HttpPost
 org.apache.http.client.methods.HttpRequestBase
 org.apache.http.client.methods.HttpUriRequest
-org.apache.http.client.utils.URLEncodedUtils
 org.apache.http.conn.ClientConnectionManager
 org.apache.http.conn.ConnectTimeoutException
-org.apache.http.conn.params.ConnManagerPNames
-org.apache.http.conn.params.ConnManagerParams
-org.apache.http.conn.params.ConnManagerParams$1
-org.apache.http.conn.params.ConnPerRoute
-org.apache.http.conn.scheme.LayeredSocketFactory
-org.apache.http.conn.scheme.SocketFactory
 org.apache.http.entity.AbstractHttpEntity
-org.apache.http.entity.BasicHttpEntity
 org.apache.http.entity.ByteArrayEntity
-org.apache.http.impl.client.EntityEnclosingRequestWrapper
-org.apache.http.impl.client.RequestWrapper
 org.apache.http.impl.cookie.DateParseException
 org.apache.http.impl.cookie.DateUtils
 org.apache.http.message.AbstractHttpMessage
 org.apache.http.message.BasicHeader
 org.apache.http.message.BasicHttpResponse
-org.apache.http.message.BasicNameValuePair
 org.apache.http.message.BasicStatusLine
 org.apache.http.message.HeaderGroup
 org.apache.http.params.AbstractHttpParams
@@ -3933,6 +3944,18 @@
 org.apache.http.params.HttpConnectionParams
 org.apache.http.params.HttpParams
 org.apache.http.protocol.HttpContext
+org.ccil.cowan.tagsoup.AttributesImpl
+org.ccil.cowan.tagsoup.AutoDetector
+org.ccil.cowan.tagsoup.Element
+org.ccil.cowan.tagsoup.ElementType
+org.ccil.cowan.tagsoup.HTMLModels
+org.ccil.cowan.tagsoup.HTMLScanner
+org.ccil.cowan.tagsoup.HTMLSchema
+org.ccil.cowan.tagsoup.Parser
+org.ccil.cowan.tagsoup.Parser$1
+org.ccil.cowan.tagsoup.ScanHandler
+org.ccil.cowan.tagsoup.Scanner
+org.ccil.cowan.tagsoup.Schema
 org.json.JSON
 org.json.JSONArray
 org.json.JSONException
@@ -3954,6 +3977,7 @@
 org.xml.sax.SAXNotRecognizedException
 org.xml.sax.SAXNotSupportedException
 org.xml.sax.XMLReader
+org.xml.sax.ext.LexicalHandler
 org.xml.sax.helpers.DefaultHandler
 org.xmlpull.v1.XmlPullParser
 org.xmlpull.v1.XmlPullParserException
diff --git a/proto/src/metrics_constants.proto b/proto/src/metrics_constants.proto
index b3613df..ea3cffe 100644
--- a/proto/src/metrics_constants.proto
+++ b/proto/src/metrics_constants.proto
@@ -2135,6 +2135,9 @@
     // Suggestion -> Overflow -> Remove.
     ACTION_SETTINGS_DISMISS_SUGGESTION = 387;
 
+    // Settings > Apps > Gear > Special Access > Premium SMS access
+    PREMIUM_SMS_ACCESS = 388;
+
     // Add new aosp constants above this line.
     // END OF AOSP CONSTANTS
   }
diff --git a/rs/java/android/renderscript/ScriptGroup.java b/rs/java/android/renderscript/ScriptGroup.java
index 219f16b..35ae8b4 100644
--- a/rs/java/android/renderscript/ScriptGroup.java
+++ b/rs/java/android/renderscript/ScriptGroup.java
@@ -187,6 +187,23 @@
             guard.open("destroy");
         }
 
+        /**
+         * Destroys this Closure and the Allocation for its return value
+         */
+        public void destroy() {
+            super.destroy();
+            if (mReturnValue != null) {
+                mReturnValue.destroy();
+            }
+        }
+
+        protected void finalize() throws Throwable {
+            // Set null mReturnValue to avoid double-destroying it, in case its
+            // finalizer races ahead.
+            mReturnValue = null;
+            super.finalize();
+        }
+
         private void retrieveValueAndDependenceInfo(RenderScript rs,
                                                     int index, Script.FieldID fid, Object obj,
                                                     long[] values, int[] sizes,
@@ -1015,6 +1032,8 @@
                 throw new RSIllegalArgumentException("invalid script group name");
             }
             ScriptGroup ret = new ScriptGroup(mRS, name, mClosures, mInputs, outputs);
+            mClosures = new ArrayList<Closure>();
+            mInputs = new ArrayList<Input>();
             return ret;
         }
 
@@ -1042,4 +1061,20 @@
 
     }
 
+    /**
+     * Destroy this ScriptGroup and all Closures in it
+     */
+    public void destroy() {
+        super.destroy();
+        for(Closure c : mClosures) {
+            c.destroy();
+        }
+    }
+
+    protected void finalize() throws Throwable {
+        // Clear out the list mClosures to avoid double-destroying the closures,
+        // in case their finalizers race ahead.
+        mClosures.clear();
+        super.finalize();
+    }
 }
diff --git a/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java b/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
index 2741733..ca17c43 100644
--- a/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
+++ b/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
@@ -439,7 +439,7 @@
             }
             if (mSecurityPolicy.canDispatchAccessibilityEventLocked(event)) {
                 mSecurityPolicy.updateActiveAndAccessibilityFocusedWindowLocked(event.getWindowId(),
-                        event.getSourceNodeId(), event.getEventType());
+                        event.getSourceNodeId(), event.getEventType(), event.getAction());
                 mSecurityPolicy.updateEventSourceLocked(event);
                 notifyAccessibilityServicesDelayedLocked(event, false);
                 notifyAccessibilityServicesDelayedLocked(event, true);
@@ -1795,9 +1795,8 @@
                 }
                 userState.mSoftKeyboardShowMode = 0;
                 userState.mServiceChangingSoftKeyboardMode = null;
+                notifySoftKeyboardShowModeChangedLocked(userState.mSoftKeyboardShowMode);
             }
-
-            notifySoftKeyboardShowModeChangedLocked(userState.mSoftKeyboardShowMode);
         }
     }
 
@@ -3829,7 +3828,7 @@
         }
 
         public void updateActiveAndAccessibilityFocusedWindowLocked(int windowId, long nodeId,
-                int eventType) {
+                int eventType, int eventAction) {
             // The active window is either the window that has input focus or
             // the window that the user is currently touching. If the user is
             // touching a window that does not have input focus as soon as the
@@ -3882,8 +3881,12 @@
                         if (mAccessibilityFocusNodeId == nodeId) {
                             mAccessibilityFocusNodeId = AccessibilityNodeInfo.UNDEFINED_ITEM_ID;
                         }
-                        if (mAccessibilityFocusNodeId == AccessibilityNodeInfo.UNDEFINED_ITEM_ID
-                                && mAccessibilityFocusedWindowId == windowId) {
+                        // Clear the window with focus if it no longer has focus and we aren't
+                        // just moving focus from one view to the other in the same window
+                        if ((mAccessibilityFocusNodeId == AccessibilityNodeInfo.UNDEFINED_ITEM_ID)
+                                && (mAccessibilityFocusedWindowId == windowId)
+                                && (eventAction != AccessibilityNodeInfo.ACTION_ACCESSIBILITY_FOCUS)
+                                ) {
                             mAccessibilityFocusedWindowId = INVALID_WINDOW_ID;
                         }
                     }
@@ -4355,6 +4358,7 @@
                     }
                 } else if (mAccessibilitySoftKeyboardModeUri.equals(uri)) {
                     if (readSoftKeyboardShowModeChangedLocked(userState)) {
+                        notifySoftKeyboardShowModeChangedLocked(userState.mSoftKeyboardShowMode);
                         onUserStateChangedLocked(userState);
                     }
                 }
diff --git a/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java b/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
index f93fb1b..6ca3af8 100644
--- a/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
+++ b/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
@@ -460,12 +460,9 @@
         }
         synchronized (mLock) {
             reloadWidgetsMaskedState(userId);
-            List<UserInfo> profiles = mUserManager.getEnabledProfiles(userId);
-            if (profiles != null) {
-                for (int i = 0; i < profiles.size(); i++) {
-                    UserInfo user  = profiles.get(i);
-                    reloadWidgetsMaskedState(user.id);
-                }
+            int[] profileIds = mUserManager.getEnabledProfileIds(userId);
+            for (int profileId : profileIds) {
+                reloadWidgetsMaskedState(profileId);
             }
         }
     }
@@ -3458,33 +3455,12 @@
         public int[] getEnabledGroupProfileIds(int userId) {
             final int parentId = getGroupParent(userId);
 
-            final List<UserInfo> profiles;
             final long identity = Binder.clearCallingIdentity();
             try {
-                profiles = mUserManager.getProfiles(parentId);
+                return mUserManager.getEnabledProfileIds(parentId);
             } finally {
                 Binder.restoreCallingIdentity(identity);
             }
-
-            int enabledProfileCount = 0;
-            final int profileCount = profiles.size();
-            for (int i = 0; i < profileCount; i++) {
-                if (profiles.get(i).isEnabled()) {
-                    enabledProfileCount++;
-                }
-            }
-
-            int enabledProfileIndex = 0;
-            final int[] profileIds = new int[enabledProfileCount];
-            for (int i = 0; i < profileCount; i++) {
-                UserInfo profile = profiles.get(i);
-                if (profile.isEnabled()) {
-                    profileIds[enabledProfileIndex] = profile.getUserHandle().getIdentifier();
-                    enabledProfileIndex++;
-                }
-            }
-
-            return profileIds;
         }
 
         public void enforceServiceExistsAndRequiresBindRemoteViewsPermission(
diff --git a/services/core/java/com/android/server/BatteryService.java b/services/core/java/com/android/server/BatteryService.java
index 48e96aa..8753992 100644
--- a/services/core/java/com/android/server/BatteryService.java
+++ b/services/core/java/com/android/server/BatteryService.java
@@ -124,6 +124,7 @@
     private boolean mLastBatteryLevelCritical;
     private int mLastMaxChargingCurrent;
     private int mLastMaxChargingVoltage;
+    private int mLastChargeCounter;
 
     private int mInvalidCharger;
     private int mLastInvalidCharger;
@@ -341,6 +342,7 @@
                     + ", chargerWirelessOnline=" + mBatteryProps.chargerWirelessOnline
                     + ", maxChargingCurrent" + mBatteryProps.maxChargingCurrent
                     + ", maxChargingVoltage" + mBatteryProps.maxChargingVoltage
+                    + ", chargeCounter" + mBatteryProps.batteryChargeCounter
                     + ", batteryStatus=" + mBatteryProps.batteryStatus
                     + ", batteryHealth=" + mBatteryProps.batteryHealth
                     + ", batteryPresent=" + mBatteryProps.batteryPresent
@@ -373,6 +375,7 @@
                 mBatteryProps.batteryTemperature != mLastBatteryTemperature ||
                 mBatteryProps.maxChargingCurrent != mLastMaxChargingCurrent ||
                 mBatteryProps.maxChargingVoltage != mLastMaxChargingVoltage ||
+                mBatteryProps.batteryChargeCounter != mLastChargeCounter ||
                 mInvalidCharger != mLastInvalidCharger)) {
 
             if (mPlugType != mLastPlugType) {
@@ -501,6 +504,7 @@
             mLastBatteryTemperature = mBatteryProps.batteryTemperature;
             mLastMaxChargingCurrent = mBatteryProps.maxChargingCurrent;
             mLastMaxChargingVoltage = mBatteryProps.maxChargingVoltage;
+            mLastChargeCounter = mBatteryProps.batteryChargeCounter;
             mLastBatteryLevelCritical = mBatteryLevelCritical;
             mLastInvalidCharger = mInvalidCharger;
         }
@@ -527,6 +531,7 @@
         intent.putExtra(BatteryManager.EXTRA_INVALID_CHARGER, mInvalidCharger);
         intent.putExtra(BatteryManager.EXTRA_MAX_CHARGING_CURRENT, mBatteryProps.maxChargingCurrent);
         intent.putExtra(BatteryManager.EXTRA_MAX_CHARGING_VOLTAGE, mBatteryProps.maxChargingVoltage);
+        intent.putExtra(BatteryManager.EXTRA_CHARGE_COUNTER, mBatteryProps.batteryChargeCounter);
         if (DEBUG) {
             Slog.d(TAG, "Sending ACTION_BATTERY_CHANGED.  level:" + mBatteryProps.batteryLevel +
                     ", scale:" + BATTERY_SCALE + ", status:" + mBatteryProps.batteryStatus +
@@ -540,7 +545,8 @@
                     ", Wireless powered:" + mBatteryProps.chargerWirelessOnline +
                     ", icon:" + icon  + ", invalid charger:" + mInvalidCharger +
                     ", maxChargingCurrent:" + mBatteryProps.maxChargingCurrent +
-                    ", maxChargingVoltage:" + mBatteryProps.maxChargingVoltage);
+                    ", maxChargingVoltage:" + mBatteryProps.maxChargingVoltage +
+                    ", chargeCounter:" + mBatteryProps.batteryChargeCounter);
         }
 
         mHandler.post(new Runnable() {
@@ -772,6 +778,7 @@
                 pw.println("  Wireless powered: " + mBatteryProps.chargerWirelessOnline);
                 pw.println("  Max charging current: " + mBatteryProps.maxChargingCurrent);
                 pw.println("  Max charging voltage: " + mBatteryProps.maxChargingVoltage);
+                pw.println("  Charge counter: " + mBatteryProps.batteryChargeCounter);
                 pw.println("  status: " + mBatteryProps.batteryStatus);
                 pw.println("  health: " + mBatteryProps.batteryHealth);
                 pw.println("  present: " + mBatteryProps.batteryPresent);
diff --git a/services/core/java/com/android/server/ConnectivityService.java b/services/core/java/com/android/server/ConnectivityService.java
index 966deb6..428e192 100644
--- a/services/core/java/com/android/server/ConnectivityService.java
+++ b/services/core/java/com/android/server/ConnectivityService.java
@@ -116,6 +116,7 @@
 import com.android.internal.net.VpnProfile;
 import com.android.internal.util.AsyncChannel;
 import com.android.internal.util.IndentingPrintWriter;
+import com.android.internal.util.MessageUtils;
 import com.android.internal.util.XmlUtils;
 import com.android.server.am.BatteryStatsService;
 import com.android.server.connectivity.DataConnectionStats;
@@ -164,7 +165,7 @@
         implements PendingIntent.OnFinished {
     private static final String TAG = "ConnectivityService";
 
-    private static final boolean DBG = false;
+    private static final boolean DBG = true;
     private static final boolean VDBG = false;
 
     private static final boolean LOGD_RULES = false;
@@ -224,6 +225,9 @@
     private static final int ENABLED  = 1;
     private static final int DISABLED = 0;
 
+    private static final SparseArray<String> sMagicDecoderRing = MessageUtils.findMessageNames(
+            new Class[] { AsyncChannel.class, ConnectivityService.class, NetworkAgent.class });
+
     private enum ReapUnvalidatedNetworks {
         // Tear down networks that have no chance (e.g. even if validated) of becoming
         // the highest scoring network satisfying a NetworkRequest.  This should be passed when
@@ -446,9 +450,8 @@
      */
     private class LegacyTypeTracker {
 
-        private static final boolean DBG = false;
+        private static final boolean DBG = true;
         private static final boolean VDBG = false;
-        private static final String TAG = "CSLegacyTypeTracker";
 
         /**
          * Array of lists, one per legacy network type (e.g., TYPE_MOBILE_MMS).
@@ -601,12 +604,6 @@
             pw.decreaseIndent();
             pw.println();
         }
-
-        // This class needs its own log method because it has a different TAG.
-        private void log(String s) {
-            Slog.d(TAG, s);
-        }
-
     }
     private LegacyTypeTracker mLegacyTypeTracker = new LegacyTypeTracker();
 
@@ -1528,7 +1525,7 @@
                 mInitialBroadcast = new Intent(intent);
             }
             intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
-            if (DBG) {
+            if (VDBG) {
                 log("sendStickyBroadcast: action=" + intent.getAction());
             }
 
@@ -1656,7 +1653,7 @@
         }
 
         if (LinkProperties.isValidMtu(mtu, newLp.hasGlobalIPv6Address()) == false) {
-            loge("Unexpected mtu value: " + mtu + ", " + iface);
+            if (mtu != 0) loge("Unexpected mtu value: " + mtu + ", " + iface);
             return;
         }
 
@@ -1667,7 +1664,7 @@
         }
 
         try {
-            if (DBG) log("Setting MTU size: " + iface + ", " + mtu);
+            if (VDBG) log("Setting MTU size: " + iface + ", " + mtu);
             mNetd.setMtu(iface, mtu);
         } catch (Exception e) {
             Slog.e(TAG, "exception in setMtu()" + e);
@@ -1703,7 +1700,7 @@
         if (tcpBufferSizes.equals(mCurrentTcpBufferSizes)) return;
 
         try {
-            if (DBG) Slog.d(TAG, "Setting tx/rx TCP buffers to " + tcpBufferSizes);
+            if (VDBG) Slog.d(TAG, "Setting tx/rx TCP buffers to " + tcpBufferSizes);
 
             final String prefix = "/sys/kernel/ipv4/tcp_";
             FileUtils.stringToFile(prefix + "rmem_min", values[0]);
@@ -1900,11 +1897,12 @@
         }
     }
 
-    private boolean isLiveNetworkAgent(NetworkAgentInfo nai, String msg) {
+    private boolean isLiveNetworkAgent(NetworkAgentInfo nai, int what) {
         if (nai.network == null) return false;
         final NetworkAgentInfo officialNai = getNetworkAgentInfoForNetwork(nai.network);
         if (officialNai != null && officialNai.equals(nai)) return true;
         if (officialNai != null || VDBG) {
+            final String msg = sMagicDecoderRing.get(what, Integer.toString(what));
             loge(msg + " - isLiveNetworkAgent found mismatched netId: " + officialNai +
                 " - " + nai);
         }
@@ -1921,10 +1919,10 @@
             super(looper);
         }
 
-        @Override
-        public void handleMessage(Message msg) {
-            NetworkInfo info;
+        private boolean maybeHandleAsyncChannelMessage(Message msg) {
             switch (msg.what) {
+                default:
+                    return false;
                 case AsyncChannel.CMD_CHANNEL_HALF_CONNECTED: {
                     handleAsyncChannelHalfConnect(msg);
                     break;
@@ -1938,69 +1936,58 @@
                     handleAsyncChannelDisconnected(msg);
                     break;
                 }
+            }
+            return true;
+        }
+
+        private void maybeHandleNetworkAgentMessage(Message msg) {
+            NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
+            if (nai == null) {
+                if (VDBG) {
+                    final String what = sMagicDecoderRing.get(msg.what, Integer.toString(msg.what));
+                    log(String.format("%s from unknown NetworkAgent", what));
+                }
+                return;
+            }
+
+            switch (msg.what) {
                 case NetworkAgent.EVENT_NETWORK_CAPABILITIES_CHANGED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_NETWORK_CAPABILITIES_CHANGED from unknown NetworkAgent");
-                    } else {
-                        final NetworkCapabilities networkCapabilities =
-                                (NetworkCapabilities)msg.obj;
-                        if (networkCapabilities.hasCapability(NET_CAPABILITY_CAPTIVE_PORTAL) ||
-                                networkCapabilities.hasCapability(NET_CAPABILITY_VALIDATED)) {
-                            Slog.wtf(TAG, "BUG: " + nai + " has CS-managed capability.");
-                        }
-                        if (nai.created && !nai.networkCapabilities.equalImmutableCapabilities(
-                                networkCapabilities)) {
-                            Slog.wtf(TAG, "BUG: " + nai + " changed immutable capabilities: "
-                                    + nai.networkCapabilities + " -> " + networkCapabilities);
-                        }
-                        updateCapabilities(nai, networkCapabilities);
+                    final NetworkCapabilities networkCapabilities = (NetworkCapabilities) msg.obj;
+                    if (networkCapabilities.hasCapability(NET_CAPABILITY_CAPTIVE_PORTAL) ||
+                            networkCapabilities.hasCapability(NET_CAPABILITY_VALIDATED)) {
+                        Slog.wtf(TAG, "BUG: " + nai + " has CS-managed capability.");
                     }
+                    if (nai.created && !nai.networkCapabilities.equalImmutableCapabilities(
+                            networkCapabilities)) {
+                        Slog.wtf(TAG, "BUG: " + nai + " changed immutable capabilities: "
+                                + nai.networkCapabilities + " -> " + networkCapabilities);
+                    }
+                    updateCapabilities(nai, networkCapabilities);
                     break;
                 }
                 case NetworkAgent.EVENT_NETWORK_PROPERTIES_CHANGED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("NetworkAgent not found for EVENT_NETWORK_PROPERTIES_CHANGED");
-                    } else {
-                        if (VDBG) {
-                            log("Update of LinkProperties for " + nai.name() +
-                                    "; created=" + nai.created);
-                        }
-                        LinkProperties oldLp = nai.linkProperties;
-                        synchronized (nai) {
-                            nai.linkProperties = (LinkProperties)msg.obj;
-                        }
-                        if (nai.created) updateLinkProperties(nai, oldLp);
+                    if (VDBG) {
+                        log("Update of LinkProperties for " + nai.name() +
+                                "; created=" + nai.created);
                     }
+                    LinkProperties oldLp = nai.linkProperties;
+                    synchronized (nai) {
+                        nai.linkProperties = (LinkProperties)msg.obj;
+                    }
+                    if (nai.created) updateLinkProperties(nai, oldLp);
                     break;
                 }
                 case NetworkAgent.EVENT_NETWORK_INFO_CHANGED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_NETWORK_INFO_CHANGED from unknown NetworkAgent");
-                        break;
-                    }
-                    info = (NetworkInfo) msg.obj;
+                    NetworkInfo info = (NetworkInfo) msg.obj;
                     updateNetworkInfo(nai, info);
                     break;
                 }
                 case NetworkAgent.EVENT_NETWORK_SCORE_CHANGED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_NETWORK_SCORE_CHANGED from unknown NetworkAgent");
-                        break;
-                    }
                     Integer score = (Integer) msg.obj;
                     if (score != null) updateNetworkScore(nai, score.intValue());
                     break;
                 }
                 case NetworkAgent.EVENT_UID_RANGES_ADDED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_UID_RANGES_ADDED from unknown NetworkAgent");
-                        break;
-                    }
                     try {
                         mNetd.addVpnUidRanges(nai.network.netId, (UidRange[])msg.obj);
                     } catch (Exception e) {
@@ -2010,11 +1997,6 @@
                     break;
                 }
                 case NetworkAgent.EVENT_UID_RANGES_REMOVED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_UID_RANGES_REMOVED from unknown NetworkAgent");
-                        break;
-                    }
                     try {
                         mNetd.removeVpnUidRanges(nai.network.netId, (UidRange[])msg.obj);
                     } catch (Exception e) {
@@ -2024,11 +2006,6 @@
                     break;
                 }
                 case NetworkAgent.EVENT_SET_EXPLICITLY_SELECTED: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_SET_EXPLICITLY_SELECTED from unknown NetworkAgent");
-                        break;
-                    }
                     if (nai.created && !nai.networkMisc.explicitlySelected) {
                         loge("ERROR: created network explicitly selected.");
                     }
@@ -2037,17 +2014,19 @@
                     break;
                 }
                 case NetworkAgent.EVENT_PACKET_KEEPALIVE: {
-                    NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
-                    if (nai == null) {
-                        loge("EVENT_PACKET_KEEPALIVE from unknown NetworkAgent");
-                        break;
-                    }
                     mKeepaliveTracker.handleEventPacketKeepalive(nai, msg);
                     break;
                 }
+            }
+        }
+
+        private boolean maybeHandleNetworkMonitorMessage(Message msg) {
+            switch (msg.what) {
+                default:
+                    return false;
                 case NetworkMonitor.EVENT_NETWORK_TESTED: {
                     NetworkAgentInfo nai = (NetworkAgentInfo)msg.obj;
-                    if (isLiveNetworkAgent(nai, "EVENT_NETWORK_TESTED")) {
+                    if (isLiveNetworkAgent(nai, msg.what)) {
                         final boolean valid =
                                 (msg.arg1 == NetworkMonitor.NETWORK_TEST_RESULT_VALID);
                         if (DBG) log(nai.name() + " validation " + (valid ? " passed" : "failed"));
@@ -2070,7 +2049,7 @@
                 }
                 case NetworkMonitor.EVENT_NETWORK_LINGER_COMPLETE: {
                     NetworkAgentInfo nai = (NetworkAgentInfo)msg.obj;
-                    if (isLiveNetworkAgent(nai, "EVENT_NETWORK_LINGER_COMPLETE")) {
+                    if (isLiveNetworkAgent(nai, msg.what)) {
                         handleLingerComplete(nai);
                     }
                     break;
@@ -2102,6 +2081,14 @@
                     break;
                 }
             }
+            return true;
+        }
+
+        @Override
+        public void handleMessage(Message msg) {
+            if (!maybeHandleAsyncChannelMessage(msg) && !maybeHandleNetworkMonitorMessage(msg)) {
+                maybeHandleNetworkAgentMessage(msg);
+            }
         }
     }
 
@@ -2321,7 +2308,7 @@
                 if (DBG) log("Attempt to release unowned NetworkRequest " + request);
                 return;
             }
-            if (DBG) log("releasing NetworkRequest " + request);
+            if (VDBG || (DBG && nri.isRequest())) log("releasing NetworkRequest " + request);
             nri.unlinkDeathRecipient();
             mNetworkRequests.remove(request);
             mNetworkRequestInfoLogs.log("RELEASE " + nri);
@@ -2334,7 +2321,7 @@
                 for (NetworkAgentInfo nai : mNetworkAgentInfos.values()) {
                     if (nai.networkRequests.get(nri.request.requestId) != null) {
                         nai.networkRequests.remove(nri.request.requestId);
-                        if (DBG) {
+                        if (VDBG) {
                             log(" Removing from current network " + nai.name() +
                                     ", leaving " + nai.networkRequests.size() +
                                     " requests.");
@@ -2445,14 +2432,14 @@
     }
 
     private void scheduleUnvalidatedPrompt(NetworkAgentInfo nai) {
-        if (DBG) log("scheduleUnvalidatedPrompt " + nai.network);
+        if (VDBG) log("scheduleUnvalidatedPrompt " + nai.network);
         mHandler.sendMessageDelayed(
                 mHandler.obtainMessage(EVENT_PROMPT_UNVALIDATED, nai.network),
                 PROMPT_UNVALIDATED_DELAY_MS);
     }
 
     private void handlePromptUnvalidated(Network network) {
-        if (DBG) log("handlePromptUnvalidated " + network);
+        if (VDBG) log("handlePromptUnvalidated " + network);
         NetworkAgentInfo nai = getNetworkAgentInfoForNetwork(network);
 
         // Only prompt if the network is unvalidated and was explicitly selected by the user, and if
@@ -2495,11 +2482,14 @@
                             break;
                         }
                     }
-                    if (msg.what == EVENT_EXPIRE_NET_TRANSITION_WAKELOCK) {
-                        log("Failed to find a new network - expiring NetTransition Wakelock");
-                    } else {
-                        log("NetTransition Wakelock (" + (causedBy == null ? "unknown" : causedBy) +
-                                " cleared because we found a replacement network");
+                    if (VDBG) {
+                        if (msg.what == EVENT_EXPIRE_NET_TRANSITION_WAKELOCK) {
+                            log("Failed to find a new network - expiring NetTransition Wakelock");
+                        } else {
+                            log("NetTransition Wakelock (" +
+                                    (causedBy == null ? "unknown" : causedBy) +
+                                    " cleared because we found a replacement network");
+                        }
                     }
                     break;
                 }
@@ -3353,10 +3343,6 @@
     private static enum NotificationType { SIGN_IN, NO_INTERNET; };
 
     private void setProvNotificationVisible(boolean visible, int networkType, String action) {
-        if (DBG) {
-            log("setProvNotificationVisible: E visible=" + visible + " networkType=" + networkType
-                + " action=" + action);
-        }
         Intent intent = new Intent(action);
         PendingIntent pendingIntent = PendingIntent.getBroadcast(mContext, 0, intent, 0);
         // Concatenate the range of types onto the range of NetIDs.
@@ -3383,7 +3369,7 @@
     private void setProvNotificationVisibleIntent(boolean visible, int id,
             NotificationType notifyType, int networkType, String extraInfo, PendingIntent intent,
             boolean highPriority) {
-        if (DBG) {
+        if (VDBG || (DBG && visible)) {
             log("setProvNotificationVisibleIntent " + notifyType + " visible=" + visible
                     + " networkType=" + getNetworkTypeName(networkType)
                     + " extraInfo=" + extraInfo + " highPriority=" + highPriority);
@@ -3826,8 +3812,7 @@
         Bundle thresholds = new Bundle();
         thresholds.putIntegerArrayList("thresholds", thresholdsArray);
 
-        // TODO: Switch to VDBG.
-        if (DBG) {
+        if (VDBG || (DBG && !"CONNECT".equals(reason))) {
             String detail;
             if (request != null && request.networkCapabilities.hasSignalStrength()) {
                 detail = reason + " " + request.networkCapabilities.getSignalStrength();
@@ -3992,7 +3977,7 @@
                 new NetworkCapabilities(networkCapabilities), TYPE_NONE, nextNetworkRequestId());
         NetworkRequestInfo nri = new NetworkRequestInfo(messenger, networkRequest, binder,
                 NetworkRequestType.LISTEN);
-        if (DBG) log("listenForNetwork for " + nri);
+        if (VDBG) log("listenForNetwork for " + nri);
 
         mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_LISTENER, nri));
         return networkRequest;
@@ -4010,7 +3995,7 @@
                 new NetworkCapabilities(networkCapabilities), TYPE_NONE, nextNetworkRequestId());
         NetworkRequestInfo nri = new NetworkRequestInfo(networkRequest, operation,
                 NetworkRequestType.LISTEN);
-        if (DBG) log("pendingListenForNetwork for " + nri);
+        if (VDBG) log("pendingListenForNetwork for " + nri);
 
         mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_LISTENER, nri));
     }
@@ -4215,7 +4200,7 @@
         // do this twice, adding non-nexthop routes first, then routes they are dependent on
         for (RouteInfo route : routeDiff.added) {
             if (route.hasGateway()) continue;
-            if (DBG) log("Adding Route [" + route + "] to network " + netId);
+            if (VDBG) log("Adding Route [" + route + "] to network " + netId);
             try {
                 mNetd.addRoute(netId, route);
             } catch (Exception e) {
@@ -4226,7 +4211,7 @@
         }
         for (RouteInfo route : routeDiff.added) {
             if (route.hasGateway() == false) continue;
-            if (DBG) log("Adding Route [" + route + "] to network " + netId);
+            if (VDBG) log("Adding Route [" + route + "] to network " + netId);
             try {
                 mNetd.addRoute(netId, route);
             } catch (Exception e) {
@@ -4237,7 +4222,7 @@
         }
 
         for (RouteInfo route : routeDiff.removed) {
-            if (DBG) log("Removing Route [" + route + "] from network " + netId);
+            if (VDBG) log("Removing Route [" + route + "] from network " + netId);
             try {
                 mNetd.removeRoute(netId, route);
             } catch (Exception e) {
@@ -4253,7 +4238,7 @@
         }
 
         Collection<InetAddress> dnses = newLp.getDnsServers();
-        if (DBG) log("Setting Dns servers for network " + netId + " to " + dnses);
+        if (DBG) log("Setting DNS servers for network " + netId + " to " + dnses);
         try {
             mNetd.setDnsServersForNetwork(
                     netId, NetworkUtils.makeStrings(dnses), newLp.getDomains());
@@ -4521,14 +4506,14 @@
                 }
                 if (currentNetwork == null ||
                         currentNetwork.getCurrentScore() < newNetwork.getCurrentScore()) {
-                    if (DBG) log("rematch for " + newNetwork.name());
+                    if (VDBG) log("rematch for " + newNetwork.name());
                     if (currentNetwork != null) {
-                        if (DBG) log("   accepting network in place of " + currentNetwork.name());
+                        if (VDBG) log("   accepting network in place of " + currentNetwork.name());
                         currentNetwork.networkRequests.remove(nri.request.requestId);
                         currentNetwork.networkLingered.add(nri.request);
                         affectedNetworks.add(currentNetwork);
                     } else {
-                        if (DBG) log("   accepting network in place of null");
+                        if (VDBG) log("   accepting network in place of null");
                     }
                     unlinger(newNetwork);
                     mNetworkForRequestId.put(nri.request.requestId, newNetwork);
@@ -4858,7 +4843,7 @@
     }
 
     private void updateNetworkScore(NetworkAgentInfo nai, int score) {
-        if (DBG) log("updateNetworkScore for " + nai.name() + " to " + score);
+        if (VDBG) log("updateNetworkScore for " + nai.name() + " to " + score);
         if (score < 0) {
             loge("updateNetworkScore for " + nai.name() + " got a negative score (" + score +
                     ").  Bumping score to min of 0");
@@ -4936,7 +4921,7 @@
     }
 
     protected void notifyNetworkCallbacks(NetworkAgentInfo networkAgent, int notifyType) {
-        if (DBG) log("notifyType " + notifyTypeToName(notifyType) + " for " + networkAgent.name());
+        if (VDBG) log("notifyType " + notifyTypeToName(notifyType) + " for " + networkAgent.name());
         for (int i = 0; i < networkAgent.networkRequests.size(); i++) {
             NetworkRequest nr = networkAgent.networkRequests.valueAt(i);
             NetworkRequestInfo nri = mNetworkRequests.get(nr);
diff --git a/services/core/java/com/android/server/DeviceIdleController.java b/services/core/java/com/android/server/DeviceIdleController.java
index ccb4647..6a08191 100644
--- a/services/core/java/com/android/server/DeviceIdleController.java
+++ b/services/core/java/com/android/server/DeviceIdleController.java
@@ -39,7 +39,9 @@
 import android.location.Location;
 import android.location.LocationListener;
 import android.location.LocationManager;
+import android.net.ConnectivityManager;
 import android.net.INetworkPolicyManager;
+import android.net.NetworkInfo;
 import android.net.Uri;
 import android.os.BatteryStats;
 import android.os.Binder;
@@ -114,6 +116,7 @@
     private IBatteryStats mBatteryStats;
     private PowerManagerInternal mLocalPowerManager;
     private PowerManager mPowerManager;
+    private ConnectivityService mConnectivityService;
     private AlarmManagerService.LocalService mLocalAlarmManager;
     private INetworkPolicyManager mNetworkPolicyManager;
     private DisplayManager mDisplayManager;
@@ -128,6 +131,7 @@
     private boolean mLightEnabled;
     private boolean mDeepEnabled;
     private boolean mForceIdle;
+    private boolean mNetworkConnected;
     private boolean mScreenOn;
     private boolean mCharging;
     private boolean mNotMoving;
@@ -173,16 +177,20 @@
     private static final int LIGHT_STATE_PRE_IDLE = 3;
     /** Device is in the light idle state, trying to stay asleep as much as possible. */
     private static final int LIGHT_STATE_IDLE = 4;
+    /** Device is in the light idle state, we want to go in to idle maintenance but are
+     * waiting for network connectivity before doing so. */
+    private static final int LIGHT_STATE_WAITING_FOR_NETWORK = 5;
     /** Device is in the light idle state, but temporarily out of idle to do regular maintenance. */
-    private static final int LIGHT_STATE_IDLE_MAINTENANCE = 5;
+    private static final int LIGHT_STATE_IDLE_MAINTENANCE = 6;
     /** Device light idle state is overriden, now applying deep doze state. */
-    private static final int LIGHT_STATE_OVERRIDE = 6;
+    private static final int LIGHT_STATE_OVERRIDE = 7;
     private static String lightStateToString(int state) {
         switch (state) {
             case LIGHT_STATE_ACTIVE: return "ACTIVE";
             case LIGHT_STATE_INACTIVE: return "INACTIVE";
             case LIGHT_STATE_PRE_IDLE: return "PRE_IDLE";
             case LIGHT_STATE_IDLE: return "IDLE";
+            case LIGHT_STATE_WAITING_FOR_NETWORK: return "WAITING_FOR_NETWORK";
             case LIGHT_STATE_IDLE_MAINTENANCE: return "IDLE_MAINTENANCE";
             case LIGHT_STATE_OVERRIDE: return "OVERRIDE";
             default: return Integer.toString(state);
@@ -315,17 +323,27 @@
 
     private final BroadcastReceiver mReceiver = new BroadcastReceiver() {
         @Override public void onReceive(Context context, Intent intent) {
-            if (Intent.ACTION_BATTERY_CHANGED.equals(intent.getAction())) {
-                int plugged = intent.getIntExtra("plugged", 0);
-                updateChargingLocked(plugged != 0);
-            } else if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction())) {
-                if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) {
-                    Uri data = intent.getData();
-                    String ssp;
-                    if (data != null && (ssp = data.getSchemeSpecificPart()) != null) {
-                        removePowerSaveWhitelistAppInternal(ssp);
+            switch (intent.getAction()) {
+                case ConnectivityManager.CONNECTIVITY_ACTION: {
+                    synchronized (DeviceIdleController.this) {
+                        updateConnectivityStateLocked(intent);
                     }
-                }
+                } break;
+                case Intent.ACTION_BATTERY_CHANGED: {
+                    synchronized (DeviceIdleController.this) {
+                        int plugged = intent.getIntExtra("plugged", 0);
+                        updateChargingLocked(plugged != 0);
+                    }
+                } break;
+                case Intent.ACTION_PACKAGE_REMOVED: {
+                    if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) {
+                        Uri data = intent.getData();
+                        String ssp;
+                        if (data != null && (ssp = data.getSchemeSpecificPart()) != null) {
+                            removePowerSaveWhitelistAppInternal(ssp);
+                        }
+                    }
+                } break;
             }
         }
     };
@@ -1318,6 +1336,7 @@
             readConfigFileLocked();
             updateWhitelistAppIdsLocked();
 
+            mNetworkConnected = true;
             mScreenOn = true;
             // Start out assuming we are charging.  If we aren't, we will at least get
             // a battery update the next time the level drops.
@@ -1343,6 +1362,8 @@
                 mActiveIdleWakeLock = mPowerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
                         "deviceidle_maint");
                 mActiveIdleWakeLock.setReferenceCounted(false);
+                mConnectivityService = (ConnectivityService)ServiceManager.getService(
+                        Context.CONNECTIVITY_SERVICE);
                 mLocalAlarmManager = getLocalService(AlarmManagerService.LocalService.class);
                 mNetworkPolicyManager = INetworkPolicyManager.Stub.asInterface(
                         ServiceManager.getService(Context.NETWORK_POLICY_SERVICE));
@@ -1395,11 +1416,14 @@
                 filter = new IntentFilter();
                 filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
                 filter.addDataScheme("package");
+                filter = new IntentFilter();
+                filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
                 getContext().registerReceiver(mReceiver, filter);
 
                 mLocalPowerManager.setDeviceIdleWhitelist(mPowerSaveWhitelistAllAppIdArray);
                 mLocalAlarmManager.setDeviceIdleUserWhitelist(mPowerSaveWhitelistUserAppIdArray);
                 mDisplayManager.registerDisplayListener(mDisplayListener, null);
+                updateConnectivityStateLocked(null);
                 updateDisplayLocked();
             }
         }
@@ -1680,6 +1704,35 @@
         }
     }
 
+    void updateConnectivityStateLocked(Intent connIntent) {
+        if (mConnectivityService != null) {
+            NetworkInfo ni = mConnectivityService.getActiveNetworkInfo();
+            boolean conn;
+            if (ni == null) {
+                conn = false;
+            } else {
+                if (connIntent == null) {
+                    conn = ni.isConnected();
+                } else {
+                    final int networkType =
+                            connIntent.getIntExtra(ConnectivityManager.EXTRA_NETWORK_TYPE,
+                                    ConnectivityManager.TYPE_NONE);
+                    if (ni.getType() != networkType) {
+                        return;
+                    }
+                    conn = !connIntent.getBooleanExtra(ConnectivityManager.EXTRA_NO_CONNECTIVITY,
+                            false);
+                }
+            }
+            if (conn != mNetworkConnected) {
+                mNetworkConnected = conn;
+                if (conn && mLightState == LIGHT_STATE_WAITING_FOR_NETWORK) {
+                    stepLightIdleStateLocked("network");
+                }
+            }
+        }
+    }
+
     void updateDisplayLocked() {
         mCurDisplay = mDisplayManager.getDisplay(Display.DEFAULT_DISPLAY);
         // We consider any situation where the display is showing something to be it on,
@@ -1778,7 +1831,7 @@
         if (mForceIdle) {
             mForceIdle = false;
             if (mScreenOn || mCharging) {
-                becomeActiveLocked("exit-force-idle", Process.myUid());
+                becomeActiveLocked("exit-force", Process.myUid());
             }
         }
     }
@@ -1834,22 +1887,33 @@
                 mHandler.sendEmptyMessage(MSG_REPORT_IDLE_ON_LIGHT);
                 break;
             case LIGHT_STATE_IDLE:
-                // We have been idling long enough, now it is time to do some work.
-                mActiveIdleOpCount = 1;
-                mActiveIdleWakeLock.acquire();
-                mMaintenanceStartTime = SystemClock.elapsedRealtime();
-                if (mCurIdleBudget < mConstants.LIGHT_IDLE_MAINTENANCE_MIN_BUDGET) {
-                    mCurIdleBudget = mConstants.LIGHT_IDLE_MAINTENANCE_MIN_BUDGET;
-                } else if (mCurIdleBudget > mConstants.LIGHT_IDLE_MAINTENANCE_MAX_BUDGET) {
-                    mCurIdleBudget = mConstants.LIGHT_IDLE_MAINTENANCE_MAX_BUDGET;
+            case LIGHT_STATE_WAITING_FOR_NETWORK:
+                if (mNetworkConnected || mLightState == LIGHT_STATE_WAITING_FOR_NETWORK) {
+                    // We have been idling long enough, now it is time to do some work.
+                    mActiveIdleOpCount = 1;
+                    mActiveIdleWakeLock.acquire();
+                    mMaintenanceStartTime = SystemClock.elapsedRealtime();
+                    if (mCurIdleBudget < mConstants.LIGHT_IDLE_MAINTENANCE_MIN_BUDGET) {
+                        mCurIdleBudget = mConstants.LIGHT_IDLE_MAINTENANCE_MIN_BUDGET;
+                    } else if (mCurIdleBudget > mConstants.LIGHT_IDLE_MAINTENANCE_MAX_BUDGET) {
+                        mCurIdleBudget = mConstants.LIGHT_IDLE_MAINTENANCE_MAX_BUDGET;
+                    }
+                    scheduleLightAlarmLocked(mCurIdleBudget);
+                    if (DEBUG) Slog.d(TAG,
+                            "Moved from LIGHT_STATE_IDLE to LIGHT_STATE_IDLE_MAINTENANCE.");
+                    mLightState = LIGHT_STATE_IDLE_MAINTENANCE;
+                    EventLogTags.writeDeviceIdleLight(mLightState, reason);
+                    addEvent(EVENT_LIGHT_MAINTENANCE);
+                    mHandler.sendEmptyMessage(MSG_REPORT_IDLE_OFF);
+                } else {
+                    // We'd like to do maintenance, but currently don't have network
+                    // connectivity...  let's try to wait until the network comes back.
+                    // We'll only wait for another full idle period, however, and then give up.
+                    scheduleLightAlarmLocked(mNextLightIdleDelay);
+                    if (DEBUG) Slog.d(TAG, "Moved to LIGHT_WAITING_FOR_NETWORK.");
+                    mLightState = LIGHT_STATE_WAITING_FOR_NETWORK;
+                    EventLogTags.writeDeviceIdleLight(mLightState, reason);
                 }
-                scheduleLightAlarmLocked(mCurIdleBudget);
-                if (DEBUG) Slog.d(TAG,
-                        "Moved from LIGHT_STATE_IDLE to LIGHT_STATE_IDLE_MAINTENANCE.");
-                mLightState = LIGHT_STATE_IDLE_MAINTENANCE;
-                EventLogTags.writeDeviceIdleLight(mLightState, reason);
-                addEvent(EVENT_LIGHT_MAINTENANCE);
-                mHandler.sendEmptyMessage(MSG_REPORT_IDLE_OFF);
                 break;
         }
     }
@@ -2209,13 +2273,6 @@
 
     void scheduleLightAlarmLocked(long delay) {
         if (DEBUG) Slog.d(TAG, "scheduleLightAlarmLocked(" + delay + ")");
-        if (mMotionSensor == null) {
-            // If there is no motion sensor on this device, then we won't schedule
-            // alarms, because we can't determine if the device is not moving.  This effectively
-            // turns off normal execution of device idling, although it is still possible to
-            // manually poke it by pretending like the alarm is going off.
-            return;
-        }
         mNextLightAlarmTime = SystemClock.elapsedRealtime() + delay;
         mAlarmManager.set(AlarmManager.ELAPSED_REALTIME_WAKEUP,
                 mNextLightAlarmTime, "DeviceIdleController.light", mLightAlarmListener, mHandler);
@@ -2430,9 +2487,14 @@
         pw.println("    Print this help text.");
         pw.println("  step [light|deep]");
         pw.println("    Immediately step to next state, without waiting for alarm.");
-        pw.println("  force-idle");
+        pw.println("  force-idle [light|deep]");
         pw.println("    Force directly into idle mode, regardless of other device state.");
-        pw.println("    Use \"step\" to get out.");
+        pw.println("  force-inactive");
+        pw.println("    Force to be inactive, ready to freely step idle states.");
+        pw.println("  unforce");
+        pw.println("    Resume normal functioning after force-idle or force-inactive.");
+        pw.println("  get [light|deep|force|screen|charging|network]");
+        pw.println("    Retrieve the current given state.");
         pw.println("  disable [light|deep|all]");
         pw.println("    Completely disable device idle mode.");
         pw.println("  enable [light|deep|all]");
@@ -2472,12 +2534,10 @@
                 String arg = shell.getNextArg();
                 try {
                     if (arg == null || "deep".equals(arg)) {
-                        exitForceIdleLocked();
                         stepIdleStateLocked("s:shell");
                         pw.print("Stepped to deep: ");
                         pw.println(stateToString(mState));
                     } else if ("light".equals(arg)) {
-                        exitForceIdleLocked();
                         stepLightIdleStateLocked("s:shell");
                         pw.print("Stepped to light: "); pw.println(lightStateToString(mLightState));
                     } else {
@@ -2492,29 +2552,104 @@
                     null);
             synchronized (this) {
                 long token = Binder.clearCallingIdentity();
+                String arg = shell.getNextArg();
                 try {
-                    if (!mDeepEnabled) {
-                        pw.println("Unable to go idle; not enabled");
-                        return -1;
-                    }
-                    mForceIdle = true;
-                    becomeInactiveIfAppropriateLocked();
-                    int curState = mState;
-                    while (curState != STATE_IDLE) {
-                        stepIdleStateLocked("s:shell");
-                        if (curState == mState) {
-                            pw.print("Unable to go idle; stopped at ");
-                            pw.println(stateToString(mState));
-                            exitForceIdleLocked();
+                    if (arg == null || "deep".equals(arg)) {
+                        if (!mDeepEnabled) {
+                            pw.println("Unable to go deep idle; not enabled");
                             return -1;
                         }
-                        curState = mState;
+                        mForceIdle = true;
+                        becomeInactiveIfAppropriateLocked();
+                        int curState = mState;
+                        while (curState != STATE_IDLE) {
+                            stepIdleStateLocked("s:shell");
+                            if (curState == mState) {
+                                pw.print("Unable to go deep idle; stopped at ");
+                                pw.println(stateToString(mState));
+                                exitForceIdleLocked();
+                                return -1;
+                            }
+                            curState = mState;
+                        }
+                        pw.println("Now forced in to deep idle mode");
+                    } else if ("light".equals(arg)) {
+                        mForceIdle = true;
+                        becomeInactiveIfAppropriateLocked();
+                        int curLightState = mLightState;
+                        while (curLightState != LIGHT_STATE_IDLE) {
+                            stepIdleStateLocked("s:shell");
+                            if (curLightState == mLightState) {
+                                pw.print("Unable to go light idle; stopped at ");
+                                pw.println(lightStateToString(mLightState));
+                                exitForceIdleLocked();
+                                return -1;
+                            }
+                            curLightState = mLightState;
+                        }
+                        pw.println("Now forced in to light idle mode");
+                    } else {
+                        pw.println("Unknown idle mode: " + arg);
                     }
-                    pw.println("Now forced in to idle mode");
                 } finally {
                     Binder.restoreCallingIdentity(token);
                 }
             }
+        } else if ("force-inactive".equals(cmd)) {
+            getContext().enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER,
+                    null);
+            synchronized (this) {
+                long token = Binder.clearCallingIdentity();
+                try {
+                    mForceIdle = true;
+                    becomeInactiveIfAppropriateLocked();
+                    pw.print("Light state: ");
+                    pw.print(lightStateToString(mLightState));
+                    pw.print(", deep state: ");
+                    pw.println(stateToString(mState));
+                } finally {
+                    Binder.restoreCallingIdentity(token);
+                }
+            }
+        } else if ("unforce".equals(cmd)) {
+            getContext().enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER,
+                    null);
+            synchronized (this) {
+                long token = Binder.clearCallingIdentity();
+                try {
+                    exitForceIdleLocked();
+                    pw.print("Light state: ");
+                    pw.print(lightStateToString(mLightState));
+                    pw.print(", deep state: ");
+                    pw.println(stateToString(mState));
+                } finally {
+                    Binder.restoreCallingIdentity(token);
+                }
+            }
+        } else if ("get".equals(cmd)) {
+            getContext().enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER,
+                    null);
+            synchronized (this) {
+                String arg = shell.getNextArg();
+                if (arg != null) {
+                    long token = Binder.clearCallingIdentity();
+                    try {
+                        switch (arg) {
+                            case "light": pw.println(lightStateToString(mLightState)); break;
+                            case "deep": pw.println(stateToString(mState)); break;
+                            case "force": pw.println(mForceIdle); break;
+                            case "screen": pw.println(mScreenOn); break;
+                            case "charging": pw.println(mCharging); break;
+                            case "network": pw.println(mNetworkConnected); break;
+                            default: pw.println("Unknown get option: " + arg); break;
+                        }
+                    } finally {
+                        Binder.restoreCallingIdentity(token);
+                    }
+                } else {
+                    pw.println("Argument required");
+                }
+            }
         } else if ("disable".equals(cmd)) {
             getContext().enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER,
                     null);
@@ -2829,6 +2964,7 @@
             pw.print("  mMotionSensor="); pw.println(mMotionSensor);
             pw.print("  mCurDisplay="); pw.println(mCurDisplay);
             pw.print("  mScreenOn="); pw.println(mScreenOn);
+            pw.print("  mNetworkConnected="); pw.println(mNetworkConnected);
             pw.print("  mCharging="); pw.println(mCharging);
             pw.print("  mMotionActive="); pw.println(mMotionListener.active);
             pw.print("  mNotMoving="); pw.println(mNotMoving);
diff --git a/services/core/java/com/android/server/GestureLauncherService.java b/services/core/java/com/android/server/GestureLauncherService.java
index aa98648..5a90488 100644
--- a/services/core/java/com/android/server/GestureLauncherService.java
+++ b/services/core/java/com/android/server/GestureLauncherService.java
@@ -58,7 +58,6 @@
      * as a camera launch.
      */
     private static final long CAMERA_POWER_DOUBLE_TAP_MAX_TIME_MS = 300;
-    private static final long CAMERA_POWER_DOUBLE_TAP_MIN_TIME_MS = 120;
 
     /** The listener that receives the gesture event. */
     private final GestureEventListener mGestureListener = new GestureEventListener();
@@ -260,8 +259,7 @@
         synchronized (this) {
             doubleTapInterval = event.getEventTime() - mLastPowerDown;
             if (mCameraDoubleTapPowerEnabled
-                    && doubleTapInterval < CAMERA_POWER_DOUBLE_TAP_MAX_TIME_MS
-                    && doubleTapInterval > CAMERA_POWER_DOUBLE_TAP_MIN_TIME_MS) {
+                    && doubleTapInterval < CAMERA_POWER_DOUBLE_TAP_MAX_TIME_MS) {
                 launched = true;
                 intercept = interactive;
             }
diff --git a/services/core/java/com/android/server/InputMethodManagerService.java b/services/core/java/com/android/server/InputMethodManagerService.java
index ac7872a..544e645 100644
--- a/services/core/java/com/android/server/InputMethodManagerService.java
+++ b/services/core/java/com/android/server/InputMethodManagerService.java
@@ -66,7 +66,6 @@
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.content.pm.ServiceInfo;
-import android.content.pm.UserInfo;
 import android.content.res.Configuration;
 import android.content.res.Resources;
 import android.content.res.TypedArray;
@@ -1050,12 +1049,8 @@
     }
 
     void updateCurrentProfileIds() {
-        List<UserInfo> profiles = mUserManager.getProfiles(mSettings.getCurrentUserId());
-        int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null
-        for (int i = 0; i < currentProfileIds.length; i++) {
-            currentProfileIds[i] = profiles.get(i).id;
-        }
-        mSettings.setCurrentProfileIds(currentProfileIds);
+        mSettings.setCurrentProfileIds(
+                mUserManager.getProfileIdsWithDisabled(mSettings.getCurrentUserId()));
     }
 
     @Override
@@ -2546,7 +2541,8 @@
                 return false;
             }
             final ImeSubtypeListItem nextSubtype = mSwitchingController.getNextInputMethodLocked(
-                    onlyCurrentIme, mMethodMap.get(mCurMethodId), mCurrentSubtype);
+                    onlyCurrentIme, mMethodMap.get(mCurMethodId), mCurrentSubtype,
+                    true /* forward */);
             if (nextSubtype == null) {
                 return false;
             }
@@ -2569,7 +2565,8 @@
                 return false;
             }
             final ImeSubtypeListItem nextSubtype = mSwitchingController.getNextInputMethodLocked(
-                    false /* onlyCurrentIme */, mMethodMap.get(mCurMethodId), mCurrentSubtype);
+                    false /* onlyCurrentIme */, mMethodMap.get(mCurMethodId), mCurrentSubtype,
+                    true /* forward */);
             if (nextSubtype == null) {
                 return false;
             }
@@ -2963,23 +2960,12 @@
 
     private void handleSwitchInputMethod(final boolean forwardDirection) {
         synchronized (mMethodMap) {
-            // TODO: Support forwardDirection.
             final ImeSubtypeListItem nextSubtype = mSwitchingController.getNextInputMethodLocked(
-                    false, mMethodMap.get(mCurMethodId), mCurrentSubtype);
+                    false, mMethodMap.get(mCurMethodId), mCurrentSubtype, forwardDirection);
             if (nextSubtype == null) {
                 return;
             }
             setInputMethodLocked(nextSubtype.mImi.getId(), nextSubtype.mSubtypeId);
-            if (mSubtypeSwitchedByShortCutToast != null) {
-                mSubtypeSwitchedByShortCutToast.cancel();
-                mSubtypeSwitchedByShortCutToast = null;
-            }
-            if ((mImeWindowVis & InputMethodService.IME_VISIBLE) != 0) {
-                // IME window is shown.  The user should be able to visually understand that the
-                // subtype is changed in most of cases.  To avoid UI overlap, we do not show a toast
-                // in this case.
-                return;
-            }
             final InputMethodInfo newInputMethodInfo = mMethodMap.get(mCurMethodId);
             if (newInputMethodInfo == null) {
                 return;
@@ -2987,8 +2973,12 @@
             final CharSequence toastText = InputMethodUtils.getImeAndSubtypeDisplayName(mContext,
                     newInputMethodInfo, mCurrentSubtype);
             if (!TextUtils.isEmpty(toastText)) {
-                mSubtypeSwitchedByShortCutToast = Toast.makeText(mContext, toastText.toString(),
-                        Toast.LENGTH_SHORT);
+                if (mSubtypeSwitchedByShortCutToast == null) {
+                    mSubtypeSwitchedByShortCutToast = Toast.makeText(mContext, toastText,
+                            Toast.LENGTH_SHORT);
+                } else {
+                    mSubtypeSwitchedByShortCutToast.setText(toastText);
+                }
                 mSubtypeSwitchedByShortCutToast.show();
             }
         }
@@ -3648,6 +3638,7 @@
         private static final String ATTR_ID = "id";
         private static final String ATTR_LABEL = "label";
         private static final String ATTR_ICON = "icon";
+        private static final String ATTR_IME_SUBTYPE_ID = "subtypeId";
         private static final String ATTR_IME_SUBTYPE_LOCALE = "imeSubtypeLocale";
         private static final String ATTR_IME_SUBTYPE_LANGUAGE_TAG = "languageTag";
         private static final String ATTR_IME_SUBTYPE_MODE = "imeSubtypeMode";
@@ -3741,6 +3732,10 @@
                     for (int i = 0; i < N; ++i) {
                         final InputMethodSubtype subtype = subtypesList.get(i);
                         out.startTag(null, NODE_SUBTYPE);
+                        if (subtype.hasSubtypeId()) {
+                            out.attribute(null, ATTR_IME_SUBTYPE_ID,
+                                    String.valueOf(subtype.getSubtypeId()));
+                        }
                         out.attribute(null, ATTR_ICON, String.valueOf(subtype.getIconResId()));
                         out.attribute(null, ATTR_LABEL, String.valueOf(subtype.getNameResId()));
                         out.attribute(null, ATTR_IME_SUBTYPE_LOCALE, subtype.getLocale());
@@ -3819,7 +3814,7 @@
                                 parser.getAttributeValue(null, ATTR_IS_AUXILIARY)));
                         final boolean isAsciiCapable = "1".equals(String.valueOf(
                                 parser.getAttributeValue(null, ATTR_IS_ASCII_CAPABLE)));
-                        final InputMethodSubtype subtype = new InputMethodSubtypeBuilder()
+                        final InputMethodSubtypeBuilder builder = new InputMethodSubtypeBuilder()
                                 .setSubtypeNameResId(label)
                                 .setSubtypeIconResId(icon)
                                 .setSubtypeLocale(imeSubtypeLocale)
@@ -3827,9 +3822,13 @@
                                 .setSubtypeMode(imeSubtypeMode)
                                 .setSubtypeExtraValue(imeSubtypeExtraValue)
                                 .setIsAuxiliary(isAuxiliary)
-                                .setIsAsciiCapable(isAsciiCapable)
-                                .build();
-                        tempSubtypesArray.add(subtype);
+                                .setIsAsciiCapable(isAsciiCapable);
+                        final String subtypeIdString =
+                                parser.getAttributeValue(null, ATTR_IME_SUBTYPE_ID);
+                        if (subtypeIdString != null) {
+                            builder.setSubtypeId(Integer.valueOf(subtypeIdString));
+                        }
+                        tempSubtypesArray.add(builder.build());
                     }
                 }
             } catch (XmlPullParserException | IOException | NumberFormatException e) {
diff --git a/services/core/java/com/android/server/LocationManagerService.java b/services/core/java/com/android/server/LocationManagerService.java
index 9884a70..7c48634 100644
--- a/services/core/java/com/android/server/LocationManagerService.java
+++ b/services/core/java/com/android/server/LocationManagerService.java
@@ -21,6 +21,7 @@
 import com.android.internal.location.ProviderProperties;
 import com.android.internal.location.ProviderRequest;
 import com.android.internal.os.BackgroundThread;
+import com.android.internal.util.ArrayUtils;
 import com.android.server.location.ActivityRecognitionProxy;
 import com.android.server.location.FlpHardwareProvider;
 import com.android.server.location.FusedProxy;
@@ -53,7 +54,6 @@
 import android.content.pm.PackageManager.NameNotFoundException;
 import android.content.pm.ResolveInfo;
 import android.content.pm.Signature;
-import android.content.pm.UserInfo;
 import android.content.res.Resources;
 import android.database.ContentObserver;
 import android.hardware.location.ActivityRecognitionHardware;
@@ -359,12 +359,9 @@
      * @param currentUserId the current user, who might have an alter-ego.
      */
     void updateUserProfiles(int currentUserId) {
-        List<UserInfo> profiles = mUserManager.getProfiles(currentUserId);
+        int[] profileIds = mUserManager.getProfileIdsWithDisabled(currentUserId);
         synchronized (mLock) {
-            mCurrentUserProfiles = new int[profiles.size()];
-            for (int i = 0; i < mCurrentUserProfiles.length; i++) {
-                mCurrentUserProfiles[i] = profiles.get(i).id;
-            }
+            mCurrentUserProfiles = profileIds;
         }
     }
 
@@ -374,12 +371,7 @@
      */
     private boolean isCurrentProfile(int userId) {
         synchronized (mLock) {
-            for (int i = 0; i < mCurrentUserProfiles.length; i++) {
-                if (mCurrentUserProfiles[i] == userId) {
-                    return true;
-                }
-            }
-            return false;
+            return ArrayUtils.contains(mCurrentUserProfiles, userId);
         }
     }
 
diff --git a/services/core/java/com/android/server/LockSettingsStorage.java b/services/core/java/com/android/server/LockSettingsStorage.java
index d136f1a..9ab6300 100644
--- a/services/core/java/com/android/server/LockSettingsStorage.java
+++ b/services/core/java/com/android/server/LockSettingsStorage.java
@@ -401,7 +401,8 @@
         return getLockCredentialFilePathForUser(userId, BASE_ZERO_LOCK_PATTERN_FILE);
     }
 
-    private String getChildProfileLockFile(int userId) {
+    @VisibleForTesting
+    String getChildProfileLockFile(int userId) {
         return getLockCredentialFilePathForUser(userId, CHILD_PROFILE_LOCK_FILE);
     }
 
diff --git a/services/core/java/com/android/server/MountService.java b/services/core/java/com/android/server/MountService.java
index fd9a94d..229a3f4 100644
--- a/services/core/java/com/android/server/MountService.java
+++ b/services/core/java/com/android/server/MountService.java
@@ -1010,7 +1010,7 @@
         Configuration config = new Configuration();
         config.setLocale(locale);
         try {
-            ActivityManagerNative.getDefault().updateConfiguration(config);
+            ActivityManagerNative.getDefault().updatePersistentConfiguration(config);
         } catch (RemoteException e) {
             Slog.e(TAG, "Error setting system locale from mount service", e);
         }
diff --git a/services/core/java/com/android/server/NativeDaemonConnector.java b/services/core/java/com/android/server/NativeDaemonConnector.java
index d6dbad8..7db9be2 100644
--- a/services/core/java/com/android/server/NativeDaemonConnector.java
+++ b/services/core/java/com/android/server/NativeDaemonConnector.java
@@ -110,6 +110,14 @@
     }
 
     /**
+     * Like SystemClock.uptimeMillis, except truncated to an int so it will fit in a message arg.
+     * Inaccurate across 49.7 days of uptime, but only used for debugging.
+     */
+    private int uptimeMillisInt() {
+        return (int) SystemClock.uptimeMillis() & Integer.MAX_VALUE;
+    }
+
+    /**
      * Yell loudly if someone tries making future {@link #execute(Command)}
      * calls while holding a lock on the given object.
      */
@@ -134,7 +142,9 @@
 
     @Override
     public boolean handleMessage(Message msg) {
-        String event = (String) msg.obj;
+        final String event = (String) msg.obj;
+        final int start = uptimeMillisInt();
+        final int sent = msg.arg1;
         try {
             if (!mCallbacks.onEvent(msg.what, event, NativeDaemonEvent.unescapeArgs(event))) {
                 log(String.format("Unhandled event '%s'", event));
@@ -145,6 +155,13 @@
             if (mCallbacks.onCheckHoldWakeLock(msg.what) && mWakeLock != null) {
                 mWakeLock.release();
             }
+            final int end = uptimeMillisInt();
+            if (start > sent && start - sent > WARN_EXECUTE_DELAY_MS) {
+                loge(String.format("NDC event {%s} processed too late: %dms", event, start - sent));
+            }
+            if (end > start && end - start > WARN_EXECUTE_DELAY_MS) {
+                loge(String.format("NDC event {%s} took too long: %dms", event, end - start));
+            }
         }
         return true;
     }
@@ -214,8 +231,9 @@
                                     mWakeLock.acquire();
                                     releaseWl = true;
                                 }
-                                if (mCallbackHandler.sendMessage(mCallbackHandler.obtainMessage(
-                                        event.getCode(), event.getRawEvent()))) {
+                                Message msg = mCallbackHandler.obtainMessage(
+                                        event.getCode(), uptimeMillisInt(), 0, event.getRawEvent());
+                                if (mCallbackHandler.sendMessage(msg)) {
                                     releaseWl = false;
                                 }
                             } else {
diff --git a/services/core/java/com/android/server/TextServicesManagerService.java b/services/core/java/com/android/server/TextServicesManagerService.java
index 3eb20a0..801d6e0 100644
--- a/services/core/java/com/android/server/TextServicesManagerService.java
+++ b/services/core/java/com/android/server/TextServicesManagerService.java
@@ -43,7 +43,6 @@
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.content.pm.ServiceInfo;
-import android.content.pm.UserInfo;
 import android.os.Binder;
 import android.os.Bundle;
 import android.os.IBinder;
@@ -195,12 +194,8 @@
     }
 
     void updateCurrentProfileIds() {
-        final List<UserInfo> profiles = mUserManager.getProfiles(mSettings.getCurrentUserId());
-        int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null
-        for (int i = 0; i < currentProfileIds.length; i++) {
-            currentProfileIds[i] = profiles.get(i).id;
-        }
-        mSettings.setCurrentProfileIds(currentProfileIds);
+        mSettings.setCurrentProfileIds(
+                mUserManager.getProfileIdsWithDisabled(mSettings.getCurrentUserId()));
     }
 
     private class TextServicesMonitor extends PackageMonitor {
diff --git a/services/core/java/com/android/server/accounts/AccountManagerService.java b/services/core/java/com/android/server/accounts/AccountManagerService.java
index 810270d..05e4245 100644
--- a/services/core/java/com/android/server/accounts/AccountManagerService.java
+++ b/services/core/java/com/android/server/accounts/AccountManagerService.java
@@ -85,8 +85,10 @@
 import android.util.SparseBooleanArray;
 
 import com.android.internal.R;
+import com.android.internal.annotations.VisibleForTesting;
 import com.android.internal.util.ArrayUtils;
 import com.android.internal.util.IndentingPrintWriter;
+import com.android.internal.util.Preconditions;
 import com.android.server.FgThread;
 import com.android.server.LocalServices;
 import com.google.android.collect.Lists;
@@ -266,10 +268,10 @@
         private int debugDbInsertionPoint = -1;
         private SQLiteStatement statementForLogging;
 
-        UserAccounts(Context context, int userId) {
+        UserAccounts(Context context, int userId, File preNDbFile, File deDbFile) {
             this.userId = userId;
             synchronized (cacheLock) {
-                openHelper = DeDatabaseHelper.create(context, userId);
+                openHelper = DeDatabaseHelper.create(context, userId, preNDbFile, deDbFile);
             }
         }
     }
@@ -539,7 +541,9 @@
             UserAccounts accounts = mUsers.get(userId);
             boolean validateAccounts = false;
             if (accounts == null) {
-                accounts = new UserAccounts(mContext, userId);
+                File preNDbFile = new File(getPreNDatabaseName(userId));
+                File deDbFile = new File(getDeDatabaseName(userId));
+                accounts = new UserAccounts(mContext, userId, preNDbFile, deDbFile);
                 initializeDebugDbSizeAndCompileSqlStatementForLogging(
                         accounts.openHelper.getWritableDatabase(), accounts);
                 mUsers.append(userId, accounts);
@@ -550,10 +554,12 @@
             if (!accounts.openHelper.isCeDatabaseAttached() && mUnlockedUsers.get(userId)) {
                 Log.i(TAG, "User " + userId + " is unlocked - opening CE database");
                 synchronized (accounts.cacheLock) {
-                    CeDatabaseHelper.create(mContext, userId);
-                    accounts.openHelper.attachCeDatabase();
+                    File preNDatabaseFile = new File(getPreNDatabaseName(userId));
+                    File ceDatabaseFile = new File(getCeDatabaseName(userId));
+                    CeDatabaseHelper.create(mContext, userId, preNDatabaseFile, ceDatabaseFile);
+                    accounts.openHelper.attachCeDatabase(ceDatabaseFile);
                 }
-                // TODO Synchronize accounts by removing CE account not available in DE
+                syncDeCeAccountsLocked(accounts);
             }
             if (validateAccounts) {
                 validateAccountsInternal(accounts, true /* invalidateAuthenticatorCache */);
@@ -562,6 +568,21 @@
         }
     }
 
+    private void syncDeCeAccountsLocked(UserAccounts accounts) {
+        Preconditions.checkState(Thread.holdsLock(mUsers), "mUsers lock must be held");
+        final SQLiteDatabase db = accounts.openHelper.getReadableDatabaseUserIsUnlocked();
+        List<Account> accountsToRemove = CeDatabaseHelper.findCeAccountsNotInDe(db);
+        if (!accountsToRemove.isEmpty()) {
+            Slog.i(TAG, "Accounts " + accountsToRemove + " were previously deleted while user "
+                    + accounts.userId + " was locked. Removing accounts from CE tables");
+            logRecord(accounts, DebugDbHelper.ACTION_SYNC_DE_CE_ACCOUNTS, TABLE_ACCOUNTS);
+
+            for (Account account : accountsToRemove) {
+                removeAccountInternal(accounts, account, Process.myUid());
+            }
+        }
+    }
+
     private void purgeOldGrantsAll() {
         synchronized (mUsers) {
             for (int i = 0; i < mUsers.size(); i++) {
@@ -631,7 +652,8 @@
         }
     }
 
-    private void onUserUnlocked(Intent intent) {
+    @VisibleForTesting
+    void onUserUnlocked(Intent intent) {
         int userId = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, -1);
         if (Log.isLoggable(TAG, Log.VERBOSE)) {
             Log.v(TAG, "onUserUnlocked " + userId);
@@ -799,7 +821,7 @@
         if (Log.isLoggable(TAG, Log.VERBOSE)) {
             Log.v(TAG, "getAuthenticatorTypes: "
                     + "for user id " + userId
-                    + "caller's uid " + callingUid
+                    + " caller's uid " + callingUid
                     + ", pid " + Binder.getCallingPid());
         }
         // Only allow the system process to read accounts of other users
@@ -1537,27 +1559,41 @@
         }
     }
 
-    /* For testing */
+    @VisibleForTesting
     protected void removeAccountInternal(Account account) {
         removeAccountInternal(getUserAccountsForCaller(), account, getCallingUid());
     }
 
     private boolean removeAccountInternal(UserAccounts accounts, Account account, int callingUid) {
-        // For now user is required to be unlocked. TODO: Handle both cases in the future
         int deleted;
+        boolean userUnlocked = isUserUnlocked(accounts.userId);
+        if (!userUnlocked) {
+            Slog.i(TAG, "Removing account " + account + " while user "+ accounts.userId
+                    + " is still locked. CE data will be removed later");
+        }
         synchronized (accounts.cacheLock) {
-            final SQLiteDatabase db = accounts.openHelper.getWritableDatabaseUserIsUnlocked();
+            final SQLiteDatabase db = userUnlocked
+                    ? accounts.openHelper.getWritableDatabaseUserIsUnlocked()
+                    : accounts.openHelper.getWritableDatabase();
             final long accountId = getAccountIdLocked(db, account);
-            deleted = db.delete(TABLE_ACCOUNTS, ACCOUNTS_NAME + "=? AND " + ACCOUNTS_TYPE
-                    + "=?",
-                    new String[]{account.name, account.type});
-            // Delete from CE table
-            db.delete(CE_TABLE_ACCOUNTS, ACCOUNTS_NAME + "=? AND " + ACCOUNTS_TYPE + "=?",
-                    new String[]{account.name, account.type});
+            db.beginTransaction();
+            try {
+                deleted = db.delete(TABLE_ACCOUNTS, ACCOUNTS_NAME + "=? AND " + ACCOUNTS_TYPE
+                                + "=?", new String[]{account.name, account.type});
+                if (userUnlocked) {
+                    // Delete from CE table
+                    deleted = db.delete(CE_TABLE_ACCOUNTS, ACCOUNTS_NAME + "=? AND " + ACCOUNTS_TYPE
+                            + "=?", new String[]{account.name, account.type});
+                }
+                db.setTransactionSuccessful();
+            } finally {
+                db.endTransaction();
+            }
             removeAccountFromCacheLocked(accounts, account);
             sendAccountsChangedBroadcast(accounts.userId);
-
-            logRecord(db, DebugDbHelper.ACTION_ACCOUNT_REMOVE, TABLE_ACCOUNTS, accountId, accounts);
+            String action = userUnlocked ? DebugDbHelper.ACTION_ACCOUNT_REMOVE
+                    : DebugDbHelper.ACTION_ACCOUNT_REMOVE_DE;
+            logRecord(db, action, TABLE_ACCOUNTS, accountId, accounts);
         }
         long id = Binder.clearCallingIdentity();
         try {
@@ -4014,7 +4050,8 @@
         }
     }
 
-    static String getPreNDatabaseName(int userId) {
+    @VisibleForTesting
+    String getPreNDatabaseName(int userId) {
         File systemDir = Environment.getDataSystemDirectory();
         File databaseFile = new File(Environment.getUserSystemDirectory(userId),
                 PRE_N_DATABASE_NAME);
@@ -4040,13 +4077,15 @@
         return databaseFile.getPath();
     }
 
-    static String getDeDatabaseName(int userId) {
+    @VisibleForTesting
+    String getDeDatabaseName(int userId) {
         File databaseFile = new File(Environment.getDataSystemDeDirectory(userId),
                 DE_DATABASE_NAME);
         return databaseFile.getPath();
     }
 
-    static String getCeDatabaseName(int userId) {
+    @VisibleForTesting
+    String getCeDatabaseName(int userId) {
         File databaseFile = new File(Environment.getDataSystemCeDirectory(userId),
                 CE_DATABASE_NAME);
         return databaseFile.getPath();
@@ -4072,6 +4111,7 @@
         private static String ACTION_CLEAR_PASSWORD = "action_clear_password";
         private static String ACTION_ACCOUNT_ADD = "action_account_add";
         private static String ACTION_ACCOUNT_REMOVE = "action_account_remove";
+        private static String ACTION_ACCOUNT_REMOVE_DE = "action_account_remove_de";
         private static String ACTION_AUTHENTICATOR_REMOVE = "action_authenticator_remove";
         private static String ACTION_ACCOUNT_RENAME = "action_account_rename";
 
@@ -4082,6 +4122,7 @@
         // who called.
         private static String ACTION_CALLED_ACCOUNT_ADD = "action_called_account_add";
         private static String ACTION_CALLED_ACCOUNT_REMOVE = "action_called_account_remove";
+        private static String ACTION_SYNC_DE_CE_ACCOUNTS = "action_sync_de_ce_accounts";
 
         //This action doesn't add account to accountdb. Account is only
         // added in finishSession which may be in a different user profile.
@@ -4185,13 +4226,11 @@
     }
 
     static class PreNDatabaseHelper extends SQLiteOpenHelper {
-
         private final Context mContext;
         private final int mUserId;
 
-        public PreNDatabaseHelper(Context context, int userId) {
-            super(context, AccountManagerService.getPreNDatabaseName(userId), null,
-                    PRE_N_DATABASE_VERSION);
+        public PreNDatabaseHelper(Context context, int userId, String preNDatabaseName) {
+            super(context, preNDatabaseName, null, PRE_N_DATABASE_VERSION);
             mContext = context;
             mUserId = userId;
         }
@@ -4328,8 +4367,8 @@
         private final int mUserId;
         private volatile boolean mCeAttached;
 
-        private DeDatabaseHelper(Context context, int userId) {
-            super(context, getDeDatabaseName(userId), null, DE_DATABASE_VERSION);
+        private DeDatabaseHelper(Context context, int userId, String deDatabaseName) {
+            super(context, deDatabaseName, null, DE_DATABASE_VERSION);
             mUserId = userId;
         }
 
@@ -4394,8 +4433,7 @@
             }
         }
 
-        public void attachCeDatabase() {
-            File ceDbFile = new File(getCeDatabaseName(mUserId));
+        public void attachCeDatabase(File ceDbFile) {
             SQLiteDatabase db = getWritableDatabase();
             db.execSQL("ATTACH DATABASE '" +  ceDbFile.getPath()+ "' AS ceDb");
             mCeAttached = true;
@@ -4408,8 +4446,8 @@
 
         public SQLiteDatabase getReadableDatabaseUserIsUnlocked() {
             if(!mCeAttached) {
-                Log.wtf(TAG, "getReadableDatabaseUserIsUnlocked called while user "
-                        + mUserId + " is still locked ", new Throwable());
+                Log.wtf(TAG, "getReadableDatabaseUserIsUnlocked called while user " + mUserId
+                        + " is still locked. CE database is not yet available.", new Throwable());
             }
             return super.getReadableDatabase();
         }
@@ -4417,7 +4455,7 @@
         public SQLiteDatabase getWritableDatabaseUserIsUnlocked() {
             if(!mCeAttached) {
                 Log.wtf(TAG, "getWritableDatabaseUserIsUnlocked called while user " + mUserId
-                        + " is still locked ", new Throwable());
+                        + " is still locked. CE database is not yet available.", new Throwable());
             }
             return super.getWritableDatabase();
         }
@@ -4470,20 +4508,24 @@
             db.execSQL("DETACH DATABASE preNDb");
         }
 
-        static DeDatabaseHelper create(Context context, int userId) {
-            File oldDb = new File(getPreNDatabaseName(userId));
-            File newDb = new File(getDeDatabaseName(userId));
-            boolean newDbExists = newDb.exists();
-            DeDatabaseHelper deDatabaseHelper = new DeDatabaseHelper(context, userId);
+        static DeDatabaseHelper create(
+                Context context,
+                int userId,
+                File preNDatabaseFile,
+                File deDatabaseFile) {
+            boolean newDbExists = deDatabaseFile.exists();
+            DeDatabaseHelper deDatabaseHelper = new DeDatabaseHelper(context, userId,
+                    deDatabaseFile.getPath());
             // If the db just created, and there is a legacy db, migrate it
-            if (!newDbExists && oldDb.exists()) {
+            if (!newDbExists && preNDatabaseFile.exists()) {
                 // Migrate legacy db to the latest version -  PRE_N_DATABASE_VERSION
-                PreNDatabaseHelper preNDatabaseHelper = new PreNDatabaseHelper(context, userId);
+                PreNDatabaseHelper preNDatabaseHelper = new PreNDatabaseHelper(context, userId,
+                        preNDatabaseFile.getPath());
                 // Open the database to force upgrade if required
                 preNDatabaseHelper.getWritableDatabase();
                 preNDatabaseHelper.close();
                 // Move data without SPII to DE
-                deDatabaseHelper.migratePreNDbToDe(oldDb);
+                deDatabaseHelper.migratePreNDbToDe(preNDatabaseFile);
             }
             return deDatabaseHelper;
         }
@@ -4491,8 +4533,8 @@
 
     static class CeDatabaseHelper extends SQLiteOpenHelper {
 
-        public CeDatabaseHelper(Context context, int userId) {
-            super(context, getCeDatabaseName(userId), null, CE_DATABASE_VERSION);
+        public CeDatabaseHelper(Context context, String ceDatabaseName) {
+            super(context, ceDatabaseName, null, CE_DATABASE_VERSION);
         }
 
         /**
@@ -4580,33 +4622,56 @@
             }
         }
 
+        static List<Account> findCeAccountsNotInDe(SQLiteDatabase db) {
+            // Select accounts from CE that do not exist in DE
+            Cursor cursor = db.rawQuery(
+                    "SELECT " + ACCOUNTS_NAME + "," + ACCOUNTS_TYPE
+                            + " FROM " + CE_TABLE_ACCOUNTS
+                            + " WHERE NOT EXISTS "
+                            + " (SELECT " + ACCOUNTS_ID + " FROM " + TABLE_ACCOUNTS
+                            + " WHERE " + ACCOUNTS_ID + "=" + CE_TABLE_ACCOUNTS + "." + ACCOUNTS_ID
+                            + " )", null);
+            try {
+                List<Account> accounts = new ArrayList<>(cursor.getCount());
+                while (cursor.moveToNext()) {
+                    String accountName = cursor.getString(0);
+                    String accountType = cursor.getString(1);
+                    accounts.add(new Account(accountName, accountType));
+                }
+                return accounts;
+            } finally {
+                cursor.close();
+            }
+        }
+
         /**
          * Creates a new {@code CeDatabaseHelper}. If pre-N db file is present at the old location,
          * it also performs migration to the new CE database.
          * @param context
          * @param userId id of the user where the database is located
          */
-        static CeDatabaseHelper create(Context context, int userId) {
-
-            File oldDatabaseFile = new File(getPreNDatabaseName(userId));
-            File ceDatabaseFile = new File(getCeDatabaseName(userId));
+        static CeDatabaseHelper create(
+                Context context,
+                int userId,
+                File preNDatabaseFile,
+                File ceDatabaseFile) {
             boolean newDbExists = ceDatabaseFile.exists();
             if (Log.isLoggable(TAG, Log.VERBOSE)) {
                 Log.v(TAG, "CeDatabaseHelper.create userId=" + userId + " oldDbExists="
-                        + oldDatabaseFile.exists() + " newDbExists=" + newDbExists);
+                        + preNDatabaseFile.exists() + " newDbExists=" + newDbExists);
             }
             boolean removeOldDb = false;
-            if (!newDbExists && oldDatabaseFile.exists()) {
-                removeOldDb = migratePreNDbToCe(oldDatabaseFile, ceDatabaseFile);
+            if (!newDbExists && preNDatabaseFile.exists()) {
+                removeOldDb = migratePreNDbToCe(preNDatabaseFile, ceDatabaseFile);
             }
             // Try to open and upgrade if necessary
-            CeDatabaseHelper ceHelper = new CeDatabaseHelper(context, userId);
+            CeDatabaseHelper ceHelper = new CeDatabaseHelper(context, ceDatabaseFile.getPath());
             ceHelper.getWritableDatabase();
             ceHelper.close();
             if (removeOldDb) {
                 // TODO STOPSHIP - backup file during testing. Remove file before the release
-                Log.i(TAG, "Migration complete - creating backup of old db " + oldDatabaseFile);
-                renameToBakFile(oldDatabaseFile);
+                Log.i(TAG, "Migration complete - creating backup of old db " + preNDatabaseFile);
+                renameToBakFile(preNDatabaseFile);
             }
             return ceHelper;
         }
@@ -4771,12 +4836,14 @@
         }
     }
 
+    @VisibleForTesting
     protected void installNotification(final int notificationId, final Notification n,
             UserHandle user) {
         ((NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE))
                 .notifyAsUser(null, notificationId, n, user);
     }
 
+    @VisibleForTesting
     protected void cancelNotification(int id, UserHandle user) {
         long identityToken = clearCallingIdentity();
         try {
@@ -5314,7 +5381,7 @@
         HashMap<String, String> userDataForAccount = accounts.userDataCache.get(account);
         if (userDataForAccount == null) {
             // need to populate the cache for this account
-            final SQLiteDatabase db = accounts.openHelper.getReadableDatabase();
+            final SQLiteDatabase db = accounts.openHelper.getReadableDatabaseUserIsUnlocked();
             userDataForAccount = readUserDataForAccountFromDatabaseLocked(db, account);
             accounts.userDataCache.put(account, userDataForAccount);
         }
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 4852788..3ec51e3 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -1467,6 +1467,7 @@
     static final int NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG = 65;
     static final int NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG = 66;
     static final int NOTIFY_FORCED_RESIZABLE_MSG = 67;
+    static final int NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG = 68;
 
     static final int FIRST_ACTIVITY_STACK_MSG = 100;
     static final int FIRST_BROADCAST_QUEUE_MSG = 200;
@@ -2056,6 +2057,21 @@
                 }
                 break;
             }
+                case NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG: {
+                    synchronized (ActivityManagerService.this) {
+                        for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
+                            try {
+                                // Make a one-way callback to the listener
+                                mTaskStackListeners.getBroadcastItem(i)
+                                        .onActivityDismissingDockedStack();
+                            } catch (RemoteException e){
+                                // Handled by the RemoteCallbackList
+                            }
+                        }
+                        mTaskStackListeners.finishBroadcast();
+                    }
+                    break;
+                }
             case NOTIFY_CLEARTEXT_NETWORK_MSG: {
                 final int uid = msg.arg1;
                 final byte[] firstPacket = (byte[]) msg.obj;
@@ -13148,6 +13164,9 @@
         }
     }
 
+    private volatile long mWtfClusterStart;
+    private volatile int mWtfClusterCount;
+
     /**
      * Write a description of an error (crash, WTF, ANR) to the drop box.
      * @param eventType to include in the drop box tag ("crash", "wtf", etc.)
@@ -13174,6 +13193,16 @@
         // Exit early if the dropbox isn't configured to accept this report type.
         if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return;
 
+        // Rate-limit how often we're willing to do the heavy lifting below to
+        // collect and record logs; currently 5 logs per 10 second period.
+        final long now = SystemClock.elapsedRealtime();
+        if (now - mWtfClusterStart > 10 * DateUtils.SECOND_IN_MILLIS) {
+            mWtfClusterStart = now;
+            mWtfClusterCount = 1;
+        } else {
+            if (mWtfClusterCount++ >= 5) return;
+        }
+
         final StringBuilder sb = new StringBuilder(1024);
         appendDropBoxProcessHeaders(process, processName, sb);
         if (process != null) {
@@ -15641,8 +15670,8 @@
                     pw.println(totalPss - cachedPss);
                 }
             }
-            long lostRAM = memInfo.getTotalSizeKb()
-                    - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb()
+            long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss)
+                    - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb()
                     - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb();
             if (!isCompact) {
                 pw.print(" Used RAM: "); pw.print(stringifyKBSize(totalPss - cachedPss
@@ -17115,7 +17144,7 @@
                 // but historically it has not been protected and apps may be using it
                 // to poke their own app widget.  So, instead of making it protected,
                 // just limit it to the caller.
-                if (callerApp == null) {
+                if (callerPackage == null) {
                     String msg = "Permission Denial: not allowed to send broadcast "
                             + action + " from unknown caller.";
                     Slog.w(TAG, msg);
@@ -17124,17 +17153,17 @@
                     // They are good enough to send to an explicit component...  verify
                     // it is being sent to the calling app.
                     if (!intent.getComponent().getPackageName().equals(
-                            callerApp.info.packageName)) {
+                            callerPackage)) {
                         String msg = "Permission Denial: not allowed to send broadcast "
                                 + action + " to "
                                 + intent.getComponent().getPackageName() + " from "
-                                + callerApp.info.packageName;
+                                + callerPackage;
                         Slog.w(TAG, msg);
                         throw new SecurityException(msg);
                     }
                 } else {
                     // Limit broadcast to their own package.
-                    intent.setPackage(callerApp.info.packageName);
+                    intent.setPackage(callerPackage);
                 }
             }
         }
diff --git a/services/core/java/com/android/server/am/ActivityStack.java b/services/core/java/com/android/server/am/ActivityStack.java
index 4ec1f61..2e9947a 100644
--- a/services/core/java/com/android/server/am/ActivityStack.java
+++ b/services/core/java/com/android/server/am/ActivityStack.java
@@ -28,47 +28,78 @@
 import static android.content.pm.ActivityInfo.CONFIG_SMALLEST_SCREEN_SIZE;
 import static android.content.pm.ActivityInfo.FLAG_RESUME_WHILE_PAUSING;
 import static android.content.pm.ActivityInfo.FLAG_SHOW_FOR_ALL_USERS;
-
 import static android.content.res.Configuration.SCREENLAYOUT_UNDEFINED;
-import static com.android.server.am.ActivityManagerDebugConfig.*;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ADD_REMOVE;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ALL;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_APP;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CLEANUP;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CONFIGURATION;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CONTAINERS;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKSCREEN;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PAUSE;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_RELEASE;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_RESULTS;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SAVED_STATE;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SCREENSHOTS;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_STACK;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_STATES;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SWITCH;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_TASKS;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_TRANSITION;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_USER_LEAVING;
+import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBILITY;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_ADD_REMOVE;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_APP;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CLEANUP;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CONFIGURATION;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CONTAINERS;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PAUSE;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_RELEASE;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_RESULTS;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SAVED_STATE;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SCREENSHOTS;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_STACK;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_STATES;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SWITCH;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_TASKS;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_TRANSITION;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_USER_LEAVING;
+import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBILITY;
+import static com.android.server.am.ActivityManagerDebugConfig.TAG_AM;
+import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME;
 import static com.android.server.am.ActivityManagerService.LOCK_SCREEN_SHOWN;
-import static com.android.server.am.ActivityRecord.HOME_ACTIVITY_TYPE;
 import static com.android.server.am.ActivityRecord.APPLICATION_ACTIVITY_TYPE;
-
+import static com.android.server.am.ActivityRecord.HOME_ACTIVITY_TYPE;
 import static com.android.server.am.ActivityRecord.STARTING_WINDOW_REMOVED;
 import static com.android.server.am.ActivityRecord.STARTING_WINDOW_SHOWN;
 import static com.android.server.am.ActivityStackSupervisor.FindTaskResult;
 import static com.android.server.am.ActivityStackSupervisor.MOVING;
 import static com.android.server.am.ActivityStackSupervisor.PRESERVE_WINDOWS;
-
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.util.ArraySet;
-
-import com.android.internal.app.IVoiceInteractor;
-import com.android.internal.content.ReferrerIntent;
-import com.android.internal.os.BatteryStatsImpl;
-import com.android.server.Watchdog;
-import com.android.server.am.ActivityManagerService.ItemMatcher;
-import com.android.server.am.ActivityStackSupervisor.ActivityContainer;
-import com.android.server.wm.AppTransition;
-import com.android.server.wm.TaskGroup;
-import com.android.server.wm.WindowManagerService;
+import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_CLOSE;
+import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_OPEN;
+import static com.android.server.wm.AppTransition.TRANSIT_NONE;
+import static com.android.server.wm.AppTransition.TRANSIT_TASK_CLOSE;
+import static com.android.server.wm.AppTransition.TRANSIT_TASK_OPEN;
+import static com.android.server.wm.AppTransition.TRANSIT_TASK_OPEN_BEHIND;
+import static com.android.server.wm.AppTransition.TRANSIT_TASK_TO_BACK;
+import static com.android.server.wm.AppTransition.TRANSIT_TASK_TO_FRONT;
 
 import android.app.Activity;
 import android.app.ActivityManager;
+import android.app.ActivityManager.RunningTaskInfo;
 import android.app.ActivityManager.StackId;
 import android.app.ActivityOptions;
 import android.app.AppGlobals;
 import android.app.IActivityController;
 import android.app.ResultInfo;
-import android.app.ActivityManager.RunningTaskInfo;
 import android.content.ComponentName;
 import android.content.Intent;
 import android.content.pm.ActivityInfo;
 import android.content.pm.ApplicationInfo;
 import android.content.res.Configuration;
 import android.graphics.Bitmap;
+import android.graphics.Point;
+import android.graphics.Rect;
 import android.net.Uri;
 import android.os.Binder;
 import android.os.Bundle;
@@ -83,10 +114,20 @@
 import android.os.Trace;
 import android.os.UserHandle;
 import android.service.voice.IVoiceInteractionSession;
+import android.util.ArraySet;
 import android.util.EventLog;
 import android.util.Slog;
 import android.view.Display;
 
+import com.android.internal.app.IVoiceInteractor;
+import com.android.internal.content.ReferrerIntent;
+import com.android.internal.os.BatteryStatsImpl;
+import com.android.server.Watchdog;
+import com.android.server.am.ActivityManagerService.ItemMatcher;
+import com.android.server.am.ActivityStackSupervisor.ActivityContainer;
+import com.android.server.wm.TaskGroup;
+import com.android.server.wm.WindowManagerService;
+
 import java.io.FileDescriptor;
 import java.io.PrintWriter;
 import java.lang.ref.WeakReference;
@@ -1650,6 +1691,13 @@
             for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) {
                 final ActivityRecord r = activities.get(activityNdx);
                 if (r.finishing) {
+                    // Normally the screenshot will be taken in makeInvisible(). When an activity
+                    // is finishing, we no longer change its visibility, but we still need to take
+                    // the screenshots if startPausingLocked decided it should be taken.
+                    if (r.mUpdateTaskThumbnailWhenHidden) {
+                        r.updateThumbnailLocked(screenshotActivitiesLocked(r), null);
+                        r.mUpdateTaskThumbnailWhenHidden = false;
+                    }
                     continue;
                 }
                 final boolean isTop = r == top;
@@ -2225,11 +2273,11 @@
                         "Prepare close transition: prev=" + prev);
                 if (mNoAnimActivities.contains(prev)) {
                     anim = false;
-                    mWindowManager.prepareAppTransition(AppTransition.TRANSIT_NONE, false);
+                    mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
                 } else {
                     mWindowManager.prepareAppTransition(prev.task == next.task
-                            ? AppTransition.TRANSIT_ACTIVITY_CLOSE
-                            : AppTransition.TRANSIT_TASK_CLOSE, false);
+                            ? TRANSIT_ACTIVITY_CLOSE
+                            : TRANSIT_TASK_CLOSE, false);
                 }
                 mWindowManager.setAppVisibility(prev.appToken, false);
             } else {
@@ -2237,22 +2285,22 @@
                         "Prepare open transition: prev=" + prev);
                 if (mNoAnimActivities.contains(next)) {
                     anim = false;
-                    mWindowManager.prepareAppTransition(AppTransition.TRANSIT_NONE, false);
+                    mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
                 } else {
                     mWindowManager.prepareAppTransition(prev.task == next.task
-                            ? AppTransition.TRANSIT_ACTIVITY_OPEN
+                            ? TRANSIT_ACTIVITY_OPEN
                             : next.mLaunchTaskBehind
-                                    ? AppTransition.TRANSIT_TASK_OPEN_BEHIND
-                                    : AppTransition.TRANSIT_TASK_OPEN, false);
+                                    ? TRANSIT_TASK_OPEN_BEHIND
+                                    : TRANSIT_TASK_OPEN, false);
                 }
             }
         } else {
             if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION, "Prepare open transition: no previous");
             if (mNoAnimActivities.contains(next)) {
                 anim = false;
-                mWindowManager.prepareAppTransition(AppTransition.TRANSIT_NONE, false);
+                mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
             } else {
-                mWindowManager.prepareAppTransition(AppTransition.TRANSIT_ACTIVITY_OPEN, false);
+                mWindowManager.prepareAppTransition(TRANSIT_ACTIVITY_OPEN, false);
             }
         }
 
@@ -2595,14 +2643,14 @@
             if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION,
                     "Prepare open transition: starting " + r);
             if ((r.intent.getFlags() & Intent.FLAG_ACTIVITY_NO_ANIMATION) != 0) {
-                mWindowManager.prepareAppTransition(AppTransition.TRANSIT_NONE, keepCurTransition);
+                mWindowManager.prepareAppTransition(TRANSIT_NONE, keepCurTransition);
                 mNoAnimActivities.add(r);
             } else {
                 mWindowManager.prepareAppTransition(newTask
                         ? r.mLaunchTaskBehind
-                                ? AppTransition.TRANSIT_TASK_OPEN_BEHIND
-                                : AppTransition.TRANSIT_TASK_OPEN
-                        : AppTransition.TRANSIT_ACTIVITY_OPEN, keepCurTransition);
+                                ? TRANSIT_TASK_OPEN_BEHIND
+                                : TRANSIT_TASK_OPEN
+                        : TRANSIT_ACTIVITY_OPEN, keepCurTransition);
                 mNoAnimActivities.remove(r);
             }
             addConfigOverride(r, task);
@@ -3354,13 +3402,13 @@
 
         finishActivityResultsLocked(r, resultCode, resultData);
 
+        final boolean endTask = index <= 0;
+        final int transit = endTask ? TRANSIT_TASK_CLOSE : TRANSIT_ACTIVITY_CLOSE;
         if (mResumedActivity == r) {
-            boolean endTask = index <= 0;
+
             if (DEBUG_VISIBILITY || DEBUG_TRANSITION) Slog.v(TAG_TRANSITION,
                     "Prepare close transition: finishing " + r);
-            mWindowManager.prepareAppTransition(endTask
-                    ? AppTransition.TRANSIT_TASK_CLOSE
-                    : AppTransition.TRANSIT_ACTIVITY_CLOSE, false);
+            mWindowManager.prepareAppTransition(transit, false);
 
             // Tell window manager to prepare for this one to be removed.
             mWindowManager.setAppVisibility(r.appToken, false);
@@ -3380,7 +3428,9 @@
             // it is done pausing; else we can just directly finish it here.
             if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Finish not pausing: " + r);
             if (r.visible) {
+                mWindowManager.prepareAppTransition(transit, false);
                 mWindowManager.setAppVisibility(r.appToken, false);
+                mWindowManager.executeAppTransition();
             }
             return finishCurrentActivityLocked(r, FINISH_AFTER_PAUSE, oomAdj) == null;
         } else {
@@ -4122,7 +4172,7 @@
             if (noAnimation) {
                 ActivityOptions.abort(options);
             } else {
-                updateTransitLocked(AppTransition.TRANSIT_TASK_TO_FRONT, options);
+                updateTransitLocked(TRANSIT_TASK_TO_FRONT, options);
             }
             return;
         }
@@ -4152,13 +4202,13 @@
 
         if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION, "Prepare to front transition: task=" + tr);
         if (noAnimation) {
-            mWindowManager.prepareAppTransition(AppTransition.TRANSIT_NONE, false);
+            mWindowManager.prepareAppTransition(TRANSIT_NONE, false);
             if (r != null) {
                 mNoAnimActivities.add(r);
             }
             ActivityOptions.abort(options);
         } else {
-            updateTransitLocked(AppTransition.TRANSIT_TASK_TO_FRONT, options);
+            updateTransitLocked(TRANSIT_TASK_TO_FRONT, options);
         }
 
         mStackSupervisor.resumeFocusedStackTopActivityLocked();
@@ -4261,7 +4311,7 @@
             }
         }
 
-        mWindowManager.prepareAppTransition(AppTransition.TRANSIT_TASK_TO_BACK, false);
+        mWindowManager.prepareAppTransition(TRANSIT_TASK_TO_BACK, false);
         mWindowManager.moveTaskToBottom(taskId);
 
         if (VALIDATE_TOKENS) {
diff --git a/services/core/java/com/android/server/am/ActivityStackSupervisor.java b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
index 7b2a370..53c6024 100644
--- a/services/core/java/com/android/server/am/ActivityStackSupervisor.java
+++ b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
@@ -152,6 +152,7 @@
 import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME;
 import static com.android.server.am.ActivityManagerService.ANIMATE;
 import static com.android.server.am.ActivityManagerService.FIRST_SUPERVISOR_STACK_MSG;
+import static com.android.server.am.ActivityManagerService.NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG;
 import static com.android.server.am.ActivityManagerService.NOTIFY_FORCED_RESIZABLE_MSG;
 import static com.android.server.am.ActivityRecord.APPLICATION_ACTIVITY_TYPE;
 import static com.android.server.am.ActivityRecord.HOME_ACTIVITY_TYPE;
@@ -1810,7 +1811,7 @@
         if (DEBUG_STACK) Slog.d(TAG_STACK,
                 "findTaskToMoveToFront: moved to front of stack=" + task.stack);
 
-        showNonResizeableDockToastIfNeeded(task, INVALID_STACK_ID, task.stack.mStackId);
+        handleNonResizableTaskIfNeeded(task, INVALID_STACK_ID, task.stack.mStackId);
     }
 
     boolean canUseActivityOptionsLaunchBounds(ActivityOptions options, int launchStackId) {
@@ -2392,7 +2393,7 @@
             resumeFocusedStackTopActivityLocked();
         }
 
-        showNonResizeableDockToastIfNeeded(task, preferredLaunchStackId, stackId);
+        handleNonResizableTaskIfNeeded(task, preferredLaunchStackId, stackId);
 
         return (preferredLaunchStackId == stackId);
     }
@@ -3248,13 +3249,9 @@
     }
 
     private void calculateDefaultMinimalSizeOfResizeableTasks(ActivityDisplay display) {
-        if (display.mDisplayId != Display.DEFAULT_DISPLAY) {
-            return;
-        }
-        final float fraction = mService.mContext.getResources().getFraction(com.android.internal.R.
-                fraction.config_displayFractionForDefaultMinimalSizeOfResizeableTask, 1, 1);
-        mDefaultMinimalSizeOfResizeableTask = (int) (fraction * Math.min(
-                display.mDisplayInfo.logicalWidth, display.mDisplayInfo.logicalHeight));
+        mDefaultMinimalSizeOfResizeableTask =
+                mService.mContext.getResources().getDimensionPixelSize(
+                        com.android.internal.R.dimen.default_minimal_size_resizable_task);
     }
 
     private void handleDisplayRemoved(int displayId) {
@@ -3363,15 +3360,19 @@
         }
     }
 
-    void showNonResizeableDockToastIfNeeded(
+    void handleNonResizableTaskIfNeeded(
             TaskRecord task, int preferredStackId, int actualStackId) {
-        if (!isStackDockedInEffect(actualStackId) && preferredStackId != DOCKED_STACK_ID) {
+        if ((!isStackDockedInEffect(actualStackId) && preferredStackId != DOCKED_STACK_ID)
+                || task.isHomeTask()) {
             return;
         }
 
         if (!task.canGoInDockedStack()) {
             // Display a warning toast that we tried to put a non-dockable task in the docked stack.
-            mWindowManager.scheduleShowNonResizeableDockToast(task.taskId);
+            mService.mHandler.sendEmptyMessage(NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG);
+
+            // Dismiss docked stack.
+            mService.moveTasksToFullscreenStack(DOCKED_STACK_ID, false);
         } else if (task.mResizeMode == RESIZE_MODE_FORCE_RESIZEABLE) {
             String packageName = task.getTopActivity() != null
                     ? task.getTopActivity().appInfo.packageName : null;
@@ -4247,6 +4248,7 @@
         // Work Challenge is present) let startActivityInPackage handle the intercepting.
         if (!mService.mUserController.shouldConfirmCredentials(task.userId)
                 && task.getRootActivity() != null) {
+            mActivityMetricsLogger.notifyActivityLaunching();
             mService.moveTaskToFrontLocked(task.taskId, 0, bOptions);
 
             // If we are launching the task in the docked stack, put it into resizing mode so
diff --git a/services/core/java/com/android/server/am/ActivityStartInterceptor.java b/services/core/java/com/android/server/am/ActivityStartInterceptor.java
index 76dfd01..785dd47 100644
--- a/services/core/java/com/android/server/am/ActivityStartInterceptor.java
+++ b/services/core/java/com/android/server/am/ActivityStartInterceptor.java
@@ -119,7 +119,13 @@
         if (!mUserManager.isQuietModeEnabled(UserHandle.of(mUserId))) {
             return false;
         }
-        mIntent = UnlaunchableAppActivity.createInQuietModeDialogIntent(mUserId);
+        IIntentSender target = mService.getIntentSenderLocked(
+                INTENT_SENDER_ACTIVITY, mCallingPackage, mCallingUid, mUserId, null, null, 0,
+                new Intent[] {mIntent}, new String[] {mResolvedType},
+                FLAG_CANCEL_CURRENT | FLAG_ONE_SHOT, null);
+
+        mIntent = UnlaunchableAppActivity.createInQuietModeDialogIntent(mUserId,
+                new IntentSender(target));
         mCallingPid = mRealCallingPid;
         mCallingUid = mRealCallingUid;
         mResolvedType = null;
diff --git a/services/core/java/com/android/server/am/ActivityStarter.java b/services/core/java/com/android/server/am/ActivityStarter.java
index 3bbc452..6fba8c8 100644
--- a/services/core/java/com/android/server/am/ActivityStarter.java
+++ b/services/core/java/com/android/server/am/ActivityStarter.java
@@ -986,8 +986,12 @@
             }
             top.deliverNewIntentLocked(
                     mCallingUid, mStartActivity.intent, mStartActivity.launchedFromPackage);
-            mSupervisor.showNonResizeableDockToastIfNeeded(mStartActivity.task,
-                    preferredLaunchStackId, topStack.mStackId);
+
+            // Don't use mStartActivity.task to show the toast. We're not starting a new activity
+            // but reusing 'top'. Fields in mStartActivity may not be fully initialized.
+            mSupervisor.handleNonResizableTaskIfNeeded(
+                    top.task, preferredLaunchStackId, topStack.mStackId);
+
             return START_DELIVERED_TO_TOP;
         }
 
@@ -1074,7 +1078,7 @@
         }
         mSupervisor.updateUserStackLocked(mStartActivity.userId, mTargetStack);
 
-        mSupervisor.showNonResizeableDockToastIfNeeded(
+        mSupervisor.handleNonResizableTaskIfNeeded(
                 mStartActivity.task, preferredLaunchStackId, mTargetStack.mStackId);
 
         return START_SUCCESS;
@@ -1382,6 +1386,9 @@
             mTargetStack.moveToFront("intentActivityFound");
         }
 
+        mSupervisor.handleNonResizableTaskIfNeeded(intentActivity.task, INVALID_STACK_ID,
+                mTargetStack.mStackId);
+
         // If the caller has requested that the target task be reset, then do so.
         if ((mLaunchFlags & FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) != 0) {
             return mTargetStack.resetTaskIfNeededLocked(intentActivity, mStartActivity);
diff --git a/services/core/java/com/android/server/am/PreBootBroadcaster.java b/services/core/java/com/android/server/am/PreBootBroadcaster.java
index 1825c88..0e192ea 100644
--- a/services/core/java/com/android/server/am/PreBootBroadcaster.java
+++ b/services/core/java/com/android/server/am/PreBootBroadcaster.java
@@ -69,6 +69,12 @@
             return;
         }
 
+        if (!mService.isUserRunning(mUserId, 0)) {
+            Slog.i(TAG, "User " + mUserId + " is no longer running; skipping remaining receivers");
+            onFinished();
+            return;
+        }
+
         final ResolveInfo ri = mTargets.get(mIndex++);
         final ComponentName componentName = ri.activityInfo.getComponentName();
 
diff --git a/services/core/java/com/android/server/am/TaskRecord.java b/services/core/java/com/android/server/am/TaskRecord.java
index e32d1d1..e69c662 100644
--- a/services/core/java/com/android/server/am/TaskRecord.java
+++ b/services/core/java/com/android/server/am/TaskRecord.java
@@ -1447,7 +1447,8 @@
             if (stack == null || StackId.persistTaskBounds(stack.mStackId)) {
                 mLastNonFullscreenBounds = mBounds;
             }
-            mOverrideConfig = calculateOverrideConfig(mTmpRect, insetBounds);
+            mOverrideConfig = calculateOverrideConfig(mTmpRect, insetBounds,
+                    mTmpRect.right != bounds.right, mTmpRect.bottom != bounds.bottom);
         }
 
         if (mFullscreen != oldFullscreen) {
@@ -1457,33 +1458,38 @@
         return !mOverrideConfig.equals(oldConfig) ? mOverrideConfig : null;
     }
 
-    private void subtractNonDecorInsets(Rect inOutBounds, Rect inInsetBounds) {
+    private void subtractNonDecorInsets(Rect inOutBounds, Rect inInsetBounds,
+                                        boolean overrideWidth, boolean overrideHeight) {
         mTmpRect2.set(inInsetBounds);
         mService.mWindowManager.subtractNonDecorInsets(mTmpRect2);
         int leftInset = mTmpRect2.left - inInsetBounds.left;
         int topInset = mTmpRect2.top - inInsetBounds.top;
-        int rightInset = inInsetBounds.right - mTmpRect2.right;
-        int bottomInset = inInsetBounds.bottom - mTmpRect2.bottom;
+        int rightInset = overrideWidth ? 0 : inInsetBounds.right - mTmpRect2.right;
+        int bottomInset = overrideHeight ? 0 : inInsetBounds.bottom - mTmpRect2.bottom;
         inOutBounds.inset(leftInset, topInset, rightInset, bottomInset);
     }
 
-    private void subtractStableInsets(Rect inOutBounds, Rect inInsetBounds) {
+    private void subtractStableInsets(Rect inOutBounds, Rect inInsetBounds,
+                                      boolean overrideWidth, boolean overrideHeight) {
         mTmpRect2.set(inInsetBounds);
         mService.mWindowManager.subtractStableInsets(mTmpRect2);
         int leftInset = mTmpRect2.left - inInsetBounds.left;
         int topInset = mTmpRect2.top - inInsetBounds.top;
-        int rightInset = inInsetBounds.right - mTmpRect2.right;
-        int bottomInset = inInsetBounds.bottom - mTmpRect2.bottom;
+        int rightInset = overrideWidth ? 0 : inInsetBounds.right - mTmpRect2.right;
+        int bottomInset = overrideHeight ? 0 : inInsetBounds.bottom - mTmpRect2.bottom;
         inOutBounds.inset(leftInset, topInset, rightInset, bottomInset);
     }
 
-    private Configuration calculateOverrideConfig(Rect bounds, Rect insetBounds) {
+    private Configuration calculateOverrideConfig(Rect bounds, Rect insetBounds,
+                                                  boolean overrideWidth, boolean overrideHeight) {
         mTmpNonDecorBounds.set(bounds);
         mTmpStableBounds.set(bounds);
         subtractNonDecorInsets(
-                mTmpNonDecorBounds, insetBounds != null ? insetBounds : bounds);
+                mTmpNonDecorBounds, insetBounds != null ? insetBounds : bounds,
+                overrideWidth, overrideHeight);
         subtractStableInsets(
-                mTmpStableBounds, insetBounds != null ? insetBounds : bounds);
+                mTmpStableBounds, insetBounds != null ? insetBounds : bounds,
+                overrideWidth, overrideHeight);
 
         // For calculating screenWidthDp, screenWidthDp, we use the stable inset screen area,
         // i.e. the screen area without the system bars.
diff --git a/services/core/java/com/android/server/am/UserController.java b/services/core/java/com/android/server/am/UserController.java
index bea26c7..5ebb9a7 100644
--- a/services/core/java/com/android/server/am/UserController.java
+++ b/services/core/java/com/android/server/am/UserController.java
@@ -278,6 +278,31 @@
                 // Dispatch unlocked to system services
                 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_UNLOCK_MSG, userId, 0));
 
+                // Dispatch unlocked to external apps
+                final Intent unlockedIntent = new Intent(Intent.ACTION_USER_UNLOCKED);
+                unlockedIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
+                unlockedIntent.addFlags(
+                        Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_FOREGROUND);
+                mService.broadcastIntentLocked(null, null, unlockedIntent, null, null, 0, null,
+                        null, null, AppOpsManager.OP_NONE, null, false, false, MY_PID, SYSTEM_UID,
+                        userId);
+
+                if (getUserInfo(userId).isManagedProfile()) {
+                    UserInfo parent = getUserManager().getProfileParent(userId);
+                    if (parent != null) {
+                        final Intent profileUnlockedIntent = new Intent(
+                                Intent.ACTION_MANAGED_PROFILE_UNLOCKED);
+                        profileUnlockedIntent.putExtra(Intent.EXTRA_USER, UserHandle.of(userId));
+                        profileUnlockedIntent.addFlags(
+                                Intent.FLAG_RECEIVER_REGISTERED_ONLY
+                                | Intent.FLAG_RECEIVER_FOREGROUND);
+                        mService.broadcastIntentLocked(null, null, profileUnlockedIntent,
+                                null, null, 0, null, null, null, AppOpsManager.OP_NONE,
+                                null, false, false, MY_PID, SYSTEM_UID,
+                                parent.id);
+                    }
+                }
+
                 // Send PRE_BOOT broadcasts if fingerprint changed
                 final UserInfo info = getUserInfo(userId);
                 if (!Objects.equals(info.lastLoggedInFingerprint, Build.FINGERPRINT)) {
@@ -320,31 +345,6 @@
                 // Remember that we logged in
                 mUserManager.onUserLoggedIn(userId);
 
-                // Dispatch unlocked to external apps
-                final Intent unlockedIntent = new Intent(Intent.ACTION_USER_UNLOCKED);
-                unlockedIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
-                unlockedIntent.addFlags(
-                        Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_FOREGROUND);
-                mService.broadcastIntentLocked(null, null, unlockedIntent, null, null, 0, null,
-                        null, null, AppOpsManager.OP_NONE, null, false, false, MY_PID, SYSTEM_UID,
-                        userId);
-
-                if (getUserInfo(userId).isManagedProfile()) {
-                    UserInfo parent = getUserManager().getProfileParent(userId);
-                    if (parent != null) {
-                        final Intent profileUnlockedIntent = new Intent(
-                                Intent.ACTION_MANAGED_PROFILE_UNLOCKED);
-                        profileUnlockedIntent.putExtra(Intent.EXTRA_USER, UserHandle.of(userId));
-                        profileUnlockedIntent.addFlags(
-                                Intent.FLAG_RECEIVER_REGISTERED_ONLY
-                                | Intent.FLAG_RECEIVER_FOREGROUND);
-                        mService.broadcastIntentLocked(null, null, profileUnlockedIntent,
-                                null, null, 0, null, null, null, AppOpsManager.OP_NONE,
-                                null, false, false, MY_PID, SYSTEM_UID,
-                                parent.id);
-                    }
-                }
-
                 final Intent bootIntent = new Intent(Intent.ACTION_BOOT_COMPLETED, null);
                 bootIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
                 bootIntent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT
@@ -893,8 +893,9 @@
     boolean unlockUserCleared(final int userId, byte[] token, byte[] secret,
             ProgressReporter progress) {
         synchronized (mService) {
-            // Bail if already running unlocked
+            // Bail if already running unlocked, or if not running at all
             final UserState uss = mStartedUsers.get(userId);
+            if (uss == null) return false;
             switch (uss.state) {
                 case STATE_RUNNING_UNLOCKING:
                 case STATE_RUNNING_UNLOCKED:
diff --git a/services/core/java/com/android/server/audio/AudioService.java b/services/core/java/com/android/server/audio/AudioService.java
index f471af6..a6dfab0 100644
--- a/services/core/java/com/android/server/audio/AudioService.java
+++ b/services/core/java/com/android/server/audio/AudioService.java
@@ -1290,7 +1290,7 @@
             // Check if the ringer mode handles this adjustment. If it does we don't
             // need to adjust the volume further.
             final int result = checkForRingerModeChange(aliasIndex, direction, step,
-                    streamState.mIsMuted);
+                    streamState.mIsMuted, callingPackage, flags);
             adjustVolume = (result & FLAG_ADJUST_VOLUME) != 0;
             // If suppressing a volume adjustment in silent mode, display the UI hint
             if ((result & AudioManager.FLAG_SHOW_SILENT_HINT) != 0) {
@@ -1302,8 +1302,7 @@
             }
         }
         // If the ringermode is suppressing media, prevent changes
-        if (streamTypeAlias == AudioSystem.STREAM_MUSIC
-                && (mRingerModeMutedStreams & (1 << AudioSystem.STREAM_MUSIC)) != 0) {
+        if (!volumeAdjustmentAllowedByDnd(streamTypeAlias, flags)) {
             adjustVolume = false;
         }
         int oldIndex = mStreamStates[streamType].getIndex(device);
@@ -1551,6 +1550,10 @@
             throw new SecurityException("Not allowed to change Do Not Disturb state");
         }
 
+        if (!volumeAdjustmentAllowedByDnd(streamTypeAlias, flags)) {
+            return;
+        }
+
         synchronized (mSafeMediaVolumeState) {
             // reset any pending volume command
             mPendingVolumeCommand = null;
@@ -1601,6 +1604,19 @@
         sendVolumeUpdate(streamType, oldIndex, index, flags);
     }
 
+    // No ringer affected streams can be changed in total silence mode except those that
+    // will cause the device to exit total silence mode.
+    private boolean volumeAdjustmentAllowedByDnd(int streamTypeAlias, int flags) {
+        if (mNm.getZenMode() == Settings.Global.ZEN_MODE_NO_INTERRUPTIONS
+                && isStreamMutedByRingerMode(streamTypeAlias)) {
+            if (!(((flags & AudioManager.FLAG_ALLOW_RINGER_MODES) != 0) ||
+                    (streamTypeAlias == getUiSoundsStreamType()))) {
+                return false;
+            }
+        }
+        return true;
+    }
+
     /** @see AudioManager#forceVolumeControlStream(int) */
     public void forceVolumeControlStream(int streamType, IBinder cb) {
         synchronized(mForceControlStreamLock) {
@@ -3366,7 +3382,8 @@
      * adjusting volume. If so, this will set the proper ringer mode and volume
      * indices on the stream states.
      */
-    private int checkForRingerModeChange(int oldIndex, int direction, int step, boolean isMuted) {
+    private int checkForRingerModeChange(int oldIndex, int direction, int step, boolean isMuted,
+            String caller, int flags) {
         final boolean isTv = mPlatformType == AudioSystem.PLATFORM_TELEVISION;
         int result = FLAG_ADJUST_VOLUME;
         int ringerMode = getRingerModeInternal();
@@ -3455,6 +3472,12 @@
             break;
         }
 
+        if (isAndroidNPlus(caller) && wouldToggleZenMode(ringerMode)
+                && !mNm.isNotificationPolicyAccessGrantedForPackage(caller)
+                && (flags & AudioManager.FLAG_FROM_KEY) == 0) {
+            throw new SecurityException("Not allowed to change Do Not Disturb state");
+        }
+
         setRingerMode(ringerMode, TAG + ".checkForRingerModeChange", false /*external*/);
 
         mPrevVolDirection = direction;
@@ -3954,25 +3977,16 @@
 
         public void applyAllVolumes() {
             synchronized (VolumeStreamState.class) {
-                // apply default volume first: by convention this will reset all
-                // devices volumes in audio policy manager to the supplied value
+                // apply device specific volumes first
                 int index;
-                if (mIsMuted) {
-                    index = 0;
-                } else {
-                    index = (getIndex(AudioSystem.DEVICE_OUT_DEFAULT) + 5)/10;
-                }
-                AudioSystem.setStreamVolumeIndex(mStreamType, index, AudioSystem.DEVICE_OUT_DEFAULT);
-                // then apply device specific volumes
                 for (int i = 0; i < mIndexMap.size(); i++) {
-                    int device = mIndexMap.keyAt(i);
+                    final int device = mIndexMap.keyAt(i);
                     if (device != AudioSystem.DEVICE_OUT_DEFAULT) {
                         if (mIsMuted) {
                             index = 0;
                         } else if (((device & AudioSystem.DEVICE_OUT_ALL_A2DP) != 0 &&
                                 mAvrcpAbsVolSupported)
-                                    || ((device & mFullVolumeDevices) != 0))
-                        {
+                                    || ((device & mFullVolumeDevices) != 0)) {
                             index = (mIndexMax + 5)/10;
                         } else {
                             index = (mIndexMap.valueAt(i) + 5)/10;
@@ -3980,6 +3994,15 @@
                         AudioSystem.setStreamVolumeIndex(mStreamType, index, device);
                     }
                 }
+                // apply default volume last: by convention , default device volume will be used
+                // by audio policy manager if no explicit volume is present for a given device type
+                if (mIsMuted) {
+                    index = 0;
+                } else {
+                    index = (getIndex(AudioSystem.DEVICE_OUT_DEFAULT) + 5)/10;
+                }
+                AudioSystem.setStreamVolumeIndex(
+                        mStreamType, index, AudioSystem.DEVICE_OUT_DEFAULT);
             }
         }
 
diff --git a/services/core/java/com/android/server/camera/CameraService.java b/services/core/java/com/android/server/camera/CameraService.java
index cd8eb4e..7d9adf2 100644
--- a/services/core/java/com/android/server/camera/CameraService.java
+++ b/services/core/java/com/android/server/camera/CameraService.java
@@ -15,32 +15,28 @@
  */
 package com.android.server.camera;
 
-import android.app.ActivityManager;
 import android.content.BroadcastReceiver;
 import android.content.Context;
 import android.content.Intent;
 import android.content.IntentFilter;
-import android.content.pm.UserInfo;
 import android.hardware.ICameraService;
 import android.hardware.ICameraServiceProxy;
 import android.nfc.INfcAdapter;
+import android.os.Binder;
 import android.os.Handler;
 import android.os.IBinder;
-import android.os.Binder;
 import android.os.Message;
 import android.os.Process;
 import android.os.RemoteException;
-import android.os.UserManager;
 import android.os.SystemProperties;
-import android.util.Slog;
+import android.os.UserManager;
 import android.util.ArraySet;
+import android.util.Slog;
 
 import com.android.server.ServiceThread;
 import com.android.server.SystemService;
 
 import java.util.Collection;
-import java.util.HashSet;
-import java.util.List;
 import java.util.Set;
 
 /**
@@ -225,11 +221,11 @@
     }
 
     private Set<Integer> getEnabledUserHandles(int currentUserHandle) {
-        List<UserInfo> userProfiles = mUserManager.getEnabledProfiles(currentUserHandle);
-        Set<Integer> handles = new HashSet<>(userProfiles.size());
+        int[] userProfiles = mUserManager.getEnabledProfileIds(currentUserHandle);
+        Set<Integer> handles = new ArraySet<>(userProfiles.length);
 
-        for (UserInfo i : userProfiles) {
-            handles.add(i.id);
+        for (int id : userProfiles) {
+            handles.add(id);
         }
 
         return handles;
diff --git a/services/core/java/com/android/server/connectivity/Tethering.java b/services/core/java/com/android/server/connectivity/Tethering.java
index 2cba93fd..79b5978 100644
--- a/services/core/java/com/android/server/connectivity/Tethering.java
+++ b/services/core/java/com/android/server/connectivity/Tethering.java
@@ -57,12 +57,16 @@
 import android.provider.Settings;
 import android.telephony.CarrierConfigManager;
 import android.telephony.TelephonyManager;
+import android.text.TextUtils;
 import android.util.Log;
+import android.util.SparseArray;
 
 import com.android.internal.telephony.IccCardConstants;
 import com.android.internal.telephony.TelephonyIntents;
 import com.android.internal.util.IState;
 import com.android.internal.util.IndentingPrintWriter;
+import com.android.internal.util.MessageUtils;
+import com.android.internal.util.Protocol;
 import com.android.internal.util.State;
 import com.android.internal.util.StateMachine;
 import com.android.server.IoThread;
@@ -95,6 +99,12 @@
     private final static boolean DBG = false;
     private final static boolean VDBG = false;
 
+    private static final Class[] messageClasses = {
+            Tethering.class, TetherMasterSM.class, TetherInterfaceSM.class
+    };
+    private static final SparseArray<String> sMagicDecoderRing =
+            MessageUtils.findMessageNames(messageClasses);
+
     // TODO - remove both of these - should be part of interface inspection/selection stuff
     private String[] mTetherableUsbRegexs;
     private String[] mTetherableWifiRegexs;
@@ -235,6 +245,8 @@
 
     @Override
     public void interfaceStatusChanged(String iface, boolean up) {
+        // Never called directly: only called from interfaceLinkStateChanged.
+        // See NetlinkHandler.cpp:71.
         if (VDBG) Log.d(TAG, "interfaceStatusChanged " + iface + ", " + up);
         boolean found = false;
         boolean usb = false;
@@ -274,7 +286,6 @@
 
     @Override
     public void interfaceLinkStateChanged(String iface, boolean up) {
-        if (VDBG) Log.d(TAG, "interfaceLinkStateChanged " + iface + ", " + up);
         interfaceStatusChanged(iface, up);
     }
 
@@ -660,8 +671,11 @@
                 erroredList);
         mContext.sendStickyBroadcastAsUser(broadcast, UserHandle.ALL);
         if (DBG) {
-            Log.d(TAG, "sendTetherStateChangedBroadcast " + availableList.size() + ", " +
-                    activeList.size() + ", " + erroredList.size());
+            Log.d(TAG, String.format(
+                    "sendTetherStateChangedBroadcast avail=[%s] active=[%s] error=[%s]",
+                    TextUtils.join(",", availableList),
+                    TextUtils.join(",", activeList),
+                    TextUtils.join(",", erroredList)));
         }
 
         if (usbTethered) {
@@ -989,31 +1003,39 @@
         return retVal;
     }
 
+    private void maybeLogMessage(State state, int what) {
+        if (DBG) {
+            Log.d(TAG, state.getName() + " got " +
+                    sMagicDecoderRing.get(what, Integer.toString(what)));
+        }
+    }
+
     class TetherInterfaceSM extends StateMachine {
+        private static final int BASE_IFACE              = Protocol.BASE_TETHERING + 100;
         // notification from the master SM that it's not in tether mode
-        static final int CMD_TETHER_MODE_DEAD            =  1;
+        static final int CMD_TETHER_MODE_DEAD            = BASE_IFACE + 1;
         // request from the user that it wants to tether
-        static final int CMD_TETHER_REQUESTED            =  2;
+        static final int CMD_TETHER_REQUESTED            = BASE_IFACE + 2;
         // request from the user that it wants to untether
-        static final int CMD_TETHER_UNREQUESTED          =  3;
+        static final int CMD_TETHER_UNREQUESTED          = BASE_IFACE + 3;
         // notification that this interface is down
-        static final int CMD_INTERFACE_DOWN              =  4;
+        static final int CMD_INTERFACE_DOWN              = BASE_IFACE + 4;
         // notification that this interface is up
-        static final int CMD_INTERFACE_UP                =  5;
+        static final int CMD_INTERFACE_UP                = BASE_IFACE + 5;
         // notification from the master SM that it had an error turning on cellular dun
-        static final int CMD_CELL_DUN_ERROR              =  6;
+        static final int CMD_CELL_DUN_ERROR              = BASE_IFACE + 6;
         // notification from the master SM that it had trouble enabling IP Forwarding
-        static final int CMD_IP_FORWARDING_ENABLE_ERROR  =  7;
+        static final int CMD_IP_FORWARDING_ENABLE_ERROR  = BASE_IFACE + 7;
         // notification from the master SM that it had trouble disabling IP Forwarding
-        static final int CMD_IP_FORWARDING_DISABLE_ERROR =  8;
+        static final int CMD_IP_FORWARDING_DISABLE_ERROR = BASE_IFACE + 8;
         // notification from the master SM that it had trouble starting tethering
-        static final int CMD_START_TETHERING_ERROR       =  9;
+        static final int CMD_START_TETHERING_ERROR       = BASE_IFACE + 9;
         // notification from the master SM that it had trouble stopping tethering
-        static final int CMD_STOP_TETHERING_ERROR        = 10;
+        static final int CMD_STOP_TETHERING_ERROR        = BASE_IFACE + 10;
         // notification from the master SM that it had trouble setting the DNS forwarders
-        static final int CMD_SET_DNS_FORWARDERS_ERROR    = 11;
+        static final int CMD_SET_DNS_FORWARDERS_ERROR    = BASE_IFACE + 11;
         // the upstream connection has changed
-        static final int CMD_TETHER_CONNECTION_CHANGED   = 12;
+        static final int CMD_TETHER_CONNECTION_CHANGED   = BASE_IFACE + 12;
 
         private State mDefaultState;
 
@@ -1124,7 +1146,7 @@
 
             @Override
             public boolean processMessage(Message message) {
-                if (DBG) Log.d(TAG, "InitialState.processMessage what=" + message.what);
+                maybeLogMessage(this, message.what);
                 boolean retValue = true;
                 switch (message.what) {
                     case CMD_TETHER_REQUESTED:
@@ -1165,7 +1187,7 @@
             }
             @Override
             public boolean processMessage(Message message) {
-                if (DBG) Log.d(TAG, "StartingState.processMessage what=" + message.what);
+                maybeLogMessage(this, message.what);
                 boolean retValue = true;
                 switch (message.what) {
                     // maybe a parent class?
@@ -1255,7 +1277,7 @@
 
             @Override
             public boolean processMessage(Message message) {
-                if (DBG) Log.d(TAG, "TetheredState.processMessage what=" + message.what);
+                maybeLogMessage(this, message.what);
                 boolean retValue = true;
                 boolean error = false;
                 switch (message.what) {
@@ -1480,18 +1502,19 @@
     }
 
     class TetherMasterSM extends StateMachine {
+        private static final int BASE_MASTER                    = Protocol.BASE_TETHERING;
         // an interface SM has requested Tethering
-        static final int CMD_TETHER_MODE_REQUESTED              = 1;
+        static final int CMD_TETHER_MODE_REQUESTED              = BASE_MASTER + 1;
         // an interface SM has unrequested Tethering
-        static final int CMD_TETHER_MODE_UNREQUESTED            = 2;
+        static final int CMD_TETHER_MODE_UNREQUESTED            = BASE_MASTER + 2;
         // upstream connection change - do the right thing
-        static final int CMD_UPSTREAM_CHANGED                   = 3;
+        static final int CMD_UPSTREAM_CHANGED                   = BASE_MASTER + 3;
         // we don't have a valid upstream conn, check again after a delay
-        static final int CMD_RETRY_UPSTREAM                     = 4;
+        static final int CMD_RETRY_UPSTREAM                     = BASE_MASTER + 4;
         // Events from NetworkCallbacks that we process on the master state
         // machine thread on behalf of the UpstreamNetworkMonitor.
-        static final int EVENT_UPSTREAM_LINKPROPERTIES_CHANGED  = 5;
-        static final int EVENT_UPSTREAM_LOST                    = 6;
+        static final int EVENT_UPSTREAM_LINKPROPERTIES_CHANGED  = BASE_MASTER + 5;
+        static final int EVENT_UPSTREAM_LOST                    = BASE_MASTER + 6;
 
         // This indicates what a timeout event relates to.  A state that
         // sends itself a delayed timeout event and handles incoming timeout events
@@ -1748,7 +1771,7 @@
             }
 
             protected void notifyTetheredOfNewUpstreamIface(String ifaceName) {
-                if (DBG) Log.d(TAG, "notifying tethered with iface =" + ifaceName);
+                if (DBG) Log.d(TAG, "Notifying tethered with upstream=" + ifaceName);
                 mCurrentUpstreamIface = ifaceName;
                 for (TetherInterfaceSM sm : mNotifyList) {
                     sm.sendMessage(TetherInterfaceSM.CMD_TETHER_CONNECTION_CHANGED,
@@ -1862,7 +1885,7 @@
             }
             @Override
             public boolean processMessage(Message message) {
-                if (DBG) Log.d(TAG, "MasterInitialState.processMessage what=" + message.what);
+                maybeLogMessage(this, message.what);
                 boolean retValue = true;
                 switch (message.what) {
                     case CMD_TETHER_MODE_REQUESTED:
@@ -1910,7 +1933,7 @@
             }
             @Override
             public boolean processMessage(Message message) {
-                if (DBG) Log.d(TAG, "TetherModeAliveState.processMessage what=" + message.what);
+                maybeLogMessage(this, message.what);
                 boolean retValue = true;
                 switch (message.what) {
                     case CMD_TETHER_MODE_REQUESTED:
diff --git a/services/core/java/com/android/server/fingerprint/FingerprintService.java b/services/core/java/com/android/server/fingerprint/FingerprintService.java
index 3d8bf51..e3f3849 100644
--- a/services/core/java/com/android/server/fingerprint/FingerprintService.java
+++ b/services/core/java/com/android/server/fingerprint/FingerprintService.java
@@ -541,10 +541,8 @@
         UserManager um = UserManager.get(mContext);
 
         // Allow current user or profiles of the current user...
-        List<UserInfo> profiles = um.getEnabledProfiles(userId);
-        final int n = profiles.size();
-        for (int i = 0; i < n; i++) {
-            if (profiles.get(i).id == userId) {
+        for (int profileId : um.getEnabledProfileIds(userId)) {
+            if (profileId == userId) {
                 return true;
             }
         }
diff --git a/services/core/java/com/android/server/job/controllers/ConnectivityController.java b/services/core/java/com/android/server/job/controllers/ConnectivityController.java
index 5ad8189..be9d800 100644
--- a/services/core/java/com/android/server/job/controllers/ConnectivityController.java
+++ b/services/core/java/com/android/server/job/controllers/ConnectivityController.java
@@ -77,8 +77,10 @@
         if (cs != null) {
             if (cs.getActiveNetworkInfo() != null) {
                 mNetworkConnected = cs.getActiveNetworkInfo().isConnected();
+                mNetworkUnmetered = mNetworkConnected && !cs.isActiveNetworkMetered();
+            } else {
+                mNetworkConnected = mNetworkUnmetered = false;
             }
-            mNetworkUnmetered = mNetworkConnected && !cs.isActiveNetworkMetered();
         }
     }
 
diff --git a/services/core/java/com/android/server/location/GnssLocationProvider.java b/services/core/java/com/android/server/location/GnssLocationProvider.java
index 6b916be..d80dc3b 100644
--- a/services/core/java/com/android/server/location/GnssLocationProvider.java
+++ b/services/core/java/com/android/server/location/GnssLocationProvider.java
@@ -40,6 +40,7 @@
 import android.location.IGnssStatusProvider;
 import android.location.GnssMeasurementsEvent;
 import android.location.GnssNavigationMessage;
+import android.location.GnssNavigationMessageEvent;
 import android.location.IGpsGeofenceHardware;
 import android.location.ILocationManager;
 import android.location.INetInitiatedListener;
@@ -1667,6 +1668,16 @@
     }
 
     /**
+     * called from native code - GPS navigation message callback
+     */
+    private void reportNavigationMessage(GnssNavigationMessageEvent event) {
+        if (event != null) {
+            mGnssNavigationMessageProvider
+                    .onNavigationMessageAvailable(event.getNavigationMessage());
+        }
+    }
+
+    /**
      * called from native code to inform us what the GPS engine capabilities are
      */
     private void setEngineCapabilities(int capabilities) {
diff --git a/services/core/java/com/android/server/media/MediaSessionService.java b/services/core/java/com/android/server/media/MediaSessionService.java
index e3c540a..a4d2cd2 100644
--- a/services/core/java/com/android/server/media/MediaSessionService.java
+++ b/services/core/java/com/android/server/media/MediaSessionService.java
@@ -962,6 +962,7 @@
                         mKeyEventReceiver.aquireWakeLockLocked();
                     }
                     Intent mediaButtonIntent = new Intent(Intent.ACTION_MEDIA_BUTTON);
+                    mediaButtonIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
                     mediaButtonIntent.putExtra(Intent.EXTRA_KEY_EVENT, keyEvent);
                     try {
                         if (user.mLastMediaButtonReceiver != null) {
@@ -986,6 +987,7 @@
                     }
                     // Fallback to legacy behavior
                     Intent keyIntent = new Intent(Intent.ACTION_MEDIA_BUTTON, null);
+                    keyIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
                     keyIntent.putExtra(Intent.EXTRA_KEY_EVENT, keyEvent);
                     if (needWakeLock) {
                         keyIntent.putExtra(EXTRA_WAKELOCK_ACQUIRED,
diff --git a/services/core/java/com/android/server/net/NetworkIdentitySet.java b/services/core/java/com/android/server/net/NetworkIdentitySet.java
index 68dc715..959a823 100644
--- a/services/core/java/com/android/server/net/NetworkIdentitySet.java
+++ b/services/core/java/com/android/server/net/NetworkIdentitySet.java
@@ -23,6 +23,8 @@
 import java.io.IOException;
 import java.util.HashSet;
 
+import static android.net.ConnectivityManager.TYPE_MOBILE;
+
 /**
  * Identity of a {@code iface}, defined by the set of {@link NetworkIdentity}
  * active on that interface.
@@ -34,6 +36,7 @@
     private static final int VERSION_INIT = 1;
     private static final int VERSION_ADD_ROAMING = 2;
     private static final int VERSION_ADD_NETWORK_ID = 3;
+    private static final int VERSION_ADD_METERED = 4;
 
     public NetworkIdentitySet() {
     }
@@ -61,12 +64,22 @@
                 roaming = false;
             }
 
-            add(new NetworkIdentity(type, subType, subscriberId, networkId, roaming));
+            final boolean metered;
+            if (version >= VERSION_ADD_METERED) {
+                metered = in.readBoolean();
+            } else {
+                // If this is the old data and the type is mobile, treat it as metered. (Note that
+                // if this is a mobile network, TYPE_MOBILE is the only possible type that could be
+                // used.)
+                metered = (type == TYPE_MOBILE);
+            }
+
+            add(new NetworkIdentity(type, subType, subscriberId, networkId, roaming, metered));
         }
     }
 
     public void writeToStream(DataOutputStream out) throws IOException {
-        out.writeInt(VERSION_ADD_NETWORK_ID);
+        out.writeInt(VERSION_ADD_METERED);
         out.writeInt(size());
         for (NetworkIdentity ident : this) {
             out.writeInt(ident.getType());
@@ -74,6 +87,7 @@
             writeOptionalString(out, ident.getSubscriberId());
             writeOptionalString(out, ident.getNetworkId());
             out.writeBoolean(ident.getRoaming());
+            out.writeBoolean(ident.getMetered());
         }
     }
 
diff --git a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
index 612bae2..c248608 100644
--- a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
+++ b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
@@ -940,7 +940,7 @@
             for (int subId : subIds) {
                 final String subscriberId = tele.getSubscriberId(subId);
                 final NetworkIdentity probeIdent = new NetworkIdentity(TYPE_MOBILE,
-                        TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false);
+                        TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false, true);
                 if (template.matches(probeIdent)) {
                     return true;
                 }
@@ -1333,7 +1333,7 @@
     private void ensureActiveMobilePolicyLocked(String subscriberId) {
         // Poke around to see if we already have a policy
         final NetworkIdentity probeIdent = new NetworkIdentity(TYPE_MOBILE,
-                TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false);
+                TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false, true);
         for (int i = mNetworkPolicy.size() - 1; i >= 0; i--) {
             final NetworkTemplate template = mNetworkPolicy.keyAt(i);
             if (template.matches(probeIdent)) {
diff --git a/services/core/java/com/android/server/notification/NotificationManagerService.java b/services/core/java/com/android/server/notification/NotificationManagerService.java
index 99c41ea..9a5988c 100644
--- a/services/core/java/com/android/server/notification/NotificationManagerService.java
+++ b/services/core/java/com/android/server/notification/NotificationManagerService.java
@@ -30,8 +30,11 @@
 import static android.service.notification.NotificationRankerService.REASON_PACKAGE_CHANGED;
 import static android.service.notification.NotificationRankerService.REASON_PACKAGE_SUSPENDED;
 import static android.service.notification.NotificationRankerService.REASON_PROFILE_TURNED_OFF;
+import static android.service.notification.NotificationRankerService.REASON_UNAUTOBUNDLED;
 import static android.service.notification.NotificationRankerService.REASON_USER_STOPPED;
 import static android.service.notification.NotificationListenerService.HINT_HOST_DISABLE_EFFECTS;
+import static android.service.notification.NotificationListenerService.HINT_HOST_DISABLE_NOTIFICATION_EFFECTS;
+import static android.service.notification.NotificationListenerService.HINT_HOST_DISABLE_CALL_EFFECTS;
 import static android.service.notification.NotificationListenerService.SUPPRESSED_EFFECT_SCREEN_OFF;
 import static android.service.notification.NotificationListenerService.SUPPRESSED_EFFECT_SCREEN_ON;
 import static android.service.notification.NotificationListenerService.TRIM_FULL;
@@ -39,8 +42,6 @@
 import static android.service.notification.NotificationListenerService.Ranking.IMPORTANCE_DEFAULT;
 import static android.service.notification.NotificationListenerService.Ranking.IMPORTANCE_NONE;
 import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT;
-import static org.xmlpull.v1.XmlPullParser.END_TAG;
-import static org.xmlpull.v1.XmlPullParser.START_TAG;
 
 import android.Manifest;
 import android.annotation.Nullable;
@@ -97,6 +98,7 @@
 import android.os.UserManager;
 import android.os.Vibrator;
 import android.provider.Settings;
+import android.service.notification.Adjustment;
 import android.service.notification.Condition;
 import android.service.notification.IConditionProvider;
 import android.service.notification.INotificationListener;
@@ -114,6 +116,7 @@
 import android.util.AtomicFile;
 import android.util.Log;
 import android.util.Slog;
+import android.util.SparseArray;
 import android.util.Xml;
 import android.view.accessibility.AccessibilityEvent;
 import android.view.accessibility.AccessibilityManager;
@@ -136,7 +139,6 @@
 
 import libcore.io.IoUtils;
 
-import org.json.JSONArray;
 import org.json.JSONException;
 import org.json.JSONObject;
 import org.xmlpull.v1.XmlPullParser;
@@ -158,7 +160,6 @@
 import java.util.ArrayDeque;
 import java.util.ArrayList;
 import java.util.Arrays;
-import java.util.HashSet;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Map;
@@ -248,8 +249,9 @@
     private String mSoundNotificationKey;
     private String mVibrateNotificationKey;
 
-    private final ArraySet<ManagedServiceInfo> mListenersDisablingEffects = new ArraySet<>();
-    private ComponentName mEffectsSuppressor;
+    private final SparseArray<ArraySet<ManagedServiceInfo>> mListenersDisablingEffects =
+            new SparseArray<ArraySet<ManagedServiceInfo>>();
+    private List<ComponentName> mEffectsSuppressors = new ArrayList<ComponentName>();
     private int mListenerHints;  // right now, all hints are global
     private int mInterruptionFilter = NotificationListenerService.INTERRUPTION_FILTER_UNKNOWN;
 
@@ -263,6 +265,7 @@
             new ArrayList<NotificationRecord>();
     final ArrayMap<String, NotificationRecord> mNotificationsByKey =
             new ArrayMap<String, NotificationRecord>();
+    final ArrayMap<String, String> mAutobundledSummaries = new ArrayMap<>();
     final ArrayList<ToastRecord> mToastQueue = new ArrayList<ToastRecord>();
     final ArrayMap<String, NotificationRecord> mSummaryByGroupKey = new ArrayMap<>();
     final PolicyAccess mPolicyAccess = new PolicyAccess();
@@ -283,11 +286,6 @@
     private static final String TAG_NOTIFICATION_POLICY = "notification-policy";
     private static final String ATTR_VERSION = "version";
 
-    // Obsolete:  converted if present, but not resaved to disk.
-    private static final String TAG_BLOCKED_PKGS = "blocked-packages";
-    private static final String TAG_PACKAGE = "package";
-    private static final String ATTR_NAME = "name";
-
     private RankingHelper mRankingHelper;
 
     private final UserProfiles mUserProfiles = new UserProfiles();
@@ -1118,23 +1116,112 @@
     }
 
     private void updateListenerHintsLocked() {
-        final int hints = mListenersDisablingEffects.isEmpty() ? 0 : HINT_HOST_DISABLE_EFFECTS;
+        final int hints = calculateHints();
         if (hints == mListenerHints) return;
-        ZenLog.traceListenerHintsChanged(mListenerHints, hints, mListenersDisablingEffects.size());
+        ZenLog.traceListenerHintsChanged(mListenerHints, hints, mEffectsSuppressors.size());
         mListenerHints = hints;
         scheduleListenerHintsChanged(hints);
     }
 
     private void updateEffectsSuppressorLocked() {
-        final ComponentName suppressor = !mListenersDisablingEffects.isEmpty()
-                ? mListenersDisablingEffects.valueAt(0).component : null;
-        if (Objects.equals(suppressor, mEffectsSuppressor)) return;
-        ZenLog.traceEffectsSuppressorChanged(mEffectsSuppressor, suppressor);
-        mEffectsSuppressor = suppressor;
-        mZenModeHelper.setEffectsSuppressed(suppressor != null);
+        final long updatedSuppressedEffects = calculateSuppressedEffects();
+        if (updatedSuppressedEffects == mZenModeHelper.getSuppressedEffects()) return;
+        final List<ComponentName> suppressors = getSuppressors();
+        ZenLog.traceEffectsSuppressorChanged(mEffectsSuppressors, suppressors, updatedSuppressedEffects);
+        mEffectsSuppressors = suppressors;
+        mZenModeHelper.setSuppressedEffects(updatedSuppressedEffects);
         sendRegisteredOnlyBroadcast(NotificationManager.ACTION_EFFECTS_SUPPRESSOR_CHANGED);
     }
 
+    private ArrayList<ComponentName> getSuppressors() {
+        ArrayList<ComponentName> names = new ArrayList<ComponentName>();
+        for (int i = mListenersDisablingEffects.size() - 1; i >= 0; --i) {
+            ArraySet<ManagedServiceInfo> serviceInfoList = mListenersDisablingEffects.valueAt(i);
+
+            for (ManagedServiceInfo info : serviceInfoList) {
+                names.add(info.component);
+            }
+        }
+
+        return names;
+    }
+
+    private boolean removeDisabledHints(ManagedServiceInfo info) {
+        return removeDisabledHints(info, 0);
+    }
+
+    private boolean removeDisabledHints(ManagedServiceInfo info, int hints) {
+        boolean removed = false;
+
+        for (int i = mListenersDisablingEffects.size() - 1; i >= 0; --i) {
+            final int hint = mListenersDisablingEffects.keyAt(i);
+            final ArraySet<ManagedServiceInfo> listeners =
+                    mListenersDisablingEffects.valueAt(i);
+
+            if (hints == 0 || (hint & hints) == hint) {
+                removed = removed || listeners.remove(info);
+            }
+        }
+
+        return removed;
+    }
+
+    private void addDisabledHints(ManagedServiceInfo info, int hints) {
+        if ((hints & HINT_HOST_DISABLE_EFFECTS) != 0) {
+            addDisabledHint(info, HINT_HOST_DISABLE_EFFECTS);
+        }
+
+        if ((hints & HINT_HOST_DISABLE_NOTIFICATION_EFFECTS) != 0) {
+            addDisabledHint(info, HINT_HOST_DISABLE_NOTIFICATION_EFFECTS);
+        }
+
+        if ((hints & HINT_HOST_DISABLE_CALL_EFFECTS) != 0) {
+            addDisabledHint(info, HINT_HOST_DISABLE_CALL_EFFECTS);
+        }
+    }
+
+    private void addDisabledHint(ManagedServiceInfo info, int hint) {
+        if (mListenersDisablingEffects.indexOfKey(hint) < 0) {
+            mListenersDisablingEffects.put(hint, new ArraySet<ManagedServiceInfo>());
+        }
+
+        ArraySet<ManagedServiceInfo> hintListeners = mListenersDisablingEffects.get(hint);
+        hintListeners.add(info);
+    }
+
+    private int calculateHints() {
+        int hints = 0;
+        for (int i = mListenersDisablingEffects.size() - 1; i >= 0; --i) {
+            int hint = mListenersDisablingEffects.keyAt(i);
+            ArraySet<ManagedServiceInfo> serviceInfoList = mListenersDisablingEffects.valueAt(i);
+
+            if (!serviceInfoList.isEmpty()) {
+                hints |= hint;
+            }
+        }
+
+        return hints;
+    }
+
+    private long calculateSuppressedEffects() {
+        int hints = calculateHints();
+        long suppressedEffects = 0;
+
+        if ((hints & HINT_HOST_DISABLE_EFFECTS) != 0) {
+            suppressedEffects |= ZenModeHelper.SUPPRESSED_EFFECT_ALL;
+        }
+
+        if ((hints & HINT_HOST_DISABLE_NOTIFICATION_EFFECTS) != 0) {
+            suppressedEffects |= ZenModeHelper.SUPPRESSED_EFFECT_NOTIFICATIONS;
+        }
+
+        if ((hints & HINT_HOST_DISABLE_CALL_EFFECTS) != 0) {
+            suppressedEffects |= ZenModeHelper.SUPPRESSED_EFFECT_CALLS;
+        }
+
+        return suppressedEffects;
+    }
+
     private void updateInterruptionFilterLocked() {
         int interruptionFilter = mZenModeHelper.getZenModeListenerInterruptionFilter();
         if (interruptionFilter == mInterruptionFilter) return;
@@ -1259,10 +1346,13 @@
             checkCallerIsSystemOrSameApp(pkg);
             userId = ActivityManager.handleIncomingUser(Binder.getCallingPid(),
                     Binder.getCallingUid(), userId, true, false, "cancelNotificationWithTag", pkg);
-            // Don't allow client applications to cancel foreground service notis.
+            // Don't allow client applications to cancel foreground service notis or autobundled
+            // summaries.
             cancelNotification(Binder.getCallingUid(), Binder.getCallingPid(), pkg, tag, id, 0,
-                    Binder.getCallingUid() == Process.SYSTEM_UID
-                            ? 0 : Notification.FLAG_FOREGROUND_SERVICE, false, userId,
+                    (Binder.getCallingUid() == Process.SYSTEM_UID
+                            ? 0 : Notification.FLAG_FOREGROUND_SERVICE)
+                            | (Binder.getCallingUid() == Process.SYSTEM_UID
+                            ? 0 : Notification.FLAG_AUTOGROUP_SUMMARY), false, userId,
                     REASON_APP_CANCEL, null);
         }
 
@@ -1404,7 +1494,9 @@
                 final int N = mNotificationList.size();
                 for (int i = 0; i < N; i++) {
                     final StatusBarNotification sbn = mNotificationList.get(i).sbn;
-                    if (sbn.getPackageName().equals(pkg) && sbn.getUserId() == userId) {
+                    if (sbn.getPackageName().equals(pkg) && sbn.getUserId() == userId
+                            && (sbn.getNotification().flags
+                            & Notification.FLAG_AUTOGROUP_SUMMARY) == 0) {
                         // We could pass back a cloneLight() but clients might get confused and
                         // try to send this thing back to notify() again, which would not work
                         // very well.
@@ -1519,7 +1611,8 @@
             checkCallerIsSystemOrSameApp(component.getPackageName());
             long identity = Binder.clearCallingIdentity();
             try {
-                ManagedServices manager = mRankerServices.isComponentEnabledForCurrentProfiles(component)
+                ManagedServices manager =
+                        mRankerServices.isComponentEnabledForCurrentProfiles(component)
                         ? mRankerServices
                         : mListeners;
                 manager.setComponentState(component, true);
@@ -1651,11 +1744,14 @@
             try {
                 synchronized (mNotificationList) {
                     final ManagedServiceInfo info = mListeners.checkServiceTokenLocked(token);
-                    final boolean disableEffects = (hints & HINT_HOST_DISABLE_EFFECTS) != 0;
+                    final int disableEffectsMask = HINT_HOST_DISABLE_EFFECTS
+                            | HINT_HOST_DISABLE_NOTIFICATION_EFFECTS
+                            | HINT_HOST_DISABLE_CALL_EFFECTS;
+                    final boolean disableEffects = (hints & disableEffectsMask) != 0;
                     if (disableEffects) {
-                        mListenersDisablingEffects.add(info);
+                        addDisabledHints(info, hints);
                     } else {
-                        mListenersDisablingEffects.remove(info);
+                        removeDisabledHints(info, hints);
                     }
                     updateListenerHintsLocked();
                     updateEffectsSuppressorLocked();
@@ -1913,7 +2009,7 @@
         @Override
         public ComponentName getEffectsSuppressor() {
             enforceSystemOrSystemUIOrVolume("INotificationManager.getEffectsSuppressor");
-            return mEffectsSuppressor;
+            return !mEffectsSuppressors.isEmpty() ? mEffectsSuppressors.get(0) : null;
         }
 
         @Override
@@ -2035,25 +2131,123 @@
         }
 
         @Override
-        public void setImportanceFromRankerService(INotificationListener token, String key,
-                int importance, CharSequence explanation) throws RemoteException {
-            if (importance == IMPORTANCE_NONE) {
-                throw new IllegalArgumentException("blocking not allowed: key=" + key);
-            }
+        public void applyAdjustmentFromRankerService(INotificationListener token,
+                Adjustment adjustment) throws RemoteException {
             final long identity = Binder.clearCallingIdentity();
             try {
                 synchronized (mNotificationList) {
                     mRankerServices.checkServiceTokenLocked(token);
-                    NotificationRecord n = mNotificationsByKey.get(key);
-                    n.setImportance(importance, explanation);
-                    mRankingHandler.requestSort();
+                    applyAdjustmentLocked(adjustment);
                 }
+                maybeAddAutobundleSummary(adjustment);
+                mRankingHandler.requestSort();
+            } finally {
+                Binder.restoreCallingIdentity(identity);
+            }
+        }
+
+        @Override
+        public void applyAdjustmentsFromRankerService(INotificationListener token,
+                List<Adjustment> adjustments) throws RemoteException {
+
+            final long identity = Binder.clearCallingIdentity();
+            try {
+                synchronized (mNotificationList) {
+                    mRankerServices.checkServiceTokenLocked(token);
+                    for (Adjustment adjustment : adjustments) {
+                        applyAdjustmentLocked(adjustment);
+                    }
+                }
+                for (Adjustment adjustment : adjustments) {
+                    maybeAddAutobundleSummary(adjustment);
+                }
+                mRankingHandler.requestSort();
             } finally {
                 Binder.restoreCallingIdentity(identity);
             }
         }
     };
 
+    private void applyAdjustmentLocked(Adjustment adjustment) {
+        maybeClearAutobundleSummaryLocked(adjustment);
+        NotificationRecord n = mNotificationsByKey.get(adjustment.getKey());
+        if (n == null) {
+            return;
+        }
+        if (adjustment.getImportance() != IMPORTANCE_NONE) {
+            n.setImportance(adjustment.getImportance(), adjustment.getExplanation());
+        }
+        if (adjustment.getSignals() != null) {
+            Bundle.setDefusable(adjustment.getSignals(), true);
+            n.sbn.setOverrideGroupKey(adjustment.getSignals().getString(
+                    Adjustment.GROUP_KEY_OVERRIDE_KEY, null));
+        }
+    }
+
+    // Clears the 'fake' auto-bunding summary.
+    private void maybeClearAutobundleSummaryLocked(Adjustment adjustment) {
+        if (adjustment.getSignals() != null
+                && adjustment.getSignals().containsKey(Adjustment.NEEDS_AUTOGROUPING_KEY)
+                && !adjustment.getSignals().getBoolean(Adjustment.NEEDS_AUTOGROUPING_KEY, false)) {
+            if (mAutobundledSummaries.containsKey(adjustment.getPackage())) {
+                // Clear summary.
+                final NotificationRecord removed = mNotificationsByKey.get(
+                        mAutobundledSummaries.remove(adjustment.getPackage()));
+                if (removed != null) {
+                    mNotificationList.remove(removed);
+                    cancelNotificationLocked(removed, false, REASON_UNAUTOBUNDLED);
+                }
+            }
+        }
+    }
+
+    // Posts a 'fake' summary for a package that has exceeded the solo-notification limit.
+    private void maybeAddAutobundleSummary(Adjustment adjustment) {
+        if (adjustment.getSignals() != null
+                && adjustment.getSignals().getBoolean(Adjustment.NEEDS_AUTOGROUPING_KEY, false)) {
+            final String newAutoBundleKey =
+                    adjustment.getSignals().getString(Adjustment.GROUP_KEY_OVERRIDE_KEY, null);
+            int userId = -1;
+            NotificationRecord summaryRecord = null;
+            synchronized (mNotificationList) {
+                if (!mAutobundledSummaries.containsKey(adjustment.getPackage())
+                        && newAutoBundleKey != null) {
+                    // Add summary
+                    final StatusBarNotification adjustedSbn
+                            = mNotificationsByKey.get(adjustment.getKey()).sbn;
+
+                    final ApplicationInfo appInfo =
+                            adjustedSbn.getNotification().extras.getParcelable(
+                                    Notification.EXTRA_BUILDER_APPLICATION_INFO);
+                    final Bundle extras = new Bundle();
+                    extras.putParcelable(Notification.EXTRA_BUILDER_APPLICATION_INFO, appInfo);
+                    final Notification summaryNotification =
+                            new Notification.Builder(getContext()).setSmallIcon(
+                                    adjustedSbn.getNotification().getSmallIcon())
+                                    .setGroupSummary(true)
+                                    .setGroup(newAutoBundleKey)
+                                    .setFlag(Notification.FLAG_AUTOGROUP_SUMMARY, true)
+                                    .setFlag(Notification.FLAG_GROUP_SUMMARY, true)
+                                    .build();
+                    summaryNotification.extras.putAll(extras);
+                    final StatusBarNotification summarySbn =
+                            new StatusBarNotification(adjustedSbn.getPackageName(),
+                                    adjustedSbn.getOpPkg(),
+                                    Integer.MAX_VALUE, Adjustment.GROUP_KEY_OVERRIDE_KEY,
+                                    adjustedSbn.getUid(), adjustedSbn.getInitialPid(),
+                                    summaryNotification, adjustedSbn.getUser(), newAutoBundleKey,
+                                    System.currentTimeMillis());
+                    summaryRecord = new NotificationRecord(getContext(), summarySbn);
+                    mAutobundledSummaries.put(adjustment.getPackage(), summarySbn.getKey());
+                    userId = adjustedSbn.getUser().getIdentifier();
+                }
+            }
+            if (summaryRecord != null) {
+                mHandler.post(new EnqueueNotificationRunnable(userId, summaryRecord));
+            }
+        }
+    }
+
     private String disableNotificationEffects(NotificationRecord record) {
         if (mDisableNotificationEffects) {
             return "booleanState";
@@ -2175,9 +2369,19 @@
                 pw.print("    mListenersDisablingEffects: (");
                 N = mListenersDisablingEffects.size();
                 for (int i = 0; i < N; i++) {
-                    final ManagedServiceInfo listener = mListenersDisablingEffects.valueAt(i);
-                    if (i > 0) pw.print(',');
-                    pw.print(listener.component);
+                    final int hint = mListenersDisablingEffects.keyAt(i);
+                    if (i > 0) pw.print(';');
+                    pw.print("hint[" + hint + "]:");
+
+                    final ArraySet<ManagedServiceInfo> listeners =
+                            mListenersDisablingEffects.valueAt(i);
+                    final int listenerSize = listeners.size();
+
+                    for (int j = 0; j < listenerSize; j++) {
+                        if (i > 0) pw.print(',');
+                        final ManagedServiceInfo listener = listeners.valueAt(i);
+                        pw.print(listener.component);
+                    }
                 }
                 pw.println(')');
                 pw.println("\n  mRankerServicePackageName: " + mRankerServicePackageName);
@@ -2253,6 +2457,17 @@
                 callingUid, incomingUserId, true, false, "enqueueNotification", pkg);
         final UserHandle user = new UserHandle(userId);
 
+        // Fix the notification as best we can.
+        try {
+            final ApplicationInfo ai = getContext().getPackageManager().getApplicationInfoAsUser(
+                    pkg, PackageManager.MATCH_DEBUG_TRIAGED_MISSING,
+                    (userId == UserHandle.USER_ALL) ? UserHandle.USER_SYSTEM : userId);
+            Notification.addFieldsFromContext(ai, userId, notification);
+        } catch (NameNotFoundException e) {
+            Slog.e(TAG, "Cannot create a context for sending app", e);
+            return;
+        }
+
         // Limit the number of notifications that any given package except the android
         // package or a registered listener can enqueue.  Prevents DOS attacks and deals with leaks.
         if (!isSystemNotification && !isNotificationFromListener) {
@@ -2328,18 +2543,13 @@
                 // Handle grouped notifications and bail out early if we
                 // can to avoid extracting signals.
                 handleGroupedNotificationLocked(r, old, callingUid, callingPid);
-                boolean ignoreNotification =
-                        removeUnusedGroupedNotificationLocked(r, old, callingUid, callingPid);
-                if (DBG) Slog.d(TAG, "ignoreNotification is " + ignoreNotification);
 
                 // This conditional is a dirty hack to limit the logging done on
                 //     behalf of the download manager without affecting other apps.
                 if (!pkg.equals("com.android.providers.downloads")
                         || Log.isLoggable("DownloadManager", Log.VERBOSE)) {
                     int enqueueStatus = EVENTLOG_ENQUEUE_STATUS_NEW;
-                    if (ignoreNotification) {
-                        enqueueStatus = EVENTLOG_ENQUEUE_STATUS_IGNORED;
-                    } else if (old != null) {
+                    if (old != null) {
                         enqueueStatus = EVENTLOG_ENQUEUE_STATUS_UPDATE;
                     }
                     EventLogTags.writeNotificationEnqueue(callingUid, callingPid,
@@ -2347,10 +2557,6 @@
                             enqueueStatus);
                 }
 
-                if (ignoreNotification) {
-                    return;
-                }
-
                 mRankingHelper.extractSignals(r);
 
                 final boolean isPackageSuspended = isPackageSuspendedForUser(pkg, callingUid);
@@ -2466,58 +2672,6 @@
         }
     }
 
-    /**
-     * Performs group notification optimizations if SysUI is the only active
-     * notification listener and returns whether the given notification should
-     * be ignored.
-     *
-     * <p>Returns true if the given notification is a child of a group with a
-     * summary, which means that SysUI will never show it, and hence the new
-     * notification can be safely ignored. Also cancels any previous instance
-     * of the ignored notification.</p>
-     *
-     * <p>For summaries, cancels all children of that group, as SysUI will
-     * never show them anymore.</p>
-     *
-     * @return true if the given notification can be ignored as an optimization
-     */
-    private boolean removeUnusedGroupedNotificationLocked(NotificationRecord r,
-            NotificationRecord old, int callingUid, int callingPid) {
-        if (!ENABLE_CHILD_NOTIFICATIONS) {
-            // No optimizations are possible if listeners want groups.
-            if (mListeners.notificationGroupsDesired()) {
-                return false;
-            }
-
-            StatusBarNotification sbn = r.sbn;
-            String group = sbn.getGroupKey();
-            boolean isSummary = sbn.getNotification().isGroupSummary();
-            boolean isChild = sbn.getNotification().isGroupChild();
-
-            NotificationRecord summary = mSummaryByGroupKey.get(group);
-            if (isChild && summary != null) {
-                // Child with an active summary -> ignore
-                if (DBG) {
-                    Slog.d(TAG, "Ignoring group child " + sbn.getKey() + " due to existing summary "
-                            + summary.getKey());
-                }
-                // Make sure we don't leave an old version of the notification around.
-                if (old != null) {
-                    if (DBG) {
-                        Slog.d(TAG, "Canceling old version of ignored group child " + sbn.getKey());
-                    }
-                    cancelNotificationLocked(old, false, REASON_GROUP_OPTIMIZATION);
-                }
-                return true;
-            } else if (isSummary) {
-                // Summary -> cancel children
-                cancelGroupChildrenLocked(r, callingUid, callingPid, null,
-                        REASON_GROUP_OPTIMIZATION);
-            }
-        }
-        return false;
-    }
-
     @VisibleForTesting
     void buzzBeepBlinkLocked(NotificationRecord record) {
         boolean buzz = false;
@@ -2857,11 +3011,13 @@
         synchronized (mNotificationList) {
             final int N = mNotificationList.size();
             ArrayList<String> orderBefore = new ArrayList<String>(N);
+            ArrayList<String> groupOverrideBefore = new ArrayList<>(N);
             int[] visibilities = new int[N];
-            int [] importances = new int[N];
+            int[] importances = new int[N];
             for (int i = 0; i < N; i++) {
                 final NotificationRecord r = mNotificationList.get(i);
                 orderBefore.add(r.getKey());
+                groupOverrideBefore.add(r.sbn.getGroupKey());
                 visibilities[i] = r.getPackageVisibilityOverride();
                 importances[i] = r.getImportance();
                 mRankingHelper.extractSignals(r);
@@ -2871,7 +3027,8 @@
                 final NotificationRecord r = mNotificationList.get(i);
                 if (!orderBefore.get(i).equals(r.getKey())
                         || visibilities[i] != r.getPackageVisibilityOverride()
-                        || importances[i] != r.getImportance()) {
+                        || importances[i] != r.getImportance()
+                        || !groupOverrideBefore.get(i).equals(r.sbn.getGroupKey())) {
                     scheduleSendRankingUpdate();
                     return;
                 }
@@ -3070,6 +3227,7 @@
         mLights.remove(canceledKey);
 
         // Record usage stats
+        // TODO: add unbundling stats?
         switch (reason) {
             case REASON_DELEGATE_CANCEL:
             case REASON_DELEGATE_CANCEL_ALL:
@@ -3089,6 +3247,9 @@
         if (groupSummary != null && groupSummary.getKey().equals(r.getKey())) {
             mSummaryByGroupKey.remove(groupKey);
         }
+        if (r.sbn.getKey().equals(mAutobundledSummaries.get(r.sbn.getPackageName()))) {
+            mAutobundledSummaries.remove(r.sbn.getPackageName());
+        }
 
         // Save it for users of getHistoricalNotifications()
         mArchive.record(r.sbn);
@@ -3287,7 +3448,7 @@
         for (int i = N - 1; i >= 0; i--) {
             NotificationRecord childR = mNotificationList.get(i);
             StatusBarNotification childSbn = childR.sbn;
-            if (childR.getNotification().isGroupChild() &&
+            if ((childSbn.isGroup() && !childSbn.getNotification().isGroupSummary()) &&
                     childR.getGroupKey().equals(r.getGroupKey())) {
                 EventLogTags.writeNotificationCancel(callingUid, callingPid, pkg, childSbn.getId(),
                         childSbn.getTag(), userId, 0, 0, reason, listenerName);
@@ -3438,6 +3599,7 @@
         ArrayList<String> keys = new ArrayList<String>(N);
         ArrayList<String> interceptedKeys = new ArrayList<String>(N);
         ArrayList<Integer> importance = new ArrayList<>(N);
+        Bundle overrideGroupKeys = new Bundle();
         Bundle visibilityOverrides = new Bundle();
         Bundle suppressedVisualEffects = new Bundle();
         Bundle explanation = new Bundle();
@@ -3461,6 +3623,7 @@
                     != NotificationListenerService.Ranking.VISIBILITY_NO_OVERRIDE) {
                 visibilityOverrides.putInt(key, record.getPackageVisibilityOverride());
             }
+            overrideGroupKeys.putString(key, record.sbn.getOverrideGroupKey());
         }
         final int M = keys.size();
         String[] keysAr = keys.toArray(new String[M]);
@@ -3470,7 +3633,7 @@
             importanceAr[i] = importance.get(i);
         }
         return new NotificationRankingUpdate(keysAr, interceptedKeysAr, visibilityOverrides,
-                suppressedVisualEffects, importanceAr, explanation);
+                suppressedVisualEffects, importanceAr, explanation, overrideGroupKeys);
     }
 
     private boolean isVisibleToListener(StatusBarNotification sbn, ManagedServiceInfo listener) {
@@ -3645,7 +3808,6 @@
     public class NotificationListeners extends ManagedServices {
 
         private final ArraySet<ManagedServiceInfo> mLightTrimListeners = new ArraySet<>();
-        private boolean mNotificationGroupsDesired;
 
         public NotificationListeners() {
             super(getContext(), mHandler, mNotificationList, mUserProfiles);
@@ -3678,7 +3840,6 @@
             final INotificationListener listener = (INotificationListener) info.service;
             final NotificationRankingUpdate update;
             synchronized (mNotificationList) {
-                updateNotificationGroupsDesiredLocked();
                 update = makeRankingUpdateLocked(info);
             }
             try {
@@ -3690,12 +3851,11 @@
 
         @Override
         protected void onServiceRemovedLocked(ManagedServiceInfo removed) {
-            if (mListenersDisablingEffects.remove(removed)) {
+            if (removeDisabledHints(removed)) {
                 updateListenerHintsLocked();
                 updateEffectsSuppressorLocked();
             }
             mLightTrimListeners.remove(removed);
-            updateNotificationGroupsDesiredLocked();
         }
 
         public void setOnNotificationPostedTrimLocked(ManagedServiceInfo info, int trim) {
@@ -3888,31 +4048,6 @@
             }
             return false;
         }
-
-        /**
-         * Returns whether any of the currently registered listeners wants to receive notification
-         * groups.
-         *
-         * <p>Currently we assume groups are desired by non-SystemUI listeners.</p>
-         */
-        public boolean notificationGroupsDesired() {
-            return mNotificationGroupsDesired;
-        }
-
-        private void updateNotificationGroupsDesiredLocked() {
-            mNotificationGroupsDesired = true;
-            // No listeners, no groups.
-            if (mServices.isEmpty()) {
-                mNotificationGroupsDesired = false;
-                return;
-            }
-            // One listener: Check whether it's SysUI.
-            if (mServices.size() == 1 &&
-                    mServices.get(0).component.getPackageName().equals("com.android.systemui")) {
-                mNotificationGroupsDesired = false;
-                return;
-            }
-        }
     }
 
     public static final class DumpFilter {
diff --git a/services/core/java/com/android/server/notification/NotificationRecord.java b/services/core/java/com/android/server/notification/NotificationRecord.java
index fd893fa..f29970c 100644
--- a/services/core/java/com/android/server/notification/NotificationRecord.java
+++ b/services/core/java/com/android/server/notification/NotificationRecord.java
@@ -24,18 +24,15 @@
 
 import android.app.Notification;
 import android.content.Context;
-import android.content.pm.ApplicationInfo;
 import android.content.pm.PackageManager.NameNotFoundException;
 import android.content.res.Resources;
 import android.graphics.Bitmap;
 import android.graphics.drawable.Icon;
 import android.media.AudioAttributes;
-import android.os.Build;
 import android.os.UserHandle;
 import android.service.notification.NotificationListenerService;
 import android.service.notification.StatusBarNotification;
 import android.util.Log;
-import android.util.Slog;
 
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.server.EventLogTags;
@@ -179,10 +176,7 @@
         mRankingTimeMs = calculateRankingTimeMs(previous.getRankingTimeMs());
         mCreationTimeMs = previous.mCreationTimeMs;
         mVisibleSinceMs = previous.mVisibleSinceMs;
-        mUserImportance = previous.mUserImportance;
-        mImportance = previous.mImportance;
-        mImportanceExplanation = previous.mImportanceExplanation;
-        // Don't copy mGlobalSortKey, recompute it.
+        // Don't copy importance information or mGlobalSortKey, recompute them.
     }
 
     public Notification getNotification() { return sbn.getNotification(); }
diff --git a/services/core/java/com/android/server/notification/ZenLog.java b/services/core/java/com/android/server/notification/ZenLog.java
index c45071b..207bdba 100644
--- a/services/core/java/com/android/server/notification/ZenLog.java
+++ b/services/core/java/com/android/server/notification/ZenLog.java
@@ -31,6 +31,7 @@
 import java.io.PrintWriter;
 import java.text.SimpleDateFormat;
 import java.util.Date;
+import java.util.List;
 
 public class ZenLog {
     private static final String TAG = "ZenLog";
@@ -126,10 +127,11 @@
         append(TYPE_DISABLE_EFFECTS, record.getKey() + "," + reason);
     }
 
-    public static void traceEffectsSuppressorChanged(ComponentName oldSuppressor,
-            ComponentName newSuppressor) {
-        append(TYPE_SUPPRESSOR_CHANGED, componentToString(oldSuppressor) + "->"
-            + componentToString(newSuppressor));
+    public static void traceEffectsSuppressorChanged(List<ComponentName> oldSuppressors,
+            List<ComponentName> newSuppressors, long suppressedEffects) {
+        append(TYPE_SUPPRESSOR_CHANGED, "suppressed effects:" + suppressedEffects + ","
+                + componentListToString(oldSuppressors) + "->"
+                + componentListToString(newSuppressors));
     }
 
     public static void traceListenerHintsChanged(int oldHints, int newHints, int listenerCount) {
@@ -193,6 +195,19 @@
         return component != null ? component.toShortString() : null;
     }
 
+    private static String componentListToString(List<ComponentName> components) {
+        StringBuilder stringBuilder = new StringBuilder();
+
+        for (int i = 0; i < components.size(); ++i) {
+            if (i > 0) {
+                stringBuilder.append(", ");
+            }
+            stringBuilder.append(componentToString(components.get(i)));
+        }
+
+        return stringBuilder.toString();
+    }
+
     private static void append(int type, String msg) {
         synchronized(MSGS) {
             TIMES[sNext] = System.currentTimeMillis();
diff --git a/services/core/java/com/android/server/notification/ZenModeHelper.java b/services/core/java/com/android/server/notification/ZenModeHelper.java
index 5c5c8f8..eb49e9f 100644
--- a/services/core/java/com/android/server/notification/ZenModeHelper.java
+++ b/services/core/java/com/android/server/notification/ZenModeHelper.java
@@ -102,7 +102,12 @@
     private ZenModeConfig mConfig;
     private AudioManagerInternal mAudioManager;
     private PackageManager mPm;
-    private boolean mEffectsSuppressed;
+    private long mSuppressedEffects;
+
+    public static final long SUPPRESSED_EFFECT_NOTIFICATIONS = 1;
+    public static final long SUPPRESSED_EFFECT_CALLS = 1 << 1;
+    public static final long SUPPRESSED_EFFECT_ALL = SUPPRESSED_EFFECT_CALLS
+            | SUPPRESSED_EFFECT_NOTIFICATIONS;
 
     public ZenModeHelper(Context context, Looper looper, ConditionProviders conditionProviders) {
         mContext = context;
@@ -228,12 +233,16 @@
         }
     }
 
-    public void setEffectsSuppressed(boolean effectsSuppressed) {
-        if (mEffectsSuppressed == effectsSuppressed) return;
-        mEffectsSuppressed = effectsSuppressed;
+    public void setSuppressedEffects(long suppressedEffects) {
+        if (mSuppressedEffects == suppressedEffects) return;
+        mSuppressedEffects = suppressedEffects;
         applyRestrictions();
     }
 
+    public long getSuppressedEffects() {
+        return mSuppressedEffects;
+    }
+
     public int getZenMode() {
         return mZenMode;
     }
@@ -484,7 +493,8 @@
         synchronized (mConfig) {
             dump(pw, prefix, "mConfig", mConfig);
         }
-        pw.print(prefix); pw.print("mEffectsSuppressed="); pw.println(mEffectsSuppressed);
+
+        pw.print(prefix); pw.print("mSuppressedEffects="); pw.println(mSuppressedEffects);
         mFiltering.dump(pw, prefix);
         mConditions.dump(pw, prefix);
     }
@@ -708,9 +718,11 @@
         final boolean zen = mZenMode != Global.ZEN_MODE_OFF;
 
         // notification restrictions
-        final boolean muteNotifications = mEffectsSuppressed;
+        final boolean muteNotifications =
+                (mSuppressedEffects & SUPPRESSED_EFFECT_NOTIFICATIONS) != 0;
         // call restrictions
-        final boolean muteCalls = zen && !mConfig.allowCalls && !mConfig.allowRepeatCallers;
+        final boolean muteCalls = zen && !mConfig.allowCalls && !mConfig.allowRepeatCallers
+                || (mSuppressedEffects & SUPPRESSED_EFFECT_CALLS) != 0;
         // total silence restrictions
         final boolean muteEverything = mZenMode == Global.ZEN_MODE_NO_INTERRUPTIONS;
 
diff --git a/services/core/java/com/android/server/pm/BackgroundDexOptService.java b/services/core/java/com/android/server/pm/BackgroundDexOptService.java
index eae2eaa..f6255af 100644
--- a/services/core/java/com/android/server/pm/BackgroundDexOptService.java
+++ b/services/core/java/com/android/server/pm/BackgroundDexOptService.java
@@ -16,6 +16,8 @@
 
 package com.android.server.pm;
 
+import static com.android.server.pm.PackageManagerService.DEBUG_DEXOPT;
+
 import android.app.AlarmManager;
 import android.app.job.JobInfo;
 import android.app.job.JobParameters;
@@ -23,6 +25,9 @@
 import android.app.job.JobService;
 import android.content.ComponentName;
 import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.os.BatteryManager;
 import android.os.ServiceManager;
 import android.util.ArraySet;
 import android.util.Log;
@@ -38,7 +43,9 @@
 
     static final long RETRY_LATENCY = 4 * AlarmManager.INTERVAL_HOUR;
 
-    static final int BACKGROUND_DEXOPT_JOB = 800;
+    static final int JOB_IDLE_OPTIMIZE = 800;
+    static final int JOB_POST_BOOT_UPDATE = 801;
+
     private static ComponentName sDexoptServiceName = new ComponentName(
             "android",
             BackgroundDexOptService.class.getName());
@@ -48,66 +55,193 @@
      */
     static final ArraySet<String> sFailedPackageNames = new ArraySet<String>();
 
-    final AtomicBoolean mIdleTime = new AtomicBoolean(false);
+    /**
+     * Atomics set to true if the JobScheduler requests an abort.
+     */
+    final AtomicBoolean mAbortPostBootUpdate = new AtomicBoolean(false);
+    final AtomicBoolean mAbortIdleOptimization = new AtomicBoolean(false);
+
+    /**
+     * Atomic set to true if one job should exit early because another job was started.
+     */
+    final AtomicBoolean mExitPostBootUpdate = new AtomicBoolean(false);
 
     public static void schedule(Context context) {
         JobScheduler js = (JobScheduler) context.getSystemService(Context.JOB_SCHEDULER_SERVICE);
-        JobInfo job = new JobInfo.Builder(BACKGROUND_DEXOPT_JOB, sDexoptServiceName)
-                .setRequiresDeviceIdle(true)
-                .setRequiresCharging(true)
-                .setPeriodic(TimeUnit.DAYS.toMillis(1))
-                .build();
-        js.schedule(job);
+
+        // Schedule a one-off job which scans installed packages and updates
+        // out-of-date oat files.
+        js.schedule(new JobInfo.Builder(JOB_POST_BOOT_UPDATE, sDexoptServiceName)
+                    .setMinimumLatency(TimeUnit.MINUTES.toMillis(1))
+                    .setOverrideDeadline(TimeUnit.MINUTES.toMillis(1))
+                    .build());
+
+        // Schedule a daily job which scans installed packages and compiles
+        // those with fresh profiling data.
+        js.schedule(new JobInfo.Builder(JOB_IDLE_OPTIMIZE, sDexoptServiceName)
+                    .setRequiresDeviceIdle(true)
+                    .setRequiresCharging(true)
+                    .setPeriodic(TimeUnit.DAYS.toMillis(1))
+                    .build());
+
+        if (DEBUG_DEXOPT) {
+            Log.i(TAG, "Jobs scheduled");
+        }
     }
 
-    @Override
-    public boolean onStartJob(JobParameters params) {
-        Log.i(TAG, "onStartJob");
-        final PackageManagerService pm =
-                (PackageManagerService)ServiceManager.getService("package");
-
-        if (pm.isStorageLow()) {
-            Log.i(TAG, "Low storage, skipping this run");
-            return false;
+    public static void notifyPackageChanged(String packageName) {
+        // The idle maintanance job skips packages which previously failed to
+        // compile. The given package has changed and may successfully compile
+        // now. Remove it from the list of known failing packages.
+        synchronized (sFailedPackageNames) {
+            sFailedPackageNames.remove(packageName);
         }
-        final ArraySet<String> pkgs = pm.getOptimizablePackages();
-        if (pkgs == null || pkgs.isEmpty()) {
-            Log.i(TAG, "No packages to optimize");
+    }
+
+    // Returns the current battery level as a 0-100 integer.
+    private int getBatteryLevel() {
+        IntentFilter filter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);
+        Intent intent = registerReceiver(null, filter);
+        int level = intent.getIntExtra(BatteryManager.EXTRA_LEVEL, -1);
+        int scale = intent.getIntExtra(BatteryManager.EXTRA_SCALE, -1);
+
+        if (level < 0 || scale <= 0) {
+            // Battery data unavailable. This should never happen, so assume the worst.
+            return 0;
+        }
+
+        return (100 * level / scale);
+    }
+
+    private boolean runPostBootUpdate(final JobParameters jobParams,
+            final PackageManagerService pm, final ArraySet<String> pkgs) {
+        if (mExitPostBootUpdate.get()) {
+            // This job has already been superseded. Do not start it.
             return false;
         }
 
-        final JobParameters jobParams = params;
-        mIdleTime.set(true);
-        new Thread("BackgroundDexOptService_DexOpter") {
+        // Load low battery threshold from the system config. This is a 0-100 integer.
+        final int lowBatteryThreshold = getResources().getInteger(
+                com.android.internal.R.integer.config_lowBatteryWarningLevel);
+
+        mAbortPostBootUpdate.set(false);
+        new Thread("BackgroundDexOptService_PostBootUpdate") {
             @Override
             public void run() {
                 for (String pkg : pkgs) {
-                    if (!mIdleTime.get()) {
-                        // Out of the idle state. Stop the compilation.
+                    if (mAbortPostBootUpdate.get()) {
+                        // JobScheduler requested an early abort.
+                        return;
+                    }
+                    if (mExitPostBootUpdate.get()) {
+                        // Different job, which supersedes this one, is running.
+                        break;
+                    }
+                    if (getBatteryLevel() < lowBatteryThreshold) {
+                        // Rather bail than completely drain the battery.
+                        break;
+                    }
+                    if (DEBUG_DEXOPT) {
+                        Log.i(TAG, "Updating package " + pkg);
+                    }
+                    // Update package if needed. Note that there can be no race between concurrent
+                    // jobs because PackageDexOptimizer.performDexOpt is synchronized.
+                    pm.performDexOpt(pkg,
+                            /* instruction set */ null,
+                            /* checkProfiles */ false,
+                            PackageManagerService.REASON_BOOT,
+                            /* force */ false);
+                }
+                // Ran to completion, so we abandon our timeslice and do not reschedule.
+                jobFinished(jobParams, /* reschedule */ false);
+            }
+        }.start();
+        return true;
+    }
+
+    private boolean runIdleOptimization(final JobParameters jobParams,
+            final PackageManagerService pm, final ArraySet<String> pkgs) {
+        // If post-boot update is still running, request that it exits early.
+        mExitPostBootUpdate.set(true);
+
+        mAbortIdleOptimization.set(false);
+        new Thread("BackgroundDexOptService_IdleOptimization") {
+            @Override
+            public void run() {
+                for (String pkg : pkgs) {
+                    if (mAbortIdleOptimization.get()) {
+                        // JobScheduler requested an early abort.
                         return;
                     }
                     if (sFailedPackageNames.contains(pkg)) {
-                        // skip previously failing package
+                        // Skip previously failing package
                         continue;
                     }
-                    if (!pm.performDexOpt(pkg, /* instruction set */ null, /* checkProfiles */ true,
-                            PackageManagerService.REASON_BACKGROUND_DEXOPT, /* force */ false)) {
-                        // there was a problem running dexopt,
-                        // remember this so we do not keep retrying.
+                    // Conservatively add package to the list of failing ones in case performDexOpt
+                    // never returns.
+                    synchronized (sFailedPackageNames) {
                         sFailedPackageNames.add(pkg);
                     }
+                    // Optimize package if needed. Note that there can be no race between
+                    // concurrent jobs because PackageDexOptimizer.performDexOpt is synchronized.
+                    if (pm.performDexOpt(pkg,
+                            /* instruction set */ null,
+                            /* checkProfiles */ true,
+                            PackageManagerService.REASON_BACKGROUND_DEXOPT,
+                            /* force */ false)) {
+                        // Dexopt succeeded, remove package from the list of failing ones.
+                        synchronized (sFailedPackageNames) {
+                            sFailedPackageNames.remove(pkg);
+                        }
+                    }
                 }
-                // ran to completion, so we abandon our timeslice and do not reschedule
-                jobFinished(jobParams, false);
+                // Ran to completion, so we abandon our timeslice and do not reschedule.
+                jobFinished(jobParams, /* reschedule */ false);
             }
         }.start();
         return true;
     }
 
     @Override
+    public boolean onStartJob(JobParameters params) {
+        if (DEBUG_DEXOPT) {
+            Log.i(TAG, "onStartJob");
+        }
+
+        PackageManagerService pm = (PackageManagerService)ServiceManager.getService("package");
+        if (pm.isStorageLow()) {
+            if (DEBUG_DEXOPT) {
+                Log.i(TAG, "Low storage, skipping this run");
+            }
+            return false;
+        }
+
+        final ArraySet<String> pkgs = pm.getOptimizablePackages();
+        if (pkgs == null || pkgs.isEmpty()) {
+            if (DEBUG_DEXOPT) {
+                Log.i(TAG, "No packages to optimize");
+            }
+            return false;
+        }
+
+        if (params.getJobId() == JOB_POST_BOOT_UPDATE) {
+            return runPostBootUpdate(params, pm, pkgs);
+        } else {
+            return runIdleOptimization(params, pm, pkgs);
+        }
+    }
+
+    @Override
     public boolean onStopJob(JobParameters params) {
-        Log.i(TAG, "onIdleStop");
-        mIdleTime.set(false);
+        if (DEBUG_DEXOPT) {
+            Log.i(TAG, "onStopJob");
+        }
+
+        if (params.getJobId() == JOB_POST_BOOT_UPDATE) {
+            mAbortPostBootUpdate.set(true);
+        } else {
+            mAbortIdleOptimization.set(true);
+        }
         return false;
     }
 }
diff --git a/services/core/java/com/android/server/pm/Installer.java b/services/core/java/com/android/server/pm/Installer.java
index 7e25632..a11ee74 100644
--- a/services/core/java/com/android/server/pm/Installer.java
+++ b/services/core/java/com/android/server/pm/Installer.java
@@ -28,6 +28,8 @@
 
 import dalvik.system.VMRuntime;
 
+import java.util.Arrays;
+
 public final class Installer extends SystemService {
     private static final String TAG = "Installer";
 
@@ -90,14 +92,14 @@
         mInstaller.execute("migrate_app_data", uuid, pkgname, userid, flags);
     }
 
-    public void clearAppData(String uuid, String pkgname, int userid, int flags)
+    public void clearAppData(String uuid, String pkgname, int userid, int flags, long ceDataInode)
             throws InstallerException {
-        mInstaller.execute("clear_app_data", uuid, pkgname, userid, flags);
+        mInstaller.execute("clear_app_data", uuid, pkgname, userid, flags, ceDataInode);
     }
 
-    public void destroyAppData(String uuid, String pkgname, int userid, int flags)
+    public void destroyAppData(String uuid, String pkgname, int userid, int flags, long ceDataInode)
             throws InstallerException {
-        mInstaller.execute("destroy_app_data", uuid, pkgname, userid, flags);
+        mInstaller.execute("destroy_app_data", uuid, pkgname, userid, flags, ceDataInode);
     }
 
     public void moveCompleteApp(String from_uuid, String to_uuid, String package_name,
@@ -107,31 +109,26 @@
                 data_app_name, appid, seinfo, targetSdkVersion);
     }
 
-    public void getAppSize(String uuid, String pkgname, int userid, int flags, String apkPath,
-            String libDirPath, String fwdLockApkPath, String asecPath, String[] instructionSets,
-            PackageStats pStats) throws InstallerException {
-        for (String instructionSet : instructionSets) {
-            assertValidInstructionSet(instructionSet);
-        }
-
-        // TODO: Extend getSizeInfo to look at the full subdirectory tree,
-        // not just the first level.
-        // TODO: Extend getSizeInfo to look at *all* instrution sets, not
-        // just the primary.
-        final String rawRes = mInstaller.executeForResult("get_app_size", uuid, pkgname, userid,
-                flags, apkPath, libDirPath, fwdLockApkPath, asecPath, instructionSets[0]);
-        final String res[] = rawRes.split(" ");
-
-        if ((res == null) || (res.length != 5)) {
-            throw new InstallerException("Invalid size result: " + rawRes);
-        }
+    public void getAppSize(String uuid, String pkgname, int userid, int flags, long ceDataInode,
+            String codePath, PackageStats stats) throws InstallerException {
+        final String[] res = mInstaller.execute("get_app_size", uuid, pkgname, userid, flags,
+                ceDataInode, codePath);
         try {
-            pStats.codeSize = Long.parseLong(res[1]);
-            pStats.dataSize = Long.parseLong(res[2]);
-            pStats.cacheSize = Long.parseLong(res[3]);
-            pStats.externalCodeSize = Long.parseLong(res[4]);
-        } catch (NumberFormatException e) {
-            throw new InstallerException("Invalid size result: " + rawRes);
+            stats.codeSize += Long.parseLong(res[1]);
+            stats.dataSize += Long.parseLong(res[2]);
+            stats.cacheSize += Long.parseLong(res[3]);
+        } catch (ArrayIndexOutOfBoundsException | NumberFormatException e) {
+            throw new InstallerException("Invalid size result: " + Arrays.toString(res));
+        }
+    }
+
+    public long getAppDataInode(String uuid, String pkgname, int userid, int flags)
+            throws InstallerException {
+        final String[] res = mInstaller.execute("get_app_data_inode", uuid, pkgname, userid, flags);
+        try {
+            return Long.parseLong(res[1]);
+        } catch (ArrayIndexOutOfBoundsException | NumberFormatException e) {
+            throw new InstallerException("Invalid inode result: " + Arrays.toString(res));
         }
     }
 
diff --git a/services/core/java/com/android/server/pm/LauncherAppsService.java b/services/core/java/com/android/server/pm/LauncherAppsService.java
index 4c18e15..43a0b91 100644
--- a/services/core/java/com/android/server/pm/LauncherAppsService.java
+++ b/services/core/java/com/android/server/pm/LauncherAppsService.java
@@ -147,6 +147,7 @@
         @Override
         public void addOnAppsChangedListener(String callingPackage, IOnAppsChangedListener listener)
                 throws RemoteException {
+            verifyCallingPackage(callingPackage);
             synchronized (mListeners) {
                 if (DEBUG) {
                     Log.d(TAG, "Adding listener from " + Binder.getCallingUserHandle());
@@ -213,8 +214,11 @@
          * Checks if the caller is in the same group as the userToCheck.
          */
         private void ensureInUserProfiles(UserHandle userToCheck, String message) {
+            ensureInUserProfiles(userToCheck.getIdentifier(), message);
+        }
+
+        private void ensureInUserProfiles(int targetUserId, String message) {
             final int callingUserId = injectCallingUserId();
-            final int targetUserId = userToCheck.getIdentifier();
 
             if (targetUserId == callingUserId) return;
 
@@ -253,9 +257,13 @@
          * Checks if the user is enabled.
          */
         private boolean isUserEnabled(UserHandle user) {
+            return isUserEnabled(user.getIdentifier());
+        }
+
+        private boolean isUserEnabled(int userId) {
             long ident = injectClearCallingIdentity();
             try {
-                UserInfo targetUserInfo = mUm.getUserInfo(user.getIdentifier());
+                UserInfo targetUserInfo = mUm.getUserInfo(userId);
                 return targetUserInfo != null && targetUserInfo.isEnabled();
             } finally {
                 injectRestoreCallingIdentity(ident);
@@ -286,7 +294,7 @@
         }
 
         @Override
-        public ResolveInfo resolveActivity(Intent intent, UserHandle user)
+        public ActivityInfo resolveActivity(ComponentName component, UserHandle user)
                 throws RemoteException {
             ensureInUserProfiles(user, "Cannot resolve activity for unrelated profile " + user);
             if (!isUserEnabled(user)) {
@@ -295,11 +303,11 @@
 
             long ident = Binder.clearCallingIdentity();
             try {
-                ResolveInfo app = mPm.resolveActivityAsUser(intent,
+                IPackageManager pm = AppGlobals.getPackageManager();
+                return pm.getActivityInfo(component,
                         PackageManager.MATCH_DIRECT_BOOT_AWARE
                                 | PackageManager.MATCH_DIRECT_BOOT_UNAWARE,
                         user.getIdentifier());
-                return app;
             } finally {
                 Binder.restoreCallingIdentity(ident);
             }
@@ -346,8 +354,12 @@
         }
 
         private void ensureShortcutPermission(@NonNull String callingPackage, UserHandle user) {
+            ensureShortcutPermission(callingPackage, user.getIdentifier());
+        }
+
+        private void ensureShortcutPermission(@NonNull String callingPackage, int userId) {
             verifyCallingPackage(callingPackage);
-            ensureInUserProfiles(user, "Cannot start activity for unrelated profile " + user);
+            ensureInUserProfiles(userId, "Cannot start activity for unrelated profile " + userId);
 
             if (!mShortcutServiceInternal.hasShortcutHostPermission(getCallingUserId(),
                     callingPackage)) {
@@ -357,32 +369,24 @@
 
         @Override
         public ParceledListSlice getShortcuts(String callingPackage, long changedSince,
-                String packageName, ComponentName componentName, int flags, UserHandle user) {
+                String packageName, List shortcutIds, ComponentName componentName, int flags,
+                UserHandle user) {
             ensureShortcutPermission(callingPackage, user);
             if (!isUserEnabled(user)) {
                 return new ParceledListSlice<>(new ArrayList(0));
             }
+            if (shortcutIds != null && packageName == null) {
+                throw new IllegalArgumentException(
+                        "To query by shortcut ID, package name must also be set");
+            }
 
             return new ParceledListSlice<>(
                     mShortcutServiceInternal.getShortcuts(getCallingUserId(),
-                            callingPackage, changedSince, packageName,
+                            callingPackage, changedSince, packageName, shortcutIds,
                             componentName, flags, user.getIdentifier()));
         }
 
         @Override
-        public ParceledListSlice getShortcutInfo(String callingPackage, String packageName,
-                List<String> ids, UserHandle user) {
-            ensureShortcutPermission(callingPackage, user);
-            if (!isUserEnabled(user)) {
-                return new ParceledListSlice<>(new ArrayList(0));
-            }
-
-            return new ParceledListSlice<>(
-                    mShortcutServiceInternal.getShortcutInfo(getCallingUserId(),
-                            callingPackage, packageName, ids, user.getIdentifier()));
-        }
-
-        @Override
         public void pinShortcuts(String callingPackage, String packageName, List<String> ids,
                 UserHandle user) {
             ensureShortcutPermission(callingPackage, user);
@@ -396,27 +400,27 @@
         }
 
         @Override
-        public int getShortcutIconResId(String callingPackage, ShortcutInfo shortcut,
-                UserHandle user) {
-            ensureShortcutPermission(callingPackage, user);
-            if (!isUserEnabled(user)) {
+        public int getShortcutIconResId(String callingPackage, String packageName, String id,
+                int userId) {
+            ensureShortcutPermission(callingPackage, userId);
+            if (!isUserEnabled(userId)) {
                 return 0;
             }
 
             return mShortcutServiceInternal.getShortcutIconResId(getCallingUserId(),
-                    callingPackage, shortcut, user.getIdentifier());
+                    callingPackage, packageName, id, userId);
         }
 
         @Override
-        public ParcelFileDescriptor getShortcutIconFd(String callingPackage, ShortcutInfo shortcut,
-                UserHandle user) {
-            ensureShortcutPermission(callingPackage, user);
-            if (!isUserEnabled(user)) {
+        public ParcelFileDescriptor getShortcutIconFd(String callingPackage,
+                String packageName, String id, int userId) {
+            ensureShortcutPermission(callingPackage, userId);
+            if (!isUserEnabled(userId)) {
                 return null;
             }
 
             return mShortcutServiceInternal.getShortcutIconFd(getCallingUserId(),
-                    callingPackage, shortcut, user.getIdentifier());
+                    callingPackage, packageName, id, userId);
         }
 
         @Override
@@ -428,23 +432,23 @@
 
         @Override
         public boolean startShortcut(String callingPackage, String packageName, String shortcutId,
-                Rect sourceBounds, Bundle startActivityOptions, UserHandle user) {
+                Rect sourceBounds, Bundle startActivityOptions, int userId) {
             verifyCallingPackage(callingPackage);
-            ensureInUserProfiles(user, "Cannot start activity for unrelated profile " + user);
+            ensureInUserProfiles(userId, "Cannot start activity for unrelated profile " + userId);
 
-            if (!isUserEnabled(user)) {
+            if (!isUserEnabled(userId)) {
                 throw new IllegalStateException("Cannot start a shortcut for disabled profile "
-                        + user);
+                        + userId);
             }
 
             // Even without the permission, pinned shortcuts are always launchable.
             if (!mShortcutServiceInternal.isPinnedByCaller(getCallingUserId(),
-                    callingPackage, packageName, shortcutId, user.getIdentifier())) {
-                ensureShortcutPermission(callingPackage, user);
+                    callingPackage, packageName, shortcutId, userId)) {
+                ensureShortcutPermission(callingPackage, userId);
             }
 
             final Intent intent = mShortcutServiceInternal.createShortcutIntent(getCallingUserId(),
-                    callingPackage, packageName, shortcutId, user.getIdentifier());
+                    callingPackage, packageName, shortcutId, userId);
             if (intent == null) {
                 return false;
             }
@@ -455,7 +459,7 @@
 
             final long ident = Binder.clearCallingIdentity();
             try {
-                mContext.startActivityAsUser(intent, startActivityOptions, user);
+                mContext.startActivityAsUser(intent, startActivityOptions, UserHandle.of(userId));
             } finally {
                 Binder.restoreCallingIdentity(ident);
             }
@@ -768,7 +772,8 @@
                     final List<ShortcutInfo> list =
                             mShortcutServiceInternal.getShortcuts(launcherUserId,
                                     cookie.packageName,
-                                    /* changedSince= */ 0, packageName, /* component= */ null,
+                                    /* changedSince= */ 0, packageName, /* shortcutIds=*/ null,
+                                    /* component= */ null,
                                     ShortcutQuery.FLAG_GET_KEY_FIELDS_ONLY
                                     | ShortcutQuery.FLAG_GET_PINNED
                                     | ShortcutQuery.FLAG_GET_DYNAMIC
diff --git a/services/core/java/com/android/server/pm/PackageDexOptimizer.java b/services/core/java/com/android/server/pm/PackageDexOptimizer.java
index d13f472..b3ac05c 100644
--- a/services/core/java/com/android/server/pm/PackageDexOptimizer.java
+++ b/services/core/java/com/android/server/pm/PackageDexOptimizer.java
@@ -53,7 +53,6 @@
     // TODO b/19550105 Remove error codes and use exceptions
     static final int DEX_OPT_SKIPPED = 0;
     static final int DEX_OPT_PERFORMED = 1;
-    static final int DEX_OPT_DEFERRED = 2;
     static final int DEX_OPT_FAILED = -1;
 
     private final Installer mInstaller;
@@ -170,6 +169,8 @@
         final boolean debuggable = (pkg.applicationInfo.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0;
 
         boolean performedDexOpt = false;
+        boolean successfulDexOpt = true;
+
         final String[] dexCodeInstructionSets = getDexCodeInstructionSets(instructionSets);
         for (String dexCodeInstructionSet : dexCodeInstructionSets) {
             for (String path : paths) {
@@ -226,15 +227,20 @@
                     performedDexOpt = true;
                 } catch (InstallerException e) {
                     Slog.w(TAG, "Failed to dexopt", e);
+                    successfulDexOpt = false;
                 }
             }
         }
 
-        // If we've gotten here, we're sure that no error occurred and that we haven't
-        // deferred dex-opt. We've either dex-opted one more paths or instruction sets or
-        // we've skipped all of them because they are up to date. In both cases this
-        // package doesn't need dexopt any longer.
-        return performedDexOpt ? DEX_OPT_PERFORMED : DEX_OPT_SKIPPED;
+        if (successfulDexOpt) {
+            // If we've gotten here, we're sure that no error occurred. We've either
+            // dex-opted one or more paths or instruction sets or we've skipped
+            // all of them because they are up to date. In both cases this package
+            // doesn't need dexopt any longer.
+            return performedDexOpt ? DEX_OPT_PERFORMED : DEX_OPT_SKIPPED;
+        } else {
+            return DEX_OPT_FAILED;
+        }
     }
 
     /**
diff --git a/services/core/java/com/android/server/pm/PackageInstallerService.java b/services/core/java/com/android/server/pm/PackageInstallerService.java
index 928c19f..8368185 100644
--- a/services/core/java/com/android/server/pm/PackageInstallerService.java
+++ b/services/core/java/com/android/server/pm/PackageInstallerService.java
@@ -862,8 +862,12 @@
                 IntentSender statusReceiver, int userId) {
         final int callingUid = Binder.getCallingUid();
         mPm.enforceCrossUserPermission(callingUid, userId, true, true, "uninstall");
+        boolean allowSilentUninstall = true;
         if ((callingUid != Process.SHELL_UID) && (callingUid != Process.ROOT_UID)) {
             mAppOps.checkPackage(callingUid, callerPackageName);
+            final String installerPackageName = mPm.getInstallerPackageName(packageName);
+            allowSilentUninstall = installerPackageName != null
+                    && installerPackageName.equals(callerPackageName);
         }
 
         // Check whether the caller is device owner, in which case we do it silently.
@@ -874,8 +878,8 @@
 
         final PackageDeleteObserverAdapter adapter = new PackageDeleteObserverAdapter(mContext,
                 statusReceiver, packageName, isDeviceOwner, userId);
-        if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DELETE_PACKAGES)
-                == PackageManager.PERMISSION_GRANTED) {
+        if (allowSilentUninstall && mContext.checkCallingOrSelfPermission(
+                android.Manifest.permission.DELETE_PACKAGES) == PackageManager.PERMISSION_GRANTED) {
             // Sweet, call straight through!
             mPm.deletePackage(packageName, adapter.getBinder(), userId, flags);
         } else if (isDeviceOwner) {
@@ -901,7 +905,10 @@
         mContext.enforceCallingOrSelfPermission(android.Manifest.permission.INSTALL_PACKAGES, TAG);
 
         synchronized (mSessions) {
-            mSessions.get(sessionId).setPermissionsResult(accepted);
+            PackageInstallerSession session = mSessions.get(sessionId);
+            if (session != null) {
+                session.setPermissionsResult(accepted);
+            }
         }
     }
 
diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java
index a6fce51..3b07fe1 100644
--- a/services/core/java/com/android/server/pm/PackageManagerService.java
+++ b/services/core/java/com/android/server/pm/PackageManagerService.java
@@ -76,7 +76,6 @@
 import static android.content.pm.PackageManager.PERMISSION_GRANTED;
 import static android.content.pm.PackageParser.PARSE_IS_PRIVILEGED;
 import static android.content.pm.PackageParser.isApkFile;
-import static android.os.Process.FIRST_APPLICATION_UID;
 import static android.os.Process.PACKAGE_INFO_GID;
 import static android.os.Process.SYSTEM_UID;
 import static android.os.Trace.TRACE_TAG_PACKAGE_MANAGER;
@@ -117,7 +116,6 @@
 import android.content.IIntentReceiver;
 import android.content.Intent;
 import android.content.IntentFilter;
-import android.content.IntentFilter.AuthorityEntry;
 import android.content.IntentSender;
 import android.content.IntentSender.SendIntentException;
 import android.content.ServiceConnection;
@@ -150,7 +148,6 @@
 import android.content.pm.PackageManagerInternal;
 import android.content.pm.PackageParser;
 import android.content.pm.PackageParser.ActivityIntentInfo;
-import android.content.pm.PackageParser.IntentInfo;
 import android.content.pm.PackageParser.PackageLite;
 import android.content.pm.PackageParser.PackageParserException;
 import android.content.pm.PackageStats;
@@ -232,6 +229,7 @@
 import com.android.internal.os.InstallerConnection.InstallerException;
 import com.android.internal.os.SomeArgs;
 import com.android.internal.os.Zygote;
+import com.android.internal.telephony.CarrierAppUtils;
 import com.android.internal.util.ArrayUtils;
 import com.android.internal.util.FastPrintWriter;
 import com.android.internal.util.FastXmlSerializer;
@@ -250,6 +248,7 @@
 import com.android.server.pm.Settings.VersionInfo;
 import com.android.server.storage.DeviceStorageMonitorInternal;
 
+import dalvik.system.CloseGuard;
 import dalvik.system.DexFile;
 import dalvik.system.VMRuntime;
 
@@ -301,14 +300,37 @@
 import java.util.concurrent.atomic.AtomicLong;
 
 /**
- * Keep track of all those .apks everywhere.
+ * Keep track of all those APKs everywhere.
+ * <p>
+ * Internally there are two important locks:
+ * <ul>
+ * <li>{@link #mPackages} is used to guard all in-memory parsed package details
+ * and other related state. It is a fine-grained lock that should only be held
+ * momentarily, as it's one of the most contended locks in the system.
+ * <li>{@link #mInstallLock} is used to guard all {@code installd} access, whose
+ * operations typically involve heavy lifting of application data on disk. Since
+ * {@code installd} is single-threaded, and it's operations can often be slow,
+ * this lock should never be acquired while already holding {@link #mPackages}.
+ * Conversely, it's safe to acquire {@link #mPackages} momentarily while already
+ * holding {@link #mInstallLock}.
+ * </ul>
+ * Many internal methods rely on the caller to hold the appropriate locks, and
+ * this contract is expressed through method name suffixes:
+ * <ul>
+ * <li>fooLI(): the caller must hold {@link #mInstallLock}
+ * <li>fooLIF(): the caller must hold {@link #mInstallLock} and the package
+ * being modified must be frozen
+ * <li>fooLPr(): the caller must hold {@link #mPackages} for reading
+ * <li>fooLPw(): the caller must hold {@link #mPackages} for writing
+ * </ul>
+ * <p>
+ * Because this class is very central to the platform's security; please run all
+ * CTS and unit tests whenever making modifications:
  *
- * This is very central to the platform's security; please run the unit
- * tests whenever making modifications here:
- *
-runtest -c android.content.pm.PackageManagerTests frameworks-core
- *
- * {@hide}
+ * <pre>
+ * $ runtest -c android.content.pm.PackageManagerTests frameworks-core
+ * $ cts-tradefed run commandAndExit cts -m AppSecurityTests
+ * </pre>
  */
 public class PackageManagerService extends IPackageManager.Stub {
     static final String TAG = "PackageManager";
@@ -370,6 +392,7 @@
     static final int SCAN_INITIAL = 1<<14;
     static final int SCAN_CHECK_ONLY = 1<<15;
     static final int SCAN_DONT_KILL_APP = 1<<17;
+    static final int SCAN_IGNORE_FROZEN = 1<<18;
 
     static final int REMOVE_CHATTY = 1<<16;
 
@@ -573,7 +596,19 @@
      */
     boolean mPromoteSystemApps;
 
+    @GuardedBy("mPackages")
     final Settings mSettings;
+
+    /**
+     * Set of package names that are currently "frozen", which means active
+     * surgery is being done on the code/data for that package. The platform
+     * will refuse to launch frozen packages to avoid race conditions.
+     *
+     * @see PackageFreezer
+     */
+    @GuardedBy("mPackages")
+    final ArraySet<String> mFrozenPackages = new ArraySet<>();
+
     boolean mRestoredSettings;
 
     // System configuration read by SystemConfig.
@@ -1066,8 +1101,9 @@
             | FLAG_PERMISSION_REVOKE_ON_UPGRADE;
 
     final @Nullable String mRequiredVerifierPackage;
-    final @Nullable String mRequiredInstallerPackage;
+    final @NonNull String mRequiredInstallerPackage;
     final @Nullable String mSetupWizardPackage;
+    final @NonNull String mServicesSystemSharedLibraryPackageName;
 
     private final PackageUsage mPackageUsage = new PackageUsage();
 
@@ -2016,6 +2052,10 @@
         PackageManagerService m = new PackageManagerService(context, installer,
                 factoryTest, onlyCore);
         m.enableSystemUserPackages();
+        // Disable any carrier apps. We do this very early in boot to prevent the apps from being
+        // disabled after already being started.
+        CarrierAppUtils.disableCarrierAppsUntilPrivileged(context.getOpPackageName(), m,
+                UserHandle.USER_SYSTEM);
         ServiceManager.addService("package", m);
         return m;
     }
@@ -2353,8 +2393,9 @@
                     if (!mSettings.isDisabledSystemPackageLPr(ps.name)) {
                         psit.remove();
                         logCriticalInfo(Log.WARN, "System package " + ps.name
-                                + " no longer exists; wiping its data");
-                        removeDataDirsLI(null, ps.name);
+                                + " no longer exists; it's data will be wiped");
+                        // Actual deletion of code and data will be handled by later
+                        // reconciliation step
                     } else {
                         final PackageSetting disabledPs = mSettings.getDisabledSystemPkgLPr(ps.name);
                         if (disabledPs.codePath == null || !disabledPs.codePath.exists()) {
@@ -2366,11 +2407,16 @@
 
             //look for any incomplete package installations
             ArrayList<PackageSetting> deletePkgsList = mSettings.getListOfIncompleteInstallPackagesLPr();
-            //clean up list
-            for(int i = 0; i < deletePkgsList.size(); i++) {
-                //clean up here
-                cleanupInstallFailedPackage(deletePkgsList.get(i));
+            for (int i = 0; i < deletePkgsList.size(); i++) {
+                // Actual deletion of code and data will be handled by later
+                // reconciliation step
+                final String packageName = deletePkgsList.get(i).name;
+                logCriticalInfo(Log.WARN, "Cleaning up incompletely installed app: " + packageName);
+                synchronized (mPackages) {
+                    mSettings.removePackageLPw(packageName);
+                }
             }
+
             //delete tmp files
             deleteTempPackageFiles();
 
@@ -2401,8 +2447,9 @@
                     String msg;
                     if (deletedPkg == null) {
                         msg = "Updated system package " + deletedAppName
-                                + " no longer exists; wiping its data";
-                        removeDataDirsLI(null, deletedAppName);
+                                + " no longer exists; it's data will be wiped";
+                        // Actual deletion of code and data will be handled by later
+                        // reconciliation step
                     } else {
                         msg = "Updated system app + " + deletedAppName
                                 + " no longer present; removing system privileges for "
@@ -2548,7 +2595,7 @@
             } else {
                 storageFlags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
             }
-            reconcileAppsData(StorageManager.UUID_PRIVATE_INTERNAL, UserHandle.USER_SYSTEM,
+            reconcileAppsDataLI(StorageManager.UUID_PRIVATE_INTERNAL, UserHandle.USER_SYSTEM,
                     storageFlags);
 
             // If this is first boot after an OTA, and a normal boot, then
@@ -2558,8 +2605,12 @@
                 for (int i = 0; i < mSettings.mPackages.size(); i++) {
                     final PackageSetting ps = mSettings.mPackages.valueAt(i);
                     if (Objects.equals(StorageManager.UUID_PRIVATE_INTERNAL, ps.volumeUuid)) {
-                        deleteCodeCacheDirsLI(ps.volumeUuid, ps.name);
+                        // No apps are running this early, so no need to freeze
+                        clearAppDataLIF(ps.pkg, UserHandle.USER_ALL,
+                                StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE
+                                        | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
                     }
+                    clearAppProfilesLIF(ps.pkg);
                 }
                 ver.fingerprint = Build.FINGERPRINT;
             }
@@ -2585,11 +2636,16 @@
                 mIntentFilterVerifierComponent = getIntentFilterVerifierComponentNameLPr();
                 mIntentFilterVerifier = new IntentVerifierProxy(mContext,
                         mIntentFilterVerifierComponent);
+                mServicesSystemSharedLibraryPackageName = getRequiredSharedLibraryLPr(
+                        PackageManager.SYSTEM_SHARED_LIBRARY_SERVICES);
+                getRequiredSharedLibraryLPr(
+                        PackageManager.SYSTEM_SHARED_LIBRARY_SHARED);
             } else {
                 mRequiredVerifierPackage = null;
                 mRequiredInstallerPackage = null;
                 mIntentFilterVerifierComponent = null;
                 mIntentFilterVerifier = null;
+                mServicesSystemSharedLibraryPackageName = null;
             }
 
             mInstallerService = new PackageInstallerService(context, this);
@@ -2669,6 +2725,16 @@
         }
     }
 
+    private @NonNull String getRequiredSharedLibraryLPr(String libraryName) {
+        synchronized (mPackages) {
+            SharedLibraryEntry libraryEntry = mSharedLibraries.get(libraryName);
+            if (libraryEntry == null) {
+                throw new IllegalStateException("Missing required shared library:" + libraryName);
+            }
+            return libraryEntry.apk;
+        }
+    }
+
     private @NonNull String getRequiredInstallerLPr() {
         final Intent intent = new Intent(Intent.ACTION_INSTALL_PACKAGE);
         intent.addCategory(Intent.CATEGORY_DEFAULT);
@@ -2678,6 +2744,10 @@
                 MATCH_SYSTEM_ONLY | MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE,
                 UserHandle.USER_SYSTEM);
         if (matches.size() == 1) {
+            ResolveInfo resolveInfo = matches.get(0);
+            if (!resolveInfo.activityInfo.applicationInfo.isPrivilegedApp()) {
+                throw new RuntimeException("The installer must be a privileged app");
+            }
             return matches.get(0).getComponentInfo().packageName;
         } else {
             throw new RuntimeException("There must be exactly one installer; found " + matches);
@@ -2924,22 +2994,6 @@
         }
     }
 
-    void cleanupInstallFailedPackage(PackageSetting ps) {
-        logCriticalInfo(Log.WARN, "Cleaning up incompletely installed app: " + ps.name);
-
-        removeDataDirsLI(ps.volumeUuid, ps.name);
-        if (ps.codePath != null) {
-            removeCodePathLI(ps.codePath);
-        }
-        if (ps.resourcePath != null && !ps.resourcePath.equals(ps.codePath)) {
-            if (ps.resourcePath.isDirectory()) {
-                FileUtils.deleteContents(ps.resourcePath);
-            }
-            ps.resourcePath.delete();
-        }
-        mSettings.removePackageLPw(ps.name);
-    }
-
     static int[] appendInts(int[] cur, int[] add) {
         if (add == null) return cur;
         if (cur == null) return add;
@@ -2989,7 +3043,7 @@
                 throw new SecurityException("Package " + packageName + " not a system app!");
             }
 
-            if (ps.frozen) {
+            if (mFrozenPackages.contains(packageName)) {
                 throw new SecurityException("Package " + packageName + " is currently frozen!");
             }
 
@@ -3038,7 +3092,7 @@
             }
             if (p == null) {
                 p = mPackages.get(packageName);
-                if (matchFactoryOnly && !isSystemApp(p)) {
+                if (matchFactoryOnly && p != null && !isSystemApp(p)) {
                     return null;
                 }
             }
@@ -3560,15 +3614,10 @@
     }
 
     @Override
-    public @Nullable String getServicesSystemSharedLibraryPackageName() {
+    public @NonNull String getServicesSystemSharedLibraryPackageName() {
         synchronized (mPackages) {
-            SharedLibraryEntry libraryEntry = mSharedLibraries.get(
-                    PackageManager.SYSTEM_SHARED_LIBRARY_SERVICES);
-            if (libraryEntry != null) {
-                return libraryEntry.apk;
-            }
+            return mServicesSystemSharedLibraryPackageName;
         }
-        return null;
     }
 
     @Override
@@ -4391,6 +4440,13 @@
         }
     }
 
+    /**
+     * This method should typically only be used when granting or revoking
+     * permissions, since the app may immediately restart after this call.
+     * <p>
+     * If you're doing surgery on app code/data, use {@link PackageFreezer} to
+     * guard your work against the app being relaunched.
+     */
     private void killUid(int appId, int userId, String reason) {
         final long identity = Binder.clearCallingIdentity();
         try {
@@ -4665,27 +4721,39 @@
     @Override
     public ResolveInfo resolveIntent(Intent intent, String resolvedType,
             int flags, int userId) {
-        if (!sUserManager.exists(userId)) return null;
-        flags = updateFlagsForResolve(flags, userId, intent);
-        enforceCrossUserPermission(Binder.getCallingUid(), userId,
-                false /* requireFullPermission */, false /* checkShell */, "resolve intent");
-        final List<ResolveInfo> query = queryIntentActivitiesInternal(intent, resolvedType, flags,
-                userId);
-        final ResolveInfo bestChoice =
-                chooseBestActivity(intent, resolvedType, flags, query, userId);
+        try {
+            Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "resolveIntent");
 
-        if (isEphemeralAllowed(intent, query, userId)) {
-            final EphemeralResolveInfo ai =
-                    getEphemeralResolveInfo(intent, resolvedType, userId);
-            if (ai != null) {
-                if (DEBUG_EPHEMERAL) {
-                    Slog.v(TAG, "Returning an EphemeralResolveInfo");
+            if (!sUserManager.exists(userId)) return null;
+            flags = updateFlagsForResolve(flags, userId, intent);
+            enforceCrossUserPermission(Binder.getCallingUid(), userId,
+                    false /*requireFullPermission*/, false /*checkShell*/, "resolve intent");
+
+            Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "queryIntentActivities");
+            final List<ResolveInfo> query = queryIntentActivitiesInternal(intent, resolvedType,
+                    flags, userId);
+            Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
+
+            final ResolveInfo bestChoice =
+                    chooseBestActivity(intent, resolvedType, flags, query, userId);
+
+            if (isEphemeralAllowed(intent, query, userId)) {
+                Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "resolveEphemeral");
+                final EphemeralResolveInfo ai =
+                        getEphemeralResolveInfo(intent, resolvedType, userId);
+                if (ai != null) {
+                    if (DEBUG_EPHEMERAL) {
+                        Slog.v(TAG, "Returning an EphemeralResolveInfo");
+                    }
+                    bestChoice.ephemeralInstaller = mEphemeralInstallerInfo;
+                    bestChoice.ephemeralResolveInfo = ai;
                 }
-                bestChoice.ephemeralInstaller = mEphemeralInstallerInfo;
-                bestChoice.ephemeralResolveInfo = ai;
+                Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
             }
+            return bestChoice;
+        } finally {
+            Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
         }
-        return bestChoice;
     }
 
     @Override
@@ -5132,8 +5200,14 @@
     @Override
     public @NonNull ParceledListSlice<ResolveInfo> queryIntentActivities(Intent intent,
             String resolvedType, int flags, int userId) {
-        return new ParceledListSlice<>(
-                queryIntentActivitiesInternal(intent, resolvedType, flags, userId));
+        try {
+            Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "queryIntentActivities");
+
+            return new ParceledListSlice<>(
+                    queryIntentActivitiesInternal(intent, resolvedType, flags, userId));
+        } finally {
+            Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
+        }
     }
 
     private @NonNull List<ResolveInfo> queryIntentActivitiesInternal(Intent intent,
@@ -6788,7 +6862,10 @@
                     != PackageManager.SIGNATURE_MATCH) {
                 logCriticalInfo(Log.WARN, "Package " + ps.name + " appeared on system, but"
                         + " signatures don't match existing userdata copy; removing");
-                deletePackageLI(pkg.packageName, null, true, null, 0, null, false, null);
+                try (PackageFreezer freezer = freezePackage(pkg.packageName,
+                        "scanPackageInternalLI")) {
+                    deletePackageLIF(pkg.packageName, null, true, null, 0, null, false, null);
+                }
                 ps = null;
             } else {
                 /*
@@ -7093,6 +7170,8 @@
         }
     }
 
+    // Run dexopt on a given package. Returns true if dexopt did not fail, i.e.
+    // if the package can now be considered up to date for the given filter.
     private boolean performDexOptInternal(String packageName, String instructionSet,
                 boolean checkProfiles, String targetCompilerFilter, boolean force) {
         PackageParser.Package p;
@@ -7113,7 +7192,7 @@
                 final String[] instructionSets = new String[] { targetInstructionSet };
                 int result = performDexOptInternalWithDependenciesLI(p, instructionSets,
                         checkProfiles, targetCompilerFilter, force);
-                return result == PackageDexOptimizer.DEX_OPT_PERFORMED;
+                return result != PackageDexOptimizer.DEX_OPT_FAILED;
             }
         } finally {
             Binder.restoreCallingIdentity(callingId);
@@ -7257,23 +7336,6 @@
         return true;
     }
 
-    private boolean removeDataDirsLI(String volumeUuid, String packageName) {
-        // TODO: triage flags as part of 26466827
-        final int flags = StorageManager.FLAG_STORAGE_CE | StorageManager.FLAG_STORAGE_DE;
-
-        boolean res = true;
-        final int[] users = sUserManager.getUserIds();
-        for (int user : users) {
-            try {
-                mInstaller.destroyAppData(volumeUuid, packageName, user, flags);
-            } catch (InstallerException e) {
-                Slog.w(TAG, "Failed to delete data directory", e);
-                res = false;
-            }
-        }
-        return res;
-    }
-
     void removeCodePathLI(File codePath) {
         if (codePath.isDirectory()) {
             try {
@@ -7286,87 +7348,106 @@
         }
     }
 
-    void destroyAppDataLI(String volumeUuid, String packageName, int userId, int flags) {
-        try {
-            mInstaller.destroyAppData(volumeUuid, packageName, userId, flags);
-        } catch (InstallerException e) {
-            Slog.w(TAG, "Failed to destroy app data", e);
-        }
+    private int[] resolveUserIds(int userId) {
+        return (userId == UserHandle.USER_ALL) ? sUserManager.getUserIds() : new int[] { userId };
     }
 
-    void restoreconAppDataLI(String volumeUuid, String packageName, int userId, int flags,
-            int appId, String seinfo) {
-        try {
-            mInstaller.restoreconAppData(volumeUuid, packageName, userId, flags, appId, seinfo);
-        } catch (InstallerException e) {
-            Slog.e(TAG, "Failed to restorecon for " + packageName + ": " + e);
-        }
-    }
-
-    private void deleteProfilesLI(String packageName, boolean destroy) {
-        final PackageParser.Package pkg;
-        synchronized (mPackages) {
-            pkg = mPackages.get(packageName);
-        }
+    private void clearAppDataLIF(PackageParser.Package pkg, int userId, int flags) {
         if (pkg == null) {
-            Slog.w(TAG, "Failed to delete profiles. No package: " + packageName);
+            Slog.wtf(TAG, "Package was null!", new Throwable());
             return;
         }
-        deleteProfilesLI(pkg, destroy);
-    }
-
-    private void deleteProfilesLI(PackageParser.Package pkg, boolean destroy) {
-        try {
-            if (destroy) {
-                mInstaller.destroyAppProfiles(pkg.packageName);
-            } else {
-                mInstaller.clearAppProfiles(pkg.packageName);
-            }
-        } catch (InstallerException ex) {
-            Log.e(TAG, "Could not delete profiles for package " + pkg.packageName);
+        clearAppDataLeafLIF(pkg, userId, flags);
+        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
+        for (int i = 0; i < childCount; i++) {
+            clearAppDataLeafLIF(pkg.childPackages.get(i), userId, flags);
         }
     }
 
-    private void deleteCodeCacheDirsLI(String volumeUuid, String packageName) {
-        final PackageParser.Package pkg;
+    private void clearAppDataLeafLIF(PackageParser.Package pkg, int userId, int flags) {
+        final PackageSetting ps;
         synchronized (mPackages) {
-            pkg = mPackages.get(packageName);
+            ps = mSettings.mPackages.get(pkg.packageName);
         }
-        if (pkg == null) {
-            Slog.w(TAG, "Failed to delete code cache directory. No package: " + packageName);
-            return;
-        }
-        deleteCodeCacheDirsLI(pkg);
-    }
-
-    private void deleteCodeCacheDirsLI(PackageParser.Package pkg) {
-        // TODO: triage flags as part of 26466827
-        final int flags = StorageManager.FLAG_STORAGE_CE | StorageManager.FLAG_STORAGE_DE;
-
-        int[] users = sUserManager.getUserIds();
-        int res = 0;
-        for (int user : users) {
-            // Remove the parent code cache
+        for (int realUserId : resolveUserIds(userId)) {
+            final long ceDataInode = (ps != null) ? ps.getCeDataInode(realUserId) : 0;
             try {
-                mInstaller.clearAppData(pkg.volumeUuid, pkg.packageName, user,
-                        flags | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
+                mInstaller.clearAppData(pkg.volumeUuid, pkg.packageName, realUserId, flags,
+                        ceDataInode);
             } catch (InstallerException e) {
-                Slog.w(TAG, "Failed to delete code cache directory", e);
+                Slog.w(TAG, String.valueOf(e));
             }
-            final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
-            for (int i = 0; i < childCount; i++) {
-                PackageParser.Package childPkg = pkg.childPackages.get(i);
-                // Remove the child code cache
-                try {
-                    mInstaller.clearAppData(childPkg.volumeUuid, childPkg.packageName,
-                            user, flags | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
-                } catch (InstallerException e) {
-                    Slog.w(TAG, "Failed to delete code cache directory", e);
-                }
+        }
+    }
+
+    private void destroyAppDataLIF(PackageParser.Package pkg, int userId, int flags) {
+        if (pkg == null) {
+            Slog.wtf(TAG, "Package was null!", new Throwable());
+            return;
+        }
+        destroyAppDataLeafLIF(pkg, userId, flags);
+        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
+        for (int i = 0; i < childCount; i++) {
+            destroyAppDataLeafLIF(pkg.childPackages.get(i), userId, flags);
+        }
+    }
+
+    private void destroyAppDataLeafLIF(PackageParser.Package pkg, int userId, int flags) {
+        final PackageSetting ps;
+        synchronized (mPackages) {
+            ps = mSettings.mPackages.get(pkg.packageName);
+        }
+        for (int realUserId : resolveUserIds(userId)) {
+            final long ceDataInode = (ps != null) ? ps.getCeDataInode(realUserId) : 0;
+            try {
+                mInstaller.destroyAppData(pkg.volumeUuid, pkg.packageName, realUserId, flags,
+                        ceDataInode);
+            } catch (InstallerException e) {
+                Slog.w(TAG, String.valueOf(e));
             }
         }
     }
 
+    private void destroyAppProfilesLIF(PackageParser.Package pkg) {
+        if (pkg == null) {
+            Slog.wtf(TAG, "Package was null!", new Throwable());
+            return;
+        }
+        destroyAppProfilesLeafLIF(pkg);
+        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
+        for (int i = 0; i < childCount; i++) {
+            destroyAppProfilesLeafLIF(pkg.childPackages.get(i));
+        }
+    }
+
+    private void destroyAppProfilesLeafLIF(PackageParser.Package pkg) {
+        try {
+            mInstaller.destroyAppProfiles(pkg.packageName);
+        } catch (InstallerException e) {
+            Slog.w(TAG, String.valueOf(e));
+        }
+    }
+
+    private void clearAppProfilesLIF(PackageParser.Package pkg) {
+        if (pkg == null) {
+            Slog.wtf(TAG, "Package was null!", new Throwable());
+            return;
+        }
+        clearAppProfilesLeafLIF(pkg);
+        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
+        for (int i = 0; i < childCount; i++) {
+            clearAppProfilesLeafLIF(pkg.childPackages.get(i));
+        }
+    }
+
+    private void clearAppProfilesLeafLIF(PackageParser.Package pkg) {
+        try {
+            mInstaller.clearAppProfiles(pkg.packageName);
+        } catch (InstallerException e) {
+            Slog.w(TAG, String.valueOf(e));
+        }
+    }
+
     private void setInstallAndUpdateTime(PackageParser.Package pkg, long firstInstallTime,
             long lastUpdateTime) {
         // Set parent install/update time
@@ -7552,7 +7633,10 @@
             return res;
         } finally {
             if (!success && (scanFlags & SCAN_DELETE_DATA_ON_FAILURES) != 0) {
-                removeDataDirsLI(pkg.volumeUuid, pkg.packageName);
+                // DELETE_DATA_ON_FAILURES is only used by frozen paths
+                destroyAppDataLIF(pkg, UserHandle.USER_ALL,
+                        StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE);
+                destroyAppProfilesLIF(pkg);
             }
         }
     }
@@ -8109,20 +8193,17 @@
             }
         }
 
-        // Request the ActivityManager to kill the process(only for existing packages)
-        // so that we do not end up in a confused state while the user is still using the older
-        // version of the application while the new one gets installed.
-        final boolean isReplacing = (scanFlags & SCAN_REPLACING) != 0;
-        final boolean killApp = (scanFlags & SCAN_DONT_KILL_APP) == 0;
-        if (killApp) {
-            if (isReplacing) {
-                Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "killApplication");
-
-                killApplication(pkg.applicationInfo.packageName,
-                            pkg.applicationInfo.uid, "replace pkg");
-
-                Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
-            }
+        if ((scanFlags & SCAN_BOOTING) != 0) {
+            // No apps can run during boot scan, so they don't need to be frozen
+        } else if ((scanFlags & SCAN_DONT_KILL_APP) != 0) {
+            // Caller asked to not kill app, so it's probably not frozen
+        } else if ((scanFlags & SCAN_IGNORE_FROZEN) != 0) {
+            // Caller asked us to ignore frozen check for some reason; they
+            // probably didn't know the package name
+        } else {
+            // We're doing major surgery on this package, so it better be frozen
+            // right now to keep it from launching
+            checkPackageFrozen(pkgName);
         }
 
         // Also need to kill any apps that are dependent on the library.
@@ -8593,7 +8674,7 @@
                 if (abi32 >= 0) {
                     final String abi = Build.SUPPORTED_32_BIT_ABIS[abi32];
                     if (abi64 >= 0) {
-                        if (cpuAbiOverride == null && pkg.use32bitAbi) {
+                        if (pkg.use32bitAbi) {
                             pkg.applicationInfo.secondaryCpuAbi = pkg.applicationInfo.primaryCpuAbi;
                             pkg.applicationInfo.primaryCpuAbi = abi;
                         } else {
@@ -8989,27 +9070,21 @@
         }
     }
 
-    private void killPackage(PackageParser.Package pkg, String reason) {
-        // Kill the parent package
-        killApplication(pkg.packageName, pkg.applicationInfo.uid, reason);
-        // Kill the child packages
-        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
-        for (int i = 0; i < childCount; i++) {
-            PackageParser.Package childPkg = pkg.childPackages.get(i);
-            killApplication(childPkg.packageName, childPkg.applicationInfo.uid, reason);
-        }
-    }
-
     private void killApplication(String pkgName, int appId, String reason) {
         // Request the ActivityManager to kill the process(only for existing packages)
         // so that we do not end up in a confused state while the user is still using the older
         // version of the application while the new one gets installed.
-        IActivityManager am = ActivityManagerNative.getDefault();
-        if (am != null) {
-            try {
-                am.killApplicationWithAppId(pkgName, appId, reason);
-            } catch (RemoteException e) {
+        final long token = Binder.clearCallingIdentity();
+        try {
+            IActivityManager am = ActivityManagerNative.getDefault();
+            if (am != null) {
+                try {
+                    am.killApplicationWithAppId(pkgName, appId, reason);
+                } catch (RemoteException e) {
+                }
             }
+        } finally {
+            Binder.restoreCallingIdentity(token);
         }
     }
 
@@ -11193,7 +11268,10 @@
 
             if (installed) {
                 if (pkgSetting.pkg != null) {
-                    prepareAppDataAfterInstall(pkgSetting.pkg);
+                    synchronized (mInstallLock) {
+                        // We don't need to freeze for a brand new install
+                        prepareAppDataAfterInstallLIF(pkgSetting.pkg);
+                    }
                 }
                 sendPackageAddedForUser(packageName, pkgSetting, userId);
             }
@@ -11742,6 +11820,9 @@
 
             // Okay!
             targetPackageSetting.installerPackageName = installerPackageName;
+            if (installerPackageName != null) {
+                mSettings.mInstallerPackages.add(installerPackageName);
+            }
             scheduleWriteSettingsLocked();
         }
     }
@@ -13315,7 +13396,13 @@
             Slog.d(TAG, "Cleaning up " + move.packageName + " on " + volumeUuid);
             synchronized (mInstallLock) {
                 // Clean up both app data and code
-                removeDataDirsLI(volumeUuid, move.packageName);
+                // All package moves are frozen until finished
+                try {
+                    mInstaller.destroyAppData(volumeUuid, move.packageName, UserHandle.USER_ALL,
+                            StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE, 0);
+                } catch (InstallerException e) {
+                    Slog.w(TAG, String.valueOf(e));
+                }
                 removeCodePathLI(codeFile);
             }
             return true;
@@ -13460,7 +13547,7 @@
     /*
      * Install a non-existing package.
      */
-    private void installNewPackageLI(PackageParser.Package pkg, int parseFlags, int scanFlags,
+    private void installNewPackageLIF(PackageParser.Package pkg, int parseFlags, int scanFlags,
             UserHandle user, String installerPackageName, String volumeUuid,
             PackageInstalledInfo res) {
         Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "installNewPackage");
@@ -13496,12 +13583,12 @@
             updateSettingsLI(newPackage, installerPackageName, null, res, user);
 
             if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) {
-                prepareAppDataAfterInstall(newPackage);
+                prepareAppDataAfterInstallLIF(newPackage);
 
             } else {
                 // Remove package from internal structures, but keep around any
                 // data that might have already existed
-                deletePackageLI(pkgName, UserHandle.ALL, false, null,
+                deletePackageLIF(pkgName, UserHandle.ALL, false, null,
                         PackageManager.DELETE_KEEP_DATA, res.removedInfo, true, null);
             }
         } catch (PackageManagerException e) {
@@ -13547,14 +13634,13 @@
         return false;
     }
 
-    private void replacePackageLI(PackageParser.Package pkg, int parseFlags, int scanFlags,
+    private void replacePackageLIF(PackageParser.Package pkg, int parseFlags, int scanFlags,
             UserHandle user, String installerPackageName, PackageInstalledInfo res) {
         final boolean isEphemeral = (parseFlags & PackageParser.PARSE_IS_EPHEMERAL) != 0;
 
         final PackageParser.Package oldPackage;
         final String pkgName = pkg.packageName;
         final int[] allUsers;
-        final boolean weFroze;
 
         // First find the old package info and check signatures
         synchronized(mPackages) {
@@ -13585,34 +13671,20 @@
                 }
             }
 
+            // Check for shared user id changes
+            String invalidPackageName =
+                    getParentOrChildPackageChangedSharedUser(oldPackage, pkg);
+            if (invalidPackageName != null) {
+                res.setError(INSTALL_FAILED_SHARED_USER_INCOMPATIBLE,
+                        "Package " + invalidPackageName + " tried to change user "
+                                + oldPackage.mSharedUserId);
+                return;
+            }
+
             // In case of rollback, remember per-user/profile install state
             allUsers = sUserManager.getUserIds();
-
-            // Mark the app as frozen to prevent launching during the upgrade
-            // process, and then kill all running instances
-            if (!ps.frozen) {
-                ps.frozen = true;
-                weFroze = true;
-            } else {
-                weFroze = false;
-            }
         }
 
-        try {
-            replacePackageDirtyLI(pkg, oldPackage, parseFlags, scanFlags, user, allUsers,
-                    installerPackageName, res);
-        } finally {
-            // Regardless of success or failure of upgrade steps above, always
-            // unfreeze the package if we froze it
-            if (weFroze) {
-                unfreezePackage(pkgName);
-            }
-        }
-    }
-
-    private void replacePackageDirtyLI(PackageParser.Package pkg, PackageParser.Package oldPackage,
-            int parseFlags, int scanFlags, UserHandle user, int[] allUsers,
-            String installerPackageName, PackageInstalledInfo res) {
         // Update what is removed
         res.removedInfo = new PackageRemovedInfo();
         res.removedInfo.uid = oldPackage.applicationInfo.uid;
@@ -13652,10 +13724,10 @@
 
         boolean sysPkg = (isSystemApp(oldPackage));
         if (sysPkg) {
-            replaceSystemPackageLI(oldPackage, pkg, parseFlags, scanFlags,
+            replaceSystemPackageLIF(oldPackage, pkg, parseFlags, scanFlags,
                     user, allUsers, installerPackageName, res);
         } else {
-            replaceNonSystemPackageLI(oldPackage, pkg, parseFlags, scanFlags,
+            replaceNonSystemPackageLIF(oldPackage, pkg, parseFlags, scanFlags,
                     user, allUsers, installerPackageName, res);
         }
     }
@@ -13669,7 +13741,7 @@
         return result;
     }
 
-    private void replaceNonSystemPackageLI(PackageParser.Package deletedPackage,
+    private void replaceNonSystemPackageLIF(PackageParser.Package deletedPackage,
             PackageParser.Package pkg, int parseFlags, int scanFlags, UserHandle user,
             int[] allUsers, String installerPackageName, PackageInstalledInfo res) {
         if (DEBUG_INSTALL) Slog.d(TAG, "replaceNonSystemPackageLI: new=" + pkg + ", old="
@@ -13687,7 +13759,7 @@
                 ? ((PackageSetting)pkg.mExtras).lastUpdateTime : 0;
 
         // First delete the existing package while retaining the data directory
-        if (!deletePackageLI(pkgName, null, true, allUsers, deleteFlags,
+        if (!deletePackageLIF(pkgName, null, true, allUsers, deleteFlags,
                 res.removedInfo, true, pkg)) {
             // If the existing package wasn't successfully deleted
             res.setError(INSTALL_FAILED_REPLACE_COULDNT_DELETE, "replaceNonSystemPackageLI");
@@ -13707,8 +13779,9 @@
                 sendResourcesChangedBroadcast(false, true, pkgList, uidArray, null);
             }
 
-            deleteCodeCacheDirsLI(pkg);
-            deleteProfilesLI(pkg, /*destroy*/ false);
+            clearAppDataLIF(pkg, UserHandle.USER_ALL, StorageManager.FLAG_STORAGE_DE
+                    | StorageManager.FLAG_STORAGE_CE | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
+            clearAppProfilesLIF(pkg);
 
             try {
                 final PackageParser.Package newPackage = scanPackageTracedLI(pkg, parseFlags,
@@ -13735,7 +13808,7 @@
                         childPs.oldCodePaths = ps.oldCodePaths;
                     }
                 }
-                prepareAppDataAfterInstall(newPackage);
+                prepareAppDataAfterInstallLIF(newPackage);
                 addedPkg = true;
             } catch (PackageManagerException e) {
                 res.setError("Package couldn't be installed in " + pkg.codePath, e);
@@ -13747,7 +13820,7 @@
 
             // Revert all internal state mutations and added folders for the failed install
             if (addedPkg) {
-                deletePackageLI(pkgName, null, true, allUsers, deleteFlags,
+                deletePackageLIF(pkgName, null, true, allUsers, deleteFlags,
                         res.removedInfo, true, null);
             }
 
@@ -13807,7 +13880,7 @@
         }
     }
 
-    private void replaceSystemPackageLI(PackageParser.Package deletedPackage,
+    private void replaceSystemPackageLIF(PackageParser.Package deletedPackage,
             PackageParser.Package pkg, int parseFlags, int scanFlags, UserHandle user,
             int[] allUsers, String installerPackageName, PackageInstalledInfo res) {
         if (DEBUG_INSTALL) Slog.d(TAG, "replaceSystemPackageLI: new=" + pkg
@@ -13822,9 +13895,6 @@
             parseFlags |= PackageParser.PARSE_IS_PRIVILEGED;
         }
 
-        // Kill package processes including services, providers, etc.
-        killPackage(deletedPackage, "replace sys pkg");
-
         // Remove existing system package
         removePackageLI(deletedPackage, true);
 
@@ -13842,8 +13912,9 @@
         }
 
         // Successfully disabled the old package. Now proceed with re-installation
-        deleteCodeCacheDirsLI(pkg);
-        deleteProfilesLI(pkg, /*destroy*/ false);
+        clearAppDataLIF(pkg, UserHandle.USER_ALL, StorageManager.FLAG_STORAGE_DE
+                | StorageManager.FLAG_STORAGE_CE | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
+        clearAppProfilesLIF(pkg);
 
         res.setReturnCode(PackageManager.INSTALL_SUCCEEDED);
         pkg.setApplicationInfoFlags(ApplicationInfo.FLAG_UPDATED_SYSTEM_APP,
@@ -13859,15 +13930,6 @@
             setInstallAndUpdateTime(newPackage, deletedPkgSetting.firstInstallTime,
                     System.currentTimeMillis());
 
-            // Check for shared user id changes
-            String invalidPackageName = getParentOrChildPackageChangedSharedUser(
-                    deletedPackage, newPackage);
-            if (invalidPackageName != null) {
-                res.setError(INSTALL_FAILED_SHARED_USER_INCOMPATIBLE,
-                        "Forbidding shared user change from " + deletedPkgSetting.sharedUser
-                                + " to " + invalidPackageName);
-            }
-
             // Update the package dynamic state if succeeded
             if (res.returnCode == PackageManager.INSTALL_SUCCEEDED) {
                 // Now that the install succeeded make sure we remove data
@@ -13892,14 +13954,14 @@
                         if (ps != null && res.removedInfo.removedChildPackages != null) {
                             PackageRemovedInfo removedChildRes = res.removedInfo
                                     .removedChildPackages.get(deletedChildPkg.packageName);
-                            removePackageDataLI(ps, allUsers, removedChildRes, 0, false);
+                            removePackageDataLIF(ps, allUsers, removedChildRes, 0, false);
                             removedChildRes.removedForAllUsers = mPackages.get(ps.name) == null;
                         }
                     }
                 }
 
                 updateSettingsLI(newPackage, installerPackageName, allUsers, res, user);
-                prepareAppDataAfterInstall(newPackage);
+                prepareAppDataAfterInstallLIF(newPackage);
             }
         } catch (PackageManagerException e) {
             res.setReturnCode(INSTALL_FAILED_INTERNAL_ERROR);
@@ -14478,7 +14540,6 @@
                 return;
             }
 
-
             Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dexopt");
             // Do not run PackageDexOptimizer through the local performDexOpt
             // method because `pkg` is not in `mPackages` yet.
@@ -14486,10 +14547,15 @@
                     false /* checkProfiles */, getCompilerFilterForReason(REASON_INSTALL));
             Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
             if (result == PackageDexOptimizer.DEX_OPT_FAILED) {
-                String msg = "Extracking package failed for " + pkgName;
+                String msg = "Extracting package failed for " + pkgName;
                 res.setError(INSTALL_FAILED_DEXOPT, msg);
                 return;
             }
+
+            // Notify BackgroundDexOptService that the package has been changed.
+            // If this is an update of a package which used to fail to compile,
+            // BDOS will remove it from its blacklist.
+            BackgroundDexOptService.notifyPackageChanged(pkg.packageName);
         }
 
         if (!args.doRename(res.returnCode, pkg, oldCodePath)) {
@@ -14499,12 +14565,15 @@
 
         startIntentFilterVerifications(args.user.getIdentifier(), replace, pkg);
 
-        if (replace) {
-            replacePackageLI(pkg, parseFlags, scanFlags | SCAN_REPLACING, args.user,
-                    installerPackageName, res);
-        } else {
-            installNewPackageLI(pkg, parseFlags, scanFlags | SCAN_DELETE_DATA_ON_FAILURES,
-                    args.user, installerPackageName, volumeUuid, res);
+        try (PackageFreezer freezer = freezePackageForInstall(pkgName, installFlags,
+                "installPackageLI")) {
+            if (replace) {
+                replacePackageLIF(pkg, parseFlags, scanFlags | SCAN_REPLACING, args.user,
+                        installerPackageName, res);
+            } else {
+                installNewPackageLIF(pkg, parseFlags, scanFlags | SCAN_DELETE_DATA_ON_FAILURES,
+                        args.user, installerPackageName, volumeUuid, res);
+            }
         }
         synchronized (mPackages) {
             final PackageSetting ps = mSettings.mPackages.get(pkgName);
@@ -14752,13 +14821,13 @@
 
     @Override
     public void deletePackage(final String packageName,
-            final IPackageDeleteObserver2 observer, final int userId, final int flags) {
+            final IPackageDeleteObserver2 observer, final int userId, final int deleteFlags) {
         mContext.enforceCallingOrSelfPermission(
                 android.Manifest.permission.DELETE_PACKAGES, null);
         Preconditions.checkNotNull(packageName);
         Preconditions.checkNotNull(observer);
         final int uid = Binder.getCallingUid();
-        final boolean deleteAllUsers = (flags & PackageManager.DELETE_ALL_USERS) != 0;
+        final boolean deleteAllUsers = (deleteFlags & PackageManager.DELETE_ALL_USERS) != 0;
         final int[] users = deleteAllUsers ? sUserManager.getUserIds() : new int[]{ userId };
         if (UserHandle.getUserId(uid) != userId || (deleteAllUsers && users.length > 1)) {
             mContext.enforceCallingOrSelfPermission(
@@ -14794,15 +14863,15 @@
                 mHandler.removeCallbacks(this);
                 int returnCode;
                 if (!deleteAllUsers) {
-                    returnCode = deletePackageX(packageName, userId, flags);
+                    returnCode = deletePackageX(packageName, userId, deleteFlags);
                 } else {
                     int[] blockUninstallUserIds = getBlockUninstallForUsers(packageName, users);
                     // If nobody is blocking uninstall, proceed with delete for all users
                     if (ArrayUtils.isEmpty(blockUninstallUserIds)) {
-                        returnCode = deletePackageX(packageName, userId, flags);
+                        returnCode = deletePackageX(packageName, userId, deleteFlags);
                     } else {
                         // Otherwise uninstall individually for users with blockUninstalls=false
-                        final int userFlags = flags & ~PackageManager.DELETE_ALL_USERS;
+                        final int userFlags = deleteFlags & ~PackageManager.DELETE_ALL_USERS;
                         for (int userId : users) {
                             if (!ArrayUtils.contains(blockUninstallUserIds, userId)) {
                                 returnCode = deletePackageX(packageName, userId, userFlags);
@@ -14883,7 +14952,7 @@
      *  This method is an internal method that could be get invoked either
      *  to delete an installed package or to clean up a failed installation.
      *  After deleting an installed package, a broadcast is sent to notify any
-     *  listeners that the package has been installed. For cleaning up a failed
+     *  listeners that the package has been removed. For cleaning up a failed
      *  installation, the broadcast is not necessary since the package's
      *  installation wouldn't have sent the initial broadcast either
      *  The key steps in deleting a package are
@@ -14893,11 +14962,11 @@
      *  persisting settings for later use
      *  sending a broadcast if necessary
      */
-    private int deletePackageX(String packageName, int userId, int flags) {
+    private int deletePackageX(String packageName, int userId, int deleteFlags) {
         final PackageRemovedInfo info = new PackageRemovedInfo();
         final boolean res;
 
-        final UserHandle removeForUser = (flags & PackageManager.DELETE_ALL_USERS) != 0
+        final UserHandle removeForUser = (deleteFlags & PackageManager.DELETE_ALL_USERS) != 0
                 ? UserHandle.ALL : new UserHandle(userId);
 
         if (isPackageDeviceAdmin(packageName, removeForUser.getIdentifier())) {
@@ -14922,8 +14991,11 @@
 
         synchronized (mInstallLock) {
             if (DEBUG_REMOVE) Slog.d(TAG, "deletePackageX: pkg=" + packageName + " user=" + userId);
-            res = deletePackageLI(packageName, removeForUser, true, allUsers,
-                    flags | REMOVE_CHATTY, info, true, null);
+            try (PackageFreezer freezer = freezePackageForDelete(packageName, deleteFlags,
+                    "deletePackageX")) {
+                res = deletePackageLIF(packageName, removeForUser, true, allUsers,
+                        deleteFlags | REMOVE_CHATTY, info, true, null);
+            }
             synchronized (mPackages) {
                 if (res) {
                     mEphemeralApplicationRegistry.onPackageUninstalledLPw(uninstalledPs.pkg);
@@ -14932,7 +15004,7 @@
         }
 
         if (res) {
-            final boolean killApp = (flags & PackageManager.INSTALL_DONT_KILL_APP) == 0;
+            final boolean killApp = (deleteFlags & PackageManager.DELETE_DONT_KILL_APP) == 0;
             info.sendPackageRemovedBroadcasts(killApp);
             info.sendSystemPackageUpdatedBroadcasts();
             info.sendSystemPackageAppearedBroadcasts();
@@ -15042,15 +15114,16 @@
      * make sure this flag is set for partially installed apps. If not its meaningless to
      * delete a partially installed application.
      */
-    private void removePackageDataLI(PackageSetting ps, int[] allUserHandles,
+    private void removePackageDataLIF(PackageSetting ps, int[] allUserHandles,
             PackageRemovedInfo outInfo, int flags, boolean writeSettings) {
         String packageName = ps.name;
         if (DEBUG_REMOVE) Slog.d(TAG, "removePackageDataLI: " + ps);
-        removePackageLI(ps, (flags&REMOVE_CHATTY) != 0);
         // Retrieve object to delete permissions for shared user later on
+        final PackageParser.Package deletedPkg;
         final PackageSetting deletedPs;
         // reader
         synchronized (mPackages) {
+            deletedPkg = mPackages.get(packageName);
             deletedPs = mSettings.mPackages.get(packageName);
             if (outInfo != null) {
                 outInfo.removedPackage = packageName;
@@ -15059,13 +15132,19 @@
                         : null;
             }
         }
-        if ((flags&PackageManager.DELETE_KEEP_DATA) == 0) {
-            removeDataDirsLI(ps.volumeUuid, packageName);
+
+        removePackageLI(ps, (flags & REMOVE_CHATTY) != 0);
+
+        if ((flags & PackageManager.DELETE_KEEP_DATA) == 0) {
+            destroyAppDataLIF(deletedPkg, UserHandle.USER_ALL,
+                    StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE);
+            destroyAppProfilesLIF(deletedPkg);
             if (outInfo != null) {
                 outInfo.dataRemoved = true;
             }
             schedulePackageCleaning(packageName, UserHandle.USER_ALL, true);
         }
+
         // writer
         synchronized (mPackages) {
             if (deletedPs != null) {
@@ -15145,7 +15224,7 @@
     /*
      * Tries to delete system package.
      */
-    private boolean deleteSystemPackageLI(PackageParser.Package deletedPkg,
+    private boolean deleteSystemPackageLIF(PackageParser.Package deletedPkg,
             PackageSetting deletedPs, int[] allUserHandles, int flags, PackageRemovedInfo outInfo,
             boolean writeSettings) {
         if (deletedPs.parentPackageName != null) {
@@ -15210,7 +15289,7 @@
             flags |= PackageManager.DELETE_KEEP_DATA;
         }
 
-        boolean ret = deleteInstalledPackageLI(deletedPs, true, flags, allUserHandles,
+        boolean ret = deleteInstalledPackageLIF(deletedPs, true, flags, allUserHandles,
                 outInfo, writeSettings, disabledPs.pkg);
         if (!ret) {
             return false;
@@ -15240,7 +15319,7 @@
             return false;
         }
 
-        prepareAppDataAfterInstall(newPkg);
+        prepareAppDataAfterInstallLIF(newPkg);
 
         // writer
         synchronized (mPackages) {
@@ -15278,7 +15357,7 @@
         return true;
     }
 
-    private boolean deleteInstalledPackageLI(PackageSetting ps,
+    private boolean deleteInstalledPackageLIF(PackageSetting ps,
             boolean deleteCodeAndResources, int flags, int[] allUserHandles,
             PackageRemovedInfo outInfo, boolean writeSettings,
             PackageParser.Package replacingPackage) {
@@ -15306,7 +15385,7 @@
         }
 
         // Delete package data from internal structures and also remove data if flag is set
-        removePackageDataLI(ps, allUserHandles, outInfo, flags, writeSettings);
+        removePackageDataLIF(ps, allUserHandles, outInfo, flags, writeSettings);
 
         // Delete the child packages data
         final int childCount = (ps.childPackageNames != null) ? ps.childPackageNames.size() : 0;
@@ -15323,7 +15402,7 @@
                         && (replacingPackage != null
                         && !replacingPackage.hasChildPackage(childPs.name))
                         ? flags & ~DELETE_KEEP_DATA : flags;
-                removePackageDataLI(childPs, allUserHandles, childOutInfo,
+                removePackageDataLIF(childPs, allUserHandles, childOutInfo,
                         deleteFlags, writeSettings);
             }
         }
@@ -15400,7 +15479,7 @@
     /*
      * This method handles package deletion in general
      */
-    private boolean deletePackageLI(String packageName, UserHandle user,
+    private boolean deletePackageLIF(String packageName, UserHandle user,
             boolean deleteCodeAndResources, int[] allUserHandles, int flags,
             PackageRemovedInfo outInfo, boolean writeSettings,
             PackageParser.Package replacingPackage) {
@@ -15428,7 +15507,7 @@
                 }
                 final int removedUserId = (user != null) ? user.getIdentifier()
                         : UserHandle.USER_ALL;
-                if (!clearPackageStateForUser(ps, removedUserId, outInfo)) {
+                if (!clearPackageStateForUserLIF(ps, removedUserId, outInfo)) {
                     return false;
                 }
                 markPackageUninstalledForUserLPw(ps, user);
@@ -15454,7 +15533,7 @@
                     // we need to do is clear this user's data and save that
                     // it is uninstalled.
                     if (DEBUG_REMOVE) Slog.d(TAG, "Still installed by other users");
-                    if (!clearPackageStateForUser(ps, user.getIdentifier(), outInfo)) {
+                    if (!clearPackageStateForUserLIF(ps, user.getIdentifier(), outInfo)) {
                         return false;
                     }
                     scheduleWritePackageRestrictionsLocked(user);
@@ -15471,7 +15550,7 @@
                 // we need to do is clear this user's data and save that
                 // it is uninstalled.
                 if (DEBUG_REMOVE) Slog.d(TAG, "Deleting system app");
-                if (!clearPackageStateForUser(ps, user.getIdentifier(), outInfo)) {
+                if (!clearPackageStateForUserLIF(ps, user.getIdentifier(), outInfo)) {
                     return false;
                 }
                 scheduleWritePackageRestrictionsLocked(user);
@@ -15503,15 +15582,10 @@
             if (DEBUG_REMOVE) Slog.d(TAG, "Removing system package: " + ps.name);
             // When an updated system application is deleted we delete the existing resources
             // as well and fall back to existing code in system partition
-            ret = deleteSystemPackageLI(ps.pkg, ps, allUserHandles, flags, outInfo, writeSettings);
+            ret = deleteSystemPackageLIF(ps.pkg, ps, allUserHandles, flags, outInfo, writeSettings);
         } else {
             if (DEBUG_REMOVE) Slog.d(TAG, "Removing non-system package: " + ps.name);
-            // Kill application pre-emptively especially for apps on sd.
-            final boolean killApp = (flags & PackageManager.DELETE_DONT_KILL_APP) == 0;
-            if (killApp) {
-                killApplication(packageName, ps.appId, "uninstall pkg");
-            }
-            ret = deleteInstalledPackageLI(ps, deleteCodeAndResources, flags, allUserHandles,
+            ret = deleteInstalledPackageLIF(ps, deleteCodeAndResources, flags, allUserHandles,
                     outInfo, writeSettings, replacingPackage);
         }
 
@@ -15571,7 +15645,7 @@
             if (DEBUG_REMOVE) {
                 Slog.d(TAG, "Marking package:" + ps.name + " uninstalled for user:" + nextUserId);
             }
-            ps.setUserState(nextUserId, COMPONENT_ENABLED_STATE_DEFAULT,
+            ps.setUserState(nextUserId, 0, COMPONENT_ENABLED_STATE_DEFAULT,
                     false /*installed*/, true /*stopped*/, true /*notLaunched*/,
                     false /*hidden*/, false /*suspended*/, null, null, null,
                     false /*blockUninstall*/,
@@ -15579,8 +15653,13 @@
         }
     }
 
-    private boolean clearPackageStateForUser(PackageSetting ps, int userId,
+    private boolean clearPackageStateForUserLIF(PackageSetting ps, int userId,
             PackageRemovedInfo outInfo) {
+        final PackageParser.Package pkg;
+        synchronized (mPackages) {
+            pkg = mPackages.get(ps.name);
+        }
+
         final int[] userIds = (userId == UserHandle.USER_ALL) ? sUserManager.getUserIds()
                 : new int[] {userId};
         for (int nextUserId : userIds) {
@@ -15588,13 +15667,9 @@
                 Slog.d(TAG, "Updating package:" + ps.name + " install state for user:"
                         + nextUserId);
             }
-            final int flags =  StorageManager.FLAG_STORAGE_CE|  StorageManager.FLAG_STORAGE_DE;
-            try {
-                mInstaller.destroyAppData(ps.volumeUuid, ps.name, nextUserId, flags);
-            } catch (InstallerException e) {
-                Slog.w(TAG, "Couldn't remove cache files for package " + ps.name, e);
-                return false;
-            }
+
+            destroyAppDataLIF(pkg, userId,
+                    StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE);
             removeKeystoreDataIfNeeded(nextUserId, ps.appId);
             schedulePackageCleaning(ps.name, nextUserId, false);
             synchronized (mPackages) {
@@ -15631,6 +15706,8 @@
     }
 
     private void clearExternalStorageDataSync(String packageName, int userId, boolean allData) {
+        if (DEFAULT_CONTAINER_PACKAGE.equals(packageName)) return;
+
         final boolean mounted;
         if (Environment.isExternalStorageEmulated()) {
             mounted = true;
@@ -15690,10 +15767,16 @@
     @Override
     public void clearApplicationProfileData(String packageName) {
         enforceSystemOrRoot("Only the system can clear all profile data");
-        try {
-            mInstaller.clearAppProfiles(packageName);
-        } catch (InstallerException ex) {
-            Log.e(TAG, "Could not clear profile data of package " + packageName);
+
+        final PackageParser.Package pkg;
+        synchronized (mPackages) {
+            pkg = mPackages.get(packageName);
+        }
+
+        try (PackageFreezer freezer = freezePackage(packageName, "clearApplicationProfileData")) {
+            synchronized (mInstallLock) {
+                clearAppProfilesLIF(pkg);
+            }
         }
     }
 
@@ -15716,10 +15799,13 @@
             public void run() {
                 mHandler.removeCallbacks(this);
                 final boolean succeeded;
-                synchronized (mInstallLock) {
-                    succeeded = clearApplicationUserDataLI(packageName, userId);
+                try (PackageFreezer freezer = freezePackage(packageName,
+                        "clearApplicationUserData")) {
+                    synchronized (mInstallLock) {
+                        succeeded = clearApplicationUserDataLIF(packageName, userId);
+                    }
+                    clearExternalStorageDataSync(packageName, userId, true);
                 }
-                clearExternalStorageDataSync(packageName, userId, true);
                 if (succeeded) {
                     // invoke DeviceStorageMonitor's update method to clear any notifications
                     DeviceStorageMonitorInternal dsm = LocalServices
@@ -15739,7 +15825,7 @@
         });
     }
 
-    private boolean clearApplicationUserDataLI(String packageName, int userId) {
+    private boolean clearApplicationUserDataLIF(String packageName, int userId) {
         if (packageName == null) {
             Slog.w(TAG, "Attempt to delete null packageName.");
             return false;
@@ -15765,35 +15851,22 @@
             resetUserChangesToRuntimePermissionsAndFlagsLPw(ps, userId);
         }
 
-        // Always delete data directories for package, even if we found no other
-        // record of app. This helps users recover from UID mismatches without
-        // resorting to a full data wipe.
-        // TODO: triage flags as part of 26466827
-        final int flags = StorageManager.FLAG_STORAGE_CE | StorageManager.FLAG_STORAGE_DE;
-        try {
-            mInstaller.clearAppData(pkg.volumeUuid, packageName, userId, flags);
-        } catch (InstallerException e) {
-            Slog.w(TAG, "Couldn't remove cache files for package " + packageName, e);
-            return false;
-        }
+        clearAppDataLIF(pkg, userId,
+                StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE);
 
         final int appId = UserHandle.getAppId(pkg.applicationInfo.uid);
         removeKeystoreDataIfNeeded(userId, appId);
 
-        // Create a native library symlink only if we have native libraries
-        // and if the native libraries are 32 bit libraries. We do not provide
-        // this symlink for 64 bit libraries.
-        if (pkg.applicationInfo.primaryCpuAbi != null &&
-                !VMRuntime.is64BitAbi(pkg.applicationInfo.primaryCpuAbi)) {
-            final String nativeLibPath = pkg.applicationInfo.nativeLibraryDir;
-            try {
-                mInstaller.linkNativeLibraryDirectory(pkg.volumeUuid, pkg.packageName,
-                        nativeLibPath, userId);
-            } catch (InstallerException e) {
-                Slog.w(TAG, "Failed linking native library dir", e);
-                return false;
-            }
+        final UserManager um = mContext.getSystemService(UserManager.class);
+        final int flags;
+        if (um.isUserUnlocked(userId)) {
+            flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
+        } else if (um.isUserRunning(userId)) {
+            flags = StorageManager.FLAG_STORAGE_DE;
+        } else {
+            flags = 0;
         }
+        prepareAppDataContentsLIF(pkg, userId, flags);
 
         return true;
     }
@@ -15963,56 +16036,35 @@
                 android.Manifest.permission.DELETE_CACHE_FILES, null);
         // Queue up an async operation since the package deletion may take a little while.
         final int userId = UserHandle.getCallingUserId();
+
+        final PackageParser.Package pkg;
+        synchronized (mPackages) {
+            pkg = mPackages.get(packageName);
+        }
+
         mHandler.post(new Runnable() {
             public void run() {
-                mHandler.removeCallbacks(this);
-                final boolean succeded;
-                synchronized (mInstallLock) {
-                    succeded = deleteApplicationCacheFilesLI(packageName, userId);
+                try (PackageFreezer freezer = freezePackage(packageName,
+                        "deleteApplicationCacheFiles")) {
+                    synchronized (mInstallLock) {
+                        final int flags = StorageManager.FLAG_STORAGE_DE
+                                | StorageManager.FLAG_STORAGE_CE;
+                        clearAppDataLIF(pkg, userId, flags | Installer.FLAG_CLEAR_CACHE_ONLY);
+                        clearAppDataLIF(pkg, userId, flags | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
+                    }
+                    clearExternalStorageDataSync(packageName, userId, false);
                 }
-                clearExternalStorageDataSync(packageName, userId, false);
                 if (observer != null) {
                     try {
-                        observer.onRemoveCompleted(packageName, succeded);
+                        observer.onRemoveCompleted(packageName, true);
                     } catch (RemoteException e) {
                         Log.i(TAG, "Observer no longer exists.");
                     }
-                } //end if observer
-            } //end run
+                }
+            }
         });
     }
 
-    private boolean deleteApplicationCacheFilesLI(String packageName, int userId) {
-        if (packageName == null) {
-            Slog.w(TAG, "Attempt to delete null packageName.");
-            return false;
-        }
-        PackageParser.Package p;
-        synchronized (mPackages) {
-            p = mPackages.get(packageName);
-        }
-        if (p == null) {
-            Slog.w(TAG, "Package named '" + packageName +"' doesn't exist.");
-            return false;
-        }
-        final ApplicationInfo applicationInfo = p.applicationInfo;
-        if (applicationInfo == null) {
-            Slog.w(TAG, "Package " + packageName + " has no applicationInfo.");
-            return false;
-        }
-        // TODO: triage flags as part of 26466827
-        final int flags = StorageManager.FLAG_STORAGE_CE | StorageManager.FLAG_STORAGE_DE;
-        try {
-            mInstaller.clearAppData(p.volumeUuid, packageName, userId,
-                    flags | Installer.FLAG_CLEAR_CACHE_ONLY);
-        } catch (InstallerException e) {
-            Slog.w(TAG, "Couldn't remove cache files for package "
-                    + packageName + " u" + userId, e);
-            return false;
-        }
-        return true;
-    }
-
     @Override
     public void getPackageSizeInfo(final String packageName, int userHandle,
             final IPackageStatsObserver observer) {
@@ -16033,90 +16085,24 @@
         mHandler.sendMessage(msg);
     }
 
-    private boolean getPackageSizeInfoLI(String packageName, int userHandle,
-            PackageStats pStats) {
-        if (packageName == null) {
-            Slog.w(TAG, "Attempt to get size of null packageName.");
-            return false;
-        }
-        PackageParser.Package p;
-        boolean dataOnly = false;
-        String libDirRoot = null;
-        String asecPath = null;
-        PackageSetting ps = null;
+    private boolean getPackageSizeInfoLI(String packageName, int userId, PackageStats stats) {
+        final PackageSetting ps;
         synchronized (mPackages) {
-            p = mPackages.get(packageName);
             ps = mSettings.mPackages.get(packageName);
-            if(p == null) {
-                dataOnly = true;
-                if((ps == null) || (ps.pkg == null)) {
-                    Slog.w(TAG, "Package named '" + packageName +"' doesn't exist.");
-                    return false;
-                }
-                p = ps.pkg;
-            }
-            if (ps != null) {
-                libDirRoot = ps.legacyNativeLibraryPathString;
-            }
-            if (p != null && (p.isForwardLocked() || p.applicationInfo.isExternalAsec())) {
-                final long token = Binder.clearCallingIdentity();
-                try {
-                    String secureContainerId = cidFromCodePath(p.applicationInfo.getBaseCodePath());
-                    if (secureContainerId != null) {
-                        asecPath = PackageHelper.getSdFilesystem(secureContainerId);
-                    }
-                } finally {
-                    Binder.restoreCallingIdentity(token);
-                }
-            }
-        }
-        String publicSrcDir = null;
-        if(!dataOnly) {
-            final ApplicationInfo applicationInfo = p.applicationInfo;
-            if (applicationInfo == null) {
-                Slog.w(TAG, "Package " + packageName + " has no applicationInfo.");
+            if (ps == null) {
+                Slog.w(TAG, "Failed to find settings for " + packageName);
                 return false;
             }
-            if (p.isForwardLocked()) {
-                publicSrcDir = applicationInfo.getBaseResourcePath();
-            }
         }
-        // TODO: extend to measure size of split APKs
-        // TODO(multiArch): Extend getSizeInfo to look at the full subdirectory tree,
-        // not just the first level.
-        // TODO(multiArch): Extend getSizeInfo to look at *all* instruction sets, not
-        // just the primary.
-        String[] dexCodeInstructionSets = getDexCodeInstructionSets(getAppDexInstructionSets(ps));
-
-        String apkPath;
-        File packageDir = new File(p.codePath);
-
-        if (packageDir.isDirectory() && p.canHaveOatDir()) {
-            apkPath = packageDir.getAbsolutePath();
-            // If libDirRoot is inside a package dir, set it to null to avoid it being counted twice
-            if (libDirRoot != null && libDirRoot.startsWith(apkPath)) {
-                libDirRoot = null;
-            }
-        } else {
-            apkPath = p.baseCodePath;
-        }
-
-        // TODO: triage flags as part of 26466827
-        final int flags = StorageManager.FLAG_STORAGE_CE | StorageManager.FLAG_STORAGE_DE;
         try {
-            mInstaller.getAppSize(p.volumeUuid, packageName, userHandle, flags, apkPath,
-                    libDirRoot, publicSrcDir, asecPath, dexCodeInstructionSets, pStats);
+            mInstaller.getAppSize(ps.volumeUuid, packageName, userId,
+                    StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE,
+                    ps.getCeDataInode(userId), ps.codePathString, stats);
+            return true;
         } catch (InstallerException e) {
+            Slog.w(TAG, String.valueOf(e));
             return false;
         }
-
-        // Fix-up for forward-locked applications in ASEC containers.
-        if (!isExternal(p)) {
-            pStats.codeSize += pStats.externalCodeSize;
-            pStats.externalCodeSize = 0L;
-        }
-
-        return true;
     }
 
     private int getUidTargetSdkVersionLockedLPr(int uid) {
@@ -17076,8 +17062,13 @@
         }
         PackageSetting pkgSetting;
         final int uid = Binder.getCallingUid();
-        final int permission = mContext.checkCallingOrSelfPermission(
-                android.Manifest.permission.CHANGE_COMPONENT_ENABLED_STATE);
+        final int permission;
+        if (uid == Process.SYSTEM_UID) {
+            permission = PackageManager.PERMISSION_GRANTED;
+        } else {
+            permission = mContext.checkCallingOrSelfPermission(
+                    android.Manifest.permission.CHANGE_COMPONENT_ENABLED_STATE);
+        }
         enforceCrossUserPermission(uid, userId,
                 false /* requireFullPermission */, true /* checkShell */, "set enabled");
         final boolean allowedByPermission = (permission == PackageManager.PERMISSION_GRANTED);
@@ -17431,6 +17422,7 @@
         public static final int DUMP_INSTALLS = 1 << 16;
         public static final int DUMP_INTENT_FILTER_VERIFIERS = 1 << 17;
         public static final int DUMP_DOMAIN_PREFERRED = 1 << 18;
+        public static final int DUMP_FROZEN = 1 << 19;
 
         public static final int OPTION_SHOW_FILTERS = 1 << 0;
 
@@ -17664,6 +17656,8 @@
                 dumpState.setDump(DumpState.DUMP_KEYSETS);
             } else if ("installs".equals(cmd)) {
                 dumpState.setDump(DumpState.DUMP_INSTALLS);
+            } else if ("frozen".equals(cmd)) {
+                dumpState.setDump(DumpState.DUMP_FROZEN);
             } else if ("write".equals(cmd)) {
                 synchronized (mPackages) {
                     mSettings.writeLPr();
@@ -18002,6 +17996,25 @@
                 mInstallerService.dump(new IndentingPrintWriter(pw, "  ", 120));
             }
 
+            if (!checkin && dumpState.isDumping(DumpState.DUMP_FROZEN) && packageName == null) {
+                // XXX should handle packageName != null by dumping only install data that
+                // the given package is involved with.
+                if (dumpState.onTitlePrinted()) pw.println();
+
+                final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, "  ", 120);
+                ipw.println();
+                ipw.println("Frozen packages:");
+                ipw.increaseIndent();
+                if (mFrozenPackages.size() == 0) {
+                    ipw.println("(none)");
+                } else {
+                    for (int i = 0; i < mFrozenPackages.size(); i++) {
+                        ipw.println(mFrozenPackages.valueAt(i));
+                    }
+                }
+                ipw.decreaseIndent();
+            }
+
             if (!checkin && dumpState.isDumping(DumpState.DUMP_MESSAGES) && packageName == null) {
                 if (dumpState.onTitlePrinted()) pw.println();
                 mSettings.dumpReadMessagesLPr(pw, dumpState);
@@ -18314,7 +18327,9 @@
                 synchronized (mInstallLock) {
                     PackageParser.Package pkg = null;
                     try {
-                        pkg = scanPackageTracedLI(new File(codePath), parseFlags, 0, 0, null);
+                        // Sadly we don't know the package name yet to freeze it
+                        pkg = scanPackageTracedLI(new File(codePath), parseFlags,
+                                SCAN_IGNORE_FROZEN, 0, null);
                     } catch (PackageManagerException e) {
                         Slog.w(TAG, "Failed to scan " + codePath + ": " + e.getMessage());
                     }
@@ -18413,8 +18428,13 @@
             // Delete package internally
             PackageRemovedInfo outInfo = new PackageRemovedInfo();
             synchronized (mInstallLock) {
-                boolean res = deletePackageLI(pkgName, null, false, null,
-                        PackageManager.DELETE_KEEP_DATA, outInfo, false, null);
+                final int deleteFlags = PackageManager.DELETE_KEEP_DATA;
+                final boolean res;
+                try (PackageFreezer freezer = freezePackageForDelete(pkgName, deleteFlags,
+                        "unloadMediaPackages")) {
+                    res = deletePackageLIF(pkgName, null, false, null, deleteFlags, outInfo, false,
+                            null);
+                }
                 if (res) {
                     pkgList.add(pkgName);
                 } else {
@@ -18469,6 +18489,7 @@
             return;
         }
 
+        final ArrayList<PackageFreezer> freezers = new ArrayList<>();
         final ArrayList<ApplicationInfo> loaded = new ArrayList<>();
         final int parseFlags = mDefParseFlags | PackageParser.PARSE_EXTERNAL_STORAGE;
 
@@ -18479,9 +18500,8 @@
             packages = mSettings.getVolumePackagesLPr(volumeUuid);
         }
 
-        // TODO: introduce a new concept similar to "frozen" to prevent these
-        // apps from being launched until after data has been fully reconciled
         for (PackageSetting ps : packages) {
+            freezers.add(freezePackage(ps.name, "loadPrivatePackagesInner"));
             synchronized (mInstallLock) {
                 final PackageParser.Package pkg;
                 try {
@@ -18493,7 +18513,9 @@
                 }
 
                 if (!Build.FINGERPRINT.equals(ver.fingerprint)) {
-                    deleteCodeCacheDirsLI(ps.volumeUuid, ps.name);
+                    clearAppDataLIF(ps.pkg, UserHandle.USER_ALL,
+                            StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE
+                                    | Installer.FLAG_CLEAR_CODE_CACHE_ONLY);
                 }
             }
         }
@@ -18512,7 +18534,9 @@
             }
 
             sm.prepareUserStorage(volumeUuid, user.id, user.serialNumber, flags);
-            reconcileAppsData(volumeUuid, user.id, flags);
+            synchronized (mInstallLock) {
+                reconcileAppsDataLI(volumeUuid, user.id, flags);
+            }
         }
 
         synchronized (mPackages) {
@@ -18530,6 +18554,10 @@
             mSettings.writeLPr();
         }
 
+        for (PackageFreezer freezer : freezers) {
+            freezer.close();
+        }
+
         if (DEBUG_INSTALL) Slog.d(TAG, "Loaded packages " + loaded);
         sendResourcesChangedBroadcast(true, false, loaded, null);
     }
@@ -18558,12 +18586,17 @@
                 if (ps.pkg == null) continue;
 
                 final ApplicationInfo info = ps.pkg.applicationInfo;
+                final int deleteFlags = PackageManager.DELETE_KEEP_DATA;
                 final PackageRemovedInfo outInfo = new PackageRemovedInfo();
-                if (deletePackageLI(ps.name, null, false, null,
-                        PackageManager.DELETE_KEEP_DATA, outInfo, false, null)) {
-                    unloaded.add(info);
-                } else {
-                    Slog.w(TAG, "Failed to unload " + ps.codePath);
+
+                try (PackageFreezer freezer = freezePackageForDelete(ps.name, deleteFlags,
+                        "unloadPrivatePackagesInner")) {
+                    if (deletePackageLIF(ps.name, null, false, null, deleteFlags, outInfo,
+                            false, null)) {
+                        unloaded.add(info);
+                    } else {
+                        Slog.w(TAG, "Failed to unload " + ps.codePath);
+                    }
                 }
             }
 
@@ -18695,7 +18728,9 @@
         final StorageManager storage = mContext.getSystemService(StorageManager.class);
         for (VolumeInfo vol : storage.getWritablePrivateVolumes()) {
             final String volumeUuid = vol.getFsUuid();
-            reconcileAppsData(volumeUuid, userId, flags);
+            synchronized (mInstallLock) {
+                reconcileAppsDataLI(volumeUuid, userId, flags);
+            }
         }
     }
 
@@ -18708,7 +18743,7 @@
      * Verifies that directories exist and that ownership and labeling is
      * correct for all installed apps.
      */
-    private void reconcileAppsData(String volumeUuid, int userId, int flags) {
+    private void reconcileAppsDataLI(String volumeUuid, int userId, int flags) {
         Slog.v(TAG, "reconcileAppsData for " + volumeUuid + " u" + userId + " 0x"
                 + Integer.toHexString(flags));
 
@@ -18735,9 +18770,11 @@
                     assertPackageKnownAndInstalled(volumeUuid, packageName, userId);
                 } catch (PackageManagerException e) {
                     logCriticalInfo(Log.WARN, "Destroying " + file + " due to: " + e);
-                    synchronized (mInstallLock) {
-                        destroyAppDataLI(volumeUuid, packageName, userId,
-                                StorageManager.FLAG_STORAGE_CE);
+                    try {
+                        mInstaller.destroyAppData(volumeUuid, packageName, userId,
+                                StorageManager.FLAG_STORAGE_CE, 0);
+                    } catch (InstallerException e2) {
+                        logCriticalInfo(Log.WARN, "Failed to destroy: " + e2);
                     }
                 }
             }
@@ -18752,9 +18789,11 @@
                     assertPackageKnownAndInstalled(volumeUuid, packageName, userId);
                 } catch (PackageManagerException e) {
                     logCriticalInfo(Log.WARN, "Destroying " + file + " due to: " + e);
-                    synchronized (mInstallLock) {
-                        destroyAppDataLI(volumeUuid, packageName, userId,
-                                StorageManager.FLAG_STORAGE_DE);
+                    try {
+                        mInstaller.destroyAppData(volumeUuid, packageName, userId,
+                                StorageManager.FLAG_STORAGE_DE, 0);
+                    } catch (InstallerException e2) {
+                        logCriticalInfo(Log.WARN, "Failed to destroy: " + e2);
                     }
                 }
             }
@@ -18777,12 +18816,12 @@
             }
 
             if (ps.getInstalled(userId)) {
-                prepareAppData(volumeUuid, userId, flags, ps.pkg, restoreconNeeded);
+                prepareAppDataLIF(ps.pkg, userId, flags, restoreconNeeded);
 
-                if (maybeMigrateAppData(volumeUuid, userId, ps.pkg)) {
+                if (maybeMigrateAppDataLIF(ps.pkg, userId)) {
                     // We may have just shuffled around app data directories, so
                     // prepare them one more time
-                    prepareAppData(volumeUuid, userId, flags, ps.pkg, restoreconNeeded);
+                    prepareAppDataLIF(ps.pkg, userId, flags, restoreconNeeded);
                 }
 
                 preparedCount++;
@@ -18814,16 +18853,7 @@
      * <p>
      * <em>Note: To avoid a deadlock, do not call this method with {@code mPackages} lock held</em>
      */
-    private void prepareAppDataAfterInstall(PackageParser.Package pkg) {
-        prepareAppDataAfterInstallInternal(pkg);
-        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
-        for (int i = 0; i < childCount; i++) {
-            PackageParser.Package childPackage = pkg.childPackages.get(i);
-            prepareAppDataAfterInstallInternal(childPackage);
-        }
-    }
-
-    private void prepareAppDataAfterInstallInternal(PackageParser.Package pkg) {
+    private void prepareAppDataAfterInstallLIF(PackageParser.Package pkg) {
         final PackageSetting ps;
         synchronized (mPackages) {
             ps = mSettings.mPackages.get(pkg.packageName);
@@ -18844,7 +18874,7 @@
             if (ps.getInstalled(user.id)) {
                 // Whenever an app changes, force a restorecon of its data
                 // TODO: when user data is locked, mark that we're still dirty
-                prepareAppData(pkg.volumeUuid, user.id, flags, pkg, true);
+                prepareAppDataLIF(pkg, user.id, flags, true);
             }
         }
     }
@@ -18857,57 +18887,112 @@
      * will try recovering system apps by wiping data; third-party app data is
      * left intact.
      */
-    private void prepareAppData(String volumeUuid, int userId, int flags,
-            PackageParser.Package pkg, boolean restoreconNeeded) {
+    private void prepareAppDataLIF(PackageParser.Package pkg, int userId, int flags,
+            boolean restoreconNeeded) {
+        if (pkg == null) {
+            Slog.wtf(TAG, "Package was null!", new Throwable());
+            return;
+        }
+        prepareAppDataLeafLIF(pkg, userId, flags, restoreconNeeded);
+        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
+        for (int i = 0; i < childCount; i++) {
+            prepareAppDataLeafLIF(pkg.childPackages.get(i), userId, flags, restoreconNeeded);
+        }
+    }
+
+    private void prepareAppDataLeafLIF(PackageParser.Package pkg, int userId, int flags,
+            boolean restoreconNeeded) {
         if (DEBUG_APP_DATA) {
             Slog.v(TAG, "prepareAppData for " + pkg.packageName + " u" + userId + " 0x"
                     + Integer.toHexString(flags) + (restoreconNeeded ? " restoreconNeeded" : ""));
         }
 
+        final String volumeUuid = pkg.volumeUuid;
         final String packageName = pkg.packageName;
         final ApplicationInfo app = pkg.applicationInfo;
         final int appId = UserHandle.getAppId(app.uid);
 
         Preconditions.checkNotNull(app.seinfo);
 
-        synchronized (mInstallLock) {
-            try {
-                mInstaller.createAppData(volumeUuid, packageName, userId, flags,
-                        appId, app.seinfo, app.targetSdkVersion);
-            } catch (InstallerException e) {
-                if (app.isSystemApp()) {
-                    logCriticalInfo(Log.ERROR, "Failed to create app data for " + packageName
-                            + ", but trying to recover: " + e);
-                    destroyAppDataLI(volumeUuid, packageName, userId, flags);
-                    try {
-                        mInstaller.createAppData(volumeUuid, packageName, userId, flags,
-                                appId, app.seinfo, app.targetSdkVersion);
-                        logCriticalInfo(Log.DEBUG, "Recovery succeeded!");
-                    } catch (InstallerException e2) {
-                        logCriticalInfo(Log.DEBUG, "Recovery failed!");
-                    }
-                } else {
-                    Slog.e(TAG, "Failed to create app data for " + packageName + ": " + e);
+        try {
+            mInstaller.createAppData(volumeUuid, packageName, userId, flags,
+                    appId, app.seinfo, app.targetSdkVersion);
+        } catch (InstallerException e) {
+            if (app.isSystemApp()) {
+                logCriticalInfo(Log.ERROR, "Failed to create app data for " + packageName
+                        + ", but trying to recover: " + e);
+                destroyAppDataLeafLIF(pkg, userId, flags);
+                try {
+                    mInstaller.createAppData(volumeUuid, packageName, userId, flags,
+                            appId, app.seinfo, app.targetSdkVersion);
+                    logCriticalInfo(Log.DEBUG, "Recovery succeeded!");
+                } catch (InstallerException e2) {
+                    logCriticalInfo(Log.DEBUG, "Recovery failed!");
                 }
+            } else {
+                Slog.e(TAG, "Failed to create app data for " + packageName + ": " + e);
             }
+        }
 
-            if (restoreconNeeded) {
-                restoreconAppDataLI(volumeUuid, packageName, userId, flags, appId, app.seinfo);
+        if (restoreconNeeded) {
+            try {
+                mInstaller.restoreconAppData(volumeUuid, packageName, userId, flags, appId,
+                        app.seinfo);
+            } catch (InstallerException e) {
+                Slog.e(TAG, "Failed to restorecon for " + packageName + ": " + e);
             }
+        }
 
-            if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) {
-                // Create a native library symlink only if we have native libraries
-                // and if the native libraries are 32 bit libraries. We do not provide
-                // this symlink for 64 bit libraries.
-                if (app.primaryCpuAbi != null && !VMRuntime.is64BitAbi(app.primaryCpuAbi)) {
-                    final String nativeLibPath = app.nativeLibraryDir;
-                    try {
-                        mInstaller.linkNativeLibraryDirectory(volumeUuid, packageName,
-                                nativeLibPath, userId);
-                    } catch (InstallerException e) {
-                        Slog.e(TAG, "Failed to link native for " + packageName + ": " + e);
+        if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) {
+            try {
+                // CE storage is unlocked right now, so read out the inode and
+                // remember for use later when it's locked
+                // TODO: mark this structure as dirty so we persist it!
+                final long ceDataInode = mInstaller.getAppDataInode(volumeUuid, packageName, userId,
+                        StorageManager.FLAG_STORAGE_CE);
+                synchronized (mPackages) {
+                    final PackageSetting ps = mSettings.mPackages.get(packageName);
+                    if (ps != null) {
+                        ps.setCeDataInode(ceDataInode, userId);
                     }
                 }
+            } catch (InstallerException e) {
+                Slog.e(TAG, "Failed to find inode for " + packageName + ": " + e);
+            }
+        }
+
+        prepareAppDataContentsLeafLIF(pkg, userId, flags);
+    }
+
+    private void prepareAppDataContentsLIF(PackageParser.Package pkg, int userId, int flags) {
+        if (pkg == null) {
+            Slog.wtf(TAG, "Package was null!", new Throwable());
+            return;
+        }
+        prepareAppDataContentsLeafLIF(pkg, userId, flags);
+        final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0;
+        for (int i = 0; i < childCount; i++) {
+            prepareAppDataContentsLeafLIF(pkg.childPackages.get(i), userId, flags);
+        }
+    }
+
+    private void prepareAppDataContentsLeafLIF(PackageParser.Package pkg, int userId, int flags) {
+        final String volumeUuid = pkg.volumeUuid;
+        final String packageName = pkg.packageName;
+        final ApplicationInfo app = pkg.applicationInfo;
+
+        if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) {
+            // Create a native library symlink only if we have native libraries
+            // and if the native libraries are 32 bit libraries. We do not provide
+            // this symlink for 64 bit libraries.
+            if (app.primaryCpuAbi != null && !VMRuntime.is64BitAbi(app.primaryCpuAbi)) {
+                final String nativeLibPath = app.nativeLibraryDir;
+                try {
+                    mInstaller.linkNativeLibraryDirectory(volumeUuid, packageName,
+                            nativeLibPath, userId);
+                } catch (InstallerException e) {
+                    Slog.e(TAG, "Failed to link native for " + packageName + ": " + e);
+                }
             }
         }
     }
@@ -18917,18 +19002,17 @@
      * CE/DE data to match the {@code defaultToDeviceProtectedStorage} flag
      * requested by the app.
      */
-    private boolean maybeMigrateAppData(String volumeUuid, int userId, PackageParser.Package pkg) {
+    private boolean maybeMigrateAppDataLIF(PackageParser.Package pkg, int userId) {
         if (pkg.isSystemApp() && !StorageManager.isFileEncryptedNativeOrEmulated()
                 && PackageManager.APPLY_DEFAULT_TO_DEVICE_PROTECTED_STORAGE) {
             final int storageTarget = pkg.applicationInfo.isDefaultToDeviceProtectedStorage()
                     ? StorageManager.FLAG_STORAGE_DE : StorageManager.FLAG_STORAGE_CE;
-            synchronized (mInstallLock) {
-                try {
-                    mInstaller.migrateAppData(volumeUuid, pkg.packageName, userId, storageTarget);
-                } catch (InstallerException e) {
-                    logCriticalInfo(Log.WARN,
-                            "Failed to migrate " + pkg.packageName + ": " + e.getMessage());
-                }
+            try {
+                mInstaller.migrateAppData(pkg.volumeUuid, pkg.packageName, userId,
+                        storageTarget);
+            } catch (InstallerException e) {
+                logCriticalInfo(Log.WARN,
+                        "Failed to migrate " + pkg.packageName + ": " + e.getMessage());
             }
             return true;
         } else {
@@ -18936,11 +19020,116 @@
         }
     }
 
-    private void unfreezePackage(String packageName) {
+    public PackageFreezer freezePackage(String packageName, String killReason) {
+        return new PackageFreezer(packageName, killReason);
+    }
+
+    public PackageFreezer freezePackageForInstall(String packageName, int installFlags,
+            String killReason) {
+        if ((installFlags & PackageManager.INSTALL_DONT_KILL_APP) != 0) {
+            return new PackageFreezer();
+        } else {
+            return freezePackage(packageName, killReason);
+        }
+    }
+
+    public PackageFreezer freezePackageForDelete(String packageName, int deleteFlags,
+            String killReason) {
+        if ((deleteFlags & PackageManager.DELETE_DONT_KILL_APP) != 0) {
+            return new PackageFreezer();
+        } else {
+            return freezePackage(packageName, killReason);
+        }
+    }
+
+    /**
+     * Class that freezes and kills the given package upon creation, and
+     * unfreezes it upon closing. This is typically used when doing surgery on
+     * app code/data to prevent the app from running while you're working.
+     */
+    private class PackageFreezer implements AutoCloseable {
+        private final String mPackageName;
+        private final PackageFreezer[] mChildren;
+
+        private final boolean mWeFroze;
+
+        private final AtomicBoolean mClosed = new AtomicBoolean();
+        private final CloseGuard mCloseGuard = CloseGuard.get();
+
+        /**
+         * Create and return a stub freezer that doesn't actually do anything,
+         * typically used when someone requested
+         * {@link PackageManager#INSTALL_DONT_KILL_APP} or
+         * {@link PackageManager#DELETE_DONT_KILL_APP}.
+         */
+        public PackageFreezer() {
+            mPackageName = null;
+            mChildren = null;
+            mWeFroze = false;
+            mCloseGuard.open("close");
+        }
+
+        public PackageFreezer(String packageName, String killReason) {
+            synchronized (mPackages) {
+                mPackageName = packageName;
+                mWeFroze = mFrozenPackages.add(mPackageName);
+
+                final PackageSetting ps = mSettings.mPackages.get(mPackageName);
+                if (ps != null) {
+                    killApplication(ps.name, ps.appId, killReason);
+                }
+
+                final PackageParser.Package p = mPackages.get(packageName);
+                if (p != null && p.childPackages != null) {
+                    final int N = p.childPackages.size();
+                    mChildren = new PackageFreezer[N];
+                    for (int i = 0; i < N; i++) {
+                        mChildren[i] = new PackageFreezer(p.childPackages.get(i).packageName,
+                                killReason);
+                    }
+                } else {
+                    mChildren = null;
+                }
+            }
+            mCloseGuard.open("close");
+        }
+
+        @Override
+        protected void finalize() throws Throwable {
+            try {
+                mCloseGuard.warnIfOpen();
+                close();
+            } finally {
+                super.finalize();
+            }
+        }
+
+        @Override
+        public void close() {
+            mCloseGuard.close();
+            if (mClosed.compareAndSet(false, true)) {
+                synchronized (mPackages) {
+                    if (mWeFroze) {
+                        mFrozenPackages.remove(mPackageName);
+                    }
+
+                    if (mChildren != null) {
+                        for (PackageFreezer freezer : mChildren) {
+                            freezer.close();
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    /**
+     * Verify that given package is currently frozen.
+     */
+    private void checkPackageFrozen(String packageName) {
         synchronized (mPackages) {
-            final PackageSetting ps = mSettings.mPackages.get(packageName);
-            if (ps != null) {
-                ps.frozen = false;
+            if (!mFrozenPackages.contains(packageName)) {
+                Slog.wtf(TAG, "Expected " + packageName + " to be frozen!", new Throwable());
             }
         }
     }
@@ -18980,6 +19169,7 @@
         final String seinfo;
         final String label;
         final int targetSdkVersion;
+        final PackageFreezer freezer;
 
         // reader
         synchronized (mPackages) {
@@ -19021,11 +19211,10 @@
                         "Device admin cannot be moved");
             }
 
-            if (ps.frozen) {
+            if (mFrozenPackages.contains(packageName)) {
                 throw new PackageManagerException(MOVE_FAILED_OPERATION_PENDING,
                         "Failed to move already frozen package");
             }
-            ps.frozen = true;
 
             codeFile = new File(pkg.codePath);
             installerPackageName = ps.installerPackageName;
@@ -19034,14 +19223,7 @@
             seinfo = pkg.applicationInfo.seinfo;
             label = String.valueOf(pm.getApplicationLabel(pkg.applicationInfo));
             targetSdkVersion = pkg.applicationInfo.targetSdkVersion;
-        }
-
-        // Now that we're guarded by frozen state, kill app during move
-        final long token = Binder.clearCallingIdentity();
-        try {
-            killApplication(packageName, appId, "move pkg");
-        } finally {
-            Binder.restoreCallingIdentity(token);
+            freezer = new PackageFreezer(packageName, "movePackageInternal");
         }
 
         final Bundle extras = new Bundle();
@@ -19065,7 +19247,7 @@
             final VolumeInfo volume = storage.findVolumeByUuid(volumeUuid);
             if (volume == null || volume.getType() != VolumeInfo.TYPE_PRIVATE
                     || !volume.isMountedWritable()) {
-                unfreezePackage(packageName);
+                freezer.close();
                 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR,
                         "Move location not mounted private volume");
             }
@@ -19080,7 +19262,7 @@
         final PackageStats stats = new PackageStats(null, -1);
         synchronized (mInstaller) {
             if (!getPackageSizeInfoLI(packageName, -1, stats)) {
-                unfreezePackage(packageName);
+                freezer.close();
                 throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR,
                         "Failed to measure package size");
             }
@@ -19098,7 +19280,7 @@
         }
 
         if (sizeBytes > storage.getStorageBytesUntilLow(measurePath)) {
-            unfreezePackage(packageName);
+            freezer.close();
             throw new PackageManagerException(MOVE_FAILED_INTERNAL_ERROR,
                     "Not enough free space to move");
         }
@@ -19119,10 +19301,7 @@
                         + PackageManager.installStatusToString(returnCode, msg));
 
                 installedLatch.countDown();
-
-                // Regardless of success or failure of the move operation,
-                // always unfreeze the package
-                unfreezePackage(packageName);
+                freezer.close();
 
                 final int status = PackageManager.installStatusToPublicStatus(returnCode);
                 switch (status) {
diff --git a/services/core/java/com/android/server/pm/PackageSettingBase.java b/services/core/java/com/android/server/pm/PackageSettingBase.java
index 1434718..9d04472 100644
--- a/services/core/java/com/android/server/pm/PackageSettingBase.java
+++ b/services/core/java/com/android/server/pm/PackageSettingBase.java
@@ -114,12 +114,6 @@
     int installStatus = PKG_INSTALL_COMPLETE;
 
     /**
-     * Non-persisted value indicating this package has been temporarily frozen,
-     * usually during a critical section of the package update pipeline. The
-     * platform will refuse to launch packages in a frozen state.
-     */
-    boolean frozen = false;
-    /**
      * Non-persisted value. During an "upgrade without restart", we need the set
      * of all previous code paths so we can surgically add the new APKs to the
      * active classloader. If at any point an application is upgraded with a
@@ -329,6 +323,14 @@
         return res;
     }
 
+    long getCeDataInode(int userId) {
+        return readUserState(userId).ceDataInode;
+    }
+
+    void setCeDataInode(long ceDataInode, int userId) {
+        modifyUserState(userId).ceDataInode = ceDataInode;
+    }
+
     boolean getStopped(int userId) {
         return readUserState(userId).stopped;
     }
@@ -369,12 +371,13 @@
         modifyUserState(userId).blockUninstall = blockUninstall;
     }
 
-    void setUserState(int userId, int enabled, boolean installed, boolean stopped,
+    void setUserState(int userId, long ceDataInode, int enabled, boolean installed, boolean stopped,
             boolean notLaunched, boolean hidden, boolean suspended,
             String lastDisableAppCaller, ArraySet<String> enabledComponents,
             ArraySet<String> disabledComponents, boolean blockUninstall, int domainVerifState,
             int linkGeneration) {
         PackageUserState state = modifyUserState(userId);
+        state.ceDataInode = ceDataInode;
         state.enabled = enabled;
         state.installed = installed;
         state.stopped = stopped;
diff --git a/services/core/java/com/android/server/pm/Settings.java b/services/core/java/com/android/server/pm/Settings.java
index 3c3c576..7debf9b 100644
--- a/services/core/java/com/android/server/pm/Settings.java
+++ b/services/core/java/com/android/server/pm/Settings.java
@@ -195,23 +195,26 @@
     private static final String ATTR_NAME = "name";
     private static final String ATTR_USER = "user";
     private static final String ATTR_CODE = "code";
-    private static final String ATTR_NOT_LAUNCHED = "nl";
-    private static final String ATTR_ENABLED = "enabled";
     private static final String ATTR_GRANTED = "granted";
     private static final String ATTR_FLAGS = "flags";
-    private static final String ATTR_ENABLED_CALLER = "enabledCaller";
+
+    private static final String ATTR_CE_DATA_INODE = "ceDataInode";
+    private static final String ATTR_INSTALLED = "inst";
     private static final String ATTR_STOPPED = "stopped";
+    private static final String ATTR_NOT_LAUNCHED = "nl";
     // Legacy, here for reading older versions of the package-restrictions.
     private static final String ATTR_BLOCKED = "blocked";
     // New name for the above attribute.
     private static final String ATTR_HIDDEN = "hidden";
     private static final String ATTR_SUSPENDED = "suspended";
-    private static final String ATTR_INSTALLED = "inst";
     private static final String ATTR_BLOCK_UNINSTALL = "blockUninstall";
+    private static final String ATTR_ENABLED = "enabled";
+    private static final String ATTR_ENABLED_CALLER = "enabledCaller";
     private static final String ATTR_DOMAIN_VERIFICATON_STATE = "domainVerificationStatus";
+    private static final String ATTR_APP_LINK_GENERATION = "app-link-generation";
+
     private static final String ATTR_PACKAGE_NAME = "packageName";
     private static final String ATTR_FINGERPRINT = "fingerprint";
-    private static final String ATTR_APP_LINK_GENERATION = "app-link-generation";
     private static final String ATTR_VOLUME_UUID = "volumeUuid";
     private static final String ATTR_SDK_VERSION = "sdkVersion";
     private static final String ATTR_DATABASE_VERSION = "databaseVersion";
@@ -247,6 +250,9 @@
     /** Map from package name to settings */
     final ArrayMap<String, PackageSetting> mPackages = new ArrayMap<>();
 
+    /** List of packages that installed other packages */
+    final ArraySet<String> mInstallerPackages = new ArraySet<>();
+
     /** Map from package name to appId */
     private final ArrayMap<String, Integer> mKernelMapping = new ArrayMap<>();
 
@@ -360,7 +366,7 @@
     // Packages that have been uninstalled and still need their external
     // storage data deleted.
     final ArrayList<PackageCleanItem> mPackagesToBeCleaned = new ArrayList<PackageCleanItem>();
-    
+
     // Packages that have been renamed since they were first installed.
     // Keys are the new names of the packages, values are the original
     // names.  The packages appear everwhere else under their original
@@ -506,6 +512,9 @@
         PackageSetting p = mPackages.get(pkgName);
         if (p != null) {
             p.setInstallerPackageName(installerPkgName);
+            if (installerPkgName != null) {
+                mInstallerPackages.add(installerPkgName);
+            }
         }
     }
 
@@ -572,7 +581,7 @@
         }
         PackageSetting ret = addPackageLPw(name, p.realName, p.codePath, p.resourcePath,
                 p.legacyNativeLibraryPathString, p.primaryCpuAbiString,
-                p.secondaryCpuAbiString, p.secondaryCpuAbiString,
+                p.secondaryCpuAbiString, p.cpuAbiOverrideString,
                 p.appId, p.versionCode, p.pkgFlags, p.pkgPrivateFlags,
                 p.parentPackageName, p.childPackageNames);
         mDisabledSysPackages.remove(name);
@@ -784,7 +793,7 @@
                                     || (installUserId == UserHandle.USER_ALL
                                         && !isAdbInstallDisallowed(userManager, user.id))
                                     || installUserId == user.id;
-                            p.setUserState(user.id, COMPONENT_ENABLED_STATE_DEFAULT,
+                            p.setUserState(user.id, 0, COMPONENT_ENABLED_STATE_DEFAULT,
                                     installed,
                                     true, // stopped,
                                     true, // notLaunched
@@ -1062,6 +1071,7 @@
         final PackageSetting p = mPackages.get(name);
         if (p != null) {
             mPackages.remove(name);
+            removeInstallerPackageStatus(name);
             if (p.sharedUser != null) {
                 p.sharedUser.removePackage(p);
                 if (p.sharedUser.packages.size() == 0) {
@@ -1077,6 +1087,26 @@
         return -1;
     }
 
+    /**
+     * Checks if {@param packageName} is an installer package and if so, clear the installer
+     * package name of the packages that are installed by this.
+     */
+    private void removeInstallerPackageStatus(String packageName) {
+        // Check if the package to be removed is an installer package.
+        if (!mInstallerPackages.contains(packageName)) {
+            return;
+        }
+        for (int i = 0; i < mPackages.size(); i++) {
+            final PackageSetting ps = mPackages.valueAt(i);
+            final String installerPackageName = ps.getInstallerPackageName();
+            if (installerPackageName != null
+                    && installerPackageName.equals(packageName)) {
+                ps.setInstallerPackageName(null);
+            }
+        }
+        mInstallerPackages.remove(packageName);
+    }
+
     private void replacePackageLPw(String name, PackageSetting newp) {
         final PackageSetting p = mPackages.get(name);
         if (p != null) {
@@ -1547,7 +1577,7 @@
                     // in the stopped state, but not at first boot.  Also
                     // consider all applications to be installed.
                     for (PackageSetting pkg : mPackages.values()) {
-                        pkg.setUserState(userId, COMPONENT_ENABLED_STATE_DEFAULT,
+                        pkg.setUserState(userId, 0, COMPONENT_ENABLED_STATE_DEFAULT,
                                 true,   // installed
                                 false,  // stopped
                                 false,  // notLaunched
@@ -1599,17 +1629,16 @@
                         XmlUtils.skipCurrentTag(parser);
                         continue;
                     }
-                    final String enabledStr = parser.getAttributeValue(null, ATTR_ENABLED);
-                    final int enabled = enabledStr == null
-                            ? COMPONENT_ENABLED_STATE_DEFAULT : Integer.parseInt(enabledStr);
-                    final String enabledCaller = parser.getAttributeValue(null,
-                            ATTR_ENABLED_CALLER);
-                    final String installedStr = parser.getAttributeValue(null, ATTR_INSTALLED);
-                    final boolean installed = installedStr == null
-                            ? true : Boolean.parseBoolean(installedStr);
-                    final String stoppedStr = parser.getAttributeValue(null, ATTR_STOPPED);
-                    final boolean stopped = stoppedStr == null
-                            ? false : Boolean.parseBoolean(stoppedStr);
+
+                    final long ceDataInode = XmlUtils.readLongAttribute(parser, ATTR_CE_DATA_INODE,
+                            0);
+                    final boolean installed = XmlUtils.readBooleanAttribute(parser, ATTR_INSTALLED,
+                            true);
+                    final boolean stopped = XmlUtils.readBooleanAttribute(parser, ATTR_STOPPED,
+                            false);
+                    final boolean notLaunched = XmlUtils.readBooleanAttribute(parser,
+                            ATTR_NOT_LAUNCHED, false);
+
                     // For backwards compatibility with the previous name of "blocked", which
                     // now means hidden, read the old attribute as well.
                     final String blockedStr = parser.getAttributeValue(null, ATTR_BLOCKED);
@@ -1618,25 +1647,21 @@
                     final String hiddenStr = parser.getAttributeValue(null, ATTR_HIDDEN);
                     hidden = hiddenStr == null
                             ? hidden : Boolean.parseBoolean(hiddenStr);
-                    final String suspendedStr = parser.getAttributeValue(null, ATTR_SUSPENDED);
-                    final boolean suspended = suspendedStr == null
-                            ? false : Boolean.parseBoolean(suspendedStr);
-                    final String notLaunchedStr = parser.getAttributeValue(null, ATTR_NOT_LAUNCHED);
-                    final boolean notLaunched = stoppedStr == null
-                            ? false : Boolean.parseBoolean(notLaunchedStr);
-                    final String blockUninstallStr = parser.getAttributeValue(null,
-                            ATTR_BLOCK_UNINSTALL);
-                    final boolean blockUninstall = blockUninstallStr == null
-                            ? false : Boolean.parseBoolean(blockUninstallStr);
 
-                    final String verifStateStr =
-                            parser.getAttributeValue(null, ATTR_DOMAIN_VERIFICATON_STATE);
-                    final int verifState = (verifStateStr == null) ?
-                            PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED :
-                            Integer.parseInt(verifStateStr);
+                    final boolean suspended = XmlUtils.readBooleanAttribute(parser, ATTR_SUSPENDED,
+                            false);
+                    final boolean blockUninstall = XmlUtils.readBooleanAttribute(parser,
+                            ATTR_BLOCK_UNINSTALL, false);
+                    final int enabled = XmlUtils.readIntAttribute(parser, ATTR_ENABLED,
+                            COMPONENT_ENABLED_STATE_DEFAULT);
+                    final String enabledCaller = parser.getAttributeValue(null,
+                            ATTR_ENABLED_CALLER);
 
-                    final String linkGenStr = parser.getAttributeValue(null, ATTR_APP_LINK_GENERATION);
-                    final int linkGeneration = linkGenStr == null ? 0 : Integer.parseInt(linkGenStr);
+                    final int verifState = XmlUtils.readIntAttribute(parser,
+                            ATTR_DOMAIN_VERIFICATON_STATE,
+                            PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED);
+                    final int linkGeneration = XmlUtils.readIntAttribute(parser,
+                            ATTR_APP_LINK_GENERATION, 0);
                     if (linkGeneration > maxAppLinkGeneration) {
                         maxAppLinkGeneration = linkGeneration;
                     }
@@ -1660,8 +1685,8 @@
                         }
                     }
 
-                    ps.setUserState(userId, enabled, installed, stopped, notLaunched, hidden,
-                            suspended, enabledCaller, enabledComponents, disabledComponents,
+                    ps.setUserState(userId, ceDataInode, enabled, installed, stopped, notLaunched,
+                            hidden, suspended, enabledCaller, enabledComponents, disabledComponents,
                             blockUninstall, verifState, linkGeneration);
                 } else if (tagName.equals("preferred-activities")) {
                     readPreferredActivitiesLPw(parser, userId);
@@ -1900,80 +1925,69 @@
             serializer.startTag(null, TAG_PACKAGE_RESTRICTIONS);
 
             for (final PackageSetting pkg : mPackages.values()) {
-                PackageUserState ustate = pkg.readUserState(userId);
-                if (ustate.stopped || ustate.notLaunched || !ustate.installed
-                        || ustate.enabled != COMPONENT_ENABLED_STATE_DEFAULT
-                        || ustate.hidden
-                        || ustate.suspended
-                        || (ustate.enabledComponents != null
-                                && ustate.enabledComponents.size() > 0)
-                        || (ustate.disabledComponents != null
-                                && ustate.disabledComponents.size() > 0)
-                        || ustate.blockUninstall
-                        || (ustate.domainVerificationStatus !=
-                            PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED)) {
-                    serializer.startTag(null, TAG_PACKAGE);
-                    serializer.attribute(null, ATTR_NAME, pkg.name);
-                    if (DEBUG_MU) Log.i(TAG, "  pkg=" + pkg.name + ", state=" + ustate.enabled);
+                final PackageUserState ustate = pkg.readUserState(userId);
+                if (DEBUG_MU) Log.i(TAG, "  pkg=" + pkg.name + ", state=" + ustate.enabled);
 
-                    if (!ustate.installed) {
-                        serializer.attribute(null, ATTR_INSTALLED, "false");
-                    }
-                    if (ustate.stopped) {
-                        serializer.attribute(null, ATTR_STOPPED, "true");
-                    }
-                    if (ustate.notLaunched) {
-                        serializer.attribute(null, ATTR_NOT_LAUNCHED, "true");
-                    }
-                    if (ustate.hidden) {
-                        serializer.attribute(null, ATTR_HIDDEN, "true");
-                    }
-                    if (ustate.suspended) {
-                        serializer.attribute(null, ATTR_SUSPENDED, "true");
-                    }
-                    if (ustate.blockUninstall) {
-                        serializer.attribute(null, ATTR_BLOCK_UNINSTALL, "true");
-                    }
-                    if (ustate.enabled != COMPONENT_ENABLED_STATE_DEFAULT) {
-                        serializer.attribute(null, ATTR_ENABLED,
-                                Integer.toString(ustate.enabled));
-                        if (ustate.lastDisableAppCaller != null) {
-                            serializer.attribute(null, ATTR_ENABLED_CALLER,
-                                    ustate.lastDisableAppCaller);
-                        }
-                    }
-                    if (ustate.domainVerificationStatus !=
-                            PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED) {
-                        serializer.attribute(null, ATTR_DOMAIN_VERIFICATON_STATE,
-                                Integer.toString(ustate.domainVerificationStatus));
-                    }
-                    if (ustate.appLinkGeneration != 0) {
-                        serializer.attribute(null, ATTR_APP_LINK_GENERATION,
-                                Integer.toString(ustate.appLinkGeneration));
-                    }
-                    if (ustate.enabledComponents != null
-                            && ustate.enabledComponents.size() > 0) {
-                        serializer.startTag(null, TAG_ENABLED_COMPONENTS);
-                        for (final String name : ustate.enabledComponents) {
-                            serializer.startTag(null, TAG_ITEM);
-                            serializer.attribute(null, ATTR_NAME, name);
-                            serializer.endTag(null, TAG_ITEM);
-                        }
-                        serializer.endTag(null, TAG_ENABLED_COMPONENTS);
-                    }
-                    if (ustate.disabledComponents != null
-                            && ustate.disabledComponents.size() > 0) {
-                        serializer.startTag(null, TAG_DISABLED_COMPONENTS);
-                        for (final String name : ustate.disabledComponents) {
-                            serializer.startTag(null, TAG_ITEM);
-                            serializer.attribute(null, ATTR_NAME, name);
-                            serializer.endTag(null, TAG_ITEM);
-                        }
-                        serializer.endTag(null, TAG_DISABLED_COMPONENTS);
-                    }
-
-                    serializer.endTag(null, TAG_PACKAGE);
+                serializer.startTag(null, TAG_PACKAGE);
+                serializer.attribute(null, ATTR_NAME, pkg.name);
+                if (ustate.ceDataInode != 0) {
+                    XmlUtils.writeLongAttribute(serializer, ATTR_CE_DATA_INODE, ustate.ceDataInode);
                 }
+                if (!ustate.installed) {
+                    serializer.attribute(null, ATTR_INSTALLED, "false");
+                }
+                if (ustate.stopped) {
+                    serializer.attribute(null, ATTR_STOPPED, "true");
+                }
+                if (ustate.notLaunched) {
+                    serializer.attribute(null, ATTR_NOT_LAUNCHED, "true");
+                }
+                if (ustate.hidden) {
+                    serializer.attribute(null, ATTR_HIDDEN, "true");
+                }
+                if (ustate.suspended) {
+                    serializer.attribute(null, ATTR_SUSPENDED, "true");
+                }
+                if (ustate.blockUninstall) {
+                    serializer.attribute(null, ATTR_BLOCK_UNINSTALL, "true");
+                }
+                if (ustate.enabled != COMPONENT_ENABLED_STATE_DEFAULT) {
+                    serializer.attribute(null, ATTR_ENABLED,
+                            Integer.toString(ustate.enabled));
+                    if (ustate.lastDisableAppCaller != null) {
+                        serializer.attribute(null, ATTR_ENABLED_CALLER,
+                                ustate.lastDisableAppCaller);
+                    }
+                }
+                if (ustate.domainVerificationStatus !=
+                        PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED) {
+                    XmlUtils.writeIntAttribute(serializer, ATTR_DOMAIN_VERIFICATON_STATE,
+                            ustate.domainVerificationStatus);
+                }
+                if (ustate.appLinkGeneration != 0) {
+                    XmlUtils.writeIntAttribute(serializer, ATTR_APP_LINK_GENERATION,
+                            ustate.appLinkGeneration);
+                }
+                if (!ArrayUtils.isEmpty(ustate.enabledComponents)) {
+                    serializer.startTag(null, TAG_ENABLED_COMPONENTS);
+                    for (final String name : ustate.enabledComponents) {
+                        serializer.startTag(null, TAG_ITEM);
+                        serializer.attribute(null, ATTR_NAME, name);
+                        serializer.endTag(null, TAG_ITEM);
+                    }
+                    serializer.endTag(null, TAG_ENABLED_COMPONENTS);
+                }
+                if (!ArrayUtils.isEmpty(ustate.disabledComponents)) {
+                    serializer.startTag(null, TAG_DISABLED_COMPONENTS);
+                    for (final String name : ustate.disabledComponents) {
+                        serializer.startTag(null, TAG_ITEM);
+                        serializer.attribute(null, ATTR_NAME, name);
+                        serializer.endTag(null, TAG_ITEM);
+                    }
+                    serializer.endTag(null, TAG_DISABLED_COMPONENTS);
+                }
+
+                serializer.endTag(null, TAG_PACKAGE);
             }
 
             writePreferredActivitiesLPr(serializer, userId, true);
@@ -2672,7 +2686,7 @@
 
     void writePermissionLPr(XmlSerializer serializer, BasePermission bp)
             throws XmlPullParserException, java.io.IOException {
-        if (bp.type != BasePermission.TYPE_BUILTIN && bp.sourcePackage != null) {
+        if (bp.sourcePackage != null) {
             serializer.startTag(null, TAG_ITEM);
             serializer.attribute(null, ATTR_NAME, bp.name);
             serializer.attribute(null, "package", bp.sourcePackage);
@@ -2742,6 +2756,7 @@
         mPendingPackages.clear();
         mPastSignatures.clear();
         mKeySetRefs.clear();
+        mInstallerPackages.clear();
 
         try {
             if (str == null) {
@@ -3333,8 +3348,12 @@
                 final String ptype = parser.getAttributeValue(null, "type");
                 if (name != null && sourcePackage != null) {
                     final boolean dynamic = "dynamic".equals(ptype);
-                    final BasePermission bp = new BasePermission(name.intern(), sourcePackage,
-                            dynamic ? BasePermission.TYPE_DYNAMIC : BasePermission.TYPE_NORMAL);
+                    BasePermission bp = out.get(name);
+                    // If the permission is builtin, do not clobber it.
+                    if (bp == null || bp.type != BasePermission.TYPE_BUILTIN) {
+                        bp = new BasePermission(name.intern(), sourcePackage,
+                                dynamic ? BasePermission.TYPE_DYNAMIC : BasePermission.TYPE_NORMAL);
+                    }
                     bp.protectionLevel = readInt(parser, null, "protection",
                             PermissionInfo.PROTECTION_NORMAL);
                     bp.protectionLevel = PermissionInfo.fixProtectionLevel(bp.protectionLevel);
@@ -3706,6 +3725,10 @@
                 packageSetting.setEnabled(COMPONENT_ENABLED_STATE_DEFAULT, 0, null);
             }
 
+            if (installerPackageName != null) {
+                mInstallerPackages.add(installerPackageName);
+            }
+
             final String installStatusStr = parser.getAttributeValue(null, "installStatus");
             if (installStatusStr != null) {
                 if (installStatusStr.equalsIgnoreCase("false")) {
@@ -3724,7 +3747,7 @@
                 }
 
                 String tagName = parser.getName();
-                // Legacy 
+                // Legacy
                 if (tagName.equals(TAG_DISABLED_COMPONENTS)) {
                     readDisabledComponentsLPw(packageSetting, parser, 0);
                 } else if (tagName.equals(TAG_ENABLED_COMPONENTS)) {
@@ -4293,10 +4316,6 @@
             pw.print(Integer.toHexString(System.identityHashCode(ps)));
             pw.println("):");
 
-        if (ps.frozen) {
-            pw.print(prefix); pw.println("  FROZEN!");
-        }
-
         if (ps.realName != null) {
             pw.print(prefix); pw.print("  compat name=");
             pw.println(ps.name);
@@ -4504,6 +4523,8 @@
 
         for (UserInfo user : users) {
             pw.print(prefix); pw.print("  User "); pw.print(user.id); pw.print(": ");
+            pw.print("ceDataInode=");
+            pw.print(ps.getCeDataInode(user.id));
             pw.print(" installed=");
             pw.print(ps.getInstalled(user.id));
             pw.print(" hidden=");
diff --git a/services/core/java/com/android/server/pm/ShortcutPackage.java b/services/core/java/com/android/server/pm/ShortcutPackage.java
index 1076a7a..b9b65eb 100644
--- a/services/core/java/com/android/server/pm/ShortcutPackage.java
+++ b/services/core/java/com/android/server/pm/ShortcutPackage.java
@@ -17,6 +17,7 @@
 
 import android.annotation.NonNull;
 import android.annotation.Nullable;
+import android.annotation.UserIdInt;
 import android.content.ComponentName;
 import android.content.Intent;
 import android.content.pm.ShortcutInfo;
@@ -27,6 +28,7 @@
 import android.util.Slog;
 
 import com.android.internal.annotations.VisibleForTesting;
+import com.android.internal.util.XmlUtils;
 
 import org.xmlpull.v1.XmlPullParser;
 import org.xmlpull.v1.XmlPullParserException;
@@ -36,7 +38,7 @@
 import java.io.IOException;
 import java.io.PrintWriter;
 import java.util.ArrayList;
-import java.util.Collection;
+import java.util.Arrays;
 import java.util.List;
 import java.util.function.Predicate;
 
@@ -50,6 +52,7 @@
     private static final String TAG_INTENT_EXTRAS = "intent-extras";
     private static final String TAG_EXTRAS = "extras";
     private static final String TAG_SHORTCUT = "shortcut";
+    private static final String TAG_CATEGORIES = "categories";
 
     private static final String ATTR_NAME = "name";
     private static final String ATTR_DYNAMIC_COUNT = "dynamic-count";
@@ -66,6 +69,11 @@
     private static final String ATTR_ICON_RES = "icon-res";
     private static final String ATTR_BITMAP_PATH = "bitmap-path";
 
+    private static final String NAME_CATEGORIES = "categories";
+
+    private static final String TAG_STRING_ARRAY_XMLUTILS = "string-array";
+    private static final String ATTR_NAME_XMLUTILS = "name";
+
     /**
      * All the shortcuts from the package, keyed on IDs.
      */
@@ -304,7 +312,7 @@
      * and return true.  Otherwise just return false.
      */
     public boolean tryApiCall(@NonNull ShortcutService s) {
-        if (getApiCallCount(s) >= s.mMaxDailyUpdates) {
+        if (getApiCallCount(s) >= s.mMaxUpdatesPerInterval) {
             return false;
         }
         mApiCallCount++;
@@ -484,6 +492,16 @@
             ShortcutService.writeAttr(out, ATTR_BITMAP_PATH, si.getBitmapPath());
         }
 
+        {
+            final List<String> cat = si.getCategories();
+            if (cat != null && cat.size() > 0) {
+                out.startTag(null, TAG_CATEGORIES);
+                XmlUtils.writeStringArrayXml(cat.toArray(new String[cat.size()]),
+                        NAME_CATEGORIES, out);
+                out.endTag(null, TAG_CATEGORIES);
+            }
+        }
+
         ShortcutService.writeTagExtra(out, TAG_INTENT_EXTRAS,
                 si.getIntentPersistableExtras());
         ShortcutService.writeTagExtra(out, TAG_EXTRAS, si.getExtras());
@@ -522,7 +540,7 @@
                         ret.getPackageInfo().loadFromXml(parser, fromBackup);
                         continue;
                     case TAG_SHORTCUT:
-                        final ShortcutInfo si = parseShortcut(parser, packageName);
+                        final ShortcutInfo si = parseShortcut(parser, packageName, ownerUserId);
 
                         // Don't use addShortcut(), we don't need to save the icon.
                         ret.mShortcuts.put(si.getId(), si);
@@ -534,8 +552,8 @@
         return ret;
     }
 
-    private static ShortcutInfo parseShortcut(XmlPullParser parser, String packageName)
-            throws IOException, XmlPullParserException {
+    private static ShortcutInfo parseShortcut(XmlPullParser parser, String packageName,
+            @UserIdInt int userId) throws IOException, XmlPullParserException {
         String id;
         ComponentName activityComponent;
         // Icon icon;
@@ -549,6 +567,7 @@
         int flags;
         int iconRes;
         String bitmapPath;
+        String[] categories = null;
 
         id = ShortcutService.parseStringAttribute(parser, ATTR_ID);
         activityComponent = ShortcutService.parseComponentNameAttribute(parser,
@@ -582,11 +601,21 @@
                 case TAG_EXTRAS:
                     extras = PersistableBundle.restoreFromXml(parser);
                     continue;
+                case TAG_CATEGORIES:
+                    // This just contains string-array.
+                    continue;
+                case TAG_STRING_ARRAY_XMLUTILS:
+                    if (NAME_CATEGORIES.equals(ShortcutService.parseStringAttribute(parser,
+                            ATTR_NAME_XMLUTILS))) {
+                        categories = XmlUtils.readThisStringArrayXml(parser, TAG_STRING_ARRAY_XMLUTILS, null);
+                    }
+                    continue;
             }
             throw ShortcutService.throwForInvalidTag(depth, tag);
         }
         return new ShortcutInfo(
-                id, packageName, activityComponent, /* icon =*/ null, title, text, intent,
+                userId, id, packageName, activityComponent, /* icon =*/ null, title, text,
+                (categories == null ? null : Arrays.asList(categories)), intent,
                 intentPersistableExtras, weight, extras, lastChangedTimestamp, flags,
                 iconRes, bitmapPath);
     }
diff --git a/services/core/java/com/android/server/pm/ShortcutService.java b/services/core/java/com/android/server/pm/ShortcutService.java
index 5c1e7a8..ac6510a 100644
--- a/services/core/java/com/android/server/pm/ShortcutService.java
+++ b/services/core/java/com/android/server/pm/ShortcutService.java
@@ -126,10 +126,10 @@
     static final boolean DEBUG_LOAD = false; // STOPSHIP if true
 
     @VisibleForTesting
-    static final long DEFAULT_RESET_INTERVAL_SEC = 24 * 60 * 60; // 1 day
+    static final long DEFAULT_RESET_INTERVAL_SEC = 60 * 60; // 1 hour
 
     @VisibleForTesting
-    static final int DEFAULT_MAX_DAILY_UPDATES = 10;
+    static final int DEFAULT_MAX_UPDATES_PER_INTERVAL = 2;
 
     @VisibleForTesting
     static final int DEFAULT_MAX_SHORTCUTS_PER_APP = 5;
@@ -180,7 +180,7 @@
         /**
          * Key name for the max number of modifying API calls per app for every interval. (int)
          */
-        String KEY_MAX_DAILY_UPDATES = "max_daily_updates";
+        String KEY_MAX_UPDATES_PER_INTERVAL = "max_updates_per_interval";
 
         /**
          * Key name for the max icon dimensions in DP, for non-low-memory devices.
@@ -232,9 +232,9 @@
     private int mMaxDynamicShortcuts;
 
     /**
-     * Max number of updating API calls that each application can make a day.
+     * Max number of updating API calls that each application can make during the interval.
      */
-    int mMaxDailyUpdates;
+    int mMaxUpdatesPerInterval;
 
     /**
      * Actual throttling-reset interval.  By default it's a day.
@@ -419,26 +419,26 @@
             result = false;
         }
 
-        mSaveDelayMillis = (int) parser.getLong(ConfigConstants.KEY_SAVE_DELAY_MILLIS,
-                DEFAULT_SAVE_DELAY_MS);
+        mSaveDelayMillis = Math.max(0, (int) parser.getLong(ConfigConstants.KEY_SAVE_DELAY_MILLIS,
+                DEFAULT_SAVE_DELAY_MS));
 
-        mResetInterval = parser.getLong(
+        mResetInterval = Math.max(1, parser.getLong(
                 ConfigConstants.KEY_RESET_INTERVAL_SEC, DEFAULT_RESET_INTERVAL_SEC)
-                * 1000L;
+                * 1000L);
 
-        mMaxDailyUpdates = (int) parser.getLong(
-                ConfigConstants.KEY_MAX_DAILY_UPDATES, DEFAULT_MAX_DAILY_UPDATES);
+        mMaxUpdatesPerInterval = Math.max(0, (int) parser.getLong(
+                ConfigConstants.KEY_MAX_UPDATES_PER_INTERVAL, DEFAULT_MAX_UPDATES_PER_INTERVAL));
 
-        mMaxDynamicShortcuts = (int) parser.getLong(
-                ConfigConstants.KEY_MAX_SHORTCUTS, DEFAULT_MAX_SHORTCUTS_PER_APP);
+        mMaxDynamicShortcuts = Math.max(0, (int) parser.getLong(
+                ConfigConstants.KEY_MAX_SHORTCUTS, DEFAULT_MAX_SHORTCUTS_PER_APP));
 
-        final int iconDimensionDp = injectIsLowRamDevice()
+        final int iconDimensionDp = Math.max(1, injectIsLowRamDevice()
                 ? (int) parser.getLong(
                     ConfigConstants.KEY_MAX_ICON_DIMENSION_DP_LOWRAM,
                     DEFAULT_MAX_ICON_DIMENSION_LOWRAM_DP)
                 : (int) parser.getLong(
                     ConfigConstants.KEY_MAX_ICON_DIMENSION_DP,
-                    DEFAULT_MAX_ICON_DIMENSION_DP);
+                    DEFAULT_MAX_ICON_DIMENSION_DP));
 
         mMaxIconDimension = injectDipToPixel(iconDimensionDp);
 
@@ -968,7 +968,8 @@
                 return; // has no icon
             }
 
-            Bitmap bitmap = null;
+            Bitmap bitmap;
+            Bitmap bitmapToRecycle = null;
             try {
                 switch (icon.getType()) {
                     case Icon.TYPE_RESOURCE: {
@@ -979,7 +980,7 @@
                         return;
                     }
                     case Icon.TYPE_BITMAP: {
-                        bitmap = icon.getBitmap();
+                        bitmap = icon.getBitmap(); // Don't recycle in this case.
                         break;
                     }
                     case Icon.TYPE_URI: {
@@ -987,7 +988,8 @@
 
                         try (InputStream is = mContext.getContentResolver().openInputStream(uri)) {
 
-                            bitmap = BitmapFactory.decodeStream(is);
+                            bitmapToRecycle = BitmapFactory.decodeStream(is);
+                            bitmap = bitmapToRecycle;
 
                         } catch (IOException e) {
                             Slog.e(TAG, "Unable to load icon from " + uri);
@@ -1011,8 +1013,14 @@
                     try {
                         path = out.getFile();
 
-                        shrinkBitmap(bitmap, mMaxIconDimension)
-                                .compress(mIconPersistFormat, mIconPersistQuality, out);
+                        Bitmap shrunk = shrinkBitmap(bitmap, mMaxIconDimension);
+                        try {
+                            shrunk.compress(mIconPersistFormat, mIconPersistQuality, out);
+                        } finally {
+                            if (bitmap != shrunk) {
+                                shrunk.recycle();
+                            }
+                        }
 
                         shortcut.setBitmapPath(out.getFile().getAbsolutePath());
                         shortcut.addFlags(ShortcutInfo.FLAG_HAS_ICON_FILE);
@@ -1027,8 +1035,8 @@
                     }
                 }
             } finally {
-                if (bitmap != null) {
-                    bitmap.recycle();
+                if (bitmapToRecycle != null) {
+                    bitmapToRecycle.recycle();
                 }
                 // Once saved, we won't use the original icon information, so null it out.
                 shortcut.clearIcon();
@@ -1076,8 +1084,6 @@
 
         c.drawBitmap(in, /*src=*/ null, dst, /* paint =*/ null);
 
-        in.recycle();
-
         return scaledBitmap;
     }
 
@@ -1122,7 +1128,7 @@
         if (injectGetPackageUid(packageName, userId) == injectBinderCallingUid()) {
             return; // Caller is valid.
         }
-        throw new SecurityException("Caller UID= doesn't own " + packageName);
+        throw new SecurityException("Calling package name mismatch");
     }
 
     void postToHandler(Runnable r) {
@@ -1313,10 +1319,13 @@
     }
 
     @Override
-    public boolean addDynamicShortcut(String packageName, ShortcutInfo newShortcut,
+    public boolean addDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList,
             @UserIdInt int userId) {
         verifyCaller(packageName, userId);
 
+        final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList();
+        final int size = newShortcuts.size();
+
         synchronized (mLock) {
             final ShortcutPackage ps = getPackageShortcutsLocked(packageName, userId);
 
@@ -1324,12 +1333,15 @@
             if (!ps.tryApiCall(this)) {
                 return false;
             }
+            for (int i = 0; i < size; i++) {
+                final ShortcutInfo newShortcut = newShortcuts.get(i);
 
-            // Validate the shortcut.
-            fixUpIncomingShortcutInfo(newShortcut, /* forUpdate= */ false);
+                // Validate the shortcut.
+                fixUpIncomingShortcutInfo(newShortcut, /* forUpdate= */ false);
 
-            // Add it.
-            ps.addDynamicShortcut(this, newShortcut);
+                // Add it.
+                ps.addDynamicShortcut(this, newShortcut);
+            }
         }
         userPackageChanged(packageName, userId);
 
@@ -1337,19 +1349,22 @@
     }
 
     @Override
-    public void deleteDynamicShortcut(String packageName, String shortcutId,
+    public void removeDynamicShortcuts(String packageName, List shortcutIds,
             @UserIdInt int userId) {
         verifyCaller(packageName, userId);
-        Preconditions.checkStringNotEmpty(shortcutId, "shortcutId must be provided");
+        Preconditions.checkNotNull(shortcutIds, "shortcutIds must be provided");
 
         synchronized (mLock) {
-            getPackageShortcutsLocked(packageName, userId).deleteDynamicWithId(this, shortcutId);
+            for (int i = shortcutIds.size() - 1; i >= 0; i--) {
+                getPackageShortcutsLocked(packageName, userId).deleteDynamicWithId(this,
+                        Preconditions.checkStringNotEmpty((String) shortcutIds.get(i)));
+            }
         }
         userPackageChanged(packageName, userId);
     }
 
     @Override
-    public void deleteAllDynamicShortcuts(String packageName, @UserIdInt int userId) {
+    public void removeAllDynamicShortcuts(String packageName, @UserIdInt int userId) {
         verifyCaller(packageName, userId);
 
         synchronized (mLock) {
@@ -1403,7 +1418,7 @@
         verifyCaller(packageName, userId);
 
         synchronized (mLock) {
-            return mMaxDailyUpdates
+            return mMaxUpdatesPerInterval
                     - getPackageShortcutsLocked(packageName, userId).getApiCallCount(this);
         }
     }
@@ -1419,6 +1434,8 @@
 
     @Override
     public int getIconMaxDimensions(String packageName, int userId) throws RemoteException {
+        verifyCaller(packageName, userId);
+
         synchronized (mLock) {
             return mMaxIconDimension;
         }
@@ -1439,7 +1456,15 @@
             getUserShortcutsLocked(userId).resetThrottling();
         }
         scheduleSaveUser(userId);
-        Slog.i(TAG, "ShortcutManager: throttling counter reset");
+        Slog.i(TAG, "ShortcutManager: throttling counter reset for user " + userId);
+    }
+
+    void resetAllThrottlingInner() {
+        synchronized (mLock) {
+            mRawLastResetTime = injectCurrentTimeMillis();
+        }
+        scheduleSaveBaseState();
+        Slog.i(TAG, "ShortcutManager: throttling counter reset for all users");
     }
 
     // We override this method in unit tests to do a simpler check.
@@ -1522,14 +1547,20 @@
 
     // === House keeping ===
 
+    @VisibleForTesting
+    void cleanUpPackageLocked(String packageName, int owningUserId, int packageUserId) {
+        cleanUpPackageLocked(packageName, owningUserId, packageUserId,
+                /* forceForCommandLine= */ false);
+    }
+
     /**
      * Remove all the information associated with a package.  This will really remove all the
      * information, including the restore information (i.e. it'll remove packages even if they're
      * shadow).
      */
-    @VisibleForTesting
-    void cleanUpPackageLocked(String packageName, int owningUserId, int packageUserId) {
-        if (isPackageInstalled(packageName, packageUserId)) {
+    private void cleanUpPackageLocked(String packageName, int owningUserId, int packageUserId,
+            boolean forceForCommandLine) {
+        if (!forceForCommandLine && isPackageInstalled(packageName, packageUserId)) {
             wtf("Package " + packageName + " is still installed for user " + packageUserId);
             return;
         }
@@ -1580,13 +1611,17 @@
         @Override
         public List<ShortcutInfo> getShortcuts(int launcherUserId,
                 @NonNull String callingPackage, long changedSince,
-                @Nullable String packageName, @Nullable ComponentName componentName,
+                @Nullable String packageName, @Nullable List<String> shortcutIds,
+                @Nullable ComponentName componentName,
                 int queryFlags, int userId) {
             final ArrayList<ShortcutInfo> ret = new ArrayList<>();
             final int cloneFlag =
                     ((queryFlags & ShortcutQuery.FLAG_GET_KEY_FIELDS_ONLY) == 0)
                             ? ShortcutInfo.CLONE_REMOVE_FOR_LAUNCHER
                             : ShortcutInfo.CLONE_REMOVE_NON_KEY_INFO;
+            if (packageName == null) {
+                shortcutIds = null; // LauncherAppsService already threw for it though.
+            }
 
             synchronized (mLock) {
                 getLauncherShortcutsLocked(callingPackage, userId, launcherUserId)
@@ -1594,14 +1629,14 @@
 
                 if (packageName != null) {
                     getShortcutsInnerLocked(launcherUserId,
-                            callingPackage, packageName, changedSince,
+                            callingPackage, packageName, shortcutIds, changedSince,
                             componentName, queryFlags, userId, ret, cloneFlag);
                 } else {
                     final ArrayMap<String, ShortcutPackage> packages =
                             getUserShortcutsLocked(userId).getAllPackages();
                     for (int i = packages.size() - 1; i >= 0; i--) {
                         getShortcutsInnerLocked(launcherUserId,
-                                callingPackage, packages.keyAt(i), changedSince,
+                                callingPackage, packages.keyAt(i), shortcutIds, changedSince,
                                 componentName, queryFlags, userId, ret, cloneFlag);
                     }
                 }
@@ -1610,14 +1645,20 @@
         }
 
         private void getShortcutsInnerLocked(int launcherUserId, @NonNull String callingPackage,
-                @Nullable String packageName,long changedSince,
+                @Nullable String packageName, @Nullable List<String> shortcutIds, long changedSince,
                 @Nullable ComponentName componentName, int queryFlags,
                 int userId, ArrayList<ShortcutInfo> ret, int cloneFlag) {
+            final ArraySet<String> ids = shortcutIds == null ? null
+                    : new ArraySet<>(shortcutIds);
+
             getPackageShortcutsLocked(packageName, userId).findAll(ShortcutService.this, ret,
                     (ShortcutInfo si) -> {
                         if (si.getLastChangedTimestamp() < changedSince) {
                             return false;
                         }
+                        if (ids != null && !ids.contains(si.getId())) {
+                            return false;
+                        }
                         if (componentName != null
                                 && !componentName.equals(si.getActivityComponent())) {
                             return false;
@@ -1633,27 +1674,6 @@
         }
 
         @Override
-        public List<ShortcutInfo> getShortcutInfo(int launcherUserId,
-                @NonNull String callingPackage,
-                @NonNull String packageName, @Nullable List<String> ids, int userId) {
-            // Calling permission must be checked by LauncherAppsImpl.
-            Preconditions.checkStringNotEmpty(packageName, "packageName");
-
-            final ArrayList<ShortcutInfo> ret = new ArrayList<>(ids.size());
-            final ArraySet<String> idSet = new ArraySet<>(ids);
-            synchronized (mLock) {
-                getLauncherShortcutsLocked(callingPackage, userId, launcherUserId)
-                        .attemptToRestoreIfNeededAndSave(ShortcutService.this);
-
-                getPackageShortcutsLocked(packageName, userId).findAll(
-                        ShortcutService.this, ret,
-                        (ShortcutInfo si) -> idSet.contains(si.getId()),
-                        ShortcutInfo.CLONE_REMOVE_FOR_LAUNCHER, callingPackage, launcherUserId);
-            }
-            return ret;
-        }
-
-        @Override
         public boolean isPinnedByCaller(int launcherUserId, @NonNull String callingPackage,
                 @NonNull String packageName, @NonNull String shortcutId, int userId) {
             Preconditions.checkStringNotEmpty(packageName, "packageName");
@@ -1733,17 +1753,18 @@
         }
 
         @Override
-        public int getShortcutIconResId(int launcherUserId,
-                @NonNull String callingPackage,
-                @NonNull ShortcutInfo shortcut, int userId) {
-            Preconditions.checkNotNull(shortcut, "shortcut");
+        public int getShortcutIconResId(int launcherUserId, @NonNull String callingPackage,
+                @NonNull String packageName, @NonNull String shortcutId, int userId) {
+            Preconditions.checkNotNull(callingPackage, "callingPackage");
+            Preconditions.checkNotNull(packageName, "packageName");
+            Preconditions.checkNotNull(shortcutId, "shortcutId");
 
             synchronized (mLock) {
                 getLauncherShortcutsLocked(callingPackage, userId, launcherUserId)
                         .attemptToRestoreIfNeededAndSave(ShortcutService.this);
 
                 final ShortcutInfo shortcutInfo = getPackageShortcutsLocked(
-                        shortcut.getPackageName(), userId).findShortcutById(shortcut.getId());
+                        packageName, userId).findShortcutById(shortcutId);
                 return (shortcutInfo != null && shortcutInfo.hasIconResource())
                         ? shortcutInfo.getIconResourceId() : 0;
             }
@@ -1751,16 +1772,18 @@
 
         @Override
         public ParcelFileDescriptor getShortcutIconFd(int launcherUserId,
-                @NonNull String callingPackage,
-                @NonNull ShortcutInfo shortcutIn, int userId) {
-            Preconditions.checkNotNull(shortcutIn, "shortcut");
+                @NonNull String callingPackage, @NonNull String packageName,
+                @NonNull String shortcutId, int userId) {
+            Preconditions.checkNotNull(callingPackage, "callingPackage");
+            Preconditions.checkNotNull(packageName, "packageName");
+            Preconditions.checkNotNull(shortcutId, "shortcutId");
 
             synchronized (mLock) {
                 getLauncherShortcutsLocked(callingPackage, userId, launcherUserId)
                         .attemptToRestoreIfNeededAndSave(ShortcutService.this);
 
                 final ShortcutInfo shortcutInfo = getPackageShortcutsLocked(
-                        shortcutIn.getPackageName(), userId).findShortcutById(shortcutIn.getId());
+                        packageName, userId).findShortcutById(shortcutId);
                 if (shortcutInfo == null || !shortcutInfo.hasIconFile()) {
                     return null;
                 }
@@ -1865,9 +1888,15 @@
             Slog.d(TAG, String.format("handlePackageRemoved: %s user=%d", packageName,
                     packageUserId));
         }
+        handlePackageRemovedInner(packageName, packageUserId, /* forceForCommandLine =*/ false);
+    }
+
+    private void handlePackageRemovedInner(String packageName, @UserIdInt int packageUserId,
+            boolean forceForCommandLine) {
         synchronized (mLock) {
             forEachLoadedUserLocked(user ->
-                cleanUpPackageLocked(packageName, user.getUserId(), packageUserId));
+                cleanUpPackageLocked(packageName, user.getUserId(), packageUserId,
+                        forceForCommandLine));
         }
     }
 
@@ -2048,17 +2077,26 @@
             pw.print(formatTime(next));
             pw.println();
 
-            pw.print("  Max icon dim: ");
-            pw.print(mMaxIconDimension);
-            pw.print("  Icon format: ");
-            pw.print(mIconPersistFormat);
-            pw.print("  Icon quality: ");
+            pw.print("  Config:");
+            pw.print("    Max icon dim: ");
+            pw.println(mMaxIconDimension);
+            pw.print("    Icon format: ");
+            pw.println(mIconPersistFormat);
+            pw.print("    Icon quality: ");
             pw.println(mIconPersistQuality);
+            pw.print("    saveDelayMillis:");
+            pw.println(mSaveDelayMillis);
+            pw.print("    resetInterval:");
+            pw.println(mResetInterval);
+            pw.print("    maxUpdatesPerInterval:");
+            pw.println(mMaxUpdatesPerInterval);
+            pw.print("    maxDynamicShortcuts:");
+            pw.println(mMaxDynamicShortcuts);
             pw.println();
 
             pw.println("  Stats:");
             synchronized (mStatLock) {
-                final String p = "     ";
+                final String p = "    ";
                 dumpStatLS(pw, p, Stats.GET_DEFAULT_HOME, "getHomeActivities()");
                 dumpStatLS(pw, p, Stats.LAUNCHER_PERMISSION_CHECK, "Launcher permission check");
 
@@ -2144,6 +2182,9 @@
                     case "reset-throttling":
                         handleResetThrottling();
                         break;
+                    case "reset-all-throttling":
+                        handleResetAllThrottling();
+                        break;
                     case "override-config":
                         handleOverrideConfig();
                         break;
@@ -2162,6 +2203,9 @@
                     case "unload-user":
                         handleUnloadUser();
                         break;
+                    case "clear-shortcuts":
+                        handleClearShortcuts();
+                        break;
                     default:
                         return handleDefaultCommands(cmd);
                 }
@@ -2181,9 +2225,12 @@
             pw.println("cmd shortcut reset-package-throttling [--user USER_ID] PACKAGE");
             pw.println("    Reset throttling for a package");
             pw.println();
-            pw.println("cmd shortcut reset-throttling");
+            pw.println("cmd shortcut reset-throttling [--user USER_ID]");
             pw.println("    Reset throttling for all packages and users");
             pw.println();
+            pw.println("cmd shortcut reset-all-throttling");
+            pw.println("    Reset the throttling state for all users");
+            pw.println();
             pw.println("cmd shortcut override-config CONFIG");
             pw.println("    Override the configuration for testing (will last until reboot)");
             pw.println();
@@ -2203,13 +2250,23 @@
             pw.println("    Unload a user from the memory");
             pw.println("    (This should not affect any observable behavior)");
             pw.println();
+            pw.println("cmd shortcut clear-shortcuts [--user USER_ID] PACKAGE");
+            pw.println("    Remove all shortcuts from a package, including pinned shortcuts");
+            pw.println();
         }
 
-        private int handleResetThrottling() throws CommandException {
+        private void handleResetThrottling() throws CommandException {
             parseOptions(/* takeUser =*/ true);
 
+            Slog.i(TAG, "cmd: handleResetThrottling");
+
             resetThrottlingInner(mUserId);
-            return 0;
+        }
+
+        private void handleResetAllThrottling() {
+            Slog.i(TAG, "cmd: handleResetAllThrottling");
+
+            resetAllThrottlingInner();
         }
 
         private void handleResetPackageThrottling() throws CommandException {
@@ -2217,6 +2274,8 @@
 
             final String packageName = getNextArgRequired();
 
+            Slog.i(TAG, "cmd: handleResetPackageThrottling: " + packageName);
+
             synchronized (mLock) {
                 getPackageShortcutsLocked(packageName, mUserId).resetRateLimitingForCommandLine();
                 saveUserLocked(mUserId);
@@ -2226,6 +2285,8 @@
         private void handleOverrideConfig() throws CommandException {
             final String config = getNextArgRequired();
 
+            Slog.i(TAG, "cmd: handleOverrideConfig: " + config);
+
             synchronized (mLock) {
                 if (!updateConfigurationLocked(config)) {
                     throw new CommandException("override-config failed.  See logcat for details.");
@@ -2234,6 +2295,8 @@
         }
 
         private void handleResetConfig() {
+            Slog.i(TAG, "cmd: handleResetConfig");
+
             synchronized (mLock) {
                 loadConfigurationLocked();
             }
@@ -2278,8 +2341,20 @@
         private void handleUnloadUser() throws CommandException {
             parseOptions(/* takeUser =*/ true);
 
+            Slog.i(TAG, "cmd: handleUnloadUser: " + mUserId);
+
             ShortcutService.this.handleCleanupUser(mUserId);
         }
+
+        private void handleClearShortcuts() throws CommandException {
+            parseOptions(/* takeUser =*/ true);
+            final String packageName = getNextArgRequired();
+
+            Slog.i(TAG, "cmd: handleClearShortcuts: " + mUserId + ", " + packageName);
+
+            ShortcutService.this.handlePackageRemovedInner(packageName, mUserId,
+                    /* forceForCommandLine= */ true);
+        }
     }
 
     // === Unit test support ===
@@ -2357,8 +2432,8 @@
     }
 
     @VisibleForTesting
-    int getMaxDailyUpdatesForTest() {
-        return mMaxDailyUpdates;
+    int getMaxUpdatesPerIntervalForTest() {
+        return mMaxUpdatesPerInterval;
     }
 
     @VisibleForTesting
diff --git a/services/core/java/com/android/server/pm/UserManagerService.java b/services/core/java/com/android/server/pm/UserManagerService.java
index 60a0d62..60ea254 100644
--- a/services/core/java/com/android/server/pm/UserManagerService.java
+++ b/services/core/java/com/android/server/pm/UserManagerService.java
@@ -65,6 +65,7 @@
 import android.system.Os;
 import android.system.OsConstants;
 import android.util.AtomicFile;
+import android.util.IntArray;
 import android.util.Log;
 import android.util.Slog;
 import android.util.SparseArray;
@@ -483,13 +484,50 @@
         }
     }
 
+    @Override
+    public int[] getProfileIds(int userId, boolean enabledOnly) {
+        if (userId != UserHandle.getCallingUserId()) {
+            checkManageUsersPermission("getting profiles related to user " + userId);
+        }
+        final long ident = Binder.clearCallingIdentity();
+        try {
+            synchronized (mUsersLock) {
+                return getProfileIdsLU(userId, enabledOnly).toArray();
+            }
+        } finally {
+            Binder.restoreCallingIdentity(ident);
+        }
+    }
+
     /** Assume permissions already checked and caller's identity cleared */
     private List<UserInfo> getProfilesLU(int userId, boolean enabledOnly, boolean fullInfo) {
+        IntArray profileIds = getProfileIdsLU(userId, enabledOnly);
+        ArrayList<UserInfo> users = new ArrayList<>(profileIds.size());
+        for (int i = 0; i < profileIds.size(); i++) {
+            int profileId = profileIds.get(i);
+            UserInfo userInfo = mUsers.get(profileId).info;
+            // If full info is not required - clear PII data to prevent 3P apps from reading it
+            if (!fullInfo) {
+                userInfo = new UserInfo(userInfo);
+                userInfo.name = null;
+                userInfo.iconPath = null;
+            } else {
+                userInfo = userWithName(userInfo);
+            }
+            users.add(userInfo);
+        }
+        return users;
+    }
+
+    /**
+     *  Assume permissions already checked and caller's identity cleared
+     */
+    private IntArray getProfileIdsLU(int userId, boolean enabledOnly) {
         UserInfo user = getUserInfoLU(userId);
-        ArrayList<UserInfo> users = new ArrayList<UserInfo>(mUsers.size());
+        IntArray result = new IntArray(mUsers.size());
         if (user == null) {
             // Probably a dying user
-            return users;
+            return result;
         }
         final int userSize = mUsers.size();
         for (int i = 0; i < userSize; i++) {
@@ -506,16 +544,9 @@
             if (profile.partial) {
                 continue;
             }
-            UserInfo userInfo = userWithName(profile);
-            // If full info is not required - clear PII data to prevent 3P apps from reading it
-            if (!fullInfo) {
-                userInfo = new UserInfo(userInfo);
-                userInfo.name = null;
-                userInfo.iconPath = null;
-            }
-            users.add(userInfo);
+            result.add(profile.id);
         }
-        return users;
+        return result;
     }
 
     @Override
diff --git a/services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java b/services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java
index 160d44c..27077f2 100644
--- a/services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java
+++ b/services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java
@@ -27,8 +27,11 @@
 import android.graphics.drawable.ColorDrawable;
 import android.os.Handler;
 import android.os.Message;
+import android.os.RemoteException;
+import android.os.ServiceManager;
 import android.os.UserHandle;
 import android.provider.Settings;
+import android.service.vr.IVrManager;
 import android.util.DisplayMetrics;
 import android.util.Slog;
 import android.util.SparseBooleanArray;
@@ -45,6 +48,7 @@
 import android.widget.FrameLayout;
 
 import com.android.internal.R;
+import com.android.server.vr.VrManagerService;
 
 /**
  *  Helper to manage showing/hiding a confirmation prompt when the navigation bar is hidden
@@ -66,6 +70,7 @@
     private long mPanicTime;
     private WindowManager mWindowManager;
     private int mCurrentUserId;
+    private IVrManager mVrManager;
 
     public ImmersiveModeConfirmation(Context context) {
         mContext = context;
@@ -75,6 +80,8 @@
                 .getInteger(R.integer.config_immersive_mode_confirmation_panic);
         mWindowManager = (WindowManager)
                 mContext.getSystemService(Context.WINDOW_SERVICE);
+        mVrManager = (IVrManager) IVrManager.Stub.asInterface(
+                ServiceManager.getService(VrManagerService.VR_MANAGER_BINDER_SERVICE));
     }
 
     private long getNavBarExitDuration() {
@@ -112,6 +119,14 @@
         }
     }
 
+    private boolean getVrMode() {
+        boolean vrMode = false;
+        try {
+            vrMode = mVrManager.getVrModeState();
+        } catch (RemoteException ex) { }
+        return vrMode;
+    }        
+
     public void immersiveModeChanged(String pkg, boolean isImmersiveMode,
             boolean userSetupComplete) {
         mHandler.removeMessages(H.SHOW);
@@ -119,7 +134,10 @@
             final boolean disabled = PolicyControl.disableImmersiveConfirmation(pkg);
             if (DEBUG) Slog.d(TAG, String.format("immersiveModeChanged() disabled=%s mConfirmed=%s",
                     disabled, mConfirmed));
-            if (!disabled && (DEBUG_SHOW_EVERY_TIME || !mConfirmed) && userSetupComplete) {
+            if (!disabled
+                    && (DEBUG_SHOW_EVERY_TIME || !mConfirmed)
+                    && userSetupComplete
+                    && !getVrMode()) {
                 mHandler.sendEmptyMessageDelayed(H.SHOW, mShowDelayMs);
             }
         } else {
diff --git a/services/core/java/com/android/server/policy/PhoneWindowManager.java b/services/core/java/com/android/server/policy/PhoneWindowManager.java
index fb56a0c..5ce451f 100644
--- a/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -692,9 +692,7 @@
     private final LogDecelerateInterpolator mLogDecelerateInterpolator
             = new LogDecelerateInterpolator(100, 0);
 
-    private boolean mForceWindowDrawsStatusBarBackground;
     private final MutableBoolean mTmpBoolean = new MutableBoolean(false);
-
     private static final int MSG_ENABLE_POINTER_LOCATION = 1;
     private static final int MSG_DISABLE_POINTER_LOCATION = 2;
     private static final int MSG_DISPATCH_MEDIA_KEY_WITH_WAKE_LOCK = 3;
@@ -1745,8 +1743,6 @@
 
         mScreenshotChordEnabled = mContext.getResources().getBoolean(
                 com.android.internal.R.bool.config_enableScreenshotChord);
-        mForceWindowDrawsStatusBarBackground = mContext.getResources().getBoolean(
-                R.bool.config_forceWindowDrawsStatusBarBackground);
 
         mGlobalKeyManager = new GlobalKeyManager(mContext);
 
@@ -2217,9 +2213,12 @@
             if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0) {
                 attrs.subtreeSystemUiVisibility |= View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
             }
+            final boolean forceWindowDrawsStatusBarBackground =
+                    (attrs.privateFlags & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND)
+                            != 0;
             if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0
-                    || (mForceWindowDrawsStatusBarBackground
-                            && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT)) {
+                    || forceWindowDrawsStatusBarBackground
+                            && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT) {
                 attrs.subtreeSystemUiVisibility |= View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
             }
         }
@@ -4274,6 +4273,7 @@
         }
 
         final int fl = PolicyControl.getWindowFlags(win, attrs);
+        final int pfl = attrs.privateFlags;
         final int sim = attrs.softInputMode;
         final int sysUiFl = PolicyControl.getSystemUiVisibility(win, null);
 
@@ -4369,7 +4369,7 @@
                         && (fl & WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS) == 0
                         && (fl & WindowManager.LayoutParams.
                                 FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) == 0
-                        && !mForceWindowDrawsStatusBarBackground) {
+                        && (pfl & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) == 0) {
                     // Ensure policy decor includes status bar
                     dcf.top = mStableTop;
                 }
@@ -7243,6 +7243,15 @@
         return vis;
     }
 
+    private boolean drawsSystemBarBackground(WindowState win) {
+        return win == null || (win.getAttrs().flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0;
+    }
+
+    private boolean forcesDrawStatusBarBackground(WindowState win) {
+        return win == null || (win.getAttrs().privateFlags
+                & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) != 0;
+    }
+
     private int updateSystemBarsLw(WindowState win, int oldVis, int vis) {
         final boolean dockedStackVisible = mWindowManagerInternal.isStackVisible(DOCKED_STACK_ID);
         final boolean freeformStackVisible =
@@ -7256,11 +7265,22 @@
         final boolean forceOpaqueStatusBar = mForceShowSystemBars && !mForceStatusBarFromKeyguard;
 
         // apply translucent bar vis flags
-        WindowState transWin = isStatusBarKeyguard() && !mHideLockScreen
+        WindowState fullscreenTransWin = isStatusBarKeyguard() && !mHideLockScreen
                 ? mStatusBar
                 : mTopFullscreenOpaqueWindowState;
-        vis = mStatusBarController.applyTranslucentFlagLw(transWin, vis, oldVis);
-        vis = mNavigationBarController.applyTranslucentFlagLw(transWin, vis, oldVis);
+        vis = mStatusBarController.applyTranslucentFlagLw(fullscreenTransWin, vis, oldVis);
+        vis = mNavigationBarController.applyTranslucentFlagLw(fullscreenTransWin, vis, oldVis);
+        final int dockedVis = mStatusBarController.applyTranslucentFlagLw(
+                mTopDockedOpaqueWindowState, 0, 0);
+
+        final boolean fullscreenDrawsStatusBarBackground =
+                (drawsSystemBarBackground(mTopFullscreenOpaqueWindowState)
+                        && (vis & View.STATUS_BAR_TRANSLUCENT) == 0)
+                || forcesDrawStatusBarBackground(mTopFullscreenOpaqueWindowState);
+        final boolean dockedDrawsStatusBarBackground =
+                (drawsSystemBarBackground(mTopDockedOpaqueWindowState)
+                        && (dockedVis & View.STATUS_BAR_TRANSLUCENT) == 0)
+                || forcesDrawStatusBarBackground(mTopDockedOpaqueWindowState);
 
         // prevent status bar interaction from clearing certain flags
         int type = win.getAttrs().type;
@@ -7277,18 +7297,16 @@
             vis = (vis & ~flags) | (oldVis & flags);
         }
 
-        if ((!areTranslucentBarsAllowed() && transWin != mStatusBar)
+        if (fullscreenDrawsStatusBarBackground && dockedDrawsStatusBarBackground) {
+            vis |= View.STATUS_BAR_TRANSPARENT;
+            vis &= ~View.STATUS_BAR_TRANSLUCENT;
+        } else if ((!areTranslucentBarsAllowed() && fullscreenTransWin != mStatusBar)
                 || forceOpaqueStatusBar) {
             vis &= ~(View.STATUS_BAR_TRANSLUCENT | View.STATUS_BAR_TRANSPARENT);
         }
 
         vis = configureNavBarOpacity(vis, dockedStackVisible, freeformStackVisible, resizing);
 
-        if (mForceWindowDrawsStatusBarBackground) {
-            vis |= View.STATUS_BAR_TRANSPARENT;
-            vis &= ~View.STATUS_BAR_TRANSLUCENT;
-        }
-
         // update status bar
         boolean immersiveSticky =
                 (vis & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
diff --git a/services/core/java/com/android/server/policy/ShortcutManager.java b/services/core/java/com/android/server/policy/ShortcutManager.java
index a14c614..ab404db 100644
--- a/services/core/java/com/android/server/policy/ShortcutManager.java
+++ b/services/core/java/com/android/server/policy/ShortcutManager.java
@@ -27,7 +27,9 @@
 import android.util.SparseArray;
 import android.view.KeyCharacterMap;
 import android.view.KeyEvent;
+
 import com.android.internal.util.XmlUtils;
+
 import org.xmlpull.v1.XmlPullParser;
 import org.xmlpull.v1.XmlPullParserException;
 
diff --git a/services/core/java/com/android/server/power/ShutdownThread.java b/services/core/java/com/android/server/power/ShutdownThread.java
index bcafddc..5b9d139 100644
--- a/services/core/java/com/android/server/power/ShutdownThread.java
+++ b/services/core/java/com/android/server/power/ShutdownThread.java
@@ -93,6 +93,7 @@
 
     // Indicates whether we are rebooting into safe mode
     public static final String REBOOT_SAFEMODE_PROPERTY = "persist.sys.safemode";
+    public static final String RO_SAFEMODE_PROPERTY = "ro.sys.safemode";
 
     // Indicates whether we should stay in safe mode until ro.build.date.utc is newer than this
     public static final String AUDIT_SAFEMODE_PROPERTY = "persist.sys.audit_safemode";
diff --git a/services/core/java/com/android/server/vr/EnabledComponentsObserver.java b/services/core/java/com/android/server/vr/EnabledComponentsObserver.java
index eb926c1..30194bf 100644
--- a/services/core/java/com/android/server/vr/EnabledComponentsObserver.java
+++ b/services/core/java/com/android/server/vr/EnabledComponentsObserver.java
@@ -24,7 +24,6 @@
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.content.pm.ServiceInfo;
-import android.content.pm.UserInfo;
 import android.os.Handler;
 import android.os.Looper;
 import android.os.UserHandle;
@@ -213,18 +212,7 @@
         if (userManager == null) {
             return null;
         }
-        int currentUserId = ActivityManager.getCurrentUser();
-        List<UserInfo> profiles = userManager.getProfiles(currentUserId);
-        if (profiles == null) {
-            return null;
-        }
-        final int s = profiles.size();
-        int[] userIds = new int[s];
-        int ctr = 0;
-        for (UserInfo info : profiles) {
-            userIds[ctr++] = info.id;
-        }
-        return userIds;
+        return userManager.getProfileIdsWithDisabled(ActivityManager.getCurrentUser());
     }
 
     public static ArraySet<ComponentName> loadComponentNames(PackageManager pm, int userId,
diff --git a/services/core/java/com/android/server/vr/VrManagerService.java b/services/core/java/com/android/server/vr/VrManagerService.java
index e6e5a2d..49ff385 100644
--- a/services/core/java/com/android/server/vr/VrManagerService.java
+++ b/services/core/java/com/android/server/vr/VrManagerService.java
@@ -50,6 +50,8 @@
 import com.android.server.utils.ManagedApplicationService;
 import com.android.server.utils.ManagedApplicationService.BinderChecker;
 
+import java.io.FileDescriptor;
+import java.io.PrintWriter;
 import java.lang.StringBuilder;
 import java.lang.ref.WeakReference;
 import java.util.ArrayList;
@@ -103,6 +105,7 @@
             new RemoteCallbackList<>();
     private final ArraySet<String> mPreviousToggledListenerSettings = new ArraySet<>();
     private String mPreviousNotificationPolicyAccessPackage;
+    private String mPreviousCoarseLocationPackage;
     private String mPreviousManageOverlayPackage;
 
     private static final int MSG_VR_STATE_CHANGE = 0;
@@ -186,6 +189,32 @@
             return VrManagerService.this.getVrMode();
         }
 
+        @Override
+        protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
+            if (getContext().checkCallingOrSelfPermission(android.Manifest.permission.DUMP)
+                    != PackageManager.PERMISSION_GRANTED) {
+                pw.println("permission denied: can't dump VrManagerService from pid="
+                        + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid());
+                return;
+            }
+            pw.print("mVrModeEnabled=");
+            pw.println(mVrModeEnabled);
+            pw.print("mCurrentVrModeUser=");
+            pw.println(mCurrentVrModeUser);
+            pw.print("mRemoteCallbacks=");
+            int i=mRemoteCallbacks.beginBroadcast(); // create the broadcast item array
+            while(i-->0) {
+                pw.print(mRemoteCallbacks.getBroadcastItem(i));
+                if (i>0) pw.print(", ");
+            }
+            mRemoteCallbacks.finishBroadcast();
+            pw.println();
+            pw.print("mCurrentVrService=");
+            pw.println(mCurrentVrService != null ? mCurrentVrService.getComponent() : "(none)");
+            pw.print("mCurrentVrModeComponent=");
+            pw.println(mCurrentVrModeComponent);
+        }
+
     };
 
     private void enforceCallerPermission(String permission) {
@@ -418,6 +447,7 @@
 
         mWasDefaultGranted = true;
 
+        grantCoarseLocationAccess(pName, userId);
         grantOverlayAccess(pName, userId);
         grantNotificationPolicyAccess(pName);
         grantNotificationListenerAccess(pName, userId);
@@ -447,6 +477,7 @@
 
         String pName = component.getPackageName();
         if (mWasDefaultGranted) {
+            revokeCoarseLocationAccess(userId);
             revokeOverlayAccess(userId);
             revokeNotificationPolicyAccess(pName);
             revokeNotificiationListenerAccess();
@@ -455,6 +486,27 @@
 
     }
 
+    private void grantCoarseLocationAccess(String pkg, UserHandle userId) {
+        PackageManager pm = mContext.getPackageManager();
+        boolean prev = (PackageManager.PERMISSION_GRANTED ==
+                pm.checkPermission(android.Manifest.permission.ACCESS_COARSE_LOCATION, pkg));
+        mPreviousCoarseLocationPackage = null;
+        if (!prev) {
+            pm.grantRuntimePermission(pkg, android.Manifest.permission.ACCESS_COARSE_LOCATION,
+                    userId);
+            mPreviousCoarseLocationPackage = pkg;
+        }
+    }
+
+    private void revokeCoarseLocationAccess(UserHandle userId) {
+        PackageManager pm = mContext.getPackageManager();
+        if (mPreviousCoarseLocationPackage != null) {
+            pm.revokeRuntimePermission(mPreviousCoarseLocationPackage,
+                    android.Manifest.permission.ACCESS_COARSE_LOCATION, userId);
+            mPreviousCoarseLocationPackage = null;
+        }
+    }
+
     private void grantOverlayAccess(String pkg, UserHandle userId) {
         PackageManager pm = mContext.getPackageManager();
         boolean prev = (PackageManager.PERMISSION_GRANTED ==
@@ -476,7 +528,6 @@
         }
     }
 
-
     private void grantNotificationPolicyAccess(String pkg) {
         NotificationManager nm = mContext.getSystemService(NotificationManager.class);
         boolean prev = nm.isNotificationPolicyAccessGrantedForPackage(pkg);
@@ -490,8 +541,15 @@
     private void revokeNotificationPolicyAccess(String pkg) {
         NotificationManager nm = mContext.getSystemService(NotificationManager.class);
         if (mPreviousNotificationPolicyAccessPackage != null) {
-            nm.setNotificationPolicyAccessGranted(mPreviousNotificationPolicyAccessPackage, false);
-            mPreviousNotificationPolicyAccessPackage = null;
+            if (mPreviousNotificationPolicyAccessPackage.equals(pkg)) {
+                // Remove any DND zen rules possibly created by the package.
+                nm.removeAutomaticZenRules(mPreviousNotificationPolicyAccessPackage);
+                // Remove Notification Policy Access.
+                nm.setNotificationPolicyAccessGranted(mPreviousNotificationPolicyAccessPackage, false);
+                mPreviousNotificationPolicyAccessPackage = null;
+            } else {
+                Slog.e(TAG, "Couldn't remove Notification Policy Access for package: " + pkg);
+            }
         }
     }
 
diff --git a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
index fb3c6ec..fe32104 100644
--- a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
+++ b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
@@ -49,6 +49,7 @@
 import android.graphics.Bitmap;
 import android.graphics.BitmapFactory;
 import android.graphics.BitmapRegionDecoder;
+import android.graphics.Matrix;
 import android.graphics.Point;
 import android.graphics.Rect;
 import android.os.Binder;
@@ -265,70 +266,134 @@
      */
     private void generateCrop(WallpaperData wallpaper) {
         boolean success = false;
-        boolean needCrop = false;
-        boolean needScale = false;
+
+        Rect cropHint = new Rect(wallpaper.cropHint);
 
         if (DEBUG) {
             Slog.v(TAG, "Generating crop for new wallpaper(s): 0x"
                     + Integer.toHexString(wallpaper.whichPending)
-                    + " to " + wallpaper.cropFile.getName());
+                    + " to " + wallpaper.cropFile.getName()
+                    + " crop=(" + cropHint.width() + 'x' + cropHint.height()
+                    + ") dim=(" + wallpaper.width + 'x' + wallpaper.height + ')');
         }
 
         // Analyse the source; needed in multiple cases
         BitmapFactory.Options options = new BitmapFactory.Options();
         options.inJustDecodeBounds = true;
         BitmapFactory.decodeFile(wallpaper.wallpaperFile.getAbsolutePath(), options);
-
-        // We'll need to scale if the crop is sufficiently bigger than the display
-
-        // Legacy case uses an empty crop rect here, so we just preserve the
-        // source image verbatim
-        if (!wallpaper.cropHint.isEmpty()) {
-            // ...clamp the crop rect to the measured bounds...
-            wallpaper.cropHint.right = Math.min(wallpaper.cropHint.right, options.outWidth);
-            wallpaper.cropHint.bottom = Math.min(wallpaper.cropHint.bottom, options.outHeight);
-            // ...and don't bother cropping if what we're left with is identity
-            needCrop = (options.outHeight >= wallpaper.cropHint.height()
-                    && options.outWidth >= wallpaper.cropHint.width());
-        }
-
-        if (!needCrop && !needScale) {
-            // Simple case:  the nominal crop is at least as big as the source image,
-            // so we take the whole thing and just copy the image file directly.
-            if (DEBUG) {
-                Slog.v(TAG, "Null crop of new wallpaper; copying");
-            }
-            success = FileUtils.copyFile(wallpaper.wallpaperFile, wallpaper.cropFile);
-            if (!success) {
-                wallpaper.cropFile.delete();
-                // TODO: fall back to default wallpaper in this case
-            }
+        if (options.outWidth <= 0 || options.outHeight <= 0) {
+            Slog.e(TAG, "Invalid wallpaper data");
+            success = false;
         } else {
-            // Fancy case: crop and/or scale
-            FileOutputStream f = null;
-            BufferedOutputStream bos = null;
-            try {
-                BitmapRegionDecoder decoder = BitmapRegionDecoder.newInstance(
-                        wallpaper.wallpaperFile.getAbsolutePath(), false);
-                Bitmap cropped = decoder.decodeRegion(wallpaper.cropHint, null);
-                decoder.recycle();
+            boolean needCrop = false;
+            boolean needScale = false;
 
-                if (cropped == null) {
-                    Slog.e(TAG, "Could not decode new wallpaper");
-                } else {
-                    f = new FileOutputStream(wallpaper.cropFile);
-                    bos = new BufferedOutputStream(f, 32*1024);
-                    cropped.compress(Bitmap.CompressFormat.PNG, 90, bos);
-                    bos.flush();  // don't rely on the implicit flush-at-close when noting success
-                    success = true;
-                }
-            } catch (IOException e) {
+            // Empty crop means use the full image
+            if (cropHint.isEmpty()) {
+                cropHint.left = cropHint.top = 0;
+                cropHint.right = options.outWidth;
+                cropHint.bottom = options.outHeight;
+            } else {
+                // force the crop rect to lie within the measured bounds
+                cropHint.offset(
+                        (cropHint.right > options.outWidth ? options.outWidth - cropHint.right : 0),
+                        (cropHint.bottom > options.outHeight ? options.outHeight - cropHint.bottom : 0));
+
+                // Don't bother cropping if what we're left with is identity
+                needCrop = (options.outHeight >= cropHint.height()
+                        && options.outWidth >= cropHint.width());
+            }
+
+            // scale if the crop height winds up not matching the recommended metrics
+            needScale = (wallpaper.height != cropHint.height());
+
+            if (DEBUG) {
+                Slog.v(TAG, "crop: w=" + cropHint.width() + " h=" + cropHint.height());
+                Slog.v(TAG, "dims: w=" + wallpaper.width + " h=" + wallpaper.height);
+                Slog.v(TAG, "meas: w=" + options.outWidth + " h=" + options.outHeight);
+                Slog.v(TAG, "crop?=" + needCrop + " scale?=" + needScale);
+            }
+
+            if (!needCrop && !needScale) {
+                // Simple case:  the nominal crop fits what we want, so we take
+                // the whole thing and just copy the image file directly.
                 if (DEBUG) {
-                    Slog.e(TAG, "I/O error decoding crop: " + e.getMessage());
+                    Slog.v(TAG, "Null crop of new wallpaper; copying");
                 }
-            } finally {
-                IoUtils.closeQuietly(bos);
-                IoUtils.closeQuietly(f);
+                success = FileUtils.copyFile(wallpaper.wallpaperFile, wallpaper.cropFile);
+                if (!success) {
+                    wallpaper.cropFile.delete();
+                    // TODO: fall back to default wallpaper in this case
+                }
+            } else {
+                // Fancy case: crop and scale.  First, we decode and scale down if appropriate.
+                FileOutputStream f = null;
+                BufferedOutputStream bos = null;
+                try {
+                    BitmapRegionDecoder decoder = BitmapRegionDecoder.newInstance(
+                            wallpaper.wallpaperFile.getAbsolutePath(), false);
+
+                    // This actually downsamples only by powers of two, but that's okay; we do
+                    // a proper scaling blit later.  This is to minimize transient RAM use.
+                    // We calculate the largest power-of-two under the actual ratio rather than
+                    // just let the decode take care of it because we also want to remap where the
+                    // cropHint rectangle lies in the decoded [super]rect.
+                    final BitmapFactory.Options scaler;
+                    final int actualScale = cropHint.height() / wallpaper.height;
+                    int scale = 1;
+                    while (2*scale < actualScale) {
+                        scale *= 2;
+                    }
+                    if (scale > 1) {
+                        scaler = new BitmapFactory.Options();
+                        scaler.inSampleSize = scale;
+                        if (DEBUG) {
+                            Slog.v(TAG, "Downsampling cropped rect with scale " + scale);
+                        }
+                    } else {
+                        scaler = null;
+                    }
+                    Bitmap cropped = decoder.decodeRegion(cropHint, scaler);
+                    decoder.recycle();
+
+                    if (cropped == null) {
+                        Slog.e(TAG, "Could not decode new wallpaper");
+                    } else {
+                        // We've got the extracted crop; now we want to scale it properly to
+                        // the desired rectangle.  That's a height-biased operation: make it
+                        // fit the hinted height, and accept whatever width we end up with.
+                        cropHint.offsetTo(0, 0);
+                        cropHint.right /= scale;    // adjust by downsampling factor
+                        cropHint.bottom /= scale;
+                        final float heightR = ((float)wallpaper.height) / ((float)cropHint.height());
+                        if (DEBUG) {
+                            Slog.v(TAG, "scale " + heightR + ", extracting " + cropHint);
+                        }
+                        final int destWidth = (int)(cropHint.width() * heightR);
+                        final Bitmap finalCrop = Bitmap.createScaledBitmap(cropped,
+                                destWidth, wallpaper.height, true);
+                        if (DEBUG) {
+                            Slog.v(TAG, "Final extract:");
+                            Slog.v(TAG, "  dims: w=" + wallpaper.width
+                                    + " h=" + wallpaper.height);
+                            Slog.v(TAG, "   out: w=" + finalCrop.getWidth()
+                                    + " h=" + finalCrop.getHeight());
+                        }
+
+                        f = new FileOutputStream(wallpaper.cropFile);
+                        bos = new BufferedOutputStream(f, 32*1024);
+                        finalCrop.compress(Bitmap.CompressFormat.PNG, 90, bos);
+                        bos.flush();  // don't rely on the implicit flush-at-close when noting success
+                        success = true;
+                    }
+                } catch (Exception e) {
+                    if (DEBUG) {
+                        Slog.e(TAG, "Error decoding crop", e);
+                    }
+                } finally {
+                    IoUtils.closeQuietly(bos);
+                    IoUtils.closeQuietly(f);
+                }
             }
         }
 
diff --git a/services/core/java/com/android/server/webkit/SystemImpl.java b/services/core/java/com/android/server/webkit/SystemImpl.java
index 9486cfd..a5d68da 100644
--- a/services/core/java/com/android/server/webkit/SystemImpl.java
+++ b/services/core/java/com/android/server/webkit/SystemImpl.java
@@ -19,6 +19,7 @@
 import android.app.ActivityManagerNative;
 import android.app.AppGlobals;
 import android.content.Context;
+import android.content.pm.ApplicationInfo;
 import android.content.pm.IPackageDeleteObserver;
 import android.content.pm.PackageInfo;
 import android.content.pm.PackageManager;
@@ -33,7 +34,6 @@
 import android.provider.Settings;
 import android.util.AndroidRuntimeException;
 import android.util.Log;
-import android.webkit.WebViewFactory.MissingWebViewPackageException;
 import android.webkit.WebViewFactory;
 import android.webkit.WebViewProviderInfo;
 
@@ -67,6 +67,7 @@
     @Override
     public WebViewProviderInfo[] getWebViewPackages() {
         int numFallbackPackages = 0;
+        int numAvailableByDefaultPackages = 0;
         XmlResourceParser parser = null;
         List<WebViewProviderInfo> webViewProviders = new ArrayList<WebViewProviderInfo>();
         try {
@@ -82,12 +83,12 @@
                 if (element.equals(TAG_WEBVIEW_PROVIDER)) {
                     String packageName = parser.getAttributeValue(null, TAG_PACKAGE_NAME);
                     if (packageName == null) {
-                        throw new MissingWebViewPackageException(
+                        throw new AndroidRuntimeException(
                                 "WebView provider in framework resources missing package name");
                     }
                     String description = parser.getAttributeValue(null, TAG_DESCRIPTION);
                     if (description == null) {
-                        throw new MissingWebViewPackageException(
+                        throw new AndroidRuntimeException(
                                 "WebView provider in framework resources missing description");
                     }
                     boolean availableByDefault = "true".equals(
@@ -99,22 +100,33 @@
                             readSignatures(parser));
                     if (currentProvider.isFallback) {
                         numFallbackPackages++;
+                        if (!currentProvider.availableByDefault) {
+                            throw new AndroidRuntimeException(
+                                    "Each WebView fallback package must be available by default.");
+                        }
                         if (numFallbackPackages > 1) {
                             throw new AndroidRuntimeException(
-                                    "There can be at most one webview fallback package.");
+                                    "There can be at most one WebView fallback package.");
                         }
                     }
+                    if (currentProvider.availableByDefault) {
+                        numAvailableByDefaultPackages++;
+                    }
                     webViewProviders.add(currentProvider);
                 }
                 else {
-                    Log.e(TAG, "Found an element that is not a webview provider");
+                    Log.e(TAG, "Found an element that is not a WebView provider");
                 }
             }
         } catch (XmlPullParserException | IOException e) {
-            throw new MissingWebViewPackageException("Error when parsing WebView meta data " + e);
+            throw new AndroidRuntimeException("Error when parsing WebView config " + e);
         } finally {
             if (parser != null) parser.close();
         }
+        if (numAvailableByDefaultPackages == 0) {
+            throw new AndroidRuntimeException("There must be at least one WebView package "
+                    + "that is available by default");
+        }
         return webViewProviders.toArray(new WebViewProviderInfo[webViewProviders.size()]);
     }
 
@@ -187,7 +199,8 @@
         enablePackageForAllUsers(context, packageName, false);
         try {
             PackageManager pm = AppGlobals.getInitialApplication().getPackageManager();
-            if (pm.getApplicationInfo(packageName, 0).isUpdatedSystemApp()) {
+            ApplicationInfo applicationInfo = pm.getApplicationInfo(packageName, 0);
+            if (applicationInfo != null && applicationInfo.isUpdatedSystemApp()) {
                 pm.deletePackage(packageName, new IPackageDeleteObserver.Stub() {
                         public void packageDeleted(String packageName, int returnCode) {
                             enablePackageForAllUsers(context, packageName, false);
@@ -214,8 +227,9 @@
                     enable ? PackageManager.COMPONENT_ENABLED_STATE_DEFAULT :
                     PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER, 0,
                     userId, null);
-        } catch (RemoteException e) {
-            Log.w(TAG, "Tried to disable " + packageName + " for user " + userId + ": " + e);
+        } catch (RemoteException | IllegalArgumentException e) {
+            Log.w(TAG, "Tried to " + (enable ? "enable " : "disable ") + packageName
+                    + " for user " + userId + ": " + e);
         }
     }
 
diff --git a/services/core/java/com/android/server/webkit/WebViewUpdateService.java b/services/core/java/com/android/server/webkit/WebViewUpdateService.java
index ebec445..bbb4951 100644
--- a/services/core/java/com/android/server/webkit/WebViewUpdateService.java
+++ b/services/core/java/com/android/server/webkit/WebViewUpdateService.java
@@ -20,17 +20,12 @@
 import android.content.Context;
 import android.content.Intent;
 import android.content.IntentFilter;
-import android.content.pm.ApplicationInfo;
-import android.content.pm.PackageInfo;
 import android.content.pm.PackageManager;
-import android.content.pm.PackageManager.NameNotFoundException;
-import android.content.pm.Signature;
 import android.os.Binder;
 import android.os.PatternMatcher;
 import android.os.Process;
 import android.os.ResultReceiver;
 import android.os.UserHandle;
-import android.util.Base64;
 import android.util.Slog;
 import android.webkit.IWebViewUpdateService;
 import android.webkit.WebViewFactory;
@@ -40,9 +35,7 @@
 import com.android.server.SystemService;
 
 import java.io.FileDescriptor;
-import java.util.ArrayList;
 import java.util.Arrays;
-import java.util.List;
 
 /**
  * Private service to wait for the updatable WebView to be ready for use.
@@ -53,19 +46,16 @@
     private static final String TAG = "WebViewUpdateService";
 
     private BroadcastReceiver mWebViewUpdatedReceiver;
-    private SystemInterface mSystemInterface;
+    private WebViewUpdateServiceImpl mImpl;
 
     static final int PACKAGE_CHANGED = 0;
     static final int PACKAGE_ADDED = 1;
     static final int PACKAGE_ADDED_REPLACED = 2;
     static final int PACKAGE_REMOVED = 3;
 
-    private WebViewUpdater mWebViewUpdater;
-
     public WebViewUpdateService(Context context) {
         super(context);
-        mSystemInterface = new SystemImpl();
-        mWebViewUpdater = new WebViewUpdater(getContext(), mSystemInterface);
+        mImpl = new WebViewUpdateServiceImpl(context, new SystemImpl());
     }
 
     @Override
@@ -82,24 +72,26 @@
                             // the package that is being replaced we early-out here so that we don't
                             // run the update-logic twice.
                             if (intent.getExtras().getBoolean(Intent.EXTRA_REPLACING)) return;
-                            packageStateChanged(packageNameFromIntent(intent), PACKAGE_REMOVED);
+                            mImpl.packageStateChanged(packageNameFromIntent(intent),
+                                    PACKAGE_REMOVED);
                             break;
                         case Intent.ACTION_PACKAGE_CHANGED:
                             // Ensure that we only heed PACKAGE_CHANGED intents if they change an
                             // entire package, not just a component
                             if (entirePackageChanged(intent)) {
-                                packageStateChanged(packageNameFromIntent(intent), PACKAGE_CHANGED);
+                                mImpl.packageStateChanged(packageNameFromIntent(intent),
+                                        PACKAGE_CHANGED);
                             }
                             break;
                         case Intent.ACTION_PACKAGE_ADDED:
-                            packageStateChanged(packageNameFromIntent(intent),
+                            mImpl.packageStateChanged(packageNameFromIntent(intent),
                                     (intent.getExtras().getBoolean(Intent.EXTRA_REPLACING)
                                      ? PACKAGE_ADDED_REPLACED : PACKAGE_ADDED));
                             break;
                         case Intent.ACTION_USER_ADDED:
                             int userId =
                                 intent.getIntExtra(Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL);
-                            handleNewUser(userId);
+                            mImpl.handleNewUser(userId);
                             break;
                     }
                 }
@@ -110,7 +102,7 @@
         filter.addAction(Intent.ACTION_PACKAGE_CHANGED);
         filter.addDataScheme("package");
         // Make sure we only receive intents for WebView packages from our config file.
-        for (WebViewProviderInfo provider : mSystemInterface.getWebViewPackages()) {
+        for (WebViewProviderInfo provider : mImpl.getWebViewPackages()) {
             filter.addDataSchemeSpecificPart(provider.packageName, PatternMatcher.PATTERN_LITERAL);
         }
         getContext().registerReceiver(mWebViewUpdatedReceiver, filter);
@@ -122,518 +114,14 @@
         publishBinderService("webviewupdate", new BinderService(), true /*allowIsolated*/);
     }
 
-    private void packageStateChanged(String packageName, int changedState) {
-        updateFallbackState(packageName, changedState);
-        mWebViewUpdater.packageStateChanged(packageName, changedState);
-    }
-
     public void prepareWebViewInSystemServer() {
-        updateFallbackStateOnBoot();
-        mWebViewUpdater.prepareWebViewInSystemServer();
+        mImpl.prepareWebViewInSystemServer();
     }
 
     private static String packageNameFromIntent(Intent intent) {
         return intent.getDataString().substring("package:".length());
     }
 
-    private boolean existsValidNonFallbackProvider(WebViewProviderInfo[] providers) {
-        for (WebViewProviderInfo provider : providers) {
-            if (provider.availableByDefault && !provider.isFallback) {
-                try {
-                    PackageInfo packageInfo = mSystemInterface.getPackageInfoForProvider(provider);
-                    if (isEnabledPackage(packageInfo)
-                            && mWebViewUpdater.isValidProvider(provider, packageInfo)) {
-                        return true;
-                    }
-                } catch (NameNotFoundException e) {
-                    // A non-existent provider is neither valid nor enabled
-                }
-            }
-        }
-        return false;
-    }
-
-    /**
-     * Called when a new user has been added to update the state of its fallback package.
-     */
-    void handleNewUser(int userId) {
-        if (!mSystemInterface.isFallbackLogicEnabled()) return;
-
-        WebViewProviderInfo[] webviewProviders = mSystemInterface.getWebViewPackages();
-        WebViewProviderInfo fallbackProvider = getFallbackProvider(webviewProviders);
-        if (fallbackProvider == null) return;
-
-        mSystemInterface.enablePackageForUser(fallbackProvider.packageName,
-                !existsValidNonFallbackProvider(webviewProviders), userId);
-    }
-
-    public void updateFallbackStateOnBoot() {
-        WebViewProviderInfo[] webviewProviders = mSystemInterface.getWebViewPackages();
-        updateFallbackState(webviewProviders, true);
-    }
-
-    /**
-     * Handle the enabled-state of our fallback package, i.e. if there exists some non-fallback
-     * package that is valid (and available by default) then disable the fallback package,
-     * otherwise, enable the fallback package.
-     */
-    public void updateFallbackState(String changedPackage, int changedState) {
-        if (!mSystemInterface.isFallbackLogicEnabled()) return;
-
-        WebViewProviderInfo[] webviewProviders = mSystemInterface.getWebViewPackages();
-
-        // A package was changed / updated / downgraded, early out if it is not one of the
-        // webview packages that are available by default.
-        boolean changedPackageAvailableByDefault = false;
-        for (WebViewProviderInfo provider : webviewProviders) {
-            if (provider.packageName.equals(changedPackage)) {
-                if (provider.availableByDefault) {
-                    changedPackageAvailableByDefault = true;
-                }
-                break;
-            }
-        }
-        if (!changedPackageAvailableByDefault) return;
-        updateFallbackState(webviewProviders, false);
-    }
-
-    private void updateFallbackState(WebViewProviderInfo[] webviewProviders, boolean isBoot) {
-        // If there exists a valid and enabled non-fallback package - disable the fallback
-        // package, otherwise, enable it.
-        WebViewProviderInfo fallbackProvider = getFallbackProvider(webviewProviders);
-        if (fallbackProvider == null) return;
-        boolean existsValidNonFallbackProvider = existsValidNonFallbackProvider(webviewProviders);
-
-        boolean isFallbackEnabled = false;
-        try {
-            isFallbackEnabled = isEnabledPackage(
-                    mSystemInterface.getPackageInfoForProvider(fallbackProvider));
-        } catch (NameNotFoundException e) {
-        }
-
-        if (existsValidNonFallbackProvider
-                // During an OTA the primary user's WebView state might differ from other users', so
-                // ignore the state of that user during boot.
-                && (isFallbackEnabled || isBoot)) {
-            mSystemInterface.uninstallAndDisablePackageForAllUsers(getContext(),
-                    fallbackProvider.packageName);
-        } else if (!existsValidNonFallbackProvider
-                // During an OTA the primary user's WebView state might differ from other users', so
-                // ignore the state of that user during boot.
-                && (!isFallbackEnabled || isBoot)) {
-            // Enable the fallback package for all users.
-            mSystemInterface.enablePackageForAllUsers(getContext(),
-                    fallbackProvider.packageName, true);
-        }
-    }
-
-    /**
-     * Returns the only fallback provider in the set of given packages, or null if there is none.
-     */
-    private static WebViewProviderInfo getFallbackProvider(WebViewProviderInfo[] webviewPackages) {
-        for (WebViewProviderInfo provider : webviewPackages) {
-            if (provider.isFallback) {
-                return provider;
-            }
-        }
-        return null;
-    }
-
-    private boolean isFallbackPackage(String packageName) {
-        if (packageName == null || !mSystemInterface.isFallbackLogicEnabled()) return false;
-
-        WebViewProviderInfo[] webviewPackages = mSystemInterface.getWebViewPackages();
-        WebViewProviderInfo fallbackProvider = getFallbackProvider(webviewPackages);
-        return (fallbackProvider != null
-                && packageName.equals(fallbackProvider.packageName));
-    }
-
-    /**
-     * Class that decides what WebView implementation to use and prepares that implementation for
-     * use.
-     */
-    private static class WebViewUpdater {
-        private Context mContext;
-        private SystemInterface mSystemInterface;
-        private int mMinimumVersionCode = -1;
-
-        public WebViewUpdater(Context context, SystemInterface systemInterface) {
-            mContext = context;
-            mSystemInterface = systemInterface;
-        }
-
-        private static final int WAIT_TIMEOUT_MS = 4500; // KEY_DISPATCHING_TIMEOUT is 5000.
-
-        // Keeps track of the number of running relro creations
-        private int mNumRelroCreationsStarted = 0;
-        private int mNumRelroCreationsFinished = 0;
-        // Implies that we need to rerun relro creation because we are using an out-of-date package
-        private boolean mWebViewPackageDirty = false;
-        private boolean mAnyWebViewInstalled = false;
-
-        private int NUMBER_OF_RELROS_UNKNOWN = Integer.MAX_VALUE;
-
-        // The WebView package currently in use (or the one we are preparing).
-        private PackageInfo mCurrentWebViewPackage = null;
-
-        private Object mLock = new Object();
-
-        public void packageStateChanged(String packageName, int changedState) {
-            for (WebViewProviderInfo provider : mSystemInterface.getWebViewPackages()) {
-                String webviewPackage = provider.packageName;
-
-                if (webviewPackage.equals(packageName)) {
-                    boolean updateWebView = false;
-                    boolean removedOrChangedOldPackage = false;
-                    String oldProviderName = null;
-                    PackageInfo newPackage = null;
-                    synchronized(mLock) {
-                        try {
-                            newPackage = findPreferredWebViewPackage();
-                            if (mCurrentWebViewPackage != null)
-                                oldProviderName = mCurrentWebViewPackage.packageName;
-                            // Only trigger update actions if the updated package is the one
-                            // that will be used, or the one that was in use before the
-                            // update, or if we haven't seen a valid WebView package before.
-                            updateWebView =
-                                provider.packageName.equals(newPackage.packageName)
-                                || provider.packageName.equals(oldProviderName)
-                                || mCurrentWebViewPackage == null;
-                            // We removed the old package if we received an intent to remove
-                            // or replace the old package.
-                            removedOrChangedOldPackage =
-                                provider.packageName.equals(oldProviderName);
-                            if (updateWebView) {
-                                onWebViewProviderChanged(newPackage);
-                            }
-                        } catch (WebViewFactory.MissingWebViewPackageException e) {
-                            Slog.e(TAG, "Could not find valid WebView package to create " +
-                                    "relro with " + e);
-                        }
-                    }
-                    if(updateWebView && !removedOrChangedOldPackage
-                            && oldProviderName != null) {
-                        // If the provider change is the result of adding or replacing a
-                        // package that was not the previous provider then we must kill
-                        // packages dependent on the old package ourselves. The framework
-                        // only kills dependents of packages that are being removed.
-                        mSystemInterface.killPackageDependents(oldProviderName);
-                    }
-                    return;
-                }
-            }
-        }
-
-        public void prepareWebViewInSystemServer() {
-            try {
-                synchronized(mLock) {
-                    mCurrentWebViewPackage = findPreferredWebViewPackage();
-                    onWebViewProviderChanged(mCurrentWebViewPackage);
-                }
-            } catch (Throwable t) {
-                // Log and discard errors at this stage as we must not crash the system server.
-                Slog.e(TAG, "error preparing webview provider from system server", t);
-            }
-        }
-
-        /**
-         * Change WebView provider and provider setting and kill packages using the old provider.
-         * Return the new provider (in case we are in the middle of creating relro files this new
-         * provider will not be in use directly, but will when the relros are done).
-         */
-        public String changeProviderAndSetting(String newProviderName) {
-            PackageInfo oldPackage = null;
-            PackageInfo newPackage = null;
-            synchronized(mLock) {
-                oldPackage = mCurrentWebViewPackage;
-                mSystemInterface.updateUserSetting(mContext, newProviderName);
-
-                try {
-                    newPackage = findPreferredWebViewPackage();
-                    if (oldPackage != null
-                            && newPackage.packageName.equals(oldPackage.packageName)) {
-                        // If we don't perform the user change, revert the settings change.
-                        mSystemInterface.updateUserSetting(mContext, newPackage.packageName);
-                        return newPackage.packageName;
-                    }
-                } catch (WebViewFactory.MissingWebViewPackageException e) {
-                    Slog.e(TAG, "Tried to change WebView provider but failed to fetch WebView " +
-                            "package " + e);
-                    // If we don't perform the user change but don't have an installed WebView
-                    // package, we will have changed the setting and it will be used when a package
-                    // is available.
-                    return newProviderName;
-                }
-                onWebViewProviderChanged(newPackage);
-            }
-            // Kill apps using the old provider
-            if (oldPackage != null) {
-                mSystemInterface.killPackageDependents(oldPackage.packageName);
-            }
-            return newPackage.packageName;
-        }
-
-        /**
-         * This is called when we change WebView provider, either when the current provider is
-         * updated or a new provider is chosen / takes precedence.
-         */
-        private void onWebViewProviderChanged(PackageInfo newPackage) {
-            synchronized(mLock) {
-                mAnyWebViewInstalled = true;
-                if (mNumRelroCreationsStarted == mNumRelroCreationsFinished) {
-                    mCurrentWebViewPackage = newPackage;
-                    mSystemInterface.updateUserSetting(mContext, newPackage.packageName);
-
-                    // The relro creations might 'finish' (not start at all) before
-                    // WebViewFactory.onWebViewProviderChanged which means we might not know the
-                    // number of started creations before they finish.
-                    mNumRelroCreationsStarted = NUMBER_OF_RELROS_UNKNOWN;
-                    mNumRelroCreationsFinished = 0;
-                    mNumRelroCreationsStarted =
-                        mSystemInterface.onWebViewProviderChanged(newPackage);
-                    // If the relro creations finish before we know the number of started creations
-                    // we will have to do any cleanup/notifying here.
-                    checkIfRelrosDoneLocked();
-                } else {
-                    mWebViewPackageDirty = true;
-                }
-            }
-        }
-
-        private ProviderAndPackageInfo[] getValidWebViewPackagesAndInfos() {
-            WebViewProviderInfo[] allProviders = mSystemInterface.getWebViewPackages();
-            List<ProviderAndPackageInfo> providers = new ArrayList<>();
-            for(int n = 0; n < allProviders.length; n++) {
-                try {
-                    PackageInfo packageInfo =
-                        mSystemInterface.getPackageInfoForProvider(allProviders[n]);
-                    if (isValidProvider(allProviders[n], packageInfo)) {
-                        providers.add(new ProviderAndPackageInfo(allProviders[n], packageInfo));
-                    }
-                } catch (NameNotFoundException e) {
-                    // Don't add non-existent packages
-                }
-            }
-            return providers.toArray(new ProviderAndPackageInfo[providers.size()]);
-        }
-
-        /**
-         * Fetch only the currently valid WebView packages.
-         **/
-        public WebViewProviderInfo[] getValidWebViewPackages() {
-            ProviderAndPackageInfo[] providersAndPackageInfos = getValidWebViewPackagesAndInfos();
-            WebViewProviderInfo[] providers =
-                new WebViewProviderInfo[providersAndPackageInfos.length];
-            for(int n = 0; n < providersAndPackageInfos.length; n++) {
-                providers[n] = providersAndPackageInfos[n].provider;
-            }
-            return providers;
-        }
-
-
-        private class ProviderAndPackageInfo {
-            public final WebViewProviderInfo provider;
-            public final PackageInfo packageInfo;
-
-            public ProviderAndPackageInfo(WebViewProviderInfo provider, PackageInfo packageInfo) {
-                this.provider = provider;
-                this.packageInfo = packageInfo;
-            }
-        }
-
-        /**
-         * Returns either the package info of the WebView provider determined in the following way:
-         * If the user has chosen a provider then use that if it is valid,
-         * otherwise use the first package in the webview priority list that is valid.
-         *
-         */
-        private PackageInfo findPreferredWebViewPackage() {
-            ProviderAndPackageInfo[] providers = getValidWebViewPackagesAndInfos();
-
-            String userChosenProvider = mSystemInterface.getUserChosenWebViewProvider(mContext);
-
-            // If the user has chosen provider, use that
-            for (ProviderAndPackageInfo providerAndPackage : providers) {
-                if (providerAndPackage.provider.packageName.equals(userChosenProvider)
-                        && isEnabledPackage(providerAndPackage.packageInfo)) {
-                    return providerAndPackage.packageInfo;
-                }
-            }
-
-            // User did not choose, or the choice failed; use the most stable provider that is
-            // enabled and available by default (not through user choice).
-            for (ProviderAndPackageInfo providerAndPackage : providers) {
-                if (providerAndPackage.provider.availableByDefault
-                        && isEnabledPackage(providerAndPackage.packageInfo)) {
-                    return providerAndPackage.packageInfo;
-                }
-            }
-
-            // Could not find any enabled package either, use the most stable provider.
-            for (ProviderAndPackageInfo providerAndPackage : providers) {
-                return providerAndPackage.packageInfo;
-            }
-
-            mAnyWebViewInstalled = false;
-            throw new WebViewFactory.MissingWebViewPackageException(
-                    "Could not find a loadable WebView package");
-        }
-
-        public void notifyRelroCreationCompleted() {
-            synchronized (mLock) {
-                mNumRelroCreationsFinished++;
-                checkIfRelrosDoneLocked();
-            }
-        }
-
-        public WebViewProviderResponse waitForAndGetProvider() {
-            PackageInfo webViewPackage = null;
-            final long NS_PER_MS = 1000000;
-            final long timeoutTimeMs = System.nanoTime() / NS_PER_MS + WAIT_TIMEOUT_MS;
-            boolean webViewReady = false;
-            int webViewStatus = WebViewFactory.LIBLOAD_SUCCESS;
-            synchronized (mLock) {
-                webViewReady = webViewIsReadyLocked();
-                while (!webViewReady) {
-                    final long timeNowMs = System.nanoTime() / NS_PER_MS;
-                    if (timeNowMs >= timeoutTimeMs) break;
-                    try {
-                        mLock.wait(timeoutTimeMs - timeNowMs);
-                    } catch (InterruptedException e) {}
-                    webViewReady = webViewIsReadyLocked();
-                }
-                // Make sure we return the provider that was used to create the relro file
-                webViewPackage = mCurrentWebViewPackage;
-                if (webViewReady) {
-                } else if (!mAnyWebViewInstalled) {
-                    webViewStatus = WebViewFactory.LIBLOAD_FAILED_LISTING_WEBVIEW_PACKAGES;
-                } else {
-                    // Either the current relro creation  isn't done yet, or the new relro creatioin
-                    // hasn't kicked off yet (the last relro creation used an out-of-date WebView).
-                    webViewStatus = WebViewFactory.LIBLOAD_FAILED_WAITING_FOR_RELRO;
-                }
-            }
-            if (!webViewReady) Slog.w(TAG, "creating relro file timed out");
-            return new WebViewProviderResponse(webViewPackage, webViewStatus);
-        }
-
-        public String getCurrentWebViewPackageName() {
-            synchronized(mLock) {
-                if (mCurrentWebViewPackage == null)
-                    return null;
-                return mCurrentWebViewPackage.packageName;
-            }
-        }
-
-        /**
-         * Returns whether WebView is ready and is not going to go through its preparation phase
-         * again directly.
-         */
-        private boolean webViewIsReadyLocked() {
-            return !mWebViewPackageDirty
-                && (mNumRelroCreationsStarted == mNumRelroCreationsFinished)
-                // The current package might be replaced though we haven't received an intent
-                // declaring this yet, the following flag makes anyone loading WebView to wait in
-                // this case.
-                && mAnyWebViewInstalled;
-        }
-
-        private void checkIfRelrosDoneLocked() {
-            if (mNumRelroCreationsStarted == mNumRelroCreationsFinished) {
-                if (mWebViewPackageDirty) {
-                    mWebViewPackageDirty = false;
-                    // If we have changed provider since we started the relro creation we need to
-                    // redo the whole process using the new package instead.
-                    PackageInfo newPackage = findPreferredWebViewPackage();
-                    onWebViewProviderChanged(newPackage);
-                } else {
-                    mLock.notifyAll();
-                }
-            }
-        }
-
-        /**
-         * Returns whether this provider is valid for use as a WebView provider.
-         */
-        public boolean isValidProvider(WebViewProviderInfo configInfo,
-                PackageInfo packageInfo) {
-            if ((packageInfo.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) == 0
-                    && packageInfo.versionCode < getMinimumVersionCode()
-                    && !mSystemInterface.systemIsDebuggable()) {
-                // Non-system package webview providers may be downgraded arbitrarily low, prevent
-                // that by enforcing minimum version code. This check is only enforced for user
-                // builds.
-                return false;
-            }
-            if (providerHasValidSignature(configInfo, packageInfo, mSystemInterface) &&
-                    WebViewFactory.getWebViewLibrary(packageInfo.applicationInfo) != null) {
-                return true;
-            }
-            return false;
-        }
-
-        /**
-         * Gets the minimum version code allowed for a valid provider. It is the minimum versionCode
-         * of all available-by-default and non-fallback WebView provider packages. If there is no
-         * such WebView provider package on the system, then return -1, which means all positive
-         * versionCode WebView packages are accepted.
-         */
-        private int getMinimumVersionCode() {
-            if (mMinimumVersionCode > 0) {
-                return mMinimumVersionCode;
-            }
-
-            for (WebViewProviderInfo provider : mSystemInterface.getWebViewPackages()) {
-                if (provider.availableByDefault && !provider.isFallback) {
-                    try {
-                        int versionCode =
-                            mSystemInterface.getFactoryPackageVersion(provider.packageName);
-                        if (mMinimumVersionCode < 0 || versionCode < mMinimumVersionCode) {
-                            mMinimumVersionCode = versionCode;
-                        }
-                    } catch (PackageManager.NameNotFoundException e) {
-                        // Safe to ignore.
-                    }
-                }
-            }
-
-            return mMinimumVersionCode;
-        }
-    }
-
-    private static boolean providerHasValidSignature(WebViewProviderInfo provider,
-            PackageInfo packageInfo, SystemInterface systemInterface) {
-        if (systemInterface.systemIsDebuggable()) {
-            return true;
-        }
-        Signature[] packageSignatures;
-        // If no signature is declared, instead check whether the package is included in the
-        // system.
-        if (provider.signatures == null || provider.signatures.length == 0) {
-            return packageInfo.applicationInfo.isSystemApp();
-        }
-        packageSignatures = packageInfo.signatures;
-        if (packageSignatures.length != 1)
-            return false;
-
-        final byte[] packageSignature = packageSignatures[0].toByteArray();
-        // Return whether the package signature matches any of the valid signatures
-        for (String signature : provider.signatures) {
-            final byte[] validSignature = Base64.decode(signature, Base64.DEFAULT);
-            if (Arrays.equals(packageSignature, validSignature))
-                return true;
-        }
-        return false;
-    }
-
-    /**
-     * Returns whether the given package is enabled.
-     * This state can be changed by the user from Settings->Apps
-     */
-    private static boolean isEnabledPackage(PackageInfo packageInfo) {
-        return packageInfo.applicationInfo.enabled;
-    }
-
     /**
      * Returns whether the entire package from an ACTION_PACKAGE_CHANGED intent was changed (rather
      * than just one of its components).
@@ -673,7 +161,7 @@
 
             long callingId = Binder.clearCallingIdentity();
             try {
-                WebViewUpdateService.this.mWebViewUpdater.notifyRelroCreationCompleted();
+                WebViewUpdateService.this.mImpl.notifyRelroCreationCompleted();
             } finally {
                 Binder.restoreCallingIdentity(callingId);
             }
@@ -693,7 +181,7 @@
                 throw new IllegalStateException("Cannot create a WebView from the SystemServer");
             }
 
-            return WebViewUpdateService.this.mWebViewUpdater.waitForAndGetProvider();
+            return WebViewUpdateService.this.mImpl.waitForAndGetProvider();
         }
 
         /**
@@ -714,7 +202,7 @@
 
             long callingId = Binder.clearCallingIdentity();
             try {
-                return WebViewUpdateService.this.mWebViewUpdater.changeProviderAndSetting(
+                return WebViewUpdateService.this.mImpl.changeProviderAndSetting(
                         newProvider);
             } finally {
                 Binder.restoreCallingIdentity(callingId);
@@ -723,22 +211,22 @@
 
         @Override // Binder call
         public WebViewProviderInfo[] getValidWebViewPackages() {
-            return WebViewUpdateService.this.mWebViewUpdater.getValidWebViewPackages();
+            return WebViewUpdateService.this.mImpl.getValidWebViewPackages();
         }
 
         @Override // Binder call
         public WebViewProviderInfo[] getAllWebViewPackages() {
-            return WebViewUpdateService.this.mSystemInterface.getWebViewPackages();
+            return WebViewUpdateService.this.mImpl.getWebViewPackages();
         }
 
         @Override // Binder call
         public String getCurrentWebViewPackageName() {
-            return WebViewUpdateService.this.mWebViewUpdater.getCurrentWebViewPackageName();
+            return WebViewUpdateService.this.mImpl.getCurrentWebViewPackageName();
         }
 
         @Override // Binder call
         public boolean isFallbackPackage(String packageName) {
-            return WebViewUpdateService.this.isFallbackPackage(packageName);
+            return WebViewUpdateService.this.mImpl.isFallbackPackage(packageName);
         }
 
         @Override // Binder call
@@ -754,7 +242,12 @@
                 throw new SecurityException(msg);
             }
 
-            WebViewUpdateService.this.mSystemInterface.enableFallbackLogic(enable);
+            long callingId = Binder.clearCallingIdentity();
+            try {
+                WebViewUpdateService.this.mImpl.enableFallbackLogic(enable);
+            } finally {
+                Binder.restoreCallingIdentity(callingId);
+            }
         }
     }
 }
diff --git a/services/core/java/com/android/server/webkit/WebViewUpdateServiceImpl.java b/services/core/java/com/android/server/webkit/WebViewUpdateServiceImpl.java
new file mode 100644
index 0000000..df5d027
--- /dev/null
+++ b/services/core/java/com/android/server/webkit/WebViewUpdateServiceImpl.java
@@ -0,0 +1,599 @@
+/*
+ * 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 com.android.server.webkit;
+
+import android.content.Context;
+import android.content.pm.ApplicationInfo;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager.NameNotFoundException;
+import android.content.pm.Signature;
+import android.util.Base64;
+import android.util.Slog;
+import android.webkit.WebViewFactory;
+import android.webkit.WebViewProviderInfo;
+import android.webkit.WebViewProviderResponse;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * Implementation of the WebViewUpdateService.
+ * This class doesn't depend on the android system like the actual Service does and can be used
+ * directly by tests (as long as they implement a SystemInterface).
+ * @hide
+ */
+public class WebViewUpdateServiceImpl {
+    private static final String TAG = WebViewUpdateServiceImpl.class.getSimpleName();
+
+    private SystemInterface mSystemInterface;
+    private WebViewUpdater mWebViewUpdater;
+    private Context mContext;
+
+    public WebViewUpdateServiceImpl(Context context, SystemInterface systemInterface) {
+        mContext = context;
+        mSystemInterface = systemInterface;
+        mWebViewUpdater = new WebViewUpdater(mContext, mSystemInterface);
+    }
+
+    void packageStateChanged(String packageName, int changedState) {
+        updateFallbackStateOnPackageChange(packageName, changedState);
+        mWebViewUpdater.packageStateChanged(packageName, changedState);
+    }
+
+    void prepareWebViewInSystemServer() {
+        updateFallbackStateOnBoot();
+        mWebViewUpdater.prepareWebViewInSystemServer();
+    }
+
+    private boolean existsValidNonFallbackProvider(WebViewProviderInfo[] providers) {
+        for (WebViewProviderInfo provider : providers) {
+            if (provider.availableByDefault && !provider.isFallback) {
+                try {
+                    PackageInfo packageInfo = mSystemInterface.getPackageInfoForProvider(provider);
+                    if (isEnabledPackage(packageInfo)
+                            && mWebViewUpdater.isValidProvider(provider, packageInfo)) {
+                        return true;
+                    }
+                } catch (NameNotFoundException e) {
+                    // A non-existent provider is neither valid nor enabled
+                }
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Called when a new user has been added to update the state of its fallback package.
+     */
+    void handleNewUser(int userId) {
+        if (!mSystemInterface.isFallbackLogicEnabled()) return;
+
+        WebViewProviderInfo[] webviewProviders = mSystemInterface.getWebViewPackages();
+        WebViewProviderInfo fallbackProvider = getFallbackProvider(webviewProviders);
+        if (fallbackProvider == null) return;
+
+        mSystemInterface.enablePackageForUser(fallbackProvider.packageName,
+                !existsValidNonFallbackProvider(webviewProviders), userId);
+    }
+
+    void notifyRelroCreationCompleted() {
+        mWebViewUpdater.notifyRelroCreationCompleted();
+    }
+
+    WebViewProviderResponse waitForAndGetProvider() {
+        return mWebViewUpdater.waitForAndGetProvider();
+    }
+
+    String changeProviderAndSetting(String newProvider) {
+        return mWebViewUpdater.changeProviderAndSetting(newProvider);
+    }
+
+    WebViewProviderInfo[] getValidWebViewPackages() {
+        return mWebViewUpdater.getValidWebViewPackages();
+    }
+
+    WebViewProviderInfo[] getWebViewPackages() {
+        return mSystemInterface.getWebViewPackages();
+    }
+
+    String getCurrentWebViewPackageName() {
+        return mWebViewUpdater.getCurrentWebViewPackageName();
+    }
+
+    void enableFallbackLogic(boolean enable) {
+        mSystemInterface.enableFallbackLogic(enable);
+    }
+
+    private void updateFallbackStateOnBoot() {
+        if (!mSystemInterface.isFallbackLogicEnabled()) return;
+
+        WebViewProviderInfo[] webviewProviders = mSystemInterface.getWebViewPackages();
+        updateFallbackState(webviewProviders, true);
+    }
+
+    /**
+     * Handle the enabled-state of our fallback package, i.e. if there exists some non-fallback
+     * package that is valid (and available by default) then disable the fallback package,
+     * otherwise, enable the fallback package.
+     */
+    private void updateFallbackStateOnPackageChange(String changedPackage, int changedState) {
+        if (!mSystemInterface.isFallbackLogicEnabled()) return;
+
+        WebViewProviderInfo[] webviewProviders = mSystemInterface.getWebViewPackages();
+
+        // A package was changed / updated / downgraded, early out if it is not one of the
+        // webview packages that are available by default.
+        boolean changedPackageAvailableByDefault = false;
+        for (WebViewProviderInfo provider : webviewProviders) {
+            if (provider.packageName.equals(changedPackage)) {
+                if (provider.availableByDefault) {
+                    changedPackageAvailableByDefault = true;
+                }
+                break;
+            }
+        }
+        if (!changedPackageAvailableByDefault) return;
+        updateFallbackState(webviewProviders, false);
+    }
+
+    private void updateFallbackState(WebViewProviderInfo[] webviewProviders, boolean isBoot) {
+        // If there exists a valid and enabled non-fallback package - disable the fallback
+        // package, otherwise, enable it.
+        WebViewProviderInfo fallbackProvider = getFallbackProvider(webviewProviders);
+        if (fallbackProvider == null) return;
+        boolean existsValidNonFallbackProvider = existsValidNonFallbackProvider(webviewProviders);
+
+        boolean isFallbackEnabled = false;
+        try {
+            isFallbackEnabled = isEnabledPackage(
+                    mSystemInterface.getPackageInfoForProvider(fallbackProvider));
+        } catch (NameNotFoundException e) {
+            // No fallback package installed -> early out.
+            return;
+        }
+
+        if (existsValidNonFallbackProvider
+                // During an OTA the primary user's WebView state might differ from other users', so
+                // ignore the state of that user during boot.
+                && (isFallbackEnabled || isBoot)) {
+            mSystemInterface.uninstallAndDisablePackageForAllUsers(mContext,
+                    fallbackProvider.packageName);
+        } else if (!existsValidNonFallbackProvider
+                // During an OTA the primary user's WebView state might differ from other users', so
+                // ignore the state of that user during boot.
+                && (!isFallbackEnabled || isBoot)) {
+            // Enable the fallback package for all users.
+            mSystemInterface.enablePackageForAllUsers(mContext,
+                    fallbackProvider.packageName, true);
+        }
+    }
+
+    /**
+     * Returns the only fallback provider in the set of given packages, or null if there is none.
+     */
+    private static WebViewProviderInfo getFallbackProvider(WebViewProviderInfo[] webviewPackages) {
+        for (WebViewProviderInfo provider : webviewPackages) {
+            if (provider.isFallback) {
+                return provider;
+            }
+        }
+        return null;
+    }
+
+    boolean isFallbackPackage(String packageName) {
+        if (packageName == null || !mSystemInterface.isFallbackLogicEnabled()) return false;
+
+        WebViewProviderInfo[] webviewPackages = mSystemInterface.getWebViewPackages();
+        WebViewProviderInfo fallbackProvider = getFallbackProvider(webviewPackages);
+        return (fallbackProvider != null
+                && packageName.equals(fallbackProvider.packageName));
+    }
+
+    /**
+     * Class that decides what WebView implementation to use and prepares that implementation for
+     * use.
+     */
+    private static class WebViewUpdater {
+        private Context mContext;
+        private SystemInterface mSystemInterface;
+        private int mMinimumVersionCode = -1;
+
+        public WebViewUpdater(Context context, SystemInterface systemInterface) {
+            mContext = context;
+            mSystemInterface = systemInterface;
+        }
+
+        private static final int WAIT_TIMEOUT_MS = 4500; // KEY_DISPATCHING_TIMEOUT is 5000.
+
+        // Keeps track of the number of running relro creations
+        private int mNumRelroCreationsStarted = 0;
+        private int mNumRelroCreationsFinished = 0;
+        // Implies that we need to rerun relro creation because we are using an out-of-date package
+        private boolean mWebViewPackageDirty = false;
+        private boolean mAnyWebViewInstalled = false;
+
+        private int NUMBER_OF_RELROS_UNKNOWN = Integer.MAX_VALUE;
+
+        // The WebView package currently in use (or the one we are preparing).
+        private PackageInfo mCurrentWebViewPackage = null;
+
+        private Object mLock = new Object();
+
+        public void packageStateChanged(String packageName, int changedState) {
+            for (WebViewProviderInfo provider : mSystemInterface.getWebViewPackages()) {
+                String webviewPackage = provider.packageName;
+
+                if (webviewPackage.equals(packageName)) {
+                    boolean updateWebView = false;
+                    boolean removedOrChangedOldPackage = false;
+                    String oldProviderName = null;
+                    PackageInfo newPackage = null;
+                    synchronized(mLock) {
+                        try {
+                            newPackage = findPreferredWebViewPackage();
+                            if (mCurrentWebViewPackage != null)
+                                oldProviderName = mCurrentWebViewPackage.packageName;
+                            // Only trigger update actions if the updated package is the one
+                            // that will be used, or the one that was in use before the
+                            // update, or if we haven't seen a valid WebView package before.
+                            updateWebView =
+                                provider.packageName.equals(newPackage.packageName)
+                                || provider.packageName.equals(oldProviderName)
+                                || mCurrentWebViewPackage == null;
+                            // We removed the old package if we received an intent to remove
+                            // or replace the old package.
+                            removedOrChangedOldPackage =
+                                provider.packageName.equals(oldProviderName);
+                            if (updateWebView) {
+                                onWebViewProviderChanged(newPackage);
+                            }
+                        } catch (WebViewFactory.MissingWebViewPackageException e) {
+                            Slog.e(TAG, "Could not find valid WebView package to create " +
+                                    "relro with " + e);
+                        }
+                    }
+                    if(updateWebView && !removedOrChangedOldPackage
+                            && oldProviderName != null) {
+                        // If the provider change is the result of adding or replacing a
+                        // package that was not the previous provider then we must kill
+                        // packages dependent on the old package ourselves. The framework
+                        // only kills dependents of packages that are being removed.
+                        mSystemInterface.killPackageDependents(oldProviderName);
+                    }
+                    return;
+                }
+            }
+        }
+
+        public void prepareWebViewInSystemServer() {
+            try {
+                synchronized(mLock) {
+                    mCurrentWebViewPackage = findPreferredWebViewPackage();
+                    onWebViewProviderChanged(mCurrentWebViewPackage);
+                }
+            } catch (Throwable t) {
+                // Log and discard errors at this stage as we must not crash the system server.
+                Slog.e(TAG, "error preparing webview provider from system server", t);
+            }
+        }
+
+        /**
+         * Change WebView provider and provider setting and kill packages using the old provider.
+         * Return the new provider (in case we are in the middle of creating relro files this new
+         * provider will not be in use directly, but will when the relros are done).
+         */
+        public String changeProviderAndSetting(String newProviderName) {
+            PackageInfo oldPackage = null;
+            PackageInfo newPackage = null;
+            synchronized(mLock) {
+                oldPackage = mCurrentWebViewPackage;
+                mSystemInterface.updateUserSetting(mContext, newProviderName);
+
+                try {
+                    newPackage = findPreferredWebViewPackage();
+                    if (oldPackage != null
+                            && newPackage.packageName.equals(oldPackage.packageName)) {
+                        // If we don't perform the user change, revert the settings change.
+                        mSystemInterface.updateUserSetting(mContext, newPackage.packageName);
+                        return newPackage.packageName;
+                    }
+                } catch (WebViewFactory.MissingWebViewPackageException e) {
+                    Slog.e(TAG, "Tried to change WebView provider but failed to fetch WebView " +
+                            "package " + e);
+                    // If we don't perform the user change but don't have an installed WebView
+                    // package, we will have changed the setting and it will be used when a package
+                    // is available.
+                    return newProviderName;
+                }
+                onWebViewProviderChanged(newPackage);
+            }
+            // Kill apps using the old provider
+            if (oldPackage != null) {
+                mSystemInterface.killPackageDependents(oldPackage.packageName);
+            }
+            return newPackage.packageName;
+        }
+
+        /**
+         * This is called when we change WebView provider, either when the current provider is
+         * updated or a new provider is chosen / takes precedence.
+         */
+        private void onWebViewProviderChanged(PackageInfo newPackage) {
+            synchronized(mLock) {
+                mAnyWebViewInstalled = true;
+                if (mNumRelroCreationsStarted == mNumRelroCreationsFinished) {
+                    mCurrentWebViewPackage = newPackage;
+                    mSystemInterface.updateUserSetting(mContext, newPackage.packageName);
+
+                    // The relro creations might 'finish' (not start at all) before
+                    // WebViewFactory.onWebViewProviderChanged which means we might not know the
+                    // number of started creations before they finish.
+                    mNumRelroCreationsStarted = NUMBER_OF_RELROS_UNKNOWN;
+                    mNumRelroCreationsFinished = 0;
+                    mNumRelroCreationsStarted =
+                        mSystemInterface.onWebViewProviderChanged(newPackage);
+                    // If the relro creations finish before we know the number of started creations
+                    // we will have to do any cleanup/notifying here.
+                    checkIfRelrosDoneLocked();
+                } else {
+                    mWebViewPackageDirty = true;
+                }
+            }
+        }
+
+        private ProviderAndPackageInfo[] getValidWebViewPackagesAndInfos() {
+            WebViewProviderInfo[] allProviders = mSystemInterface.getWebViewPackages();
+            List<ProviderAndPackageInfo> providers = new ArrayList<>();
+            for(int n = 0; n < allProviders.length; n++) {
+                try {
+                    PackageInfo packageInfo =
+                        mSystemInterface.getPackageInfoForProvider(allProviders[n]);
+                    if (isValidProvider(allProviders[n], packageInfo)) {
+                        providers.add(new ProviderAndPackageInfo(allProviders[n], packageInfo));
+                    }
+                } catch (NameNotFoundException e) {
+                    // Don't add non-existent packages
+                }
+            }
+            return providers.toArray(new ProviderAndPackageInfo[providers.size()]);
+        }
+
+        /**
+         * Fetch only the currently valid WebView packages.
+         **/
+        public WebViewProviderInfo[] getValidWebViewPackages() {
+            ProviderAndPackageInfo[] providersAndPackageInfos = getValidWebViewPackagesAndInfos();
+            WebViewProviderInfo[] providers =
+                new WebViewProviderInfo[providersAndPackageInfos.length];
+            for(int n = 0; n < providersAndPackageInfos.length; n++) {
+                providers[n] = providersAndPackageInfos[n].provider;
+            }
+            return providers;
+        }
+
+
+        private class ProviderAndPackageInfo {
+            public final WebViewProviderInfo provider;
+            public final PackageInfo packageInfo;
+
+            public ProviderAndPackageInfo(WebViewProviderInfo provider, PackageInfo packageInfo) {
+                this.provider = provider;
+                this.packageInfo = packageInfo;
+            }
+        }
+
+        /**
+         * Returns either the package info of the WebView provider determined in the following way:
+         * If the user has chosen a provider then use that if it is valid,
+         * otherwise use the first package in the webview priority list that is valid.
+         *
+         */
+        private PackageInfo findPreferredWebViewPackage() {
+            ProviderAndPackageInfo[] providers = getValidWebViewPackagesAndInfos();
+
+            String userChosenProvider = mSystemInterface.getUserChosenWebViewProvider(mContext);
+
+            // If the user has chosen provider, use that
+            for (ProviderAndPackageInfo providerAndPackage : providers) {
+                if (providerAndPackage.provider.packageName.equals(userChosenProvider)
+                        && isEnabledPackage(providerAndPackage.packageInfo)) {
+                    return providerAndPackage.packageInfo;
+                }
+            }
+
+            // User did not choose, or the choice failed; use the most stable provider that is
+            // enabled and available by default (not through user choice).
+            for (ProviderAndPackageInfo providerAndPackage : providers) {
+                if (providerAndPackage.provider.availableByDefault
+                        && isEnabledPackage(providerAndPackage.packageInfo)) {
+                    return providerAndPackage.packageInfo;
+                }
+            }
+
+            // Could not find any enabled package either, use the most stable provider.
+            for (ProviderAndPackageInfo providerAndPackage : providers) {
+                return providerAndPackage.packageInfo;
+            }
+
+            mAnyWebViewInstalled = false;
+            throw new WebViewFactory.MissingWebViewPackageException(
+                    "Could not find a loadable WebView package");
+        }
+
+        public void notifyRelroCreationCompleted() {
+            synchronized (mLock) {
+                mNumRelroCreationsFinished++;
+                checkIfRelrosDoneLocked();
+            }
+        }
+
+        public WebViewProviderResponse waitForAndGetProvider() {
+            PackageInfo webViewPackage = null;
+            final long NS_PER_MS = 1000000;
+            final long timeoutTimeMs = System.nanoTime() / NS_PER_MS + WAIT_TIMEOUT_MS;
+            boolean webViewReady = false;
+            int webViewStatus = WebViewFactory.LIBLOAD_SUCCESS;
+            synchronized (mLock) {
+                webViewReady = webViewIsReadyLocked();
+                while (!webViewReady) {
+                    final long timeNowMs = System.nanoTime() / NS_PER_MS;
+                    if (timeNowMs >= timeoutTimeMs) break;
+                    try {
+                        mLock.wait(timeoutTimeMs - timeNowMs);
+                    } catch (InterruptedException e) {}
+                    webViewReady = webViewIsReadyLocked();
+                }
+                // Make sure we return the provider that was used to create the relro file
+                webViewPackage = mCurrentWebViewPackage;
+                if (webViewReady) {
+                } else if (!mAnyWebViewInstalled) {
+                    webViewStatus = WebViewFactory.LIBLOAD_FAILED_LISTING_WEBVIEW_PACKAGES;
+                } else {
+                    // Either the current relro creation  isn't done yet, or the new relro creatioin
+                    // hasn't kicked off yet (the last relro creation used an out-of-date WebView).
+                    webViewStatus = WebViewFactory.LIBLOAD_FAILED_WAITING_FOR_RELRO;
+                }
+            }
+            if (!webViewReady) Slog.w(TAG, "creating relro file timed out");
+            return new WebViewProviderResponse(webViewPackage, webViewStatus);
+        }
+
+        public String getCurrentWebViewPackageName() {
+            synchronized(mLock) {
+                if (mCurrentWebViewPackage == null)
+                    return null;
+                return mCurrentWebViewPackage.packageName;
+            }
+        }
+
+        /**
+         * Returns whether WebView is ready and is not going to go through its preparation phase
+         * again directly.
+         */
+        private boolean webViewIsReadyLocked() {
+            return !mWebViewPackageDirty
+                && (mNumRelroCreationsStarted == mNumRelroCreationsFinished)
+                // The current package might be replaced though we haven't received an intent
+                // declaring this yet, the following flag makes anyone loading WebView to wait in
+                // this case.
+                && mAnyWebViewInstalled;
+        }
+
+        private void checkIfRelrosDoneLocked() {
+            if (mNumRelroCreationsStarted == mNumRelroCreationsFinished) {
+                if (mWebViewPackageDirty) {
+                    mWebViewPackageDirty = false;
+                    // If we have changed provider since we started the relro creation we need to
+                    // redo the whole process using the new package instead.
+                    try {
+                        PackageInfo newPackage = findPreferredWebViewPackage();
+                        onWebViewProviderChanged(newPackage);
+                    } catch (WebViewFactory.MissingWebViewPackageException e) {
+                        // If we can't find any valid WebView package we are now in a state where
+                        // mAnyWebViewInstalled is false, so loading WebView will be blocked and we
+                        // should simply wait until we receive an intent declaring a new package was
+                        // installed.
+                    }
+                } else {
+                    mLock.notifyAll();
+                }
+            }
+        }
+
+        /**
+         * Returns whether this provider is valid for use as a WebView provider.
+         */
+        public boolean isValidProvider(WebViewProviderInfo configInfo,
+                PackageInfo packageInfo) {
+            if ((packageInfo.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) == 0
+                    && packageInfo.versionCode < getMinimumVersionCode()
+                    && !mSystemInterface.systemIsDebuggable()) {
+                // Non-system package webview providers may be downgraded arbitrarily low, prevent
+                // that by enforcing minimum version code. This check is only enforced for user
+                // builds.
+                return false;
+            }
+            if (providerHasValidSignature(configInfo, packageInfo, mSystemInterface) &&
+                    WebViewFactory.getWebViewLibrary(packageInfo.applicationInfo) != null) {
+                return true;
+            }
+            return false;
+        }
+
+        /**
+         * Gets the minimum version code allowed for a valid provider. It is the minimum versionCode
+         * of all available-by-default and non-fallback WebView provider packages. If there is no
+         * such WebView provider package on the system, then return -1, which means all positive
+         * versionCode WebView packages are accepted.
+         */
+        private int getMinimumVersionCode() {
+            if (mMinimumVersionCode > 0) {
+                return mMinimumVersionCode;
+            }
+
+            for (WebViewProviderInfo provider : mSystemInterface.getWebViewPackages()) {
+                if (provider.availableByDefault && !provider.isFallback) {
+                    try {
+                        int versionCode =
+                            mSystemInterface.getFactoryPackageVersion(provider.packageName);
+                        if (mMinimumVersionCode < 0 || versionCode < mMinimumVersionCode) {
+                            mMinimumVersionCode = versionCode;
+                        }
+                    } catch (NameNotFoundException e) {
+                        // Safe to ignore.
+                    }
+                }
+            }
+
+            return mMinimumVersionCode;
+        }
+    }
+
+    private static boolean providerHasValidSignature(WebViewProviderInfo provider,
+            PackageInfo packageInfo, SystemInterface systemInterface) {
+        if (systemInterface.systemIsDebuggable()) {
+            return true;
+        }
+        Signature[] packageSignatures;
+        // If no signature is declared, instead check whether the package is included in the
+        // system.
+        if (provider.signatures == null || provider.signatures.length == 0) {
+            return packageInfo.applicationInfo.isSystemApp();
+        }
+        packageSignatures = packageInfo.signatures;
+        if (packageSignatures.length != 1)
+            return false;
+
+        final byte[] packageSignature = packageSignatures[0].toByteArray();
+        // Return whether the package signature matches any of the valid signatures
+        for (String signature : provider.signatures) {
+            final byte[] validSignature = Base64.decode(signature, Base64.DEFAULT);
+            if (Arrays.equals(packageSignature, validSignature))
+                return true;
+        }
+        return false;
+    }
+
+    /**
+     * Returns whether the given package is enabled.
+     * This state can be changed by the user from Settings->Apps
+     */
+    private static boolean isEnabledPackage(PackageInfo packageInfo) {
+        return packageInfo.applicationInfo.enabled;
+    }
+
+}
diff --git a/services/core/java/com/android/server/wm/AccessibilityController.java b/services/core/java/com/android/server/wm/AccessibilityController.java
index bae628a..3ef077b 100644
--- a/services/core/java/com/android/server/wm/AccessibilityController.java
+++ b/services/core/java/com/android/server/wm/AccessibilityController.java
@@ -1214,7 +1214,10 @@
             window.type = windowState.mAttrs.type;
             window.layer = windowState.mLayer;
             window.token = windowState.mClient.asBinder();
-            window.title = windowState.mAttrs.getTitle();
+            window.title = windowState.mAttrs.accessibilityTitle;
+            if (window.title == null) {
+                window.title = windowState.mAttrs.getTitle();
+            }
             window.accessibilityIdOfAnchor = windowState.mAttrs.accessibilityIdOfAnchor;
 
             WindowState attachedWindow = windowState.mAttachedWindow;
diff --git a/services/core/java/com/android/server/wm/Task.java b/services/core/java/com/android/server/wm/Task.java
index 8a9ace7..7b16dbe 100644
--- a/services/core/java/com/android/server/wm/Task.java
+++ b/services/core/java/com/android/server/wm/Task.java
@@ -16,24 +16,17 @@
 
 package com.android.server.wm;
 
+import static android.app.ActivityManager.RESIZE_MODE_SYSTEM_SCREEN_ROTATION;
 import static android.app.ActivityManager.StackId.DOCKED_STACK_ID;
 import static android.app.ActivityManager.StackId.FREEFORM_WORKSPACE_STACK_ID;
 import static android.app.ActivityManager.StackId.HOME_STACK_ID;
-import static android.content.pm.ActivityInfo.RESIZE_MODE_FORCE_RESIZEABLE;
-import static android.content.pm.ActivityInfo.RESIZE_MODE_UNRESIZEABLE;
-import static android.content.res.Configuration.ORIENTATION_LANDSCAPE;
-import static android.app.ActivityManager.RESIZE_MODE_SYSTEM_SCREEN_ROTATION;
 import static android.content.pm.ActivityInfo.RESIZE_MODE_CROP_WINDOWS;
-import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
-import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
+import static android.content.res.Configuration.ORIENTATION_LANDSCAPE;
 import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_RESIZE;
 import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_STACK;
+import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
+import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
 import static com.android.server.wm.WindowManagerService.H.RESIZE_TASK;
-import static com.android.server.wm.WindowManagerService.H.SHOW_NON_RESIZEABLE_DOCK_TOAST;
-import static android.view.WindowManager.DOCKED_INVALID;
-import static android.view.WindowManager.DOCKED_LEFT;
-import static android.view.WindowManager.DOCKED_RIGHT;
-import static android.view.WindowManager.DOCKED_TOP;
 
 import android.app.ActivityManager.StackId;
 import android.content.pm.ActivityInfo;
@@ -44,7 +37,6 @@
 import android.view.DisplayInfo;
 import android.view.Surface;
 
-import com.android.internal.R;
 import com.android.server.EventLogTags;
 
 import java.io.PrintWriter;
@@ -94,11 +86,6 @@
     // Resize mode of the task. See {@link ActivityInfo#resizeMode}
     private int mResizeMode;
 
-    // Whether we need to show toast about the app being non-resizeable when it becomes visible.
-    // This flag is set when a non-resizeable task is docked (or side-by-side). It's cleared
-    // after we show the toast.
-    private boolean mShowNonResizeableDockToast;
-
     // Whether the task is currently being drag-resized
     private boolean mDragResizing;
     private int mDragResizeMode;
@@ -118,30 +105,6 @@
         return mStack.getDisplayContent();
     }
 
-    void setShowNonResizeableDockToast() {
-        mShowNonResizeableDockToast = true;
-    }
-
-    void scheduleShowNonResizeableDockToastIfNeeded() {
-        if (!mShowNonResizeableDockToast) {
-            return;
-        }
-        final DisplayContent displayContent = mStack.getDisplayContent();
-        // If docked stack is not yet visible, we don't want to show the toast yet,
-        // since we need the visible rect of the docked task to position the toast.
-        if (displayContent == null || displayContent.getDockedStackLocked() == null) {
-            return;
-        }
-
-        mShowNonResizeableDockToast = false;
-
-        if (mResizeMode == RESIZE_MODE_UNRESIZEABLE) {
-            final String text =
-                    mService.mContext.getString(R.string.dock_non_resizeble_failed_to_dock_text);
-            mService.mH.obtainMessage(SHOW_NON_RESIZEABLE_DOCK_TOAST, 0, 0, text).sendToTarget();
-        }
-    }
-
     void addAppToken(int addPos, AppWindowToken wtoken, int resizeMode, boolean homeTask) {
         final int lastPos = mAppTokens.size();
         if (addPos >= lastPos) {
diff --git a/services/core/java/com/android/server/wm/TaskStack.java b/services/core/java/com/android/server/wm/TaskStack.java
index 3430ac9..1475686 100644
--- a/services/core/java/com/android/server/wm/TaskStack.java
+++ b/services/core/java/com/android/server/wm/TaskStack.java
@@ -720,9 +720,9 @@
                 }
             } else {
                 if (splitHorizontally) {
-                    outBounds.left = position - dockDividerWidth;
+                    outBounds.left = position + dockDividerWidth;
                 } else {
-                    outBounds.top = position - dockDividerWidth;
+                    outBounds.top = position + dockDividerWidth;
                 }
             }
             return;
@@ -910,7 +910,7 @@
         // Calculate the content bounds excluding the area occupied by IME
         getDisplayContent().getContentRect(displayContentRect);
         contentBounds.set(displayContentRect);
-        int imeTop = Math.max(imeWin.getDisplayFrameLw().top, contentBounds.top);
+        int imeTop = Math.max(imeWin.getFrameLw().top, contentBounds.top);
 
         // if IME window is animating, get its actual vertical shown position (but no smaller than
         // the final target vertical position)
diff --git a/services/core/java/com/android/server/wm/WindowAnimator.java b/services/core/java/com/android/server/wm/WindowAnimator.java
index eae7838..6bc633f 100644
--- a/services/core/java/com/android/server/wm/WindowAnimator.java
+++ b/services/core/java/com/android/server/wm/WindowAnimator.java
@@ -670,7 +670,6 @@
         if (SHOW_TRANSACTIONS) Slog.i(
                 TAG, ">>> OPEN TRANSACTION animateLocked");
         SurfaceControl.openTransaction();
-        SurfaceControl.setAnimationTransaction();
         try {
             final int numDisplays = mDisplayContentsAnimators.size();
             for (int i = 0; i < numDisplays; i++) {
diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java
index 2af324d..57f38d1 100644
--- a/services/core/java/com/android/server/wm/WindowManagerService.java
+++ b/services/core/java/com/android/server/wm/WindowManagerService.java
@@ -4193,6 +4193,7 @@
                                     WindowManagerPolicy.TRANSIT_EXIT);
                         }
                     }
+                    win.mAnimatingExit = true;
                     changed = true;
                     win.setDisplayLayoutNeeded();
                 }
@@ -4940,17 +4941,6 @@
         }
     }
 
-    public void scheduleShowNonResizeableDockToast(int taskId) {
-        synchronized (mWindowMap) {
-            Task task = mTaskIdToTask.get(taskId);
-            if (task == null) {
-                if (DEBUG_STACK) Slog.i(TAG_WM, "scheduleShowToast: could not find taskId=" + taskId);
-                return;
-            }
-            task.setShowNonResizeableDockToast();
-        }
-    }
-
     @Override
     public void getStackBounds(int stackId, Rect bounds) {
         synchronized (mWindowMap) {
@@ -6035,7 +6025,6 @@
             minLayer = Integer.MAX_VALUE;
         }
 
-        int retryCount = 0;
         WindowState appWin = null;
 
         boolean appIsImTarget;
@@ -6049,193 +6038,172 @@
         final int aboveAppLayer = (mPolicy.windowTypeToLayerLw(TYPE_APPLICATION) + 1)
                 * TYPE_LAYER_MULTIPLIER + TYPE_LAYER_OFFSET;
 
-        while (true) {
-            if (retryCount++ > 0) {
-                // Reset max/min layers on retries so we don't accidentally take a screenshot of a
-                // layer based on the previous try.
-                maxLayer = 0;
-                minLayer = Integer.MAX_VALUE;
-                try {
-                    Thread.sleep(100);
-                } catch (InterruptedException e) {
-                }
-            }
-            synchronized(mWindowMap) {
-                // Figure out the part of the screen that is actually the app.
-                appWin = null;
-                final WindowList windows = displayContent.getWindowList();
-                for (int i = windows.size() - 1; i >= 0; i--) {
-                    WindowState ws = windows.get(i);
-                    if (!ws.mHasSurface) {
-                        continue;
-                    }
-                    if (ws.mLayer >= aboveAppLayer) {
-                        continue;
-                    }
-                    if (ws.mIsImWindow) {
-                        if (!appIsImTarget) {
-                            continue;
-                        }
-                    } else if (ws.mIsWallpaper) {
-                        if (appWin == null) {
-                            // We have not ran across the target window yet, so it is probably
-                            // behind the wallpaper. This can happen when the keyguard is up and
-                            // all windows are moved behind the wallpaper. We don't want to
-                            // include the wallpaper layer in the screenshot as it will coverup
-                            // the layer of the target window.
-                            continue;
-                        }
-                        // Fall through. The target window is in front of the wallpaper. For this
-                        // case we want to include the wallpaper layer in the screenshot because
-                        // the target window might have some transparent areas.
-                    } else if (appToken != null) {
-                        if (ws.mAppToken == null || ws.mAppToken.token != appToken) {
-                            // This app window is of no interest if it is not associated with the
-                            // screenshot app.
-                            continue;
-                        }
-                        appWin = ws;
-                    }
-
-                    // Include this window.
-
-                    final WindowStateAnimator winAnim = ws.mWinAnimator;
-                    int layer = winAnim.mSurfaceController.getLayer();
-                    if (maxLayer < layer) {
-                        maxLayer = layer;
-                    }
-                    if (minLayer > layer) {
-                        minLayer = layer;
-                    }
-
-                    // Don't include wallpaper in bounds calculation
-                    if (!includeFullDisplay && !ws.mIsWallpaper) {
-                        final Rect wf = ws.mFrame;
-                        final Rect cr = ws.mContentInsets;
-                        int left = wf.left + cr.left;
-                        int top = wf.top + cr.top;
-                        int right = wf.right - cr.right;
-                        int bottom = wf.bottom - cr.bottom;
-                        frame.union(left, top, right, bottom);
-                        ws.getVisibleBounds(stackBounds);
-                        if (!Rect.intersects(frame, stackBounds)) {
-                            // Set frame empty if there's no intersection.
-                            frame.setEmpty();
-                        }
-                    }
-
-                    if (ws.mAppToken != null && ws.mAppToken.token == appToken &&
-                            ws.isDisplayedLw() && winAnim.getShown()) {
-                        screenshotReady = true;
-                    }
-
-                    if (ws.isObscuringFullscreen(displayInfo)){
-                        break;
-                    }
-                }
-
-                if (appToken != null && appWin == null) {
-                    // Can't find a window to snapshot.
-                    if (DEBUG_SCREENSHOT) Slog.i(TAG_WM,
-                            "Screenshot: Couldn't find a surface matching " + appToken);
-                    return null;
-                }
-
-                if (!screenshotReady) {
-                    if (retryCount > MAX_SCREENSHOT_RETRIES) {
-                        Slog.i(TAG_WM, "Screenshot max retries " + retryCount + " of " + appToken +
-                                " appWin=" + (appWin == null ? "null" : (appWin + " drawState=" +
-                                appWin.mWinAnimator.mDrawState)));
-                        return null;
-                    }
-
-                    // Delay and hope that window gets drawn.
-                    if (DEBUG_SCREENSHOT) Slog.i(TAG_WM, "Screenshot: No image ready for " + appToken
-                            + ", " + appWin + " drawState=" + appWin.mWinAnimator.mDrawState);
+        synchronized(mWindowMap) {
+            // Figure out the part of the screen that is actually the app.
+            appWin = null;
+            final WindowList windows = displayContent.getWindowList();
+            for (int i = windows.size() - 1; i >= 0; i--) {
+                WindowState ws = windows.get(i);
+                if (!ws.mHasSurface) {
                     continue;
                 }
-
-                // Screenshot is ready to be taken. Everything from here below will continue
-                // through the bottom of the loop and return a value. We only stay in the loop
-                // because we don't want to release the mWindowMap lock until the screenshot is
-                // taken.
-
-                if (maxLayer == 0) {
-                    if (DEBUG_SCREENSHOT) Slog.i(TAG_WM, "Screenshot of " + appToken
-                            + ": returning null maxLayer=" + maxLayer);
-                    return null;
+                if (ws.mLayer >= aboveAppLayer) {
+                    continue;
+                }
+                if (ws.mIsImWindow) {
+                    if (!appIsImTarget) {
+                        continue;
+                    }
+                } else if (ws.mIsWallpaper) {
+                    if (appWin == null) {
+                        // We have not ran across the target window yet, so it is probably
+                        // behind the wallpaper. This can happen when the keyguard is up and
+                        // all windows are moved behind the wallpaper. We don't want to
+                        // include the wallpaper layer in the screenshot as it will coverup
+                        // the layer of the target window.
+                        continue;
+                    }
+                    // Fall through. The target window is in front of the wallpaper. For this
+                    // case we want to include the wallpaper layer in the screenshot because
+                    // the target window might have some transparent areas.
+                } else if (appToken != null) {
+                    if (ws.mAppToken == null || ws.mAppToken.token != appToken) {
+                        // This app window is of no interest if it is not associated with the
+                        // screenshot app.
+                        continue;
+                    }
+                    appWin = ws;
                 }
 
-                if (!includeFullDisplay) {
-                    // Constrain frame to the screen size.
-                    if (!frame.intersect(0, 0, dw, dh)) {
+                // Include this window.
+
+                final WindowStateAnimator winAnim = ws.mWinAnimator;
+                int layer = winAnim.mSurfaceController.getLayer();
+                if (maxLayer < layer) {
+                    maxLayer = layer;
+                }
+                if (minLayer > layer) {
+                    minLayer = layer;
+                }
+
+                // Don't include wallpaper in bounds calculation
+                if (!includeFullDisplay && !ws.mIsWallpaper) {
+                    final Rect wf = ws.mFrame;
+                    final Rect cr = ws.mContentInsets;
+                    int left = wf.left + cr.left;
+                    int top = wf.top + cr.top;
+                    int right = wf.right - cr.right;
+                    int bottom = wf.bottom - cr.bottom;
+                    frame.union(left, top, right, bottom);
+                    ws.getVisibleBounds(stackBounds);
+                    if (!Rect.intersects(frame, stackBounds)) {
+                        // Set frame empty if there's no intersection.
                         frame.setEmpty();
                     }
-                } else {
-                    // Caller just wants entire display.
-                    frame.set(0, 0, dw, dh);
-                }
-                if (frame.isEmpty()) {
-                    return null;
                 }
 
-                if (width < 0) {
-                    width = (int) (frame.width() * frameScale);
-                }
-                if (height < 0) {
-                    height = (int) (frame.height() * frameScale);
+                if (ws.mAppToken != null && ws.mAppToken.token == appToken &&
+                        ws.isDisplayedLw() && winAnim.getShown()) {
+                    screenshotReady = true;
                 }
 
-                // Tell surface flinger what part of the image to crop. Take the top
-                // right part of the application, and crop the larger dimension to fit.
-                Rect crop = new Rect(frame);
-                if (width / (float) frame.width() < height / (float) frame.height()) {
-                    int cropWidth = (int)((float)width / (float)height * frame.height());
-                    crop.right = crop.left + cropWidth;
-                } else {
-                    int cropHeight = (int)((float)height / (float)width * frame.width());
-                    crop.bottom = crop.top + cropHeight;
-                }
-
-                // The screenshot API does not apply the current screen rotation.
-                int rot = getDefaultDisplayContentLocked().getDisplay().getRotation();
-
-                if (rot == Surface.ROTATION_90 || rot == Surface.ROTATION_270) {
-                    rot = (rot == Surface.ROTATION_90) ? Surface.ROTATION_270 : Surface.ROTATION_90;
-                }
-
-                // Surfaceflinger is not aware of orientation, so convert our logical
-                // crop to surfaceflinger's portrait orientation.
-                convertCropForSurfaceFlinger(crop, rot, dw, dh);
-
-                if (DEBUG_SCREENSHOT) {
-                    Slog.i(TAG_WM, "Screenshot: " + dw + "x" + dh + " from " + minLayer + " to "
-                            + maxLayer + " appToken=" + appToken);
-                    for (int i = 0; i < windows.size(); i++) {
-                        WindowState win = windows.get(i);
-                        Slog.i(TAG_WM, win + ": " + win.mLayer
-                                + " animLayer=" + win.mWinAnimator.mAnimLayer
-                                + " surfaceLayer=" + win.mWinAnimator.mSurfaceController.getLayer());
-                    }
-                }
-
-                ScreenRotationAnimation screenRotationAnimation =
-                        mAnimator.getScreenRotationAnimationLocked(Display.DEFAULT_DISPLAY);
-                final boolean inRotation = screenRotationAnimation != null &&
-                        screenRotationAnimation.isAnimating();
-                if (DEBUG_SCREENSHOT && inRotation) Slog.v(TAG_WM,
-                        "Taking screenshot while rotating");
-
-                bm = SurfaceControl.screenshot(crop, width, height, minLayer, maxLayer,
-                        inRotation, rot);
-                if (bm == null) {
-                    Slog.w(TAG_WM, "Screenshot failure taking screenshot for (" + dw + "x" + dh
-                            + ") to layer " + maxLayer);
-                    return null;
+                if (ws.isObscuringFullscreen(displayInfo)){
+                    break;
                 }
             }
 
-            break;
+            if (appToken != null && appWin == null) {
+                // Can't find a window to snapshot.
+                if (DEBUG_SCREENSHOT) Slog.i(TAG_WM,
+                        "Screenshot: Couldn't find a surface matching " + appToken);
+                return null;
+            }
+
+            if (!screenshotReady) {
+                Slog.i(TAG_WM, "Failed to capture screenshot of " + appToken +
+                        " appWin=" + (appWin == null ? "null" : (appWin + " drawState=" +
+                        appWin.mWinAnimator.mDrawState)));
+                return null;
+            }
+
+            // Screenshot is ready to be taken. Everything from here below will continue
+            // through the bottom of the loop and return a value. We only stay in the loop
+            // because we don't want to release the mWindowMap lock until the screenshot is
+            // taken.
+
+            if (maxLayer == 0) {
+                if (DEBUG_SCREENSHOT) Slog.i(TAG_WM, "Screenshot of " + appToken
+                        + ": returning null maxLayer=" + maxLayer);
+                return null;
+            }
+
+            if (!includeFullDisplay) {
+                // Constrain frame to the screen size.
+                if (!frame.intersect(0, 0, dw, dh)) {
+                    frame.setEmpty();
+                }
+            } else {
+                // Caller just wants entire display.
+                frame.set(0, 0, dw, dh);
+            }
+            if (frame.isEmpty()) {
+                return null;
+            }
+
+            if (width < 0) {
+                width = (int) (frame.width() * frameScale);
+            }
+            if (height < 0) {
+                height = (int) (frame.height() * frameScale);
+            }
+
+            // Tell surface flinger what part of the image to crop. Take the top
+            // right part of the application, and crop the larger dimension to fit.
+            Rect crop = new Rect(frame);
+            if (width / (float) frame.width() < height / (float) frame.height()) {
+                int cropWidth = (int)((float)width / (float)height * frame.height());
+                crop.right = crop.left + cropWidth;
+            } else {
+                int cropHeight = (int)((float)height / (float)width * frame.width());
+                crop.bottom = crop.top + cropHeight;
+            }
+
+            // The screenshot API does not apply the current screen rotation.
+            int rot = getDefaultDisplayContentLocked().getDisplay().getRotation();
+
+            if (rot == Surface.ROTATION_90 || rot == Surface.ROTATION_270) {
+                rot = (rot == Surface.ROTATION_90) ? Surface.ROTATION_270 : Surface.ROTATION_90;
+            }
+
+            // Surfaceflinger is not aware of orientation, so convert our logical
+            // crop to surfaceflinger's portrait orientation.
+            convertCropForSurfaceFlinger(crop, rot, dw, dh);
+
+            if (DEBUG_SCREENSHOT) {
+                Slog.i(TAG_WM, "Screenshot: " + dw + "x" + dh + " from " + minLayer + " to "
+                        + maxLayer + " appToken=" + appToken);
+                for (int i = 0; i < windows.size(); i++) {
+                    WindowState win = windows.get(i);
+                    Slog.i(TAG_WM, win + ": " + win.mLayer
+                            + " animLayer=" + win.mWinAnimator.mAnimLayer
+                            + " surfaceLayer=" + win.mWinAnimator.mSurfaceController.getLayer());
+                }
+            }
+
+            ScreenRotationAnimation screenRotationAnimation =
+                    mAnimator.getScreenRotationAnimationLocked(Display.DEFAULT_DISPLAY);
+            final boolean inRotation = screenRotationAnimation != null &&
+                    screenRotationAnimation.isAnimating();
+            if (DEBUG_SCREENSHOT && inRotation) Slog.v(TAG_WM,
+                    "Taking screenshot while rotating");
+
+            bm = SurfaceControl.screenshot(crop, width, height, minLayer, maxLayer,
+                    inRotation, rot);
+            if (bm == null) {
+                Slog.w(TAG_WM, "Screenshot failure taking screenshot for (" + dw + "x" + dh
+                        + ") to layer " + maxLayer);
+                return null;
+            }
         }
 
         if (DEBUG_SCREENSHOT) {
@@ -7635,7 +7603,8 @@
         mSafeMode = menuState > 0 || sState > 0 || dpadState > 0 || trackballState > 0
                 || volumeDownState > 0;
         try {
-            if (SystemProperties.getInt(ShutdownThread.REBOOT_SAFEMODE_PROPERTY, 0) != 0) {
+            if (SystemProperties.getInt(ShutdownThread.REBOOT_SAFEMODE_PROPERTY, 0) != 0
+                    || SystemProperties.getInt(ShutdownThread.RO_SAFEMODE_PROPERTY, 0) != 0) {
                 int auditSafeMode = SystemProperties.getInt(ShutdownThread.AUDIT_SAFEMODE_PROPERTY, 0);
 
                 if (auditSafeMode == 0) {
@@ -7659,6 +7628,7 @@
         if (mSafeMode) {
             Log.i(TAG_WM, "SAFE MODE ENABLED (menu=" + menuState + " s=" + sState
                     + " dpad=" + dpadState + " trackball=" + trackballState + ")");
+            SystemProperties.set(ShutdownThread.RO_SAFEMODE_PROPERTY, "1");
         } else {
             Log.i(TAG_WM, "SAFE MODE not enabled");
         }
@@ -7770,7 +7740,6 @@
         public static final int RESIZE_TASK = 43;
 
         public static final int TWO_FINGER_SCROLL_START = 44;
-        public static final int SHOW_NON_RESIZEABLE_DOCK_TOAST = 45;
 
         public static final int WINDOW_REPLACEMENT_TIMEOUT = 46;
 
@@ -8338,16 +8307,6 @@
                     }
                 }
                 break;
-                case SHOW_NON_RESIZEABLE_DOCK_TOAST: {
-                    final Toast toast = Toast.makeText(
-                            mContext, (String) msg.obj, Toast.LENGTH_SHORT);
-                    final int gravity = toast.getGravity();
-                    final int xOffset = toast.getXOffset() + msg.arg1;
-                    final int yOffset = toast.getYOffset() + msg.arg2;
-                    toast.setGravity(gravity, xOffset, yOffset);
-                    toast.show();
-                }
-                break;
                 case WINDOW_REPLACEMENT_TIMEOUT: {
                     final AppWindowToken token = (AppWindowToken) msg.obj;
                     synchronized (mWindowMap) {
diff --git a/services/core/java/com/android/server/wm/WindowState.java b/services/core/java/com/android/server/wm/WindowState.java
index de485de..c991130 100644
--- a/services/core/java/com/android/server/wm/WindowState.java
+++ b/services/core/java/com/android/server/wm/WindowState.java
@@ -642,13 +642,14 @@
      * Subtracts the insets calculated by intersecting {@param layoutFrame} with {@param insetFrame}
      * from {@param frame}. In other words, it applies the insets that would result if
      * {@param frame} would be shifted to {@param layoutFrame} and then applying the insets from
-     * {@param insetFrame}.
+     * {@param insetFrame}. Also it respects {@param displayFrame} in case window has minimum
+     * width/height applied and insets should be overridden.
      */
-    private void subtractInsets(Rect frame, Rect layoutFrame, Rect insetFrame) {
-        final int left = Math.max(0, insetFrame.left - layoutFrame.left);
-        final int top = Math.max(0, insetFrame.top - layoutFrame.top);
-        final int right = Math.max(0, layoutFrame.right - insetFrame.right);
-        final int bottom = Math.max(0, layoutFrame.bottom - insetFrame.bottom);
+    private void subtractInsets(Rect frame, Rect layoutFrame, Rect insetFrame, Rect displayFrame) {
+        final int left = Math.max(0, insetFrame.left - Math.max(layoutFrame.left, displayFrame.left));
+        final int top = Math.max(0, insetFrame.top - Math.max(layoutFrame.top, displayFrame.top));
+        final int right = Math.max(0, Math.min(layoutFrame.right, displayFrame.right) - insetFrame.right);
+        final int bottom = Math.max(0, Math.min(layoutFrame.bottom, displayFrame.bottom) - insetFrame.bottom);
         frame.inset(left, top, right, bottom);
     }
 
@@ -687,8 +688,7 @@
         // The offset from the layout containing frame to the actual containing frame.
         final int layoutXDiff;
         final int layoutYDiff;
-        if (mInsetFrame.isEmpty()  && (fullscreenTask
-                || layoutInParentFrame())) {
+        if (mInsetFrame.isEmpty() && (fullscreenTask || layoutInParentFrame())) {
             // We use the parent frame as the containing frame for fullscreen and child windows
             mContainingFrame.set(pf);
             mDisplayFrame.set(df);
@@ -733,10 +733,12 @@
             layoutXDiff = !mInsetFrame.isEmpty() ? mInsetFrame.left - mContainingFrame.left : 0;
             layoutYDiff = !mInsetFrame.isEmpty() ? mInsetFrame.top - mContainingFrame.top : 0;
             layoutContainingFrame = !mInsetFrame.isEmpty() ? mInsetFrame : mContainingFrame;
-            subtractInsets(mDisplayFrame, layoutContainingFrame, df);
+            mTmpRect.set(0, 0, mDisplayContent.getDisplayInfo().logicalWidth,
+                    mDisplayContent.getDisplayInfo().logicalHeight);
+            subtractInsets(mDisplayFrame, layoutContainingFrame, df, mTmpRect);
             if (!layoutInParentFrame()) {
-                subtractInsets(mContainingFrame, layoutContainingFrame, pf);
-                subtractInsets(mInsetFrame, layoutContainingFrame, pf);
+                subtractInsets(mContainingFrame, layoutContainingFrame, pf, mTmpRect);
+                subtractInsets(mInsetFrame, layoutContainingFrame, pf, mTmpRect);
             }
             layoutDisplayFrame = df;
             layoutDisplayFrame.intersect(layoutContainingFrame);
@@ -855,8 +857,8 @@
             getDisplayContent().getLogicalDisplayRect(mTmpRect);
             // Override right and/or bottom insets in case if the frame doesn't fit the screen in
             // non-fullscreen mode.
-            boolean overrideRightInset = !fullscreenTask && mFrame.right > mTmpRect.right;
-            boolean overrideBottomInset = !fullscreenTask && mFrame.bottom > mTmpRect.bottom;
+            boolean overrideRightInset = !fullscreenTask && layoutContainingFrame.right > mTmpRect.right;
+            boolean overrideBottomInset = !fullscreenTask && layoutContainingFrame.bottom > mTmpRect.bottom;
             mContentInsets.set(mContentFrame.left - layoutContainingFrame.left,
                     mContentFrame.top - layoutContainingFrame.top,
                     overrideRightInset ? mTmpRect.right - mContentFrame.right
@@ -2355,6 +2357,10 @@
         return mDragResizing;
     }
 
+    boolean isDockedResizing() {
+        return mDragResizing && getResizeMode() == DRAG_RESIZE_MODE_DOCKED_DIVIDER;
+    }
+
     void dump(PrintWriter pw, String prefix, boolean dumpAll) {
         final TaskStack stack = getStack();
         pw.print(prefix); pw.print("mDisplayId="); pw.print(getDisplayId());
@@ -2586,7 +2592,7 @@
         final int ph = containingFrame.height();
         final Task task = getTask();
         final boolean nonFullscreenTask = isInMultiWindowMode();
-        final boolean fitToDisplay = task != null && !task.isFloating() && !layoutInParentFrame();
+        final boolean fitToDisplay = task != null && !nonFullscreenTask && !layoutInParentFrame();
         float x, y;
         int w,h;
 
diff --git a/services/core/java/com/android/server/wm/WindowStateAnimator.java b/services/core/java/com/android/server/wm/WindowStateAnimator.java
index 34452ee..140f381 100644
--- a/services/core/java/com/android/server/wm/WindowStateAnimator.java
+++ b/services/core/java/com/android/server/wm/WindowStateAnimator.java
@@ -1125,13 +1125,21 @@
         final int top = w.mYOffset + w.mFrame.top;
 
         // Initialize the decor rect to the entire frame.
-        if (w.isDragResizing() && w.getResizeMode() == DRAG_RESIZE_MODE_DOCKED_DIVIDER) {
+        if (w.isDockedResizing() ||
+                (w.isChildWindow() && w.mAttachedWindow.isDockedResizing())) {
 
             // If we are resizing with the divider, the task bounds might be smaller than the
             // stack bounds. The system decor is used to clip to the task bounds, which we don't
             // want in this case in order to avoid holes.
+            //
+            // We take care to not shrink the width, for surfaces which are larger than
+            // the display region. Of course this area will not eventually be visible
+            // but if we truncate the width now, we will calculate incorrectly
+            // when adjusting to the stack bounds.
             final DisplayInfo displayInfo = w.getDisplayContent().getDisplayInfo();
-            mSystemDecorRect.set(0, 0, displayInfo.logicalWidth, displayInfo.logicalHeight);
+            mSystemDecorRect.set(0, 0,
+                    Math.max(width, displayInfo.logicalWidth),
+                    Math.max(height, displayInfo.logicalHeight));
         } else {
             mSystemDecorRect.set(0, 0, width, height);
         }
@@ -1280,7 +1288,7 @@
         }
 
         final WindowState winShowWhenLocked = (WindowState) mPolicy.getWinShowWhenLockedLw();
-        if (w == winShowWhenLocked) {
+        if (w == winShowWhenLocked && mPolicy.isKeyguardShowingOrOccluded()) {
             return;
         }
 
@@ -1483,11 +1491,6 @@
                 }
             }
             w.mToken.hasVisible = true;
-
-            final Task task = w.getTask();
-            if (task != null) {
-                task.scheduleShowNonResizeableDockToastIfNeeded();
-            }
         }
     }
 
diff --git a/services/core/jni/com_android_server_location_GnssLocationProvider.cpp b/services/core/jni/com_android_server_location_GnssLocationProvider.cpp
index ae05042..78b0844 100644
--- a/services/core/jni/com_android_server_location_GnssLocationProvider.cpp
+++ b/services/core/jni/com_android_server_location_GnssLocationProvider.cpp
@@ -1112,7 +1112,7 @@
     JavaObject object(env, "android/location/GnssClock");
     GpsClockFlags flags = clock->flags;
 
-    SET_IF(GNSS_CLOCK_HAS_LEAP_SECOND,
+    SET_IF(GPS_CLOCK_HAS_LEAP_SECOND,
            LeapSecond,
            static_cast<int32_t>(clock->leap_second));
 
@@ -1121,8 +1121,9 @@
     // old GPS_CLOCK types (active only in a limited number of older devices),
     // the GPS time information is handled as an always discontinuous HW clock,
     // with the GPS time information put into the full_bias_ns instead - so that
-    // time_ns + full_bias_ns = local estimate of GPS time (as remains true, in
-    // the new GnssClock struct.)
+    // time_ns - full_bias_ns = local estimate of GPS time. Additionally, the
+    // sign of full_bias_ns and bias_ns has flipped between GpsClock &
+    // GnssClock, so that is also handled below.
     switch (clock->type) {
       case GPS_CLOCK_TYPE_UNKNOWN:
         // Clock type unsupported.
@@ -1133,7 +1134,7 @@
         break;
       case GPS_CLOCK_TYPE_GPS_TIME:
         // GPS time, need to convert.
-        flags |= GNSS_CLOCK_HAS_FULL_BIAS;
+        flags |= GPS_CLOCK_HAS_FULL_BIAS;
         clock->full_bias_ns = clock->time_ns;
         clock->time_ns = 0;
         SET(HardwareClockDiscontinuityCount,
@@ -1142,16 +1143,20 @@
     }
 
     SET(TimeNanos, clock->time_ns);
-    SET_IF(GNSS_CLOCK_HAS_TIME_UNCERTAINTY,
+    SET_IF(GPS_CLOCK_HAS_TIME_UNCERTAINTY,
            TimeUncertaintyNanos,
            clock->time_uncertainty_ns);
-    SET_IF(GNSS_CLOCK_HAS_FULL_BIAS, FullBiasNanos, clock->full_bias_ns);
-    SET_IF(GNSS_CLOCK_HAS_BIAS, BiasNanos, clock->bias_ns);
-    SET_IF(GNSS_CLOCK_HAS_BIAS_UNCERTAINTY,
+
+    // Definition of sign for full_bias_ns & bias_ns has been changed since N,
+    // so flip signs here.
+    SET_IF(GPS_CLOCK_HAS_FULL_BIAS, FullBiasNanos, -(clock->full_bias_ns));
+    SET_IF(GPS_CLOCK_HAS_BIAS, BiasNanos, -(clock->bias_ns));
+
+    SET_IF(GPS_CLOCK_HAS_BIAS_UNCERTAINTY,
            BiasUncertaintyNanos,
            clock->bias_uncertainty_ns);
-    SET_IF(GNSS_CLOCK_HAS_DRIFT, DriftNanosPerSecond, clock->drift_nsps);
-    SET_IF(GNSS_CLOCK_HAS_DRIFT_UNCERTAINTY,
+    SET_IF(GPS_CLOCK_HAS_DRIFT, DriftNanosPerSecond, clock->drift_nsps);
+    SET_IF(GPS_CLOCK_HAS_DRIFT_UNCERTAINTY,
            DriftUncertaintyNanosPerSecond,
            clock->drift_uncertainty_nsps);
 
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
index fdea84b..d229633 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
@@ -21,8 +21,6 @@
 import static android.app.admin.DevicePolicyManager.WIPE_EXTERNAL_STORAGE;
 import static android.app.admin.DevicePolicyManager.WIPE_RESET_PROTECTION_DATA;
 import static android.content.pm.PackageManager.GET_UNINSTALLED_PACKAGES;
-import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_AWARE;
-import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE;
 
 import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW;
 import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT;
@@ -57,7 +55,6 @@
 import android.app.backup.IBackupManager;
 import android.content.BroadcastReceiver;
 import android.content.ComponentName;
-import android.content.ContentResolver;
 import android.content.Context;
 import android.content.Intent;
 import android.content.IntentFilter;
@@ -85,7 +82,6 @@
 import android.os.AsyncTask;
 import android.os.Binder;
 import android.os.Build;
-import android.os.Build.VERSION_CODES;
 import android.os.Bundle;
 import android.os.Environment;
 import android.os.FileUtils;
@@ -2065,10 +2061,9 @@
      */
     private void sendAdminCommandToSelfAndProfilesLocked(String action, int reqPolicy,
             int userHandle) {
-        List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
-        for (UserInfo ui : profiles) {
-            int id = ui.id;
-            sendAdminCommandLocked(action, reqPolicy, id);
+        int[] profileIds = mUserManager.getProfileIdsWithDisabled(userHandle);
+        for (int profileId : profileIds) {
+            sendAdminCommandLocked(action, reqPolicy, profileId);
         }
     }
 
@@ -3968,9 +3963,9 @@
         // moment so we set the screen off timeout regardless of whether it affects the parent user
         // or the profile challenge only.
         long timeMs = Long.MAX_VALUE;
-        List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
-        for (UserInfo userInfo : profiles) {
-            DevicePolicyData policy = getUserDataUnchecked(userInfo.id);
+        int[] profileIds = mUserManager.getProfileIdsWithDisabled(userHandle);
+        for (int profileId : profileIds) {
+            DevicePolicyData policy = getUserDataUnchecked(profileId);
             final int N = policy.mAdminList.size();
             for (int i = 0; i < N; i++) {
                 ActiveAdmin admin = policy.mAdminList.get(i);
@@ -6708,19 +6703,18 @@
             // If we have multiple profiles we return the intersection of the
             // permitted lists. This can happen in cases where we have a device
             // and profile owner.
-            List<UserInfo> profiles = mUserManager.getProfiles(userId);
-            final int PROFILES_SIZE = profiles.size();
-            for (int i = 0; i < PROFILES_SIZE; ++i) {
+            int[] profileIds = mUserManager.getProfileIdsWithDisabled(userId);
+            for (int profileId : profileIds) {
                 // Just loop though all admins, only device or profiles
                 // owners can have permitted lists set.
-                DevicePolicyData policy = getUserDataUnchecked(profiles.get(i).id);
+                DevicePolicyData policy = getUserDataUnchecked(profileId);
                 final int N = policy.mAdminList.size();
                 for (int j = 0; j < N; j++) {
                     ActiveAdmin admin = policy.mAdminList.get(j);
                     List<String> fromAdmin = admin.permittedAccessiblityServices;
                     if (fromAdmin != null) {
                         if (result == null) {
-                            result = new ArrayList<String>(fromAdmin);
+                            result = new ArrayList<>(fromAdmin);
                         } else {
                             result.retainAll(fromAdmin);
                         }
@@ -6888,12 +6882,11 @@
             // If we have multiple profiles we return the intersection of the
             // permitted lists. This can happen in cases where we have a device
             // and profile owner.
-            List<UserInfo> profiles = mUserManager.getProfiles(userId);
-            final int PROFILES_SIZE = profiles.size();
-            for (int i = 0; i < PROFILES_SIZE; ++i) {
+            int[] profileIds = mUserManager.getProfileIdsWithDisabled(userId);
+            for (int profileId : profileIds) {
                 // Just loop though all admins, only device or profiles
                 // owners can have permitted lists set.
-                DevicePolicyData policy = getUserDataUnchecked(profiles.get(i).id);
+                DevicePolicyData policy = getUserDataUnchecked(profileId);
                 final int N = policy.mAdminList.size();
                 for (int j = 0; j < N; j++) {
                     ActiveAdmin admin = policy.mAdminList.get(j);
@@ -8078,7 +8071,8 @@
                     }
                 }
             }
-            return null;
+            // We're not specifying the device admin because there isn't one.
+            return intent;
         }
     }
 
diff --git a/services/java/com/android/server/SystemServer.java b/services/java/com/android/server/SystemServer.java
index e7ae2b0..6f45508 100644
--- a/services/java/com/android/server/SystemServer.java
+++ b/services/java/com/android/server/SystemServer.java
@@ -823,7 +823,7 @@
                 mSystemServiceManager.startService(WIFI_P2P_SERVICE_CLASS);
                 mSystemServiceManager.startService(WIFI_SERVICE_CLASS);
                 mSystemServiceManager.startService(
-                            "com.android.server.wifi.WifiScanningService");
+                            "com.android.server.wifi.scanner.WifiScanningService");
 
                 if (!disableRtt) {
                     mSystemServiceManager.startService("com.android.server.wifi.RttService");
diff --git a/services/net/java/android/net/apf/ApfFilter.java b/services/net/java/android/net/apf/ApfFilter.java
index f430a30..6722332 100644
--- a/services/net/java/android/net/apf/ApfFilter.java
+++ b/services/net/java/android/net/apf/ApfFilter.java
@@ -252,15 +252,22 @@
         long mLastSeen;
 
         // For debugging only. Offsets into the packet where PIOs are.
-        private final ArrayList<Integer> mPrefixOptionOffsets;
+        private final ArrayList<Integer> mPrefixOptionOffsets = new ArrayList<>();
+
+        // For debugging only. Offsets into the packet where RDNSS options are.
+        private final ArrayList<Integer> mRdnssOptionOffsets = new ArrayList<>();
+
         // For debugging only. How many times this RA was seen.
         int seenCount = 0;
 
         // For debugging only. Returns the hex representation of the last matching packet.
         String getLastMatchingPacket() {
-            return HexDump.toHexString(mPacket.array(), 0, mPacket.capacity(), false /* lowercase */);
+            return HexDump.toHexString(mPacket.array(), 0, mPacket.capacity(),
+                    false /* lowercase */);
         }
 
+        // For debugging only. Returns the string representation of the IPv6 address starting at
+        // position pos in the packet.
         private String IPv6AddresstoString(int pos) {
             try {
                 byte[] array = mPacket.array();
@@ -295,19 +302,37 @@
             return s & 0xffffffff;
         }
 
+        private void prefixOptionToString(StringBuffer sb, int offset) {
+            String prefix = IPv6AddresstoString(offset + 16);
+            int length = uint8(mPacket.get(offset + 2));
+            long valid = mPacket.getInt(offset + 4);
+            long preferred = mPacket.getInt(offset + 8);
+            sb.append(String.format("%s/%d %ds/%ds ", prefix, length, valid, preferred));
+        }
+
+        private void rdnssOptionToString(StringBuffer sb, int offset) {
+            int optLen = uint8(mPacket.get(offset + 1)) * 8;
+            if (optLen < 24) return;  // Malformed or empty.
+            long lifetime = uint32(mPacket.getInt(offset + 4));
+            int numServers = (optLen - 8) / 16;
+            sb.append("DNS ").append(lifetime).append("s");
+            for (int server = 0; server < numServers; server++) {
+                sb.append(" ").append(IPv6AddresstoString(offset + 8 + 16 * server));
+            }
+        }
+
         public String toString() {
             try {
                 StringBuffer sb = new StringBuffer();
-                sb.append(String.format("RA %s -> %s %d ",
+                sb.append(String.format("RA %s -> %s %ds ",
                         IPv6AddresstoString(IPV6_SRC_ADDR_OFFSET),
                         IPv6AddresstoString(IPV6_DEST_ADDR_OFFSET),
                         uint16(mPacket.getShort(ICMP6_RA_ROUTER_LIFETIME_OFFSET))));
                 for (int i: mPrefixOptionOffsets) {
-                    String prefix = IPv6AddresstoString(i + 16);
-                    int length = uint8(mPacket.get(i + 2));
-                    long valid = mPacket.getInt(i + 4);
-                    long preferred = mPacket.getInt(i + 8);
-                    sb.append(String.format("%s/%d %d/%d ", prefix, length, valid, preferred));
+                    prefixOptionToString(sb, i);
+                }
+                for (int i: mRdnssOptionOffsets) {
+                    rdnssOptionToString(sb, i);
                 }
                 return sb.toString();
             } catch (BufferUnderflowException | IndexOutOfBoundsException e) {
@@ -352,8 +377,7 @@
                     ICMP6_RA_ROUTER_LIFETIME_OFFSET,
                     ICMP6_RA_ROUTER_LIFETIME_LEN);
 
-            // Parse ICMPv6 options
-            mPrefixOptionOffsets = new ArrayList<>();
+            // Ensures that the RA is not truncated.
             mPacket.position(ICMP6_RA_OPTION_OFFSET);
             while (mPacket.hasRemaining()) {
                 int optionType = ((int)mPacket.get(mPacket.position())) & 0xff;
@@ -372,8 +396,10 @@
                         break;
                     // These three options have the same lifetime offset and size, so process
                     // together:
-                    case ICMP6_ROUTE_INFO_OPTION_TYPE:
                     case ICMP6_RDNSS_OPTION_TYPE:
+                        mRdnssOptionOffsets.add(mPacket.position());
+                        // Fall through.
+                    case ICMP6_ROUTE_INFO_OPTION_TYPE:
                     case ICMP6_DNSSL_OPTION_TYPE:
                         // Parse lifetime
                         lastNonLifetimeStart = addNonLifetime(lastNonLifetimeStart,
@@ -520,6 +546,10 @@
     @GuardedBy("this")
     private byte[] mLastInstalledProgram;
 
+    // For debugging only. How many times the program was updated since we started.
+    @GuardedBy("this")
+    private int mNumProgramUpdates;
+
     /**
      * Generate filter code to process ARP packets. Execution of this code ends in either the
      * DROP_LABEL or PASS_LABEL and does not fall off the end.
@@ -724,6 +754,8 @@
         mLastTimeInstalledProgram = curTime();
         mLastInstalledProgramMinLifetime = programMinLifetime;
         mLastInstalledProgram = program;
+        mNumProgramUpdates++;
+
         if (VDBG) {
             hexDump("Installing filter: ", program, program.length);
         }
@@ -865,19 +897,20 @@
     }
 
     public synchronized void dump(IndentingPrintWriter pw) {
-        pw.println("APF caps: " + mApfCapabilities);
+        pw.println("Capabilities: " + mApfCapabilities);
         pw.println("Receive thread: " + (mReceiveThread != null ? "RUNNING" : "STOPPED"));
-        pw.println("Multicast filtering: " + mMulticastFilter);
+        pw.println("Multicast: " + (mMulticastFilter ? "DROP" : "ALLOW"));
         try {
-            pw.println("IPv4 address: " + InetAddress.getByAddress(mIPv4Address));
+            pw.println("IPv4 address: " + InetAddress.getByAddress(mIPv4Address).getHostAddress());
         } catch (UnknownHostException|NullPointerException e) {}
+
         if (mLastTimeInstalledProgram == 0) {
             pw.println("No program installed.");
             return;
         }
-
+        pw.println("Program updates: " + mNumProgramUpdates);
         pw.println(String.format(
-                "Last program length %d, installed %ds ago, lifetime %d",
+                "Last program length %d, installed %ds ago, lifetime %ds",
                 mLastInstalledProgram.length, curTime() - mLastTimeInstalledProgram,
                 mLastInstalledProgramMinLifetime));
 
@@ -896,6 +929,7 @@
             }
             pw.decreaseIndent();
         }
+        pw.decreaseIndent();
 
         if (DBG) {
             pw.println("Last program:");
@@ -903,7 +937,5 @@
             pw.println(HexDump.toHexString(mLastInstalledProgram, false /* lowercase */));
             pw.decreaseIndent();
         }
-
-        pw.decreaseIndent();
     }
 }
diff --git a/services/tests/servicestests/Android.mk b/services/tests/servicestests/Android.mk
index e6dd6a4..7ffdb35 100644
--- a/services/tests/servicestests/Android.mk
+++ b/services/tests/servicestests/Android.mk
@@ -19,7 +19,8 @@
     easymocklib \
     guava \
     android-support-test \
-    mockito-target
+    mockito-target \
+    ShortcutManagerTestUtils
 
 LOCAL_JAVA_LIBRARIES := android.test.runner
 
diff --git a/services/tests/servicestests/src/com/android/server/LockSettingsStorageTests.java b/services/tests/servicestests/src/com/android/server/LockSettingsStorageTests.java
index dae8447..7d28e39 100644
--- a/services/tests/servicestests/src/com/android/server/LockSettingsStorageTests.java
+++ b/services/tests/servicestests/src/com/android/server/LockSettingsStorageTests.java
@@ -87,6 +87,12 @@
                 return new File(mStorageDir,
                         super.getLockPasswordFilename(userId).replace('/', '-')).getAbsolutePath();
             }
+
+            @Override
+            String getChildProfileLockFile(int userId) {
+                return new File(mStorageDir,
+                        super.getChildProfileLockFile(userId).replace('/', '-')).getAbsolutePath();
+            }
         };
     }
 
@@ -235,6 +241,27 @@
         assertArrayEquals("profilepassword".getBytes(), mStorage.readPasswordHash(2).hash);
     }
 
+    public void testLockType_WriteProfileWritesParent() {
+        mStorage.writePasswordHash("parentpassword".getBytes(), 10);
+        mStorage.writePatternHash("12345678".getBytes(), 20);
+
+        assertEquals(2, mStorage.getStoredCredentialType(10));
+        assertEquals(1, mStorage.getStoredCredentialType(20));
+        mStorage.clearCache();
+        assertEquals(2, mStorage.getStoredCredentialType(10));
+        assertEquals(1, mStorage.getStoredCredentialType(20));
+    }
+
+    public void testProfileLock_ReadWriteChildProfileLock() {
+        assertFalse(mStorage.hasChildProfileLock(20));
+        mStorage.writeChildProfileLock(20, "profilepassword".getBytes());
+        assertArrayEquals("profilepassword".getBytes(), mStorage.readChildProfileLock(20));
+        assertTrue(mStorage.hasChildProfileLock(20));
+        mStorage.clearCache();
+        assertArrayEquals("profilepassword".getBytes(), mStorage.readChildProfileLock(20));
+        assertTrue(mStorage.hasChildProfileLock(20));
+    }
+
     public void testPassword_WriteParentWritesProfile() {
         mStorage.writePasswordHash("profilepassword".getBytes(), 2);
         mStorage.writePasswordHash("parentpasswordd".getBytes(), 1);
diff --git a/services/tests/servicestests/src/com/android/server/accounts/AccountManagerServiceTest.java b/services/tests/servicestests/src/com/android/server/accounts/AccountManagerServiceTest.java
index 5b4803b..4468857 100644
--- a/services/tests/servicestests/src/com/android/server/accounts/AccountManagerServiceTest.java
+++ b/services/tests/servicestests/src/com/android/server/accounts/AccountManagerServiceTest.java
@@ -16,23 +16,34 @@
 
 package com.android.server.accounts;
 
+import static org.mockito.Matchers.eq;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
 import android.accounts.Account;
 import android.accounts.AuthenticatorDescription;
+import android.app.AppOpsManager;
 import android.app.Notification;
+import android.content.BroadcastReceiver;
 import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
 import android.content.pm.PackageManager;
 import android.content.pm.RegisteredServicesCache.ServiceInfo;
 import android.content.pm.RegisteredServicesCacheListener;
+import android.content.pm.UserInfo;
+import android.database.DatabaseErrorHandler;
+import android.database.sqlite.SQLiteDatabase;
 import android.os.Bundle;
 import android.os.Handler;
 import android.os.UserHandle;
+import android.os.UserManager;
 import android.test.AndroidTestCase;
-import android.test.IsolatedContext;
-import android.test.RenamingDelegatingContext;
-import android.test.mock.MockContentResolver;
 import android.test.mock.MockContext;
 import android.test.mock.MockPackageManager;
+import android.util.Log;
 
+import java.io.File;
 import java.io.FileDescriptor;
 import java.io.PrintWriter;
 import java.util.ArrayList;
@@ -41,20 +52,28 @@
 import java.util.Comparator;
 
 public class AccountManagerServiceTest extends AndroidTestCase {
+    private static final String TAG = AccountManagerServiceTest.class.getSimpleName();
+
+    static final String PREN_DB = "pren.db";
+    static final String DE_DB = "de.db";
+    static final String CE_DB = "ce.db";
     private AccountManagerService mAms;
 
     @Override
     protected void setUp() throws Exception {
-        final String filenamePrefix = "test.";
-        MockContentResolver resolver = new MockContentResolver();
-        RenamingDelegatingContext targetContextWrapper = new RenamingDelegatingContext(
-                new MyMockContext(), // The context that most methods are delegated to
-                getContext(), // The context that file methods are delegated to
-                filenamePrefix);
-        Context context = new IsolatedContext(resolver, targetContextWrapper);
-        setContext(context);
+        Context realTestContext = getContext();
+        Context mockContext = new MyMockContext(realTestContext);
+        setContext(mockContext);
         mAms = new MyAccountManagerService(getContext(),
-                new MyMockPackageManager(), new MockAccountAuthenticatorCache());
+                new MyMockPackageManager(), new MockAccountAuthenticatorCache(), realTestContext);
+    }
+
+    @Override
+    protected void tearDown() throws Exception {
+        new File(mAms.getCeDatabaseName(UserHandle.USER_SYSTEM)).delete();
+        new File(mAms.getDeDatabaseName(UserHandle.USER_SYSTEM)).delete();
+        new File(mAms.getPreNDatabaseName(UserHandle.USER_SYSTEM)).delete();
+        super.tearDown();
     }
 
     public class AccountSorter implements Comparator<Account> {
@@ -69,6 +88,7 @@
     }
 
     public void testCheckAddAccount() throws Exception {
+        unlockUser(UserHandle.USER_SYSTEM);
         Account a11 = new Account("account1", "type1");
         Account a21 = new Account("account2", "type1");
         Account a31 = new Account("account3", "type1");
@@ -109,6 +129,7 @@
     }
 
     public void testPasswords() throws Exception {
+        unlockUser(UserHandle.USER_SYSTEM);
         Account a11 = new Account("account1", "type1");
         Account a12 = new Account("account1", "type2");
         mAms.addAccountExplicitly(a11, "p11", null);
@@ -124,6 +145,7 @@
     }
 
     public void testUserdata() throws Exception {
+        unlockUser(UserHandle.USER_SYSTEM);
         Account a11 = new Account("account1", "type1");
         Bundle u11 = new Bundle();
         u11.putString("a", "a_a11");
@@ -156,6 +178,7 @@
     }
 
     public void testAuthtokens() throws Exception {
+        unlockUser(UserHandle.USER_SYSTEM);
         Account a11 = new Account("account1", "type1");
         Account a12 = new Account("account1", "type2");
         mAms.addAccountExplicitly(a11, "p11", null);
@@ -188,15 +211,21 @@
         assertNull(mAms.peekAuthToken(a12, "att2"));
     }
 
+    private void unlockUser(int userId) {
+        Intent intent = new Intent();
+        intent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
+        mAms.onUserUnlocked(intent);
+    }
+
     static public class MockAccountAuthenticatorCache implements IAccountAuthenticatorCache {
         private ArrayList<ServiceInfo<AuthenticatorDescription>> mServices;
 
         public MockAccountAuthenticatorCache() {
-            mServices = new ArrayList<ServiceInfo<AuthenticatorDescription>>();
+            mServices = new ArrayList<>();
             AuthenticatorDescription d1 = new AuthenticatorDescription("type1", "p1", 0, 0, 0, 0);
             AuthenticatorDescription d2 = new AuthenticatorDescription("type2", "p2", 0, 0, 0, 0);
-            mServices.add(new ServiceInfo<AuthenticatorDescription>(d1, null, null));
-            mServices.add(new ServiceInfo<AuthenticatorDescription>(d2, null, null));
+            mServices.add(new ServiceInfo<>(d1, null, null));
+            mServices.add(new ServiceInfo<>(d2, null, null));
         }
 
         @Override
@@ -232,10 +261,68 @@
     }
 
     static public class MyMockContext extends MockContext {
+        private Context mTestContext;
+        private AppOpsManager mAppOpsManager;
+        private UserManager mUserManager;
+
+        public MyMockContext(Context testContext) {
+            this.mTestContext = testContext;
+            this.mAppOpsManager = mock(AppOpsManager.class);
+            this.mUserManager = mock(UserManager.class);
+            final UserInfo ui = new UserInfo(UserHandle.USER_SYSTEM, "user0", 0);
+            when(mUserManager.getUserInfo(eq(ui.id))).thenReturn(ui);
+        }
+
         @Override
         public int checkCallingOrSelfPermission(final String permission) {
             return PackageManager.PERMISSION_GRANTED;
         }
+
+        @Override
+        public Object getSystemService(String name) {
+            if (Context.APP_OPS_SERVICE.equals(name)) {
+                return mAppOpsManager;
+            } else if( Context.USER_SERVICE.equals(name)) {
+                return mUserManager;
+            }
+            return null;
+        }
+
+        @Override
+        public String getSystemServiceName(Class<?> serviceClass) {
+            if (AppOpsManager.class.equals(serviceClass)) {
+                return Context.APP_OPS_SERVICE;
+            }
+            return null;
+        }
+
+        @Override
+        public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) {
+            return null;
+        }
+
+        @Override
+        public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user,
+                IntentFilter filter, String broadcastPermission, Handler scheduler) {
+            return null;
+        }
+
+        @Override
+        public SQLiteDatabase openOrCreateDatabase(String file, int mode,
+                SQLiteDatabase.CursorFactory factory, DatabaseErrorHandler errorHandler) {
+            Log.i(TAG, "openOrCreateDatabase " + file + " mode " + mode);
+            return mTestContext.openOrCreateDatabase(file, mode, factory,errorHandler);
+        }
+
+        @Override
+        public void sendBroadcastAsUser(Intent intent, UserHandle user) {
+            Log.i(TAG, "sendBroadcastAsUser " + intent + " " + user);
+        }
+
+        @Override
+        public String getOpPackageName() {
+            return null;
+        }
     }
 
     static public class MyMockPackageManager extends MockPackageManager {
@@ -246,9 +333,11 @@
     }
 
     static public class MyAccountManagerService extends AccountManagerService {
+        private Context mRealTestContext;
         public MyAccountManagerService(Context context, PackageManager packageManager,
-                IAccountAuthenticatorCache authenticatorCache) {
+                IAccountAuthenticatorCache authenticatorCache, Context realTestContext) {
             super(context, packageManager, authenticatorCache);
+            this.mRealTestContext = realTestContext;
         }
 
         @Override
@@ -258,5 +347,20 @@
         @Override
         protected void cancelNotification(final int id, UserHandle user) {
         }
+
+        @Override
+        protected String getCeDatabaseName(int userId) {
+            return new File(mRealTestContext.getCacheDir(), CE_DB).getPath();
+        }
+
+        @Override
+        protected String getDeDatabaseName(int userId) {
+            return new File(mRealTestContext.getCacheDir(), DE_DB).getPath();
+        }
+
+        @Override
+        String getPreNDatabaseName(int userId) {
+            return new File(mRealTestContext.getCacheDir(), PREN_DB).getPath();
+        }
     }
 }
diff --git a/services/tests/servicestests/src/com/android/server/devicepolicy/DpmMockContext.java b/services/tests/servicestests/src/com/android/server/devicepolicy/DpmMockContext.java
index 60d7382..f6e35f5 100644
--- a/services/tests/servicestests/src/com/android/server/devicepolicy/DpmMockContext.java
+++ b/services/tests/servicestests/src/com/android/server/devicepolicy/DpmMockContext.java
@@ -39,7 +39,6 @@
 import android.os.UserHandle;
 import android.os.UserManager;
 import android.os.UserManagerInternal;
-import android.os.storage.StorageManager;
 import android.telephony.TelephonyManager;
 import android.test.mock.MockContentResolver;
 import android.test.mock.MockContext;
@@ -343,31 +342,25 @@
                     @Override
                     public List<UserInfo> answer(InvocationOnMock invocation) throws Throwable {
                         final int userId = (int) invocation.getArguments()[0];
-                        final ArrayList<UserInfo> ret = new ArrayList<UserInfo>();
-                        UserInfo parent = null;
-                        for (UserInfo ui : mUserInfos) {
-                            if (ui.id == userId) {
-                                parent = ui;
-                                break;
-                            }
-                        }
-                        if (parent == null) {
-                            return ret;
-                        }
-                        ret.add(parent);
-                        for (UserInfo ui : mUserInfos) {
-                            if (ui.id == userId) {
-                                continue;
-                            }
-                            if (ui.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID
-                                    && ui.profileGroupId == parent.profileGroupId) {
-                                ret.add(ui);
-                            }
-                        }
-                        return ret;
+                        return getProfiles(userId);
                     }
                 }
         );
+        when(userManager.getProfileIdsWithDisabled(anyInt())).thenAnswer(
+                new Answer<int[]>() {
+                    @Override
+                    public int[] answer(InvocationOnMock invocation) throws Throwable {
+                        final int userId = (int) invocation.getArguments()[0];
+                        List<UserInfo> profiles = getProfiles(userId);
+                        int[] results = new int[profiles.size()];
+                        for (int i = 0; i < results.length; i++) {
+                            results[i] = profiles.get(i).id;
+                        }
+                        return results;
+                    }
+                }
+        );
+
 
         // Create a data directory.
         final File dir = new File(dataDir, "user" + userId);
@@ -377,6 +370,31 @@
         return dir;
     }
 
+    private List<UserInfo> getProfiles(int userId) {
+        final ArrayList<UserInfo> ret = new ArrayList<UserInfo>();
+        UserInfo parent = null;
+        for (UserInfo ui : mUserInfos) {
+            if (ui.id == userId) {
+                parent = ui;
+                break;
+            }
+        }
+        if (parent == null) {
+            return ret;
+        }
+        ret.add(parent);
+        for (UserInfo ui : mUserInfos) {
+            if (ui.id == userId) {
+                continue;
+            }
+            if (ui.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID
+                    && ui.profileGroupId == parent.profileGroupId) {
+                ret.add(ui);
+            }
+        }
+        return ret;
+    }
+
     /**
      * Add multiple users at once.  They'll all have flag 0.
      */
diff --git a/services/tests/servicestests/src/com/android/server/net/NetworkStatsCollectionTest.java b/services/tests/servicestests/src/com/android/server/net/NetworkStatsCollectionTest.java
index 6026644..9f53c87 100644
--- a/services/tests/servicestests/src/com/android/server/net/NetworkStatsCollectionTest.java
+++ b/services/tests/servicestests/src/com/android/server/net/NetworkStatsCollectionTest.java
@@ -162,7 +162,7 @@
         final NetworkStats.Entry entry = new NetworkStats.Entry();
         final NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                TEST_IMSI, null, false));
+                TEST_IMSI, null, false, true));
 
         int myUid = Process.myUid();
         int otherUidInSameUser = Process.myUid() + 1;
diff --git a/services/tests/servicestests/src/com/android/server/net/NetworkStatsObserversTest.java b/services/tests/servicestests/src/com/android/server/net/NetworkStatsObserversTest.java
index 82c6b6d..cff5876 100644
--- a/services/tests/servicestests/src/com/android/server/net/NetworkStatsObserversTest.java
+++ b/services/tests/servicestests/src/com/android/server/net/NetworkStatsObserversTest.java
@@ -283,7 +283,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -315,7 +315,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -354,7 +354,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -393,13 +393,13 @@
         NetworkIdentitySet identSet1 = new NetworkIdentitySet();
         identSet1.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveIfaces.put(TEST_IFACE, identSet1);
 
         NetworkIdentitySet identSet2 = new NetworkIdentitySet();
         identSet2.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_2, null /* networkId */, false /* roaming */));
+                IMSI_2, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveIfaces.put(TEST_IFACE2, identSet2);
 
         // Baseline
@@ -441,7 +441,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveUidIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -481,7 +481,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveUidIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -521,7 +521,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveUidIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -561,7 +561,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveUidIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
@@ -601,7 +601,7 @@
         NetworkIdentitySet identSet = new NetworkIdentitySet();
         identSet.add(new NetworkIdentity(
                 TYPE_MOBILE, TelephonyManager.NETWORK_TYPE_UNKNOWN,
-                IMSI_1, null /* networkId */, false /* roaming */));
+                IMSI_1, null /* networkId */, false /* roaming */, true /* metered */));
         mActiveUidIfaces.put(TEST_IFACE, identSet);
 
         // Baseline
diff --git a/services/tests/servicestests/src/com/android/server/pm/ShortcutManagerTest.java b/services/tests/servicestests/src/com/android/server/pm/ShortcutManagerTest.java
index baa5d36..ce02a79 100644
--- a/services/tests/servicestests/src/com/android/server/pm/ShortcutManagerTest.java
+++ b/services/tests/servicestests/src/com/android/server/pm/ShortcutManagerTest.java
@@ -27,6 +27,7 @@
 import static org.mockito.Mockito.times;
 import static org.mockito.Mockito.verify;
 import static org.mockito.Mockito.when;
+import static com.android.server.pm.shortcutmanagertest.ShortcutManagerTestUtils.*;
 
 import android.annotation.NonNull;
 import android.annotation.Nullable;
@@ -172,6 +173,11 @@
         public String getPackageName() {
             return mInjectedClientPackage;
         }
+
+        @Override
+        public int getUserId() {
+            return getCallingUserId();
+        }
     }
 
     /** Context used in the service side */
@@ -190,6 +196,11 @@
         public void startActivityAsUser(@RequiresPermission Intent intent, @Nullable Bundle options,
                 UserHandle userId) {
         }
+
+        @Override
+        public int getUserId() {
+            return UserHandle.USER_SYSTEM;
+        }
     }
 
     /** ShortcutService with injection override methods. */
@@ -205,7 +216,8 @@
         String injectShortcutManagerConstants() {
             return ConfigConstants.KEY_RESET_INTERVAL_SEC + "=" + (INTERVAL / 1000) + ","
                     + ConfigConstants.KEY_MAX_SHORTCUTS + "=" + MAX_SHORTCUTS + ","
-                    + ConfigConstants.KEY_MAX_DAILY_UPDATES + "=" + MAX_DAILY_UPDATES + ","
+                    + ConfigConstants.KEY_MAX_UPDATES_PER_INTERVAL + "="
+                    + MAX_UPDATES_PER_INTERVAL + ","
                     + ConfigConstants.KEY_MAX_ICON_DIMENSION_DP + "=" + MAX_ICON_DIMENSION + ","
                     + ConfigConstants.KEY_MAX_ICON_DIMENSION_DP_LOWRAM + "="
                     + MAX_ICON_DIMENSION_LOWRAM + ","
@@ -454,7 +466,7 @@
 
     private static final int MAX_SHORTCUTS = 10;
 
-    private static final int MAX_DAILY_UPDATES = 3;
+    private static final int MAX_UPDATES_PER_INTERVAL = 3;
 
     private static final int MAX_ICON_DIMENSION = 128;
 
@@ -598,14 +610,6 @@
         addPackage(packageName, uid, version, packageName);
     }
 
-    private <T> List<T> list(T... array) {
-        return Arrays.asList(array);
-    }
-
-    private <T> Set<T> set(Set<T> in) {
-        return new ArraySet<T>(in);
-    }
-
     private Signature[] genSignatures(String... signatures) {
         final Signature[] sigs = new Signature[signatures.length];
         for (int i = 0; i < signatures.length; i++){
@@ -789,33 +793,6 @@
         runTestOnUiThread(() -> {});
     }
 
-    public static Bundle makeBundle(Object... keysAndValues) {
-        Preconditions.checkState((keysAndValues.length % 2) == 0);
-
-        if (keysAndValues.length == 0) {
-            return null;
-        }
-        final Bundle ret = new Bundle();
-
-        for (int i = keysAndValues.length - 2; i >= 0; i -= 2) {
-            final String key = keysAndValues[i].toString();
-            final Object value = keysAndValues[i + 1];
-
-            if (value == null) {
-                ret.putString(key, null);
-            } else if (value instanceof Integer) {
-                ret.putInt(key, (Integer) value);
-            } else if (value instanceof String) {
-                ret.putString(key, (String) value);
-            } else if (value instanceof Bundle) {
-                ret.putBundle(key, (Bundle) value);
-            } else {
-                fail("Type not supported yet: " + value.getClass().getName());
-            }
-        }
-        return ret;
-    }
-
     /**
      * Make a shortcut with an ID.
      */
@@ -913,20 +890,6 @@
         return new ComponentName(mClientContext, clazz);
     }
 
-    private <T> Set<T> makeSet(T... values) {
-        final HashSet<T> ret = new HashSet<>();
-        for (T s : values) {
-            ret.add(s);
-        }
-        return ret;
-    }
-
-    private static void resetAll(Collection<?> mocks) {
-        for (Object o : mocks) {
-            reset(o);
-        }
-    }
-
     @NonNull
     private ShortcutInfo findById(List<ShortcutInfo> list, String id) {
         for (ShortcutInfo s : list) {
@@ -947,59 +910,8 @@
         assertEquals(expectedNextResetTime, mService.getNextResetTimeLocked());
     }
 
-    @NonNull
-    private List<ShortcutInfo> assertShortcutIds(@NonNull List<ShortcutInfo> actualShortcuts,
-            String... expectedIds) {
-        final HashSet<String> expected = new HashSet<>(list(expectedIds));
-        final HashSet<String> actual = new HashSet<>();
-        for (ShortcutInfo s : actualShortcuts) {
-            actual.add(s.getId());
-        }
-
-        // Compare the sets.
-        assertEquals(expected, actual);
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllHaveIntents(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertNotNull("ID " + s.getId(), s.getIntent());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllNotHaveIntents(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertNull("ID " + s.getId(), s.getIntent());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllHaveTitle(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertNotNull("ID " + s.getId(), s.getTitle());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllNotHaveTitle(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertNull("ID " + s.getId(), s.getTitle());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllNotHaveIcon(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
+    public static List<ShortcutInfo> assertAllNotHaveIcon(
+            List<ShortcutInfo> actualShortcuts) {
         for (ShortcutInfo s : actualShortcuts) {
             assertNull("ID " + s.getId(), s.getIcon());
         }
@@ -1007,35 +919,6 @@
     }
 
     @NonNull
-    private List<ShortcutInfo> assertAllHaveIconResId(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertTrue("ID " + s.getId() + " not have icon res ID", s.hasIconResource());
-            assertFalse("ID " + s.getId() + " shouldn't have icon FD", s.hasIconFile());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllHaveIconFile(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertFalse("ID " + s.getId() + " shouldn't have icon res ID", s.hasIconResource());
-            assertTrue("ID " + s.getId() + " not have icon FD", s.hasIconFile());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllHaveIcon(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertTrue("ID " + s.getId() + " has no icon ", s.hasIconFile() || s.hasIconResource());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
     private List<ShortcutInfo> assertAllHaveFlags(@NonNull List<ShortcutInfo> actualShortcuts,
             int shortcutFlags) {
         for (ShortcutInfo s : actualShortcuts) {
@@ -1045,87 +928,6 @@
         return actualShortcuts;
     }
 
-    @NonNull
-    private List<ShortcutInfo> assertAllKeyFieldsOnly(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertTrue("ID " + s.getId(), s.hasKeyFieldsOnly());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllNotKeyFieldsOnly(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertFalse("ID " + s.getId(), s.hasKeyFieldsOnly());
-        }
-        return actualShortcuts;
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllDynamic(@NonNull List<ShortcutInfo> actualShortcuts) {
-        return assertAllHaveFlags(actualShortcuts, ShortcutInfo.FLAG_DYNAMIC);
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllPinned(@NonNull List<ShortcutInfo> actualShortcuts) {
-        return assertAllHaveFlags(actualShortcuts, ShortcutInfo.FLAG_PINNED);
-    }
-
-    @NonNull
-    private List<ShortcutInfo> assertAllDynamicOrPinned(
-            @NonNull List<ShortcutInfo> actualShortcuts) {
-        for (ShortcutInfo s : actualShortcuts) {
-            assertTrue("ID " + s.getId(), s.isDynamic() || s.isPinned());
-        }
-        return actualShortcuts;
-    }
-
-    private void assertDynamicOnly(ShortcutInfo si) {
-        assertTrue(si.isDynamic());
-        assertFalse(si.isPinned());
-    }
-
-    private void assertPinnedOnly(ShortcutInfo si) {
-        assertFalse(si.isDynamic());
-        assertTrue(si.isPinned());
-    }
-
-    private void assertDynamicAndPinned(ShortcutInfo si) {
-        assertTrue(si.isDynamic());
-        assertTrue(si.isPinned());
-    }
-
-    private void assertBitmapSize(int expectedWidth, int expectedHeight, @NonNull Bitmap bitmap) {
-        assertEquals("width", expectedWidth, bitmap.getWidth());
-        assertEquals("height", expectedHeight, bitmap.getHeight());
-    }
-
-    private <T> void assertAllUnique(Collection<T> list) {
-        final Set<Object> set = new HashSet<>();
-        for (T item : list) {
-            if (set.contains(item)) {
-                fail("Duplicate item found: " + item + " (in the list: " + list + ")");
-            }
-            set.add(item);
-        }
-    }
-
-    @NonNull
-    private Bitmap pfdToBitmap(@NonNull ParcelFileDescriptor pfd) {
-        Preconditions.checkNotNull(pfd);
-        try {
-            return BitmapFactory.decodeFileDescriptor(pfd.getFileDescriptor());
-        } finally {
-            IoUtils.closeQuietly(pfd);
-        }
-    }
-
-    private void assertBundleEmpty(BaseBundle b) {
-        assertTrue(b == null || b.size() == 0);
-    }
-
     private ShortcutInfo getPackageShortcut(String packageName, String shortcutId, int userId) {
         return mService.getPackageShortcutForTest(packageName, shortcutId, userId);
     }
@@ -1152,9 +954,25 @@
         return intentCaptor.getValue();
     }
 
+    private Intent launchShortcutAndGetIntent_withShortcutInfo(
+            @NonNull String packageName, @NonNull String shortcutId, int userId) {
+        reset(mServiceContext);
+
+        assertTrue(mLauncherApps.startShortcut(
+                getShortcutInfoAsLauncher(packageName, shortcutId, userId), null, null));
+
+        final ArgumentCaptor<Intent> intentCaptor = ArgumentCaptor.forClass(Intent.class);
+        verify(mServiceContext).startActivityAsUser(
+                intentCaptor.capture(),
+                any(Bundle.class),
+                eq(UserHandle.of(userId)));
+        return intentCaptor.getValue();
+    }
+
     private void assertShortcutLaunchable(@NonNull String packageName, @NonNull String shortcutId,
             int userId) {
         assertNotNull(launchShortcutAndGetIntent(packageName, shortcutId, userId));
+        assertNotNull(launchShortcutAndGetIntent_withShortcutInfo(packageName, shortcutId, userId));
     }
 
     private void assertShortcutNotLaunchable(@NonNull String packageName,
@@ -1193,6 +1011,14 @@
         return getLauncherShortcuts(launcher, userId, ShortcutQuery.FLAG_GET_PINNED);
     }
 
+    private ShortcutInfo getShortcutInfoAsLauncher(String packageName, String shortcutId,
+            int userId) {
+        final List<ShortcutInfo> infoList =
+                mLauncherApps.getShortcutInfo(packageName, list(shortcutId),
+                        UserHandle.of(userId));
+        assertEquals("No shortcutInfo found (or too many of them)", 1, infoList.size());
+        return infoList.get(0);
+    }
 
     private Intent genPackageDeleteIntent(String pakcageName, int userId) {
         Intent i = new Intent(Intent.ACTION_PACKAGE_REMOVED);
@@ -1249,7 +1075,7 @@
 
         assertResetTimes(START_TIME + INTERVAL, START_TIME + 2 * INTERVAL);
 
-        // Advance further; 4 days since start.
+        // Advance further; 4 hours since start.
         mInjectedCurrentTimeLillis = START_TIME + 4 * INTERVAL + 50;
 
         assertResetTimes(START_TIME + 4 * INTERVAL, START_TIME + 5 * INTERVAL);
@@ -1286,14 +1112,14 @@
         mService.updateConfigurationLocked(
                 ConfigConstants.KEY_RESET_INTERVAL_SEC + "=123,"
                         + ConfigConstants.KEY_MAX_SHORTCUTS + "=4,"
-                        + ConfigConstants.KEY_MAX_DAILY_UPDATES + "=5,"
+                        + ConfigConstants.KEY_MAX_UPDATES_PER_INTERVAL + "=5,"
                         + ConfigConstants.KEY_MAX_ICON_DIMENSION_DP + "=100,"
                         + ConfigConstants.KEY_MAX_ICON_DIMENSION_DP_LOWRAM + "=50,"
                         + ConfigConstants.KEY_ICON_FORMAT + "=WEBP,"
                         + ConfigConstants.KEY_ICON_QUALITY + "=75");
         assertEquals(123000, mService.getResetIntervalForTest());
         assertEquals(4, mService.getMaxDynamicShortcutsForTest());
-        assertEquals(5, mService.getMaxDailyUpdatesForTest());
+        assertEquals(5, mService.getMaxUpdatesPerIntervalForTest());
         assertEquals(100, mService.getMaxIconDimensionForTest());
         assertEquals(CompressFormat.WEBP, mService.getIconPersistFormatForTest());
         assertEquals(75, mService.getIconPersistQualityForTest());
@@ -1309,8 +1135,8 @@
         assertEquals(ShortcutService.DEFAULT_MAX_SHORTCUTS_PER_APP,
                 mService.getMaxDynamicShortcutsForTest());
 
-        assertEquals(ShortcutService.DEFAULT_MAX_DAILY_UPDATES,
-                mService.getMaxDailyUpdatesForTest());
+        assertEquals(ShortcutService.DEFAULT_MAX_UPDATES_PER_INTERVAL,
+                mService.getMaxUpdatesPerIntervalForTest());
 
         assertEquals(50, mService.getMaxIconDimensionForTest());
 
@@ -1329,7 +1155,7 @@
 
     /** Test for {@link android.content.pm.ShortcutManager#getRemainingCallCount()} */
     public void testGetRemainingCallCount() {
-        assertEquals(MAX_DAILY_UPDATES, mManager.getRemainingCallCount());
+        assertEquals(MAX_UPDATES_PER_INTERVAL, mManager.getRemainingCallCount());
     }
 
     /** Test for {@link android.content.pm.ShortcutManager#getRateLimitResetTime()} */
@@ -1416,61 +1242,71 @@
                 mManager.getDynamicShortcuts()),
                 "shortcut1");
 
-        assertTrue(mManager.addDynamicShortcut(si2));
+        assertTrue(mManager.addDynamicShortcuts(list(si2, si3)));
         assertEquals(1, mManager.getRemainingCallCount());
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
-                "shortcut1", "shortcut2");
+                "shortcut1", "shortcut2", "shortcut3");
 
-        // Add with the same ID
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("shortcut1")));
+        // This should not crash.  It'll still consume the quota.
+        assertTrue(mManager.addDynamicShortcuts(list()));
         assertEquals(0, mManager.getRemainingCallCount());
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
-                "shortcut1", "shortcut2");
+                "shortcut1", "shortcut2", "shortcut3");
+
+        mInjectedCurrentTimeLillis += INTERVAL; // reset
+
+        // Add with the same ID
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("shortcut1"))));
+        assertEquals(2, mManager.getRemainingCallCount());
+        assertShortcutIds(assertAllNotKeyFieldsOnly(
+                mManager.getDynamicShortcuts()),
+                "shortcut1", "shortcut2", "shortcut3");
 
         // TODO Check max number
 
         // TODO Check fields.
 
         runWithCaller(CALLING_PACKAGE_2, USER_10, () -> {
-            assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+            assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
         });
     }
 
-    public void testDeleteDynamicShortcut() {
+    public void testDeleteDynamicShortcuts() {
         final ShortcutInfo si1 = makeShortcut("shortcut1");
         final ShortcutInfo si2 = makeShortcut("shortcut2");
         final ShortcutInfo si3 = makeShortcut("shortcut3");
+        final ShortcutInfo si4 = makeShortcut("shortcut4");
 
-        assertTrue(mManager.setDynamicShortcuts(list(si1, si2, si3)));
+        assertTrue(mManager.setDynamicShortcuts(list(si1, si2, si3, si4)));
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
-                "shortcut1", "shortcut2", "shortcut3");
+                "shortcut1", "shortcut2", "shortcut3", "shortcut4");
 
         assertEquals(2, mManager.getRemainingCallCount());
 
-        mManager.deleteDynamicShortcut("shortcut1");
+        mManager.removeDynamicShortcuts(list("shortcut1"));
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
-                "shortcut2", "shortcut3");
+                "shortcut2", "shortcut3", "shortcut4");
 
-        mManager.deleteDynamicShortcut("shortcut1");
+        mManager.removeDynamicShortcuts(list("shortcut1"));
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
-                "shortcut2", "shortcut3");
+                "shortcut2", "shortcut3", "shortcut4");
 
-        mManager.deleteDynamicShortcut("shortcutXXX");
+        mManager.removeDynamicShortcuts(list("shortcutXXX"));
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
-                "shortcut2", "shortcut3");
+                "shortcut2", "shortcut3", "shortcut4");
 
-        mManager.deleteDynamicShortcut("shortcut2");
+        mManager.removeDynamicShortcuts(list("shortcut2", "shortcut4"));
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()),
                 "shortcut3");
 
-        mManager.deleteDynamicShortcut("shortcut3");
+        mManager.removeDynamicShortcuts(list("shortcut3"));
         assertShortcutIds(assertAllNotKeyFieldsOnly(
                 mManager.getDynamicShortcuts()));
 
@@ -1490,7 +1326,7 @@
 
         assertEquals(2, mManager.getRemainingCallCount());
 
-        mManager.deleteAllDynamicShortcuts();
+        mManager.removeAllDynamicShortcuts();
         assertEquals(0, mManager.getDynamicShortcuts().size());
         assertEquals(2, mManager.getRemainingCallCount());
 
@@ -1558,7 +1394,7 @@
         assertEquals(0, mManager.getRemainingCallCount());
         assertEquals(START_TIME + INTERVAL * 2, mManager.getRateLimitResetTime());
 
-        // 4 days later...
+        // 4 hours later...
         mInjectedCurrentTimeLillis = START_TIME + 4 * INTERVAL;
         assertTrue(mManager.setDynamicShortcuts(list(si1)));
         assertEquals(2, mManager.getRemainingCallCount());
@@ -1684,7 +1520,7 @@
         assertFalse(mManager.setDynamicShortcuts(list(si2)));
     }
 
-    public void testIcons() {
+    public void testIcons() throws IOException {
         final Icon res32x32 = Icon.createWithResource(getTestContext(), R.drawable.black_32x32);
         final Icon res64x64 = Icon.createWithResource(getTestContext(), R.drawable.black_64x64);
         final Icon res512x512 = Icon.createWithResource(getTestContext(), R.drawable.black_512x512);
@@ -1728,6 +1564,16 @@
                 "res64x64",
                 "none");
 
+        // Different profile.  Note the names and the contents don't match.
+        setCaller(CALLING_PACKAGE_1, USER_P0);
+        assertTrue(mManager.setDynamicShortcuts(list(
+                makeShortcutWithIcon("res32x32", res512x512),
+                makeShortcutWithIcon("bmp32x32", bmp512x512)
+        )));
+        assertShortcutIds(assertAllNotHaveIcon(mManager.getDynamicShortcuts()),
+                "res32x32",
+                "bmp32x32");
+
         // Re-initialize and load from the files.
         mService.saveDirtyInfo();
         initService();
@@ -1737,61 +1583,90 @@
 
         setCaller(LAUNCHER_1);
         // Check hasIconResource()/hasIconFile().
-        assertShortcutIds(assertAllHaveIconResId(mLauncherApps.getShortcutInfo(
-                CALLING_PACKAGE_1, list("res32x32"),
-                getCallingUser())), "res32x32");
+        assertShortcutIds(assertAllHaveIconResId(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "res32x32", USER_0))),
+                "res32x32");
 
-        assertShortcutIds(assertAllHaveIconResId(mLauncherApps.getShortcutInfo(
-                CALLING_PACKAGE_1, list("res64x64"), getCallingUser())),
+        assertShortcutIds(assertAllHaveIconResId(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "res64x64", USER_0))),
                 "res64x64");
 
-        assertShortcutIds(assertAllHaveIconFile(mLauncherApps.getShortcutInfo(
-                CALLING_PACKAGE_1, list("bmp32x32"), getCallingUser())),
+        assertShortcutIds(assertAllHaveIconFile(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp32x32", USER_0))),
                 "bmp32x32");
 
-        assertShortcutIds(assertAllHaveIconFile(mLauncherApps.getShortcutInfo(
-                CALLING_PACKAGE_1, list("bmp64x64"), getCallingUser())),
+        assertShortcutIds(assertAllHaveIconFile(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp64x64", USER_0))),
                 "bmp64x64");
 
-        assertShortcutIds(assertAllHaveIconFile(mLauncherApps.getShortcutInfo(
-                CALLING_PACKAGE_1, list("bmp512x512"), getCallingUser())),
+        assertShortcutIds(assertAllHaveIconFile(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp512x512", USER_0))),
                 "bmp512x512");
 
+        assertShortcutIds(assertAllHaveIconResId(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "res32x32", USER_P0))),
+                "res32x32");
+        assertShortcutIds(assertAllHaveIconFile(
+                list(getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp32x32", USER_P0))),
+                "bmp32x32");
+
         // Check
         assertEquals(
                 R.drawable.black_32x32,
                 mLauncherApps.getShortcutIconResId(
-                        makePackageShortcut(CALLING_PACKAGE_1, "res32x32"), getCallingUser()));
+                        getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "res32x32", USER_0)));
 
         assertEquals(
                 R.drawable.black_64x64,
                 mLauncherApps.getShortcutIconResId(
-
-                        makePackageShortcut(CALLING_PACKAGE_1, "res64x64"), getCallingUser()));
+                        getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "res64x64", USER_0)));
 
         assertEquals(
                 0, // because it's not a resource
                 mLauncherApps.getShortcutIconResId(
-                        makePackageShortcut(CALLING_PACKAGE_1, "bmp32x32"), getCallingUser()));
+                        getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp32x32", USER_0)));
         assertEquals(
                 0, // because it's not a resource
                 mLauncherApps.getShortcutIconResId(
-                        makePackageShortcut(CALLING_PACKAGE_1, "bmp64x64"), getCallingUser()));
+                        getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp64x64", USER_0)));
         assertEquals(
                 0, // because it's not a resource
                 mLauncherApps.getShortcutIconResId(
-                        makePackageShortcut(CALLING_PACKAGE_1, "bmp512x512"), getCallingUser()));
+                        getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp512x512", USER_0)));
 
         bmp = pfdToBitmap(mLauncherApps.getShortcutIconFd(
-                makePackageShortcut(CALLING_PACKAGE_1, "bmp32x32"), getCallingUser()));
+                getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp32x32", USER_0)));
         assertBitmapSize(32, 32, bmp);
 
         bmp = pfdToBitmap(mLauncherApps.getShortcutIconFd(
-                makePackageShortcut(CALLING_PACKAGE_1, "bmp64x64"), getCallingUser()));
+                getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp64x64", USER_0)));
         assertBitmapSize(64, 64, bmp);
 
         bmp = pfdToBitmap(mLauncherApps.getShortcutIconFd(
-                makePackageShortcut(CALLING_PACKAGE_1, "bmp512x512"), getCallingUser()));
+                getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp512x512", USER_0)));
+        assertBitmapSize(128, 128, bmp);
+
+        assertEquals(
+                R.drawable.black_512x512,
+                mLauncherApps.getShortcutIconResId(
+                        getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "res32x32", USER_P0)));
+        // Should be 512x512, so shrunk.
+        bmp = pfdToBitmap(mLauncherApps.getShortcutIconFd(
+                getShortcutInfoAsLauncher(CALLING_PACKAGE_1, "bmp32x32", USER_P0)));
+        assertBitmapSize(128, 128, bmp);
+
+        // Also check the overload APIs too.
+        assertEquals(
+                R.drawable.black_32x32,
+                mLauncherApps.getShortcutIconResId(CALLING_PACKAGE_1, "res32x32", HANDLE_USER_0));
+        assertEquals(
+                R.drawable.black_64x64,
+                mLauncherApps.getShortcutIconResId(CALLING_PACKAGE_1, "res64x64", HANDLE_USER_0));
+        assertEquals(
+                R.drawable.black_512x512,
+                mLauncherApps.getShortcutIconResId(CALLING_PACKAGE_1, "res32x32", HANDLE_USER_P0));
+        bmp = pfdToBitmap(
+                mLauncherApps.getShortcutIconFd(CALLING_PACKAGE_1, "bmp32x32", HANDLE_USER_P0));
         assertBitmapSize(128, 128, bmp);
 
         // TODO Test the content URI case too.
@@ -1927,13 +1802,13 @@
                     getCallingUser());
         });
         runWithCaller(CALLING_PACKAGE_1, UserHandle.USER_SYSTEM, () -> {
-            mManager.deleteDynamicShortcut("s1");
-            mManager.deleteDynamicShortcut("s2");
+            mManager.removeDynamicShortcuts(list("s1"));
+            mManager.removeDynamicShortcuts(list("s2"));
         });
         runWithCaller(CALLING_PACKAGE_2, UserHandle.USER_SYSTEM, () -> {
-            mManager.deleteDynamicShortcut("s1");
-            mManager.deleteDynamicShortcut("s3");
-            mManager.deleteDynamicShortcut("s5");
+            mManager.removeDynamicShortcuts(list("s1"));
+            mManager.removeDynamicShortcuts(list("s3"));
+            mManager.removeDynamicShortcuts(list("s5"));
         });
         runWithCaller(CALLING_PACKAGE_1, UserHandle.USER_SYSTEM, () -> {
             assertShortcutIds(assertAllDynamic(
@@ -2034,9 +1909,16 @@
     private static ShortcutQuery buildQuery(long changedSince,
             String packageName, ComponentName componentName,
             /* @ShortcutQuery.QueryFlags */ int flags) {
+        return buildQuery(changedSince, packageName, null, componentName, flags);
+    }
+
+    private static ShortcutQuery buildQuery(long changedSince,
+            String packageName, List<String> shortcutIds, ComponentName componentName,
+            /* @ShortcutQuery.QueryFlags */ int flags) {
         final ShortcutQuery q = new ShortcutQuery();
         q.setChangedSince(changedSince);
         q.setPackage(packageName);
+        q.setShortcutIds(shortcutIds);
         q.setActivity(componentName);
         q.setQueryFlags(flags);
         return q;
@@ -2110,6 +1992,36 @@
                         getCallingUser())),
                 "s2", "s3"))));
 
+        // With ID.
+        assertAllDynamic(assertAllNotHaveTitle(assertAllNotHaveIntents(assertShortcutIds(
+                assertAllKeyFieldsOnly(mLauncherApps.getShortcuts(buildQuery(
+                        /* time =*/ 1000, CALLING_PACKAGE_2, list("s3"),
+                        /* activity =*/ null,
+                        ShortcutQuery.FLAG_GET_DYNAMIC | ShortcutQuery.FLAG_GET_KEY_FIELDS_ONLY),
+                        getCallingUser())),
+                "s3"))));
+        assertAllDynamic(assertAllNotHaveTitle(assertAllNotHaveIntents(assertShortcutIds(
+                assertAllKeyFieldsOnly(mLauncherApps.getShortcuts(buildQuery(
+                        /* time =*/ 1000, CALLING_PACKAGE_2, list("s3", "s2", "ss"),
+                        /* activity =*/ null,
+                        ShortcutQuery.FLAG_GET_DYNAMIC | ShortcutQuery.FLAG_GET_KEY_FIELDS_ONLY),
+                        getCallingUser())),
+                "s2", "s3"))));
+        assertAllDynamic(assertAllNotHaveTitle(assertAllNotHaveIntents(assertShortcutIds(
+                assertAllKeyFieldsOnly(mLauncherApps.getShortcuts(buildQuery(
+                        /* time =*/ 1000, CALLING_PACKAGE_2, list("s3x", "s2x"),
+                        /* activity =*/ null,
+                        ShortcutQuery.FLAG_GET_DYNAMIC | ShortcutQuery.FLAG_GET_KEY_FIELDS_ONLY),
+                        getCallingUser()))
+                /* empty */))));
+        assertAllDynamic(assertAllNotHaveTitle(assertAllNotHaveIntents(assertShortcutIds(
+                assertAllKeyFieldsOnly(mLauncherApps.getShortcuts(buildQuery(
+                        /* time =*/ 1000, CALLING_PACKAGE_2, list(),
+                        /* activity =*/ null,
+                        ShortcutQuery.FLAG_GET_DYNAMIC | ShortcutQuery.FLAG_GET_KEY_FIELDS_ONLY),
+                        getCallingUser()))
+                /* empty */))));
+
         // Pin some shortcuts.
         mLauncherApps.pinShortcuts(CALLING_PACKAGE_2,
                 list("s3", "s4"), getCallingUser());
@@ -2132,6 +2044,13 @@
                         getCallingUser())),
                 "s1", "s3");
 
+        assertExpectException(
+                IllegalArgumentException.class, "package name must also be set", () -> {
+            mLauncherApps.getShortcuts(buildQuery(
+                    /* time =*/ 0, /* package= */ null, list("id"),
+                    /* activity =*/ null, /* flags */ 0), getCallingUser());
+        });
+
         // TODO More tests: pinned but dynamic, filter by activity
     }
 
@@ -2181,7 +2100,7 @@
         // Delete some.
         setCaller(CALLING_PACKAGE_1);
         assertShortcutIds(mManager.getPinnedShortcuts(), "s2");
-        mManager.deleteDynamicShortcut("s2");
+        mManager.removeDynamicShortcuts(list("s2"));
         assertShortcutIds(mManager.getPinnedShortcuts(), "s2");
 
         dumpsysOnLogcat();
@@ -2246,19 +2165,19 @@
         // Delete some.
         runWithCaller(CALLING_PACKAGE_1, USER_0, () -> {
             assertShortcutIds(mManager.getPinnedShortcuts(), "s2");
-            mManager.deleteDynamicShortcut("s2");
+            mManager.removeDynamicShortcuts(list("s2"));
             assertShortcutIds(mManager.getPinnedShortcuts(), "s2");
         });
 
         runWithCaller(CALLING_PACKAGE_2, USER_0, () -> {
             assertShortcutIds(mManager.getPinnedShortcuts(), "s3", "s4");
-            mManager.deleteDynamicShortcut("s3");
+            mManager.removeDynamicShortcuts(list("s3"));
             assertShortcutIds(mManager.getPinnedShortcuts(), "s3", "s4");
         });
 
         runWithCaller(CALLING_PACKAGE_3, USER_0, () -> {
             assertShortcutIds(mManager.getPinnedShortcuts() /* none */);
-            mManager.deleteDynamicShortcut("s2");
+            mManager.removeDynamicShortcuts(list("s2"));
             assertShortcutIds(mManager.getPinnedShortcuts() /* none */);
         });
 
@@ -2310,7 +2229,7 @@
         // Delete some.
         runWithCaller(CALLING_PACKAGE_1, USER_0, () -> {
             assertShortcutIds(mManager.getPinnedShortcuts(), "s3");
-            mManager.deleteDynamicShortcut("s3");
+            mManager.removeDynamicShortcuts(list("s3"));
             assertShortcutIds(mManager.getPinnedShortcuts(), "s3");
         });
 
@@ -2318,8 +2237,8 @@
 
         runWithCaller(CALLING_PACKAGE_2, USER_0, () -> {
             assertShortcutIds(mManager.getPinnedShortcuts(), "s1", "s2");
-            mManager.deleteDynamicShortcut("s1");
-            mManager.deleteDynamicShortcut("s3");
+            mManager.removeDynamicShortcuts(list("s1"));
+            mManager.removeDynamicShortcuts(list("s3"));
             assertShortcutIds(mManager.getPinnedShortcuts(), "s1", "s2");
         });
 
@@ -2428,13 +2347,13 @@
 
         // Delete all dynamic.
         runWithCaller(CALLING_PACKAGE_1, USER_0, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
 
             assertEquals(0, mManager.getDynamicShortcuts().size());
             assertShortcutIds(assertAllPinned(mManager.getPinnedShortcuts()), "s1", "s2", "s3");
         });
         runWithCaller(CALLING_PACKAGE_2, USER_0, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
 
             assertEquals(0, mManager.getDynamicShortcuts().size());
             assertShortcutIds(assertAllPinned(mManager.getPinnedShortcuts()), "s2", "s1");
@@ -2469,7 +2388,7 @@
         });
         // Re-publish s1.
         runWithCaller(CALLING_PACKAGE_1, USER_0, () -> {
-            assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+            assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
             assertShortcutIds(assertAllDynamic(mManager.getDynamicShortcuts()), "s1");
             assertShortcutIds(assertAllPinned(mManager.getPinnedShortcuts()), "s1", "s2", "s3");
@@ -3071,7 +2990,7 @@
 
         // Just to make it complicated, delete some.
         setCaller(CALLING_PACKAGE_1);
-        mManager.deleteDynamicShortcut("s2");
+        mManager.removeDynamicShortcuts(list("s2"));
 
         // intent and check.
         setCaller(LAUNCHER_1);
@@ -3143,11 +3062,11 @@
                 any(UserHandle.class)
         );
 
-        // Test for addDynamicShortcut.
+        // Test for addDynamicShortcuts.
         reset(c0);
         runWithCaller(CALLING_PACKAGE_1, UserHandle.USER_SYSTEM, () -> {
-            dumpsysOnLogcat("before addDynamicShortcut");
-            assertTrue(mManager.addDynamicShortcut(makeShortcut("s4")));
+            dumpsysOnLogcat("before addDynamicShortcuts");
+            assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s4"))));
         });
 
         waitOnMainThread();
@@ -3163,7 +3082,7 @@
         // Test for remove
         reset(c0);
         runWithCaller(CALLING_PACKAGE_1, UserHandle.USER_SYSTEM, () -> {
-            mManager.deleteDynamicShortcut("s1");
+            mManager.removeDynamicShortcuts(list("s1"));
         });
 
         waitOnMainThread();
@@ -3196,7 +3115,7 @@
         // Test for deleteAll
         reset(c0);
         runWithCaller(CALLING_PACKAGE_1, UserHandle.USER_SYSTEM, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
         });
 
         waitOnMainThread();
@@ -3224,20 +3143,6 @@
         assertEquals(0, shortcuts.getValue().size());
     }
 
-    private void assertCallbackNotReceived(LauncherApps.Callback mock) {
-        verify(mock, times(0)).onShortcutsChanged(anyString(), anyList(),
-                any(UserHandle.class));
-    }
-
-    private void assertCallbackReceived(LauncherApps.Callback mock,
-            UserHandle user, String packageName, String... ids) {
-        ArgumentCaptor<List> shortcutsCaptor = ArgumentCaptor.forClass(List.class);
-
-        verify(mock, times(1)).onShortcutsChanged(eq(packageName), shortcutsCaptor.capture(),
-                eq(user));
-        assertShortcutIds(shortcutsCaptor.getValue(), ids);
-    }
-
     public void testLauncherCallback_crossProfile() throws Throwable {
         prepareCrossProfileDataSet();
 
@@ -3284,7 +3189,7 @@
 
         resetAll(all);
         runWithCaller(CALLING_PACKAGE_1, USER_0, () -> {
-            mManager.deleteDynamicShortcut("x");
+            mManager.removeDynamicShortcuts(list());
         });
         waitOnMainThread();
 
@@ -3301,7 +3206,7 @@
 
         resetAll(all);
         runWithCaller(CALLING_PACKAGE_3, USER_0, () -> {
-            mManager.deleteDynamicShortcut("x");
+            mManager.removeDynamicShortcuts(list());
         });
         waitOnMainThread();
 
@@ -3319,7 +3224,7 @@
 
         resetAll(all);
         runWithCaller(CALLING_PACKAGE_1, USER_P0, () -> {
-            mManager.deleteDynamicShortcut("x");
+            mManager.removeDynamicShortcuts(list());
         });
         waitOnMainThread();
 
@@ -3339,7 +3244,7 @@
 
         resetAll(all);
         runWithCaller(CALLING_PACKAGE_1, USER_P0, () -> {
-            mManager.deleteDynamicShortcut("x");
+            mManager.removeDynamicShortcuts(list());
         });
         waitOnMainThread();
 
@@ -3359,7 +3264,7 @@
 
         resetAll(all);
         runWithCaller(CALLING_PACKAGE_1, USER_10, () -> {
-            mManager.deleteDynamicShortcut("x");
+            mManager.removeDynamicShortcuts(list());
         });
         waitOnMainThread();
 
@@ -3583,16 +3488,16 @@
 
         // Remove all dynamic shortcuts; now all shortcuts are just pinned.
         runWithCaller(CALLING_PACKAGE_1, USER_0, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
         });
         runWithCaller(CALLING_PACKAGE_2, USER_0, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
         });
         runWithCaller(CALLING_PACKAGE_1, USER_10, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
         });
         runWithCaller(CALLING_PACKAGE_2, USER_10, () -> {
-            mManager.deleteAllDynamicShortcuts();
+            mManager.removeAllDynamicShortcuts();
         });
 
 
@@ -3607,18 +3512,18 @@
 
         // Check the registered packages.
         dumpsysOnLogcat();
-        assertEquals(makeSet(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_10, LAUNCHER_1),
+                set(PackageWithUser.of(USER_10, LAUNCHER_1),
                         PackageWithUser.of(USER_10, LAUNCHER_2)),
-                set(user10.getAllLaunchers().keySet()));
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_1", "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -3639,18 +3544,18 @@
         mService.cleanUpPackageLocked("abc", USER_0, USER_0);
 
         // No changes.
-        assertEquals(makeSet(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_10, LAUNCHER_1),
+                set(PackageWithUser.of(USER_10, LAUNCHER_1),
                         PackageWithUser.of(USER_10, LAUNCHER_2)),
-                set(user10.getAllLaunchers().keySet()));
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_1", "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -3670,18 +3575,18 @@
         uninstallPackage(USER_0, CALLING_PACKAGE_1);
         mService.cleanUpPackageLocked(CALLING_PACKAGE_1, USER_0, USER_0);
 
-        assertEquals(makeSet(CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_10, LAUNCHER_1),
+                set(PackageWithUser.of(USER_10, LAUNCHER_1),
                         PackageWithUser.of(USER_10, LAUNCHER_2)),
-                set(user10.getAllLaunchers().keySet()));
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -3701,17 +3606,17 @@
         uninstallPackage(USER_10, LAUNCHER_1);
         mService.cleanUpPackageLocked(LAUNCHER_1, USER_10, USER_10);
 
-        assertEquals(makeSet(CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1, CALLING_PACKAGE_2),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_10, LAUNCHER_2)),
-                set(user10.getAllLaunchers().keySet()));
+                set(PackageWithUser.of(USER_10, LAUNCHER_2)),
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -3729,17 +3634,17 @@
         uninstallPackage(USER_10, CALLING_PACKAGE_2);
         mService.cleanUpPackageLocked(CALLING_PACKAGE_2, USER_10, USER_10);
 
-        assertEquals(makeSet(CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(CALLING_PACKAGE_1),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_10, LAUNCHER_2)),
-                set(user10.getAllLaunchers().keySet()));
+                set(PackageWithUser.of(USER_10, LAUNCHER_2)),
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -3757,17 +3662,17 @@
         uninstallPackage(USER_10, LAUNCHER_2);
         mService.cleanUpPackageLocked(LAUNCHER_2, USER_10, USER_10);
 
-        assertEquals(makeSet(CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(CALLING_PACKAGE_1),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_1),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
         assertEquals(
-                makeSet(),
-                set(user10.getAllLaunchers().keySet()));
+                set(),
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -3785,16 +3690,16 @@
         uninstallPackage(USER_10, CALLING_PACKAGE_1);
         mService.cleanUpPackageLocked(CALLING_PACKAGE_1, USER_10, USER_10);
 
-        assertEquals(makeSet(CALLING_PACKAGE_2),
-                set(user0.getAllPackages().keySet()));
-        assertEquals(makeSet(),
-                set(user10.getAllPackages().keySet()));
+        assertEquals(set(CALLING_PACKAGE_2),
+                hashSet(user0.getAllPackages().keySet()));
+        assertEquals(set(),
+                hashSet(user10.getAllPackages().keySet()));
         assertEquals(
-                makeSet(PackageWithUser.of(USER_0, LAUNCHER_1),
+                set(PackageWithUser.of(USER_0, LAUNCHER_1),
                         PackageWithUser.of(USER_0, LAUNCHER_2)),
-                set(user0.getAllLaunchers().keySet()));
-        assertEquals(makeSet(),
-                set(user10.getAllLaunchers().keySet()));
+                hashSet(user0.getAllLaunchers().keySet()));
+        assertEquals(set(),
+                hashSet(user10.getAllLaunchers().keySet()));
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_1, USER_0),
                 "s0_2");
         assertShortcutIds(getLauncherPinnedShortcuts(LAUNCHER_2, USER_0),
@@ -4115,22 +4020,22 @@
 
     public void testHandlePackageDelete() {
         setCaller(CALLING_PACKAGE_1, USER_0);
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
         setCaller(CALLING_PACKAGE_2, USER_0);
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
         setCaller(CALLING_PACKAGE_3, USER_0);
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
         setCaller(CALLING_PACKAGE_1, USER_10);
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
         setCaller(CALLING_PACKAGE_2, USER_10);
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
         setCaller(CALLING_PACKAGE_3, USER_10);
-        assertTrue(mManager.addDynamicShortcut(makeShortcut("s1")));
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcut("s1"))));
 
         assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_0));
         assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_0));
@@ -4935,7 +4840,7 @@
             assertShortcutIds(
                     mLauncherApps.getShortcuts(buildPinnedQuery(CALLING_PACKAGE_2), HANDLE_USER_P0)
                     /* empty */);
-            TestUtils.assertExpectException(
+            assertExpectException(
                     SecurityException.class, "", () -> {
                         mLauncherApps.getShortcuts(
                                 buildAllQuery(CALLING_PACKAGE_1), HANDLE_USER_10);
@@ -5014,7 +4919,7 @@
             assertShortcutIds(
                     mLauncherApps.getShortcuts(buildPinnedQuery(CALLING_PACKAGE_1), HANDLE_USER_P0),
                     "s1", "s4");
-            TestUtils.assertExpectException(
+            assertExpectException(
                     SecurityException.class, "unrelated profile", () -> {
                         mLauncherApps.getShortcuts(
                                 buildAllQuery(CALLING_PACKAGE_1), HANDLE_USER_10);
@@ -5030,12 +4935,12 @@
             assertShortcutIds(
                     mLauncherApps.getShortcuts(buildPinnedQuery(CALLING_PACKAGE_3), HANDLE_USER_10)
                     /* empty */);
-            TestUtils.assertExpectException(
+            assertExpectException(
                     SecurityException.class, "unrelated profile", () -> {
                         mLauncherApps.getShortcuts(
                                 buildAllQuery(CALLING_PACKAGE_1), HANDLE_USER_0);
                     });
-            TestUtils.assertExpectException(
+            assertExpectException(
                     SecurityException.class, "unrelated profile", () -> {
                         mLauncherApps.getShortcuts(
                                 buildAllQuery(CALLING_PACKAGE_1), HANDLE_USER_P0);
@@ -5046,16 +4951,16 @@
     // ShortcutInfo tests
 
     public void testShortcutInfoMissingMandatoryFields() {
-        TestUtils.assertExpectException(
+        assertExpectException(
                 IllegalArgumentException.class,
                 "ID must be provided",
                 () -> new ShortcutInfo.Builder(getTestContext()).build());
-        TestUtils.assertExpectException(
+        assertExpectException(
                 IllegalArgumentException.class,
                 "title must be provided",
                 () -> new ShortcutInfo.Builder(getTestContext()).setId("id").build()
                         .enforceMandatoryFields());
-        TestUtils.assertExpectException(
+        assertExpectException(
                 NullPointerException.class,
                 "Intent must be provided",
                 () -> new ShortcutInfo.Builder(getTestContext()).setId("id").setTitle("x").build()
@@ -5063,12 +4968,15 @@
     }
 
     public void testShortcutInfoParcel() {
-        ShortcutInfo si = parceled(new ShortcutInfo.Builder(getTestContext())
+        setCaller(CALLING_PACKAGE_1, USER_10);
+        ShortcutInfo si = parceled(new ShortcutInfo.Builder(mClientContext)
                 .setId("id")
                 .setTitle("title")
                 .setIntent(makeIntent("action", ShortcutActivity.class))
                 .build());
-        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals(mClientContext.getPackageName(), si.getPackageName());
+        assertEquals(USER_10, si.getUserId());
+        assertEquals(HANDLE_USER_10, si.getUserHandle());
         assertEquals("id", si.getId());
         assertEquals("title", si.getTitle());
         assertEquals("action", si.getIntent().getAction());
@@ -5083,6 +4991,7 @@
                 .setTitle("title")
                 .setText("text")
                 .setIntent(makeIntent("action", ShortcutActivity.class, "key", "val"))
+                .setCategories(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"))
                 .setWeight(123)
                 .setExtras(pb)
                 .build();
@@ -5098,6 +5007,7 @@
         assertEquals("content://a.b.c/", si.getIcon().getUriString());
         assertEquals("title", si.getTitle());
         assertEquals("text", si.getText());
+        assertEquals(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"), si.getCategories());
         assertEquals("action", si.getIntent().getAction());
         assertEquals("val", si.getIntent().getStringExtra("key"));
         assertEquals(123, si.getWeight());
@@ -5109,14 +5019,17 @@
     }
 
     public void testShortcutInfoClone() {
+        setCaller(CALLING_PACKAGE_1, USER_11);
+
         PersistableBundle pb = new PersistableBundle();
         pb.putInt("k", 1);
-        ShortcutInfo sorig = new ShortcutInfo.Builder(getTestContext())
+        ShortcutInfo sorig = new ShortcutInfo.Builder(mClientContext)
                 .setId("id")
                 .setActivityComponent(new ComponentName("a", "b"))
                 .setIcon(Icon.createWithContentUri("content://a.b.c/"))
                 .setTitle("title")
                 .setText("text")
+                .setCategories(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"))
                 .setIntent(makeIntent("action", ShortcutActivity.class, "key", "val"))
                 .setWeight(123)
                 .setExtras(pb)
@@ -5127,12 +5040,15 @@
 
         ShortcutInfo si = sorig.clone(/* clone flags*/ 0);
 
-        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals(USER_11, si.getUserId());
+        assertEquals(HANDLE_USER_11, si.getUserHandle());
+        assertEquals(mClientContext.getPackageName(), si.getPackageName());
         assertEquals("id", si.getId());
         assertEquals(new ComponentName("a", "b"), si.getActivityComponent());
         assertEquals("content://a.b.c/", si.getIcon().getUriString());
         assertEquals("title", si.getTitle());
         assertEquals("text", si.getText());
+        assertEquals(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"), si.getCategories());
         assertEquals("action", si.getIntent().getAction());
         assertEquals("val", si.getIntent().getStringExtra("key"));
         assertEquals(123, si.getWeight());
@@ -5144,12 +5060,13 @@
 
         si = sorig.clone(ShortcutInfo.CLONE_REMOVE_FOR_CREATOR);
 
-        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals(mClientContext.getPackageName(), si.getPackageName());
         assertEquals("id", si.getId());
         assertEquals(new ComponentName("a", "b"), si.getActivityComponent());
         assertEquals(null, si.getIcon());
         assertEquals("title", si.getTitle());
         assertEquals("text", si.getText());
+        assertEquals(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"), si.getCategories());
         assertEquals("action", si.getIntent().getAction());
         assertEquals("val", si.getIntent().getStringExtra("key"));
         assertEquals(123, si.getWeight());
@@ -5157,39 +5074,85 @@
 
         assertEquals(ShortcutInfo.FLAG_PINNED, si.getFlags());
         assertEquals(null, si.getBitmapPath());
-        assertEquals(0, si.getIconResourceId());
+
+        assertEquals(456, si.getIconResourceId());
 
         si = sorig.clone(ShortcutInfo.CLONE_REMOVE_FOR_LAUNCHER);
 
-        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals(mClientContext.getPackageName(), si.getPackageName());
         assertEquals("id", si.getId());
         assertEquals(new ComponentName("a", "b"), si.getActivityComponent());
         assertEquals(null, si.getIcon());
         assertEquals("title", si.getTitle());
         assertEquals("text", si.getText());
+        assertEquals(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"), si.getCategories());
         assertEquals(null, si.getIntent());
         assertEquals(123, si.getWeight());
         assertEquals(1, si.getExtras().getInt("k"));
 
         assertEquals(ShortcutInfo.FLAG_PINNED, si.getFlags());
         assertEquals(null, si.getBitmapPath());
-        assertEquals(0, si.getIconResourceId());
+
+        assertEquals(456, si.getIconResourceId());
 
         si = sorig.clone(ShortcutInfo.CLONE_REMOVE_NON_KEY_INFO);
 
-        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals(mClientContext.getPackageName(), si.getPackageName());
         assertEquals("id", si.getId());
         assertEquals(null, si.getActivityComponent());
         assertEquals(null, si.getIcon());
         assertEquals(null, si.getTitle());
         assertEquals(null, si.getText());
+        assertEquals(null, si.getCategories());
         assertEquals(null, si.getIntent());
         assertEquals(0, si.getWeight());
         assertEquals(null, si.getExtras());
 
         assertEquals(ShortcutInfo.FLAG_PINNED | ShortcutInfo.FLAG_KEY_FIELDS_ONLY, si.getFlags());
         assertEquals(null, si.getBitmapPath());
-        assertEquals(0, si.getIconResourceId());
+
+        assertEquals(456, si.getIconResourceId());
+    }
+
+    public void testShortcutInfoClone_minimum() {
+        PersistableBundle pb = new PersistableBundle();
+        pb.putInt("k", 1);
+        ShortcutInfo sorig = new ShortcutInfo.Builder(getTestContext())
+                .setId("id")
+                .setTitle("title")
+                .setIntent(makeIntent("action", ShortcutActivity.class))
+                .build();
+        ShortcutInfo si = sorig.clone(/* clone flags*/ 0);
+
+        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals("id", si.getId());
+        assertEquals("title", si.getTitle());
+        assertEquals("action", si.getIntent().getAction());
+        assertEquals(null, si.getCategories());
+
+        si = sorig.clone(ShortcutInfo.CLONE_REMOVE_FOR_CREATOR);
+
+        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals("id", si.getId());
+        assertEquals("title", si.getTitle());
+        assertEquals("action", si.getIntent().getAction());
+        assertEquals(null, si.getCategories());
+
+        si = sorig.clone(ShortcutInfo.CLONE_REMOVE_FOR_LAUNCHER);
+
+        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals("id", si.getId());
+        assertEquals("title", si.getTitle());
+        assertEquals(null, si.getIntent());
+        assertEquals(null, si.getCategories());
+
+        si = sorig.clone(ShortcutInfo.CLONE_REMOVE_NON_KEY_INFO);
+
+        assertEquals(getTestContext().getPackageName(), si.getPackageName());
+        assertEquals("id", si.getId());
+        assertEquals(null, si.getTitle());
+        assertEquals(null, si.getIntent());
+        assertEquals(null, si.getCategories());
     }
 
     public void testShortcutInfoCopyNonNullFieldsFrom() throws InterruptedException {
@@ -5201,6 +5164,7 @@
                 .setIcon(Icon.createWithContentUri("content://a.b.c/"))
                 .setTitle("title")
                 .setText("text")
+                .setCategories(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"))
                 .setIntent(makeIntent("action", ShortcutActivity.class, "key", "val"))
                 .setWeight(123)
                 .setExtras(pb)
@@ -5214,38 +5178,57 @@
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setActivityComponent(new ComponentName("x", "y")).build());
+        assertEquals("text", si.getText());
         assertEquals(new ComponentName("x", "y"), si.getActivityComponent());
 
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setIcon(Icon.createWithContentUri("content://x.y.z/")).build());
+        assertEquals("text", si.getText());
         assertEquals("content://x.y.z/", si.getIcon().getUriString());
 
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setTitle("xyz").build());
+        assertEquals("text", si.getText());
         assertEquals("xyz", si.getTitle());
 
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setText("xxx").build());
+        assertEquals(123, si.getWeight());
         assertEquals("xxx", si.getText());
 
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
+                .setCategories(list()).build());
+        assertEquals("text", si.getText());
+        assertEquals(list(), si.getCategories());
+
+        si = sorig.clone(/* flags=*/ 0);
+        si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
+                .setCategories(list("x")).build());
+        assertEquals("text", si.getText());
+        assertEquals(list("x"), si.getCategories());
+
+        si = sorig.clone(/* flags=*/ 0);
+        si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setIntent(makeIntent("action2", ShortcutActivity.class)).build());
+        assertEquals("text", si.getText());
         assertEquals("action2", si.getIntent().getAction());
         assertEquals(null, si.getIntent().getStringExtra("key"));
 
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setIntent(makeIntent("action3", ShortcutActivity.class, "key", "x")).build());
+        assertEquals("text", si.getText());
         assertEquals("action3", si.getIntent().getAction());
         assertEquals("x", si.getIntent().getStringExtra("key"));
 
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setWeight(999).build());
+        assertEquals("text", si.getText());
         assertEquals(999, si.getWeight());
 
 
@@ -5255,8 +5238,11 @@
         si = sorig.clone(/* flags=*/ 0);
         si.copyNonNullFieldsFrom(new ShortcutInfo.Builder(getTestContext()).setId("id")
                 .setExtras(pb2).build());
+        assertEquals("text", si.getText());
         assertEquals(99, si.getExtras().getInt("x"));
 
+        // Make sure the timestamp gets updated too.
+
         final long timestamp = si.getLastChangedTimestamp();
         Thread.sleep(2);
 
@@ -5267,7 +5253,7 @@
     }
 
     public void testShortcutInfoSaveAndLoad() throws InterruptedException {
-        setCaller(CALLING_PACKAGE_1, USER_0);
+        setCaller(CALLING_PACKAGE_1, USER_10);
 
         final Icon bmp32x32 = Icon.createWithBitmap(BitmapFactory.decodeResource(
                 getTestContext().getResources(), R.drawable.black_32x32));
@@ -5280,12 +5266,13 @@
                 .setIcon(bmp32x32)
                 .setTitle("title")
                 .setText("text")
+                .setCategories(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"))
                 .setIntent(makeIntent("action", ShortcutActivity.class, "key", "val"))
                 .setWeight(123)
                 .setExtras(pb)
                 .build();
 
-        mManager.addDynamicShortcut(sorig);
+        mManager.addDynamicShortcuts(list(sorig));
 
         Thread.sleep(2);
         final long now = System.currentTimeMillis();
@@ -5293,17 +5280,20 @@
         // Save and load.
         mService.saveDirtyInfo();
         initService();
-        mService.handleUnlockUser(USER_0);
+        mService.handleUnlockUser(USER_10);
 
         ShortcutInfo si;
-        si = mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "id", USER_0);
+        si = mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "id", USER_10);
 
+        assertEquals(USER_10, si.getUserId());
+        assertEquals(HANDLE_USER_10, si.getUserHandle());
         assertEquals(CALLING_PACKAGE_1, si.getPackageName());
         assertEquals("id", si.getId());
         assertEquals(ShortcutActivity2.class.getName(), si.getActivityComponent().getClassName());
         assertEquals(null, si.getIcon());
         assertEquals("title", si.getTitle());
         assertEquals("text", si.getText());
+        assertEquals(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"), si.getCategories());
         assertEquals("action", si.getIntent().getAction());
         assertEquals("val", si.getIntent().getStringExtra("key"));
         assertEquals(123, si.getWeight());
@@ -5329,12 +5319,13 @@
                 .setIcon(bmp32x32)
                 .setTitle("title")
                 .setText("text")
+                .setCategories(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"))
                 .setIntent(makeIntent("action", ShortcutActivity.class, "key", "val"))
                 .setWeight(123)
                 .setExtras(pb)
                 .build();
 
-        mManager.addDynamicShortcut(sorig);
+        mManager.addDynamicShortcuts(list(sorig));
 
         // Dynamic shortcuts won't be backed up, so we need to pin it.
         setCaller(LAUNCHER_1, USER_0);
@@ -5343,6 +5334,8 @@
         // Do backup & restore.
         backupAndRestore();
 
+        mService.handleUnlockUser(USER_0); // Load user-0.
+
         ShortcutInfo si;
         si = mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "id", USER_0);
 
@@ -5352,6 +5345,7 @@
         assertEquals(null, si.getIcon());
         assertEquals("title", si.getTitle());
         assertEquals("text", si.getText());
+        assertEquals(list(ShortcutInfo.SHORTCUT_CATEGORY_CONVERSATION, "xyz"), si.getCategories());
         assertEquals("action", si.getIntent().getAction());
         assertEquals("val", si.getIntent().getStringExtra("key"));
         assertEquals(123, si.getWeight());
@@ -5367,7 +5361,7 @@
         dumpsysOnLogcat("test1", /* force= */ true);
     }
 
-    public void testDumpsys_withIcons() {
+    public void testDumpsys_withIcons() throws IOException {
         testIcons();
         // Dump after having some icons.
         dumpsysOnLogcat("test1", /* force= */ true);
diff --git a/services/tests/servicestests/src/com/android/server/webkit/TestSystemImpl.java b/services/tests/servicestests/src/com/android/server/webkit/TestSystemImpl.java
new file mode 100644
index 0000000..26b87c5
--- /dev/null
+++ b/services/tests/servicestests/src/com/android/server/webkit/TestSystemImpl.java
@@ -0,0 +1,112 @@
+/*
+ * 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 com.android.server.webkit;
+
+import android.content.Context;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager.NameNotFoundException;
+import android.webkit.WebViewProviderInfo;
+
+import java.util.HashMap;
+
+public class TestSystemImpl implements SystemInterface {
+    private String mUserProvider = "";
+    private final WebViewProviderInfo[] mPackageConfigs;
+    HashMap<String, PackageInfo> mPackages = new HashMap();
+    private boolean mFallbackLogicEnabled;
+    private final int mNumRelros;
+    private final boolean mIsDebuggable;
+
+    public TestSystemImpl(WebViewProviderInfo[] packageConfigs, boolean fallbackLogicEnabled,
+            int numRelros, boolean isDebuggable) {
+        mPackageConfigs = packageConfigs;
+        mFallbackLogicEnabled = fallbackLogicEnabled;
+        mNumRelros = numRelros;
+        mIsDebuggable = isDebuggable;
+    }
+
+    @Override
+    public WebViewProviderInfo[] getWebViewPackages() {
+        return mPackageConfigs;
+    }
+
+    @Override
+    public int onWebViewProviderChanged(PackageInfo packageInfo) {
+        return mNumRelros;
+    }
+
+    @Override
+    public String getUserChosenWebViewProvider(Context context) { return mUserProvider; }
+
+    @Override
+    public void updateUserSetting(Context context, String newProviderName) {
+        mUserProvider = newProviderName;
+    }
+
+    @Override
+    public void killPackageDependents(String packageName) {}
+
+    @Override
+    public boolean isFallbackLogicEnabled() {
+        return mFallbackLogicEnabled;
+    }
+
+    @Override
+    public void enableFallbackLogic(boolean enable) {
+        mFallbackLogicEnabled = enable;
+    }
+
+    @Override
+    public void uninstallAndDisablePackageForAllUsers(Context context, String packageName) {
+        enablePackageForAllUsers(context, packageName, false);
+    }
+
+    @Override
+    public void enablePackageForAllUsers(Context context, String packageName, boolean enable) {
+        enablePackageForUser(packageName, enable, 0);
+    }
+
+    @Override
+    public void enablePackageForUser(String packageName, boolean enable, int userId) {
+        PackageInfo packageInfo = mPackages.get(packageName);
+        if (packageInfo == null) {
+            throw new IllegalArgumentException("There is no package called " + packageName);
+        }
+        packageInfo.applicationInfo.enabled = enable;
+        setPackageInfo(packageInfo);
+    }
+
+    @Override
+    public boolean systemIsDebuggable() { return mIsDebuggable; }
+
+    @Override
+    public PackageInfo getPackageInfoForProvider(WebViewProviderInfo info) throws
+            NameNotFoundException {
+        PackageInfo ret = mPackages.get(info.packageName);
+        if (ret == null) throw new NameNotFoundException(info.packageName);
+        return ret;
+    }
+
+    public void setPackageInfo(PackageInfo pi) {
+        mPackages.put(pi.packageName, pi);
+    }
+
+    @Override
+    public int getFactoryPackageVersion(String packageName) {
+        return 0;
+    }
+}
diff --git a/services/tests/servicestests/src/com/android/server/webkit/WebViewUpdateServiceTest.java b/services/tests/servicestests/src/com/android/server/webkit/WebViewUpdateServiceTest.java
new file mode 100644
index 0000000..c00520d
--- /dev/null
+++ b/services/tests/servicestests/src/com/android/server/webkit/WebViewUpdateServiceTest.java
@@ -0,0 +1,613 @@
+/*
+ * 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 com.android.server.webkit;
+
+import android.content.Context;
+import android.content.pm.ApplicationInfo;
+import android.content.pm.PackageInfo;
+import android.content.pm.Signature;
+import android.os.Bundle;
+import android.util.Base64;
+import android.test.AndroidTestCase;
+
+import android.webkit.WebViewFactory;
+import android.webkit.WebViewProviderInfo;
+import android.webkit.WebViewProviderResponse;
+
+import java.util.concurrent.CountDownLatch;
+
+import org.hamcrest.Description;
+
+import org.mockito.Mockito;
+import org.mockito.Matchers;
+import org.mockito.ArgumentMatcher;
+
+
+/**
+ * Tests for WebViewUpdateService
+ */
+public class WebViewUpdateServiceTest extends AndroidTestCase {
+    private final static String TAG = WebViewUpdateServiceTest.class.getSimpleName();
+
+    private WebViewUpdateServiceImpl mWebViewUpdateServiceImpl;
+    private TestSystemImpl mTestSystemImpl;
+
+    private static final String WEBVIEW_LIBRARY_FLAG = "com.android.webview.WebViewLibrary";
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+    }
+
+    /**
+     * Creates a new instance.
+     */
+    public WebViewUpdateServiceTest() {
+    }
+
+    private void setupWithPackages(WebViewProviderInfo[] packages) {
+        setupWithPackages(packages, true);
+    }
+
+    private void setupWithPackages(WebViewProviderInfo[] packages,
+            boolean fallbackLogicEnabled) {
+        setupWithPackages(packages, fallbackLogicEnabled, 1);
+    }
+
+    private void setupWithPackages(WebViewProviderInfo[] packages,
+            boolean fallbackLogicEnabled, int numRelros) {
+        setupWithPackages(packages, fallbackLogicEnabled, numRelros,
+                true /* isDebuggable == true -> don't check package signatures */);
+    }
+
+    private void setupWithPackages(WebViewProviderInfo[] packages,
+            boolean fallbackLogicEnabled, int numRelros, boolean isDebuggable) {
+        TestSystemImpl testing = new TestSystemImpl(packages, fallbackLogicEnabled, numRelros,
+                isDebuggable);
+        mTestSystemImpl = Mockito.spy(testing);
+        mWebViewUpdateServiceImpl =
+            new WebViewUpdateServiceImpl(null /*Context*/, mTestSystemImpl);
+    }
+
+    private void setEnabledAndValidPackageInfos(WebViewProviderInfo[] providers) {
+        for(WebViewProviderInfo wpi : providers) {
+            mTestSystemImpl.setPackageInfo(createPackageInfo(wpi.packageName, true /* enabled */,
+                        true /* valid */));
+        }
+    }
+
+    private void checkCertainPackageUsedAfterWebViewPreparation(String expectedProviderName,
+            WebViewProviderInfo[] webviewPackages) {
+        checkCertainPackageUsedAfterWebViewPreparation(expectedProviderName, webviewPackages, 1);
+    }
+
+    private void checkCertainPackageUsedAfterWebViewPreparation(String expectedProviderName,
+            WebViewProviderInfo[] webviewPackages, int numRelros) {
+        setupWithPackages(webviewPackages, true, numRelros);
+        // Add (enabled and valid) package infos for each provider
+        setEnabledAndValidPackageInfos(webviewPackages);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(expectedProviderName)));
+
+        for (int n = 0; n < numRelros; n++) {
+            mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+        }
+
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_SUCCESS, response.status);
+        assertEquals(expectedProviderName, response.packageInfo.packageName);
+    }
+
+    // For matching the package name of a PackageInfo
+    private class IsPackageInfoWithName extends ArgumentMatcher<PackageInfo> {
+        private final String mPackageName;
+
+        IsPackageInfoWithName(String name) {
+            mPackageName = name;
+        }
+
+        @Override
+        public boolean matches(Object p) {
+            return ((PackageInfo) p).packageName.equals(mPackageName);
+        }
+
+        // Provide a more useful description in case of mismatch
+        @Override
+        public void describeTo (Description description) {
+            description.appendText(String.format("PackageInfo with name '%s'", mPackageName));
+        }
+    }
+
+    private static PackageInfo createPackageInfo(
+            String packageName, boolean enabled, boolean valid) {
+        PackageInfo p = new PackageInfo();
+        p.packageName = packageName;
+        p.applicationInfo = new ApplicationInfo();
+        p.applicationInfo.enabled = enabled;
+        p.applicationInfo.metaData = new Bundle();
+        if (valid) {
+            // no flag means invalid
+            p.applicationInfo.metaData.putString(WEBVIEW_LIBRARY_FLAG, "blah");
+        }
+        return p;
+    }
+
+    private static PackageInfo createPackageInfo(
+            String packageName, boolean enabled, boolean valid, Signature[] signatures) {
+        PackageInfo p = createPackageInfo(packageName, enabled, valid);
+        p.signatures = signatures;
+        return p;
+    }
+
+
+    // ****************
+    // Tests
+    // ****************
+
+
+    public void testWithSinglePackage() {
+        String testPackageName = "test.package.name";
+        checkCertainPackageUsedAfterWebViewPreparation(testPackageName,
+                new WebViewProviderInfo[] {
+                    new WebViewProviderInfo(testPackageName, "",
+                            true /*default available*/, false /* fallback */, null)});
+    }
+
+    public void testDefaultPackageUsedOverNonDefault() {
+        String defaultPackage = "defaultPackage";
+        String nonDefaultPackage = "nonDefaultPackage";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(nonDefaultPackage, "", false, false, null),
+            new WebViewProviderInfo(defaultPackage, "", true, false, null)};
+        checkCertainPackageUsedAfterWebViewPreparation(defaultPackage, packages);
+    }
+
+    public void testSeveralRelros() {
+        String singlePackage = "singlePackage";
+        checkCertainPackageUsedAfterWebViewPreparation(
+                singlePackage,
+                new WebViewProviderInfo[] {
+                    new WebViewProviderInfo(singlePackage, "", true /*def av*/, false, null)},
+                2);
+    }
+
+    // Ensure that package with valid signatures is chosen rather than package with invalid
+    // signatures.
+    public void testWithSignatures() {
+        String validPackage = "valid package";
+        String invalidPackage = "invalid package";
+
+        Signature validSignature = new Signature("11");
+        Signature invalidExpectedSignature = new Signature("22");
+        Signature invalidPackageSignature = new Signature("33");
+
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(invalidPackage, "", true, false, new String[]{
+                        Base64.encodeToString(
+                                invalidExpectedSignature.toByteArray(), Base64.DEFAULT)}),
+            new WebViewProviderInfo(validPackage, "", true, false, new String[]{
+                        Base64.encodeToString(
+                                validSignature.toByteArray(), Base64.DEFAULT)})
+        };
+        setupWithPackages(packages, true /* fallback logic enabled */, 1 /* numRelros */,
+                false /* isDebuggable */);
+        mTestSystemImpl.setPackageInfo(createPackageInfo(invalidPackage, true /* enabled */,
+                    true /* valid */, new Signature[]{invalidPackageSignature}));
+        mTestSystemImpl.setPackageInfo(createPackageInfo(validPackage, true /* enabled */,
+                    true /* valid */, new Signature[]{validSignature}));
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(validPackage)));
+
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_SUCCESS, response.status);
+        assertEquals(validPackage, response.packageInfo.packageName);
+
+        WebViewProviderInfo[] validPackages = mWebViewUpdateServiceImpl.getValidWebViewPackages();
+        assertEquals(1, validPackages.length);
+        assertEquals(validPackage, validPackages[0].packageName);
+    }
+
+    public void testFailWaitingForRelro() {
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo("packagename", "", true, true, null)};
+        setupWithPackages(packages);
+        setEnabledAndValidPackageInfos(packages);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(packages[0].packageName)));
+
+        // Never call notifyRelroCreation()
+
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_FAILED_WAITING_FOR_RELRO, response.status);
+    }
+
+    public void testFailListingEmptyWebviewPackages() {
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[0];
+        setupWithPackages(packages);
+        setEnabledAndValidPackageInfos(packages);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        Mockito.verify(mTestSystemImpl, Mockito.never()).onWebViewProviderChanged(
+                Matchers.anyObject());
+
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_FAILED_LISTING_WEBVIEW_PACKAGES, response.status);
+    }
+
+    public void testFailListingInvalidWebviewPackage() {
+        WebViewProviderInfo wpi = new WebViewProviderInfo("", "", true, true, null);
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {wpi};
+        setupWithPackages(packages);
+        mTestSystemImpl.setPackageInfo(createPackageInfo(wpi.packageName, true, false));
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_FAILED_LISTING_WEBVIEW_PACKAGES, response.status);
+    }
+
+    // Test that switching provider using changeProviderAndSetting works.
+    public void testSwitchingProvider() {
+        String firstPackage = "first";
+        String secondPackage = "second";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(firstPackage, "", true, false, null),
+            new WebViewProviderInfo(secondPackage, "", true, false, null)};
+        checkSwitchingProvider(packages, firstPackage, secondPackage);
+    }
+
+    public void testSwitchingProviderToNonDefault() {
+        String defaultPackage = "defaultPackage";
+        String nonDefaultPackage = "nonDefaultPackage";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(defaultPackage, "", true, false, null),
+            new WebViewProviderInfo(nonDefaultPackage, "", false, false, null)};
+        checkSwitchingProvider(packages, defaultPackage, nonDefaultPackage);
+    }
+
+    private void checkSwitchingProvider(WebViewProviderInfo[] packages, String initialPackage,
+            String finalPackage) {
+        checkCertainPackageUsedAfterWebViewPreparation(initialPackage, packages);
+
+        mWebViewUpdateServiceImpl.changeProviderAndSetting(finalPackage);
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(finalPackage)));
+
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+
+        WebViewProviderResponse secondResponse = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_SUCCESS, secondResponse.status);
+        assertEquals(finalPackage, secondResponse.packageInfo.packageName);
+
+        Mockito.verify(mTestSystemImpl).killPackageDependents(Mockito.eq(initialPackage));
+    }
+
+    // Change provider during relro creation by using changeProviderAndSetting
+    public void testSwitchingProviderDuringRelroCreation() {
+        checkChangingProviderDuringRelroCreation(true);
+    }
+
+    // Change provider during relro creation by enabling a provider
+    public void testChangingProviderThroughEnablingDuringRelroCreation() {
+        checkChangingProviderDuringRelroCreation(false);
+    }
+
+    private void checkChangingProviderDuringRelroCreation(boolean settingsChange) {
+        String firstPackage = "first";
+        String secondPackage = "second";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(firstPackage, "", true, false, null),
+            new WebViewProviderInfo(secondPackage, "", true, false, null)};
+        setupWithPackages(packages);
+        if (settingsChange) {
+            // Have all packages be enabled, so that we can change provider however we want to
+            setEnabledAndValidPackageInfos(packages);
+        } else {
+            // Have all packages be disabled so that we can change one to enabled later
+            for(WebViewProviderInfo wpi : packages) {
+                mTestSystemImpl.setPackageInfo(createPackageInfo(wpi.packageName,
+                            false /* enabled */, true /* valid */));
+            }
+        }
+
+        CountDownLatch countdown = new CountDownLatch(1);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(firstPackage)));
+
+        assertEquals(firstPackage, mWebViewUpdateServiceImpl.getCurrentWebViewPackageName());
+
+        new Thread(new Runnable() {
+            @Override
+            public void run() {
+                WebViewProviderResponse threadResponse =
+                    mWebViewUpdateServiceImpl.waitForAndGetProvider();
+                assertEquals(WebViewFactory.LIBLOAD_SUCCESS, threadResponse.status);
+                assertEquals(secondPackage, threadResponse.packageInfo.packageName);
+                // Verify that we killed the first package
+                Mockito.verify(mTestSystemImpl).killPackageDependents(Mockito.eq(firstPackage));
+                countdown.countDown();
+            }
+        }).start();
+        try {
+            Thread.sleep(1000); // Let the new thread run / be blocked
+        } catch (InterruptedException e) {
+        }
+
+        if (settingsChange) {
+            mWebViewUpdateServiceImpl.changeProviderAndSetting(secondPackage);
+        } else {
+            // Switch provider by enabling the second one
+            mTestSystemImpl.setPackageInfo(createPackageInfo(secondPackage, true /* enabled */,
+                        true /* valid */));
+            mWebViewUpdateServiceImpl.packageStateChanged(
+                    secondPackage, WebViewUpdateService.PACKAGE_CHANGED);
+        }
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+        // first package done, should start on second
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(secondPackage)));
+
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+        // second package done, the other thread should now be unblocked
+        try {
+            countdown.await();
+        } catch (InterruptedException e) {
+        }
+    }
+
+    public void testRunFallbackLogicIfEnabled() {
+        checkFallbackLogicBeingRun(true);
+    }
+
+    public void testDontRunFallbackLogicIfDisabled() {
+        checkFallbackLogicBeingRun(false);
+    }
+
+    private void checkFallbackLogicBeingRun(boolean fallbackLogicEnabled) {
+        String primaryPackage = "primary";
+        String fallbackPackage = "fallback";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(
+                    primaryPackage, "", true /* default available */, false /* fallback */, null),
+            new WebViewProviderInfo(
+                    fallbackPackage, "", true /* default available */, true /* fallback */, null)};
+        setupWithPackages(packages, fallbackLogicEnabled);
+        setEnabledAndValidPackageInfos(packages);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+        // Verify that we disable the fallback package if fallback logic enabled, and don't disable
+        // the fallback package if that logic is disabled
+        if (fallbackLogicEnabled) {
+            Mockito.verify(mTestSystemImpl).uninstallAndDisablePackageForAllUsers(
+                    Matchers.anyObject(), Mockito.eq(fallbackPackage));
+        } else {
+            Mockito.verify(mTestSystemImpl, Mockito.never()).uninstallAndDisablePackageForAllUsers(
+                    Matchers.anyObject(), Matchers.anyObject());
+        }
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(primaryPackage)));
+
+        // Enable fallback package
+        mTestSystemImpl.setPackageInfo(createPackageInfo(fallbackPackage, true /* enabled */,
+                        true /* valid */));
+        mWebViewUpdateServiceImpl.packageStateChanged(
+                fallbackPackage, WebViewUpdateService.PACKAGE_CHANGED);
+
+        if (fallbackLogicEnabled) {
+            // Check that we have now disabled the fallback package twice
+            Mockito.verify(mTestSystemImpl, Mockito.times(2)).uninstallAndDisablePackageForAllUsers(
+                    Matchers.anyObject(), Mockito.eq(fallbackPackage));
+        } else {
+            // Check that we still haven't disabled any package
+            Mockito.verify(mTestSystemImpl, Mockito.never()).uninstallAndDisablePackageForAllUsers(
+                    Matchers.anyObject(), Matchers.anyObject());
+        }
+    }
+
+    /**
+     * Scenario for installing primary package when fallback enabled.
+     * 1. Start with only fallback installed
+     * 2. Install non-fallback
+     * 3. Fallback should be disabled
+     */
+    public void testInstallingNonFallbackPackage() {
+        String primaryPackage = "primary";
+        String fallbackPackage = "fallback";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(
+                    primaryPackage, "", true /* default available */, false /* fallback */, null),
+            new WebViewProviderInfo(
+                    fallbackPackage, "", true /* default available */, true /* fallback */, null)};
+        setupWithPackages(packages, true /* isFallbackLogicEnabled */);
+        mTestSystemImpl.setPackageInfo(
+                createPackageInfo(fallbackPackage, true /* enabled */ , true /* valid */));
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+        Mockito.verify(mTestSystemImpl, Mockito.never()).uninstallAndDisablePackageForAllUsers(
+                Matchers.anyObject(), Matchers.anyObject());
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(fallbackPackage)));
+
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_SUCCESS, response.status);
+        assertEquals(fallbackPackage, response.packageInfo.packageName);
+
+        // Install primary package
+        mTestSystemImpl.setPackageInfo(
+                createPackageInfo(primaryPackage, true /* enabled */ , true /* valid */));
+        mWebViewUpdateServiceImpl.packageStateChanged(primaryPackage,
+                WebViewUpdateService.PACKAGE_ADDED);
+
+        // Verify fallback disabled and primary package used as provider
+        Mockito.verify(mTestSystemImpl).uninstallAndDisablePackageForAllUsers(
+                Matchers.anyObject(), Mockito.eq(fallbackPackage));
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(primaryPackage)));
+
+        // Finish the webview preparation and ensure primary package used and fallback killed
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+        response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_SUCCESS, response.status);
+        assertEquals(primaryPackage, response.packageInfo.packageName);
+        Mockito.verify(mTestSystemImpl).killPackageDependents(Mockito.eq(fallbackPackage));
+    }
+
+    public void testFallbackChangesEnabledState() {
+        String primaryPackage = "primary";
+        String fallbackPackage = "fallback";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(
+                    primaryPackage, "", true /* default available */, false /* fallback */, null),
+            new WebViewProviderInfo(
+                    fallbackPackage, "", true /* default available */, true /* fallback */, null)};
+        setupWithPackages(packages, true /* fallbackLogicEnabled */);
+        setEnabledAndValidPackageInfos(packages);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        // Verify fallback disabled at boot when primary package enabled
+        Mockito.verify(mTestSystemImpl).enablePackageForUser(
+                Mockito.eq(fallbackPackage), Mockito.eq(false) /* enable */,
+                Matchers.anyInt());
+
+        mTestSystemImpl.setPackageInfo(
+                createPackageInfo(primaryPackage, false /* enabled */, true /* valid */));
+        mWebViewUpdateServiceImpl.packageStateChanged(primaryPackage,
+                WebViewUpdateService.PACKAGE_CHANGED);
+
+        // Verify fallback becomes enabled when primary package becomes disabled
+        Mockito.verify(mTestSystemImpl).enablePackageForUser(
+                Mockito.eq(fallbackPackage), Mockito.eq(true) /* enable */,
+                Matchers.anyInt());
+
+        mTestSystemImpl.setPackageInfo(
+                createPackageInfo(primaryPackage, true /* enabled */, true /* valid */));
+        mWebViewUpdateServiceImpl.packageStateChanged(primaryPackage,
+                WebViewUpdateService.PACKAGE_CHANGED);
+
+        // Verify fallback is disabled a second time when primary package becomes enabled
+        Mockito.verify(mTestSystemImpl, Mockito.times(2)).enablePackageForUser(
+                Mockito.eq(fallbackPackage), Mockito.eq(false) /* enable */,
+                Matchers.anyInt());
+    }
+
+    public void testAddUserWhenFallbackLogicEnabled() {
+        checkAddingNewUser(true);
+    }
+
+    public void testAddUserWhenFallbackLogicDisabled() {
+        checkAddingNewUser(false);
+    }
+
+    public void checkAddingNewUser(boolean fallbackLogicEnabled) {
+        String primaryPackage = "primary";
+        String fallbackPackage = "fallback";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(
+                    primaryPackage, "", true /* default available */, false /* fallback */, null),
+            new WebViewProviderInfo(
+                    fallbackPackage, "", true /* default available */, true /* fallback */, null)};
+        setupWithPackages(packages, fallbackLogicEnabled);
+        setEnabledAndValidPackageInfos(packages);
+        int newUser = 100;
+        mWebViewUpdateServiceImpl.handleNewUser(newUser);
+        if (fallbackLogicEnabled) {
+            // Verify fallback package becomes disabled for new user
+            Mockito.verify(mTestSystemImpl).enablePackageForUser(
+                    Mockito.eq(fallbackPackage), Mockito.eq(false) /* enable */,
+                    Mockito.eq(newUser));
+        } else {
+            // Verify that we don't disable fallback for new user
+            Mockito.verify(mTestSystemImpl, Mockito.never()).enablePackageForUser(
+                    Mockito.anyObject(), Matchers.anyBoolean() /* enable */,
+                    Matchers.anyInt() /* user */);
+        }
+    }
+
+    /**
+     * Timing dependent test where we verify that the list of valid webview packages becoming empty
+     * at a certain point doesn't crash us or break our state.
+     */
+    public void testNotifyRelroDoesntCrashIfNoPackages() {
+        String firstPackage = "first";
+        String secondPackage = "second";
+        WebViewProviderInfo[] packages = new WebViewProviderInfo[] {
+            new WebViewProviderInfo(firstPackage, "", true /* default available */,
+                    false /* fallback */, null),
+            new WebViewProviderInfo(secondPackage, "", true /* default available */,
+                    false /* fallback */, null)};
+        setupWithPackages(packages);
+        // Add (enabled and valid) package infos for each provider
+        setEnabledAndValidPackageInfos(packages);
+
+        mWebViewUpdateServiceImpl.prepareWebViewInSystemServer();
+
+        Mockito.verify(mTestSystemImpl).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(firstPackage)));
+
+        mWebViewUpdateServiceImpl.changeProviderAndSetting(secondPackage);
+
+        // Make packages invalid to cause exception to be thrown
+        mTestSystemImpl.setPackageInfo(createPackageInfo(firstPackage, true /* enabled */,
+                    false /* valid */));
+        mTestSystemImpl.setPackageInfo(createPackageInfo(secondPackage, true /* enabled */,
+                    false /* valid */));
+
+        // This shouldn't throw an exception!
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+
+        WebViewProviderResponse response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_FAILED_LISTING_WEBVIEW_PACKAGES, response.status);
+
+        // Now make a package valid again and verify that we can switch back to that
+        mTestSystemImpl.setPackageInfo(createPackageInfo(firstPackage, true /* enabled */,
+                    true /* valid */));
+
+        mWebViewUpdateServiceImpl.packageStateChanged(firstPackage,
+                WebViewUpdateService.PACKAGE_ADDED);
+
+        // Second time we call onWebViewProviderChanged for firstPackage
+        Mockito.verify(mTestSystemImpl, Mockito.times(2)).onWebViewProviderChanged(
+                Mockito.argThat(new IsPackageInfoWithName(firstPackage)));
+
+        mWebViewUpdateServiceImpl.notifyRelroCreationCompleted();
+
+        response = mWebViewUpdateServiceImpl.waitForAndGetProvider();
+        assertEquals(WebViewFactory.LIBLOAD_SUCCESS, response.status);
+        assertEquals(firstPackage, response.packageInfo.packageName);
+    }
+
+    // TODO (gsennton) add more tests for ensuring killPackageDependents is called / not called
+}
diff --git a/services/tests/shortcutmanagerutils/Android.mk b/services/tests/shortcutmanagerutils/Android.mk
new file mode 100644
index 0000000..701e058
--- /dev/null
+++ b/services/tests/shortcutmanagerutils/Android.mk
@@ -0,0 +1,31 @@
+# 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.
+
+LOCAL_PATH:= $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_SRC_FILES := \
+    $(call all-java-files-under, src)
+
+LOCAL_STATIC_JAVA_LIBRARIES := \
+    mockito-target
+
+LOCAL_MODULE_TAGS := optional
+
+LOCAL_MODULE := ShortcutManagerTestUtils
+
+LOCAL_SDK_VERSION := current
+
+include $(BUILD_STATIC_JAVA_LIBRARY)
diff --git a/services/tests/shortcutmanagerutils/src/com/android/server/pm/shortcutmanagertest/ShortcutManagerTestUtils.java b/services/tests/shortcutmanagerutils/src/com/android/server/pm/shortcutmanagertest/ShortcutManagerTestUtils.java
new file mode 100644
index 0000000..d09b62c
--- /dev/null
+++ b/services/tests/shortcutmanagerutils/src/com/android/server/pm/shortcutmanagertest/ShortcutManagerTestUtils.java
@@ -0,0 +1,506 @@
+/*
+ * 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 com.android.server.pm.shortcutmanagertest;
+
+import static junit.framework.Assert.assertEquals;
+import static junit.framework.Assert.assertFalse;
+import static junit.framework.Assert.assertNotNull;
+import static junit.framework.Assert.assertNull;
+import static junit.framework.Assert.assertTrue;
+import static junit.framework.Assert.fail;
+
+import static org.mockito.Matchers.any;
+import static org.mockito.Matchers.anyList;
+import static org.mockito.Matchers.anyString;
+import static org.mockito.Matchers.eq;
+import static org.mockito.Mockito.reset;
+import static org.mockito.Mockito.times;
+import static org.mockito.Mockito.verify;
+
+import android.app.Instrumentation;
+import android.content.Context;
+import android.content.pm.LauncherApps;
+import android.content.pm.ShortcutInfo;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.os.BaseBundle;
+import android.os.Bundle;
+import android.os.ParcelFileDescriptor;
+import android.os.UserHandle;
+import android.test.MoreAsserts;
+import android.util.Log;
+
+import junit.framework.Assert;
+
+import org.hamcrest.BaseMatcher;
+import org.hamcrest.Description;
+import org.hamcrest.Matcher;
+import org.mockito.Mockito;
+
+import java.io.BufferedReader;
+import java.io.FileReader;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.function.BooleanSupplier;
+import java.util.function.Function;
+import java.util.function.Predicate;
+
+public class ShortcutManagerTestUtils {
+    private static final String TAG = "ShortcutManagerUtils";
+
+    private static final boolean ENABLE_DUMPSYS = true; // DO NOT SUBMIT WITH true
+
+    private static final int STANDARD_TIMEOUT_SEC = 5;
+
+    private ShortcutManagerTestUtils() {
+    }
+
+    private static List<String> readAll(ParcelFileDescriptor pfd) {
+        try {
+            try {
+                final ArrayList<String> ret = new ArrayList<>();
+                try (BufferedReader r = new BufferedReader(
+                        new FileReader(pfd.getFileDescriptor()))) {
+                    String line;
+                    while ((line = r.readLine()) != null) {
+                        ret.add(line);
+                    }
+                    r.readLine();
+                }
+                return ret;
+            } finally {
+                pfd.close();
+            }
+        } catch (IOException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    private static String concatResult(List<String> result) {
+        final StringBuilder sb = new StringBuilder();
+        for (String s : result) {
+            sb.append(s);
+            sb.append("\n");
+        }
+        return sb.toString();
+    }
+
+    private static List<String> runCommand(Instrumentation instrumentation, String command) {
+        return runCommand(instrumentation, command, null);
+    }
+    private static List<String> runCommand(Instrumentation instrumentation, String command,
+            Predicate<List<String>> resultAsserter) {
+        Log.d(TAG, "Running command: " + command);
+        final List<String> result;
+        try {
+            result = readAll(
+                    instrumentation.getUiAutomation().executeShellCommand(command));
+        } catch (Exception e) {
+            throw new RuntimeException(e);
+        }
+        if (resultAsserter != null && !resultAsserter.test(result)) {
+            fail("Command '" + command + "' failed, output was:\n" + concatResult(result));
+        }
+        return result;
+    }
+
+    private static void runCommandForNoOutput(Instrumentation instrumentation, String command) {
+        runCommand(instrumentation, command, result -> result.size() == 0);
+    }
+
+    private static List<String> runShortcutCommand(Instrumentation instrumentation, String command,
+            Predicate<List<String>> resultAsserter) {
+        return runCommand(instrumentation, "cmd shortcut " + command, resultAsserter);
+    }
+
+    public static List<String> runShortcutCommandForSuccess(Instrumentation instrumentation,
+            String command) {
+        return runShortcutCommand(instrumentation, command, result -> result.contains("Success"));
+    }
+
+    public static String getDefaultLauncher(Instrumentation instrumentation) {
+        final String PREFIX = "Launcher: ComponentInfo{";
+        final String POSTFIX = "}";
+        final List<String> result = runShortcutCommandForSuccess(
+                instrumentation, "get-default-launcher");
+        for (String s : result) {
+            if (s.startsWith(PREFIX) && s.endsWith(POSTFIX)) {
+                return s.substring(PREFIX.length(), s.length() - POSTFIX.length());
+            }
+        }
+        fail("Default launcher not found");
+        return null;
+    }
+
+    public static void setDefaultLauncher(Instrumentation instrumentation, String component) {
+        runCommandForNoOutput(instrumentation, "cmd package set-home-activity " + component);
+    }
+
+    public static void setDefaultLauncher(Instrumentation instrumentation, Context packageContext) {
+        setDefaultLauncher(instrumentation, packageContext.getPackageName()
+                + "/android.content.pm.cts.shortcutmanager.packages.Launcher");
+    }
+
+    public static void overrideConfig(Instrumentation instrumentation, String config) {
+        runShortcutCommandForSuccess(instrumentation, "override-config " + config);
+    }
+
+    public static void resetConfig(Instrumentation instrumentation) {
+        runShortcutCommandForSuccess(instrumentation, "reset-config");
+    }
+
+    public static void resetThrottling(Instrumentation instrumentation) {
+        runShortcutCommandForSuccess(instrumentation, "reset-throttling");
+    }
+
+    public static void resetAllThrottling(Instrumentation instrumentation) {
+        runShortcutCommandForSuccess(instrumentation, "reset-all-throttling");
+    }
+
+    public static void clearShortcuts(Instrumentation instrumentation, int userId,
+            String packageName) {
+        runShortcutCommandForSuccess(instrumentation, "clear-shortcuts "
+                + " --user " + userId + " " + packageName);
+    }
+
+    public static void dumpsysShortcut(Instrumentation instrumentation) {
+        if (!ENABLE_DUMPSYS) {
+            return;
+        }
+        for (String s : runCommand(instrumentation, "dumpsys shortcut")) {
+            Log.e(TAG, s);
+        }
+    }
+
+    public static Bundle makeBundle(Object... keysAndValues) {
+        assertTrue((keysAndValues.length % 2) == 0);
+
+        if (keysAndValues.length == 0) {
+            return null;
+        }
+        final Bundle ret = new Bundle();
+
+        for (int i = keysAndValues.length - 2; i >= 0; i -= 2) {
+            final String key = keysAndValues[i].toString();
+            final Object value = keysAndValues[i + 1];
+
+            if (value == null) {
+                ret.putString(key, null);
+            } else if (value instanceof Integer) {
+                ret.putInt(key, (Integer) value);
+            } else if (value instanceof String) {
+                ret.putString(key, (String) value);
+            } else if (value instanceof Bundle) {
+                ret.putBundle(key, (Bundle) value);
+            } else {
+                fail("Type not supported yet: " + value.getClass().getName());
+            }
+        }
+        return ret;
+    }
+
+    public static <T> List<T> list(T... array) {
+        return Arrays.asList(array);
+    }
+
+    public static <T> Set<T> hashSet(Set<T> in) {
+        return new HashSet<T>(in);
+    }
+
+    public static <T> Set<T> set(T... values) {
+        return set(v -> v, values);
+    }
+
+    public static <T, V> Set<T> set(Function<V, T> converter, V... values) {
+        return set(converter, Arrays.asList(values));
+    }
+
+    public static <T, V> Set<T> set(Function<V, T> converter, List<V> values) {
+        final HashSet<T> ret = new HashSet<>();
+        for (V v : values) {
+            ret.add(converter.apply(v));
+        }
+        return ret;
+    }
+
+    public static void resetAll(Collection<?> mocks) {
+        for (Object o : mocks) {
+            reset(o);
+        }
+    }
+    public static void assertExpectException(Class<? extends Throwable> expectedExceptionType,
+            String expectedExceptionMessageRegex, Runnable r) {
+        assertExpectException("", expectedExceptionType, expectedExceptionMessageRegex, r);
+    }
+
+    public static void assertDynamicShortcutCountExceeded(Runnable r) {
+        assertExpectException(IllegalArgumentException.class,
+                "Max number of dynamic shortcuts exceeded", r);
+    }
+
+    public static void assertExpectException(String message,
+            Class<? extends Throwable> expectedExceptionType,
+            String expectedExceptionMessageRegex, Runnable r) {
+        try {
+            r.run();
+            Assert.fail("Expected exception type " + expectedExceptionType.getName()
+                    + " was not thrown (message=" + message + ")");
+        } catch (Throwable e) {
+            Assert.assertTrue(
+                    "Expected exception type was " + expectedExceptionType.getName()
+                            + " but caught " + e + " (message=" + message + ")",
+                    expectedExceptionType.isAssignableFrom(e.getClass()));
+            if (expectedExceptionMessageRegex != null) {
+                MoreAsserts.assertContainsRegex(expectedExceptionMessageRegex, e.getMessage());
+            }
+        }
+    }
+
+    public static List<ShortcutInfo> assertShortcutIds(List<ShortcutInfo> actualShortcuts,
+            String... expectedIds) {
+        final HashSet<String> expected = new HashSet<>(list(expectedIds));
+        final HashSet<String> actual = new HashSet<>();
+        for (ShortcutInfo s : actualShortcuts) {
+            actual.add(s.getId());
+        }
+
+        // Compare the sets.
+        assertEquals(expected, actual);
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllHaveIntents(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertNotNull("ID " + s.getId(), s.getIntent());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllNotHaveIntents(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertNull("ID " + s.getId(), s.getIntent());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllHaveTitle(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertNotNull("ID " + s.getId(), s.getTitle());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllNotHaveTitle(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertNull("ID " + s.getId(), s.getTitle());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllHaveIconResId(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertTrue("ID " + s.getId() + " not have icon res ID", s.hasIconResource());
+            assertFalse("ID " + s.getId() + " shouldn't have icon FD", s.hasIconFile());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllHaveIconFile(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertFalse("ID " + s.getId() + " shouldn't have icon res ID", s.hasIconResource());
+            assertTrue("ID " + s.getId() + " not have icon FD", s.hasIconFile());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllHaveIcon(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertTrue("ID " + s.getId() + " has no icon ", s.hasIconFile() || s.hasIconResource());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllKeyFieldsOnly(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertTrue("ID " + s.getId(), s.hasKeyFieldsOnly());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllNotKeyFieldsOnly(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertFalse("ID " + s.getId(), s.hasKeyFieldsOnly());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllDynamic(List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertTrue("ID " + s.getId(), s.isDynamic());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllPinned(List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertTrue("ID " + s.getId(), s.isPinned());
+        }
+        return actualShortcuts;
+    }
+
+    public static List<ShortcutInfo> assertAllDynamicOrPinned(
+            List<ShortcutInfo> actualShortcuts) {
+        for (ShortcutInfo s : actualShortcuts) {
+            assertTrue("ID " + s.getId(), s.isDynamic() || s.isPinned());
+        }
+        return actualShortcuts;
+    }
+
+    public static void assertDynamicOnly(ShortcutInfo si) {
+        assertTrue(si.isDynamic());
+        assertFalse(si.isPinned());
+    }
+
+    public static void assertPinnedOnly(ShortcutInfo si) {
+        assertFalse(si.isDynamic());
+        assertTrue(si.isPinned());
+    }
+
+    public static void assertDynamicAndPinned(ShortcutInfo si) {
+        assertTrue(si.isDynamic());
+        assertTrue(si.isPinned());
+    }
+
+    public static void assertBitmapSize(int expectedWidth, int expectedHeight, Bitmap bitmap) {
+        assertEquals("width", expectedWidth, bitmap.getWidth());
+        assertEquals("height", expectedHeight, bitmap.getHeight());
+    }
+
+    public static <T> void assertAllUnique(Collection<T> list) {
+        final Set<Object> set = new HashSet<>();
+        for (T item : list) {
+            if (set.contains(item)) {
+                fail("Duplicate item found: " + item + " (in the list: " + list + ")");
+            }
+            set.add(item);
+        }
+    }
+
+    public static Bitmap pfdToBitmap(ParcelFileDescriptor pfd) {
+        assertNotNull(pfd);
+        try {
+            try {
+                return BitmapFactory.decodeFileDescriptor(pfd.getFileDescriptor());
+            } finally {
+                pfd.close();
+            }
+        } catch (IOException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    public static void assertBundleEmpty(BaseBundle b) {
+        assertTrue(b == null || b.size() == 0);
+    }
+
+    public static void assertCallbackNotReceived(LauncherApps.Callback mock) {
+        verify(mock, times(0)).onShortcutsChanged(anyString(), anyList(),
+                any(UserHandle.class));
+    }
+
+    public static void assertCallbackReceived(LauncherApps.Callback mock,
+            UserHandle user, String packageName, String... ids) {
+        verify(mock).onShortcutsChanged(eq(packageName), checkShortcutIds(ids),
+                eq(user));
+    }
+
+    public static boolean checkAssertSuccess(Runnable r) {
+        try {
+            r.run();
+            return true;
+        } catch (AssertionError e) {
+            return false;
+        }
+    }
+
+    public static <T> T checkArgument(Predicate<T> checker, String description,
+            List<T> matchedCaptor) {
+        final Matcher<T> m = new BaseMatcher<T>() {
+            @Override
+            public boolean matches(Object item) {
+                if (item == null) {
+                    return false;
+                }
+                final T value = (T) item;
+                if (!checker.test(value)) {
+                    return false;
+                }
+
+                if (matchedCaptor != null) {
+                    matchedCaptor.add(value);
+                }
+                return true;
+            }
+
+            @Override
+            public void describeTo(Description d) {
+                d.appendText(description);
+            }
+        };
+        return Mockito.argThat(m);
+    }
+
+    public static List<ShortcutInfo> checkShortcutIds(String... ids) {
+        return checkArgument((List<ShortcutInfo> list) -> {
+            final Set<String> actualSet = set(si -> si.getId(), list);
+            return actualSet.equals(set(ids));
+
+        }, "Shortcut IDs=[" + Arrays.toString(ids) + "]", null);
+    }
+
+    public static void waitUntil(String message, BooleanSupplier condition) {
+        waitUntil(message, condition, STANDARD_TIMEOUT_SEC);
+    }
+
+    public static void waitUntil(String message, BooleanSupplier condition, int timeoutSeconds) {
+        final long timeout = System.currentTimeMillis() + (timeoutSeconds * 1000L);
+        while (System.currentTimeMillis() < timeout) {
+            if (condition.getAsBoolean()) {
+                return;
+            }
+            try {
+                Thread.sleep(100);
+            } catch (InterruptedException e) {
+                throw new RuntimeException(e);
+            }
+        }
+        fail("Timed out for: " + message);
+    }
+}
diff --git a/services/usage/java/com/android/server/usage/UsageStatsService.java b/services/usage/java/com/android/server/usage/UsageStatsService.java
index 0aeb96f..ecfeff9 100644
--- a/services/usage/java/com/android/server/usage/UsageStatsService.java
+++ b/services/usage/java/com/android/server/usage/UsageStatsService.java
@@ -152,6 +152,7 @@
     private ArrayList<UsageStatsManagerInternal.AppIdleStateChangeListener>
             mPackageAccessListeners = new ArrayList<>();
 
+    private boolean mHaveCarrierPrivilegedApps;
     private List<String> mCarrierPrivilegedApps;
 
     public UsageStatsService(Context context) {
@@ -931,11 +932,14 @@
 
     private boolean isCarrierApp(String packageName) {
         synchronized (mLock) {
-            if (mCarrierPrivilegedApps == null) {
+            if (!mHaveCarrierPrivilegedApps) {
                 fetchCarrierPrivilegedAppsLocked();
             }
+            if (mCarrierPrivilegedApps != null) {
+                return mCarrierPrivilegedApps.contains(packageName);
+            }
+            return false;
         }
-        return mCarrierPrivilegedApps.contains(packageName);
     }
 
     void clearCarrierPrivilegedApps() {
@@ -943,6 +947,7 @@
             Slog.i(TAG, "Clearing carrier privileged apps list");
         }
         synchronized (mLock) {
+            mHaveCarrierPrivilegedApps = false;
             mCarrierPrivilegedApps = null; // Need to be refetched.
         }
     }
@@ -951,6 +956,7 @@
         TelephonyManager telephonyManager =
                 getContext().getSystemService(TelephonyManager.class);
         mCarrierPrivilegedApps = telephonyManager.getPackagesWithCarrierPrivileges();
+        mHaveCarrierPrivilegedApps = true;
         if (DEBUG) {
             Slog.d(TAG, "apps with carrier privilege " + mCarrierPrivilegedApps);
         }
@@ -1024,7 +1030,8 @@
             }
 
             pw.println();
-            pw.println("Carrier privileged apps: " + mCarrierPrivilegedApps);
+            pw.println("Carrier privileged apps (have=" + mHaveCarrierPrivilegedApps
+                    + "): " + mCarrierPrivilegedApps);
 
             pw.println();
             pw.println("Settings:");
diff --git a/services/voiceinteraction/java/com/android/server/soundtrigger/SoundTriggerHelper.java b/services/voiceinteraction/java/com/android/server/soundtrigger/SoundTriggerHelper.java
index 40687b0..f13e019 100644
--- a/services/voiceinteraction/java/com/android/server/soundtrigger/SoundTriggerHelper.java
+++ b/services/voiceinteraction/java/com/android/server/soundtrigger/SoundTriggerHelper.java
@@ -41,6 +41,7 @@
 import android.telephony.PhoneStateListener;
 import android.telephony.TelephonyManager;
 import android.util.Slog;
+import com.android.internal.logging.MetricsLogger;
 
 import java.io.FileDescriptor;
 import java.io.PrintWriter;
@@ -56,7 +57,6 @@
  * (ii) Generic sound-trigger models: Supports multiple of these.
  *
  * Currently this just acts as an abstraction over all SoundTrigger API calls.
- *
  * @hide
  */
 public class SoundTriggerHelper implements SoundTrigger.StatusListener {
@@ -84,25 +84,23 @@
     private final PhoneStateListener mPhoneStateListener;
     private final PowerManager mPowerManager;
 
-    // TODO: Since the voice layer currently only handles one recognition
-    // we simplify things by assuming one listener here too.
-    private IRecognitionStatusCallback mKeyphraseListener;
-
     // The SoundTriggerManager layer handles multiple generic recognition models. We store the
     // ModelData here in a hashmap.
     private final HashMap<UUID, ModelData> mGenericModelDataMap;
 
-    // Note: KeyphraseId is not really used.
+    // This ModelData instance ensures that the keyphrase sound model is a singleton and
+    // all other sound models are of type Generic. Any keyphrase sound model will be stored here
+    // and any previously running instances will be replaced. This restriction was earlier
+    // implemented by three instance variables which stored data about the keyphrase
+    // model. That data now gets encapsulated in this ModelData instance.
+    private ModelData mKeyphraseModelData;
+
+    // The keyphrase ID for keyphrase sound models. We store this specially here since ModelData
+    // does not support this.
+    // TODO: The role of the keyphrase ID is a bit unclear. Its just used to ensure that
+    // recognition events have the correct keyphrase ID check.
     private int mKeyphraseId = INVALID_VALUE;
 
-    // Current voice sound model handle. We only allow one voice model to run at any given time.
-    private int mCurrentKeyphraseModelHandle = INVALID_VALUE;
-    private KeyphraseSoundModel mCurrentSoundModel = null;
-    // FIXME: Ideally this should not be stored if allowMultipleTriggers happens at a lower layer.
-    private RecognitionConfig mRecognitionConfig = null;
-
-    // Whether we are requesting recognition to start.
-    private boolean mRequested = false;
     private boolean mCallActive = false;
     private boolean mIsPowerSaveMode = false;
     // Indicates if the native sound trigger service is disabled or not.
@@ -112,8 +110,6 @@
     // Whether we have ANY recognition (keyphrase or generic) running.
     private boolean mRecognitionRunning = false;
 
-    // Keeps track of whether the keyphrase recognition is running.
-    private boolean mKeyphraseStarted = false;
     private boolean mRecognitionAborted = false;
     private PowerSaveModeListener mPowerSaveModeListener;
 
@@ -136,26 +132,89 @@
     }
 
     /**
-     * Starts recognition for the given generic sound model ID.
+     * Starts recognition for the given generic sound model ID. This is a wrapper around {@link
+     * startRecognition()}.
      *
-     * @param soundModel The sound model to use for recognition.
-     * @param listener The listener for the recognition events related to the given keyphrase.
+     * @param modelId UUID of the sound model.
+     * @param soundModel The generic sound model to use for recognition.
+     * @param callback Callack for the recognition events related to the given keyphrase.
+     * @param recognitionConfig Instance of RecognitionConfig containing the parameters for the
+     * recognition.
      * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
      */
     int startGenericRecognition(UUID modelId, GenericSoundModel soundModel,
             IRecognitionStatusCallback callback, RecognitionConfig recognitionConfig) {
-        if (soundModel == null || callback == null || recognitionConfig == null) {
+        MetricsLogger.count(mContext, "sth_start_recognition", 1);
+        if (modelId == null || soundModel == null || callback == null ||
+                recognitionConfig == null) {
             Slog.w(TAG, "Passed in bad data to startGenericRecognition().");
             return STATUS_ERROR;
         }
 
         synchronized (mLock) {
+            ModelData modelData = getOrCreateGenericModelDataLocked(modelId);
+            return startRecognition(soundModel, modelData, callback, recognitionConfig,
+                    INVALID_VALUE /* keyphraseId */);
+        }
+    }
 
+    /**
+     * Starts recognition for the given keyphraseId.
+     *
+     * @param keyphraseId The identifier of the keyphrase for which
+     *        the recognition is to be started.
+     * @param soundModel The sound model to use for recognition.
+     * @param callback The callback for the recognition events related to the given keyphrase.
+     * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
+     */
+    int startKeyphraseRecognition(int keyphraseId, KeyphraseSoundModel soundModel,
+            IRecognitionStatusCallback callback, RecognitionConfig recognitionConfig) {
+        synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_start_recognition", 1);
+            if (soundModel == null || callback == null || recognitionConfig == null) {
+                return STATUS_ERROR;
+            }
+
+            if (DBG) {
+                Slog.d(TAG, "startKeyphraseRecognition for keyphraseId=" + keyphraseId
+                        + " soundModel=" + soundModel + ", callback=" + callback.asBinder()
+                        + ", recognitionConfig=" + recognitionConfig);
+                Slog.d(TAG, "moduleProperties=" + mModuleProperties);
+                if (mKeyphraseModelData != null) {
+                    Slog.d(TAG, mKeyphraseModelData.toString());
+                } else {
+                    Slog.d(TAG, "Null KeyphraseModelData.");
+                }
+            }
+            if (mKeyphraseModelData == null) {
+                mKeyphraseModelData = ModelData.createKeyphraseModelData(soundModel.uuid);
+            }
+            return startRecognition(soundModel, mKeyphraseModelData, callback, recognitionConfig,
+                    keyphraseId);
+        }
+    }
+
+    /**
+     * Starts recognition for the given sound model. A single routine for both keyphrase and
+     * generic sound models.
+     *
+     * @param soundModel The sound model to use for recognition.
+     * @param modelData Instance of {@link #ModelData} for the given model.
+     * @param callback Callback for the recognition events related to the given keyphrase.
+     * @param recognitionConfig Instance of {@link RecognitionConfig} containing the parameters
+     * @param keyphraseId Keyphrase ID for keyphrase models only. Pass in INVALID_VALUE for other
+     * models.
+     * for the recognition.
+     * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
+     */
+    int startRecognition(SoundModel soundModel, ModelData modelData,
+            IRecognitionStatusCallback callback, RecognitionConfig recognitionConfig,
+            int keyphraseId) {
+        synchronized (mLock) {
             if (mModuleProperties == null) {
                 Slog.w(TAG, "Attempting startRecognition without the capability");
                 return STATUS_ERROR;
             }
-
             if (mModule == null) {
                 mModule = SoundTrigger.attachModule(mModuleProperties.id, this, null);
                 if (mModule == null) {
@@ -169,13 +228,43 @@
                 initializeTelephonyAndPowerStateListeners();
             }
 
-            // Fetch a ModelData instance from the hash map. Creates a new one if none
-            // exists.
-            ModelData modelData = getOrCreateGenericModelDataLocked(modelId);
+            // If the previous model is different (for the same UUID), ensure that its unloaded
+            // and stopped before proceeding. This works for both keyphrase and generic models.
+            // Specifically for keyphrase since we have 'mKeyphraseModelData' holding a single
+            // allowed instance of such a model, this ensures that a previously loaded (or started)
+            // keyphrase model is appropriately stopped. This ensures no regression with the
+            // previous version of this code as given in the startKeyphrase() routine.
+            //
+            // For generic sound models, all this means is that if we are given a different sound
+            // model with the same UUID, then we will "replace" it.
+            if (modelData.getSoundModel() != null) {
+                boolean stopModel = false; // Stop the model after checking that its started.
+                boolean unloadModel = false;
+                if (modelData.getSoundModel().equals(soundModel) && modelData.isModelStarted()) {
+                    // The model has not changed, but the previous model is "started".
+                    // Stop the previously running model.
+                    stopModel = true;
+                    unloadModel = false; // No need to unload if the model hasn't changed.
+                } else if (!modelData.getSoundModel().equals(soundModel)) {
+                    // We have a different model for this UUID. Stop and unload if needed. This
+                    // helps maintain the singleton restriction for keyphrase sound models.
+                    stopModel = modelData.isModelStarted();
+                    unloadModel = modelData.isModelLoaded();
+                }
+                if (stopModel || unloadModel) {
+                    int status = tryStopAndUnloadLocked(modelData, stopModel, unloadModel);
+                    if (status != STATUS_OK) {
+                        Slog.w(TAG, "Unable to stop or unload previous model: " +
+                                modelData.toString());
+                        return status;
+                    }
+                }
+            }
 
             IRecognitionStatusCallback oldCallback = modelData.getCallback();
-            if (oldCallback != null) {
-                Slog.w(TAG, "Canceling previous recognition for model id: " + modelId);
+            if (oldCallback != null && oldCallback.asBinder() != callback.asBinder()) {
+                Slog.w(TAG, "Canceling previous recognition for model id: " +
+                        modelData.getModelId());
                 try {
                     oldCallback.onError(STATUS_ERROR);
                 } catch (RemoteException e) {
@@ -199,182 +288,49 @@
                 }
                 modelData.setHandle(handle[0]);
                 modelData.setLoaded();
-                Slog.d(TAG, "Generic sound model loaded with handle:" + handle[0]);
+                Slog.d(TAG, "Sound model loaded with handle:" + handle[0]);
             }
             modelData.setCallback(callback);
+            if (modelData.isKeyphraseModel()) {
+                mKeyphraseId = keyphraseId;
+            }
+            modelData.setRequested(true);
             modelData.setRecognitionConfig(recognitionConfig);
+            modelData.setSoundModel(soundModel);
 
-            // Don't notify for synchronous calls.
-            return startGenericRecognitionLocked(modelData, false);
+            return startRecognitionLocked(modelData,
+                    false /* Don't notify for synchronous calls */);
         }
     }
 
     /**
-     * Starts recognition for the given keyphraseId.
-     *
-     * @param keyphraseId The identifier of the keyphrase for which
-     *        the recognition is to be started.
-     * @param soundModel The sound model to use for recognition.
-     * @param listener The listener for the recognition events related to the given keyphrase.
-     * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
-     */
-    int startKeyphraseRecognition(int keyphraseId,
-            KeyphraseSoundModel soundModel,
-            IRecognitionStatusCallback listener,
-            RecognitionConfig recognitionConfig) {
-        if (soundModel == null || listener == null || recognitionConfig == null) {
-            return STATUS_ERROR;
-        }
-
-        synchronized (mLock) {
-            if (DBG) {
-                Slog.d(TAG, "startKeyphraseRecognition for keyphraseId=" + keyphraseId
-                        + " soundModel=" + soundModel + ", listener=" + listener.asBinder()
-                        + ", recognitionConfig=" + recognitionConfig);
-                Slog.d(TAG, "moduleProperties=" + mModuleProperties);
-                Slog.d(TAG, "current listener="
-                        + (mKeyphraseListener == null ? "null" : mKeyphraseListener.asBinder()));
-                Slog.d(TAG, "current SoundModel handle=" + mCurrentKeyphraseModelHandle);
-                Slog.d(TAG, "current SoundModel UUID="
-                        + (mCurrentSoundModel == null ? null : mCurrentSoundModel.uuid));
-            }
-
-            if (!mRecognitionRunning) {
-                initializeTelephonyAndPowerStateListeners();
-            }
-
-            if (mModuleProperties == null) {
-                Slog.w(TAG, "Attempting startKeyphraseRecognition without the capability");
-                return STATUS_ERROR;
-            }
-            if (mModule == null) {
-                mModule = SoundTrigger.attachModule(mModuleProperties.id, this, null);
-                if (mModule == null) {
-                    Slog.w(TAG, "startKeyphraseRecognition cannot attach to sound trigger module");
-                    return STATUS_ERROR;
-                }
-            }
-
-            // Unload the previous model if the current one isn't invalid
-            // and, it's not the same as the new one.
-            // This helps use cache and reuse the model and just start/stop it when necessary.
-            if (mCurrentKeyphraseModelHandle != INVALID_VALUE
-                    && !soundModel.equals(mCurrentSoundModel)) {
-                Slog.w(TAG, "Unloading previous sound model");
-                int status = mModule.unloadSoundModel(mCurrentKeyphraseModelHandle);
-                if (status != SoundTrigger.STATUS_OK) {
-                    Slog.w(TAG, "unloadSoundModel call failed with " + status);
-                }
-                internalClearKeyphraseSoundModelLocked();
-                mKeyphraseStarted = false;
-            }
-
-            // If the previous recognition was by a different listener,
-            // Notify them that it was stopped.
-            if (mKeyphraseListener != null && mKeyphraseListener.asBinder() != listener.asBinder()) {
-                Slog.w(TAG, "Canceling previous recognition");
-                try {
-                    mKeyphraseListener.onError(STATUS_ERROR);
-                } catch (RemoteException e) {
-                    Slog.w(TAG, "RemoteException in onDetectionStopped", e);
-                }
-                mKeyphraseListener = null;
-            }
-
-            // Load the sound model if the current one is null.
-            int soundModelHandle = mCurrentKeyphraseModelHandle;
-            if (mCurrentKeyphraseModelHandle == INVALID_VALUE
-                    || mCurrentSoundModel == null) {
-                int[] handle = new int[] { INVALID_VALUE };
-                int status = mModule.loadSoundModel(soundModel, handle);
-                if (status != SoundTrigger.STATUS_OK) {
-                    Slog.w(TAG, "loadSoundModel call failed with " + status);
-                    return status;
-                }
-                if (handle[0] == INVALID_VALUE) {
-                    Slog.w(TAG, "loadSoundModel call returned invalid sound model handle");
-                    return STATUS_ERROR;
-                }
-                soundModelHandle = handle[0];
-            } else {
-                if (DBG) Slog.d(TAG, "Reusing previously loaded sound model");
-            }
-
-            // Start the recognition.
-            mRequested = true;
-            mKeyphraseId = keyphraseId;
-            mCurrentKeyphraseModelHandle = soundModelHandle;
-            mCurrentSoundModel = soundModel;
-            mRecognitionConfig = recognitionConfig;
-            // Register the new listener. This replaces the old one.
-            // There can only be a maximum of one active listener at any given time.
-            mKeyphraseListener = listener;
-
-            return updateRecognitionLocked(false /* don't notify for synchronous calls */);
-        }
-    }
-
-    /**
-     * Stops recognition for the given generic sound model.
+     * Stops recognition for the given generic sound model. This is a wrapper for {@link
+     * #stopRecognition}.
      *
      * @param modelId The identifier of the generic sound model for which
      *        the recognition is to be stopped.
-     * @param listener The listener for the recognition events related to the given sound model.
+     * @param callback The callback for the recognition events related to the given sound model.
      *
      * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
      */
-    int stopGenericRecognition(UUID modelId, IRecognitionStatusCallback listener) {
-        if (listener == null) {
-            return STATUS_ERROR;
-        }
-
+    int stopGenericRecognition(UUID modelId, IRecognitionStatusCallback callback) {
         synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_stop_recognition", 1);
+            if (callback == null || modelId == null) {
+                Slog.e(TAG, "Null callbackreceived for stopGenericRecognition() for modelid:" +
+                        modelId);
+                return STATUS_ERROR;
+            }
+
             ModelData modelData = mGenericModelDataMap.get(modelId);
             if (modelData == null) {
                 Slog.w(TAG, "Attempting stopRecognition on invalid model with id:" + modelId);
                 return STATUS_ERROR;
             }
 
-            IRecognitionStatusCallback currentCallback = modelData.getCallback();
-            if (DBG) {
-                Slog.d(TAG, "stopRecognition for modelId=" + modelId
-                        + ", listener=" + listener.asBinder());
-                Slog.d(TAG, "current callback ="
-                        + (currentCallback == null ? "null" : currentCallback.asBinder()));
-            }
-
-            if (mModuleProperties == null || mModule == null) {
-                Slog.w(TAG, "Attempting stopRecognition without the capability");
-                return STATUS_ERROR;
-            }
-
-            if (currentCallback == null || !modelData.isModelStarted()) {
-                // startGenericRecognition hasn't been called or it failed.
-                Slog.w(TAG, "Attempting stopGenericRecognition without a successful" +
-                        " startGenericRecognition");
-                return STATUS_ERROR;
-            }
-            if (currentCallback.asBinder() != listener.asBinder()) {
-                // We don't allow a different listener to stop the recognition than the one
-                // that started it.
-                Slog.w(TAG, "Attempting stopGenericRecognition for another recognition");
-                return STATUS_ERROR;
-            }
-
-            int status = stopGenericRecognitionLocked(modelData,
-                    false /* don't notify for synchronous calls */);
+            int status = stopRecognition(modelData, callback);
             if (status != SoundTrigger.STATUS_OK) {
                 Slog.w(TAG, "stopGenericRecognition failed: " + status);
-                return status;
-            }
-
-            // We leave the sound model loaded but not started, this helps us when we start
-            // back.
-            // Also clear the internal state once the recognition has been stopped.
-            modelData.setLoaded();
-            modelData.clearCallback();
-            if (!computeRecognitionRunningLocked()) {
-                internalClearGlobalStateLocked();
             }
             return status;
         }
@@ -382,47 +338,30 @@
 
     /**
      * Stops recognition for the given {@link Keyphrase} if a recognition is
-     * currently active.
+     * currently active. This is a wrapper for {@link #stopRecognition()}.
      *
      * @param keyphraseId The identifier of the keyphrase for which
      *        the recognition is to be stopped.
-     * @param listener The listener for the recognition events related to the given keyphrase.
+     * @param callback The callback for the recognition events related to the given keyphrase.
      *
      * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
      */
-    int stopKeyphraseRecognition(int keyphraseId, IRecognitionStatusCallback listener) {
-        if (listener == null) {
-            return STATUS_ERROR;
-        }
-
+    int stopKeyphraseRecognition(int keyphraseId, IRecognitionStatusCallback callback) {
         synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_stop_recognition", 1);
+            if (callback == null) {
+                Slog.e(TAG, "Null callback received for stopKeyphraseRecognition() for keyphraseId:" +
+                        keyphraseId);
+                return STATUS_ERROR;
+            }
+
             if (DBG) {
-                Slog.d(TAG, "stopRecognition for keyphraseId=" + keyphraseId
-                        + ", listener=" + listener.asBinder());
-                Slog.d(TAG, "current listener="
-                        + (mKeyphraseListener == null ? "null" : mKeyphraseListener.asBinder()));
+                Slog.d(TAG, "stopRecognition for keyphraseId=" + keyphraseId + ", callback =" +
+                        callback.asBinder());
+                Slog.d(TAG, "current callback=" + (mKeyphraseModelData == null ? "null" :
+                            mKeyphraseModelData.getCallback().asBinder()));
             }
-
-            if (mModuleProperties == null || mModule == null) {
-                Slog.w(TAG, "Attempting stopRecognition without the capability");
-                return STATUS_ERROR;
-            }
-
-            if (mKeyphraseListener == null) {
-                // startRecognition hasn't been called or it failed.
-                Slog.w(TAG, "Attempting stopRecognition without a successful startRecognition");
-                return STATUS_ERROR;
-            }
-            if (mKeyphraseListener.asBinder() != listener.asBinder()) {
-                // We don't allow a different listener to stop the recognition than the one
-                // that started it.
-                Slog.w(TAG, "Attempting stopRecognition for another recognition");
-                return STATUS_ERROR;
-            }
-
-            // Stop recognition if it's the current one, ignore otherwise.
-            mRequested = false;
-            int status = updateRecognitionLocked(false /* don't notify for synchronous calls */);
+            int status = stopRecognition(mKeyphraseModelData, callback);
             if (status != SoundTrigger.STATUS_OK) {
                 return status;
             }
@@ -431,25 +370,115 @@
             // back.
             // Also clear the internal state once the recognition has been stopped.
             internalClearKeyphraseStateLocked();
-            internalClearGlobalStateLocked();
             return status;
         }
     }
 
     /**
+     * Stops recognition for the given ModelData instance.
+     *
+     * @param modelData Instance of {@link #ModelData} sound model.
+     * @param callback The callback for the recognition events related to the given keyphrase.
+     * @return One of {@link #STATUS_ERROR} or {@link #STATUS_OK}.
+     */
+    private int stopRecognition(ModelData modelData, IRecognitionStatusCallback callback) {
+        synchronized (mLock) {
+            if (callback == null) {
+                return STATUS_ERROR;
+            }
+            if (mModuleProperties == null || mModule == null) {
+                Slog.w(TAG, "Attempting stopRecognition without the capability");
+                return STATUS_ERROR;
+            }
+
+            IRecognitionStatusCallback currentCallback = modelData.getCallback();
+            if (modelData == null || currentCallback == null || !modelData.isModelStarted()) {
+                // startGenericRecognition hasn't been called or it failed.
+                Slog.w(TAG, "Attempting stopGenericRecognition without a successful" +
+                        " startGenericRecognition");
+                return STATUS_ERROR;
+            }
+
+            if (currentCallback.asBinder() != callback.asBinder()) {
+                // We don't allow a different listener to stop the recognition than the one
+                // that started it.
+                Slog.w(TAG, "Attempting stopRecognition for another recognition");
+                return STATUS_ERROR;
+            }
+
+            // Request stop recognition via the update() method.
+            modelData.setRequested(false);
+            int status = updateRecognitionLocked(modelData, isRecognitionAllowed(),
+                    false /* don't notify for synchronous calls */);
+            if (status != SoundTrigger.STATUS_OK) {
+                return status;
+            }
+
+            // We leave the sound model loaded but not started, this helps us when we start back.
+            // Also clear the internal state once the recognition has been stopped.
+            modelData.setLoaded();
+            modelData.clearCallback();
+            modelData.setRecognitionConfig(null);
+
+            if (!computeRecognitionRunningLocked()) {
+                internalClearGlobalStateLocked();
+            }
+
+            if (modelData.isKeyphraseModel()) {
+                mKeyphraseId = INVALID_VALUE;
+            }
+            return status;
+        }
+    }
+
+    // Stop a previously started model if it was started. Optionally, unload if the previous model
+    // is stale and is about to be replaced.
+    // Needs to be called with the mLock held.
+    private int tryStopAndUnloadLocked(ModelData modelData, boolean stopModel,
+            boolean unloadModel) {
+        int status = STATUS_OK;
+        if (modelData.isModelNotLoaded()) {
+            return status;
+        }
+        if (stopModel && modelData.isModelStarted()) {
+            status = stopRecognitionLocked(modelData,
+                    false /* don't notify for synchronous calls */);
+            if (status != SoundTrigger.STATUS_OK) {
+                Slog.w(TAG, "stopRecognition failed: " + status);
+                return status;
+            }
+        }
+
+        if (unloadModel && modelData.isModelLoaded()) {
+            Slog.d(TAG, "Unloading previously loaded stale model.");
+            status = mModule.unloadSoundModel(modelData.getHandle());
+            MetricsLogger.count(mContext, "sth_unloading_stale_model", 1);
+            if (status != SoundTrigger.STATUS_OK) {
+                Slog.w(TAG, "unloadSoundModel call failed with " + status);
+            } else {
+                // Clear the ModelData state if successful.
+                modelData.clearState();
+                modelData.clearCallback();
+                modelData.setRecognitionConfig(null);
+            }
+        }
+        return status;
+    }
+
+    /**
      * Stops all recognitions active currently and clears the internal state.
      */
     void stopAllRecognitions() {
         synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_stop_all_recognitions", 1);
             if (mModuleProperties == null || mModule == null) {
                 return;
             }
 
             // Stop Keyphrase recognition if one exists.
-            if (mCurrentKeyphraseModelHandle != INVALID_VALUE) {
-
-                mRequested = false;
-                int status = updateRecognitionLocked(
+            if (mKeyphraseModelData != null && mKeyphraseModelData.getHandle() != INVALID_VALUE) {
+                mKeyphraseModelData.setRequested(false);
+                int status = updateRecognitionLocked(mKeyphraseModelData, isRecognitionAllowed(),
                         false /* don't notify for synchronous calls */);
                 internalClearKeyphraseStateLocked();
             }
@@ -457,7 +486,7 @@
             // Stop all generic recognition models.
             for (ModelData model : mGenericModelDataMap.values()) {
                 if (model.isModelStarted()) {
-                    int status = stopGenericRecognitionLocked(model,
+                    int status = stopRecognitionLocked(model,
                             false /* do not notify for synchronous calls */);
                     if (status != STATUS_OK) {
                         // What else can we do if there is an error here.
@@ -476,39 +505,40 @@
     }
 
     int unloadKeyphraseSoundModel(int keyphraseId) {
-        if (mModule == null || mCurrentKeyphraseModelHandle == INVALID_VALUE) {
-            return STATUS_ERROR;
-        }
-        if (mKeyphraseId != keyphraseId) {
-            Slog.w(TAG, "Given sound model is not the one loaded.");
-            return STATUS_ERROR;
-        }
-
         synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_unload_keyphrase_sound_model", 1);
+            if (mModule == null || mKeyphraseModelData == null ||
+                    mKeyphraseModelData.getHandle() == INVALID_VALUE) {
+                return STATUS_ERROR;
+            }
+
             // Stop recognition if it's the current one.
-            mRequested = false;
-            int status = updateRecognitionLocked(false /* don't notify */);
+            mKeyphraseModelData.setRequested(false);
+            int status = updateRecognitionLocked(mKeyphraseModelData, isRecognitionAllowed(),
+                    false /* don't notify */);
             if (status != SoundTrigger.STATUS_OK) {
                 Slog.w(TAG, "Stop recognition failed for keyphrase ID:" + status);
             }
 
-            status = mModule.unloadSoundModel(mCurrentKeyphraseModelHandle);
+            status = mModule.unloadSoundModel(mKeyphraseModelData.getHandle());
             if (status != SoundTrigger.STATUS_OK) {
                 Slog.w(TAG, "unloadKeyphraseSoundModel call failed with " + status);
             }
-            internalClearKeyphraseSoundModelLocked();
+            mKeyphraseModelData.clearState();
             return status;
         }
     }
 
     int unloadGenericSoundModel(UUID modelId) {
-        if (modelId == null || mModule == null) {
-            return STATUS_ERROR;
-        }
         synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_unload_generic_sound_model", 1);
+            if (modelId == null || mModule == null) {
+                return STATUS_ERROR;
+            }
             ModelData modelData = mGenericModelDataMap.get(modelId);
             if (modelData == null) {
-                Slog.w(TAG, "Unload error: Attempting unload invalid generic model with id:" + modelId);
+                Slog.w(TAG, "Unload error: Attempting unload invalid generic model with id:" +
+                        modelId);
                 return STATUS_ERROR;
             }
             if (!modelData.isModelLoaded()) {
@@ -517,7 +547,7 @@
                 return STATUS_OK;
             }
             if (modelData.isModelStarted()) {
-                int status = stopGenericRecognitionLocked(modelData,
+                int status = stopRecognitionLocked(modelData,
                         false /* don't notify for synchronous calls */);
                 if (status != SoundTrigger.STATUS_OK) {
                     Slog.w(TAG, "stopGenericRecognition failed: " + status);
@@ -577,6 +607,7 @@
     }
 
     private void onGenericRecognitionSuccessLocked(GenericRecognitionEvent event) {
+        MetricsLogger.count(mContext, "sth_generic_recognition_event", 1);
         if (event.status != SoundTrigger.RECOGNITION_STATUS_SUCCESS) {
             return;
         }
@@ -608,9 +639,11 @@
             return;
         }
 
+        model.setRequested(config.allowMultipleTriggers);
         // TODO: Remove this block if the lower layer supports multiple triggers.
-        if (config.allowMultipleTriggers) {
-            startGenericRecognitionLocked(model, true /* notify */);
+        if (model.getRequested()) {
+            updateRecognitionLocked(model, isRecognitionAllowed() /* isAllowed */,
+                    true /* notify */);
         }
     }
 
@@ -622,6 +655,7 @@
         }
         if (DBG) Slog.d(TAG, "onSoundModelUpdate: " + event);
         synchronized (mLock) {
+            MetricsLogger.count(mContext, "sth_sound_model_updated", 1);
             onSoundModelUpdatedLocked(event);
         }
     }
@@ -637,6 +671,7 @@
     @Override
     public void onServiceDied() {
         Slog.e(TAG, "onServiceDied!!");
+        MetricsLogger.count(mContext, "sth_service_died", 1);
         synchronized (mLock) {
             onServiceDiedLocked();
         }
@@ -649,7 +684,7 @@
             return;
         }
         mCallActive = callActive;
-        updateRecognitionLocked(true /* notify */);
+        updateAllRecognitionsLocked(true /* notify */);
     }
 
     private void onPowerSaveModeChangedLocked(boolean isPowerSaveMode) {
@@ -657,7 +692,7 @@
             return;
         }
         mIsPowerSaveMode = isPowerSaveMode;
-        updateRecognitionLocked(true /* notify */);
+        updateAllRecognitionsLocked(true /* notify */);
     }
 
     private void onSoundModelUpdatedLocked(SoundModelEvent event) {
@@ -669,11 +704,12 @@
             return;
         }
         mServiceDisabled = disabled;
-        updateRecognitionLocked(true /* notify */);
+        updateAllRecognitionsLocked(true /* notify */);
     }
 
     private void onRecognitionAbortLocked() {
         Slog.w(TAG, "Recognition aborted");
+        MetricsLogger.count(mContext, "sth_recognition_aborted", 1);
         // If abort has been called, the hardware has already stopped recognition, so we shouldn't
         // call it again when we process the state change.
         mRecognitionAborted = true;
@@ -681,23 +717,29 @@
 
     private void onRecognitionFailureLocked() {
         Slog.w(TAG, "Recognition failure");
+        MetricsLogger.count(mContext, "sth_recognition_failure_event", 1);
         try {
-            if (mKeyphraseListener != null) {
-                mKeyphraseListener.onError(STATUS_ERROR);
-            }
+            sendErrorCallbacksToAll(STATUS_ERROR);
         } catch (RemoteException e) {
             Slog.w(TAG, "RemoteException in onError", e);
         } finally {
             internalClearKeyphraseStateLocked();
+            internalClearGenericModelStateLocked();
             internalClearGlobalStateLocked();
         }
     }
 
     private void onKeyphraseRecognitionSuccessLocked(KeyphraseRecognitionEvent event) {
         Slog.i(TAG, "Recognition success");
+        MetricsLogger.count(mContext, "sth_keyphrase_recognition_event", 1);
 
-        if (mKeyphraseListener == null) {
-            Slog.w(TAG, "received onRecognition event without any listener for it");
+        if (mKeyphraseModelData == null) {
+            Slog.e(TAG, "Received onRecognition event for null keyphrase model data.");
+            return;
+        }
+
+        if (mKeyphraseModelData.getCallback() == null) {
+            Slog.w(TAG, "Received onRecognition event without any listener for it.");
             return;
         }
 
@@ -714,30 +756,62 @@
         }
 
         try {
-            if (mKeyphraseListener != null) {
-                mKeyphraseListener.onKeyphraseDetected((KeyphraseRecognitionEvent) event);
-            }
+            mKeyphraseModelData.getCallback().onKeyphraseDetected(
+                    (KeyphraseRecognitionEvent) event);
         } catch (RemoteException e) {
             Slog.w(TAG, "RemoteException in onKeyphraseDetected", e);
         }
 
-        mKeyphraseStarted = false;
-        mRequested = mRecognitionConfig.allowMultipleTriggers;
+        mKeyphraseModelData.setStopped();
+
+        RecognitionConfig config = mKeyphraseModelData.getRecognitionConfig();
+        if (config != null) {
+            // Whether we should continue by starting this again.
+            mKeyphraseModelData.setRequested(config.allowMultipleTriggers);
+        }
         // TODO: Remove this block if the lower layer supports multiple triggers.
-        if (mRequested) {
-            updateRecognitionLocked(true /* notify */);
+        if (mKeyphraseModelData.getRequested()) {
+            updateRecognitionLocked(mKeyphraseModelData, isRecognitionAllowed(),
+                true /* notify */);
+        }
+    }
+
+    private void updateAllRecognitionsLocked(boolean notify) {
+        boolean isAllowed = isRecognitionAllowed();
+        // Keyphrase model.
+        if (mKeyphraseModelData != null) {
+            updateRecognitionLocked(mKeyphraseModelData, isAllowed, notify);
+        }
+        for (UUID modelId : mGenericModelDataMap.keySet()) {
+            ModelData modelData = mGenericModelDataMap.get(modelId);
+            updateRecognitionLocked(modelData, isAllowed, notify);
+        }
+    }
+
+    private int updateRecognitionLocked(ModelData model, boolean isAllowed,
+        boolean notify) {
+        boolean start = model.getRequested() && isAllowed;
+        if (start == model.isModelStarted()) {
+            // No-op.
+            return STATUS_OK;
+        }
+        if (start) {
+            return startRecognitionLocked(model, notify);
+        } else {
+            return stopRecognitionLocked(model, notify);
         }
     }
 
     private void onServiceDiedLocked() {
         try {
-            if (mKeyphraseListener != null) {
-                mKeyphraseListener.onError(SoundTrigger.STATUS_DEAD_OBJECT);
-            }
+          MetricsLogger.count(mContext, "sth_service_died", 1);
+            sendErrorCallbacksToAll(SoundTrigger.STATUS_DEAD_OBJECT);
         } catch (RemoteException e) {
             Slog.w(TAG, "RemoteException in onError", e);
         } finally {
-            internalClearKeyphraseSoundModelLocked();
+            if (mKeyphraseModelData != null) {
+                mKeyphraseModelData.clearState();
+            }
             internalClearKeyphraseStateLocked();
             internalClearGenericModelStateLocked();
             internalClearGlobalStateLocked();
@@ -748,78 +822,6 @@
         }
     }
 
-    private int updateRecognitionLocked(boolean notify) {
-        if (mModule == null || mModuleProperties == null
-                || mCurrentKeyphraseModelHandle == INVALID_VALUE || mKeyphraseListener == null) {
-            // Nothing to do here.
-            return STATUS_OK;
-        }
-
-        boolean start = mRequested && !mCallActive && !mServiceDisabled && !mIsPowerSaveMode;
-        if (start == mKeyphraseStarted) {
-            // No-op.
-            return STATUS_OK;
-        }
-
-        // See if the recognition needs to be started.
-        if (start) {
-            // Start recognition.
-            int status = mModule.startRecognition(mCurrentKeyphraseModelHandle,
-                    mRecognitionConfig);
-            if (status != SoundTrigger.STATUS_OK) {
-                Slog.w(TAG, "startKeyphraseRecognition failed with " + status);
-                // Notify of error if needed.
-                if (notify) {
-                    try {
-                        mKeyphraseListener.onError(status);
-                    } catch (RemoteException e) {
-                        Slog.w(TAG, "RemoteException in onError", e);
-                    }
-                }
-            } else {
-                mKeyphraseStarted = true;
-                // Notify of resume if needed.
-                if (notify) {
-                    try {
-                        mKeyphraseListener.onRecognitionResumed();
-                    } catch (RemoteException e) {
-                        Slog.w(TAG, "RemoteException in onRecognitionResumed", e);
-                    }
-                }
-            }
-            return status;
-        } else {
-            // Stop recognition (only if we haven't been aborted).
-            int status = STATUS_OK;
-            if (!mRecognitionAborted) {
-                status = mModule.stopRecognition(mCurrentKeyphraseModelHandle);
-            } else {
-                mRecognitionAborted = false;
-            }
-            if (status != SoundTrigger.STATUS_OK) {
-                Slog.w(TAG, "stopRecognition call failed with " + status);
-                if (notify) {
-                    try {
-                        mKeyphraseListener.onError(status);
-                    } catch (RemoteException e) {
-                        Slog.w(TAG, "RemoteException in onError", e);
-                    }
-                }
-            } else {
-                mKeyphraseStarted = false;
-                // Notify of pause if needed.
-                if (notify) {
-                    try {
-                        mKeyphraseListener.onRecognitionPaused();
-                    } catch (RemoteException e) {
-                        Slog.w(TAG, "RemoteException in onRecognitionPaused", e);
-                    }
-                }
-            }
-            return status;
-        }
-    }
-
     // internalClearGlobalStateLocked() gets split into two routines. Cleanup that is
     // specific to keyphrase sound models named as internalClearKeyphraseStateLocked() and
     // internalClearGlobalStateLocked() for global state. The global cleanup routine will be used
@@ -836,12 +838,14 @@
     }
 
     private void internalClearKeyphraseStateLocked() {
-        mKeyphraseStarted = false;
-        mRequested = false;
+        if (mKeyphraseModelData != null) {
+            mKeyphraseModelData.setStopped();
+            mKeyphraseModelData.setRequested(false);
+            mKeyphraseModelData.setRecognitionConfig(null);
+            mKeyphraseModelData.setCallback(null);
+        }
 
         mKeyphraseId = INVALID_VALUE;
-        mRecognitionConfig = null;
-        mKeyphraseListener = null;
     }
 
     private void internalClearGenericModelStateLocked() {
@@ -852,13 +856,6 @@
         }
     }
 
-    // This routine is a replacement for internalClearSoundModelLocked(). However, we
-    // should see why this should be different from internalClearKeyphraseStateLocked().
-    private void internalClearKeyphraseSoundModelLocked() {
-        mCurrentKeyphraseModelHandle = INVALID_VALUE;
-        mCurrentSoundModel = null;
-    }
-
     class MyCallStateListener extends PhoneStateListener {
         @Override
         public void onCallStateChanged(int state, String arg1) {
@@ -888,17 +885,13 @@
             pw.print("  module properties=");
             pw.println(mModuleProperties == null ? "null" : mModuleProperties);
             pw.print("  keyphrase ID="); pw.println(mKeyphraseId);
-            pw.print("  sound model handle="); pw.println(mCurrentKeyphraseModelHandle);
-            pw.print("  sound model UUID=");
-            pw.println(mCurrentSoundModel == null ? "null" : mCurrentSoundModel.uuid);
-            pw.print("  current listener=");
-            pw.println(mKeyphraseListener == null ? "null" : mKeyphraseListener.asBinder());
 
-            pw.print("  requested="); pw.println(mRequested);
-            pw.print("  started="); pw.println(mKeyphraseStarted);
             pw.print("  call active="); pw.println(mCallActive);
             pw.print("  power save mode active="); pw.println(mIsPowerSaveMode);
             pw.print("  service disabled="); pw.println(mServiceDisabled);
+            if (mKeyphraseModelData != null) {
+                pw.println(mKeyphraseModelData.toString());
+            }
         }
     }
 
@@ -919,11 +912,25 @@
         mIsPowerSaveMode = mPowerManager.isPowerSaveMode();
     }
 
+    // Sends an error callback to all models with a valid registered callback.
+    private void sendErrorCallbacksToAll(int errorCode) throws RemoteException {
+        IRecognitionStatusCallback keyphraseListener = mKeyphraseModelData.getCallback();
+        if (keyphraseListener != null) {
+            keyphraseListener.onError(STATUS_ERROR);
+        }
+        for (UUID modelId: mGenericModelDataMap.keySet()) {
+            ModelData modelData = mGenericModelDataMap.get(modelId);
+            IRecognitionStatusCallback keyphraseCallback = mKeyphraseModelData.getCallback();
+            if (keyphraseCallback != null) {
+                keyphraseCallback.onError(STATUS_ERROR);
+            }
+        }
+    }
+
     private ModelData getOrCreateGenericModelDataLocked(UUID modelId) {
         ModelData modelData = mGenericModelDataMap.get(modelId);
         if (modelData == null) {
-            modelData = new ModelData(modelId);
-            modelData.setTypeGeneric();
+            modelData = ModelData.createGenericModelData(modelId);
             mGenericModelDataMap.put(modelId, modelData);
         }
         return modelData;
@@ -949,25 +956,30 @@
         return !mCallActive && !mServiceDisabled && !mIsPowerSaveMode;
     }
 
-    private int startGenericRecognitionLocked(ModelData modelData, boolean notify) {
+    // A single routine that implements the start recognition logic for both generic and keyphrase
+    // models.
+    private int startRecognitionLocked(ModelData modelData, boolean notify) {
         IRecognitionStatusCallback callback = modelData.getCallback();
         int handle = modelData.getHandle();
         RecognitionConfig config = modelData.getRecognitionConfig();
         if (callback == null || handle == INVALID_VALUE || config == null) {
             // Nothing to do here.
-            Slog.w(TAG, "startGenericRecognition: Bad data passed in.");
+            Slog.w(TAG, "startRecognition: Bad data passed in.");
+            MetricsLogger.count(mContext, "sth_start_recognition_error", 1);
             return STATUS_ERROR;
         }
 
         if (!isRecognitionAllowed()) {
             // Nothing to do here.
-            Slog.w(TAG, "startGenericRecognition requested but not allowed.");
+            Slog.w(TAG, "startRecognition requested but not allowed.");
+            MetricsLogger.count(mContext, "sth_start_recognition_not_allowed", 1);
             return STATUS_OK;
         }
 
         int status = mModule.startRecognition(handle, config);
         if (status != SoundTrigger.STATUS_OK) {
-            Slog.w(TAG, "startGenericRecognition failed with " + status);
+            Slog.w(TAG, "startRecognition failed with " + status);
+            MetricsLogger.count(mContext, "sth_start_recognition_error", 1);
             // Notify of error if needed.
             if (notify) {
                 try {
@@ -978,6 +990,7 @@
             }
         } else {
             Slog.i(TAG, "startRecognition successful.");
+            MetricsLogger.count(mContext, "sth_start_recognition_success", 1);
             modelData.setStarted();
             // Notify of resume if needed.
             if (notify) {
@@ -988,17 +1001,31 @@
                 }
             }
         }
-        if (DBG) dumpGenericModelStateLocked();
+        if (DBG) {
+            Slog.d(TAG, "Model being started :" + modelData.toString());
+        }
         return status;
     }
 
-    private int stopGenericRecognitionLocked(ModelData modelData, boolean notify) {
+    private int stopRecognitionLocked(ModelData modelData, boolean notify) {
         IRecognitionStatusCallback callback = modelData.getCallback();
 
         // Stop recognition (only if we haven't been aborted).
-        int status = mModule.stopRecognition(modelData.getHandle());
+        int status = STATUS_OK;
+
+        // This logic for "recognition aborted" now works for both generic and keyphrase models.
+        // The idea here is to "skip" the stopRecognition() call if the lower layer has
+        // aborted recognition. Also we "consume" the abort state as well, so if there is another
+        // stopRecognition() request, it will go through -- this seems to have been the previously
+        // intended design.
+        if (!mRecognitionAborted) {
+            status = mModule.stopRecognition(modelData.getHandle());
+        } else {
+            mRecognitionAborted = false;
+        }
         if (status != SoundTrigger.STATUS_OK) {
             Slog.w(TAG, "stopRecognition call failed with " + status);
+            MetricsLogger.count(mContext, "sth_stop_recognition_error", 1);
             if (notify) {
                 try {
                     callback.onError(status);
@@ -1008,6 +1035,7 @@
             }
         } else {
             modelData.setStopped();
+            MetricsLogger.count(mContext, "sth_stop_recognition_success", 1);
             // Notify of pause if needed.
             if (notify) {
                 try {
@@ -1017,7 +1045,9 @@
                 }
             }
         }
-        if (DBG) dumpGenericModelStateLocked();
+        if (DBG) {
+            Slog.d(TAG, "Model being stopped :" + modelData.toString());
+        }
         return status;
     }
 
@@ -1035,8 +1065,9 @@
             mRecognitionRunning = false;
             return mRecognitionRunning;
         }
-        if (mKeyphraseListener != null && mKeyphraseStarted &&
-            mCurrentKeyphraseModelHandle != INVALID_VALUE && mCurrentSoundModel != null) {
+        if (mKeyphraseModelData != null && mKeyphraseModelData.getCallback() != null &&
+                mKeyphraseModelData.isModelStarted() &&
+            mKeyphraseModelData.getHandle() != INVALID_VALUE) {
             mRecognitionRunning = true;
             return mRecognitionRunning;
         }
@@ -1065,26 +1096,55 @@
 
         // One of MODEL_NOTLOADED, MODEL_LOADED, MODEL_STARTED (which implies loaded).
         private int mModelState;
-
         private UUID mModelId;
 
+        // mRequested captures the explicit intent that a start was requested for this model. We
+        // continue to capture and retain this state even after the model gets started, so that we
+        // know when a model gets stopped due to "other" reasons, that we should start it again.
+        // This was the intended behavior of the "mRequested" variable in the previous version of
+        // this code that we are replicating here.
+        //
+        // The "other" reasons include power save, abort being called from the lower layer (due
+        // to concurrent capture not being supported) and phone call state. Once we recover from
+        // these transient disruptions, we would start such models again where mRequested == true.
+        // Thus, mRequested gets reset only when there is an explicit intent to stop the model
+        // coming from the SoundTriggerService layer that uses this class (and thus eventually
+        // from the app that manages this model).
+        private boolean mRequested = false;
+
         // One of SoundModel.TYPE_GENERIC or SoundModel.TYPE_KEYPHRASE. Initially set
         // to SoundModel.TYPE_UNKNOWN;
         private int mModelType = SoundModel.TYPE_UNKNOWN;
+
         private IRecognitionStatusCallback mCallback = null;
         private RecognitionConfig mRecognitionConfig = null;
 
-
         // Model handle is an integer used by the HAL as an identifier for sound
         // models.
         private int mModelHandle = INVALID_VALUE;
 
-        ModelData(UUID modelId) {
+        // The SoundModel instance, one of KeyphraseSoundModel or GenericSoundModel.
+        private SoundModel mSoundModel = null;
+
+        private ModelData(UUID modelId, int modelType) {
             mModelId = modelId;
+            // Private constructor, since we require modelType to be one of TYPE_GENERIC,
+            // TYPE_KEYPHRASE or TYPE_UNKNOWN.
+            mModelType = modelType;
         }
 
-        synchronized void setTypeGeneric() {
-            mModelType = SoundModel.TYPE_GENERIC_SOUND;
+        static ModelData createKeyphraseModelData(UUID modelId) {
+            return new ModelData(modelId, SoundModel.TYPE_KEYPHRASE);
+        }
+
+        static ModelData createGenericModelData(UUID modelId) {
+            return new ModelData(modelId, SoundModel.TYPE_GENERIC_SOUND);
+        }
+
+        // Note that most of the functionality in this Java class will not work for
+        // SoundModel.TYPE_UNKNOWN nevertheless we have it since lower layers support it.
+        static ModelData createModelDataOfUnknownType(UUID modelId) {
+            return new ModelData(modelId, SoundModel.TYPE_UNKNOWN);
         }
 
         synchronized void setCallback(IRecognitionStatusCallback callback) {
@@ -1099,6 +1159,10 @@
             return (mModelState == MODEL_LOADED || mModelState == MODEL_STARTED);
         }
 
+        synchronized boolean isModelNotLoaded() {
+            return mModelState == MODEL_NOTLOADED;
+        }
+
         synchronized void setStarted() {
             mModelState = MODEL_STARTED;
         }
@@ -1136,11 +1200,40 @@
             return mModelHandle;
         }
 
+        synchronized UUID getModelId() {
+            return mModelId;
+        }
+
         synchronized RecognitionConfig getRecognitionConfig() {
             return mRecognitionConfig;
         }
 
-        String stateToString() {
+        // Whether a start recognition was requested.
+        synchronized boolean getRequested() {
+            return mRequested;
+        }
+
+        synchronized void setRequested(boolean requested) {
+            mRequested = requested;
+        }
+
+        synchronized void setSoundModel(SoundModel soundModel) {
+            mSoundModel = soundModel;
+        }
+
+        synchronized SoundModel getSoundModel() {
+            return mSoundModel;
+        }
+
+        synchronized int getModelType() {
+            return mModelType;
+        }
+
+        synchronized boolean isKeyphraseModel() {
+            return mModelType == SoundModel.TYPE_KEYPHRASE;
+        }
+
+        synchronized String stateToString() {
             switch(mModelState) {
                 case MODEL_NOTLOADED: return "NOT_LOADED";
                 case MODEL_LOADED: return "LOADED";
@@ -1149,8 +1242,24 @@
             return "Unknown state";
         }
 
-        public String toString() {
-            return "Handle: " + mModelHandle + "ModelState: " + stateToString();
+        synchronized String requestedToString() {
+            return "Requested: " + (mRequested ? "Yes" : "No");
+        }
+
+        synchronized String callbackToString() {
+            return "Callback: " + (mCallback != null ? mCallback.asBinder() : "null");
+        }
+
+        synchronized String uuidToString() {
+            return "UUID: " + mModelId;
+        }
+
+        synchronized public String toString() {
+            return "Handle: " + mModelHandle + "\n" +
+                    "ModelState: " + stateToString() + "\n" +
+                    requestedToString() + "\n" +
+                    callbackToString() + "\n" +
+                    uuidToString();
         }
     }
 }
diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java
index 461611d..adc7c21 100644
--- a/telephony/java/android/telephony/CarrierConfigManager.java
+++ b/telephony/java/android/telephony/CarrierConfigManager.java
@@ -419,6 +419,13 @@
     public static final String KEY_CARRIER_DATA_CALL_APN_DELAY_FASTER_LONG =
             "carrier_data_call_apn_delay_faster_long";
 
+    /**
+     * Default APN types that are metered by the carrier
+     * @hide
+     */
+    public static final String KEY_CARRIER_METERED_APN_TYPES_STRINGS =
+            "carrier_metered_apn_types_strings";
+
     /* The following 3 fields are related to carrier visual voicemail. */
 
     /**
@@ -699,6 +706,8 @@
         sDefaults.putLong(KEY_CARRIER_DATA_CALL_APN_DELAY_DEFAULT_LONG, 20000);
         sDefaults.putLong(KEY_CARRIER_DATA_CALL_APN_DELAY_FASTER_LONG, 3000);
         sDefaults.putInt(KEY_DURATION_BLOCKING_DISABLED_AFTER_EMERGENCY_INT, 7200);
+        sDefaults.putStringArray(KEY_CARRIER_METERED_APN_TYPES_STRINGS,
+                new String[]{"default", "mms", "dun", "supl"});
 
         sDefaults.putStringArray(KEY_GSM_ROAMING_NETWORKS_STRING_ARRAY, null);
         sDefaults.putStringArray(KEY_GSM_NONROAMING_NETWORKS_STRING_ARRAY, null);
diff --git a/telephony/java/com/android/internal/telephony/CarrierAppUtils.java b/telephony/java/com/android/internal/telephony/CarrierAppUtils.java
new file mode 100644
index 0000000..ca7354f
--- /dev/null
+++ b/telephony/java/com/android/internal/telephony/CarrierAppUtils.java
@@ -0,0 +1,234 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.internal.telephony;
+
+import android.annotation.Nullable;
+import android.content.pm.ApplicationInfo;
+import android.content.pm.IPackageManager;
+import android.content.pm.PackageManager;
+import android.content.res.Resources;
+import android.os.RemoteException;
+import android.telephony.TelephonyManager;
+import android.util.Slog;
+
+import com.android.internal.annotations.VisibleForTesting;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Utilities for handling carrier applications.
+ * @hide
+ */
+public final class CarrierAppUtils {
+    private static final String TAG = "CarrierAppUtils";
+
+    private static final boolean DEBUG = false; // STOPSHIP if true
+
+    private CarrierAppUtils() {}
+
+    /**
+     * Handle preinstalled carrier apps which should be disabled until a matching SIM is inserted.
+     *
+     * Evaluates the list of applications in config_disabledUntilUsedPreinstalledCarrierApps. We
+     * want to disable each such application which is present on the system image until the user
+     * inserts a SIM which causes that application to gain carrier privilege (indicating a "match"),
+     * without interfering with the user if they opt to enable/disable the app explicitly.
+     *
+     * So, for each such app, we either disable until used IFF the app is not carrier privileged AND
+     * in the default state (e.g. not explicitly DISABLED/DISABLED_BY_USER/ENABLED), or we enable if
+     * the app is carrier privileged and in either the default state or DISABLED_UNTIL_USED.
+     *
+     * When enabling a carrier app we also grant it default permissions.
+     *
+     * This method is idempotent and is safe to be called at any time; it should be called once at
+     * system startup prior to any application running, as well as any time the set of carrier
+     * privileged apps may have changed.
+     */
+    public synchronized static void disableCarrierAppsUntilPrivileged(String callingPackage,
+            IPackageManager packageManager, TelephonyManager telephonyManager, int userId) {
+        if (DEBUG) {
+            Slog.d(TAG, "disableCarrierAppsUntilPrivileged");
+        }
+        String[] systemCarrierAppsDisabledUntilUsed = Resources.getSystem().getStringArray(
+                com.android.internal.R.array.config_disabledUntilUsedPreinstalledCarrierApps);
+        disableCarrierAppsUntilPrivileged(callingPackage, packageManager, telephonyManager, userId,
+                systemCarrierAppsDisabledUntilUsed);
+    }
+
+    /**
+     * Like {@link #disableCarrierAppsUntilPrivileged(String, IPackageManager, TelephonyManager,
+     * int)}, but assumes that no carrier apps have carrier privileges.
+     *
+     * This prevents a potential race condition on first boot - since the app's default state is
+     * enabled, we will initially disable it when the telephony stack is first initialized as it has
+     * not yet read the carrier privilege rules. However, since telephony is initialized later on
+     * late in boot, the app being disabled may have already been started in response to certain
+     * broadcasts. The app will continue to run (briefly) after being disabled, before the Package
+     * Manager can kill it, and this can lead to crashes as the app is in an unexpected state.
+     */
+    public synchronized static void disableCarrierAppsUntilPrivileged(String callingPackage,
+            IPackageManager packageManager, int userId) {
+        if (DEBUG) {
+            Slog.d(TAG, "disableCarrierAppsUntilPrivileged");
+        }
+        String[] systemCarrierAppsDisabledUntilUsed = Resources.getSystem().getStringArray(
+                com.android.internal.R.array.config_disabledUntilUsedPreinstalledCarrierApps);
+        disableCarrierAppsUntilPrivileged(callingPackage, packageManager,
+                null /* telephonyManager */, userId, systemCarrierAppsDisabledUntilUsed);
+    }
+
+    // Must be public b/c framework unit tests can't access package-private methods.
+    @VisibleForTesting
+    public static void disableCarrierAppsUntilPrivileged(String callingPackage,
+            IPackageManager packageManager, @Nullable TelephonyManager telephonyManager, int userId,
+            String[] systemCarrierAppsDisabledUntilUsed) {
+        List<ApplicationInfo> candidates = getDefaultCarrierAppCandidatesHelper(packageManager,
+                userId, systemCarrierAppsDisabledUntilUsed);
+        if (candidates == null || candidates.isEmpty()) {
+            return;
+        }
+
+        List<String> enabledCarrierPackages = new ArrayList<>();
+
+        try {
+            for (ApplicationInfo ai : candidates) {
+                String packageName = ai.packageName;
+                boolean hasPrivileges = telephonyManager != null &&
+                        telephonyManager.checkCarrierPrivilegesForPackageAnyPhone(packageName) ==
+                                TelephonyManager.CARRIER_PRIVILEGE_STATUS_HAS_ACCESS;
+
+                // Only update enabled state for the app on /system. Once it has been updated we
+                // shouldn't touch it.
+                if (!ai.isUpdatedSystemApp()) {
+                    if (hasPrivileges
+                            && (ai.enabledSetting == PackageManager.COMPONENT_ENABLED_STATE_DEFAULT
+                            || ai.enabledSetting ==
+                            PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED)) {
+                        Slog.i(TAG, "Update state(" + packageName + "): ENABLED for user "
+                                + userId);
+                        packageManager.setApplicationEnabledSetting(packageName,
+                                PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
+                                PackageManager.DONT_KILL_APP, userId, callingPackage);
+                    } else if (!hasPrivileges
+                            && ai.enabledSetting ==
+                            PackageManager.COMPONENT_ENABLED_STATE_DEFAULT) {
+                        Slog.i(TAG, "Update state(" + packageName
+                                + "): DISABLED_UNTIL_USED for user " + userId);
+                        packageManager.setApplicationEnabledSetting(packageName,
+                                PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED, 0,
+                                userId, callingPackage);
+                    }
+                }
+
+                // Always re-grant default permissions to carrier apps w/ privileges.
+                if (hasPrivileges) {
+                    enabledCarrierPackages.add(ai.packageName);
+                }
+            }
+
+            if (!enabledCarrierPackages.isEmpty()) {
+                // Since we enabled at least one app, ensure we grant default permissions to those
+                // apps.
+                String[] packageNames = new String[enabledCarrierPackages.size()];
+                enabledCarrierPackages.toArray(packageNames);
+                packageManager.grantDefaultPermissionsToEnabledCarrierApps(packageNames, userId);
+            }
+        } catch (RemoteException e) {
+            Slog.w(TAG, "Could not reach PackageManager", e);
+        }
+    }
+
+    /**
+     * Returns the list of "default" carrier apps.
+     *
+     * This is the subset of apps returned by
+     * {@link #getDefaultCarrierAppCandidates(IPackageManager, int)} which currently have carrier
+     * privileges per the SIM(s) inserted in the device.
+     */
+    public static List<ApplicationInfo> getDefaultCarrierApps(IPackageManager packageManager,
+            TelephonyManager telephonyManager, int userId) {
+        // Get all system apps from the default list.
+        List<ApplicationInfo> candidates = getDefaultCarrierAppCandidates(packageManager, userId);
+        if (candidates == null || candidates.isEmpty()) {
+            return null;
+        }
+
+        // Filter out apps without carrier privileges.
+        // Iterate from the end to avoid creating an Iterator object and because we will be removing
+        // elements from the list as we pass through it.
+        for (int i = candidates.size() - 1; i >= 0; i--) {
+            ApplicationInfo ai = candidates.get(i);
+            String packageName = ai.packageName;
+            boolean hasPrivileges =
+                    telephonyManager.checkCarrierPrivilegesForPackageAnyPhone(packageName) ==
+                            TelephonyManager.CARRIER_PRIVILEGE_STATUS_HAS_ACCESS;
+            if (!hasPrivileges) {
+                candidates.remove(i);
+            }
+        }
+
+        return candidates;
+    }
+
+    /**
+     * Returns the list of "default" carrier app candidates.
+     *
+     * These are the apps subject to the hiding/showing logic in
+     * {@link CarrierAppUtils#disableCarrierAppsUntilPrivileged(String, IPackageManager,
+     * TelephonyManager, int)}, as well as the apps which should have default permissions granted,
+     * when a matching SIM is inserted.
+     *
+     * Whether or not the app is actually considered a default app depends on whether the app has
+     * carrier privileges as determined by the SIMs in the device.
+     */
+    public static List<ApplicationInfo> getDefaultCarrierAppCandidates(
+            IPackageManager packageManager, int userId) {
+        String[] systemCarrierAppsDisabledUntilUsed = Resources.getSystem().getStringArray(
+                com.android.internal.R.array.config_disabledUntilUsedPreinstalledCarrierApps);
+        return getDefaultCarrierAppCandidatesHelper(packageManager, userId,
+                systemCarrierAppsDisabledUntilUsed);
+    }
+
+    private static List<ApplicationInfo> getDefaultCarrierAppCandidatesHelper(
+            IPackageManager packageManager, int userId,
+            String[] systemCarrierAppsDisabledUntilUsed) {
+        if (systemCarrierAppsDisabledUntilUsed == null
+                || systemCarrierAppsDisabledUntilUsed.length == 0) {
+            return null;
+        }
+        List<ApplicationInfo> apps = null;
+        try {
+            apps = new ArrayList<>(systemCarrierAppsDisabledUntilUsed.length);
+            for (String packageName : systemCarrierAppsDisabledUntilUsed) {
+                ApplicationInfo ai = packageManager.getApplicationInfo(packageName,
+                        PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, userId);
+                if (ai == null) {
+                    // No app found for packageName
+                    continue;
+                }
+                if (!ai.isSystemApp()) {
+                    continue;
+                }
+                apps.add(ai);
+            }
+        } catch (RemoteException e) {
+            Slog.w(TAG, "Could not reach PackageManager", e);
+        }
+        return apps;
+    }
+}
diff --git a/telephony/java/com/android/internal/telephony/DctConstants.java b/telephony/java/com/android/internal/telephony/DctConstants.java
index fcb967f..ccabace 100644
--- a/telephony/java/com/android/internal/telephony/DctConstants.java
+++ b/telephony/java/com/android/internal/telephony/DctConstants.java
@@ -102,6 +102,7 @@
     public static final int CMD_NET_STAT_POLL = BASE + 40;
     public static final int EVENT_DATA_RAT_CHANGED = BASE + 41;
     public static final int CMD_CLEAR_PROVISIONING_SPINNER = BASE + 42;
+    public static final int EVENT_DEVICE_PROVISIONED_CHANGE = BASE + 43;
 
     /***** Constants *****/
 
diff --git a/tests/HwAccelerationTest/AndroidManifest.xml b/tests/HwAccelerationTest/AndroidManifest.xml
index 18fd985..b9e9ac8 100644
--- a/tests/HwAccelerationTest/AndroidManifest.xml
+++ b/tests/HwAccelerationTest/AndroidManifest.xml
@@ -374,6 +374,15 @@
         </activity>
 
         <activity
+                android:name="GetBitmapSurfaceViewActivity"
+                android:label="SurfaceView/GetBitmap with Camera source">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="com.android.test.hwui.TEST" />
+            </intent-filter>
+        </activity>
+
+        <activity
                 android:name="GLTextureViewActivity"
                 android:label="TextureView/OpenGL">
             <intent-filter>
diff --git a/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java b/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java
new file mode 100644
index 0000000..d3cd7db
--- /dev/null
+++ b/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java
@@ -0,0 +1,111 @@
+/*
+ * 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 com.android.test.hwui;
+
+import android.app.Activity;
+import android.graphics.Bitmap;
+import android.graphics.PixelCopy;
+import android.graphics.PixelCopy.OnPixelCopyFinished;
+import android.graphics.PixelCopy.Response;
+import android.hardware.Camera;
+import android.os.Bundle;
+import android.os.Environment;
+import android.view.Gravity;
+import android.view.SurfaceHolder;
+import android.view.SurfaceView;
+import android.view.View;
+import android.widget.Button;
+import android.widget.FrameLayout;
+import android.widget.Toast;
+
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+
+public class GetBitmapSurfaceViewActivity extends Activity implements SurfaceHolder.Callback {
+    private Camera mCamera;
+    private SurfaceView mSurfaceView;
+
+    @Override
+    protected void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        FrameLayout content = new FrameLayout(this);
+
+        mSurfaceView = new SurfaceView(this);
+        mSurfaceView.getHolder().addCallback(this);
+
+        Button button = new Button(this);
+        button.setText("Copy bitmap to /sdcard/surfaceview.png");
+        button.setOnClickListener((View v) -> {
+            Bitmap b = Bitmap.createBitmap(
+                            mSurfaceView.getWidth(),
+                            mSurfaceView.getHeight(),
+                            Bitmap.Config.ARGB_8888);
+            PixelCopy.request(mSurfaceView, b,
+                    mOnCopyFinished, mSurfaceView.getHandler());
+        });
+
+        content.addView(mSurfaceView, new FrameLayout.LayoutParams(500, 400, Gravity.CENTER));
+        content.addView(button, new FrameLayout.LayoutParams(
+                FrameLayout.LayoutParams.WRAP_CONTENT, FrameLayout.LayoutParams.WRAP_CONTENT,
+                Gravity.CENTER_HORIZONTAL | Gravity.BOTTOM));
+        setContentView(content);
+    }
+
+    private final OnPixelCopyFinished mOnCopyFinished = new OnPixelCopyFinished() {
+        @Override
+        public void onPixelCopyFinished(Response response) {
+            if (!response.success) {
+                Toast.makeText(GetBitmapSurfaceViewActivity.this,
+                        "Failed to copy", Toast.LENGTH_SHORT).show();
+                return;
+            }
+            try {
+                try (FileOutputStream out = new FileOutputStream(
+                        Environment.getExternalStorageDirectory() + "/surfaceview.png");) {
+                    response.bitmap.compress(Bitmap.CompressFormat.PNG, 100, out);
+                }
+            } catch (Exception e) {
+                // Ignore
+            }
+        }
+    };
+
+    @Override
+    public void surfaceCreated(SurfaceHolder holder) {
+        mCamera = Camera.open();
+
+        try {
+            mCamera.setPreviewSurface(holder.getSurface());
+        } catch (IOException t) {
+            android.util.Log.e("TextureView", "Cannot set preview texture target!", t);
+        }
+
+        mCamera.startPreview();
+    }
+
+    @Override
+    public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
+    }
+
+    @Override
+    public void surfaceDestroyed(SurfaceHolder holder) {
+        mCamera.stopPreview();
+        mCamera.release();
+    }
+}
diff --git a/tests/HwAccelerationTest/src/com/android/test/hwui/HardwareCanvasSurfaceViewActivity.java b/tests/HwAccelerationTest/src/com/android/test/hwui/HardwareCanvasSurfaceViewActivity.java
index b1431c5..5c30fab 100644
--- a/tests/HwAccelerationTest/src/com/android/test/hwui/HardwareCanvasSurfaceViewActivity.java
+++ b/tests/HwAccelerationTest/src/com/android/test/hwui/HardwareCanvasSurfaceViewActivity.java
@@ -17,18 +17,29 @@
 package com.android.test.hwui;
 
 import android.app.Activity;
+import android.graphics.Bitmap;
 import android.graphics.Canvas;
 import android.graphics.Paint;
+import android.graphics.PixelCopy;
+import android.graphics.PixelCopy.OnPixelCopyFinished;
+import android.graphics.PixelCopy.Response;
 import android.graphics.PorterDuff;
 import android.os.Bundle;
-import android.view.Gravity;
+import android.os.Environment;
 import android.view.Surface;
 import android.view.SurfaceHolder;
 import android.view.SurfaceHolder.Callback;
 import android.view.SurfaceView;
+import android.view.View;
+import android.widget.Button;
 import android.widget.FrameLayout;
+import android.widget.LinearLayout;
+import android.widget.Toast;
 
-@SuppressWarnings({"UnusedDeclaration"})
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+
 public class HardwareCanvasSurfaceViewActivity extends Activity implements Callback {
     private SurfaceView mSurfaceView;
     private HardwareCanvasSurfaceViewActivity.RenderingThread mThread;
@@ -42,13 +53,49 @@
         mSurfaceView = new SurfaceView(this);
         mSurfaceView.getHolder().addCallback(this);
 
-        content.addView(mSurfaceView, new FrameLayout.LayoutParams(
+        Button button = new Button(this);
+        button.setText("Copy bitmap to /sdcard/surfaceview.png");
+        button.setOnClickListener((View v) -> {
+            Bitmap b = Bitmap.createBitmap(
+                            mSurfaceView.getWidth(),
+                            mSurfaceView.getHeight(),
+                            Bitmap.Config.ARGB_8888);
+            PixelCopy.request(mSurfaceView, b,
+                    mOnCopyFinished, mSurfaceView.getHandler());
+        });
+
+        LinearLayout layout = new LinearLayout(this);
+        layout.setOrientation(LinearLayout.VERTICAL);
+        layout.addView(button, LinearLayout.LayoutParams.MATCH_PARENT,
+                LinearLayout.LayoutParams.WRAP_CONTENT);
+        layout.addView(mSurfaceView, LinearLayout.LayoutParams.MATCH_PARENT,
+                LinearLayout.LayoutParams.MATCH_PARENT);
+
+        content.addView(layout, new FrameLayout.LayoutParams(
                 FrameLayout.LayoutParams.MATCH_PARENT,
-                FrameLayout.LayoutParams.MATCH_PARENT,
-                Gravity.CENTER));
+                FrameLayout.LayoutParams.MATCH_PARENT));
         setContentView(content);
     }
 
+    private final OnPixelCopyFinished mOnCopyFinished = new OnPixelCopyFinished() {
+        @Override
+        public void onPixelCopyFinished(Response response) {
+            if (!response.success) {
+                Toast.makeText(HardwareCanvasSurfaceViewActivity.this,
+                        "Failed to copy", Toast.LENGTH_SHORT).show();
+                return;
+            }
+            try {
+                try (FileOutputStream out = new FileOutputStream(
+                        Environment.getExternalStorageDirectory() + "/surfaceview.png");) {
+                    response.bitmap.compress(Bitmap.CompressFormat.PNG, 100, out);
+                }
+            } catch (Exception e) {
+                // Ignore
+            }
+        }
+    };
+
     @Override
     public void surfaceCreated(SurfaceHolder holder) {
         mThread = new RenderingThread(holder.getSurface());
diff --git a/tests/SoundTriggerTestApp/res/layout/main.xml b/tests/SoundTriggerTestApp/res/layout/main.xml
index 702be49..06949a0 100644
--- a/tests/SoundTriggerTestApp/res/layout/main.xml
+++ b/tests/SoundTriggerTestApp/res/layout/main.xml
@@ -60,29 +60,22 @@
         android:onClick="onUnEnrollButtonClicked"
         android:padding="20dp" />
 
+    <Button
+        android:id="@+id/play_trigger_id"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:text="@string/play_trigger"
+        android:onClick="onPlayTriggerButtonClicked"
+        android:padding="20dp" />
+
 </LinearLayout>
 
 <RadioGroup xmlns:android="http://schemas.android.com/apk/res/android"
+        android:id="@+id/model_group_id"
         android:layout_width="fill_parent"
         android:layout_height="wrap_content"
         android:padding="20dp"
-        android:checkedButton="@+id/model_one"
         android:orientation="vertical">
-   <RadioButton android:id="@+id/model_one"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        android:text="@string/model_one"
-        android:onClick="onRadioButtonClicked"/>
-   <RadioButton android:id="@+id/model_two"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        android:text="@string/model_two"
-        android:onClick="onRadioButtonClicked"/>
-   <RadioButton android:id="@+id/model_three"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        android:text="@string/model_three"
-        android:onClick="onRadioButtonClicked"/>
 </RadioGroup>
 
 <ScrollView
@@ -93,7 +86,7 @@
        android:fillViewport="true">
 
       <TextView
-         android:id="@+id/console"
+        android:id="@+id/console"
         android:paddingTop="20pt"
         android:layout_height="fill_parent"
         android:layout_width="fill_parent"
diff --git a/tests/SoundTriggerTestApp/res/values/strings.xml b/tests/SoundTriggerTestApp/res/values/strings.xml
index b4ca71b..7c1f649 100644
--- a/tests/SoundTriggerTestApp/res/values/strings.xml
+++ b/tests/SoundTriggerTestApp/res/values/strings.xml
@@ -21,8 +21,6 @@
     <string name="unenroll">Un-load</string>
     <string name="start_recog">Start</string>
     <string name="stop_recog">Stop</string>
-    <string name="model_one">Model One</string>
-    <string name="model_two">Model Two</string>
-    <string name="model_three">Model Three</string>
+    <string name="play_trigger">Play Trigger Audio</string>
     <string name="none">Debug messages appear here:\n</string>
 </resources>
diff --git a/tests/SoundTriggerTestApp/src/com/android/test/soundtrigger/TestSoundTriggerActivity.java b/tests/SoundTriggerTestApp/src/com/android/test/soundtrigger/TestSoundTriggerActivity.java
index 3ca96d2..5fd38e9 100644
--- a/tests/SoundTriggerTestApp/src/com/android/test/soundtrigger/TestSoundTriggerActivity.java
+++ b/tests/SoundTriggerTestApp/src/com/android/test/soundtrigger/TestSoundTriggerActivity.java
@@ -16,24 +16,36 @@
 
 package com.android.test.soundtrigger;
 
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Properties;
 import java.util.Random;
 import java.util.UUID;
 
 import android.app.Activity;
-import android.hardware.soundtrigger.SoundTrigger;
 import android.hardware.soundtrigger.SoundTrigger.GenericSoundModel;
+import android.hardware.soundtrigger.SoundTrigger;
 import android.media.AudioFormat;
+import android.media.AudioManager;
+import android.media.MediaPlayer;
 import android.media.soundtrigger.SoundTriggerDetector;
 import android.media.soundtrigger.SoundTriggerManager;
-import android.text.Editable;
-import android.text.method.ScrollingMovementMethod;
+import android.net.Uri;
 import android.os.Bundle;
 import android.os.Handler;
 import android.os.PowerManager;
 import android.os.UserManager;
+import android.text.Editable;
+import android.text.method.ScrollingMovementMethod;
 import android.util.Log;
 import android.view.View;
+import android.widget.Button;
 import android.widget.RadioButton;
+import android.widget.RadioButton;
+import android.widget.RadioGroup;
 import android.widget.ScrollView;
 import android.widget.TextView;
 import android.widget.Toast;
@@ -44,20 +56,17 @@
 
     private SoundTriggerUtil mSoundTriggerUtil;
     private Random mRandom;
-    private UUID mModelUuid1 = UUID.randomUUID();
-    private UUID mModelUuid2 = UUID.randomUUID();
-    private UUID mModelUuid3 = UUID.randomUUID();
-    private UUID mVendorUuid = UUID.randomUUID();
 
-    private SoundTriggerDetector mDetector1 = null;
-    private SoundTriggerDetector mDetector2 = null;
-    private SoundTriggerDetector mDetector3 = null;
+    private Map<Integer, ModelInfo> mModelInfoMap;
+    private Map<View, Integer> mModelIdMap;
 
     private TextView mDebugView = null;
-    private int mSelectedModelId = 1;
+    private int mSelectedModelId = -1;
     private ScrollView mScrollView = null;
+    private Button mPlayTriggerButton = null;
     private PowerManager.WakeLock mScreenWakelock;
     private Handler mHandler;
+    private RadioGroup mRadioGroup;
 
     @Override
     protected void onCreate(Bundle savedInstanceState) {
@@ -66,11 +75,108 @@
         setContentView(R.layout.main);
         mDebugView = (TextView) findViewById(R.id.console);
         mScrollView = (ScrollView) findViewById(R.id.scroller_id);
+        mRadioGroup = (RadioGroup) findViewById(R.id.model_group_id);
+        mPlayTriggerButton = (Button) findViewById(R.id.play_trigger_id);
         mDebugView.setText(mDebugView.getText(), TextView.BufferType.EDITABLE);
         mDebugView.setMovementMethod(new ScrollingMovementMethod());
         mSoundTriggerUtil = new SoundTriggerUtil(this);
         mRandom = new Random();
         mHandler = new Handler();
+
+        mModelInfoMap = new HashMap();
+        mModelIdMap = new HashMap();
+
+        setVolumeControlStream(AudioManager.STREAM_MUSIC);
+
+        // Load all the models in the data dir.
+        for (File file : getFilesDir().listFiles()) {
+            // Find meta-data in .properties files, ignore everything else.
+            if (!file.getName().endsWith(".properties")) {
+                continue;
+            }
+            try {
+                Properties properties = new Properties();
+                properties.load(new FileInputStream(file));
+                createModelInfoAndWidget(properties);
+            } catch (Exception e) {
+                Log.e(TAG, "Failed to load properties file " + file.getName());
+            }
+        }
+
+        // Create a few dummy models if we didn't load anything.
+        if (mModelIdMap.isEmpty()) {
+            Properties dummyModelProperties = new Properties();
+            for (String name : new String[]{"One", "Two", "Three"}) {
+                dummyModelProperties.setProperty("name", "Model " + name);
+                createModelInfoAndWidget(dummyModelProperties);
+            }
+        }
+    }
+
+    private void createModelInfoAndWidget(Properties properties) {
+        try {
+            ModelInfo modelInfo = new ModelInfo();
+
+            if (!properties.containsKey("name")) {
+                throw new RuntimeException("must have a 'name' property");
+            }
+            modelInfo.name = properties.getProperty("name");
+
+            if (properties.containsKey("modelUuid")) {
+                modelInfo.modelUuid = UUID.fromString(properties.getProperty("modelUuid"));
+            } else {
+                modelInfo.modelUuid = UUID.randomUUID();
+            }
+
+            if (properties.containsKey("vendorUuid")) {
+                modelInfo.vendorUuid = UUID.fromString(properties.getProperty("vendorUuid"));
+            } else {
+                modelInfo.vendorUuid = UUID.randomUUID();
+            }
+
+            if (properties.containsKey("triggerAudio")) {
+                modelInfo.triggerAudioPlayer = MediaPlayer.create(this, Uri.parse(
+                        getFilesDir().getPath() + "/" + properties.getProperty("triggerAudio")));
+            }
+
+            if (properties.containsKey("dataFile")) {
+                File modelDataFile = new File(
+                        getFilesDir().getPath() + "/" + properties.getProperty("dataFile"));
+                modelInfo.modelData = new byte[(int) modelDataFile.length()];
+                FileInputStream input = new FileInputStream(modelDataFile);
+                input.read(modelInfo.modelData, 0, modelInfo.modelData.length);
+            } else {
+                modelInfo.modelData = new byte[1024];
+                mRandom.nextBytes(modelInfo.modelData);
+            }
+
+            // TODO: Add property support for keyphrase models when they're exposed by the
+            // service. Also things like how much audio they should record with the capture session
+            // provided in the callback.
+
+            // Add a widget into the radio group.
+            RadioButton button = new RadioButton(this);
+            mRadioGroup.addView(button);
+            button.setText(modelInfo.name);
+            button.setOnClickListener(new View.OnClickListener() {
+                public void onClick(View v) {
+                    onRadioButtonClicked(v);
+                }
+            });
+
+            // Update our maps containing the button -> id and id -> modelInfo.
+            int newModelId = mModelIdMap.size() + 1;
+            mModelIdMap.put(button, newModelId);
+            mModelInfoMap.put(newModelId, modelInfo);
+
+            // If we don't have something selected, select this first thing.
+            if (mSelectedModelId < 0) {
+                button.setChecked(true);
+                onRadioButtonClicked(button);
+            }
+        } catch (IOException e) {
+            Log.e(TAG, "Error parsing properties for " + properties.getProperty("name"), e);
+        }
     }
 
     private void postMessage(String msg) {
@@ -91,27 +197,15 @@
     }
 
     private synchronized UUID getSelectedUuid() {
-        if (mSelectedModelId == 2) return mModelUuid2;
-        if (mSelectedModelId == 3) return mModelUuid3;
-        return mModelUuid1;  // Default.
+        return mModelInfoMap.get(mSelectedModelId).modelUuid;
     }
 
     private synchronized void setDetector(SoundTriggerDetector detector) {
-        if (mSelectedModelId == 2) {
-            mDetector2 = detector;
-            return;
-        }
-        if (mSelectedModelId == 3) {
-            mDetector3 = detector;
-            return;
-        }
-        mDetector1 = detector;
+        mModelInfoMap.get(mSelectedModelId).detector = detector;
     }
 
     private synchronized SoundTriggerDetector getDetector() {
-        if (mSelectedModelId == 2) return mDetector2;
-        if (mSelectedModelId == 3) return mDetector3;
-        return mDetector1;
+        return mModelInfoMap.get(mSelectedModelId).detector;
     }
 
     private void screenWakeup() {
@@ -127,25 +221,29 @@
         mScreenWakelock.release();
     }
 
+    /** TODO: Should return the abstract sound model that can be then sent to the service. */
+    private GenericSoundModel createNewSoundModel() {
+        ModelInfo modelInfo = mModelInfoMap.get(mSelectedModelId);
+        return new GenericSoundModel(modelInfo.modelUuid, modelInfo.vendorUuid,
+                modelInfo.modelData);
+    }
+
     /**
      * Called when the user clicks the enroll button.
      * Performs a fresh enrollment.
      */
     public void onEnrollButtonClicked(View v) {
         postMessage("Loading model: " + mSelectedModelId);
-        // Generate a fake model to push.
-        byte[] data = new byte[1024];
-        mRandom.nextBytes(data);
-        UUID modelUuid = getSelectedUuid();
-        GenericSoundModel model = new GenericSoundModel(modelUuid, mVendorUuid, data);
+
+        GenericSoundModel model = createNewSoundModel();
 
         boolean status = mSoundTriggerUtil.addOrUpdateSoundModel(model);
         if (status) {
             Toast.makeText(
-                    this, "Successfully created sound trigger model UUID=" + modelUuid,
+                    this, "Successfully created sound trigger model UUID=" + model.uuid,
                     Toast.LENGTH_SHORT).show();
         } else {
-            Toast.makeText(this, "Failed to enroll!!!" + modelUuid, Toast.LENGTH_SHORT).show();
+            Toast.makeText(this, "Failed to enroll!!!" + model.uuid, Toast.LENGTH_SHORT).show();
         }
 
         // Test the SoundManager API.
@@ -185,11 +283,7 @@
             Toast.makeText(this, "Sound model not found!!!", Toast.LENGTH_SHORT).show();
             return;
         }
-        // Generate a fake model to push.
-        byte[] data = new byte[2048];
-        mRandom.nextBytes(data);
-        GenericSoundModel updated = new GenericSoundModel(soundModel.uuid,
-                soundModel.vendorUuid, data);
+        GenericSoundModel updated = createNewSoundModel();
         boolean status = mSoundTriggerUtil.addOrUpdateSoundModel(updated);
         if (status) {
             Toast.makeText(this, "Successfully re-enrolled, model UUID=" + updated.uuid,
@@ -237,29 +331,32 @@
     public synchronized void onRadioButtonClicked(View view) {
         // Is the button now checked?
         boolean checked = ((RadioButton) view).isChecked();
-        // Check which radio button was clicked
-        switch(view.getId()) {
-            case R.id.model_one:
-                if (checked) {
-                    mSelectedModelId = 1;
-                    postMessage("Selected model one.");
-                }
-                break;
-            case R.id.model_two:
-                if (checked) {
-                    mSelectedModelId = 2;
-                    postMessage("Selected model two.");
-                }
-                break;
-            case R.id.model_three:
-                if (checked) {
-                    mSelectedModelId = 3;
-                    postMessage("Selected model three.");
-                }
-                break;
+        if (checked) {
+            mSelectedModelId = mModelIdMap.get(view);
+            ModelInfo modelInfo = mModelInfoMap.get(mSelectedModelId);
+            postMessage("Selected " + modelInfo.name);
+
+            // Set the play trigger button to be enabled only if we actually have some audio.
+            mPlayTriggerButton.setEnabled(modelInfo.triggerAudioPlayer != null);
         }
     }
 
+    public synchronized void onPlayTriggerButtonClicked(View v) {
+        ModelInfo modelInfo = mModelInfoMap.get(mSelectedModelId);
+        modelInfo.triggerAudioPlayer.start();
+        postMessage("Playing trigger audio for " + modelInfo.name);
+    }
+
+    // Helper struct for holding information about a model.
+    private static class ModelInfo {
+      public String name;
+      public UUID modelUuid;
+      public UUID vendorUuid;
+      public MediaPlayer triggerAudioPlayer;
+      public SoundTriggerDetector detector;
+      public byte modelData[];
+    };
+
     // Implementation of SoundTriggerDetector.Callback.
     public class DetectorCallback extends SoundTriggerDetector.Callback {
         public void onAvailabilityChanged(int status) {
diff --git a/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java b/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java
index 0da1bb1..6c8be39 100644
--- a/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java
+++ b/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java
@@ -86,6 +86,155 @@
     }
 
     private Test[] mTests = new Test[] {
+            new Test("Post a group") {
+                public void run()
+                {
+                    Notification n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("Min priority group 1")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_MIN)
+                            .setGroup("group1")
+                            .build();
+                    mNM.notify(6000, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("low priority group 1")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_LOW)
+                            .setGroup("group1")
+                            .build();
+                    mNM.notify(6001, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("default priority group 1")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_DEFAULT)
+                            .setGroup("group1")
+                            .build();
+                    mNM.notify(6002, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("summary group 1")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_MIN)
+                            .setGroup("group1")
+                            .setGroupSummary(true)
+                            .build();
+                    mNM.notify(6003, n);
+                }
+            },
+            new Test("Post a group (2) w/o summary") {
+                public void run()
+                {
+                    Notification n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("Min priority group 2")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_MIN)
+                            .setGroup("group2")
+                            .build();
+                    mNM.notify(6100, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("low priority group 2")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_LOW)
+                            .setGroup("group2")
+                            .build();
+                    mNM.notify(6101, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("default priority group 2")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_DEFAULT)
+                            .setGroup("group2")
+                            .build();
+                    mNM.notify(6102, n);
+                }
+            },
+            new Test("Summary for group 2") {
+                public void run()
+                {
+                    Notification n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("summary group 2")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_MIN)
+                            .setGroup("group2")
+                            .setGroupSummary(true)
+                            .build();
+                    mNM.notify(6103, n);
+                }
+            },
+            new Test("Group up public-secret") {
+                public void run()
+                {
+                    Notification n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("public notification")
+                            .setDefaults(Notification.DEFAULT_LIGHTS|Notification.DEFAULT_VIBRATE)
+                            .setPriority(Notification.PRIORITY_DEFAULT)
+                            .setVisibility(Notification.VISIBILITY_PUBLIC)
+                            .setGroup("public-secret")
+                            .build();
+                    mNM.notify("public", 7009, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("private only notification")
+                            .setDefaults(Notification.DEFAULT_LIGHTS|Notification.DEFAULT_VIBRATE)
+                            .setPriority(Notification.PRIORITY_DEFAULT)
+                            .setVisibility(Notification.VISIBILITY_PRIVATE)
+                            .setGroup("public-secret")
+                            .build();
+                    mNM.notify("no public", 7010, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("private version of notification")
+                            .setDefaults(Notification.DEFAULT_LIGHTS|Notification.DEFAULT_VIBRATE)
+                            .setPriority(Notification.PRIORITY_DEFAULT)
+                            .setVisibility(Notification.VISIBILITY_PRIVATE)
+                            .setGroup("public-secret")
+                            .setPublicVersion(new Notification.Builder(NotificationTestList.this)
+                                    .setSmallIcon(R.drawable.icon2)
+                                    .setContentTitle("public notification of private notification")
+                                    .setPriority(Notification.PRIORITY_DEFAULT)
+                                    .setVisibility(Notification.VISIBILITY_PUBLIC)
+                                    .build())
+                            .build();
+                    mNM.notify("priv with pub", 7011, n);
+                    n = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("secret notification")
+                            .setDefaults(Notification.DEFAULT_LIGHTS|Notification.DEFAULT_VIBRATE)
+                            .setPriority(Notification.PRIORITY_DEFAULT)
+                            .setVisibility(Notification.VISIBILITY_SECRET)
+                            .setGroup("public-secret")
+                            .build();
+                    mNM.notify("secret", 7012, n);
+
+                    Notification s = new Notification.Builder(NotificationTestList.this)
+                            .setSmallIcon(R.drawable.icon2)
+                            .setContentTitle("summary group public-secret")
+                            .setLights(0xff0000ff, 1, 0)
+                            .setPriority(Notification.PRIORITY_MIN)
+                            .setGroup("public-secret")
+                            .setGroupSummary(true)
+                            .build();
+                    mNM.notify(7113, s);
+                }
+            },
+            new Test("Cancel priority autogroup") {
+                public void run()
+                {
+                    try {
+                        mNM.cancel(Integer.MAX_VALUE);
+                    } catch (Exception e) {
+                        Toast.makeText(NotificationTestList.this, "cancel failed (yay)",
+                                Toast.LENGTH_LONG).show();
+                    }
+                }
+            },
             new Test("Min priority") {
                 public void run()
                 {
@@ -95,7 +244,7 @@
                             .setLights(0xff0000ff, 1, 0)
                             .setPriority(Notification.PRIORITY_MIN)
                             .build();
-                    mNM.notify(7000, n);
+                    mNM.notify("min", 7000, n);
                 }
             },
             new Test("Min priority, high pri flag") {
@@ -123,7 +272,7 @@
                             .setLights(0xff0000ff, 1, 0)
                             .setPriority(Notification.PRIORITY_LOW)
                             .build();
-                    mNM.notify(7002, n);
+                    mNM.notify("low", 7002, n);
                 }
             },
             new Test("Default priority") {
@@ -135,7 +284,7 @@
                             .setLights(0xff0000ff, 1, 0)
                             .setPriority(Notification.PRIORITY_DEFAULT)
                             .build();
-                    mNM.notify(7004, n);
+                    mNM.notify("default", 7004, n);
                 }
             },
             new Test("High priority") {
@@ -150,7 +299,7 @@
                                     getPackageName() + "/raw/ringer"))
                             .setPriority(Notification.PRIORITY_HIGH)
                             .build();
-                    mNM.notify(7006, n);
+                    mNM.notify("high", 7006, n);
                 }
             },
             new Test("Max priority") {
@@ -166,7 +315,7 @@
                             .setPriority(Notification.PRIORITY_MAX)
                             .setFullScreenIntent(makeIntent2(), false)
                             .build();
-                    mNM.notify(7007, n);
+                    mNM.notify("max", 7007, n);
                 }
             },
             new Test("Max priority with delay") {
@@ -199,7 +348,7 @@
                             .setPriority(Notification.PRIORITY_DEFAULT)
                             .setVisibility(Notification.VISIBILITY_PUBLIC)
                             .build();
-                    mNM.notify(7009, n);
+                    mNM.notify("public", 7009, n);
                 }
             },
             new Test("private notification, no public") {
@@ -212,7 +361,7 @@
                             .setPriority(Notification.PRIORITY_DEFAULT)
                             .setVisibility(Notification.VISIBILITY_PRIVATE)
                             .build();
-                    mNM.notify(7010, n);
+                    mNM.notify("no public", 7010, n);
                 }
             },
             new Test("private notification, has public") {
@@ -231,7 +380,7 @@
                                     .setVisibility(Notification.VISIBILITY_PUBLIC)
                                     .build())
                             .build();
-                    mNM.notify(7011, n);
+                    mNM.notify("priv with pub", 7011, n);
                 }
             },
             new Test("secret notification") {
@@ -244,7 +393,7 @@
                             .setPriority(Notification.PRIORITY_DEFAULT)
                             .setVisibility(Notification.VISIBILITY_SECRET)
                             .build();
-                    mNM.notify(7012, n);
+                    mNM.notify("secret", 7012, n);
                 }
             },
         new Test("Off") {
diff --git a/tools/aapt2/java/AnnotationProcessor.cpp b/tools/aapt2/java/AnnotationProcessor.cpp
index ba74439..b7e7f90 100644
--- a/tools/aapt2/java/AnnotationProcessor.cpp
+++ b/tools/aapt2/java/AnnotationProcessor.cpp
@@ -21,7 +21,7 @@
 
 namespace aapt {
 
-void AnnotationProcessor::appendCommentLine(const std::string& comment) {
+void AnnotationProcessor::appendCommentLine(std::string& comment) {
     static const std::string sDeprecated = "@deprecated";
     static const std::string sSystemApi = "@SystemApi";
 
@@ -29,8 +29,14 @@
         mAnnotationBitMask |= kDeprecated;
     }
 
-    if (comment.find(sSystemApi) != std::string::npos) {
+    std::string::size_type idx = comment.find(sSystemApi);
+    if (idx != std::string::npos) {
         mAnnotationBitMask |= kSystemApi;
+        comment.erase(comment.begin() + idx, comment.begin() + idx + sSystemApi.size());
+    }
+
+    if (util::trimWhitespace(comment).empty()) {
+        return;
     }
 
     if (!mHasComments) {
@@ -46,7 +52,8 @@
     for (StringPiece16 line : util::tokenize(comment, u'\n')) {
         line = util::trimWhitespace(line);
         if (!line.empty()) {
-            appendCommentLine(util::utf16ToUtf8(line));
+            std::string utf8Line = util::utf16ToUtf8(line);
+            appendCommentLine(utf8Line);
         }
     }
 }
@@ -55,7 +62,8 @@
     for (StringPiece line : util::tokenize(comment, '\n')) {
         line = util::trimWhitespace(line);
         if (!line.empty()) {
-            appendCommentLine(line.toString());
+            std::string utf8Line = line.toString();
+            appendCommentLine(utf8Line);
         }
     }
 }
diff --git a/tools/aapt2/java/AnnotationProcessor.h b/tools/aapt2/java/AnnotationProcessor.h
index 0fc5b08..8309dd9 100644
--- a/tools/aapt2/java/AnnotationProcessor.h
+++ b/tools/aapt2/java/AnnotationProcessor.h
@@ -43,7 +43,6 @@
  *  /\*
  *   * This is meant to be hidden because
  *   * It is system api. Also it is @deprecated
- *   * @SystemApi
  *   *\/
  *
  * Output Annotations:
@@ -79,7 +78,7 @@
     bool mHasComments = false;
     uint32_t mAnnotationBitMask = 0;
 
-    void appendCommentLine(const std::string& line);
+    void appendCommentLine(std::string& line);
 };
 
 } // namespace aapt
diff --git a/tools/aapt2/java/AnnotationProcessor_test.cpp b/tools/aapt2/java/AnnotationProcessor_test.cpp
index d3860a5..5a39add 100644
--- a/tools/aapt2/java/AnnotationProcessor_test.cpp
+++ b/tools/aapt2/java/AnnotationProcessor_test.cpp
@@ -14,59 +14,18 @@
  * limitations under the License.
  */
 
-#include "ResourceParser.h"
-#include "ResourceTable.h"
-#include "ResourceValues.h"
 #include "java/AnnotationProcessor.h"
-#include "test/Builders.h"
-#include "test/Context.h"
-#include "xml/XmlPullParser.h"
-
-#include <gtest/gtest.h>
+#include "test/Test.h"
 
 namespace aapt {
 
-struct AnnotationProcessorTest : public ::testing::Test {
-    std::unique_ptr<IAaptContext> mContext;
-    ResourceTable mTable;
-
-    void SetUp() override {
-        mContext = test::ContextBuilder().build();
-    }
-
-    ::testing::AssertionResult parse(const StringPiece& str) {
-        ResourceParserOptions options;
-        ResourceParser parser(mContext->getDiagnostics(), &mTable, Source{}, ConfigDescription{},
-                              options);
-        std::stringstream in;
-        in << "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" << str;
-        xml::XmlPullParser xmlParser(in);
-        if (parser.parse(&xmlParser)) {
-            return ::testing::AssertionSuccess();
-        }
-        return ::testing::AssertionFailure();
-    }
-};
-
-TEST_F(AnnotationProcessorTest, EmitsDeprecated) {
-    const char* xmlInput = R"EOF(
-    <resources>
-      <declare-styleable name="foo">
-        <!-- Some comment, and it should contain
-             a marker word, something that marks
-             this resource as nor needed.
-             {@deprecated That's the marker! } -->
-        <attr name="autoText" format="boolean" />
-      </declare-styleable>
-    </resources>)EOF";
-
-    ASSERT_TRUE(parse(xmlInput));
-
-    Attribute* attr = test::getValue<Attribute>(&mTable, u"@attr/autoText");
-    ASSERT_NE(nullptr, attr);
+TEST(AnnotationProcessorTest, EmitsDeprecated) {
+    const char* comment = "Some comment, and it should contain a marker word, "
+                          "something that marks this resource as nor needed. "
+                          "{@deprecated That's the marker! }";
 
     AnnotationProcessor processor;
-    processor.appendComment(attr->getComment());
+    processor.appendComment(comment);
 
     std::stringstream result;
     processor.writeToStream(&result, "");
@@ -75,6 +34,19 @@
     EXPECT_NE(std::string::npos, annotations.find("@Deprecated"));
 }
 
+TEST(AnnotationProcessorTest, EmitsSystemApiAnnotationAndRemovesFromComment) {
+    AnnotationProcessor processor;
+    processor.appendComment("@SystemApi This is a system API");
+
+    std::stringstream result;
+    processor.writeToStream(&result, "");
+    std::string annotations = result.str();
+
+    EXPECT_NE(std::string::npos, annotations.find("@android.annotation.SystemApi"));
+    EXPECT_EQ(std::string::npos, annotations.find("@SystemApi"));
+    EXPECT_NE(std::string::npos, annotations.find("This is a system API"));
+}
+
 } // namespace aapt
 
 
diff --git a/tools/aapt2/java/ClassDefinition.h b/tools/aapt2/java/ClassDefinition.h
index 53e0f6f..d45328f 100644
--- a/tools/aapt2/java/ClassDefinition.h
+++ b/tools/aapt2/java/ClassDefinition.h
@@ -125,7 +125,7 @@
     void writeToStream(const StringPiece& prefix, bool final, std::ostream* out) const override {
         ClassMember::writeToStream(prefix, final, out);
 
-        *out << "public static final int[] " << mName << "={";
+        *out << prefix << "public static final int[] " << mName << "={";
 
         const auto begin = mElements.begin();
         const auto end = mElements.end();
diff --git a/tools/aapt2/java/JavaClassGenerator.cpp b/tools/aapt2/java/JavaClassGenerator.cpp
index 32b8600..24347a1 100644
--- a/tools/aapt2/java/JavaClassGenerator.cpp
+++ b/tools/aapt2/java/JavaClassGenerator.cpp
@@ -188,8 +188,8 @@
 
 struct StyleableAttr {
     const Reference* attrRef;
-    std::shared_ptr<Attribute> attribute;
     std::string fieldName;
+    std::unique_ptr<SymbolTable::Symbol> symbol;
 };
 
 static bool lessStyleableAttr(const StyleableAttr& lhs, const StyleableAttr& rhs) {
@@ -245,8 +245,9 @@
         // legal values for this attribute.
         const SymbolTable::Symbol* symbol = mContext->getExternalSymbols()->findByReference(
                 mangledReference);
-        if (symbol) {
-            styleableAttr.attribute = symbol->attribute;
+        if (symbol && symbol->attribute) {
+            // Copy the symbol data structure because the returned instance can be destroyed.
+            styleableAttr.symbol = util::make_unique<SymbolTable::Symbol>(*symbol);
         }
         sortedAttributes.push_back(std::move(styleableAttr));
     }
@@ -273,6 +274,16 @@
                 "<tr><th>Attribute</th><th>Description</th></tr>\n";
 
         for (const StyleableAttr& entry : sortedAttributes) {
+            if (!entry.symbol) {
+                continue;
+            }
+
+            if (mOptions.types == JavaClassGeneratorOptions::SymbolTypes::kPublic &&
+                    !entry.symbol->isPublic) {
+                // Don't write entries for non-public attributes.
+                continue;
+            }
+
             const ResourceName& attrName = entry.attrRef->name.value();
             styleableComment << "<tr><td>";
             styleableComment << "<code>{@link #"
@@ -284,14 +295,30 @@
             styleableComment << "</td>";
 
             styleableComment << "<td>";
-            if (entry.attribute) {
-                styleableComment << entry.attribute->getComment();
+
+            // Only use the comment up until the first '.'. This is to stay compatible with
+            // the way old AAPT did it (presumably to keep it short and to avoid including
+            // annotations like @hide which would affect this Styleable).
+            StringPiece16 attrCommentLine = entry.symbol->attribute->getComment();
+            auto iter = std::find(attrCommentLine.begin(), attrCommentLine.end(), u'.');
+            if (iter != attrCommentLine.end()) {
+                attrCommentLine = attrCommentLine.substr(
+                        0, (iter - attrCommentLine.begin()) + 1);
             }
-            styleableComment << "</td></tr>\n";
+            styleableComment << attrCommentLine << "</td></tr>\n";
         }
         styleableComment << "</table>\n";
 
         for (const StyleableAttr& entry : sortedAttributes) {
+            if (!entry.symbol) {
+                continue;
+            }
+
+            if (mOptions.types == JavaClassGeneratorOptions::SymbolTypes::kPublic &&
+                    !entry.symbol->isPublic) {
+                // Don't write entries for non-public attributes.
+                continue;
+            }
             styleableComment << "@see #" << entry.fieldName << "\n";
         }
 
@@ -310,6 +337,17 @@
     // Now we emit the indices into the array.
     for (size_t i = 0; i < attrCount; i++) {
         const StyleableAttr& styleableAttr = sortedAttributes[i];
+
+        if (!styleableAttr.symbol) {
+            continue;
+        }
+
+        if (mOptions.types == JavaClassGeneratorOptions::SymbolTypes::kPublic &&
+                !styleableAttr.symbol->isPublic) {
+            // Don't write entries for non-public attributes.
+            continue;
+        }
+
         const ResourceName& attrName = styleableAttr.attrRef->name.value();
 
         StringPiece16 packageName = attrName.package;
@@ -323,8 +361,8 @@
         AnnotationProcessor* attrProcessor = indexMember->getCommentBuilder();
 
         StringPiece16 comment = styleableAttr.attrRef->getComment();
-        if (styleableAttr.attribute && comment.empty()) {
-            comment = styleableAttr.attribute->getComment();
+        if (styleableAttr.symbol->attribute && comment.empty()) {
+            comment = styleableAttr.symbol->attribute->getComment();
         }
 
         if (!comment.empty()) {
@@ -342,10 +380,8 @@
 
         attrProcessor->appendNewLine();
 
-        if (styleableAttr.attribute) {
-            addAttributeFormatDoc(attrProcessor, styleableAttr.attribute.get());
-            attrProcessor->appendNewLine();
-        }
+        addAttributeFormatDoc(attrProcessor, styleableAttr.symbol->attribute.get());
+        attrProcessor->appendNewLine();
 
         std::stringstream doclavaName;
         doclavaName << "@attr name " << packageName << ":" << attrName.entry;;
diff --git a/tools/aapt2/java/JavaClassGenerator_test.cpp b/tools/aapt2/java/JavaClassGenerator_test.cpp
index 370e78a..7d0aa83 100644
--- a/tools/aapt2/java/JavaClassGenerator_test.cpp
+++ b/tools/aapt2/java/JavaClassGenerator_test.cpp
@@ -43,7 +43,8 @@
     std::unique_ptr<ResourceTable> table = test::ResourceTableBuilder()
             .setPackageId(u"android", 0x01)
             .addSimple(u"@android:id/hey-man", ResourceId(0x01020000))
-            .addSimple(u"@android:attr/cool.attr", ResourceId(0x01010000))
+            .addValue(u"@android:attr/cool.attr", ResourceId(0x01010000),
+                      test::AttributeBuilder(false).build())
             .addValue(u"@android:styleable/hey.dude", ResourceId(0x01030000),
                       test::StyleableBuilder()
                               .addItem(u"@android:attr/cool.attr", ResourceId(0x01010000))
@@ -199,8 +200,10 @@
     std::unique_ptr<ResourceTable> table = test::ResourceTableBuilder()
                 .setPackageId(u"android", 0x01)
                 .setPackageId(u"com.lib", 0x02)
-                .addSimple(u"@android:attr/bar", ResourceId(0x01010000))
-                .addSimple(u"@com.lib:attr/bar", ResourceId(0x02010000))
+                .addValue(u"@android:attr/bar", ResourceId(0x01010000),
+                          test::AttributeBuilder(false).build())
+                .addValue(u"@com.lib:attr/bar", ResourceId(0x02010000),
+                           test::AttributeBuilder(false).build())
                 .addValue(u"@android:styleable/foo", ResourceId(0x01030000),
                           test::StyleableBuilder()
                                   .addItem(u"@android:attr/bar", ResourceId(0x01010000))
diff --git a/tools/aapt2/java/ManifestClassGenerator_test.cpp b/tools/aapt2/java/ManifestClassGenerator_test.cpp
index e7210db..d3bca70 100644
--- a/tools/aapt2/java/ManifestClassGenerator_test.cpp
+++ b/tools/aapt2/java/ManifestClassGenerator_test.cpp
@@ -126,7 +126,6 @@
 R"EOF(    /**
      * This is a private permission for system only!
      * @hide
-     * @SystemApi
      */
     @android.annotation.SystemApi
     public static final String SECRET="android.permission.SECRET";)EOF";
diff --git a/tools/aapt2/process/SymbolTable.h b/tools/aapt2/process/SymbolTable.h
index 0a6a4a5..e684bb0 100644
--- a/tools/aapt2/process/SymbolTable.h
+++ b/tools/aapt2/process/SymbolTable.h
@@ -51,9 +51,28 @@
 class SymbolTable {
 public:
     struct Symbol {
+        Symbol() : Symbol(Maybe<ResourceId>{}) {
+        }
+
+        Symbol(const Maybe<ResourceId>& i) : Symbol(i, nullptr) {
+        }
+
+        Symbol(const Maybe<ResourceId>& i, const std::shared_ptr<Attribute>& attr) :
+                Symbol(i, attr, false) {
+        }
+
+        Symbol(const Maybe<ResourceId>& i, const std::shared_ptr<Attribute>& attr, bool pub) :
+                id(i), attribute(attr), isPublic(pub) {
+        }
+
+        Symbol(const Symbol&) = default;
+        Symbol(Symbol&&) = default;
+        Symbol& operator=(const Symbol&) = default;
+        Symbol& operator=(Symbol&&) = default;
+
         Maybe<ResourceId> id;
         std::shared_ptr<Attribute> attribute;
-        bool isPublic;
+        bool isPublic = false;
     };
 
     SymbolTable() : mCache(200), mIdCache(200) {
diff --git a/tools/layoutlib/bridge/src/android/graphics/FontFamily_Delegate.java b/tools/layoutlib/bridge/src/android/graphics/FontFamily_Delegate.java
index 7412bc2..50efc7f 100644
--- a/tools/layoutlib/bridge/src/android/graphics/FontFamily_Delegate.java
+++ b/tools/layoutlib/bridge/src/android/graphics/FontFamily_Delegate.java
@@ -245,6 +245,13 @@
         return sFontLocation;
     }
 
+    // ---- delegate methods ----
+    @LayoutlibDelegate
+    /*package*/ static boolean addFont(FontFamily thisFontFamily, String path, int ttcIndex) {
+        final FontFamily_Delegate delegate = getDelegate(thisFontFamily.mNativePtr);
+        return delegate != null && delegate.addFont(path, ttcIndex);
+    }
+
     // ---- native methods ----
 
     @LayoutlibDelegate
@@ -270,16 +277,8 @@
     }
 
     @LayoutlibDelegate
-    /*package*/ static boolean nAddFont(long nativeFamily, final String path, int ttcIndex) {
-        // FIXME: support ttc fonts. Hack JRE??
-        final FontFamily_Delegate delegate = getDelegate(nativeFamily);
-        if (delegate != null) {
-            if (sFontLocation == null) {
-                delegate.mPostInitRunnables.add(() -> delegate.addFont(path));
-                return true;
-            }
-            return delegate.addFont(path);
-        }
+    /*package*/ static boolean nAddFont(long nativeFamily, ByteBuffer font, int ttcIndex) {
+        assert false : "The only client of this method has been overriden.";
         return false;
     }
 
@@ -390,6 +389,15 @@
         mPostInitRunnables = null;
     }
 
+    private boolean addFont(final String path, int ttcIndex) {
+        // FIXME: support ttc fonts. Hack JRE??
+        if (sFontLocation == null) {
+            mPostInitRunnables.add(() -> addFont(path));
+            return true;
+        }
+        return addFont(path);
+    }
+
      private boolean addFont(@NonNull String path) {
          return addFont(path, DEFAULT_FONT_WEIGHT, path.endsWith(FONT_SUFFIX_ITALIC));
      }
diff --git a/tools/layoutlib/bridge/src/android/util/PathParser_Delegate.java b/tools/layoutlib/bridge/src/android/util/PathParser_Delegate.java
index 6c34c70..6d3bb4c 100644
--- a/tools/layoutlib/bridge/src/android/util/PathParser_Delegate.java
+++ b/tools/layoutlib/bridge/src/android/util/PathParser_Delegate.java
@@ -64,15 +64,14 @@
     }
 
     @LayoutlibDelegate
-    /*package*/ static boolean nParseStringForPath(long pathPtr, @NonNull String pathString, int
+    /*package*/ static void nParseStringForPath(long pathPtr, @NonNull String pathString, int
             stringLength) {
         Path_Delegate path_delegate = Path_Delegate.getDelegate(pathPtr);
         if (path_delegate == null) {
-            return false;
+            return;
         }
         assert pathString.length() == stringLength;
         PathDataNode.nodesToPath(createNodesFromPathData(pathString), path_delegate);
-        return true;
     }
 
     @LayoutlibDelegate
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/BridgeRenderSession.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/BridgeRenderSession.java
index fea633e..308488a 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/BridgeRenderSession.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/BridgeRenderSession.java
@@ -70,23 +70,6 @@
     }
 
     @Override
-    public Map<String, String> getDefaultProperties(Object viewObject) {
-        return mSession.getDefaultProperties(viewObject);
-    }
-
-    @Override
-    public Result getProperty(Object objectView, String propertyName) {
-        // pass
-        return super.getProperty(objectView, propertyName);
-    }
-
-    @Override
-    public Result setProperty(Object objectView, String propertyName, String propertyValue) {
-        // pass
-        return super.setProperty(objectView, propertyName, propertyValue);
-    }
-
-    @Override
     public Result render(long timeout, boolean forceMeasure) {
         try {
             Bridge.prepareThread();
@@ -213,6 +196,10 @@
         }
     }
 
+    public RenderSessionImpl getSessionImpl() {
+        return mSession;
+    }
+
     /*package*/ BridgeRenderSession(RenderSessionImpl scene, Result lastResult) {
         mSession = scene;
         if (scene != null) {
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java
index 89272fa..fd95bd5 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java
@@ -27,6 +27,7 @@
 import com.android.ide.common.rendering.api.StyleResourceValue;
 import com.android.layoutlib.bridge.Bridge;
 import com.android.layoutlib.bridge.BridgeConstants;
+import com.android.layoutlib.bridge.android.PropertiesMap.Property;
 import com.android.layoutlib.bridge.android.view.WindowManagerImpl;
 import com.android.layoutlib.bridge.impl.ParserFactory;
 import com.android.layoutlib.bridge.impl.Stack;
@@ -275,7 +276,7 @@
         return mRenderResources;
     }
 
-    public Map<String, String> getDefaultPropMap(Object key) {
+    public PropertiesMap getDefaultPropMap(Object key) {
         return mDefaultPropMaps.get(key);
     }
 
@@ -731,16 +732,10 @@
                 Bridge.getLog().error(LayoutLog.TAG_RESOURCES_RESOLVE,
                         "Failed to find the style corresponding to the id " + defStyleAttr, null);
             } else {
-                if (defaultPropMap != null) {
-                    String defStyleName = defStyleAttribute.getFirst();
-                    if (defStyleAttribute.getSecond()) {
-                        defStyleName = "android:" + defStyleName;
-                    }
-                    defaultPropMap.put("style", defStyleName);
-                }
+                String defStyleName = defStyleAttribute.getFirst();
 
                 // look for the style in the current theme, and its parent:
-                ResourceValue item = mRenderResources.findItemInTheme(defStyleAttribute.getFirst(),
+                ResourceValue item = mRenderResources.findItemInTheme(defStyleName,
                         defStyleAttribute.getSecond());
 
                 if (item != null) {
@@ -750,6 +745,12 @@
                     if (item instanceof StyleResourceValue) {
                         defStyleValues = (StyleResourceValue) item;
                     }
+                    if (defaultPropMap != null) {
+                        if (defStyleAttribute.getSecond()) {
+                            defStyleName = "android:" + defStyleName;
+                        }
+                        defaultPropMap.put("style", new Property(defStyleName, item.getValue()));
+                    }
                 } else {
                     Bridge.getLog().error(LayoutLog.TAG_RESOURCES_RESOLVE_THEME_ATTR,
                             String.format(
@@ -776,7 +777,8 @@
                         item = mRenderResources.getStyle(value.getSecond(), isFrameworkRes);
                         if (item != null) {
                             if (defaultPropMap != null) {
-                                defaultPropMap.put("style", item.getName());
+                                String name = item.getName();
+                                defaultPropMap.put("style", new Property(name, name));
                             }
 
                             defStyleValues = item;
@@ -855,13 +857,14 @@
                     // if we found a value, we make sure this doesn't reference another value.
                     // So we resolve it.
                     if (resValue != null) {
-                        // put the first default value, before the resolution.
-                        if (defaultPropMap != null) {
-                            defaultPropMap.put(attrName, resValue.getValue());
-                        }
-
+                        String preResolve = resValue.getValue();
                         resValue = mRenderResources.resolveResValue(resValue);
 
+                        if (defaultPropMap != null) {
+                            defaultPropMap.put(attrName,
+                                    new Property(preResolve, resValue.getValue()));
+                        }
+
                         // If the value is a reference to another theme attribute that doesn't
                         // exist, we should log a warning and omit it.
                         String val = resValue.getValue();
@@ -949,10 +952,11 @@
 
                 if (resValue != null) {
                     // Add it to defaultPropMap before resolving
-                    defaultPropMap.put(attrName, resValue.getValue());
+                    String preResolve = resValue.getValue();
                     // resolve it to make sure there are no references left.
-                    ta.bridgeSetValue(i, attrName, attribute.getSecond(),
-                            mRenderResources.resolveResValue(resValue));
+                    resValue = mRenderResources.resolveResValue(resValue);
+                    ta.bridgeSetValue(i, attrName, attribute.getSecond(), resValue);
+                    defaultPropMap.put(attrName, new Property(preResolve, resValue.getValue()));
                 }
             }
         }
@@ -1915,11 +1919,4 @@
         }
 
     }
-
-    /**
-     * An alias used for the value in {@code {@link #mDefaultPropMaps}}
-     */
-    private static class PropertiesMap extends HashMap<String, String> {
-    }
-
 }
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/PropertiesMap.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/PropertiesMap.java
new file mode 100644
index 0000000..a38d579
--- /dev/null
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/PropertiesMap.java
@@ -0,0 +1,37 @@
+/*
+ * 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 com.android.layoutlib.bridge.android;
+
+import com.android.layoutlib.bridge.android.PropertiesMap.Property;
+
+import java.util.HashMap;
+
+/**
+ * An alias used for the value in {@link BridgeContext#mDefaultPropMaps}
+ */
+public class PropertiesMap extends HashMap<String, Property> {
+
+    public static class Property {
+        public final String resource;
+        public final String value;
+
+        public Property(String resource, String value) {
+            this.resource = resource;
+            this.value = value;
+        }
+    }
+}
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderAction.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderAction.java
index 0c53753..2d38831 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderAction.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderAction.java
@@ -286,7 +286,7 @@
         return mParams;
     }
 
-    protected BridgeContext getContext() {
+    public BridgeContext getContext() {
         return mContext;
     }
 
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderSessionImpl.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderSessionImpl.java
index 866b248..11fabc6 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderSessionImpl.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/RenderSessionImpl.java
@@ -1415,10 +1415,6 @@
         return mSystemViewInfoList;
     }
 
-    public Map<String, String> getDefaultProperties(Object viewObject) {
-        return getContext().getDefaultPropMap(viewObject);
-    }
-
     public void setScene(RenderSession session) {
         mScene = session;
     }
diff --git a/tools/layoutlib/create/src/com/android/tools/layoutlib/create/CreateInfo.java b/tools/layoutlib/create/src/com/android/tools/layoutlib/create/CreateInfo.java
index 483bddc..061bed7 100644
--- a/tools/layoutlib/create/src/com/android/tools/layoutlib/create/CreateInfo.java
+++ b/tools/layoutlib/create/src/com/android/tools/layoutlib/create/CreateInfo.java
@@ -192,6 +192,7 @@
         "android.graphics.BitmapFactory#setDensityFromOptions",
         "android.graphics.drawable.AnimatedVectorDrawable$VectorDrawableAnimatorRT#useLastSeenTarget",
         "android.graphics.drawable.GradientDrawable#buildRing",
+        "android.graphics.FontFamily#addFont",
         "android.graphics.Typeface#getSystemFontConfigLocation",
         "android.graphics.Typeface#makeFamilyFromParsed",
         "android.os.Handler#sendMessageAtTime",
diff --git a/wifi/java/android/net/wifi/IWifiManager.aidl b/wifi/java/android/net/wifi/IWifiManager.aidl
index 0f84506..be5b8fc 100644
--- a/wifi/java/android/net/wifi/IWifiManager.aidl
+++ b/wifi/java/android/net/wifi/IWifiManager.aidl
@@ -149,7 +149,7 @@
     void setAllowScansWithTraffic(int enabled);
     int getAllowScansWithTraffic();
 
-    boolean enableAutoJoinWhenAssociated(boolean enabled);
+    boolean setEnableAutoJoinWhenAssociated(boolean enabled);
     boolean getEnableAutoJoinWhenAssociated();
 
     void enableWifiConnectivityManager(boolean enabled);
diff --git a/wifi/java/android/net/wifi/WifiManager.java b/wifi/java/android/net/wifi/WifiManager.java
index 6984fe2..1cd32b6 100644
--- a/wifi/java/android/net/wifi/WifiManager.java
+++ b/wifi/java/android/net/wifi/WifiManager.java
@@ -2700,9 +2700,9 @@
      * @return true -- if set successful false -- if set failed
      * @hide
      */
-    public boolean enableAutoJoinWhenAssociated(boolean enabled) {
+    public boolean setEnableAutoJoinWhenAssociated(boolean enabled) {
         try {
-            return mService.enableAutoJoinWhenAssociated(enabled);
+            return mService.setEnableAutoJoinWhenAssociated(enabled);
         } catch (RemoteException e) {
             throw e.rethrowFromSystemServer();
         }